-
Notifications
You must be signed in to change notification settings - Fork 2
Commit
This commit does not belong to any branch on this repository, and may belong to a fork outside of the repository.
Merge pull request #392 from nulib/deploy/staging
Add IIIF search and collection sharing, address AI local storage bug.
Showing
47 changed files
with
802 additions
and
151 deletions.
There are no files selected for viewing
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,56 @@ | ||
import { render, screen } from "@/test-utils"; | ||
|
||
import IIIFShare from "@/components/Shared/IIIF/Share"; | ||
import React from "react"; | ||
|
||
describe("IIIFShare", () => { | ||
const uri = | ||
"https://iiif.io/api/cookbook/recipe/0001-mvm-image/manifest.json"; | ||
|
||
it("renders a dropdown with IIIF viewers", async () => { | ||
render(<IIIFShare uri={uri} />); | ||
|
||
// Verify that initial elements are present | ||
expect(screen.getByTestId("iiif-share")).toBeInTheDocument(); | ||
|
||
const trigger = screen.getByTestId("iiif-share-trigger"); | ||
expect(trigger).toHaveTextContent("View as IIIF"); | ||
}); | ||
|
||
it("renders dropdown content with expected items", async () => { | ||
render(<IIIFShare uri={uri} dropdownMenuProps={{ open: true }} />); | ||
|
||
const content = screen.getByTestId("iiif-share-content"); | ||
expect(screen.getByText("View in...")).toBeInTheDocument(); | ||
|
||
const links = Array.from(content.querySelectorAll("a")); | ||
const expectedLinks = { | ||
"Clover IIIF": | ||
"https://samvera-labs.github.io/clover-iiif/docs/viewer/demo?iiif-content=https%3A%2F%2Fiiif.io%2Fapi%2Fcookbook%2Frecipe%2F0001-mvm-image%2Fmanifest.json", | ||
Mirador: | ||
"https://projectmirador.org/embed?iiif-content=https%3A%2F%2Fiiif.io%2Fapi%2Fcookbook%2Frecipe%2F0001-mvm-image%2Fmanifest.json", | ||
Theseus: | ||
"https://theseusviewer.org/?iiif-content=https%3A%2F%2Fiiif.io%2Fapi%2Fcookbook%2Frecipe%2F0001-mvm-image%2Fmanifest.json", | ||
"View Raw JSON": uri, | ||
"What is IIIF?": "https://iiif.io/get-started/why-iiif/", | ||
}; | ||
|
||
// verify that the links have the expected hrefs | ||
expect(links.length).toEqual(Object.keys(expectedLinks).length); | ||
links.forEach((link) => { | ||
expect(link).toBeInTheDocument(); | ||
expect(link).toBeInstanceOf(HTMLAnchorElement); | ||
expect(link).toHaveAttribute("target", "_blank"); | ||
const key = link.textContent as keyof typeof expectedLinks; | ||
const expectedHref = expectedLinks[key]; | ||
if (expectedHref) { | ||
expect(link).toHaveAttribute("href", expectedHref); | ||
} | ||
}); | ||
|
||
// verify that the copy button is present | ||
const copyText = screen.getByText("Copy IIIF JSON"); | ||
expect(copyText).toBeInTheDocument(); | ||
expect(copyText).toBeInstanceOf(HTMLButtonElement); | ||
}); | ||
}); |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,204 @@ | ||
import * as Dropdown from "@radix-ui/react-dropdown-menu"; | ||
|
||
import { IconChevronDown, IconExternalLink } from "../SVG/Icons"; | ||
|
||
import CopyText from "../CopyText"; | ||
import IIIFLogo from "../SVG/IIIF"; | ||
import IIIFViewerLink from "./ViewerLink"; | ||
import Icon from "../Icon"; | ||
import Link from "next/link"; | ||
import { styled } from "@/stitches.config"; | ||
|
||
const IIIFShare = ({ | ||
uri, | ||
dropdownMenuProps, | ||
}: { | ||
uri: string; | ||
dropdownMenuProps?: Dropdown.DropdownMenuProps; | ||
}) => { | ||
return ( | ||
<StyledIIIFShare data-iiif-uri={uri} data-testid="iiif-share"> | ||
<Dropdown.Root {...dropdownMenuProps}> | ||
<Dropdown.Trigger data-testid="iiif-share-trigger"> | ||
<Icon> | ||
<IIIFLogo /> | ||
</Icon> | ||
<em>View as IIIF</em> | ||
<Icon> | ||
<IconChevronDown /> | ||
</Icon> | ||
</Dropdown.Trigger> | ||
<StyledIIIFShareContent | ||
data-testid="iiif-share-content" | ||
side="bottom" | ||
sideOffset={3} | ||
collisionPadding={19} | ||
> | ||
<StyledDropdownLabel>View in...</StyledDropdownLabel> | ||
<Dropdown.Item> | ||
<IIIFViewerLink | ||
viewer={{ | ||
label: "Clover IIIF", | ||
href: "https://samvera-labs.github.io/clover-iiif/docs/viewer/demo", | ||
}} | ||
uri={uri} | ||
/> | ||
</Dropdown.Item> | ||
<Dropdown.Item> | ||
<IIIFViewerLink | ||
viewer={{ | ||
label: "Mirador", | ||
href: "https://projectmirador.org/embed", | ||
}} | ||
uri={uri} | ||
/> | ||
</Dropdown.Item> | ||
<Dropdown.Item> | ||
<IIIFViewerLink | ||
viewer={{ | ||
label: "Theseus", | ||
href: "https://theseusviewer.org", | ||
}} | ||
uri={uri} | ||
/> | ||
</Dropdown.Item> | ||
<StyledDropdownSeparator /> | ||
<Dropdown.Item> | ||
<Link href={uri} target="_blank" rel="noreferrer"> | ||
View Raw JSON | ||
</Link> | ||
</Dropdown.Item> | ||
<Dropdown.Item> | ||
<CopyText textPrompt="Copy IIIF JSON" textToCopy={uri} /> | ||
</Dropdown.Item> | ||
<StyledDropdownSeparator /> | ||
<Dropdown.Item> | ||
<Link | ||
href="https://iiif.io/get-started/why-iiif/" | ||
target="_blank" | ||
rel="noreferrer" | ||
data-id="what-is-iiif" | ||
> | ||
What is IIIF? | ||
<Icon | ||
style={{ | ||
display: "inline-flex", | ||
width: "12px", | ||
height: "12px", | ||
color: "$black50", | ||
fill: "$black50", | ||
marginLeft: "0.25em", | ||
}} | ||
hasSVGPadding={false} | ||
> | ||
<IconExternalLink /> | ||
</Icon> | ||
</Link> | ||
</Dropdown.Item> | ||
</StyledIIIFShareContent> | ||
</Dropdown.Root> | ||
</StyledIIIFShare> | ||
); | ||
}; | ||
|
||
const StyledIIIFShare = styled("div", { | ||
position: "relative", | ||
zIndex: 1, | ||
|
||
"> button": { | ||
backgroundColor: "transparent", | ||
color: "$black50", | ||
fontFamily: "$northwesternSansRegular", | ||
fontSize: "$gr3", | ||
borderRadius: "38px", | ||
border: "none", | ||
display: "flex", | ||
alignItems: "center", | ||
justifyContent: "space-between", | ||
cursor: "pointer", | ||
gap: "$gr1", | ||
padding: "0 $gr1", | ||
margin: "0", | ||
|
||
"> span": { | ||
svg: { | ||
padding: "7px", | ||
path: { | ||
fill: "$purple !important", | ||
}, | ||
}, | ||
|
||
"&:last-child": { | ||
display: "inline-flex", | ||
alignItems: "center", | ||
gap: "$gr1", | ||
|
||
"svg path": { | ||
stroke: "$black50 !important", | ||
fill: "none !important", | ||
}, | ||
}, | ||
}, | ||
|
||
em: { | ||
fontStyle: "normal", | ||
display: "inline-flex", | ||
marginBottom: "-3px", | ||
}, | ||
|
||
"&:hover, &:active ": { | ||
color: "$purple", | ||
fill: "$black", | ||
backgroundColor: "$purple10", | ||
|
||
"> span:last-child svg path": { | ||
stroke: "$purple !important", | ||
}, | ||
}, | ||
}, | ||
}); | ||
|
||
const StyledIIIFShareContent = styled(Dropdown.Content, { | ||
zIndex: 1, | ||
backgroundColor: "$white", | ||
padding: "$gr3", | ||
borderRadius: "3px", | ||
boxShadow: "5px 5px 19px 0 #0002", | ||
display: "flex", | ||
flexDirection: "column", | ||
fontSize: "$gr2 ", | ||
minWidth: "160px", | ||
gap: "$gr2", | ||
|
||
a: { | ||
color: "$purple", | ||
display: "flex", | ||
|
||
svg: { | ||
color: "$purple", | ||
fill: "$purple", | ||
}, | ||
}, | ||
|
||
button: { | ||
fontSize: "$gr2", | ||
margin: "0 !important", | ||
padding: "0 !important", | ||
fontWeight: "400", | ||
lineHeight: "inherit !important", | ||
textDecoration: "none", | ||
color: "$purple", | ||
}, | ||
}); | ||
|
||
const StyledDropdownLabel = styled(Dropdown.Separator, { | ||
fontSize: "$gr2 ", | ||
color: "$black50", | ||
}); | ||
|
||
const StyledDropdownSeparator = styled(Dropdown.Separator, { | ||
height: "1px", | ||
backgroundColor: "$gray6", | ||
}); | ||
|
||
export default IIIFShare; |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,36 @@ | ||
import { render, screen } from "@testing-library/react"; | ||
|
||
import React from "react"; | ||
import ViewerLink from "./ViewerLink"; | ||
|
||
describe("ViewerLink", () => { | ||
const uri = | ||
"https://iiif.io/api/cookbook/recipe/0001-mvm-image/manifest.json"; | ||
const viewer = { | ||
label: "IIIF Viewer", | ||
href: "https://example.org/iiif-viewer", | ||
}; | ||
|
||
it("renders an `<a>` element to IIIF Viewer", () => { | ||
render(<ViewerLink viewer={viewer} uri={uri} />); | ||
expect(screen.getByText(viewer.label)).toBeInTheDocument(); | ||
expect(screen.getByText(viewer.label).closest("a")).toHaveAttribute( | ||
"href", | ||
`${viewer.href}?iiif-content=${encodeURIComponent(uri)}`, | ||
); | ||
}); | ||
|
||
it("renders an `<a>` element to IIIF Viewer with custom iiif-content param", () => { | ||
render( | ||
<ViewerLink | ||
viewer={{ ...viewer, iiifContentParam: "manifest" }} | ||
uri={uri} | ||
/>, | ||
); | ||
expect(screen.getByText(viewer.label)).toBeInTheDocument(); | ||
expect(screen.getByText(viewer.label).closest("a")).toHaveAttribute( | ||
"href", | ||
`${viewer.href}?manifest=${encodeURIComponent(uri)}`, | ||
); | ||
}); | ||
}); |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,26 @@ | ||
import Link from "next/link"; | ||
|
||
interface IIIFViewerLinkProps { | ||
viewer: { | ||
label: string; | ||
href: string; | ||
iiifContentParam?: string; | ||
}; | ||
uri: string; | ||
} | ||
|
||
const IIIFViewerLink: React.FC<IIIFViewerLinkProps> = ({ viewer, uri }) => { | ||
const iiifContent = new URL(viewer.href); | ||
iiifContent.searchParams.set( | ||
viewer.iiifContentParam ? viewer.iiifContentParam : "iiif-content", | ||
uri, | ||
); | ||
|
||
return ( | ||
<Link href={iiifContent.toString()} target="_blank" rel="noreferrer"> | ||
{viewer.label} | ||
</Link> | ||
); | ||
}; | ||
|
||
export default IIIFViewerLink; |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,46 @@ | ||
import { DC_API_SEARCH_URL } from "@/lib/constants/endpoints"; | ||
import { URLSearchParams } from "url"; | ||
import { iiifSearchUri } from "@/lib/dc-api"; | ||
|
||
describe("iiifSearchUri", () => { | ||
it("returns the expected uri", () => { | ||
const query = { q: "Joan Baez" }; | ||
const uri = new URL(iiifSearchUri(query)); | ||
const params = new URLSearchParams(uri.search); | ||
|
||
// check that the URI has the expected origin and path | ||
expect(DC_API_SEARCH_URL).toContain(uri.origin); | ||
expect(DC_API_SEARCH_URL).toContain(uri.pathname); | ||
|
||
// check that the query string has the expected params | ||
expect(params.get("query")).toEqual("Joan Baez"); | ||
expect(params.get("as")).toEqual("iiif"); | ||
}); | ||
|
||
it("returns the expected uri with a custom size", () => { | ||
const query = { q: "John Fahey" }; | ||
const uri = new URL(iiifSearchUri(query, 100)); | ||
const params = new URLSearchParams(uri.search); | ||
|
||
// check that the size param is set to 100 | ||
expect(params.get("query")).toEqual("John Fahey"); | ||
expect(params.get("as")).toEqual("iiif"); | ||
expect(params.get("size")).toEqual("100"); | ||
}); | ||
|
||
it("returns the expected uri with appended facets as params", () => { | ||
const query = { | ||
q: "Muddy Waters", | ||
workType: "Image", | ||
genre: "photographs", | ||
}; | ||
const uri = new URL(iiifSearchUri(query)); | ||
const params = new URLSearchParams(uri.search); | ||
|
||
// check that the facets are appended as params | ||
expect(params.get("query")).toEqual("Muddy Waters"); | ||
expect(params.get("as")).toEqual("iiif"); | ||
expect(params.get("workType")).toEqual("Image"); | ||
expect(params.get("genre")).toEqual("photographs"); | ||
}); | ||
}); |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Oops, something went wrong.
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,22 @@ | ||
import { test as base, expect } from "@playwright/test"; | ||
|
||
const WORK_404_ID = "00000000-0000-0000-0000-000000000000"; | ||
|
||
const test = base.extend({}); | ||
|
||
test.describe("404 page component", async () => { | ||
test.beforeEach(async ({ page }) => { | ||
await page.goto(`/items/${WORK_404_ID}`); | ||
}); | ||
|
||
test("renders the 404 page", async ({ page }) => { | ||
await expect(page).toHaveURL(`/items/${WORK_404_ID}`); | ||
|
||
const figure = await page.locator("main .swiper figure"); | ||
|
||
await expect(figure.locator(".slide-label")).toHaveText("Page Not Found"); | ||
await expect(figure.locator(".slide-summary")).toHaveText( | ||
"Sorry the page you are looking for does not exist. It's possible the resource, work, or collection is no longer available. If you think you reached this page in error, please contact us.", | ||
); | ||
}); | ||
}); |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -1,7 +1,13 @@ | ||
import { type Page } from "@playwright/test"; | ||
|
||
export const CANARY_WORK_ID = "cb8a19a7-3dec-47f3-80c0-12872ae61f8f"; | ||
|
||
export class WorkPage { | ||
readonly route: string = "/items"; | ||
readonly route: string = `/items/${CANARY_WORK_ID}`; | ||
|
||
constructor(public readonly page: Page) {} | ||
|
||
async goto() { | ||
await this.page.goto(this.route); | ||
} | ||
} |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters