icanboogie / cldr
使用Unicode的CLDR本地化应用程序
v5.0.0
2023-10-03 10:00 UTC
Requires
- php: >=7.1 <8.2
- ext-curl: *
- ext-json: *
- ext-mbstring: *
- icanboogie/accessor: ^3.0|^4.0
- icanboogie/common: ^1.3
Requires (Dev)
- ext-redis: *
- phpstan/phpstan: ^1.4
- phpunit/phpunit: ^7.5.20|^8.5
README
CLDR 包通过利用Unicode通用区域数据仓库(CLDR)建立的数据和约定,促进了您应用程序的国际化。它提供了诸如领土、语言、天……的名称等宝贵的区域信息,以及数字、货币、日期和时间、单位、序列和列表的格式化器。
注意
示例用法
<?php use ICanBoogie\CLDR\Numbers\Currency; /* @var ICanBoogie\CLDR\Repository $repository */ # You get a locale from the repository, here the locale for French. $fr = $repository->locale_for('fr'); # You can use a locale instance as an array echo $fr['characters']['auxiliary']; // [á å ä ã ā ē í ì ī ñ ó ò ö ø ú ǔ] echo $fr['delimiters']['quotationStart']; // « echo $fr['territories']['TF']; // Terres australes françaises # You can localize it and get its local name echo $fr->localized($fr)->name; // Français # You can use it to format numbers, percents, currencies, lists… echo $fr->format_number(12345.67); // 12 345,67 echo $fr->format_percent(.1234567); // 12 % echo $fr->format_currency(12345.67, 'EUR'); // 12 345,67 € echo $fr->format_list([ "Un", "deux", "trois" ]); // Un, deux et trois # You can get the default calendar for a locale and access its data $calendar = $fr->calendar; echo $calendar['days']['format']['wide']['sun']; // dimanche echo $calendar->wide_days['sun']; // dimanche # You can use the calendar to format dates, times, or both $datetime = '2018-11-24 20:12:22 UTC'; echo $calendar->format_date($datetime, 'long'); // 24 novembre 2018 echo $calendar->format_time($datetime, 'long'); // 20:12:22 UTC echo $calendar->format_datetime($datetime, 'full'); // samedi 24 novembre 2018 à 20:12:22 UTC # Alternatively, you can localize a DateTimeInterface and get formatted dates of various lengths $datetime = new \DateTime('2013-11-04 20:21:22 UTC'); $fr_datetime = new \ICanBoogie\CLDR\Dates\LocalizedDateTime($datetime, $fr); echo $fr_datetime->as_full; // lundi 4 novembre 2013 à 20:21:22 UTC echo $fr_datetime->as_long; // 4 novembre 2013 à 20:21:22 UTC echo $fr_datetime->as_medium; // 4 nov. 2013 20:21:22 echo $fr_datetime->as_short; // 04/11/2013 20:21 # You can format units $units = $repository->locale_for('en')->units; echo $units->duration_hour->name; // hours echo $units->duration_hour->short_name; // h echo $units->duration_hour(1); // 1 hour echo $units->duration_hour(23); // 23 hours echo $units->duration_hour(23)->as_short; // 23 hr echo $units->duration_hour(23)->as_narrow; // 23h # You can format a unit per another unit echo $units->volume_liter(12.345)->per($units->duration_hour); // 12.345 liters per hour echo $units->volume_liter(12.345)->per($units->duration_hour)->as_short; // 12.345 L/h echo $units->volume_liter(12.345)->per($units->duration_hour)->as_narrow; // 12.345L/h # You can format sequences of units $units->sequence->angle_degree(5)->duration_minute(30)->as_narrow; // 5° 30m $units->sequence->length_foot(3)->length_inch(2)->as_short; // 3 ft, 2 in # You can access plural rules $repository->plurals->rule_for(1.5, 'fr'); // one $repository->plurals->rule_for(2, 'fr'); // other $repository->plurals->rule_for(2, 'ar'); // two # You can access currencies and their localized data $euro = Currency::of('EUR'); $fr_euro = $euro->localized($fr); echo $fr_euro->name; echo $fr_euro->name_for(1); // euro echo $fr_euro->name_for(10); // euros echo $fr_euro->format(12345.67); // 12 345,67 € # You can access territories and their localized data $territory = $repository->territory_for('FR'); echo $territory; // FR echo $territory->currency; // EUR echo $territory->currency_at('1977-06-06'); // FRF echo $territory->currency_at('now'); // EUR echo $territory->name_as('fr'); // France echo $territory->name_as('it'); // Francia echo $territory->name_as('ja'); // フランス echo $repository->territory_for('FR')->first_day; // mon echo $repository->territory_for('EG')->first_day; // sat echo $repository->territory_for('BS')->first_day; // sun echo $repository->territory_for('AE')->weekend_start; // fri echo $repository->territory_for('AE')->weekend_end; // sat echo $territory->localized('fr')->name; // France echo $territory->localized('it')->name; // Francia echo $territory->localized('ja')->name; // フランス
安装
composer require icanboogie/cldr
文档
该文档分为以下部分,模仿 Unicode的文档
- 第1部分: 核心(语言、区域、基本结构)
- 第2部分: 通用(显示名称 & 转换等)
- 第3部分: 数字(数字 & 货币格式化)
- 第4部分: 日期(日期、时间、时区格式化)
- 第5部分:比较(排序、搜索、分组)
- 第6部分: 补充(补充数据)
入门指南
CLDR通过一个 Repository 实例表示,该实例通过一个 Provider 实例访问数据。该包提供了几个缓存机制。选择正确的提供者取决于您的需求:您可能在开发期间优先考虑灵活性或在生产中优先考虑可预测性。
优先考虑灵活性
WebProvider 通过从GitHub上托管的JSON分布 按需检索数据,提供了最大的灵活性。为了最小化Web请求,建议使用具有各自策略的缓存集合。例如,FileCache 将检索到的数据存储为PHP文件,使其能够受益于opcache。
以下示例演示了如何实例化存储库
<?php use ICanBoogie\CLDR\Cache\CacheCollection; use ICanBoogie\CLDR\Cache\FileCache; use ICanBoogie\CLDR\Cache\RedisCache; use ICanBoogie\CLDR\Cache\RuntimeCache; use ICanBoogie\CLDR\Provider\CachedProvider; use ICanBoogie\CLDR\Provider\WebProvider; use ICanBoogie\CLDR\Repository; /* @var \Redis $redis_client */ $provider = new CachedProvider( new WebProvider, new CacheCollection([ new RunTimeCache, // You don't have to use Redis, this is only an example new RedisCache($redis_client), new FileCache(FileCache::RECOMMENDED_DIR) ]) ); $cldr = new Repository($provider);
优先考虑可预测性
为了提高可预测性,请考虑将存储库的使用限制为几个特定的区域,并将它们作为您应用程序的一部分进行分发。您可以在开发期间预先填充CLDR缓存并将其提交,或者将此步骤纳入CI/CD管道构建过程。
使用 cldr命令 加热CLDR缓存
./vendor/bin/cldr warm-up de en fr
以下示例说明了限制对缓存的数据访问的设置。当尝试检索缓存中不可用的数据时,RestrictedProvider 会抛出异常。
<?php use ICanBoogie\CLDR\Cache\FileCache; use ICanBoogie\CLDR\Provider\CachedProvider; use ICanBoogie\CLDR\Provider\RestrictedProvider; use ICanBoogie\CLDR\Repository; $provider = new CachedProvider( new RestrictedProvider(), new FileCache(FileCache::RECOMMENDED_DIR), ); $cldr = new Repository($provider);
持续集成
项目由 GitHub actions 进行持续测试。
行为准则
本项目遵循贡献者行为准则。参与本项目及其社区,你应遵守此准则。
贡献
有关详细信息,请参阅 CONTRIBUTING。
许可证
icanboogie/cldr 依据MIT 许可证发布。