# shared/registries/location.registry.ts

> 89 lines of code and 22 definitions.

Tree: Governance tree
Language: typescript
Layer: infrastructure
Canonical: https://banes-lab.com/anatomy/governance#file-governance-shared-registries-location-registry-ts
Source text: https://banes-lab.com/source/governance/shared/registries/location.registry.ts.txt

Listed in [shared/registries](https://banes-lab.com/api/source/governance/shared/registries.md), before [shared/registries/taxonomy.registry.ts](https://banes-lab.com/source/governance/shared/registries/taxonomy.registry.ts.md).

## Definitions

- `tokenIn` (lexical_declaration, line 89, exported)
- `walk` (lexical_declaration, line 60)
- `toPosix` (lexical_declaration, line 6, exported)
- `collectDeclared` (lexical_declaration, line 10)
- `isRecord` (lexical_declaration, line 26)
- `recordLocation` (lexical_declaration, line 48)
- `build` (lexical_declaration, line 32)
- `keyIndex` (lexical_declaration, line 46)
- `keyForLocation` (lexical_declaration, line 81, exported)
- `ROOT_POSIX` (lexical_declaration, line 4)
- `MEMBER_ROOTS` (lexical_declaration, line 30, exported)
- `set` (lexical_declaration, line 33)
- `LOCATION_TOKENS` (lexical_declaration, line 41, exported)
- `SELF_KEY` (lexical_declaration, line 43)
- `extraKeys` (lexical_declaration, line 44)
- `byPath` (lexical_declaration, line 47)
- `dotted` (lexical_declaration, line 49)
- `branch` (lexical_declaration, line 50)
- `preferred` (lexical_declaration, line 51)
- `KEY_BY_LOCATION` (lexical_declaration, line 79)
- `locationForKey` (lexical_declaration, line 85, exported)
- `posix` (lexical_declaration, line 90, exported)

## Used by

- [codemods/analyzers/reference.analyzer.ts](https://banes-lab.com/source/governance/codemods/analyzers/reference.analyzer.ts.md)
- [shared/analyzers/segment.analyzer.ts](https://banes-lab.com/source/governance/shared/analyzers/segment.analyzer.ts.md)

## Source

```typescript
import { ROOT, paths } from "@ssot/paths";
import { memberRels } from "../loaders/manifest.loader.ts";

const ROOT_POSIX = ROOT.split("\\").join("/");

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

const collectDeclared = function collectDeclared(node: unknown, out: Set<string>): void {
    if (typeof node === "string") {
        const posix = toPosix(node);
        if (posix.startsWith(ROOT_POSIX) && posix.length > ROOT_POSIX.length) {
            out.add(posix.slice(ROOT_POSIX.length + 1));
        }
        return;
    }
    if (typeof node !== "object" || node === null) {
        return;
    }
    for (const value of Object.values(node)) {
        collectDeclared(value, out);
    }
};

const isRecord = function isRecord(value: unknown): value is Record<string, unknown> {
    return typeof value === "object" && value !== null;
};

export const MEMBER_ROOTS: readonly string[] = memberRels();

const build = function build(): string[] {
    const set = new Set<string>();
    collectDeclared(paths, set);
    for (const member of MEMBER_ROOTS) {
        set.add(member);
    }
    return [...set].sort((a, b) => b.length - a.length);
};

export const LOCATION_TOKENS: readonly string[] = build();

const SELF_KEY = "root";
const extraKeys = new Map<string, string>();

const keyIndex = function keyIndex(): Map<string, string> {
    const byPath = new Map<string, string>();
    const recordLocation = function recordLocation(location: string, trail: string[]): void {
        const dotted = trail.join(".");
        const branch = trail.at(-1) === SELF_KEY ? trail.slice(0, -1).join(".") : null;
        const preferred = branch ?? dotted;
        if (!byPath.has(location) || preferred.length < (byPath.get(location) ?? "").length) {
            byPath.set(location, preferred);
        }
        extraKeys.set(dotted, location);
        if (branch !== null) {
            extraKeys.set(branch, location);
        }
    };
    const walk = function walk(node: unknown, trail: string[]): void {
        if (typeof node === "string") {
            const posix = toPosix(node);
            if (posix.startsWith(`${ROOT_POSIX}/`)) {
                recordLocation(posix.slice(ROOT_POSIX.length + 1), trail);
            }
            return;
        }
        if (!isRecord(node)) {
            return;
        }
        for (const [key, value] of Object.entries(node)) {
            walk(value, [...trail, key]);
        }
    };
    walk(paths, []);
    return byPath;
};

const KEY_BY_LOCATION = keyIndex();

export const keyForLocation = function keyForLocation(location: string): string | null {
    return KEY_BY_LOCATION.get(toPosix(location)) ?? null;
};

export const locationForKey = function locationForKey(key: string): string | null {
    return extraKeys.get(key) ?? null;
};

export const tokenIn = function tokenIn(value: string): string | null {
    const posix = toPosix(value);
    for (const token of LOCATION_TOKENS) {
        if (
            posix === token ||
            posix.startsWith(`${token}/`) ||
            posix.includes(`/${token}/`) ||
            posix.endsWith(`/${token}`)
        ) {
            return token;
        }
    }
    return null;
};
```
