@digitalculture/ochre-sdk 0.1.21 → 0.1.23

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
package/README.md CHANGED
@@ -1,15 +1,45 @@
1
1
  # OCHRE SDK
2
2
 
3
- A JavaScript/TypeScript SDK for working with OCHRE (Online Cultural and Historical Research Environment) data.
3
+ This is the OCHRE JavaScript/TypeScript SDK for interacting with OCHRE (Online Cultural and Historical Research Environment) data.
4
4
 
5
5
  ## Installation
6
6
 
7
7
  ```bash
8
- pnpm add @uchicago/ochre
8
+ pnpm add @digital-culture/ochre-sdk
9
+ ```
10
+
9
11
  or
10
- npm install @uchicago/ochre
12
+
13
+ ```bash
14
+ npm install @digital-culture/ochre-sdk
15
+ ```
16
+
11
17
  or
12
- bun install @uchicago/ochre
18
+
19
+ ```bash
20
+ bun add @digital-culture/ochre-sdk
21
+ ```
22
+
23
+ ## Start development server
24
+
25
+ From the root directory of the project, run the following command:
26
+
27
+ ```bash
28
+ pnpm run dev:ochre-sdk
29
+ ```
30
+
31
+ ## Build production server
32
+
33
+ From the root directory of the project, run the following command:
34
+
35
+ ```bash
36
+ pnpm run ci
37
+ ```
38
+
39
+ ## Release new version to NPM
40
+
41
+ ```bash
42
+ pnpm run release
13
43
  ```
14
44
 
15
45
  ## Features
package/dist/index.cjs CHANGED
@@ -22,6 +22,7 @@ var index_exports = {};
22
22
  __export(index_exports, {
23
23
  fetchByUuid: () => fetchByUuid,
24
24
  fetchConcept: () => fetchConcept,
25
+ fetchGallery: () => fetchGallery,
25
26
  fetchResource: () => fetchResource,
26
27
  fetchSet: () => fetchSet,
27
28
  fetchSpatialUnit: () => fetchSpatialUnit,
@@ -593,7 +594,8 @@ var componentSchema = import_zod3.z.enum(
593
594
  "network-graph",
594
595
  "table",
595
596
  "text",
596
- "text-image"
597
+ "text-image",
598
+ "timeline"
597
599
  ],
598
600
  { message: "Invalid component" }
599
601
  );
@@ -933,6 +935,7 @@ function parseImageMap(imageMap) {
933
935
  function parsePeriod(period) {
934
936
  return {
935
937
  uuid: period.uuid,
938
+ category: "period",
936
939
  publicationDateTime: period.publicationDateTime != null ? new Date(period.publicationDateTime) : null,
937
940
  type: period.type ?? null,
938
941
  number: period.n ?? null,
@@ -961,6 +964,7 @@ function parseBibliography(bibliography) {
961
964
  }
962
965
  return {
963
966
  uuid: bibliography.uuid,
967
+ category: "bibliography",
964
968
  publicationDateTime: bibliography.publicationDateTime != null ? new Date(bibliography.publicationDateTime) : null,
965
969
  type: bibliography.type ?? null,
966
970
  number: bibliography.n ?? null,
@@ -1026,6 +1030,7 @@ function parseTree(tree) {
1026
1030
  let spatialUnits = [];
1027
1031
  let concepts = [];
1028
1032
  let periods = [];
1033
+ let bibliographies = [];
1029
1034
  if (typeof tree.items !== "string" && "resource" in tree.items) {
1030
1035
  resources = parseResources(
1031
1036
  Array.isArray(tree.items.resource) ? tree.items.resource : [tree.items.resource]
@@ -1046,6 +1051,11 @@ function parseTree(tree) {
1046
1051
  Array.isArray(tree.items.period) ? tree.items.period : [tree.items.period]
1047
1052
  );
1048
1053
  }
1054
+ if (typeof tree.items !== "string" && "bibliography" in tree.items) {
1055
+ bibliographies = parseBibliographies(
1056
+ Array.isArray(tree.items.bibliography) ? tree.items.bibliography : [tree.items.bibliography]
1057
+ );
1058
+ }
1049
1059
  const returnTree = {
1050
1060
  uuid: tree.uuid,
1051
1061
  category: "tree",
@@ -1060,7 +1070,8 @@ function parseTree(tree) {
1060
1070
  resources,
1061
1071
  spatialUnits,
1062
1072
  concepts,
1063
- periods
1073
+ periods,
1074
+ bibliographies
1064
1075
  },
1065
1076
  properties: tree.properties ? parseProperties(
1066
1077
  Array.isArray(tree.properties.property) ? tree.properties.property : [tree.properties.property]
@@ -1073,6 +1084,7 @@ function parseSet(set) {
1073
1084
  let spatialUnits = [];
1074
1085
  let concepts = [];
1075
1086
  let periods = [];
1087
+ let bibliographies = [];
1076
1088
  if (typeof set.items !== "string" && "resource" in set.items) {
1077
1089
  resources = parseResources(
1078
1090
  Array.isArray(set.items.resource) ? set.items.resource : [set.items.resource],
@@ -1096,6 +1108,11 @@ function parseSet(set) {
1096
1108
  Array.isArray(set.items.period) ? set.items.period : [set.items.period]
1097
1109
  );
1098
1110
  }
1111
+ if (typeof set.items !== "string" && "bibliography" in set.items) {
1112
+ bibliographies = parseBibliographies(
1113
+ Array.isArray(set.items.bibliography) ? set.items.bibliography : [set.items.bibliography]
1114
+ );
1115
+ }
1099
1116
  return {
1100
1117
  uuid: set.uuid,
1101
1118
  category: "set",
@@ -1114,7 +1131,8 @@ function parseSet(set) {
1114
1131
  resources,
1115
1132
  spatialUnits,
1116
1133
  concepts,
1117
- periods
1134
+ periods,
1135
+ bibliographies
1118
1136
  }
1119
1137
  };
1120
1138
  }
@@ -1578,6 +1596,16 @@ async function parseWebElementProperties(componentProperty, elementResource) {
1578
1596
  properties.imageOpacity = null;
1579
1597
  break;
1580
1598
  }
1599
+ case "timeline": {
1600
+ const timelineLink = links.find((link) => link.category === "tree");
1601
+ if (!timelineLink) {
1602
+ throw new Error(
1603
+ `Timeline link not found for the following component: \u201C${componentName}\u201D`
1604
+ );
1605
+ }
1606
+ properties.timelineId = timelineLink.uuid;
1607
+ break;
1608
+ }
1581
1609
  default: {
1582
1610
  console.warn(
1583
1611
  `Invalid or non-implemented component name \u201C${componentName}\u201D for the following element: \u201C${parseStringContent(
@@ -1876,6 +1904,56 @@ async function fetchConcept(uuid) {
1876
1904
  }
1877
1905
  }
1878
1906
 
1907
+ // src/utils/fetchers/gallery.ts
1908
+ var import_zod4 = require("zod");
1909
+ var gallerySchema = import_zod4.z.object({
1910
+ uuid: import_zod4.z.string().uuid({ message: "Invalid UUID" }),
1911
+ filter: import_zod4.z.string().optional(),
1912
+ page: import_zod4.z.number().positive({ message: "Page must be positive" }),
1913
+ perPage: import_zod4.z.number().positive({ message: "Per page must be positive" })
1914
+ }).strict();
1915
+ async function fetchGallery(uuid, filter, page, perPage) {
1916
+ try {
1917
+ const parsed = gallerySchema.safeParse({ uuid, filter, page, perPage });
1918
+ if (!parsed.success) {
1919
+ throw new Error(parsed.error.message);
1920
+ }
1921
+ const response = await fetch(
1922
+ `https://ochre.lib.uchicago.edu/ochre?xquery=${encodeURIComponent(`
1923
+ for $q in input()/ochre[@uuid='${uuid}']
1924
+ let $filtered := $q/tree/items/resource[contains(lower-case(identification/label), lower-case('${filter}'))]
1925
+ let $maxLength := count($filtered)
1926
+ return <gallery maxLength='{$maxLength}'>
1927
+ {$q/metadata/project}
1928
+ {$q/metadata/item}
1929
+ {$filtered[position() >= ${((page - 1) * perPage + 1).toString()} and position() < ${(page * perPage + 1).toString()}]}
1930
+ </gallery>
1931
+ `)}&format=json`
1932
+ );
1933
+ if (!response.ok) {
1934
+ throw new Error("Error fetching gallery items, please try again later.");
1935
+ }
1936
+ const data = await response.json();
1937
+ if (!("gallery" in data.result)) {
1938
+ throw new Error("Failed to fetch gallery");
1939
+ }
1940
+ const galleryIdentification = parseIdentification(data.result.gallery.item);
1941
+ const galleryProjectIdentification = parseIdentification(
1942
+ data.result.gallery.project.identification
1943
+ );
1944
+ const gallery = {
1945
+ identification: galleryIdentification,
1946
+ projectIdentification: galleryProjectIdentification,
1947
+ resources: Array.isArray(data.result.gallery.resource) ? parseResources(data.result.gallery.resource) : [parseResource(data.result.gallery.resource)],
1948
+ maxLength: data.result.gallery.maxLength
1949
+ };
1950
+ return gallery;
1951
+ } catch (error) {
1952
+ console.error(error);
1953
+ return null;
1954
+ }
1955
+ }
1956
+
1879
1957
  // src/utils/fetchers/set.ts
1880
1958
  async function fetchSet(uuid) {
1881
1959
  try {
@@ -1994,6 +2072,7 @@ async function fetchWebsite(abbreviation) {
1994
2072
  0 && (module.exports = {
1995
2073
  fetchByUuid,
1996
2074
  fetchConcept,
2075
+ fetchGallery,
1997
2076
  fetchResource,
1998
2077
  fetchSet,
1999
2078
  fetchSpatialUnit,
package/dist/index.d.cts CHANGED
@@ -287,6 +287,7 @@ type Set = {
287
287
  spatialUnits: Array<NestedSpatialUnit>;
288
288
  concepts: Array<NestedConcept>;
289
289
  periods: Array<Period>;
290
+ bibliographies: Array<Bibliography>;
290
291
  };
291
292
  };
292
293
  /**
@@ -294,6 +295,7 @@ type Set = {
294
295
  */
295
296
  type Bibliography = {
296
297
  uuid: string;
298
+ category: "bibliography";
297
299
  publicationDateTime: Date | null;
298
300
  type: string | null;
299
301
  number: number | null;
@@ -325,6 +327,7 @@ type Bibliography = {
325
327
  */
326
328
  type Period = {
327
329
  uuid: string;
330
+ category: "period";
328
331
  publicationDateTime: Date | null;
329
332
  type: string | null;
330
333
  number: number | null;
@@ -372,9 +375,19 @@ type Tree = {
372
375
  spatialUnits: Array<SpatialUnit>;
373
376
  concepts: Array<Concept>;
374
377
  periods: Array<Period>;
378
+ bibliographies: Array<Bibliography>;
375
379
  };
376
380
  properties: Array<Property>;
377
381
  };
382
+ /**
383
+ * Represents a gallery with its identification, project identification, resources and max length
384
+ */
385
+ type Gallery = {
386
+ identification: Identification;
387
+ projectIdentification: Identification;
388
+ resources: Array<Resource>;
389
+ maxLength: number;
390
+ };
378
391
  /**
379
392
  * Represents a website with its properties and elements
380
393
  */
@@ -498,6 +511,9 @@ type WebElementComponent = {
498
511
  image: WebImage;
499
512
  imageOpacity: number | null;
500
513
  content: string;
514
+ } | {
515
+ component: "timeline";
516
+ timelineId: string;
501
517
  };
502
518
  /**
503
519
  * Represents an image used in web elements
@@ -545,6 +561,34 @@ declare function fetchConcept(uuid: string): Promise<{
545
561
  concept: Concept;
546
562
  } | null>;
547
563
 
564
+ /**
565
+ * Fetches and parses a gallery from the OCHRE API
566
+ *
567
+ * @param uuid - The UUID of the gallery
568
+ * @param filter - The filter to apply to the gallery
569
+ * @param page - The page number to fetch
570
+ * @param perPage - The number of items per page
571
+ * @returns The parsed gallery or null if the fetch/parse fails
572
+ *
573
+ * @example
574
+ * ```ts
575
+ * const gallery = await fetchGallery("9c4da06b-f15e-40af-a747-0933eaf3587e", "1978", 1, 12);
576
+ * if (gallery === null) {
577
+ * console.error("Failed to fetch gallery");
578
+ * return;
579
+ * }
580
+ * console.log(`Fetched gallery: ${gallery.identification.label}`);
581
+ * console.log(`Contains ${gallery.resources.length.toLocaleString()} resources`);
582
+ * ```
583
+ *
584
+ * @remarks
585
+ * The returned gallery includes:
586
+ * - Gallery metadata and identification
587
+ * - Project identification
588
+ * - Resources (gallery items)
589
+ */
590
+ declare function fetchGallery(uuid: string, filter: string, page: number, perPage: number): Promise<Gallery | null>;
591
+
548
592
  /**
549
593
  * Raw string value that can be a string, number, or boolean
550
594
  */
@@ -681,7 +725,8 @@ type OchreTree = {
681
725
  }
682
726
  | { spatialUnit: OchreSpatialUnit | Array<OchreSpatialUnit> }
683
727
  | { concept: OchreConcept | Array<OchreConcept> }
684
- | { period: OchrePeriod | Array<OchrePeriod> };
728
+ | { period: OchrePeriod | Array<OchrePeriod> }
729
+ | { bibliography: OchreBibliography | Array<OchreBibliography> };
685
730
  properties?: { property: OchreProperty | Array<OchreProperty> };
686
731
  };
687
732
 
@@ -704,7 +749,8 @@ type OchreSet = {
704
749
  | { resource: OchreResource | Array<OchreResource> }
705
750
  | { spatialUnit: OchreSpatialUnit | Array<OchreSpatialUnit> }
706
751
  | { concept: OchreConcept | Array<OchreConcept> }
707
- | { period: OchrePeriod | Array<OchrePeriod> };
752
+ | { period: OchrePeriod | Array<OchrePeriod> }
753
+ | { bibliography: OchreBibliography | Array<OchreBibliography> };
708
754
  };
709
755
 
710
756
  /**
@@ -1651,4 +1697,4 @@ declare function trimEndLineBreaks(string: string): string;
1651
1697
  */
1652
1698
  declare function parseStringContent(content: OchreStringContent, language?: string): string;
1653
1699
 
1654
- export { type Bibliography, type Concept, type Context, type ContextItem, type ContextNode, type Coordinates, type Data, type Document, type Event, type Footnote, type Identification, type Image, type ImageMap, type ImageMapArea, type Interpretation, type License, type Link, type Metadata, type NestedConcept, type NestedResource, type NestedSpatialUnit, type Note, type Observation, type Period, type Person, type Property, type PropertyValue, type PropertyValueType, type Resource, type Set, type SpatialUnit, type Style, type Tree, type WebElement, type WebElementComponent, type WebImage, type Webpage, type WebpageProperties, type Website, type WebsiteProperties, fetchByUuid, fetchConcept, fetchResource, fetchSet, fetchSpatialUnit, fetchTree, fetchWebsite, filterProperties, getAllPropertyLabels, getPropertyByLabel, getPropertyValueByLabel, getPropertyValuesByLabel, parseBibliographies, parseBibliography, parseConcept, parseConcepts, parseContext, parseCoordinates, parseDocument, parseEmailAndUrl, parseEvents, parseFakeString, parseIdentification, parseImage, parseImageMap, parseInterpretations, parseLanguages, parseLicense, parseLink, parseLinks, parseMetadata, parseNotes, parseObservation, parseObservations, parsePeriod, parsePeriods, parsePersons, parseProperties, parseResource, parseResources, parseSet, parseSpatialUnit, parseSpatialUnits, parseStringContent, parseStringDocumentItem, parseStringItem, parseTree, parseWebsite, trimEndLineBreaks };
1700
+ export { type Bibliography, type Concept, type Context, type ContextItem, type ContextNode, type Coordinates, type Data, type Document, type Event, type Footnote, type Gallery, type Identification, type Image, type ImageMap, type ImageMapArea, type Interpretation, type License, type Link, type Metadata, type NestedConcept, type NestedResource, type NestedSpatialUnit, type Note, type Observation, type Period, type Person, type Property, type PropertyValue, type PropertyValueType, type Resource, type Set, type SpatialUnit, type Style, type Tree, type WebElement, type WebElementComponent, type WebImage, type Webpage, type WebpageProperties, type Website, type WebsiteProperties, fetchByUuid, fetchConcept, fetchGallery, fetchResource, fetchSet, fetchSpatialUnit, fetchTree, fetchWebsite, filterProperties, getAllPropertyLabels, getPropertyByLabel, getPropertyValueByLabel, getPropertyValuesByLabel, parseBibliographies, parseBibliography, parseConcept, parseConcepts, parseContext, parseCoordinates, parseDocument, parseEmailAndUrl, parseEvents, parseFakeString, parseIdentification, parseImage, parseImageMap, parseInterpretations, parseLanguages, parseLicense, parseLink, parseLinks, parseMetadata, parseNotes, parseObservation, parseObservations, parsePeriod, parsePeriods, parsePersons, parseProperties, parseResource, parseResources, parseSet, parseSpatialUnit, parseSpatialUnits, parseStringContent, parseStringDocumentItem, parseStringItem, parseTree, parseWebsite, trimEndLineBreaks };
package/dist/index.d.ts CHANGED
@@ -287,6 +287,7 @@ type Set = {
287
287
  spatialUnits: Array<NestedSpatialUnit>;
288
288
  concepts: Array<NestedConcept>;
289
289
  periods: Array<Period>;
290
+ bibliographies: Array<Bibliography>;
290
291
  };
291
292
  };
292
293
  /**
@@ -294,6 +295,7 @@ type Set = {
294
295
  */
295
296
  type Bibliography = {
296
297
  uuid: string;
298
+ category: "bibliography";
297
299
  publicationDateTime: Date | null;
298
300
  type: string | null;
299
301
  number: number | null;
@@ -325,6 +327,7 @@ type Bibliography = {
325
327
  */
326
328
  type Period = {
327
329
  uuid: string;
330
+ category: "period";
328
331
  publicationDateTime: Date | null;
329
332
  type: string | null;
330
333
  number: number | null;
@@ -372,9 +375,19 @@ type Tree = {
372
375
  spatialUnits: Array<SpatialUnit>;
373
376
  concepts: Array<Concept>;
374
377
  periods: Array<Period>;
378
+ bibliographies: Array<Bibliography>;
375
379
  };
376
380
  properties: Array<Property>;
377
381
  };
382
+ /**
383
+ * Represents a gallery with its identification, project identification, resources and max length
384
+ */
385
+ type Gallery = {
386
+ identification: Identification;
387
+ projectIdentification: Identification;
388
+ resources: Array<Resource>;
389
+ maxLength: number;
390
+ };
378
391
  /**
379
392
  * Represents a website with its properties and elements
380
393
  */
@@ -498,6 +511,9 @@ type WebElementComponent = {
498
511
  image: WebImage;
499
512
  imageOpacity: number | null;
500
513
  content: string;
514
+ } | {
515
+ component: "timeline";
516
+ timelineId: string;
501
517
  };
502
518
  /**
503
519
  * Represents an image used in web elements
@@ -545,6 +561,34 @@ declare function fetchConcept(uuid: string): Promise<{
545
561
  concept: Concept;
546
562
  } | null>;
547
563
 
564
+ /**
565
+ * Fetches and parses a gallery from the OCHRE API
566
+ *
567
+ * @param uuid - The UUID of the gallery
568
+ * @param filter - The filter to apply to the gallery
569
+ * @param page - The page number to fetch
570
+ * @param perPage - The number of items per page
571
+ * @returns The parsed gallery or null if the fetch/parse fails
572
+ *
573
+ * @example
574
+ * ```ts
575
+ * const gallery = await fetchGallery("9c4da06b-f15e-40af-a747-0933eaf3587e", "1978", 1, 12);
576
+ * if (gallery === null) {
577
+ * console.error("Failed to fetch gallery");
578
+ * return;
579
+ * }
580
+ * console.log(`Fetched gallery: ${gallery.identification.label}`);
581
+ * console.log(`Contains ${gallery.resources.length.toLocaleString()} resources`);
582
+ * ```
583
+ *
584
+ * @remarks
585
+ * The returned gallery includes:
586
+ * - Gallery metadata and identification
587
+ * - Project identification
588
+ * - Resources (gallery items)
589
+ */
590
+ declare function fetchGallery(uuid: string, filter: string, page: number, perPage: number): Promise<Gallery | null>;
591
+
548
592
  /**
549
593
  * Raw string value that can be a string, number, or boolean
550
594
  */
@@ -681,7 +725,8 @@ type OchreTree = {
681
725
  }
682
726
  | { spatialUnit: OchreSpatialUnit | Array<OchreSpatialUnit> }
683
727
  | { concept: OchreConcept | Array<OchreConcept> }
684
- | { period: OchrePeriod | Array<OchrePeriod> };
728
+ | { period: OchrePeriod | Array<OchrePeriod> }
729
+ | { bibliography: OchreBibliography | Array<OchreBibliography> };
685
730
  properties?: { property: OchreProperty | Array<OchreProperty> };
686
731
  };
687
732
 
@@ -704,7 +749,8 @@ type OchreSet = {
704
749
  | { resource: OchreResource | Array<OchreResource> }
705
750
  | { spatialUnit: OchreSpatialUnit | Array<OchreSpatialUnit> }
706
751
  | { concept: OchreConcept | Array<OchreConcept> }
707
- | { period: OchrePeriod | Array<OchrePeriod> };
752
+ | { period: OchrePeriod | Array<OchrePeriod> }
753
+ | { bibliography: OchreBibliography | Array<OchreBibliography> };
708
754
  };
709
755
 
710
756
  /**
@@ -1651,4 +1697,4 @@ declare function trimEndLineBreaks(string: string): string;
1651
1697
  */
1652
1698
  declare function parseStringContent(content: OchreStringContent, language?: string): string;
1653
1699
 
1654
- export { type Bibliography, type Concept, type Context, type ContextItem, type ContextNode, type Coordinates, type Data, type Document, type Event, type Footnote, type Identification, type Image, type ImageMap, type ImageMapArea, type Interpretation, type License, type Link, type Metadata, type NestedConcept, type NestedResource, type NestedSpatialUnit, type Note, type Observation, type Period, type Person, type Property, type PropertyValue, type PropertyValueType, type Resource, type Set, type SpatialUnit, type Style, type Tree, type WebElement, type WebElementComponent, type WebImage, type Webpage, type WebpageProperties, type Website, type WebsiteProperties, fetchByUuid, fetchConcept, fetchResource, fetchSet, fetchSpatialUnit, fetchTree, fetchWebsite, filterProperties, getAllPropertyLabels, getPropertyByLabel, getPropertyValueByLabel, getPropertyValuesByLabel, parseBibliographies, parseBibliography, parseConcept, parseConcepts, parseContext, parseCoordinates, parseDocument, parseEmailAndUrl, parseEvents, parseFakeString, parseIdentification, parseImage, parseImageMap, parseInterpretations, parseLanguages, parseLicense, parseLink, parseLinks, parseMetadata, parseNotes, parseObservation, parseObservations, parsePeriod, parsePeriods, parsePersons, parseProperties, parseResource, parseResources, parseSet, parseSpatialUnit, parseSpatialUnits, parseStringContent, parseStringDocumentItem, parseStringItem, parseTree, parseWebsite, trimEndLineBreaks };
1700
+ export { type Bibliography, type Concept, type Context, type ContextItem, type ContextNode, type Coordinates, type Data, type Document, type Event, type Footnote, type Gallery, type Identification, type Image, type ImageMap, type ImageMapArea, type Interpretation, type License, type Link, type Metadata, type NestedConcept, type NestedResource, type NestedSpatialUnit, type Note, type Observation, type Period, type Person, type Property, type PropertyValue, type PropertyValueType, type Resource, type Set, type SpatialUnit, type Style, type Tree, type WebElement, type WebElementComponent, type WebImage, type Webpage, type WebpageProperties, type Website, type WebsiteProperties, fetchByUuid, fetchConcept, fetchGallery, fetchResource, fetchSet, fetchSpatialUnit, fetchTree, fetchWebsite, filterProperties, getAllPropertyLabels, getPropertyByLabel, getPropertyValueByLabel, getPropertyValuesByLabel, parseBibliographies, parseBibliography, parseConcept, parseConcepts, parseContext, parseCoordinates, parseDocument, parseEmailAndUrl, parseEvents, parseFakeString, parseIdentification, parseImage, parseImageMap, parseInterpretations, parseLanguages, parseLicense, parseLink, parseLinks, parseMetadata, parseNotes, parseObservation, parseObservations, parsePeriod, parsePeriods, parsePersons, parseProperties, parseResource, parseResources, parseSet, parseSpatialUnit, parseSpatialUnits, parseStringContent, parseStringDocumentItem, parseStringItem, parseTree, parseWebsite, trimEndLineBreaks };
package/dist/index.js CHANGED
@@ -519,7 +519,8 @@ var componentSchema = z3.enum(
519
519
  "network-graph",
520
520
  "table",
521
521
  "text",
522
- "text-image"
522
+ "text-image",
523
+ "timeline"
523
524
  ],
524
525
  { message: "Invalid component" }
525
526
  );
@@ -859,6 +860,7 @@ function parseImageMap(imageMap) {
859
860
  function parsePeriod(period) {
860
861
  return {
861
862
  uuid: period.uuid,
863
+ category: "period",
862
864
  publicationDateTime: period.publicationDateTime != null ? new Date(period.publicationDateTime) : null,
863
865
  type: period.type ?? null,
864
866
  number: period.n ?? null,
@@ -887,6 +889,7 @@ function parseBibliography(bibliography) {
887
889
  }
888
890
  return {
889
891
  uuid: bibliography.uuid,
892
+ category: "bibliography",
890
893
  publicationDateTime: bibliography.publicationDateTime != null ? new Date(bibliography.publicationDateTime) : null,
891
894
  type: bibliography.type ?? null,
892
895
  number: bibliography.n ?? null,
@@ -952,6 +955,7 @@ function parseTree(tree) {
952
955
  let spatialUnits = [];
953
956
  let concepts = [];
954
957
  let periods = [];
958
+ let bibliographies = [];
955
959
  if (typeof tree.items !== "string" && "resource" in tree.items) {
956
960
  resources = parseResources(
957
961
  Array.isArray(tree.items.resource) ? tree.items.resource : [tree.items.resource]
@@ -972,6 +976,11 @@ function parseTree(tree) {
972
976
  Array.isArray(tree.items.period) ? tree.items.period : [tree.items.period]
973
977
  );
974
978
  }
979
+ if (typeof tree.items !== "string" && "bibliography" in tree.items) {
980
+ bibliographies = parseBibliographies(
981
+ Array.isArray(tree.items.bibliography) ? tree.items.bibliography : [tree.items.bibliography]
982
+ );
983
+ }
975
984
  const returnTree = {
976
985
  uuid: tree.uuid,
977
986
  category: "tree",
@@ -986,7 +995,8 @@ function parseTree(tree) {
986
995
  resources,
987
996
  spatialUnits,
988
997
  concepts,
989
- periods
998
+ periods,
999
+ bibliographies
990
1000
  },
991
1001
  properties: tree.properties ? parseProperties(
992
1002
  Array.isArray(tree.properties.property) ? tree.properties.property : [tree.properties.property]
@@ -999,6 +1009,7 @@ function parseSet(set) {
999
1009
  let spatialUnits = [];
1000
1010
  let concepts = [];
1001
1011
  let periods = [];
1012
+ let bibliographies = [];
1002
1013
  if (typeof set.items !== "string" && "resource" in set.items) {
1003
1014
  resources = parseResources(
1004
1015
  Array.isArray(set.items.resource) ? set.items.resource : [set.items.resource],
@@ -1022,6 +1033,11 @@ function parseSet(set) {
1022
1033
  Array.isArray(set.items.period) ? set.items.period : [set.items.period]
1023
1034
  );
1024
1035
  }
1036
+ if (typeof set.items !== "string" && "bibliography" in set.items) {
1037
+ bibliographies = parseBibliographies(
1038
+ Array.isArray(set.items.bibliography) ? set.items.bibliography : [set.items.bibliography]
1039
+ );
1040
+ }
1025
1041
  return {
1026
1042
  uuid: set.uuid,
1027
1043
  category: "set",
@@ -1040,7 +1056,8 @@ function parseSet(set) {
1040
1056
  resources,
1041
1057
  spatialUnits,
1042
1058
  concepts,
1043
- periods
1059
+ periods,
1060
+ bibliographies
1044
1061
  }
1045
1062
  };
1046
1063
  }
@@ -1504,6 +1521,16 @@ async function parseWebElementProperties(componentProperty, elementResource) {
1504
1521
  properties.imageOpacity = null;
1505
1522
  break;
1506
1523
  }
1524
+ case "timeline": {
1525
+ const timelineLink = links.find((link) => link.category === "tree");
1526
+ if (!timelineLink) {
1527
+ throw new Error(
1528
+ `Timeline link not found for the following component: \u201C${componentName}\u201D`
1529
+ );
1530
+ }
1531
+ properties.timelineId = timelineLink.uuid;
1532
+ break;
1533
+ }
1507
1534
  default: {
1508
1535
  console.warn(
1509
1536
  `Invalid or non-implemented component name \u201C${componentName}\u201D for the following element: \u201C${parseStringContent(
@@ -1802,6 +1829,56 @@ async function fetchConcept(uuid) {
1802
1829
  }
1803
1830
  }
1804
1831
 
1832
+ // src/utils/fetchers/gallery.ts
1833
+ import { z as z4 } from "zod";
1834
+ var gallerySchema = z4.object({
1835
+ uuid: z4.string().uuid({ message: "Invalid UUID" }),
1836
+ filter: z4.string().optional(),
1837
+ page: z4.number().positive({ message: "Page must be positive" }),
1838
+ perPage: z4.number().positive({ message: "Per page must be positive" })
1839
+ }).strict();
1840
+ async function fetchGallery(uuid, filter, page, perPage) {
1841
+ try {
1842
+ const parsed = gallerySchema.safeParse({ uuid, filter, page, perPage });
1843
+ if (!parsed.success) {
1844
+ throw new Error(parsed.error.message);
1845
+ }
1846
+ const response = await fetch(
1847
+ `https://ochre.lib.uchicago.edu/ochre?xquery=${encodeURIComponent(`
1848
+ for $q in input()/ochre[@uuid='${uuid}']
1849
+ let $filtered := $q/tree/items/resource[contains(lower-case(identification/label), lower-case('${filter}'))]
1850
+ let $maxLength := count($filtered)
1851
+ return <gallery maxLength='{$maxLength}'>
1852
+ {$q/metadata/project}
1853
+ {$q/metadata/item}
1854
+ {$filtered[position() >= ${((page - 1) * perPage + 1).toString()} and position() < ${(page * perPage + 1).toString()}]}
1855
+ </gallery>
1856
+ `)}&format=json`
1857
+ );
1858
+ if (!response.ok) {
1859
+ throw new Error("Error fetching gallery items, please try again later.");
1860
+ }
1861
+ const data = await response.json();
1862
+ if (!("gallery" in data.result)) {
1863
+ throw new Error("Failed to fetch gallery");
1864
+ }
1865
+ const galleryIdentification = parseIdentification(data.result.gallery.item);
1866
+ const galleryProjectIdentification = parseIdentification(
1867
+ data.result.gallery.project.identification
1868
+ );
1869
+ const gallery = {
1870
+ identification: galleryIdentification,
1871
+ projectIdentification: galleryProjectIdentification,
1872
+ resources: Array.isArray(data.result.gallery.resource) ? parseResources(data.result.gallery.resource) : [parseResource(data.result.gallery.resource)],
1873
+ maxLength: data.result.gallery.maxLength
1874
+ };
1875
+ return gallery;
1876
+ } catch (error) {
1877
+ console.error(error);
1878
+ return null;
1879
+ }
1880
+ }
1881
+
1805
1882
  // src/utils/fetchers/set.ts
1806
1883
  async function fetchSet(uuid) {
1807
1884
  try {
@@ -1919,6 +1996,7 @@ async function fetchWebsite(abbreviation) {
1919
1996
  export {
1920
1997
  fetchByUuid,
1921
1998
  fetchConcept,
1999
+ fetchGallery,
1922
2000
  fetchResource,
1923
2001
  fetchSet,
1924
2002
  fetchSpatialUnit,
package/package.json CHANGED
@@ -1,10 +1,18 @@
1
1
  {
2
2
  "name": "@digitalculture/ochre-sdk",
3
- "version": "0.1.21",
3
+ "version": "0.1.23",
4
4
  "type": "module",
5
5
  "license": "MIT",
6
6
  "description": "Node.js library for working with OCHRE (Online Cultural and Historical Research Environment) data",
7
7
  "author": "Firat Ciftci <firatciftci@uchicago.edu> (https://digitalculture.uchicago.edu)",
8
+ "homepage": "https://github.com/forumfordigitalculture/ochre-sdk",
9
+ "bugs": {
10
+ "url": "https://github.com/forumfordigitalculture/ochre-sdk/issues"
11
+ },
12
+ "repository": {
13
+ "type": "git",
14
+ "url": "git+https://github.com/forumfordigitalculture/ochre-sdk.git"
15
+ },
8
16
  "keywords": [
9
17
  "ochre",
10
18
  "uchicago",
@@ -39,6 +47,7 @@
39
47
  "@antfu/eslint-config": "^4.1.0",
40
48
  "@arethetypeswrong/cli": "^0.17.3",
41
49
  "@changesets/cli": "^2.27.12",
50
+ "@total-typescript/ts-reset": "^0.6.1",
42
51
  "@types/node": "^22.10.10",
43
52
  "eslint-plugin-unused-imports": "^4.1.4",
44
53
  "prettier": "^3.4.2",
@@ -48,7 +57,7 @@
48
57
  },
49
58
  "scripts": {
50
59
  "dev": "tsup src/index.ts --watch",
51
- "build": "tsup",
60
+ "build:ochre-sdk": "tsup",
52
61
  "lint": "eslint .",
53
62
  "lint:fix": "eslint . --fix",
54
63
  "format": "prettier --check .",
@@ -56,7 +65,7 @@
56
65
  "check-types": "tsc --noEmit",
57
66
  "check-exports": "attw --pack .",
58
67
  "test": "vitest run",
59
- "ci": "pnpm run build && pnpm run lint && pnpm run format && pnpm run check-types && pnpm run check-exports && pnpm run test",
68
+ "ci": "pnpm run build:ochre-sdk && pnpm run lint && pnpm run format && pnpm run check-types && pnpm run check-exports && pnpm run test",
60
69
  "changeset": "changeset add",
61
70
  "release": "changeset version && changeset publish"
62
71
  }