Skip to content
This repository was archived by the owner on May 10, 2021. It is now read-only.

Commit 2b7c6e0

Browse files
committed
rough pass at i18n ssg breaking changes in next 10
1 parent ee478cf commit 2b7c6e0

File tree

8 files changed

+1332
-1008
lines changed

8 files changed

+1332
-1008
lines changed
Lines changed: 19 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,19 @@
1+
const { join } = require("path");
2+
const { readFileSync } = require("fs-extra");
3+
const { NEXT_DIST_DIR } = require("../config");
4+
const getFilePathForRoute = require("./getFilePathForRoute");
5+
6+
// TO-DO: make more DRY with other getDataRoute helper
7+
8+
// Get build ID that is used for data routes, e.g. /_next/data/BUILD_ID/...
9+
const fileContents = readFileSync(join(NEXT_DIST_DIR, "BUILD_ID"));
10+
const buildId = fileContents.toString();
11+
12+
// Return the data route for the given route
13+
const getDataRouteForI18nRoute = (route, locale) => {
14+
const filePath = getFilePathForRoute(route, "json");
15+
16+
return join("/_next", "data", buildId, locale, filePath);
17+
};
18+
19+
module.exports = getDataRouteForI18nRoute;
Lines changed: 8 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,8 @@
1+
// Next apps with i18n have statically generated html for/under each locale
2+
const getFilePathForRoute = require("./getFilePathForRoute");
3+
4+
const getFilePathForRouteWithI18n = (route, extension, locale) => {
5+
return `${locale}${getFilePathForRoute(route, extension)}`;
6+
};
7+
8+
module.exports = getFilePathForRouteWithI18n;

lib/pages/getStaticProps/redirects.js

Lines changed: 38 additions & 15 deletions
Original file line numberDiff line numberDiff line change
@@ -1,6 +1,8 @@
11
const { join } = require("path");
22
const getFilePathForRoute = require("../../helpers/getFilePathForRoute");
3+
const getFilePathForRouteWithI18n = require("../../helpers/getFilePathForRouteWithI18n");
34
const getNetlifyFunctionName = require("../../helpers/getNetlifyFunctionName");
5+
const getNextConfig = require("../../helpers/getNextConfig");
46
const pages = require("./pages");
57

68
// Pages with getStaticProps (without fallback or revalidation) only need
@@ -15,22 +17,43 @@ pages.forEach(({ route, dataRoute, srcRoute }) => {
1517
const conditions = ["Cookie=__prerender_bypass,__next_preview_data"];
1618
const target = `/.netlify/functions/${functionName}`;
1719

18-
// Add one redirect for the page, but only when the NextJS
19-
// preview mode cookies are present
20-
redirects.push({
21-
route,
22-
target,
23-
force: true,
24-
conditions,
25-
});
20+
const nextConfig = getNextConfig();
21+
if (nextConfig.i18n) {
22+
const { locales } = nextConfig.i18n;
23+
locales.forEach((locale) => {
24+
const pageRoute = srcRoute ? route : `${locale}${route}`;
25+
const dataRoute_ = srcRoute ? dataRoute : `${locale}${dataRoute}`;
26+
redirects.push({
27+
route: pageRoute,
28+
target,
29+
force: true,
30+
conditions,
31+
});
32+
redirects.push({
33+
route: dataRoute_,
34+
target,
35+
force: true,
36+
conditions,
37+
});
38+
});
39+
} else {
40+
// Add one redirect for the page, but only when the NextJS
41+
// preview mode cookies are present
42+
redirects.push({
43+
route,
44+
target,
45+
force: true,
46+
conditions,
47+
});
2648

27-
// Add one redirect for the data route, same conditions
28-
redirects.push({
29-
route: dataRoute,
30-
target,
31-
force: true,
32-
conditions,
33-
});
49+
// Add one redirect for the data route, same conditions
50+
redirects.push({
51+
route: dataRoute,
52+
target,
53+
force: true,
54+
conditions,
55+
});
56+
}
3457
});
3558

3659
module.exports = redirects;

lib/pages/getStaticProps/setup.js

Lines changed: 60 additions & 11 deletions
Original file line numberDiff line numberDiff line change
@@ -1,6 +1,9 @@
11
const { join } = require("path");
22
const { logTitle, logItem } = require("../../helpers/logger");
3+
const getDataRouteForI18nRoute = require("../../helpers/getDataRouteForI18nRoute");
34
const getFilePathForRoute = require("../../helpers/getFilePathForRoute");
5+
const getFilePathForRouteWithI18n = require("../../helpers/getFilePathForRouteWithI18n");
6+
const getNextConfig = require("../../helpers/getNextConfig");
47
const isRouteWithFallback = require("../../helpers/isRouteWithFallback");
58
const setupStaticFileForPage = require("../../helpers/setupStaticFileForPage");
69
const setupNetlifyFunctionForPage = require("../../helpers/setupNetlifyFunctionForPage");
@@ -20,17 +23,63 @@ const setup = ({ functionsPath, publishPath }) => {
2023
pages.forEach(({ route, dataRoute, srcRoute }) => {
2124
logItem(route);
2225

23-
// Copy pre-rendered HTML page
24-
const htmlPath = getFilePathForRoute(route, "html");
25-
setupStaticFileForPage({ inputPath: htmlPath, publishPath });
26-
27-
// Copy page's JSON data
28-
const jsonPath = getFilePathForRoute(route, "json");
29-
setupStaticFileForPage({
30-
inputPath: jsonPath,
31-
outputPath: dataRoute,
32-
publishPath,
33-
});
26+
const nextConfig = getNextConfig();
27+
28+
// If an app is using Next 10+'s i18n feature, next will put statically
29+
// generated files under a different path for each different locale
30+
if (nextConfig.i18n) {
31+
const { locales } = nextConfig.i18n;
32+
if (!locales || locales.length === 0) return;
33+
34+
const isNotDynamic = !srcRoute;
35+
// Dynamic routes don't need special helper, Next auto prepends with locale
36+
// in prerender-manifest, but static routes are missing locale
37+
if (isNotDynamic) {
38+
locales.forEach((locale) => {
39+
// Copy pre-rendered HTML page
40+
const route_ = route === "/" ? "" : route;
41+
const htmlPath = getFilePathForRouteWithI18n(route_, "html", locale);
42+
setupStaticFileForPage({ inputPath: htmlPath, publishPath });
43+
44+
const jsonPath = getFilePathForRouteWithI18n(route_, "json", locale);
45+
46+
// the actual route to the json is under pages/{locale}
47+
// but the dataRoutes are the same for all locales according to
48+
// prerender-manifest..
49+
const realJsonDataRoute = getDataRouteForI18nRoute(route, locale);
50+
setupStaticFileForPage({
51+
inputPath: jsonPath,
52+
outputPath: realJsonDataRoute,
53+
publishPath,
54+
});
55+
});
56+
} else {
57+
// Copy pre-rendered HTML page
58+
const htmlPath = getFilePathForRoute(route, "html");
59+
setupStaticFileForPage({ inputPath: htmlPath, publishPath });
60+
61+
// Copy page's JSON data
62+
const jsonPath = getFilePathForRoute(route, "json");
63+
setupStaticFileForPage({
64+
inputPath: jsonPath,
65+
outputPath: dataRoute,
66+
publishPath,
67+
});
68+
}
69+
// TO-DO combine these conditions
70+
} else {
71+
// Copy pre-rendered HTML page
72+
const htmlPath = getFilePathForRoute(route, "html");
73+
setupStaticFileForPage({ inputPath: htmlPath, publishPath });
74+
75+
// Copy page's JSON data
76+
const jsonPath = getFilePathForRoute(route, "json");
77+
setupStaticFileForPage({
78+
inputPath: jsonPath,
79+
outputPath: dataRoute,
80+
publishPath,
81+
});
82+
}
3483

3584
// // Set up the Netlify function (this is ONLY for preview mode)
3685
const relativePath = getFilePathForRoute(srcRoute || route, "js");

0 commit comments

Comments
 (0)