mirror of
https://github.com/bendtherules/ask262.git
synced 2026-08-18 13:21:55 +00:00
137 lines
4.2 KiB
TypeScript
137 lines
4.2 KiB
TypeScript
import {
|
|
opendir, readFile, stat, writeFile,
|
|
} from 'node:fs/promises';
|
|
import { pathToFileURL } from 'node:url';
|
|
import * as path from 'path';
|
|
|
|
const nodeModules = path.resolve(path.resolve(import.meta.dirname, '..'), 'node_modules');
|
|
const unicodeDir = path.resolve(nodeModules, '@unicode', 'unicode-16.0.0');
|
|
|
|
async function writeUnicodePropertyMapping() {
|
|
async function* scan(d: string): AsyncGenerator<string, void, void> {
|
|
for await (const dirent of await opendir(d)) {
|
|
if (dirent.isDirectory()) {
|
|
const p = path.join(d, dirent.name);
|
|
const test = path.join(p, 'code-points.js');
|
|
try {
|
|
await stat(test);
|
|
yield p;
|
|
} catch {
|
|
yield* scan(p);
|
|
}
|
|
}
|
|
}
|
|
}
|
|
|
|
type Range = readonly [from: number, to: number]
|
|
|
|
const data: Record<string, readonly Range[]> = {};
|
|
|
|
for await (const item of scan(unicodeDir)) {
|
|
const category = path.relative(unicodeDir, item).replace(/\\/g, '/');
|
|
const { default: cps } = await import(`@unicode/unicode-16.0.0/${category}/code-points.js`);
|
|
if (!Array.isArray(cps)) {
|
|
continue;
|
|
}
|
|
if (!category.startsWith('General_Category/') && !category.startsWith('Script/') && !category.startsWith('Script_Extensions/') && !category.startsWith('Binary_Property/')) {
|
|
continue;
|
|
}
|
|
const ranges: Range[] = [];
|
|
let from = 0;
|
|
let to = 0;
|
|
cps.forEach((cp, i) => {
|
|
if (i === 0) {
|
|
from = cp;
|
|
to = cp;
|
|
} else {
|
|
if (to + 1 === cp) {
|
|
to += 1;
|
|
} else {
|
|
ranges.push([from, to]);
|
|
from = cp;
|
|
to = cp;
|
|
}
|
|
}
|
|
});
|
|
ranges.push([from, to]);
|
|
data[category] = ranges;
|
|
}
|
|
await writeFile(path.resolve(path.resolve(import.meta.dirname, '..'), 'src/unicode/CodePointProperties.json'), JSON.stringify(data));
|
|
}
|
|
|
|
async function writeUnicodeStringsMapping() {
|
|
const data: Record<string, string> = {};
|
|
for (const cat of [
|
|
'Basic_Emoji',
|
|
'Emoji_Keycap_Sequence',
|
|
'RGI_Emoji_Modifier_Sequence',
|
|
'RGI_Emoji_Flag_Sequence',
|
|
'RGI_Emoji_Tag_Sequence',
|
|
'RGI_Emoji_ZWJ_Sequence',
|
|
'RGI_Emoji',
|
|
]) {
|
|
const file = path.resolve(unicodeDir, 'Sequence_Property', cat, 'index.js');
|
|
// eslint-disable-next-line no-await-in-loop
|
|
const { default: strings } = await import(pathToFileURL(file).href);
|
|
data[cat] = strings.join(',');
|
|
}
|
|
await writeFile(path.resolve(path.resolve(import.meta.dirname, '..'), 'src', 'unicode/SequenceProperties.json'), JSON.stringify(data));
|
|
}
|
|
|
|
async function writeUnicodePropertyAliasMapping() {
|
|
const file = readFile(new URL('./Unicode/PropertyValueAliases.txt', import.meta.url), 'utf-8');
|
|
const lines = (await file).split('\n').filter((line) => line.length > 0 && !line.startsWith('#'));
|
|
|
|
const gc: Record<string, string> = {};
|
|
const sc: Record<string, string> = {};
|
|
const scx: Record<string, string> = {};
|
|
// gc ; M ; Mark ; Combining_Mark
|
|
// where Mark is the official name, I guess?
|
|
for (const line of lines) {
|
|
const [cat, alias, formalName, ...moreAlias] = line
|
|
.split('#')[0]
|
|
.split(';')
|
|
.map((s) => s.trim());
|
|
if (cat === 'gc') {
|
|
gc[alias] = formalName;
|
|
gc[formalName] = formalName;
|
|
moreAlias.forEach((name) => {
|
|
gc[name] = formalName;
|
|
});
|
|
} else if (cat === 'sc') {
|
|
sc[alias] = formalName;
|
|
sc[formalName] = formalName;
|
|
moreAlias.forEach((name) => {
|
|
sc[name] = formalName;
|
|
});
|
|
} else if (cat === 'scx') {
|
|
scx[alias] = formalName;
|
|
scx[formalName] = formalName;
|
|
moreAlias.forEach((name) => {
|
|
scx[name] = formalName;
|
|
});
|
|
}
|
|
}
|
|
await writeFile(
|
|
new URL('../src/unicode/PropertyValueAliases.json', import.meta.url),
|
|
JSON.stringify(
|
|
{
|
|
description:
|
|
'Unicode Property Value Aliases, generated from https://unicode.org/Public/UCD/latest/ucd/PropertyValueAliases.txt',
|
|
General_Category: gc,
|
|
Script: sc,
|
|
Script_Extensions: scx,
|
|
},
|
|
undefined,
|
|
2,
|
|
),
|
|
'utf-8',
|
|
);
|
|
}
|
|
|
|
await Promise.all([
|
|
writeUnicodePropertyMapping(),
|
|
writeUnicodeStringsMapping(),
|
|
writeUnicodePropertyAliasMapping(),
|
|
]);
|