Skip to content

Commit

Permalink
refactor!: combine onlyOnNoPrefix and onlyOnRoot
Browse files Browse the repository at this point in the history
  • Loading branch information
divine committed Jul 19, 2021
1 parent 67e5cac commit eeb535b
Show file tree
Hide file tree
Showing 9 changed files with 41 additions and 46 deletions.
2 changes: 2 additions & 0 deletions docs/content/en/migrating.md
Original file line number Diff line number Diff line change
Expand Up @@ -17,6 +17,8 @@ Follow this guide to upgrade from one major version to the other.

### `seo` option has been removed. Use `$nuxtI18nHead({ addDirAttribute: true, addSeoAttributes: true })` instead.

### `onlyOnRoot` and `onlyOnNoPrefix` has been removed. It's features are combined into `redirectOn` instead. Use `redirectOn: 'root|no_prefix'` instead.

## Upgrading from 5.x to 6.x

### Global SEO features are now disabled by default
Expand Down
20 changes: 3 additions & 17 deletions docs/content/en/options-reference.md
Original file line number Diff line number Diff line change
Expand Up @@ -147,23 +147,22 @@ Directory that contains translation files to load. Can be used with or without l
## `detectBrowserLanguage`

- type: `object`
- default: `{ alwaysRedirect: false, fallbackLocale: '', onlyOnRoot: false, useCookie: true, cookieCrossOrigin: false, cookieDomain: null, cookieKey: 'i18n_redirected', cookieSecure: false }`
- default: `{ alwaysRedirect: false, fallbackLocale: '', redirectOn: null, useCookie: true, cookieCrossOrigin: false, cookieDomain: null, cookieKey: 'i18n_redirected', cookieSecure: false }`

Enables browser language detection to automatically redirect visitors to their preferred locale as they visit your site for the first time.

See also [Browser language detection](/browser-language-detection) for a guide.

<alert type="info">

Note that for better SEO it's recommended to set `onlyOnRoot` to true.
Note that for better SEO it's recommended to set `redirectOn` to `root`.

</alert>

Supported properties:
- `alwaysRedirect` (default: `false`) - Set to always redirect to the value stored in the cookie, not just on first visit.
- `fallbackLocale` (default: `null`) - If none of the locales match the browser's locale, use this one as a fallback.
- `onlyOnRoot` (default: `false`) - Set to `true` (recommended for improved SEO) to only attempt to detect the browser locale on the root path (`/`) of the site. Only effective when using strategy other than `'no_prefix'`.
- `onlyOnNoPrefix` (default: `false`) - This is a more permissive variant of `onlyOnRoot` that will allow attempt to detect the browser locale on the root path (`/`) and also on paths that have no locale prefix (like `/foo`). Only effective when `onlyOnRoot` is not enabled and using strategy other than `'no_prefix'`.
- `redirectOn` (default: `null`) - Set to `root` (recommended for improved SEO) to only attempt to detect the browser locale on the root path (`/`) of the site. Only effective when using strategy other than `'no_prefix'`. Set to `no_prefix` as this is a more permissive variant of `root` that will allow attempt to detect the browser locale on the root path (`/`) and also on paths that have no locale prefix (like `/foo`). Only effective when `onlyOnRoot` is not enabled and using strategy other than `'no_prefix'`.
- `useCookie` (default: `true`) - If enabled, a cookie is set once the user has been redirected to browser's preferred locale, to prevent subsequent redirections. Set to `false` to redirect every time.
- `cookieKey` (default: `'i18n_redirected'`) - Cookie name.
- `cookieDomain` (default: `null`) - Set to override the default domain of the cookie. Defaults to the **host** of the site.
Expand All @@ -186,19 +185,6 @@ Set to a path to which you want to redirect users accessing the root URL (`/`).
}
```

## `seo`

<badge>deprecated</badge>

<alert type="warning">

This option is deprecated from v6.19.0. The recommended way is to set up SEO as described in [Improving performance](/seo#improving-performance).

</alert>

- type: `boolean`
- default: `false`

If `true`, a SEO metadata will be generated for the routes. Note that performance can suffer with this option enabled and there might be compatibility issues with some plugins.

## `differentDomains`
Expand Down
10 changes: 8 additions & 2 deletions src/helpers/constants.js
Original file line number Diff line number Diff line change
Expand Up @@ -17,6 +17,13 @@ export const STRATEGIES = {
NO_PREFIX: STRATEGY_NO_PREFIX
}

const REDIRECT_ROOT = 'root'
const REDIRECT_NO_PREFIX = 'no_prefix'
export const REDIRECTIONS = {
ROOT: REDIRECT_ROOT,
NO_PREFIX: REDIRECT_NO_PREFIX
}

export const COMPONENT_OPTIONS_KEY = 'nuxtI18n'

/** @type {Options} */
Expand All @@ -39,8 +46,7 @@ export const DEFAULT_OPTIONS = {
cookieKey: 'i18n_redirected',
cookieSecure: false,
fallbackLocale: '',
onlyOnNoPrefix: false,
onlyOnRoot: false,
redirectOn: null,
useCookie: true
},
differentDomains: false,
Expand Down
5 changes: 3 additions & 2 deletions src/index.js
Original file line number Diff line number Diff line change
Expand Up @@ -3,7 +3,7 @@ import { readdirSync } from 'fs'
import merge from 'lodash.merge'
// @ts-ignore
import { directive as i18nExtensionsDirective } from '@intlify/vue-i18n-extensions'
import { COMPONENT_OPTIONS_KEY, DEFAULT_OPTIONS, ROOT_DIR, STRATEGIES } from './helpers/constants'
import { COMPONENT_OPTIONS_KEY, DEFAULT_OPTIONS, ROOT_DIR, STRATEGIES, REDIRECTIONS } from './helpers/constants'
import { buildHook, createExtendRoutesHook } from './core/hooks'
import { formatMessage } from './templates/utils-common'

Expand Down Expand Up @@ -53,7 +53,8 @@ export default function (moduleOptions) {
const templatesOptions = {
Constants: {
COMPONENT_OPTIONS_KEY,
STRATEGIES
STRATEGIES,
REDIRECTIONS
},
nuxtOptions: {
isUniversalMode: nuxtOptions.mode === 'universal',
Expand Down
3 changes: 2 additions & 1 deletion src/templates/options.d.ts
Original file line number Diff line number Diff line change
@@ -1,11 +1,12 @@
import Vue from 'vue'
import { ComponentOptions } from 'vue/types/options'
import { STRATEGIES } from '../helpers/constants'
import { STRATEGIES, REDIRECTIONS } from '../helpers/constants'
import { LocaleFileExport, ResolvedOptions } from '../../types/internal'

interface ModuleConstants {
COMPONENT_OPTIONS_KEY: keyof Pick<ComponentOptions<Vue>, 'nuxtI18n'>
STRATEGIES: typeof STRATEGIES
REDIRECTIONS: typeof REDIRECTIONS
}

interface ModuleNuxtOptions {
Expand Down
11 changes: 5 additions & 6 deletions src/templates/plugin.main.js
Original file line number Diff line number Diff line change
Expand Up @@ -55,8 +55,7 @@ export default async (context) => {
const {
alwaysRedirect,
fallbackLocale,
onlyOnNoPrefix,
onlyOnRoot,
redirectOn,
useCookie,
cookieKey,
cookieDomain,
Expand Down Expand Up @@ -181,9 +180,9 @@ export default async (context) => {
}

if (getLocaleFromRoute(route) === locale) {
// If "onlyOnRoot" or "onlyOnNoPrefix" is set and strategy is "prefix_and_default", prefer unprefixed route for
// If "redirectOn" is set and strategy is "prefix_and_default", prefer unprefixed route for
// default locale.
if (!(onlyOnRoot || onlyOnNoPrefix) || locale !== options.defaultLocale || options.strategy !== Constants.STRATEGIES.PREFIX_AND_DEFAULT) {
if (!(redirectOn) || locale !== options.defaultLocale || options.strategy !== Constants.STRATEGIES.PREFIX_AND_DEFAULT) {
return ''
}
}
Expand Down Expand Up @@ -287,11 +286,11 @@ export default async (context) => {
}

if (options.strategy !== Constants.STRATEGIES.NO_PREFIX) {
if (onlyOnRoot) {
if (redirectOn === Constants.REDIRECTIONS.ROOT) {
if (route.path !== '/') {
return ''
}
} else if (onlyOnNoPrefix) {
} else if (redirectOn === Constants.REDIRECTIONS.NO_PREFIX) {
if (!alwaysRedirect && route.path.match(getLocalesRegex(options.localeCodes))) {
return ''
}
Expand Down
28 changes: 14 additions & 14 deletions test/browser.test.js
Original file line number Diff line number Diff line change
Expand Up @@ -385,7 +385,7 @@ describe(`${browserString} (generate, no subFolders, trailingSlash === false)`,
})

for (const target of ['server', 'static']) {
describe(`${browserString} (target ${target}, generate, prefix strategy, alwaysRedirect, onlyOnRoot)`, () => {
describe(`${browserString} (target ${target}, generate, prefix strategy, alwaysRedirect, redirectOn is root)`, () => {
/** @type {import('playwright-chromium').ChromiumBrowser} */
let browser
/** @type {import('playwright-chromium').Page} */
Expand All @@ -403,7 +403,7 @@ for (const target of ['server', 'static']) {
detectBrowserLanguage: {
alwaysRedirect: true,
fallbackLocale: 'en',
onlyOnRoot: true
redirectOn: 'root'
}
}
}
Expand Down Expand Up @@ -968,7 +968,7 @@ describe(`${browserString} (SPA with router in hash mode)`, () => {
})
})

describe(`${browserString} (onlyOnRoot + alwaysRedirect + no_prefix)`, () => {
describe(`${browserString} (redirectOn is root + alwaysRedirect + no_prefix)`, () => {
/** @type {Nuxt} */
let nuxt
/** @type {import('playwright-chromium').ChromiumBrowser} */
Expand All @@ -982,7 +982,7 @@ describe(`${browserString} (onlyOnRoot + alwaysRedirect + no_prefix)`, () => {
detectBrowserLanguage: {
useCookie: false,
alwaysRedirect: true,
onlyOnRoot: true
redirectOn: 'root'
}
}
}
Expand All @@ -998,13 +998,13 @@ describe(`${browserString} (onlyOnRoot + alwaysRedirect + no_prefix)`, () => {
await nuxt.close()
})

test('onlyOnRoot does not affect locale detection on root path', async () => {
test('redirectOn is root does not affect locale detection on root path', async () => {
const page = await browser.newPage({ locale: 'fr' })
await page.goto(url('/'))
expect(await (await page.$('body'))?.textContent()).toContain('locale: fr')
})

test('onlyOnRoot does not affect locale detection on sub-path', async () => {
test('redirectOn is root does not affect locale detection on sub-path', async () => {
const page = await browser.newPage({ locale: 'fr' })
await page.goto(url('/about'))
expect(await (await page.$('#current-page'))?.textContent()).toContain('page: À propos')
Expand Down Expand Up @@ -1059,7 +1059,7 @@ describe(`${browserString} (alwaysRedirect, prefix)`, () => {
})
})

describe(`${browserString} (onlyOnRoot + prefix_except_default)`, () => {
describe(`${browserString} (redirectOn is root + prefix_except_default)`, () => {
/** @type {Nuxt} */
let nuxt
/** @type {import('playwright-chromium').ChromiumBrowser} */
Expand All @@ -1071,7 +1071,7 @@ describe(`${browserString} (onlyOnRoot + prefix_except_default)`, () => {
defaultLocale: 'en',
strategy: 'prefix_except_default',
detectBrowserLanguage: {
onlyOnRoot: true
redirectOn: 'root'
}
}
}
Expand Down Expand Up @@ -1131,7 +1131,7 @@ describe(`${browserString} (onlyOnRoot + prefix_except_default)`, () => {
})
})

describe(`${browserString} (onlyOnRoot + alwaysRedirect + prefix_except_default)`, () => {
describe(`${browserString} (redirectOn is root + alwaysRedirect + prefix_except_default)`, () => {
/** @type {Nuxt} */
let nuxt
/** @type {import('playwright-chromium').ChromiumBrowser} */
Expand All @@ -1144,7 +1144,7 @@ describe(`${browserString} (onlyOnRoot + alwaysRedirect + prefix_except_default)
strategy: 'prefix_except_default',
detectBrowserLanguage: {
alwaysRedirect: true,
onlyOnRoot: true
redirectOn: 'root'
}
}
}
Expand Down Expand Up @@ -1176,7 +1176,7 @@ describe(`${browserString} (onlyOnRoot + alwaysRedirect + prefix_except_default)
})
})

describe(`${browserString} (onlyOnRoot + prefix_and_default)`, () => {
describe(`${browserString} (redirectOn is root + prefix_and_default)`, () => {
/** @type {Nuxt} */
let nuxt
/** @type {import('playwright-chromium').ChromiumBrowser} */
Expand All @@ -1188,7 +1188,7 @@ describe(`${browserString} (onlyOnRoot + prefix_and_default)`, () => {
defaultLocale: 'en',
strategy: 'prefix_and_default',
detectBrowserLanguage: {
onlyOnRoot: true
redirectOn: 'root'
}
}
}
Expand Down Expand Up @@ -1219,7 +1219,7 @@ describe(`${browserString} (onlyOnRoot + prefix_and_default)`, () => {
})
})

describe(`${browserString} (onlyOnRoot + prefix)`, () => {
describe(`${browserString} (redirectOn is root + prefix)`, () => {
/** @type {Nuxt} */
let nuxt
/** @type {import('playwright-chromium').ChromiumBrowser} */
Expand All @@ -1231,7 +1231,7 @@ describe(`${browserString} (onlyOnRoot + prefix)`, () => {
defaultLocale: 'en',
strategy: 'prefix',
detectBrowserLanguage: {
onlyOnRoot: true
redirectOn: 'root'
}
}
}
Expand Down
4 changes: 2 additions & 2 deletions test/module.test.js
Original file line number Diff line number Diff line change
Expand Up @@ -1786,7 +1786,7 @@ describe('prefix + detectBrowserLanguage', () => {
})
})

describe('prefix + detectBrowserLanguage + onlyOnNoPrefix', () => {
describe('prefix + detectBrowserLanguage + redirectOn is no_prefix', () => {
/** @type {Nuxt} */
let nuxt

Expand All @@ -1797,7 +1797,7 @@ describe('prefix + detectBrowserLanguage + onlyOnNoPrefix', () => {
strategy: 'prefix',
detectBrowserLanguage: {
useCookie: true,
onlyOnNoPrefix: true
redirectOn: 'no_prefix'
}
}
}
Expand Down
4 changes: 2 additions & 2 deletions types/index.d.ts
Original file line number Diff line number Diff line change
Expand Up @@ -5,6 +5,7 @@ import './vue'
export { Locale }
export type Strategies = 'no_prefix' | 'prefix_except_default' | 'prefix' | 'prefix_and_default'
export type Directions = 'ltr' | 'rtl' | 'auto'
export type RedirectOptions = 'root' | 'no_prefix'

export interface LocaleObject extends Record<string, any> {
code: Locale
Expand All @@ -21,8 +22,7 @@ export interface DetectBrowserLanguageOptions {
cookieKey?: string
cookieSecure?: boolean
fallbackLocale?: Locale | null
onlyOnNoPrefix?: boolean
onlyOnRoot?: boolean
redirectOn?: RedirectOptions | null
useCookie?: boolean
}

Expand Down

0 comments on commit eeb535b

Please sign in to comment.