@favish/staffbase-utils 0.10.0 → 0.11.0

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
@@ -24,9 +24,10 @@ minimumReleaseAgeExclude:
24
24
  | Subpath | Exports |
25
25
  | --- | --- |
26
26
  | `@favish/staffbase-utils/api` | `fetchJson`, `fetchAllPaginated`, `ApiError` |
27
+ | `@favish/staffbase-utils/content` | `resolveLocalizedContent`, `resolveActiveLanguage`, `detectEditorLanguage`, `detectPreviewLanguage` |
27
28
  | `@favish/staffbase-utils/log` | `logError`, `logWarn`, `logDebug`, `setLoggingEnabled` |
28
29
  | `@favish/staffbase-utils/dom` | `getDynamicClasses` |
29
- | `@favish/staffbase-utils/types` | `Channel`, `ChannelLink`, `ChannelLinkParameter`, `DropdownOption` (type-only) |
30
+ | `@favish/staffbase-utils/types` | `Channel`, `ChannelLink`, `ChannelLinkParameter`, `DropdownOption`, `LocalizedContent`, `ArticleImage`, `ArticleImageVariant` (type-only) |
30
31
 
31
32
  More modules (`/env`, `/device`, `/html`, `/links`, `/widgets`) are added per the
32
33
  delivery roadmap; each is its own subpath so consumers only bundle what they import.
@@ -0,0 +1,2 @@
1
+ Object.defineProperty(exports,Symbol.toStringTag,{value:`Module`});var e=()=>typeof document>`u`?null:(document.querySelector(`[aria-selected="true"]`)?.getAttribute(`data-testid`))?.split(`-`).pop()??null,t=()=>{if(typeof window>`u`)return null;let e=window.App?._urlParameters;return e?new URLSearchParams(e).get(`language`):null},n=n=>{let{contentLanguage:r,defaultLanguage:i,isEditor:a}=n,o=r??i;return a?e()??o:r??t()??o},r=(e,t)=>{let{defaultLanguage:r,onError:i}=t;if(!e)return i?.(`Invalid article data or missing contents`),null;let a=n(t),o=e[a]||e[r]||null;if(!o)return i?.(`Content unavailable for language: ${a} or fallback: ${r}`),null;let s=e[r];return{title:o.title||s?.title||``,teaser:o.teaser||s?.teaser||``,content:o.content||s?.content||``,image:o.image||s?.image||``,feedImage:o.feedImage||s?.feedImage||``}};exports.detectEditorLanguage=e,exports.detectPreviewLanguage=t,exports.resolveActiveLanguage=n,exports.resolveLocalizedContent=r;
2
+ //# sourceMappingURL=content.cjs.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"content.cjs.js","names":[],"sources":["../src/content/detectEditorLanguage.ts","../src/content/detectPreviewLanguage.ts","../src/content/resolveActiveLanguage.ts","../src/content/resolveLocalizedContent.ts"],"sourcesContent":["/**\n * Reads the active language from the Staffbase editor's selected language tab\n * (`[aria-selected=\"true\"]` with a `data-testid` suffixed by the language code).\n * Returns null when no tab is active or there is no DOM, so callers can fall back.\n * @returns {string | null} The detected editor language, or null.\n */\nexport const detectEditorLanguage = (): string | null => {\n if (typeof document === 'undefined') return null\n\n const activeTab = document.querySelector('[aria-selected=\"true\"]')\n const testId = activeTab?.getAttribute('data-testid')\n\n return testId?.split('-').pop() ?? null\n}\n","/**\n * Reads the `language` URL parameter the Staffbase preview shell exposes on\n * `window.App._urlParameters`. Returns null when the shell or parameter is\n * absent (or there is no DOM), so callers can fall back.\n * @returns {string | null} The preview language, or null.\n */\nexport const detectPreviewLanguage = (): string | null => {\n if (typeof window === 'undefined') return null\n\n const appConfig = (window as { App?: { _urlParameters?: string } }).App\n ?._urlParameters\n if (!appConfig) return null\n\n return new URLSearchParams(appConfig).get('language')\n}\n","import type { ResolveLocalizedContentOptions } from '../types/content/ResolveLocalizedContentOptions'\nimport { detectEditorLanguage } from './detectEditorLanguage'\nimport { detectPreviewLanguage } from './detectPreviewLanguage'\n\n/**\n * Resolves the language to render content in.\n *\n * Editor path: the selected language tab wins. Runtime path: the explicit\n * `contentLanguage` is trusted first so the article language matches the rest of\n * the UI, with preview-URL sniffing only as a fallback. Both paths fall back to\n * `contentLanguage ?? defaultLanguage`.\n * @param {ResolveLocalizedContentOptions} options - The resolution options.\n * @returns {string} The resolved active language code.\n */\nexport const resolveActiveLanguage = (\n options: ResolveLocalizedContentOptions,\n): string => {\n const { contentLanguage, defaultLanguage, isEditor } = options\n const fallback = contentLanguage ?? defaultLanguage\n\n if (isEditor) return detectEditorLanguage() ?? fallback\n\n return contentLanguage ?? detectPreviewLanguage() ?? fallback\n}\n","import type { LocalizedContent } from '../types/content/LocalizedContent'\nimport type { ResolveLocalizedContentOptions } from '../types/content/ResolveLocalizedContentOptions'\nimport { resolveActiveLanguage } from './resolveActiveLanguage'\n\n/**\n * Selects and field-merges the localized article content for the active language.\n *\n * Resolves the active language (see resolveActiveLanguage), picks that language's\n * content (falling back to the default language), then fills each field from the\n * default-language entry when the active one is empty. Returns null and reports\n * via `onError` when contents are missing or unavailable in both languages.\n * @param {Record<string, LocalizedContent> | undefined} contents - The article's per-language contents.\n * @param {ResolveLocalizedContentOptions} options - Language and diagnostics options.\n * @returns {LocalizedContent | null} The merged localized content, or null.\n */\nexport const resolveLocalizedContent = (\n contents: Record<string, LocalizedContent> | undefined,\n options: ResolveLocalizedContentOptions,\n): LocalizedContent | null => {\n const { defaultLanguage, onError } = options\n\n if (!contents) {\n onError?.('Invalid article data or missing contents')\n return null\n }\n\n const language = resolveActiveLanguage(options)\n const localized = contents[language] || contents[defaultLanguage] || null\n\n if (!localized) {\n onError?.(\n `Content unavailable for language: ${language} or fallback: ${defaultLanguage}`,\n )\n return null\n }\n\n const fallback = contents[defaultLanguage]\n\n return {\n title: localized.title || fallback?.title || '',\n teaser: localized.teaser || fallback?.teaser || '',\n content: localized.content || fallback?.content || '',\n image: localized.image || fallback?.image || '',\n feedImage: localized.feedImage || fallback?.feedImage || '',\n }\n}\n"],"mappings":"mEAMA,IAAa,MACP,OAAO,SAAa,IAAoB,MAE1B,SAAS,cAAc,wBAC1B,GAAW,aAAa,aAAa,IAErC,MAAM,GAAG,EAAE,IAAI,GAAK,KCNxB,MAA6C,CACxD,GAAI,OAAO,OAAW,IAAa,OAAO,KAE1C,IAAM,EAAa,OAAiD,KAChE,eAGJ,OAFK,EAEE,IAAI,gBAAgB,CAAS,EAAE,IAAI,UAAU,EAF7B,IAGzB,ECAa,EACX,GACW,CACX,GAAM,CAAE,kBAAiB,kBAAiB,YAAa,EACjD,EAAW,GAAmB,EAIpC,OAFI,EAAiB,EAAqB,GAAK,EAExC,GAAmB,EAAsB,GAAK,CACvD,ECRa,GACX,EACA,IAC4B,CAC5B,GAAM,CAAE,kBAAiB,WAAY,EAErC,GAAI,CAAC,EAEH,OADA,IAAU,0CAA0C,EAC7C,KAGT,IAAM,EAAW,EAAsB,CAAO,EACxC,EAAY,EAAS,IAAa,EAAS,IAAoB,KAErE,GAAI,CAAC,EAIH,OAHA,IACE,qCAAqC,EAAS,gBAAgB,GAChE,EACO,KAGT,IAAM,EAAW,EAAS,GAE1B,MAAO,CACL,MAAO,EAAU,OAAS,GAAU,OAAS,GAC7C,OAAQ,EAAU,QAAU,GAAU,QAAU,GAChD,QAAS,EAAU,SAAW,GAAU,SAAW,GACnD,MAAO,EAAU,OAAS,GAAU,OAAS,GAC7C,UAAW,EAAU,WAAa,GAAU,WAAa,EAC3D,CACF"}
@@ -0,0 +1,26 @@
1
+ //#region src/content/detectEditorLanguage.ts
2
+ var e = () => typeof document > "u" ? null : (document.querySelector("[aria-selected=\"true\"]")?.getAttribute("data-testid"))?.split("-").pop() ?? null, t = () => {
3
+ if (typeof window > "u") return null;
4
+ let e = window.App?._urlParameters;
5
+ return e ? new URLSearchParams(e).get("language") : null;
6
+ }, n = (n) => {
7
+ let { contentLanguage: r, defaultLanguage: i, isEditor: a } = n, o = r ?? i;
8
+ return a ? e() ?? o : r ?? t() ?? o;
9
+ }, r = (e, t) => {
10
+ let { defaultLanguage: r, onError: i } = t;
11
+ if (!e) return i?.("Invalid article data or missing contents"), null;
12
+ let a = n(t), o = e[a] || e[r] || null;
13
+ if (!o) return i?.(`Content unavailable for language: ${a} or fallback: ${r}`), null;
14
+ let s = e[r];
15
+ return {
16
+ title: o.title || s?.title || "",
17
+ teaser: o.teaser || s?.teaser || "",
18
+ content: o.content || s?.content || "",
19
+ image: o.image || s?.image || "",
20
+ feedImage: o.feedImage || s?.feedImage || ""
21
+ };
22
+ };
23
+ //#endregion
24
+ export { e as detectEditorLanguage, t as detectPreviewLanguage, n as resolveActiveLanguage, r as resolveLocalizedContent };
25
+
26
+ //# sourceMappingURL=content.es.mjs.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"content.es.mjs","names":[],"sources":["../src/content/detectEditorLanguage.ts","../src/content/detectPreviewLanguage.ts","../src/content/resolveActiveLanguage.ts","../src/content/resolveLocalizedContent.ts"],"sourcesContent":["/**\n * Reads the active language from the Staffbase editor's selected language tab\n * (`[aria-selected=\"true\"]` with a `data-testid` suffixed by the language code).\n * Returns null when no tab is active or there is no DOM, so callers can fall back.\n * @returns {string | null} The detected editor language, or null.\n */\nexport const detectEditorLanguage = (): string | null => {\n if (typeof document === 'undefined') return null\n\n const activeTab = document.querySelector('[aria-selected=\"true\"]')\n const testId = activeTab?.getAttribute('data-testid')\n\n return testId?.split('-').pop() ?? null\n}\n","/**\n * Reads the `language` URL parameter the Staffbase preview shell exposes on\n * `window.App._urlParameters`. Returns null when the shell or parameter is\n * absent (or there is no DOM), so callers can fall back.\n * @returns {string | null} The preview language, or null.\n */\nexport const detectPreviewLanguage = (): string | null => {\n if (typeof window === 'undefined') return null\n\n const appConfig = (window as { App?: { _urlParameters?: string } }).App\n ?._urlParameters\n if (!appConfig) return null\n\n return new URLSearchParams(appConfig).get('language')\n}\n","import type { ResolveLocalizedContentOptions } from '../types/content/ResolveLocalizedContentOptions'\nimport { detectEditorLanguage } from './detectEditorLanguage'\nimport { detectPreviewLanguage } from './detectPreviewLanguage'\n\n/**\n * Resolves the language to render content in.\n *\n * Editor path: the selected language tab wins. Runtime path: the explicit\n * `contentLanguage` is trusted first so the article language matches the rest of\n * the UI, with preview-URL sniffing only as a fallback. Both paths fall back to\n * `contentLanguage ?? defaultLanguage`.\n * @param {ResolveLocalizedContentOptions} options - The resolution options.\n * @returns {string} The resolved active language code.\n */\nexport const resolveActiveLanguage = (\n options: ResolveLocalizedContentOptions,\n): string => {\n const { contentLanguage, defaultLanguage, isEditor } = options\n const fallback = contentLanguage ?? defaultLanguage\n\n if (isEditor) return detectEditorLanguage() ?? fallback\n\n return contentLanguage ?? detectPreviewLanguage() ?? fallback\n}\n","import type { LocalizedContent } from '../types/content/LocalizedContent'\nimport type { ResolveLocalizedContentOptions } from '../types/content/ResolveLocalizedContentOptions'\nimport { resolveActiveLanguage } from './resolveActiveLanguage'\n\n/**\n * Selects and field-merges the localized article content for the active language.\n *\n * Resolves the active language (see resolveActiveLanguage), picks that language's\n * content (falling back to the default language), then fills each field from the\n * default-language entry when the active one is empty. Returns null and reports\n * via `onError` when contents are missing or unavailable in both languages.\n * @param {Record<string, LocalizedContent> | undefined} contents - The article's per-language contents.\n * @param {ResolveLocalizedContentOptions} options - Language and diagnostics options.\n * @returns {LocalizedContent | null} The merged localized content, or null.\n */\nexport const resolveLocalizedContent = (\n contents: Record<string, LocalizedContent> | undefined,\n options: ResolveLocalizedContentOptions,\n): LocalizedContent | null => {\n const { defaultLanguage, onError } = options\n\n if (!contents) {\n onError?.('Invalid article data or missing contents')\n return null\n }\n\n const language = resolveActiveLanguage(options)\n const localized = contents[language] || contents[defaultLanguage] || null\n\n if (!localized) {\n onError?.(\n `Content unavailable for language: ${language} or fallback: ${defaultLanguage}`,\n )\n return null\n }\n\n const fallback = contents[defaultLanguage]\n\n return {\n title: localized.title || fallback?.title || '',\n teaser: localized.teaser || fallback?.teaser || '',\n content: localized.content || fallback?.content || '',\n image: localized.image || fallback?.image || '',\n feedImage: localized.feedImage || fallback?.feedImage || '',\n }\n}\n"],"mappings":";AAMA,IAAa,UACP,OAAO,WAAa,MAAoB,QAE1B,SAAS,cAAc,0BAC1B,GAAW,aAAa,aAAa,IAErC,MAAM,GAAG,EAAE,IAAI,KAAK,MCNxB,UAA6C;CACxD,IAAI,OAAO,SAAW,KAAa,OAAO;CAE1C,IAAM,IAAa,OAAiD,KAChE;CAGJ,OAFK,IAEE,IAAI,gBAAgB,CAAS,EAAE,IAAI,UAAU,IAF7B;AAGzB,GCAa,KACX,MACW;CACX,IAAM,EAAE,oBAAiB,oBAAiB,gBAAa,GACjD,IAAW,KAAmB;CAIpC,OAFI,IAAiB,EAAqB,KAAK,IAExC,KAAmB,EAAsB,KAAK;AACvD,GCRa,KACX,GACA,MAC4B;CAC5B,IAAM,EAAE,oBAAiB,eAAY;CAErC,IAAI,CAAC,GAEH,OADA,IAAU,0CAA0C,GAC7C;CAGT,IAAM,IAAW,EAAsB,CAAO,GACxC,IAAY,EAAS,MAAa,EAAS,MAAoB;CAErE,IAAI,CAAC,GAIH,OAHA,IACE,qCAAqC,EAAS,gBAAgB,GAChE,GACO;CAGT,IAAM,IAAW,EAAS;CAE1B,OAAO;EACL,OAAO,EAAU,SAAS,GAAU,SAAS;EAC7C,QAAQ,EAAU,UAAU,GAAU,UAAU;EAChD,SAAS,EAAU,WAAW,GAAU,WAAW;EACnD,OAAO,EAAU,SAAS,GAAU,SAAS;EAC7C,WAAW,EAAU,aAAa,GAAU,aAAa;CAC3D;AACF"}
@@ -0,0 +1,8 @@
1
+ /**
2
+ * Reads the active language from the Staffbase editor's selected language tab
3
+ * (`[aria-selected="true"]` with a `data-testid` suffixed by the language code).
4
+ * Returns null when no tab is active or there is no DOM, so callers can fall back.
5
+ * @returns {string | null} The detected editor language, or null.
6
+ */
7
+ export declare const detectEditorLanguage: () => string | null;
8
+ //# sourceMappingURL=detectEditorLanguage.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"detectEditorLanguage.d.ts","sourceRoot":"","sources":["../../../src/content/detectEditorLanguage.ts"],"names":[],"mappings":"AAAA;;;;;GAKG;AACH,eAAO,MAAM,oBAAoB,QAAO,MAAM,GAAG,IAOhD,CAAA"}
@@ -0,0 +1,8 @@
1
+ /**
2
+ * Reads the `language` URL parameter the Staffbase preview shell exposes on
3
+ * `window.App._urlParameters`. Returns null when the shell or parameter is
4
+ * absent (or there is no DOM), so callers can fall back.
5
+ * @returns {string | null} The preview language, or null.
6
+ */
7
+ export declare const detectPreviewLanguage: () => string | null;
8
+ //# sourceMappingURL=detectPreviewLanguage.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"detectPreviewLanguage.d.ts","sourceRoot":"","sources":["../../../src/content/detectPreviewLanguage.ts"],"names":[],"mappings":"AAAA;;;;;GAKG;AACH,eAAO,MAAM,qBAAqB,QAAO,MAAM,GAAG,IAQjD,CAAA"}
@@ -0,0 +1,6 @@
1
+ export { detectEditorLanguage } from './detectEditorLanguage';
2
+ export { detectPreviewLanguage } from './detectPreviewLanguage';
3
+ export { resolveActiveLanguage } from './resolveActiveLanguage';
4
+ export { resolveLocalizedContent } from './resolveLocalizedContent';
5
+ export type { ResolveLocalizedContentOptions } from '../types/content/ResolveLocalizedContentOptions';
6
+ //# sourceMappingURL=index.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"index.d.ts","sourceRoot":"","sources":["../../../src/content/index.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,oBAAoB,EAAE,MAAM,wBAAwB,CAAA;AAC7D,OAAO,EAAE,qBAAqB,EAAE,MAAM,yBAAyB,CAAA;AAC/D,OAAO,EAAE,qBAAqB,EAAE,MAAM,yBAAyB,CAAA;AAC/D,OAAO,EAAE,uBAAuB,EAAE,MAAM,2BAA2B,CAAA;AACnE,YAAY,EAAE,8BAA8B,EAAE,MAAM,iDAAiD,CAAA"}
@@ -0,0 +1,13 @@
1
+ import { ResolveLocalizedContentOptions } from '../types/content/ResolveLocalizedContentOptions';
2
+ /**
3
+ * Resolves the language to render content in.
4
+ *
5
+ * Editor path: the selected language tab wins. Runtime path: the explicit
6
+ * `contentLanguage` is trusted first so the article language matches the rest of
7
+ * the UI, with preview-URL sniffing only as a fallback. Both paths fall back to
8
+ * `contentLanguage ?? defaultLanguage`.
9
+ * @param {ResolveLocalizedContentOptions} options - The resolution options.
10
+ * @returns {string} The resolved active language code.
11
+ */
12
+ export declare const resolveActiveLanguage: (options: ResolveLocalizedContentOptions) => string;
13
+ //# sourceMappingURL=resolveActiveLanguage.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"resolveActiveLanguage.d.ts","sourceRoot":"","sources":["../../../src/content/resolveActiveLanguage.ts"],"names":[],"mappings":"AAAA,OAAO,KAAK,EAAE,8BAA8B,EAAE,MAAM,iDAAiD,CAAA;AAIrG;;;;;;;;;GASG;AACH,eAAO,MAAM,qBAAqB,GAChC,SAAS,8BAA8B,KACtC,MAOF,CAAA"}
@@ -0,0 +1,15 @@
1
+ import { LocalizedContent } from '../types/content/LocalizedContent';
2
+ import { ResolveLocalizedContentOptions } from '../types/content/ResolveLocalizedContentOptions';
3
+ /**
4
+ * Selects and field-merges the localized article content for the active language.
5
+ *
6
+ * Resolves the active language (see resolveActiveLanguage), picks that language's
7
+ * content (falling back to the default language), then fills each field from the
8
+ * default-language entry when the active one is empty. Returns null and reports
9
+ * via `onError` when contents are missing or unavailable in both languages.
10
+ * @param {Record<string, LocalizedContent> | undefined} contents - The article's per-language contents.
11
+ * @param {ResolveLocalizedContentOptions} options - Language and diagnostics options.
12
+ * @returns {LocalizedContent | null} The merged localized content, or null.
13
+ */
14
+ export declare const resolveLocalizedContent: (contents: Record<string, LocalizedContent> | undefined, options: ResolveLocalizedContentOptions) => LocalizedContent | null;
15
+ //# sourceMappingURL=resolveLocalizedContent.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"resolveLocalizedContent.d.ts","sourceRoot":"","sources":["../../../src/content/resolveLocalizedContent.ts"],"names":[],"mappings":"AAAA,OAAO,KAAK,EAAE,gBAAgB,EAAE,MAAM,mCAAmC,CAAA;AACzE,OAAO,KAAK,EAAE,8BAA8B,EAAE,MAAM,iDAAiD,CAAA;AAGrG;;;;;;;;;;GAUG;AACH,eAAO,MAAM,uBAAuB,GAClC,UAAU,MAAM,CAAC,MAAM,EAAE,gBAAgB,CAAC,GAAG,SAAS,EACtD,SAAS,8BAA8B,KACtC,gBAAgB,GAAG,IA2BrB,CAAA"}
@@ -0,0 +1,17 @@
1
+ import { ArticleImageVariant } from './ArticleImageVariant';
2
+ /**
3
+ * The set of rendition variants the Staffbase media API returns for an article
4
+ * image. Named `ArticleImage` (not `Image`) to avoid shadowing the DOM global.
5
+ */
6
+ export interface ArticleImage {
7
+ original: ArticleImageVariant & {
8
+ size: number;
9
+ };
10
+ original_scaled: ArticleImageVariant;
11
+ thumb: ArticleImageVariant;
12
+ wide: ArticleImageVariant;
13
+ compact: ArticleImageVariant;
14
+ wide_first: ArticleImageVariant;
15
+ compact_first: ArticleImageVariant;
16
+ }
17
+ //# sourceMappingURL=ArticleImage.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"ArticleImage.d.ts","sourceRoot":"","sources":["../../../../src/types/content/ArticleImage.ts"],"names":[],"mappings":"AAAA,OAAO,KAAK,EAAE,mBAAmB,EAAE,MAAM,uBAAuB,CAAA;AAEhE;;;GAGG;AACH,MAAM,WAAW,YAAY;IAC3B,QAAQ,EAAE,mBAAmB,GAAG;QAAE,IAAI,EAAE,MAAM,CAAA;KAAE,CAAA;IAChD,eAAe,EAAE,mBAAmB,CAAA;IACpC,KAAK,EAAE,mBAAmB,CAAA;IAC1B,IAAI,EAAE,mBAAmB,CAAA;IACzB,OAAO,EAAE,mBAAmB,CAAA;IAC5B,UAAU,EAAE,mBAAmB,CAAA;IAC/B,aAAa,EAAE,mBAAmB,CAAA;CACnC"}
@@ -0,0 +1,13 @@
1
+ /**
2
+ * A single rendition of an article image (a size/format variant returned by the
3
+ * Staffbase media API). `size` is only present on the original variant.
4
+ */
5
+ export interface ArticleImageVariant {
6
+ width: number;
7
+ height: number;
8
+ size?: number;
9
+ format: string | null;
10
+ mimeType: string | null;
11
+ url: string;
12
+ }
13
+ //# sourceMappingURL=ArticleImageVariant.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"ArticleImageVariant.d.ts","sourceRoot":"","sources":["../../../../src/types/content/ArticleImageVariant.ts"],"names":[],"mappings":"AAAA;;;GAGG;AACH,MAAM,WAAW,mBAAmB;IAClC,KAAK,EAAE,MAAM,CAAA;IACb,MAAM,EAAE,MAAM,CAAA;IACd,IAAI,CAAC,EAAE,MAAM,CAAA;IACb,MAAM,EAAE,MAAM,GAAG,IAAI,CAAA;IACrB,QAAQ,EAAE,MAAM,GAAG,IAAI,CAAA;IACvB,GAAG,EAAE,MAAM,CAAA;CACZ"}
@@ -0,0 +1,16 @@
1
+ import { ArticleImage } from './ArticleImage';
2
+ /**
3
+ * The per-language content of an article (one entry of `ArticleData.contents`).
4
+ *
5
+ * `image` is `ArticleImage | string | null` because the API returns either the
6
+ * structured rendition set, a bare URL string, or nothing. Shared verbatim by
7
+ * the alerts and unacknowledged-bulletins widgets.
8
+ */
9
+ export interface LocalizedContent {
10
+ title: string;
11
+ teaser: string;
12
+ content: string;
13
+ image: ArticleImage | string | null;
14
+ feedImage: string | null;
15
+ }
16
+ //# sourceMappingURL=LocalizedContent.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"LocalizedContent.d.ts","sourceRoot":"","sources":["../../../../src/types/content/LocalizedContent.ts"],"names":[],"mappings":"AAAA,OAAO,KAAK,EAAE,YAAY,EAAE,MAAM,gBAAgB,CAAA;AAElD;;;;;;GAMG;AACH,MAAM,WAAW,gBAAgB;IAC/B,KAAK,EAAE,MAAM,CAAA;IACb,MAAM,EAAE,MAAM,CAAA;IACd,OAAO,EAAE,MAAM,CAAA;IACf,KAAK,EAAE,YAAY,GAAG,MAAM,GAAG,IAAI,CAAA;IACnC,SAAS,EAAE,MAAM,GAAG,IAAI,CAAA;CACzB"}
@@ -0,0 +1,24 @@
1
+ /**
2
+ * Options for resolveLocalizedContent.
3
+ */
4
+ export interface ResolveLocalizedContentOptions {
5
+ /**
6
+ * Language explicitly requested by the host/widget config. On the runtime path
7
+ * this is trusted first so the article language matches the rest of the UI;
8
+ * DOM/URL sniffing is only a fallback.
9
+ */
10
+ contentLanguage?: string;
11
+ /** Fallback language. Injected because the library never reads env. */
12
+ defaultLanguage: string;
13
+ /** When true, resolves the active language from the editor's selected tab. */
14
+ isEditor?: boolean;
15
+ /**
16
+ * Called with a diagnostic message when content cannot be resolved (the
17
+ * library does not log directly).
18
+ * @param {string} message - The diagnostic message.
19
+ * @param {...unknown} args - Optional extra context.
20
+ * @returns {void} Nothing.
21
+ */
22
+ onError?: (message: string, ...args: unknown[]) => void;
23
+ }
24
+ //# sourceMappingURL=ResolveLocalizedContentOptions.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"ResolveLocalizedContentOptions.d.ts","sourceRoot":"","sources":["../../../../src/types/content/ResolveLocalizedContentOptions.ts"],"names":[],"mappings":"AAAA;;GAEG;AACH,MAAM,WAAW,8BAA8B;IAC7C;;;;OAIG;IACH,eAAe,CAAC,EAAE,MAAM,CAAA;IACxB,uEAAuE;IACvE,eAAe,EAAE,MAAM,CAAA;IACvB,8EAA8E;IAC9E,QAAQ,CAAC,EAAE,OAAO,CAAA;IAClB;;;;;;OAMG;IACH,OAAO,CAAC,EAAE,CAAC,OAAO,EAAE,MAAM,EAAE,GAAG,IAAI,EAAE,OAAO,EAAE,KAAK,IAAI,CAAA;CACxD"}
@@ -1,5 +1,8 @@
1
+ export type { ArticleImage } from './ArticleImage';
2
+ export type { ArticleImageVariant } from './ArticleImageVariant';
1
3
  export type { Channel } from './Channel';
2
4
  export type { ChannelLink } from './ChannelLink';
3
5
  export type { ChannelLinkParameter } from './ChannelLinkParameter';
4
6
  export type { DropdownOption } from './DropdownOption';
7
+ export type { LocalizedContent } from './LocalizedContent';
5
8
  //# sourceMappingURL=index.d.ts.map
@@ -1 +1 @@
1
- {"version":3,"file":"index.d.ts","sourceRoot":"","sources":["../../../../src/types/content/index.ts"],"names":[],"mappings":"AAAA,YAAY,EAAE,OAAO,EAAE,MAAM,WAAW,CAAA;AACxC,YAAY,EAAE,WAAW,EAAE,MAAM,eAAe,CAAA;AAChD,YAAY,EAAE,oBAAoB,EAAE,MAAM,wBAAwB,CAAA;AAClE,YAAY,EAAE,cAAc,EAAE,MAAM,kBAAkB,CAAA"}
1
+ {"version":3,"file":"index.d.ts","sourceRoot":"","sources":["../../../../src/types/content/index.ts"],"names":[],"mappings":"AAAA,YAAY,EAAE,YAAY,EAAE,MAAM,gBAAgB,CAAA;AAClD,YAAY,EAAE,mBAAmB,EAAE,MAAM,uBAAuB,CAAA;AAChE,YAAY,EAAE,OAAO,EAAE,MAAM,WAAW,CAAA;AACxC,YAAY,EAAE,WAAW,EAAE,MAAM,eAAe,CAAA;AAChD,YAAY,EAAE,oBAAoB,EAAE,MAAM,wBAAwB,CAAA;AAClE,YAAY,EAAE,cAAc,EAAE,MAAM,kBAAkB,CAAA;AACtD,YAAY,EAAE,gBAAgB,EAAE,MAAM,oBAAoB,CAAA"}
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@favish/staffbase-utils",
3
- "version": "0.10.0",
3
+ "version": "0.11.0",
4
4
  "description": "Shared internal/host utilities for Staffbase widgets",
5
5
  "author": "Favish <dev@favish.com>",
6
6
  "license": "UNLICENSED",
@@ -13,6 +13,11 @@
13
13
  "import": "./dist/api.es.mjs",
14
14
  "require": "./dist/api.cjs.js"
15
15
  },
16
+ "./content": {
17
+ "types": "./dist/src/content/index.d.ts",
18
+ "import": "./dist/content.es.mjs",
19
+ "require": "./dist/content.cjs.js"
20
+ },
16
21
  "./log": {
17
22
  "types": "./dist/src/log/index.d.ts",
18
23
  "import": "./dist/log.es.mjs",