@nuxtjs/i18n
Version:
Internationalization for Nuxt
109 lines (108 loc) • 4.68 kB
JavaScript
import { isArray, isString } from "@intlify/shared";
import { hasProtocol } from "ufo";
import { getRequestProtocol } from "h3";
import { useRequestEvent, useRuntimeConfig, useRouter, useRequestHeaders, useNuxtApp } from "#imports";
import { normalizedLocales } from "#build/i18n.options.mjs";
import { getLocalesRegex, getRouteName } from "./routing/utils.js";
import { createLogger } from "#nuxt-i18n/logger";
import { formatMessage } from "./utils.js";
export function getHost() {
if (import.meta.client) {
return window.location.host;
}
const header = useRequestHeaders(["x-forwarded-host", "host"]);
return header["x-forwarded-host"] || header["host"] || "";
}
export function getLocaleDomain(locales, strategy, route) {
const logger = /* @__PURE__ */ createLogger(`getLocaleDomain`);
const host = getHost();
if (!host) {
return host;
}
const routePath = isString(route) ? route : route.path;
const matchingLocales = locales.filter((locale) => {
if (locale.domain) {
return (hasProtocol(locale.domain) ? locale.domain.replace(/(http|https):\/\//, "") : locale.domain) === host;
}
return isArray(locale?.domains) ? locale.domains.includes(host) : false;
});
__DEBUG__ && logger.log(`locating domain for host`, { host, strategy, path: routePath });
if (matchingLocales.length === 0) {
return "";
}
if (matchingLocales.length === 1) {
__DEBUG__ && logger.log(`found one matching domain`, { host, matchedLocale: matchingLocales[0].code });
return matchingLocales[0]?.code ?? "";
}
if (strategy === "no_prefix") {
console.warn(
formatMessage(
"Multiple matching domains found! This is not supported for no_prefix strategy in combination with differentDomains!"
)
);
return matchingLocales[0]?.code ?? "";
}
if (route && routePath) {
__DEBUG__ && logger.log(`check matched domain for locale match`, { path: routePath, host });
const matched = routePath.match(getLocalesRegex(matchingLocales.map((l) => l.code)))?.at(1);
if (matched) {
const matchingLocale2 = matchingLocales.find((l) => l.code === matched);
__DEBUG__ && logger.log(`matched locale from path`, { matchedLocale: matchingLocale2?.code });
return matchingLocale2?.code ?? "";
}
}
const matchingLocale = matchingLocales.find((l) => l.defaultForDomains?.includes(host) ?? l.domainDefault);
__DEBUG__ && logger.log(`no locale matched - using default for this domain`, { matchedLocale: matchingLocale?.code });
return matchingLocale?.code ?? "";
}
export function getDomainFromLocale(localeCode) {
const nuxt = useNuxtApp();
const host = getHost();
const { domainLocales } = useRuntimeConfig().public.i18n;
const lang = normalizedLocales.find((locale) => locale.code === localeCode);
const domain = domainLocales?.[localeCode]?.domain || lang?.domain || lang?.domains?.find((v) => v === host);
if (!domain) {
console.warn(formatMessage("Could not find domain name for locale " + localeCode));
return;
}
if (hasProtocol(domain, { strict: true })) {
return domain;
}
const protocol = import.meta.server ? getRequestProtocol(useRequestEvent(nuxt)) + ":" : new URL(window.location.origin).protocol;
return protocol + "//" + domain;
}
export function setupMultiDomainLocales(runtimeI18n, defaultLocaleDomain) {
const { multiDomainLocales, strategy, routesNameSeparator, defaultLocaleRouteNameSuffix } = runtimeI18n;
if (!multiDomainLocales) return;
if (!(strategy === "prefix_except_default" || strategy === "prefix_and_default")) return;
const router = useRouter();
const defaultRouteSuffix = [routesNameSeparator, defaultLocaleRouteNameSuffix].join("");
for (const route of router.getRoutes()) {
const routeName = getRouteName(route.name);
if (routeName.endsWith(defaultRouteSuffix)) {
router.removeRoute(routeName);
continue;
}
const routeNameLocale = routeName.split(routesNameSeparator)[1];
if (routeNameLocale === defaultLocaleDomain) {
router.addRoute({
...route,
path: route.path === `/${routeNameLocale}` ? "/" : route.path.replace(`/${routeNameLocale}`, "")
});
}
}
}
export function getDefaultLocaleForDomain(runtimeI18n) {
const { locales, defaultLocale, multiDomainLocales } = runtimeI18n;
if (!multiDomainLocales) {
return defaultLocale || "";
}
const host = getHost();
if (locales.some((l) => !isString(l) && l.defaultForDomains != null)) {
const findDefaultLocale = locales.find(
(l) => !isString(l) && !!l.defaultForDomains?.includes(host)
);
return findDefaultLocale?.code ?? "";
}
return defaultLocale || "";
}