@cmssy/next 4.0.1 → 4.1.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/dist/index.cjs +37 -26
- package/dist/index.d.cts +12 -2
- package/dist/index.d.ts +12 -2
- package/dist/index.js +38 -27
- package/package.json +3 -3
package/dist/index.cjs
CHANGED
|
@@ -586,23 +586,25 @@ function createCmssySitemap(config, options = {}) {
|
|
|
586
586
|
const baseUrl = await resolveSeoBaseUrl(config, options.baseUrl);
|
|
587
587
|
const { defaultLocale, locales } = resolveSeoLocales(config, siteConfig);
|
|
588
588
|
const excluded = new Set((options.excludeSlugs ?? []).map(normalizeSlug));
|
|
589
|
-
const
|
|
590
|
-
|
|
591
|
-
|
|
592
|
-
|
|
593
|
-
|
|
594
|
-
|
|
595
|
-
|
|
596
|
-
|
|
597
|
-
|
|
598
|
-
locales.map((locale) => [
|
|
599
|
-
locale,
|
|
600
|
-
`${baseUrl}${localizedPath(page.slug, locale, defaultLocale)}`
|
|
601
|
-
])
|
|
602
|
-
)
|
|
603
|
-
};
|
|
589
|
+
const languagesFor = (slug) => locales.length > 1 ? {
|
|
590
|
+
languages: {
|
|
591
|
+
...Object.fromEntries(
|
|
592
|
+
locales.map((locale) => [
|
|
593
|
+
locale,
|
|
594
|
+
`${baseUrl}${localizedPath(slug, locale, defaultLocale)}`
|
|
595
|
+
])
|
|
596
|
+
),
|
|
597
|
+
"x-default": `${baseUrl}${localizedPath(slug, defaultLocale, defaultLocale)}`
|
|
604
598
|
}
|
|
605
|
-
|
|
599
|
+
} : void 0;
|
|
600
|
+
const entries = pages.map((page) => ({ ...page, slug: normalizeSlug(page.slug) })).filter((page) => page.id !== notFoundPageId && !excluded.has(page.slug)).flatMap((page) => {
|
|
601
|
+
const lastModified = page.updatedAt ?? page.publishedAt ?? void 0;
|
|
602
|
+
const alternates = languagesFor(page.slug);
|
|
603
|
+
return locales.map((locale) => ({
|
|
604
|
+
url: `${baseUrl}${localizedPath(page.slug, locale, defaultLocale)}`,
|
|
605
|
+
...lastModified ? { lastModified: new Date(lastModified) } : {},
|
|
606
|
+
...alternates ? { alternates } : {}
|
|
607
|
+
}));
|
|
606
608
|
});
|
|
607
609
|
return options.extra ? [...entries, ...options.extra] : entries;
|
|
608
610
|
};
|
|
@@ -618,8 +620,7 @@ async function buildCmssyMetadata(config, path, options = {}) {
|
|
|
618
620
|
org: config.org,
|
|
619
621
|
workspaceSlug: config.workspaceSlug
|
|
620
622
|
};
|
|
621
|
-
const [
|
|
622
|
-
react.fetchPageMeta(clientConfig, path).catch(() => null),
|
|
623
|
+
const [siteConfig, baseUrl] = await Promise.all([
|
|
623
624
|
react.fetchSiteConfig(clientConfig).catch(() => null),
|
|
624
625
|
resolveSeoBaseUrl(config, options.baseUrl)
|
|
625
626
|
]);
|
|
@@ -627,20 +628,30 @@ async function buildCmssyMetadata(config, path, options = {}) {
|
|
|
627
628
|
config,
|
|
628
629
|
siteConfig
|
|
629
630
|
);
|
|
630
|
-
const
|
|
631
|
-
const
|
|
631
|
+
const segments = Array.isArray(path) ? path : path ? path.split("/").filter(Boolean) : void 0;
|
|
632
|
+
const fromPath = react.splitLocaleFromPath(segments, {
|
|
633
|
+
defaultLocale,
|
|
634
|
+
locales: enabledLocales
|
|
635
|
+
});
|
|
636
|
+
const locale = options.locale ?? (fromPath.locale !== defaultLocale ? fromPath.locale : await config.resolveLocale?.() ?? defaultLocale);
|
|
637
|
+
const slug = react.normalizeSlug(fromPath.path);
|
|
638
|
+
const meta = await react.fetchPageMeta(clientConfig, slug).catch(() => null);
|
|
632
639
|
const siteName = pick(siteConfig?.siteName, locale, defaultLocale) || siteConfig?.branding?.brandName || void 0;
|
|
633
640
|
const title = pick(meta?.seoTitle, locale, defaultLocale) || pick(meta?.displayName, locale, defaultLocale) || siteName || "";
|
|
634
641
|
const description = pick(meta?.seoDescription, locale, defaultLocale);
|
|
635
642
|
const keywords = meta?.seoKeywords?.length ? meta.seoKeywords : void 0;
|
|
636
643
|
const image = options.image ?? siteConfig?.branding?.ogImageUrl ?? void 0;
|
|
637
644
|
const canonical = baseUrl ? `${baseUrl}${localizedPath(slug, locale, defaultLocale)}` : void 0;
|
|
638
|
-
const languages = baseUrl && enabledLocales.length > 1 ?
|
|
639
|
-
|
|
640
|
-
l
|
|
641
|
-
|
|
642
|
-
|
|
643
|
-
|
|
645
|
+
const languages = baseUrl && enabledLocales.length > 1 ? {
|
|
646
|
+
...Object.fromEntries(
|
|
647
|
+
enabledLocales.map((l) => [
|
|
648
|
+
l,
|
|
649
|
+
`${baseUrl}${localizedPath(slug, l, defaultLocale)}`
|
|
650
|
+
])
|
|
651
|
+
),
|
|
652
|
+
// What to serve a reader whose language none of these match.
|
|
653
|
+
"x-default": `${baseUrl}${localizedPath(slug, defaultLocale, defaultLocale)}`
|
|
654
|
+
} : void 0;
|
|
644
655
|
return {
|
|
645
656
|
...baseUrl ? { metadataBase: new URL(baseUrl) } : {},
|
|
646
657
|
...title ? { title } : {},
|
package/dist/index.d.cts
CHANGED
|
@@ -206,6 +206,12 @@ interface BuildCmssyMetadataOptions extends SeoBaseUrlOption {
|
|
|
206
206
|
ogType?: string;
|
|
207
207
|
/** Twitter card. Defaults to "summary_large_image" when an image exists. */
|
|
208
208
|
twitterCard?: "summary" | "summary_large_image";
|
|
209
|
+
/**
|
|
210
|
+
* The language to render metadata in. Only needed when the language does not
|
|
211
|
+
* live in the URL (a per-domain or cookie strategy); with a locale prefix the
|
|
212
|
+
* path already says it.
|
|
213
|
+
*/
|
|
214
|
+
locale?: string;
|
|
209
215
|
}
|
|
210
216
|
/**
|
|
211
217
|
* Builds complete Next.js `Metadata` for a cmssy page from its SEO fields and
|
|
@@ -213,10 +219,14 @@ interface BuildCmssyMetadataOptions extends SeoBaseUrlOption {
|
|
|
213
219
|
* `hreflang` alternates, and Open Graph / Twitter cards (with the branding OG
|
|
214
220
|
* image). Use in a route's `generateMetadata`:
|
|
215
221
|
*
|
|
216
|
-
* export const generateMetadata = ({ params }) =>
|
|
222
|
+
* export const generateMetadata = async ({ params }) =>
|
|
217
223
|
* buildCmssyMetadata(cmssy, (await params).path);
|
|
218
224
|
*
|
|
219
|
-
*
|
|
225
|
+
* Pass the catch-all segments **as routed**, locale prefix and all: the prefix
|
|
226
|
+
* is what says which language this page is. Stripping it first (and leaving the
|
|
227
|
+
* language to `config.resolveLocale`) is how every localized page ends up with
|
|
228
|
+
* the default language's title - and a canonical pointing at the default
|
|
229
|
+
* language's URL, which tells Google the translation is a duplicate.
|
|
220
230
|
*/
|
|
221
231
|
declare function buildCmssyMetadata(config: CmssyNextConfig, path?: string | string[], options?: BuildCmssyMetadataOptions): Promise<Metadata>;
|
|
222
232
|
|
package/dist/index.d.ts
CHANGED
|
@@ -206,6 +206,12 @@ interface BuildCmssyMetadataOptions extends SeoBaseUrlOption {
|
|
|
206
206
|
ogType?: string;
|
|
207
207
|
/** Twitter card. Defaults to "summary_large_image" when an image exists. */
|
|
208
208
|
twitterCard?: "summary" | "summary_large_image";
|
|
209
|
+
/**
|
|
210
|
+
* The language to render metadata in. Only needed when the language does not
|
|
211
|
+
* live in the URL (a per-domain or cookie strategy); with a locale prefix the
|
|
212
|
+
* path already says it.
|
|
213
|
+
*/
|
|
214
|
+
locale?: string;
|
|
209
215
|
}
|
|
210
216
|
/**
|
|
211
217
|
* Builds complete Next.js `Metadata` for a cmssy page from its SEO fields and
|
|
@@ -213,10 +219,14 @@ interface BuildCmssyMetadataOptions extends SeoBaseUrlOption {
|
|
|
213
219
|
* `hreflang` alternates, and Open Graph / Twitter cards (with the branding OG
|
|
214
220
|
* image). Use in a route's `generateMetadata`:
|
|
215
221
|
*
|
|
216
|
-
* export const generateMetadata = ({ params }) =>
|
|
222
|
+
* export const generateMetadata = async ({ params }) =>
|
|
217
223
|
* buildCmssyMetadata(cmssy, (await params).path);
|
|
218
224
|
*
|
|
219
|
-
*
|
|
225
|
+
* Pass the catch-all segments **as routed**, locale prefix and all: the prefix
|
|
226
|
+
* is what says which language this page is. Stripping it first (and leaving the
|
|
227
|
+
* language to `config.resolveLocale`) is how every localized page ends up with
|
|
228
|
+
* the default language's title - and a canonical pointing at the default
|
|
229
|
+
* language's URL, which tells Google the translation is a duplicate.
|
|
220
230
|
*/
|
|
221
231
|
declare function buildCmssyMetadata(config: CmssyNextConfig, path?: string | string[], options?: BuildCmssyMetadataOptions): Promise<Metadata>;
|
|
222
232
|
|
package/dist/index.js
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
import { headers, draftMode, cookies } from 'next/headers';
|
|
2
2
|
import { notFound, redirect } from 'next/navigation';
|
|
3
|
-
import { createCmssyClient, resolveSiteLocales, splitLocaleFromPath, fetchPage, resolveForms, CmssyServerPage, fetchSiteConfig, fetchPageById, fetchPages,
|
|
3
|
+
import { createCmssyClient, resolveSiteLocales, splitLocaleFromPath, fetchPage, resolveForms, CmssyServerPage, fetchSiteConfig, fetchPageById, fetchPages, normalizeSlug as normalizeSlug$1, fetchPageMeta, resolveWorkspaceId, graphqlRequest, resolveApiUrl } from '@cmssy/react';
|
|
4
4
|
export { DEFAULT_CMSSY_API_URL, evaluateFieldConditionGroup, resolveApiUrl } from '@cmssy/react';
|
|
5
5
|
import { CmssyLocaleProvider } from '@cmssy/react/client';
|
|
6
6
|
import { EncryptJWT, jwtDecrypt } from 'jose';
|
|
@@ -585,23 +585,25 @@ function createCmssySitemap(config, options = {}) {
|
|
|
585
585
|
const baseUrl = await resolveSeoBaseUrl(config, options.baseUrl);
|
|
586
586
|
const { defaultLocale, locales } = resolveSeoLocales(config, siteConfig);
|
|
587
587
|
const excluded = new Set((options.excludeSlugs ?? []).map(normalizeSlug));
|
|
588
|
-
const
|
|
589
|
-
|
|
590
|
-
|
|
591
|
-
|
|
592
|
-
|
|
593
|
-
|
|
594
|
-
|
|
595
|
-
|
|
596
|
-
|
|
597
|
-
locales.map((locale) => [
|
|
598
|
-
locale,
|
|
599
|
-
`${baseUrl}${localizedPath(page.slug, locale, defaultLocale)}`
|
|
600
|
-
])
|
|
601
|
-
)
|
|
602
|
-
};
|
|
588
|
+
const languagesFor = (slug) => locales.length > 1 ? {
|
|
589
|
+
languages: {
|
|
590
|
+
...Object.fromEntries(
|
|
591
|
+
locales.map((locale) => [
|
|
592
|
+
locale,
|
|
593
|
+
`${baseUrl}${localizedPath(slug, locale, defaultLocale)}`
|
|
594
|
+
])
|
|
595
|
+
),
|
|
596
|
+
"x-default": `${baseUrl}${localizedPath(slug, defaultLocale, defaultLocale)}`
|
|
603
597
|
}
|
|
604
|
-
|
|
598
|
+
} : void 0;
|
|
599
|
+
const entries = pages.map((page) => ({ ...page, slug: normalizeSlug(page.slug) })).filter((page) => page.id !== notFoundPageId && !excluded.has(page.slug)).flatMap((page) => {
|
|
600
|
+
const lastModified = page.updatedAt ?? page.publishedAt ?? void 0;
|
|
601
|
+
const alternates = languagesFor(page.slug);
|
|
602
|
+
return locales.map((locale) => ({
|
|
603
|
+
url: `${baseUrl}${localizedPath(page.slug, locale, defaultLocale)}`,
|
|
604
|
+
...lastModified ? { lastModified: new Date(lastModified) } : {},
|
|
605
|
+
...alternates ? { alternates } : {}
|
|
606
|
+
}));
|
|
605
607
|
});
|
|
606
608
|
return options.extra ? [...entries, ...options.extra] : entries;
|
|
607
609
|
};
|
|
@@ -617,8 +619,7 @@ async function buildCmssyMetadata(config, path, options = {}) {
|
|
|
617
619
|
org: config.org,
|
|
618
620
|
workspaceSlug: config.workspaceSlug
|
|
619
621
|
};
|
|
620
|
-
const [
|
|
621
|
-
fetchPageMeta(clientConfig, path).catch(() => null),
|
|
622
|
+
const [siteConfig, baseUrl] = await Promise.all([
|
|
622
623
|
fetchSiteConfig(clientConfig).catch(() => null),
|
|
623
624
|
resolveSeoBaseUrl(config, options.baseUrl)
|
|
624
625
|
]);
|
|
@@ -626,20 +627,30 @@ async function buildCmssyMetadata(config, path, options = {}) {
|
|
|
626
627
|
config,
|
|
627
628
|
siteConfig
|
|
628
629
|
);
|
|
629
|
-
const
|
|
630
|
-
const
|
|
630
|
+
const segments = Array.isArray(path) ? path : path ? path.split("/").filter(Boolean) : void 0;
|
|
631
|
+
const fromPath = splitLocaleFromPath(segments, {
|
|
632
|
+
defaultLocale,
|
|
633
|
+
locales: enabledLocales
|
|
634
|
+
});
|
|
635
|
+
const locale = options.locale ?? (fromPath.locale !== defaultLocale ? fromPath.locale : await config.resolveLocale?.() ?? defaultLocale);
|
|
636
|
+
const slug = normalizeSlug$1(fromPath.path);
|
|
637
|
+
const meta = await fetchPageMeta(clientConfig, slug).catch(() => null);
|
|
631
638
|
const siteName = pick(siteConfig?.siteName, locale, defaultLocale) || siteConfig?.branding?.brandName || void 0;
|
|
632
639
|
const title = pick(meta?.seoTitle, locale, defaultLocale) || pick(meta?.displayName, locale, defaultLocale) || siteName || "";
|
|
633
640
|
const description = pick(meta?.seoDescription, locale, defaultLocale);
|
|
634
641
|
const keywords = meta?.seoKeywords?.length ? meta.seoKeywords : void 0;
|
|
635
642
|
const image = options.image ?? siteConfig?.branding?.ogImageUrl ?? void 0;
|
|
636
643
|
const canonical = baseUrl ? `${baseUrl}${localizedPath(slug, locale, defaultLocale)}` : void 0;
|
|
637
|
-
const languages = baseUrl && enabledLocales.length > 1 ?
|
|
638
|
-
|
|
639
|
-
l
|
|
640
|
-
|
|
641
|
-
|
|
642
|
-
|
|
644
|
+
const languages = baseUrl && enabledLocales.length > 1 ? {
|
|
645
|
+
...Object.fromEntries(
|
|
646
|
+
enabledLocales.map((l) => [
|
|
647
|
+
l,
|
|
648
|
+
`${baseUrl}${localizedPath(slug, l, defaultLocale)}`
|
|
649
|
+
])
|
|
650
|
+
),
|
|
651
|
+
// What to serve a reader whose language none of these match.
|
|
652
|
+
"x-default": `${baseUrl}${localizedPath(slug, defaultLocale, defaultLocale)}`
|
|
653
|
+
} : void 0;
|
|
643
654
|
return {
|
|
644
655
|
...baseUrl ? { metadataBase: new URL(baseUrl) } : {},
|
|
645
656
|
...title ? { title } : {},
|
package/package.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "@cmssy/next",
|
|
3
|
-
"version": "4.0
|
|
3
|
+
"version": "4.1.0",
|
|
4
4
|
"description": "Next.js App Router bindings for cmssy headless sites (createCmssyPage + draft preview)",
|
|
5
5
|
"keywords": [
|
|
6
6
|
"cmssy",
|
|
@@ -41,7 +41,7 @@
|
|
|
41
41
|
"dist"
|
|
42
42
|
],
|
|
43
43
|
"peerDependencies": {
|
|
44
|
-
"@cmssy/react": "^4.0
|
|
44
|
+
"@cmssy/react": "^4.1.0",
|
|
45
45
|
"next": ">=15",
|
|
46
46
|
"react": "^18.2.0 || ^19.0.0",
|
|
47
47
|
"react-dom": "^18.2.0 || ^19.0.0"
|
|
@@ -55,7 +55,7 @@
|
|
|
55
55
|
"tsup": "^8.3.0",
|
|
56
56
|
"typescript": "^5.6.0",
|
|
57
57
|
"vitest": "^2.1.0",
|
|
58
|
-
"@cmssy/react": "4.0
|
|
58
|
+
"@cmssy/react": "4.1.0"
|
|
59
59
|
},
|
|
60
60
|
"dependencies": {
|
|
61
61
|
"jose": "^6.2.3",
|