@fgv/ts-bcp47 5.0.0-21 → 5.0.0-23

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (95) hide show
  1. package/package.json +8 -8
  2. package/src/data/bcp/overrides.json +0 -20
  3. package/src/data/iana/language-subtags.json +0 -57439
  4. package/src/data/iana/language-tag-extensions.json +0 -38
  5. package/src/data/unsd/m49.json +0 -3723
  6. package/src/index.ts +0 -29
  7. package/src/packlets/bcp47/bcp47Subtags/converters.ts +0 -33
  8. package/src/packlets/bcp47/bcp47Subtags/index.ts +0 -27
  9. package/src/packlets/bcp47/bcp47Subtags/model.ts +0 -46
  10. package/src/packlets/bcp47/bcp47Subtags/validate.ts +0 -55
  11. package/src/packlets/bcp47/common.ts +0 -85
  12. package/src/packlets/bcp47/helpers.ts +0 -117
  13. package/src/packlets/bcp47/index.ts +0 -38
  14. package/src/packlets/bcp47/languageRegistryData.ts +0 -304
  15. package/src/packlets/bcp47/languageTag.ts +0 -467
  16. package/src/packlets/bcp47/languageTagParser.ts +0 -307
  17. package/src/packlets/bcp47/match/chooser.ts +0 -164
  18. package/src/packlets/bcp47/match/common.ts +0 -57
  19. package/src/packlets/bcp47/match/index.ts +0 -26
  20. package/src/packlets/bcp47/match/similarity.ts +0 -243
  21. package/src/packlets/bcp47/normalization/baseNormalizer.ts +0 -146
  22. package/src/packlets/bcp47/normalization/canonicalNormalizer.ts +0 -102
  23. package/src/packlets/bcp47/normalization/common.ts +0 -84
  24. package/src/packlets/bcp47/normalization/index.ts +0 -27
  25. package/src/packlets/bcp47/normalization/normalizeTag.ts +0 -116
  26. package/src/packlets/bcp47/normalization/preferredTagNormalizer.ts +0 -213
  27. package/src/packlets/bcp47/overrides/converters.ts +0 -58
  28. package/src/packlets/bcp47/overrides/defaultRegistries.ts +0 -40
  29. package/src/packlets/bcp47/overrides/index.ts +0 -25
  30. package/src/packlets/bcp47/overrides/model.ts +0 -33
  31. package/src/packlets/bcp47/overrides/overridesRegistry.ts +0 -104
  32. package/src/packlets/bcp47/validation/baseValidator.ts +0 -132
  33. package/src/packlets/bcp47/validation/common.ts +0 -86
  34. package/src/packlets/bcp47/validation/index.ts +0 -29
  35. package/src/packlets/bcp47/validation/isCanonical.ts +0 -103
  36. package/src/packlets/bcp47/validation/isInPreferredForm.ts +0 -53
  37. package/src/packlets/bcp47/validation/isStrictlyValid.ts +0 -117
  38. package/src/packlets/bcp47/validation/isValid.ts +0 -122
  39. package/src/packlets/bcp47/validation/isWellFormed.ts +0 -102
  40. package/src/packlets/bcp47/validation/validateTag.ts +0 -175
  41. package/src/packlets/iana/common/converters.ts +0 -67
  42. package/src/packlets/iana/common/model.ts +0 -56
  43. package/src/packlets/iana/common/registeredItems.ts +0 -145
  44. package/src/packlets/iana/common/utils.ts +0 -32
  45. package/src/packlets/iana/common/validate.ts +0 -64
  46. package/src/packlets/iana/converters.ts +0 -26
  47. package/src/packlets/iana/defaultRegistries.ts +0 -40
  48. package/src/packlets/iana/index.ts +0 -33
  49. package/src/packlets/iana/jar/converters.ts +0 -26
  50. package/src/packlets/iana/jar/index.ts +0 -27
  51. package/src/packlets/iana/jar/jarConverters.ts +0 -70
  52. package/src/packlets/iana/jar/jarModel.ts +0 -34
  53. package/src/packlets/iana/jar/language-subtags/converters.ts +0 -26
  54. package/src/packlets/iana/jar/language-subtags/index.ts +0 -27
  55. package/src/packlets/iana/jar/language-subtags/model.ts +0 -26
  56. package/src/packlets/iana/jar/language-subtags/registry/converters.ts +0 -40
  57. package/src/packlets/iana/jar/language-subtags/registry/index.ts +0 -26
  58. package/src/packlets/iana/jar/language-subtags/registry/model.ts +0 -171
  59. package/src/packlets/iana/jar/language-subtags/tags/converters.ts +0 -120
  60. package/src/packlets/iana/jar/language-subtags/tags/index.ts +0 -28
  61. package/src/packlets/iana/jar/language-subtags/tags/model.ts +0 -71
  62. package/src/packlets/iana/jar/language-subtags/tags/tagValidation.ts +0 -67
  63. package/src/packlets/iana/jar/language-subtags/tags/validate.ts +0 -106
  64. package/src/packlets/iana/jar/model.ts +0 -26
  65. package/src/packlets/iana/language-subtags/common.ts +0 -46
  66. package/src/packlets/iana/language-subtags/converters.ts +0 -226
  67. package/src/packlets/iana/language-subtags/index.ts +0 -30
  68. package/src/packlets/iana/language-subtags/jarConverters.ts +0 -269
  69. package/src/packlets/iana/language-subtags/model.ts +0 -213
  70. package/src/packlets/iana/language-subtags/scope.ts +0 -222
  71. package/src/packlets/iana/language-subtags/subtagRegistry.ts +0 -136
  72. package/src/packlets/iana/language-subtags/validate.ts +0 -23
  73. package/src/packlets/iana/language-tag-extensions/converters.ts +0 -71
  74. package/src/packlets/iana/language-tag-extensions/extensionsRegistry.ts +0 -92
  75. package/src/packlets/iana/language-tag-extensions/extensionsScope.ts +0 -60
  76. package/src/packlets/iana/language-tag-extensions/index.ts +0 -29
  77. package/src/packlets/iana/language-tag-extensions/jarConverters.ts +0 -91
  78. package/src/packlets/iana/language-tag-extensions/model.ts +0 -67
  79. package/src/packlets/iana/language-tag-extensions/validate.ts +0 -36
  80. package/src/packlets/iana/languageRegistries.ts +0 -57
  81. package/src/packlets/iana/model.ts +0 -26
  82. package/src/packlets/iana/validate.ts +0 -23
  83. package/src/packlets/unsd/areas.ts +0 -105
  84. package/src/packlets/unsd/common.ts +0 -79
  85. package/src/packlets/unsd/csv/converters.ts +0 -82
  86. package/src/packlets/unsd/csv/index.ts +0 -26
  87. package/src/packlets/unsd/csv/model.ts +0 -44
  88. package/src/packlets/unsd/defaultRegistries.ts +0 -40
  89. package/src/packlets/unsd/index.ts +0 -28
  90. package/src/packlets/unsd/regionCodes.ts +0 -144
  91. package/src/packlets/unsd/regions.ts +0 -95
  92. package/src/packlets/utils/index.ts +0 -24
  93. package/src/packlets/utils/jsonHelpers.ts +0 -25
  94. package/src/packlets/utils/public.ts +0 -28
  95. package/src/packlets/utils/validationHelpers.ts +0 -180
@@ -1,269 +0,0 @@
1
- /*
2
- * Copyright (c) 2022 Erik Fortune
3
- *
4
- * Permission is hereby granted, free of charge, to any person obtaining a copy
5
- * of this software and associated documentation files (the "Software"), to deal
6
- * in the Software without restriction, including without limitation the rights
7
- * to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
8
- * copies of the Software, and to permit persons to whom the Software is
9
- * furnished to do so, subject to the following conditions:
10
- *
11
- * The above copyright notice and this permission notice shall be included in all
12
- * copies or substantial portions of the Software.
13
- *
14
- * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
15
- * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
16
- * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
17
- * AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
18
- * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
19
- * OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
20
- * SOFTWARE.
21
- */
22
-
23
- /* eslint-disable @rushstack/typedef-var */
24
-
25
- import * as JarModel from '../jar/language-subtags/registry/model';
26
- import * as TagConverters from '../jar/language-subtags/tags/converters';
27
- import * as Model from './model';
28
-
29
- import { RecordJar } from '@fgv/ts-extras';
30
- import { Converters, Result } from '@fgv/ts-utils';
31
- import { datedRegistry, yearMonthDaySpec } from '../common/converters';
32
-
33
- import { JsonFile } from '@fgv/ts-json-base';
34
- import { datedRegistryFromJarRecords } from '../jar/jarConverters';
35
- import { registryScopeType } from '../jar/language-subtags/registry/converters';
36
-
37
- /**
38
- * @internal
39
- */
40
- export const registeredLanguage = Converters.transformObject<
41
- JarModel.LanguageSubtagRegistryEntry,
42
- Model.IRegisteredLanguage
43
- >(
44
- {
45
- type: { from: 'Type', converter: Converters.enumeratedValue<'language'>(['language']) },
46
- subtag: { from: 'Subtag', converter: TagConverters.tagOrStartOfTagRange(TagConverters.languageSubtag) },
47
- description: { from: 'Description', converter: Converters.stringArray },
48
- added: { from: 'Added', converter: yearMonthDaySpec },
49
- comments: { from: 'Comments', converter: Converters.stringArray, optional: true },
50
- deprecated: { from: 'Deprecated', converter: yearMonthDaySpec, optional: true },
51
- macrolanguage: { from: 'Macrolanguage', converter: TagConverters.languageSubtag, optional: true },
52
- preferredValue: { from: 'Preferred-Value', converter: TagConverters.languageSubtag, optional: true },
53
- scope: { from: 'Scope', converter: registryScopeType, optional: true },
54
- suppressScript: { from: 'Suppress-Script', converter: TagConverters.scriptSubtag, optional: true },
55
- subtagRangeEnd: {
56
- from: 'Subtag',
57
- converter: TagConverters.endOfTagRangeOrUndefined(TagConverters.languageSubtag),
58
- optional: true
59
- }
60
- },
61
- {
62
- strict: true,
63
- description: 'language subtag'
64
- }
65
- );
66
-
67
- /**
68
- * @internal
69
- */
70
- export const registeredExtLang = Converters.transformObject<
71
- JarModel.ExtLangSubtagRegistryEntry,
72
- Model.IRegisteredExtLang
73
- >(
74
- {
75
- type: { from: 'Type', converter: Converters.enumeratedValue<'extlang'>(['extlang']) },
76
- subtag: { from: 'Subtag', converter: TagConverters.extlangSubtag },
77
- preferredValue: { from: 'Preferred-Value', converter: TagConverters.extendedLanguageRange },
78
- prefix: { from: 'Prefix', converter: TagConverters.extlangPrefix },
79
- description: { from: 'Description', converter: Converters.stringArray },
80
- added: { from: 'Added', converter: yearMonthDaySpec },
81
- comments: { from: 'Comments', converter: Converters.stringArray, optional: true },
82
- deprecated: { from: 'Deprecated', converter: yearMonthDaySpec, optional: true },
83
- macrolanguage: { from: 'Macrolanguage', converter: TagConverters.languageSubtag, optional: true },
84
- scope: { from: 'Scope', converter: registryScopeType, optional: true },
85
- suppressScript: { from: 'Suppress-Script', converter: TagConverters.scriptSubtag, optional: true }
86
- },
87
- {
88
- strict: true,
89
- description: 'extlang subtag'
90
- }
91
- );
92
-
93
- /**
94
- * @internal
95
- */
96
- export const registeredScript = Converters.transformObject<
97
- JarModel.ScriptSubtagRegistryEntry,
98
- Model.IRegisteredScript
99
- >(
100
- {
101
- type: { from: 'Type', converter: Converters.enumeratedValue<'script'>(['script']) },
102
- subtag: { from: 'Subtag', converter: TagConverters.tagOrStartOfTagRange(TagConverters.scriptSubtag) },
103
- description: { from: 'Description', converter: Converters.stringArray },
104
- added: { from: 'Added', converter: yearMonthDaySpec },
105
- comments: { from: 'Comments', converter: Converters.stringArray, optional: true },
106
- deprecated: { from: 'Deprecated', converter: yearMonthDaySpec, optional: true },
107
- preferredValue: { from: 'Preferred-Value', converter: TagConverters.scriptSubtag, optional: true },
108
- subtagRangeEnd: {
109
- from: 'Subtag',
110
- converter: TagConverters.endOfTagRangeOrUndefined(TagConverters.scriptSubtag),
111
- optional: true
112
- }
113
- },
114
- {
115
- strict: true,
116
- description: 'script subtag'
117
- }
118
- );
119
-
120
- /**
121
- * @internal
122
- */
123
- export const registeredRegion = Converters.transformObject<
124
- JarModel.RegionSubtagRegistryEntry,
125
- Model.IRegisteredRegion
126
- >(
127
- {
128
- type: { from: 'Type', converter: Converters.enumeratedValue<'region'>(['region']) },
129
- subtag: { from: 'Subtag', converter: TagConverters.tagOrStartOfTagRange(TagConverters.regionSubtag) },
130
- description: { from: 'Description', converter: Converters.stringArray },
131
- added: { from: 'Added', converter: yearMonthDaySpec },
132
- comments: { from: 'Comments', converter: Converters.stringArray, optional: true },
133
- deprecated: { from: 'Deprecated', converter: yearMonthDaySpec, optional: true },
134
- preferredValue: { from: 'Preferred-Value', converter: TagConverters.regionSubtag, optional: true },
135
- subtagRangeEnd: {
136
- from: 'Subtag',
137
- converter: TagConverters.endOfTagRangeOrUndefined(TagConverters.regionSubtag),
138
- optional: true
139
- }
140
- },
141
- {
142
- strict: true,
143
- description: 'region subtag'
144
- }
145
- );
146
-
147
- /**
148
- * @internal
149
- */
150
- export const registeredVariant = Converters.transformObject<
151
- JarModel.VariantSubtagRegistryEntry,
152
- Model.IRegisteredVariant
153
- >(
154
- {
155
- type: { from: 'Type', converter: Converters.enumeratedValue<'variant'>(['variant']) },
156
- subtag: { from: 'Subtag', converter: TagConverters.variantSubtag },
157
- description: { from: 'Description', converter: Converters.stringArray },
158
- added: { from: 'Added', converter: yearMonthDaySpec },
159
- comments: { from: 'Comments', converter: Converters.stringArray, optional: true },
160
- deprecated: { from: 'Deprecated', converter: yearMonthDaySpec, optional: true },
161
- preferredValue: { from: 'Preferred-Value', converter: TagConverters.variantSubtag, optional: true },
162
- prefix: {
163
- from: 'Prefix',
164
- converter: Converters.arrayOf(TagConverters.extendedLanguageRange),
165
- optional: true
166
- }
167
- },
168
- {
169
- strict: true,
170
- description: 'variant subtag'
171
- }
172
- );
173
-
174
- /**
175
- * @internal
176
- */
177
- export const registeredGrandfatheredTag = Converters.transformObject<
178
- JarModel.GrandfatheredTagRegistryEntry,
179
- Model.IRegisteredGrandfatheredTag
180
- >(
181
- {
182
- type: { from: 'Type', converter: Converters.enumeratedValue<'grandfathered'>(['grandfathered']) },
183
- tag: { from: 'Tag', converter: TagConverters.grandfatheredTag },
184
- description: { from: 'Description', converter: Converters.stringArray },
185
- added: { from: 'Added', converter: yearMonthDaySpec },
186
- comments: { from: 'Comments', converter: Converters.stringArray, optional: true },
187
- deprecated: { from: 'Deprecated', converter: yearMonthDaySpec, optional: true },
188
- preferredValue: {
189
- from: 'Preferred-Value',
190
- converter: TagConverters.extendedLanguageRange,
191
- optional: true
192
- }
193
- },
194
- {
195
- strict: true,
196
- description: 'grandfathered tag'
197
- }
198
- );
199
-
200
- /**
201
- * @internal
202
- */
203
- export const registeredRedundantTag = Converters.transformObject<
204
- JarModel.RedundantTagRegistryEntry,
205
- Model.IRegisteredRedundantTag
206
- >(
207
- {
208
- type: { from: 'Type', converter: Converters.enumeratedValue<'redundant'>(['redundant']) },
209
- tag: { from: 'Tag', converter: TagConverters.redundantTag },
210
- description: { from: 'Description', converter: Converters.stringArray },
211
- added: { from: 'Added', converter: yearMonthDaySpec },
212
- comments: { from: 'Comments', converter: Converters.stringArray, optional: true },
213
- deprecated: { from: 'Deprecated', converter: yearMonthDaySpec, optional: true },
214
- preferredValue: {
215
- from: 'Preferred-Value',
216
- converter: TagConverters.extendedLanguageRange,
217
- optional: true
218
- }
219
- },
220
- {
221
- strict: true,
222
- description: 'redundant tag'
223
- }
224
- );
225
-
226
- /**
227
- * @internal
228
- */
229
- export const registeredItem = Converters.discriminatedObject<Model.RegisteredItem>('Type', {
230
- language: registeredLanguage,
231
- extlang: registeredExtLang,
232
- script: registeredScript,
233
- region: registeredRegion,
234
- variant: registeredVariant,
235
- grandfathered: registeredGrandfatheredTag,
236
- redundant: registeredRedundantTag
237
- });
238
-
239
- /**
240
- * @internal
241
- */
242
- export const registryFile = datedRegistry(registeredItem);
243
-
244
- /**
245
- * Loads a JSON-format language subtag registry file.
246
- * @param path - The string path from which the registry is to be loaded.
247
- * @returns `Success` with the resulting {@link Iana.LanguageSubtags.Model.RegistryFile | registry file}
248
- * or `Failure` with details if an error occurs.
249
- * @internal
250
- */
251
- export function loadJsonSubtagRegistryFileSync(path: string): Result<Model.RegistryFile> {
252
- return JsonFile.convertJsonFileSync(path, registryFile);
253
- }
254
-
255
- /**
256
- * Loads a text (JAR) format language subtag registry file.
257
- * @param path - The string path from which the registry is to be loaded.
258
- * @returns `Success` with the resulting {@link Iana.LanguageSubtags.Model.RegistryFile | registry file}
259
- * or `Failure` with details if an error occurs.
260
- * @internal
261
- */
262
- export function loadTxtSubtagRegistryFileSync(path: string): Result<Model.RegistryFile> {
263
- return RecordJar.readRecordJarFileSync(path, {
264
- arrayFields: ['Comments', 'Description', 'Prefix'],
265
- fixedContinuationSize: 1
266
- }).onSuccess((jar) => {
267
- return datedRegistryFromJarRecords(registeredItem).convert(jar);
268
- });
269
- }
@@ -1,213 +0,0 @@
1
- /*
2
- * Copyright (c) 2022 Erik Fortune
3
- *
4
- * Permission is hereby granted, free of charge, to any person obtaining a copy
5
- * of this software and associated documentation files (the "Software"), to deal
6
- * in the Software without restriction, including without limitation the rights
7
- * to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
8
- * copies of the Software, and to permit persons to whom the Software is
9
- * furnished to do so, subject to the following conditions:
10
- *
11
- * The above copyright notice and this permission notice shall be included in all
12
- * copies or substantial portions of the Software.
13
- *
14
- * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
15
- * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
16
- * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
17
- * AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
18
- * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
19
- * OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
20
- * SOFTWARE.
21
- */
22
-
23
- import * as Model from '../jar/language-subtags/registry/model';
24
-
25
- import {
26
- ExtLangSubtag,
27
- ExtendedLanguageRange,
28
- GrandfatheredTag,
29
- LanguageSubtag,
30
- RedundantTag,
31
- RegionSubtag,
32
- ScriptSubtag,
33
- VariantSubtag
34
- } from './common';
35
-
36
- import { IDatedRegistry } from '../common/model';
37
-
38
- /**
39
- * @public
40
- */
41
- export interface IRegisteredSubtag<TTYPE extends Model.RegistryEntryType, TTAG extends string> {
42
- readonly type: TTYPE;
43
- readonly subtag: TTAG;
44
- readonly description: string[];
45
- }
46
-
47
- /**
48
- * @public
49
- */
50
- export interface IRegisteredSubtagWithRange<TTYPE extends Model.RegistryEntryType, TTAG extends string>
51
- extends IRegisteredSubtag<TTYPE, TTAG> {
52
- readonly type: TTYPE;
53
- readonly subtag: TTAG;
54
- readonly description: string[];
55
-
56
- readonly subtagRangeEnd?: TTAG;
57
- }
58
-
59
- /**
60
- * @public
61
- */
62
- export interface IRegisteredTag<TTYPE extends Model.RegistryEntryType, TTAG extends string> {
63
- readonly type: TTYPE;
64
- readonly tag: TTAG;
65
- readonly description: string[];
66
- }
67
-
68
- /**
69
- * @public
70
- */
71
- export type RegisteredTagOrSubtag<TTYPE extends Model.RegistryEntryType, TTAG extends string> =
72
- | IRegisteredSubtag<TTYPE, TTAG>
73
- | IRegisteredSubtagWithRange<TTYPE, TTAG>
74
- | IRegisteredTag<TTYPE, TTAG>;
75
-
76
- /**
77
- * @public
78
- */
79
- export interface IRegisteredLanguage extends IRegisteredSubtagWithRange<'language', LanguageSubtag> {
80
- readonly type: 'language';
81
- readonly subtag: LanguageSubtag;
82
- readonly description: string[];
83
- readonly added: Model.YearMonthDaySpec;
84
-
85
- readonly comments?: string[];
86
- readonly deprecated?: Model.YearMonthDaySpec;
87
-
88
- readonly macrolanguage?: LanguageSubtag;
89
- readonly preferredValue?: LanguageSubtag;
90
- readonly scope?: Model.RegistryEntryScope;
91
- readonly suppressScript?: ScriptSubtag;
92
-
93
- readonly subtagRangeEnd?: LanguageSubtag;
94
- }
95
-
96
- /**
97
- * @public
98
- */
99
- export interface IRegisteredExtLang extends IRegisteredSubtag<'extlang', ExtLangSubtag> {
100
- readonly type: 'extlang';
101
- readonly subtag: ExtLangSubtag;
102
- readonly preferredValue: ExtendedLanguageRange;
103
- readonly prefix: LanguageSubtag;
104
- readonly description: string[];
105
- readonly added: Model.YearMonthDaySpec;
106
-
107
- readonly comments?: string[];
108
- readonly deprecated?: Model.YearMonthDaySpec;
109
-
110
- readonly macrolanguage?: LanguageSubtag;
111
- readonly scope?: Model.RegistryEntryScope;
112
- readonly suppressScript?: ScriptSubtag;
113
- }
114
-
115
- /**
116
- * @public
117
- */
118
- export interface IRegisteredScript extends IRegisteredSubtagWithRange<'script', ScriptSubtag> {
119
- readonly type: 'script';
120
- readonly subtag: ScriptSubtag;
121
- readonly description: string[];
122
- readonly added: Model.YearMonthDaySpec;
123
-
124
- readonly comments?: string[];
125
- readonly deprecated?: Model.YearMonthDaySpec;
126
- readonly preferredValue?: ScriptSubtag;
127
-
128
- readonly subtagRangeEnd?: ScriptSubtag;
129
- }
130
-
131
- /**
132
- * @public
133
- */
134
- export interface IRegisteredRegion extends IRegisteredSubtagWithRange<'region', RegionSubtag> {
135
- readonly type: 'region';
136
- readonly subtag: RegionSubtag;
137
- readonly description: string[];
138
- readonly added: Model.YearMonthDaySpec;
139
-
140
- readonly comments?: string[];
141
- readonly deprecated?: Model.YearMonthDaySpec;
142
- readonly preferredValue?: RegionSubtag;
143
-
144
- readonly subtagRangeEnd?: RegionSubtag;
145
- }
146
-
147
- /**
148
- * @public
149
- */
150
- export interface IRegisteredVariant extends IRegisteredSubtag<'variant', VariantSubtag> {
151
- readonly type: 'variant';
152
- readonly subtag: VariantSubtag;
153
- readonly description: string[];
154
- readonly added: Model.YearMonthDaySpec;
155
-
156
- readonly comments?: string[];
157
- readonly deprecated?: Model.YearMonthDaySpec;
158
- readonly preferredValue?: VariantSubtag;
159
- readonly prefix?: ExtendedLanguageRange[];
160
- }
161
-
162
- /**
163
- * @public
164
- */
165
- export interface IRegisteredGrandfatheredTag extends IRegisteredTag<'grandfathered', GrandfatheredTag> {
166
- readonly type: 'grandfathered';
167
- readonly tag: GrandfatheredTag;
168
- readonly description: string[];
169
- readonly added: Model.YearMonthDaySpec;
170
-
171
- readonly comments?: string[];
172
- readonly deprecated?: Model.YearMonthDaySpec;
173
- readonly preferredValue?: ExtendedLanguageRange;
174
- }
175
-
176
- /**
177
- * @public
178
- */
179
- export interface IRegisteredRedundantTag extends IRegisteredTag<'redundant', RedundantTag> {
180
- readonly type: 'redundant';
181
- readonly tag: RedundantTag;
182
- readonly description: string[];
183
- readonly added: Model.YearMonthDaySpec;
184
-
185
- readonly comments?: string[];
186
- readonly deprecated?: Model.YearMonthDaySpec;
187
- readonly preferredValue?: ExtendedLanguageRange;
188
- }
189
-
190
- /**
191
- * @public
192
- */
193
- export type RegisteredSubtagItem =
194
- | IRegisteredLanguage
195
- | IRegisteredExtLang
196
- | IRegisteredScript
197
- | IRegisteredRegion
198
- | IRegisteredVariant;
199
-
200
- /**
201
- * @public
202
- */
203
- export type RegisteredTagItem = IRegisteredGrandfatheredTag | IRegisteredRedundantTag;
204
-
205
- /**
206
- * @public
207
- */
208
- export type RegisteredItem = RegisteredSubtagItem | RegisteredTagItem;
209
-
210
- /**
211
- * @public
212
- */
213
- export type RegistryFile = IDatedRegistry<RegisteredItem>;
@@ -1,222 +0,0 @@
1
- /*
2
- * Copyright (c) 2022 Erik Fortune
3
- *
4
- * Permission is hereby granted, free of charge, to any person obtaining a copy
5
- * of this software and associated documentation files (the "Software"), to deal
6
- * in the Software without restriction, including without limitation the rights
7
- * to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
8
- * copies of the Software, and to permit persons to whom the Software is
9
- * furnished to do so, subject to the following conditions:
10
- *
11
- * The above copyright notice and this permission notice shall be included in all
12
- * copies or substantial portions of the Software.
13
- *
14
- * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
15
- * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
16
- * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
17
- * AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
18
- * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
19
- * OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
20
- * SOFTWARE.
21
- */
22
-
23
- import * as Model from '../jar/language-subtags/registry/model';
24
- import * as Items from './model';
25
-
26
- import { Result, allSucceed, fail, succeed } from '@fgv/ts-utils';
27
- import { ValidationHelpers, sanitizeJson } from '../../utils';
28
- import {
29
- ExtLangSubtag,
30
- GrandfatheredTag,
31
- LanguageSubtag,
32
- RedundantTag,
33
- RegionSubtag,
34
- ScriptSubtag,
35
- Validators,
36
- VariantSubtag
37
- } from '../jar/language-subtags/tags';
38
-
39
- import { RegisteredItemScope } from '../common/registeredItems';
40
-
41
- /**
42
- * @internal
43
- */
44
- class SubtagScope<
45
- TTYPE extends Model.RegistryEntryType,
46
- TTAG extends string,
47
- TITEM extends Items.IRegisteredSubtag<TTYPE, TTAG>
48
- > extends RegisteredItemScope<TTYPE, TTAG, TITEM> {
49
- protected constructor(type: TTYPE, validate: ValidationHelpers<TTAG>) {
50
- super(type, validate);
51
- }
52
-
53
- public add(entry: TITEM): Result<true> {
54
- return this._validateEntry(entry).onSuccess(() => {
55
- this._items.set(entry.subtag, entry);
56
- return succeed(true);
57
- });
58
- }
59
-
60
- protected _validateEntry(entry: TITEM): Result<true> {
61
- return this._validateKey(entry.subtag);
62
- }
63
- }
64
-
65
- /**
66
- * @internal
67
- */
68
- class SubtagScopeWithRange<
69
- TTYPE extends Model.RegistryEntryType,
70
- TTAG extends string,
71
- TITEM extends Items.IRegisteredSubtagWithRange<TTYPE, TTAG>
72
- > extends SubtagScope<TTYPE, TTAG, TITEM> {
73
- protected constructor(type: TTYPE, validate: ValidationHelpers<TTAG>) {
74
- super(type, validate);
75
- }
76
-
77
- public add(entry: TITEM): Result<true> {
78
- return this._validateEntry(entry).onSuccess(() => {
79
- return this._addRange(entry);
80
- });
81
- }
82
-
83
- protected _validateEntry(entry: TITEM): Result<true> {
84
- const start = entry.subtag;
85
- const end = entry.subtagRangeEnd ?? ('' as TTAG);
86
- if (end) {
87
- return allSucceed(
88
- [this._validateKey(start), this._validateKey(end), this._validateRange(start, end)],
89
- true
90
- );
91
- }
92
- return this._validateKey(start);
93
- }
94
-
95
- protected _validateRange(start: TTAG, end: TTAG): Result<true> {
96
- return start < end ? succeed(true) : fail(`${start}..${end}: invalid range`);
97
- }
98
-
99
- protected _addRange(entry: TITEM): Result<true> {
100
- this._items.set(entry.subtag, entry);
101
- if (entry.subtagRangeEnd) {
102
- let next = this._nextInRange(entry.subtag, entry.subtagRangeEnd);
103
- while (next) {
104
- const e = sanitizeJson({ ...entry, subtag: next, subtagRangeEnd: undefined });
105
- this._items.set(next, e);
106
- next = this._nextInRange(next, entry.subtagRangeEnd);
107
- }
108
- }
109
- return succeed(true);
110
- }
111
-
112
- protected _nextInRange(current: TTAG, end: TTAG): TTAG | undefined {
113
- if (current >= end) {
114
- return undefined;
115
- }
116
- const next = Array.from(current);
117
- for (let i = next.length - 1; i >= 0; i--) {
118
- if (next[i].toLowerCase() < 'z') {
119
- next[i] = String.fromCharCode(next[i].charCodeAt(0) + 1);
120
- break;
121
- } else {
122
- next[i] = 'a';
123
- }
124
- }
125
- return this._validate.toCanonical(next.join('')).getValueOrThrow();
126
- }
127
- }
128
-
129
- /**
130
- * @internal
131
- */
132
- class TagScope<
133
- TTYPE extends Model.RegistryEntryType,
134
- TTAG extends string,
135
- TITEM extends Items.IRegisteredTag<TTYPE, TTAG>
136
- > extends RegisteredItemScope<TTYPE, TTAG, TITEM> {
137
- protected constructor(type: TTYPE, validate: ValidationHelpers<TTAG>) {
138
- super(type, validate);
139
- }
140
-
141
- public add(entry: TITEM): Result<true> {
142
- return this._validateEntry(entry).onSuccess(() => {
143
- this._items.set(entry.tag, entry);
144
- return succeed(true);
145
- });
146
- }
147
-
148
- protected _validateEntry(entry: TITEM): Result<true> {
149
- return this._validateKey(entry.tag);
150
- }
151
- }
152
-
153
- /**
154
- * @public
155
- */
156
- export class LanguageSubtagScope extends SubtagScopeWithRange<
157
- 'language',
158
- LanguageSubtag,
159
- Items.IRegisteredLanguage
160
- > {
161
- public constructor() {
162
- super('language', Validators.languageSubtag);
163
- }
164
- }
165
-
166
- /**
167
- * @public
168
- */
169
- export class ExtLangSubtagScope extends SubtagScope<'extlang', ExtLangSubtag, Items.IRegisteredExtLang> {
170
- public constructor() {
171
- super('extlang', Validators.extlangSubtag);
172
- }
173
- }
174
-
175
- /**
176
- * @public
177
- */
178
- export class ScriptSubtagScope extends SubtagScopeWithRange<'script', ScriptSubtag, Items.IRegisteredScript> {
179
- public constructor() {
180
- super('script', Validators.scriptSubtag);
181
- }
182
- }
183
-
184
- /**
185
- * @public
186
- */
187
- export class RegionSubtagScope extends SubtagScopeWithRange<'region', RegionSubtag, Items.IRegisteredRegion> {
188
- public constructor() {
189
- super('region', Validators.regionSubtag);
190
- }
191
- }
192
-
193
- /**
194
- * @public
195
- */
196
- export class VariantSubtagScope extends SubtagScope<'variant', VariantSubtag, Items.IRegisteredVariant> {
197
- public constructor() {
198
- super('variant', Validators.variantSubtag);
199
- }
200
- }
201
-
202
- /**
203
- * @public
204
- */
205
- export class GrandfatheredTagScope extends TagScope<
206
- 'grandfathered',
207
- GrandfatheredTag,
208
- Items.IRegisteredGrandfatheredTag
209
- > {
210
- public constructor() {
211
- super('grandfathered', Validators.grandfatheredTag);
212
- }
213
- }
214
-
215
- /**
216
- * @public
217
- */
218
- export class RedundantTagScope extends TagScope<'redundant', RedundantTag, Items.IRegisteredRedundantTag> {
219
- public constructor() {
220
- super('redundant', Validators.redundantTag);
221
- }
222
- }