import { normalizeLocalePath } from '../../shared/lib/i18n/normalize-locale-path';
import { parseStaticPathsResult } from '../../lib/fallback';
import escapePathDelimiters from '../../shared/lib/router/utils/escape-path-delimiters';
import { removeTrailingSlash } from '../../shared/lib/router/utils/remove-trailing-slash';
import { getRouteMatcher } from '../../shared/lib/router/utils/route-matcher';
import { getRouteRegex } from '../../shared/lib/router/utils/route-regex';
import { encodeParam, normalizePathname } from './utils';
export async function buildPagesStaticPaths({ page, getStaticPaths, configFileName, locales, defaultLocale }) {
    const prerenderedRoutesByPathname = new Map();
    const _routeRegex = getRouteRegex(page);
    const _routeMatcher = getRouteMatcher(_routeRegex);
    // Get the default list of allowed params.
    const routeParameterKeys = Object.keys(_routeMatcher(page));
    const staticPathsResult = await getStaticPaths({
        // We create a copy here to avoid having the types of `getStaticPaths`
        // change. This ensures that users can't mutate this array and have it
        // poison the reference.
        locales: [
            ...locales ?? []
        ],
        defaultLocale
    });
    const expectedReturnVal = `Expected: { paths: [], fallback: boolean }\n` + `See here for more info: https://nextjs.org/docs/messages/invalid-getstaticpaths-value`;
    if (!staticPathsResult || typeof staticPathsResult !== 'object' || Array.isArray(staticPathsResult)) {
        throw Object.defineProperty(new Error(`Invalid value returned from getStaticPaths in ${page}. Received ${typeof staticPathsResult} ${expectedReturnVal}`), "__NEXT_ERROR_CODE", {
            value: "E1004",
            enumerable: false,
            configurable: true
        });
    }
    const invalidStaticPathKeys = Object.keys(staticPathsResult).filter((key)=>!(key === 'paths' || key === 'fallback'));
    if (invalidStaticPathKeys.length > 0) {
        throw Object.defineProperty(new Error(`Extra keys returned from getStaticPaths in ${page} (${invalidStaticPathKeys.join(', ')}) ${expectedReturnVal}`), "__NEXT_ERROR_CODE", {
            value: "E1047",
            enumerable: false,
            configurable: true
        });
    }
    if (!(typeof staticPathsResult.fallback === 'boolean' || staticPathsResult.fallback === 'blocking')) {
        throw Object.defineProperty(new Error(`The \`fallback\` key must be returned from getStaticPaths in ${page}.\n` + expectedReturnVal), "__NEXT_ERROR_CODE", {
            value: "E1034",
            enumerable: false,
            configurable: true
        });
    }
    const toPrerender = staticPathsResult.paths;
    if (!Array.isArray(toPrerender)) {
        throw Object.defineProperty(new Error(`Invalid \`paths\` value returned from getStaticPaths in ${page}.\n` + `\`paths\` must be an array of strings or objects of shape { params: [key: string]: string }`), "__NEXT_ERROR_CODE", {
            value: "E83",
            enumerable: false,
            configurable: true
        });
    }
    toPrerender.forEach((entry)=>{
        // For a string-provided path, we must make sure it matches the dynamic
        // route.
        if (typeof entry === 'string') {
            entry = removeTrailingSlash(entry);
            const localePathResult = normalizeLocalePath(entry, locales);
            let cleanedEntry = entry;
            if (localePathResult.detectedLocale) {
                cleanedEntry = entry.slice(localePathResult.detectedLocale.length + 1);
            } else if (defaultLocale) {
                entry = `/${defaultLocale}${entry}`;
            }
            const params = _routeMatcher(cleanedEntry);
            if (!params) {
                throw Object.defineProperty(new Error(`The provided path \`${cleanedEntry}\` does not match the page: \`${page}\`.`), "__NEXT_ERROR_CODE", {
                    value: "E481",
                    enumerable: false,
                    configurable: true
                });
            }
            // If leveraging the string paths variant the entry should already be
            // encoded so we decode the segments ensuring we only escape path
            // delimiters
            const pathname = entry.split('/').map((segment)=>escapePathDelimiters(decodeURIComponent(segment), true)).join('/');
            if (!prerenderedRoutesByPathname.has(pathname)) {
                prerenderedRoutesByPathname.set(pathname, {
                    params,
                    pathname,
                    encodedPathname: entry,
                    fallbackRouteParams: undefined,
                    fallbackMode: parseStaticPathsResult(staticPathsResult.fallback),
                    fallbackRootParams: undefined,
                    throwOnEmptyStaticShell: undefined
                });
            }
        } else {
            const invalidKeys = Object.keys(entry).filter((key)=>key !== 'params' && key !== 'locale');
            if (invalidKeys.length) {
                throw Object.defineProperty(new Error(`Additional keys were returned from \`getStaticPaths\` in page "${page}". ` + `URL Parameters intended for this dynamic route must be nested under the \`params\` key, i.e.:` + `\n\n\treturn { params: { ${routeParameterKeys.map((k)=>`${k}: ...`).join(', ')} } }` + `\n\nKeys that need to be moved: ${invalidKeys.join(', ')}.\n`), "__NEXT_ERROR_CODE", {
                    value: "E322",
                    enumerable: false,
                    configurable: true
                });
            }
            const { params = {} } = entry;
            let builtPage = page;
            let encodedBuiltPage = page;
            routeParameterKeys.forEach((validParamKey)=>{
                const { repeat, optional } = _routeRegex.groups[validParamKey];
                let paramValue = params[validParamKey];
                if (optional && params.hasOwnProperty(validParamKey) && (paramValue === null || paramValue === undefined || paramValue === false)) {
                    paramValue = [];
                }
                if (repeat && !Array.isArray(paramValue) || !repeat && typeof paramValue !== 'string' || typeof paramValue === 'undefined') {
                    throw Object.defineProperty(new Error(`A required parameter (${validParamKey}) was not provided as ${repeat ? 'an array' : 'a string'} received ${typeof paramValue} in getStaticPaths for ${page}`), "__NEXT_ERROR_CODE", {
                        value: "E620",
                        enumerable: false,
                        configurable: true
                    });
                }
                let replaced = `[${repeat ? '...' : ''}${validParamKey}]`;
                if (optional) {
                    replaced = `[${replaced}]`;
                }
                builtPage = builtPage.replace(replaced, encodeParam(paramValue, (value)=>escapePathDelimiters(value, true)));
                encodedBuiltPage = encodedBuiltPage.replace(replaced, encodeParam(paramValue, encodeURIComponent));
            });
            if (!builtPage && !encodedBuiltPage) {
                return;
            }
            if (entry.locale && !(locales == null ? void 0 : locales.includes(entry.locale))) {
                throw Object.defineProperty(new Error(`Invalid locale returned from getStaticPaths for ${page}, the locale ${entry.locale} is not specified in ${configFileName}`), "__NEXT_ERROR_CODE", {
                    value: "E358",
                    enumerable: false,
                    configurable: true
                });
            }
            const curLocale = entry.locale || defaultLocale || '';
            const pathname = normalizePathname(`${curLocale ? `/${curLocale}` : ''}${curLocale && builtPage === '/' ? '' : builtPage}`);
            if (!prerenderedRoutesByPathname.has(pathname)) {
                prerenderedRoutesByPathname.set(pathname, {
                    params,
                    pathname,
                    encodedPathname: normalizePathname(`${curLocale ? `/${curLocale}` : ''}${curLocale && encodedBuiltPage === '/' ? '' : encodedBuiltPage}`),
                    fallbackRouteParams: undefined,
                    fallbackMode: parseStaticPathsResult(staticPathsResult.fallback),
                    fallbackRootParams: undefined,
                    throwOnEmptyStaticShell: undefined
                });
            }
        }
    });
    return {
        fallbackMode: parseStaticPathsResult(staticPathsResult.fallback),
        prerenderedRoutes: [
            ...prerenderedRoutesByPathname.values()
        ]
    };
}

//# sourceMappingURL=pages.js.map