目录

设置语言

页面:html标签的 lang属性

浏览器->设置->语言

判断语言

命名由来

注意

通用性考虑:location:'位置' vs location:'[位置]'

标题(含列表):都大写,除了 冠、连、介词(除非首)

原理

tc参数:复数翻译

t参数:单一翻译

变量替换 (variables)

vue-i18n 9.x 版本(与Vue 3.x 兼容)

选项对象 (options)

格式化 (format)

数字格式化:1,000

复数形式 (count)

上下文 (context)

默认值 (defaultValue)

返回对象:

zh.json

en.json

react组件

传参和效果

本地资源:语言包对象

zh.ts

en.ts

开发

staticData.ts:直接返回对象效率更高

适用于静态语言

若固定顺序,可遍历对象属性

public->locales->en->模块名.json

public->locales->zh->模块名.json

适用于动态语言,非固定顺序,零散重复使用

returnObjects: true,可遍历对象属性

react-i18next库:hook、组件级

安装

react-i18next使用上下文API、或者 hook:

vue-i18n库:原型链、全局

0.安装

1.配置语言包(src\i18n或language)

1.1注册vue-i18n 

1.2动态加载语言文件

1.3设置VueI18n的options中的messages登

1.4设置VueI18n的options中的locale

1.5创建 VueI18n 实例并导出

完整代码

2.main.js引入,实例化Vue

3.使用

选项式 API .vue

类式 API  .vue、工具函数.ts

ts

src/declare.d.ts:declare module 'VueI18n';

Element:UI组件库

0.全局加载

0.按需加载

0.无法兼容/按需修改

1.重启主服务/项目

CDN加载

性能提升:就近

缓存优化

可靠性增强:多节点备份

带宽节省:分担请求

自动更新

源码分析


设置语言

页面:html标签的 lang属性

  • 英语: <html lang="en">
  • 中文: <html lang="zh"> 或 <html lang="zh-CN">

"CN" 则表示该语言的特定区域,即中华人民共和国(China)。

更符合语言标准的规范

  • 西班牙语: <html lang="es">
  • 法语: <html lang="fr">
  • 日语: <html lang="ja">

<!DOCTYPE html>
<html lang="en">
<head>
    <meta charset="UTF-8">
    <meta name="viewport" content="width=device-width, initial-scale=1.0">
    <title>Your Webpage Title</title>
</head>
<body>
    <!-- Your webpage content goes here -->
</body>
</html>

浏览器->设置->语言

判断语言

 场景:若法国、日韩本地语言不是“en”,但需要用“en”,

所以不能靠“en”判断,而是非“zh”时就显示英文

const appLanguage = window.app && window.app.appLocaleInfo 
  ? window.app.appLocaleInfo.appLanguage 
  : "zh";
const isZhLocal = (appLanguage === "zh");

命名由来

  1. 国际化(i18n)

    • i 表示单词 "internationalization" 的首字母。
    • 18 表示在 "i" 和 "n" 之间有 18 个字母。
  2. 本地化(l10n)

    • l 表示单词 "localization" 的首字母。
    • 10 表示在 "l" 和 "n" 之间有 10 个字母。
  3. react-i18next:i18n+extend(推测)

注意

通用性考虑:location:'位置' vs location:'[位置]'

`[${i18n.t('message.location')}]` 

标题(含列表):都大写,除了 冠、连、介词(除非首)

如冠词(a, an, the)、连词(and, but, or)和介词(in, on, with)通常不大写,除非它们是标题的第一个或最后一个词。

"The Quick Brown Fox Jumps Over the Lazy Dog"

"Software Update"

原理

从本地化资源文件中获取特定键的字符串,并且可以动态地插入变量。本地资源一般是.json,.xml,.ts存储对象

<!DOCTYPE html>
<html lang="en">
<head>
  <meta charset="UTF-8">
  <meta name="viewport" content="width=device-width, initial-scale=1.0">
  <title>Translation Example</title>
</head>
<body>

<script>
const translationContext = {
  t: (key) => {
    // 获取浏览器当前语言
    const userLanguage = navigator.language || navigator.userLanguage;

    // 默认翻译
    const defaultTranslations = {
      "No modifications at present.": "No modifications at present.",
      "Time Error: Current creation time is earlier than the server time, unable to submit.": "Time Error: Current creation time is earlier than the server time, unable to submit.",
      // 添加其他英文翻译
    };

    // 按语言选择翻译
    const zhCNTranslations = {
      "No modifications at present.": "当前无修改",
      "Time Error: Current creation time is earlier than the server time, unable to submit.": "时间异常,当前创建时间早于服务器端时间,无法提交",
      // 添加其他中文翻译
    };

    const currentTranslations = ['zh', 'zh-CN', 'cn'].includes(userLanguage) ? zhCNTranslations : defaultTranslations;
    
    // 示例翻译
    const translatedText = currentTranslations[key] || defaultTranslations[key] || key;
    
    // 在控制台输出翻译结果
    console.log(translatedText);
    console.log(userLanguage);
    // 可以将翻译结果插入到页面中
    // document.body.innerHTML = translatedText;

    return translatedText;
  },
};

// 示例使用
translationContext.t("No modifications at present.");
translationContext.t("Time Error: Current creation time is earlier than the server time, unable to submit.");
</script>

</body>
</html>

tc参数:复数翻译

apple: 'no apples | one apple | {count} apples'

因为tc函数可以用|分割,而t不能

count、n、可以随意命名

<p>{{ $tc('apple', 0) }}</p>
<p>{{ $tc('apple', 1) }}</p>
<p>{{ $tc('apple', 10, { count: 10 }) }}</p>
覆盖预定义的命名参数
<p>{{ $tc('apple', 100, { count: 'too many' }) }}</p>

<p>no apples</p>
<p>one apple</p>
<p>10 apples</p>
<p>too many apples</p>

t参数:单一翻译

t (translate) 函数: 这个函数用于翻译文本,传入翻译文件(如下述home.json命名空间(namespace,如下述zh.json中的login)

i18n 对象: 包含国际化设置的对象,判断和切换语言

i18n.language 的默认值浏览器的语言首选项(navigator.language

i18n.language; // 当前语言环境

i18n.changeLanguage('en'); // 切换到英语

变量替换 (variables)

  • 用法:通过一个对象来传递需要替换的变量。
  • 示例t('welcomeMessage', { username: 'John' })
  • 说明:这种方式允许你将动态变量插入到翻译文本中,类似占位符的功能。

vue-i18n 9.x 版本(与Vue 3.x 兼容)

选项对象 (options)

可选,包含配置选项,如 locale, pluralization 等。

this.$t('greeting', { name: 'Alice', locale: 'fr' })  // 使用 'fr' 语言环境

格式化 (format)

  • 用法:指定特定的格式化选项,例如日期、数字格式化等。
  • 示例t('date', { date: new Date(), format: 'longDate' })
  • 说明:在需要根据语言环境格式化日期、数字或其他类型的内容时特别有用。

数字格式化:1,000

复数形式 (count)

  • 用法:指定一个用于选择适当复数形式的数值。
  • 示例t('items', { count: 5 })
  • 说明:根据给定的数值选择文本的复数形式,如单数、复数等。

上下文 (context)

  • 用法:指定一个上下文参数,用于选择文本的特定变体。
  • 示例t('open', { context: 'verb' })
  • 说明:在需要根据不同语境下选择不同翻译版本时使用,例如动词形式和名词形式的不同翻译。

默认值 (defaultValue)

  • 用法:指定在找不到翻译键时返回的默认文本。
  • 示例t('nonExistentKey', { defaultValue: 'Default Text' })
  • 说明:确保在没有对应翻译键的情况下,能够提供一个合适的默认文本,避免出现空白或错误。

返回对象:

{ returnObjects: true } 选项来告诉 t 函数返回一个包含多个条目的对象

适用于:

  • 本身就需要对象
  • 遍历对象
  • 对象层级深,避免名字太长

zh.json

{
"home": {
  "welcomeMessage": "欢迎,{{username}}!",
  "items": {
    "one": "一个项目",
    "other": "{{count}} 个项目"
  },
  "date": {
  "longDate": "{{date, YYYY年MM月DD日}}",
  "shortDate": "{{date, YYYY-MM-DD}}",
  "fullDateTime": "{{date, YYYY年MM月DD日Ah点mm分ss秒}}"
   }

  "open": {
    "verb": "打开",
    "noun": "开放"
  },
  "features": {
      "free": {
        "title": "免费",
        "description": [
          "免费注册",
          "免费试用"
        ]
    },
},
  "login": {
    "title": "登录",
    "username": "用户名",
    "password": "密码",
    "loginButton": "登录"
  }
}
  • 长日期 (longDate):例如 2024年07月13日
  • 短日期 (shortDate):例如 2024-07-13
  • 完整日期时间 (fullDateTime):例如 2024年07月13日下午02点30分00秒

en.json

{
"home": {
  "welcomeMessage": "Welcome, {{username}}!",
  "items": {
    "one": "One item",
    "other": "{{count}} items"
  },
   "date": {
  "longDate": "{{date, MMMM Do, YYYY}}",
  "shortDate": "{{date, MM/DD/YYYY}}",
  "isoDate": "{{date, YYYY-MM-DD}}",
  "fullDateTime": "{{date, MMMM Do YYYY, h:mm:ss a}}"
  "features": {
      "free": {
        "title": "Free",
        "description": [
          "Free registration",
          "Free trial"
        ]
      },
}

  "open": {
    "verb": "Open",
     "noun": "Openness"
  }
},
"login": {
    "title": "Login",
    "username": "Username",
    "password": "Password",
    "loginButton": "Login"
  }
}
  • 长日期 (longDate):例如 July 13th, 2024
  • 短日期 (shortDate):例如 07/13/2024
  • ISO 8601 格式 (isoDate):例如 2024-07-13
  • 完整日期时间 (fullDateTime):例如 July 13th 2024, 2:30:00 pm

react组件

//不传参的话加载所有的本地资源
const { t, i18n } = useTranslation(['home', 'login']);

import React from 'react';
import { useTranslation } from 'react-i18next';

function WelcomeComponent({ username, itemCount, date }) {
  //只加载home.json,就不用带前缀home,只在home内查找
  const { t } = useTranslation('home');


  return (
    <div>
      <p>{t('welcomeMessage', { username: username })}</p>
      <p>{t('items', { count: itemCount })}</p>
      <p>{t('date', { date: date, format: 'longDate' })}</p>
      <p>{t('open', { context: 'verb' })}</p>
      <p>{t('nonExistentKey', { defaultValue: 'Default Text' })}</p>
        <ul>
        {t('features.free.description', { returnObjects: true }).map((desc, index) =>             
       (<li key={index}>{desc}</li>))}
      </ul>
    </div>
  );
}

export default WelcomeComponent;

传参和效果

<WelcomeComponent
  username="张三"
  itemCount={3}
  date={new Date()}
/>

<div>
  <p>Welcome, 张三!</p>
  <p>3 items</p>
  <p>July 12th, 2024</p>
  <p>Open</p>
  <p>Default Text</p>
   ...
</div>

<div>
  <p>欢迎,张三!</p>
  <p>3 个项目</p>
  <p>2024年7月12日</p>
  <p>打开</p>
  <p>Default Text</p>
  ...
</div>

本地资源:语言包对象

zh.ts

export default {
    languageName: '简体中文',
    common: { //通用
        you: '你',
    }
}

en.ts

export default {
    languageName: 'English',
    common: { //通用
        you: 'you',
     },
}

开发

staticData.ts:直接返回对象效率更高

  • 适用于静态语言

  • 若固定顺序,可遍历对象属性

例子可见下文的react-i18next

export function getFeatures(lang: string){
  if(lang==='cn'){
    return [
      {
        title: '免费',
        description:  [
          '你好',
           ...
        ],
      },
      {
       ...
      }
    ]
  }else{
    return [
      {
        title: 'Free',
        description: [
          'hi~~~😄',
           ....
        ],
      },
      {
       ....
        ],
      }
    ]
  }

}

public->locales->en->模块名.json

public->locales->zh->模块名.json

  • 适用于动态语言,非固定顺序,零散重复使用

  • returnObjects: true,可遍历对象属性

react-i18next库:hook、组件级

安装

npm i i18next react-i18next 
  • i18next 提供了翻译的基本能力。
  • react-i18next 是 i18next 的一个插件,用来降低 react 的使用成本。

可选:

npm i i18next-browser-languagedetector i18next-http-backend
  • i18next-browser-languagedetector 检测浏览器语言的插件。
  • i18next-http-backend从服务器加载翻译资源文件

react-i18next使用上下文API、或者 hook:

React Context API实现状态和数据在组件树中的共享。它允许在组件之间共享数据,而无需手动通过props一层层地传递数据。尤其适用于全局数据、主题设置、用户身份验证等在整个应用程序中需要访问的数据。

hook只能在函数组件

import { useTranslation } from 'react-i18next';
import { getFeatures } from './staticData';

export default function HomeContent() {
  //解构变量,根据本地的home和login文件设置i18n
  const { t, i18n } = useTranslation(['home', 'login']);
  const features = getFeatures(['zh', 'zh-CN', 'cn'].includes(i18n.language) ? 'cn' : 'en')

getFeatures见上文中的staticData.ts

<h1 className="font-bold text-2xl">{t('Sign in/Sign up')}</h1>
{features?.map((item, index) => (
          <div className='flex flex-col items-center p-4 md:w-1/2' key={item.title}>
            <div className=' min-w-full h-full bg-[#2A2935] rounded-lg p-4'>
              <div className=' text-2xl leading-loose md:leading-tight'>{item.title}
                {item.subtitle && <span className=' text-xs text-gray-400 ml-2'>( {item.subtitle} )</span>}
              </div>
              {item.description.map((item, index) => (
                <div className=' text-xs text-gray-400 leading-relaxed' key={index}>- {item}</div>
              ))}
            </div>
          </div>
        ))}

vue-i18n库:原型链、全局

0.安装

npm install vue-i18n

Vue I18n官方文档

1.配置语言包(src\i18n或language)

整合语言包对象和创建 VueI18n 实例并配置

1.1注册vue-i18n 

import Vue from "vue"
import VueI18n from "vue-i18n"
Vue.use(VueI18n) // 将 VueI18n 注入到 Vue 实例中的所有子组件

在 Vue.js 中,插件通常通过 Vue.use() 方法来注册和安装。

vue-i18n 注册后,将 i18n 实例挂载到原型链上。

  1. 全局可访问任何 Vue 组件中都可以通过 this.$i18n 访问到国际化实例

  2. 一致性:保证所有组件使用同一个 i18n 实例,避免了不同组件间状态管理的复杂性和冗余性。

1.2动态加载语言文件

let langFileds = require.context('./locales', false, /\.ts$/)
let dateTimeFormatsFileds = require.context('./dateTimeFormats', false, /\.ts$/)
let regExp = /\.\/([^\.\/]+)\.([^\.]+)$/

require.context 是 webpack 提供的一种函数,用于在编译时动态地引入模块。它接受三个参数:require.context(path,deep,regExp)

  1. path(目录路径): 表示需要搜索的目录路径。
  2. deep(是否搜索子目录): 表示是否搜索该目录下的子目录。
  3. regExp(匹配文件的正则表达式): 表示匹配文件的正则表达式。

日期时间格式文件(zh.ts+en.ts一致)

export default {
  shortMonth: {
    month: 'short',
  },
  numberMonth: {
    month: 'narrow',
  },
  shortYear: {
    year: 'numeric'
  }
}

shortMonth:

month: 'short' 表示月份的简短格式。具体格式(比如 'Jan'、'Feb')取决于具体的本地化设置,通常是缩写形式的月份名称。

numberMonth:

month: 'narrow' 表示月份的窄格式。这种格式可能比 'short' 更加紧凑,通常用于较窄的显示空间或者日历视图中。

shortYear:

year: 'numeric' 表示年份的数字格式。这种格式通常是完整的四位数字年份(例如 2023)。

1.3设置VueI18n的options中的messages登

langFileds.keys().forEach((key:any) => {
        let prop = regExp.exec(key)//正则匹配en|zh这样的值

        if(prop){
            //messages[prop]相当于 messages['en'] = {table:{...}}
            messages[prop[1]] = langFileds(key).default
//对于 ./en.ts,prop 将会是 ['en', 'ts']
//.default 表示 ES6 默认导出的内容,因为 webpack 在处理 ES6 模块时会将其包装为一个包含 default 属性的对象。
        }
})
dateTimeFormatsFileds.keys().forEach((key:any) => {
  let prop = regExp.exec(key)//正则匹配en|zh这样的值
  if(prop){
      dateTimeFormats[prop[1]] = dateTimeFormatsFileds(key).default
  }
})

messages 对象:

{
    en: {
        greeting: 'Hello!',
        farewell: 'Goodbye!'
    },
    zh: {
        greeting: '你好!',
        farewell: '再见!'
    }
}

1.4设置VueI18n的options中的locale

let locale = window.xxx.appLocaleInfo.appLanguage || "zh" //从localstorag中获取

1.5创建 VueI18n 实例并导出

export default new VueI18n({
    locale, // 指定当前的语言环境
    messages, // 语言包对象,包含不同语言的翻译
    dateTimeFormats // 日期时间格式对象,包含不同语言的日期时间格式配置
})

完整代码

import Vue from "vue"
import VueI18n from "vue-i18n"
Vue.use(VueI18n) //注入到所有的子组件

let langFileds = require.context('./locales', false, /\.ts$/)
let dateTimeFormatsFileds = require.context('./dateTimeFormats', false, /\.ts$/)

let regExp = /\.\/([^\.\/]+)\.([^\.]+)$/ //正则用于匹配 ./en.js中的'en'

let messages = {} //声明一个数据模型,对应i18n中的message属性
let dateTimeFormats = {}

langFileds.keys().forEach((key:any) => {
        let prop = regExp.exec(key)//正则匹配en|zh这样的值
        if(prop){
            //messages[prop]相当于 messages['en'] = {table:{...}}
            messages[prop[1]] = langFileds(key).default
        }
})
dateTimeFormatsFileds.keys().forEach((key:any) => {
  let prop = regExp.exec(key)//正则匹配en|zh这样的值
  if(prop){
      dateTimeFormats[prop[1]] = dateTimeFormatsFileds(key).default
  }
})

let locale = window.xxx.appLocaleInfo.appLanguage || "zh" //从localstorag中获取

export default new VueI18n({
    locale,//指定语言字段
    messages,//定义语言字段
    dateTimeFormats
})

2.main.js引入,实例化Vue

基于组件的本地化

import i18n from "./i18n"

//渲染函数 (render):动态地生成虚拟 DOM,适合复杂的逻辑和定制化需求。
new Vue({
  i18n,
  render: h => h(App)
}).$mount('#app')
​//模板字符串 (template):适合基本的应用程序结构和布局,易读和维护。
new Vue({
  i18n, // 语言国际化配置
  template: '<App/>', // 模板字符串,指定根组件
  components: { App } // 注册根组件
}).$mount('#app')

3.使用

选项式 API .vue

JS对象方式定义组件,Vue 在此对象中注入了上下文,包括 this.$t 方法

//标签文本内容
<span>{{$t("workplace.updateRecurringSchedule")}}</span>
//标签属性
:placeholder="$t('chartSend.addScheduleTheme')"

//js
this.$t("chartSend.waitBotReply")

//键值对:removeMsg:'确定将 {nickname} 移除群聊吗?',
const item.nickname={nickname:'M7'}
this.$t("chartSend.removeMsg", {nickname: item.nickname})

extent.js : Vue 的原型中挂载 $t 方法

// 把 VueI18n 对象实例的方法都注入到 Vue 实例上
Vue.prototype.$t = function (key: Path, ...values: any): TranslateResult {
  const i18n = this.$i18n
  // 代理模式的使用
  return i18n._t(key, i18n.locale, i18n._getMessages(), this, ...values)
}

调用 index.js 中的 $t 的方法

// $t 最后调用的方法
_t (key: Path, _locale: Locale, messages: LocaleMessages, host: any, ...values: any): any {
  if (!key) { return '' }
  const parsedArgs = parseArgs(...values)
  // 如果 escapeParameterHtml 被配置为 true,那么插值参数将在转换消息之前被转义。
  if(this._escapeParameterHtml) {
    parsedArgs.params = escapeParams(parsedArgs.params)
  }
  const locale: Locale = parsedArgs.locale || _locale
  // 翻译
  let ret: any = this._translate(
    messages, locale, this.fallbackLocale, key,
    host, 'string', parsedArgs.params
  )
}

a

类式 API  .vue、工具函数.ts

import i18n from '@/i18n'

class IMConListUtil {
i18n.t('common.private'),

}

如果类式 API 用 this.$t会报错

原因:ES6 类来定义组件,需要使用 vue-class-component 插件来处理 Vue 的特性

[warn]:不会阻断运行逻辑,但error会

TypeError: Cannot read properties of undefined (reading '_t')

at Vue.$t (todo.common.js:20045:1)
at VueComponent.selectPractitioners (todo.common.js:25065:1)
at click (todo.common.js:17124:2746)

export default class CreateBacklogTask extends Vue {

this.searchSelectPerson = params == this.$t('todo.add.subscriberss') ? this.followersList : this.executorList;

}

ts

src/declare.d.ts:declare module 'VueI18n';

TypeScript项目中,当第三方库或模块不是由 TypeScript 编写的,因此可能没有原生的 TypeScript 类型定义文件。

会创建一个 declare.d.ts 文件,声明模块的类型信息,以便在编译时进行类型检查和提供类型提示。

declare module 'element-ui';
declare module 'vuex';
declare module 'vue';
declare module 'VueI18n';
declare module 'axios';
eclare module 'lodash';
declare module 'vue-router';

Element:UI组件库

若用main.ts,

记得声明

 declare.d.ts

declare module 'element-ui/lib/locale';

0.全局加载

 main.js 

import Vue from 'vue'
import VueI18n from 'vue-i18n'
import Element from 'element-ui'
import enLocale from 'element-ui/lib/locale/lang/en'
import zhLocale from 'element-ui/lib/locale/lang/zh-CN'

Vue.use(VueI18n)
Vue.use(Element)
//设置默认语言
Vue.config.lang = 'zh-cn'
//注册了中文(简体)和英文的本地化资源
Vue.locale('zh-cn', zhLocale)
Vue.locale('en', enLocale)

Tip:

全局安装Element组件配置相应locale:

Vue.use(Element)

Vue.use(ElementUI, { locale })

按需安装Element组件配置相应locale:

Vue.use(DatePicker)

ElementLocale.i18n((key, value) => i18n.t(key, value))

若用Vue.use(Element)配ElementLocale.i18n((key, value) => i18n.t(key, value))会报错:

Vue.use(Element)默认没有指定语言环境,Element UI将使用它内置的默认语言设置。

此时用ElementLocale.i18n()去改变其语言处理函数可能会导致冲突或重复配置,从而引发错误。

0.按需加载

 main.js 

import Vue from 'vue'
import DatePicker from 'element/lib/date-picker'
import VueI18n from 'vue-i18n'

import enLocale from 'element-ui/lib/locale/lang/en'
import zhLocale from 'element-ui/lib/locale/lang/zh-CN'
import ElementLocale from 'element-ui/lib/locale'

Vue.use(VueI18n)
Vue.use(DatePicker)

const messages = {
  en: {
    message: 'hello',
    ...enLocale
  },
  zh: {
    message: '你好',
    ...zhLocale
  }
}
// Create VueI18n instance with options
const i18n = new VueI18n({
  locale: 'en', // set locale
  messages, // set locale messages
})

ElementLocale.i18n((key, value) => i18n.t(key, value))

0.无法兼容/按需修改

  vs:command+p 查找文件

en.js

'use strict';

exports.__esModule = true;
exports.default = {
  el: {
    colorpicker: {
      confirm: 'OK',
      clear: 'Clear'
    },
    datepicker: {
      now: 'Now',
      today: 'Today',
      cancel: 'Cancel',
      clear: 'Clear',
 ...

将'element-ui/lib/locale/lang/en','zh-CN'中相关内容粘贴合并到本地语言包文件中即可

靠el-识别

 el: {
    colorpicker: {
      confirm: 'OK',
      clear: 'Clear'
    },
    datepicker: {
      now: 'Now',
      today: 'Today',
      cancel: 'Cancel',
      clear: 'Clear',
 ...

main.ts

//全局加载
import locale_en from 'element-ui/lib/locale/lang/en'
import locale_zh from 'element-ui/lib/locale/lang/zh-CN'

const appLanguage:string = window.appName.appLocaleInfo ? window.appName.appLocaleInfo.appLanguage : "zh"
const locale = appLanguage === 'zh' ? locale_zh : locale_en;
Vue.use(ElementUI, { locale });

1.重启主服务/项目

不重启的话会报错/配置不生效

CDN加载

性能提升:就近

CDN 分布在全球多个节点,通过就近的服务器提供文件,减少了用户的加载时间,提高了性能。

缓存优化

CDN 会缓存文件,减轻了源服务器的负担,并使文件的访问速度更快。

可靠性增强:多节点备份

CDN 提供高可用性和容错性,确保文件在多个节点上都有备份,即使某些节点出现问题,用户仍然可以从其他节点获取文件。

带宽节省:分担请求

通过 CDN,减少了直接从源服务器的带宽使用,因为文件请求会分担到 CDN 网络上。

自动更新

CDN 提供的文件可以自动更新,确保用户获取到的是最新版本的语言文件。

源码分析​​​​​​​

Logo

腾讯云面向开发者汇聚海量精品云计算使用和开发经验,营造开放的云计算技术生态圈。

更多推荐