shared/manifests/taxonomy.manifest.ts

shared/manifests/taxonomy.manifest.ts is a file in GovLab Extension Host. 179 lines of code and 62 definitions.

import type { Dialect, GrammarRoles, Placement, Splitter, Vocabulary } from "../../types/taxonomy.types.ts";
import { JURISDICTION } from "../registries/taxonomy.registry.ts";
import { matchesPattern } from "../matchers/pattern.matcher.ts";
import { undeclaredConcernTag } from "../strings/taxonomy.strings.ts";

const HOST: Vocabulary = JURISDICTION.host;

export const COMPOUND_MARKERS: readonly string[] = HOST.compoundMarkers;
export const SEPARATOR: string = HOST.separator;
export const CASE: string = HOST.case;
export const DIALECTS: readonly Dialect[] = HOST.dialects;
export const FILE_SHAPES: readonly string[] = HOST.fileShapes;
export const MAX_DEPTH: number = HOST.maxDepth;
export const GRAMMAR_ROLES: GrammarRoles = HOST.roles;

const {
    containers: CONTAINERS,
    foreign: FOREIGN,
    mirrors: MIRRORS,
    roots: TAXONOMY_ROOTS,
    special: SPECIAL,
    vocabularies: VOCABULARY_BY_ROOT,
} = JURISDICTION;

const posix = function posix(value: string): string {
    return value.split("\\").join("/");
};

export const governedRoots = function governedRoots(): string[] {
    return TAXONOMY_ROOTS.filter((root) => !MIRRORS.has(root));
};

export const vocabularyFor = function vocabularyFor(root?: string): Vocabulary {
    return root === undefined ? HOST : (VOCABULARY_BY_ROOT.get(root) ?? HOST);
};

export const isImportedRoot = function isImportedRoot(root: string | undefined): boolean {
    return vocabularyFor(root) !== HOST;
};

export const containersFor = function containersFor(root: string): string[] {
    return [...(CONTAINERS.get(root) ?? []), ...(SPECIAL.get(root) ?? [])].toSorted((a, b) => a.localeCompare(b));
};

export const rootFor = function rootFor(filePath: string): string | undefined {
    const norm = posix(filePath);
    return TAXONOMY_ROOTS.find((root) => norm.includes(`/${root}/`) || norm.startsWith(`${root}/`));
};

export const isEnforced = function isEnforced(filePath: string): boolean {
    return rootFor(filePath) !== undefined;
};

export const isContainer = function isContainer(root: string, segment: string): boolean {
    return CONTAINERS.get(root)?.has(segment) === true;
};

export const isSpecialContainer = function isSpecialContainer(root: string, segment: string): boolean {
    return SPECIAL.get(root)?.has(segment) === true;
};

export const isForeignContainer = function isForeignContainer(root: string, segment: string): boolean {
    return FOREIGN.get(root)?.has(segment) === true;
};

export const isDeclaredContainer = function isDeclaredContainer(root: string, segment: string): boolean {
    return isContainer(root, segment) || isSpecialContainer(root, segment);
};

export const isNestedRoot = function isNestedRoot(root: string, segment: string): boolean {
    return CONTAINERS.has(`${root}/${segment}`);
};

export const isIgnoredName = function isIgnoredName(name: string, root?: string): boolean {
    return vocabularyFor(root).ignoredNames.some((pattern) => matchesPattern(pattern, name));
};

export const isGeneratedFolder = function isGeneratedFolder(name: string, root?: string): boolean {
    const form = vocabularyFor(root).generatedFolder;
    if (form === null) {
        return false;
    }
    const suffix = `${vocabularyFor(root).separator}${form.marker}`;
    return name.startsWith(form.prefix) && name.endsWith(suffix) && name.length > form.prefix.length + suffix.length;
};

export const excludedTrees = function excludedTrees(): string[] {
    return [...HOST.excludedTrees];
};

export const isCompoundMarker = function isCompoundMarker(segment: string, root?: string): boolean {
    return vocabularyFor(root).compoundMarkers.includes(segment);
};

export const splitterFor = function splitterFor(ext: string, root?: string): Splitter | null {
    const vocabulary = vocabularyFor(root);
    const dialect = vocabulary.dialects.find((declared) => declared.extensions.includes(ext));
    return dialect === undefined ? null : (vocabulary.splitters.get(dialect.splitter) ?? null);
};

export const isNameExempt = function isNameExempt(basename: string, root?: string): boolean {
    const vocabulary = vocabularyFor(root);
    if (isIgnoredName(basename, root) || vocabulary.boundaryDocuments.has(basename)) {
        return true;
    }
    const segments = basename.split(vocabulary.separator);
    return segments.length > 2 && isCompoundMarker(segments.at(-2) ?? "", root);
};

export const markerFolderOf = function markerFolderOf(basename: string, root?: string): string | undefined {
    const vocabulary = vocabularyFor(root);
    const segments = basename.split(vocabulary.separator);
    return segments.length > 2 ? vocabulary.markerFolders.get(segments.at(-2) ?? "") : undefined;
};

export const isMarkerFolder = function isMarkerFolder(folder: string, root?: string): boolean {
    return [...vocabularyFor(root).markerFolders.values()].includes(folder);
};

const segmentsBelowRoot = function segmentsBelowRoot(filePath: string, root: string): string[] {
    const norm = posix(filePath);
    const marker = `${root}/`;
    const at = norm.lastIndexOf(marker);
    if (at === -1) {
        return [];
    }
    return norm.slice(at + marker.length).split("/");
};

export const placementOf = function placementOf(filePath: string): Placement | undefined {
    const root = rootFor(filePath);
    if (root === undefined) {
        return undefined;
    }
    const segments = segmentsBelowRoot(filePath, root);
    const container = segments[0] ?? "";
    if (!isDeclaredContainer(root, container)) {
        return undefined;
    }
    const tail = segments.slice(1);
    const firstBelow = tail[0] ?? "";
    if (firstBelow === "") {
        return undefined;
    }
    const kind = isSpecialContainer(root, container) ? "special" : "container";
    const depth = segments.length - 1;
    return { container, depth, firstBelow, kind, root };
};

export const isConcern = function isConcern(tag: string, root?: string): boolean {
    return vocabularyFor(root).byTag.has(tag);
};

export const isConcernFolder = function isConcernFolder(folder: string, root?: string): boolean {
    return vocabularyFor(root).byFolder.has(folder);
};

export const isLegalSubject = function isLegalSubject(word: string, root?: string): boolean {
    return vocabularyFor(root).legalSubjects.has(word);
};

export const isDeclaredSubject = function isDeclaredSubject(word: string, root?: string): boolean {
    return vocabularyFor(root).subjects.has(word);
};

export const isDeclaredVariant = function isDeclaredVariant(word: string, root?: string): boolean {
    return vocabularyFor(root).variants.has(word);
};

export const folderFor = function folderFor(tag: string): string | undefined {
    return HOST.byTag.get(tag)?.folder;
};

export const layerFor = function layerFor(tag: string, root?: string): string | undefined {
    return vocabularyFor(root).byTag.get(tag)?.layer;
};

export const tagForFolder = function tagForFolder(folderSegment: string, root?: string): string | undefined {
    const vocabulary = vocabularyFor(root);
    const tail = folderSegment.slice(folderSegment.lastIndexOf(vocabulary.separator) + 1);
    return vocabulary.byFolder.get(tail)?.tag;
};

export const tagsForFolder = function tagsForFolder(folderSegment: string, root?: string): readonly string[] {
    const vocabulary = vocabularyFor(root);
    const concern = vocabulary.byFolder.get(folderSegment.slice(folderSegment.lastIndexOf(vocabulary.separator) + 1));
    if (concern === undefined) {
        return [];
    }
    return concern.collection === undefined ? [concern.tag] : [concern.tag, concern.collection];
};

export const concernForPath = function concernForPath(filePath: string): string | undefined {
    const norm = posix(filePath);
    const cut = norm.lastIndexOf("/");
    if (cut === -1) {
        return undefined;
    }
    const parent = norm.slice(0, cut);
    const start = parent.lastIndexOf("/");
    return tagForFolder(start === -1 ? parent : parent.slice(start + 1), rootFor(filePath));
};

export const concernSuffix = function concernSuffix(tag: string, ext = "ts"): string {
    if (!HOST.byTag.has(tag)) {
        throw new Error(undeclaredConcernTag(tag));
    }
    return `.${tag}.${ext}`;
};

export const concernTags = function concernTags(): string[] {
    return [...HOST.byTag.keys()];
};

export const legalSubjects = function legalSubjects(): string[] {
    return [...HOST.legalSubjects];
};