@atproto/lex-installer 0.1.2 → 0.1.4

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.
package/CHANGELOG.md CHANGED
@@ -1,5 +1,31 @@
1
1
  # @atproto/lex-installer
2
2
 
3
+ ## 0.1.4
4
+
5
+ ### Patch Changes
6
+
7
+ - [#5099](https://github.com/bluesky-social/atproto/pull/5099) [`b43ec31`](https://github.com/bluesky-social/atproto/commit/b43ec31f247f4461725b01226885f88bd430ca07) Thanks [@matthieusieben](https://github.com/matthieusieben)! - Update TypeScript build to rely on references to composite internal projects
8
+
9
+ - [#5099](https://github.com/bluesky-social/atproto/pull/5099) [`b43ec31`](https://github.com/bluesky-social/atproto/commit/b43ec31f247f4461725b01226885f88bd430ca07) Thanks [@matthieusieben](https://github.com/matthieusieben)! - Build using `verbatimModuleSyntax`, reducing runtime import graph
10
+
11
+ - [#5099](https://github.com/bluesky-social/atproto/pull/5099) [`b43ec31`](https://github.com/bluesky-social/atproto/commit/b43ec31f247f4461725b01226885f88bd430ca07) Thanks [@matthieusieben](https://github.com/matthieusieben)! - Bundle only necessary files in the NPM tarball, including the `CHANGELOG.md` and `README.md` files (if present).
12
+
13
+ - Updated dependencies [[`28a0b58`](https://github.com/bluesky-social/atproto/commit/28a0b588147863eaef948cd2bb8fc0f19d08cda9), [`b43ec31`](https://github.com/bluesky-social/atproto/commit/b43ec31f247f4461725b01226885f88bd430ca07), [`b43ec31`](https://github.com/bluesky-social/atproto/commit/b43ec31f247f4461725b01226885f88bd430ca07), [`b43ec31`](https://github.com/bluesky-social/atproto/commit/b43ec31f247f4461725b01226885f88bd430ca07)]:
14
+ - @atproto/syntax@0.6.4
15
+ - @atproto/lex-document@0.1.3
16
+ - @atproto/lex-resolver@0.1.4
17
+ - @atproto/lex-builder@0.1.5
18
+ - @atproto/lex-schema@0.1.6
19
+ - @atproto/lex-cbor@0.1.3
20
+ - @atproto/lex-data@0.1.4
21
+
22
+ ## 0.1.3
23
+
24
+ ### Patch Changes
25
+
26
+ - Updated dependencies []:
27
+ - @atproto/lex-resolver@0.1.3
28
+
3
29
  ## 0.1.2
4
30
 
5
31
  ### Patch Changes
package/dist/index.d.ts CHANGED
@@ -1,4 +1,4 @@
1
- import { LexInstallerOptions } from './lex-installer.js';
1
+ import type { LexInstallerOptions } from './lex-installer.js';
2
2
  /**
3
3
  * Options for the {@link install} function.
4
4
  *
@@ -1 +1 @@
1
- {"version":3,"file":"index.d.ts","sourceRoot":"","sources":["../src/index.ts"],"names":[],"mappings":"AACA,OAAO,EAAgB,mBAAmB,EAAE,MAAM,oBAAoB,CAAA;AAMtE;;;;;;;;;;;;;;;;GAgBG;AACH,MAAM,MAAM,iBAAiB,GAAG,mBAAmB,GAAG;IACpD;;;;OAIG;IACH,GAAG,CAAC,EAAE,MAAM,EAAE,CAAA;IAEd;;;;OAIG;IACH,IAAI,CAAC,EAAE,OAAO,CAAA;IAEd;;;;;OAKG;IACH,EAAE,CAAC,EAAE,OAAO,CAAA;CACb,CAAA;AAED;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;GAiDG;AACH,wBAAsB,OAAO,CAAC,OAAO,EAAE,iBAAiB,iBA2BvD"}
1
+ {"version":3,"file":"index.d.ts","sourceRoot":"","sources":["../src/index.ts"],"names":[],"mappings":"AACA,OAAO,KAAK,EAAE,mBAAmB,EAAE,MAAM,oBAAoB,CAAA;AAK7D;;;;;;;;;;;;;;;;GAgBG;AACH,MAAM,MAAM,iBAAiB,GAAG,mBAAmB,GAAG;IACpD;;;;OAIG;IACH,GAAG,CAAC,EAAE,MAAM,EAAE,CAAA;IAEd;;;;OAIG;IACH,IAAI,CAAC,EAAE,OAAO,CAAA;IAEd;;;;;OAKG;IACH,EAAE,CAAC,EAAE,OAAO,CAAA;CACb,CAAA;AAED;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;GAiDG;AACH,wBAAsB,OAAO,CAAC,OAAO,EAAE,iBAAiB,iBA2BvD"}
package/dist/index.js CHANGED
@@ -1,7 +1,58 @@
1
- import { __addDisposableResource, __disposeResources } from "tslib";
1
+ var __addDisposableResource = (this && this.__addDisposableResource) || function (env, value, async) {
2
+ if (value !== null && value !== void 0) {
3
+ if (typeof value !== "object" && typeof value !== "function") throw new TypeError("Object expected.");
4
+ var dispose, inner;
5
+ if (async) {
6
+ if (!Symbol.asyncDispose) throw new TypeError("Symbol.asyncDispose is not defined.");
7
+ dispose = value[Symbol.asyncDispose];
8
+ }
9
+ if (dispose === void 0) {
10
+ if (!Symbol.dispose) throw new TypeError("Symbol.dispose is not defined.");
11
+ dispose = value[Symbol.dispose];
12
+ if (async) inner = dispose;
13
+ }
14
+ if (typeof dispose !== "function") throw new TypeError("Object not disposable.");
15
+ if (inner) dispose = function() { try { inner.call(this); } catch (e) { return Promise.reject(e); } };
16
+ env.stack.push({ value: value, dispose: dispose, async: async });
17
+ }
18
+ else if (async) {
19
+ env.stack.push({ async: true });
20
+ }
21
+ return value;
22
+ };
23
+ var __disposeResources = (this && this.__disposeResources) || (function (SuppressedError) {
24
+ return function (env) {
25
+ function fail(e) {
26
+ env.error = env.hasError ? new SuppressedError(e, env.error, "An error was suppressed during disposal.") : e;
27
+ env.hasError = true;
28
+ }
29
+ var r, s = 0;
30
+ function next() {
31
+ while (r = env.stack.pop()) {
32
+ try {
33
+ if (!r.async && s === 1) return s = 0, env.stack.push(r), Promise.resolve().then(next);
34
+ if (r.dispose) {
35
+ var result = r.dispose.call(r.value);
36
+ if (r.async) return s |= 2, Promise.resolve(result).then(next, function(e) { fail(e); return next(); });
37
+ }
38
+ else s |= 1;
39
+ }
40
+ catch (e) {
41
+ fail(e);
42
+ }
43
+ }
44
+ if (s === 1) return env.hasError ? Promise.reject(env.error) : Promise.resolve();
45
+ if (env.hasError) throw env.error;
46
+ }
47
+ return next();
48
+ };
49
+ })(typeof SuppressedError === "function" ? SuppressedError : function (error, suppressed, message) {
50
+ var e = new Error(message);
51
+ return e.name = "SuppressedError", e.error = error, e.suppressed = suppressed, e;
52
+ });
2
53
  import { isEnoentError, readJsonFile } from './fs.js';
3
54
  import { LexInstaller } from './lex-installer.js';
4
- import { lexiconsManifestSchema, } from './lexicons-manifest.js';
55
+ import { lexiconsManifestSchema } from './lexicons-manifest.js';
5
56
  /**
6
57
  * Installs lexicons from the network based on the provided options.
7
58
  *
package/dist/index.js.map CHANGED
@@ -1 +1 @@
1
- {"version":3,"file":"index.js","sourceRoot":"","sources":["../src/index.ts"],"names":[],"mappings":";AAAA,OAAO,EAAE,aAAa,EAAE,YAAY,EAAE,MAAM,SAAS,CAAA;AACrD,OAAO,EAAE,YAAY,EAAuB,MAAM,oBAAoB,CAAA;AACtE,OAAO,EAEL,sBAAsB,GACvB,MAAM,wBAAwB,CAAA;AA2C/B;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;GAiDG;AACH,MAAM,CAAC,KAAK,UAAU,OAAO,CAAC,OAA0B;;;QACtD,MAAM,QAAQ,GAAiC,MAAM,YAAY,CAC/D,OAAO,CAAC,QAAQ,CACjB,CAAC,IAAI,CACJ,CAAC,IAAI,EAAE,EAAE,CAAC,sBAAsB,CAAC,KAAK,CAAC,IAAI,CAAC,EAC5C,CAAC,KAAc,EAAE,EAAE;YACjB,IAAI,aAAa,CAAC,KAAK,CAAC;gBAAE,OAAO,SAAS,CAAA;YAC1C,MAAM,IAAI,KAAK,CAAC,kCAAkC,EAAE,EAAE,KAAK,EAAE,CAAC,CAAA;QAChE,CAAC,CACF,CAAA;QAED,MAAM,SAAS,GAAG,IAAI,GAAG,CAAC,OAAO,CAAC,GAAG,CAAC,CAAA;QAEtC,iEAAiE;QACjE,MAAY,SAAS,kCAAG,IAAI,YAAY,CAAC,OAAO,CAAC,OAAA,CAAA;QAEjD,MAAM,SAAS,CAAC,OAAO,CAAC,EAAE,SAAS,EAAE,QAAQ,EAAE,CAAC,CAAA;QAEhD,kBAAkB;QAClB,IAAI,OAAO,CAAC,EAAE,IAAI,CAAC,CAAC,QAAQ,IAAI,CAAC,SAAS,CAAC,MAAM,CAAC,QAAQ,CAAC,CAAC,EAAE,CAAC;YAC7D,MAAM,IAAI,KAAK,CAAC,kCAAkC,CAAC,CAAA;QACrD,CAAC;QAED,4BAA4B;QAC5B,IAAI,OAAO,CAAC,IAAI,EAAE,CAAC;YACjB,MAAM,SAAS,CAAC,IAAI,EAAE,CAAA;QACxB,CAAC;;;;;;;;;;;AACH,CAAC","sourcesContent":["import { isEnoentError, readJsonFile } from './fs.js'\nimport { LexInstaller, LexInstallerOptions } from './lex-installer.js'\nimport {\n LexiconsManifest,\n lexiconsManifestSchema,\n} from './lexicons-manifest.js'\n\n/**\n * Options for the {@link install} function.\n *\n * Extends {@link LexInstallerOptions} with additional options for controlling\n * the installation behavior.\n *\n * @example\n * ```typescript\n * const options: LexInstallOptions = {\n * lexicons: './lexicons',\n * manifest: './lexicons.manifest.json',\n * add: ['com.example.myLexicon', 'at://did:plc:xyz/com.example.otherLexicon'],\n * save: true,\n * ci: false,\n * }\n * ```\n */\nexport type LexInstallOptions = LexInstallerOptions & {\n /**\n * Array of lexicons to add to the installation. Can be NSID strings\n * (e.g., 'com.example.myLexicon') or AT URIs\n * (e.g., 'at://did:plc:xyz/com.example.myLexicon').\n */\n add?: string[]\n\n /**\n * Whether to save the updated manifest after installation.\n * When `true`, the manifest file will be written with any new lexicons.\n * @default false\n */\n save?: boolean\n\n /**\n * Enable CI mode for strict manifest verification.\n * When `true`, throws an error if the manifest is out of date,\n * useful for continuous integration pipelines.\n * @default false\n */\n ci?: boolean\n}\n\n/**\n * Installs lexicons from the network based on the provided options.\n *\n * This is the main entry point for programmatic lexicon installation.\n * It reads an existing manifest (if present), installs any new lexicons,\n * and optionally saves the updated manifest.\n *\n * @param options - Configuration options for the installation\n * @throws {Error} When the manifest file cannot be read (unless it doesn't exist)\n * @throws {Error} When in CI mode and the manifest is out of date\n *\n * @example\n * Install lexicons and save the manifest:\n * ```typescript\n * import { install } from '@atproto/lex-installer'\n *\n * await install({\n * lexicons: './lexicons',\n * manifest: './lexicons.manifest.json',\n * add: ['app.bsky.feed.post', 'app.bsky.actor.profile'],\n * save: true,\n * })\n * ```\n *\n * @example\n * Verify manifest in CI pipeline:\n * ```typescript\n * import { install } from '@atproto/lex-installer'\n *\n * // Throws if manifest is out of date\n * await install({\n * lexicons: './lexicons',\n * manifest: './lexicons.manifest.json',\n * ci: true,\n * })\n * ```\n *\n * @example\n * Install from specific AT URIs:\n * ```typescript\n * import { install } from '@atproto/lex-installer'\n *\n * await install({\n * lexicons: './lexicons',\n * manifest: './lexicons.manifest.json',\n * add: ['at://did:plc:z72i7hdynmk6r22z27h6tvur/app.bsky.feed.post'],\n * save: true,\n * })\n * ```\n */\nexport async function install(options: LexInstallOptions) {\n const manifest: LexiconsManifest | undefined = await readJsonFile(\n options.manifest,\n ).then(\n (json) => lexiconsManifestSchema.parse(json),\n (cause: unknown) => {\n if (isEnoentError(cause)) return undefined\n throw new Error('Failed to read lexicons manifest', { cause })\n },\n )\n\n const additions = new Set(options.add)\n\n // Perform the installation using the existing manifest as \"hint\"\n await using installer = new LexInstaller(options)\n\n await installer.install({ additions, manifest })\n\n // Verify lockfile\n if (options.ci && (!manifest || !installer.equals(manifest))) {\n throw new Error('Lexicons manifest is out of date')\n }\n\n // Save changes if requested\n if (options.save) {\n await installer.save()\n }\n}\n"]}
1
+ {"version":3,"file":"index.js","sourceRoot":"","sources":["../src/index.ts"],"names":[],"mappings":";;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;AAAA,OAAO,EAAE,aAAa,EAAE,YAAY,EAAE,MAAM,SAAS,CAAA;AAErD,OAAO,EAAE,YAAY,EAAE,MAAM,oBAAoB,CAAA;AAEjD,OAAO,EAAE,sBAAsB,EAAE,MAAM,wBAAwB,CAAA;AA2C/D;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;GAiDG;AACH,MAAM,CAAC,KAAK,UAAU,OAAO,CAAC,OAA0B;;;QACtD,MAAM,QAAQ,GAAiC,MAAM,YAAY,CAC/D,OAAO,CAAC,QAAQ,CACjB,CAAC,IAAI,CACJ,CAAC,IAAI,EAAE,EAAE,CAAC,sBAAsB,CAAC,KAAK,CAAC,IAAI,CAAC,EAC5C,CAAC,KAAc,EAAE,EAAE;YACjB,IAAI,aAAa,CAAC,KAAK,CAAC;gBAAE,OAAO,SAAS,CAAA;YAC1C,MAAM,IAAI,KAAK,CAAC,kCAAkC,EAAE,EAAE,KAAK,EAAE,CAAC,CAAA;QAChE,CAAC,CACF,CAAA;QAED,MAAM,SAAS,GAAG,IAAI,GAAG,CAAC,OAAO,CAAC,GAAG,CAAC,CAAA;QAEtC,iEAAiE;QACjE,MAAY,SAAS,kCAAG,IAAI,YAAY,CAAC,OAAO,CAAC,OAAA,CAAA;QAEjD,MAAM,SAAS,CAAC,OAAO,CAAC,EAAE,SAAS,EAAE,QAAQ,EAAE,CAAC,CAAA;QAEhD,kBAAkB;QAClB,IAAI,OAAO,CAAC,EAAE,IAAI,CAAC,CAAC,QAAQ,IAAI,CAAC,SAAS,CAAC,MAAM,CAAC,QAAQ,CAAC,CAAC,EAAE,CAAC;YAC7D,MAAM,IAAI,KAAK,CAAC,kCAAkC,CAAC,CAAA;QACrD,CAAC;QAED,4BAA4B;QAC5B,IAAI,OAAO,CAAC,IAAI,EAAE,CAAC;YACjB,MAAM,SAAS,CAAC,IAAI,EAAE,CAAA;QACxB,CAAC;;;;;;;;;;;AACH,CAAC","sourcesContent":["import { isEnoentError, readJsonFile } from './fs.js'\nimport type { LexInstallerOptions } from './lex-installer.js'\nimport { LexInstaller } from './lex-installer.js'\nimport type { LexiconsManifest } from './lexicons-manifest.js'\nimport { lexiconsManifestSchema } from './lexicons-manifest.js'\n\n/**\n * Options for the {@link install} function.\n *\n * Extends {@link LexInstallerOptions} with additional options for controlling\n * the installation behavior.\n *\n * @example\n * ```typescript\n * const options: LexInstallOptions = {\n * lexicons: './lexicons',\n * manifest: './lexicons.manifest.json',\n * add: ['com.example.myLexicon', 'at://did:plc:xyz/com.example.otherLexicon'],\n * save: true,\n * ci: false,\n * }\n * ```\n */\nexport type LexInstallOptions = LexInstallerOptions & {\n /**\n * Array of lexicons to add to the installation. Can be NSID strings\n * (e.g., 'com.example.myLexicon') or AT URIs\n * (e.g., 'at://did:plc:xyz/com.example.myLexicon').\n */\n add?: string[]\n\n /**\n * Whether to save the updated manifest after installation.\n * When `true`, the manifest file will be written with any new lexicons.\n * @default false\n */\n save?: boolean\n\n /**\n * Enable CI mode for strict manifest verification.\n * When `true`, throws an error if the manifest is out of date,\n * useful for continuous integration pipelines.\n * @default false\n */\n ci?: boolean\n}\n\n/**\n * Installs lexicons from the network based on the provided options.\n *\n * This is the main entry point for programmatic lexicon installation.\n * It reads an existing manifest (if present), installs any new lexicons,\n * and optionally saves the updated manifest.\n *\n * @param options - Configuration options for the installation\n * @throws {Error} When the manifest file cannot be read (unless it doesn't exist)\n * @throws {Error} When in CI mode and the manifest is out of date\n *\n * @example\n * Install lexicons and save the manifest:\n * ```typescript\n * import { install } from '@atproto/lex-installer'\n *\n * await install({\n * lexicons: './lexicons',\n * manifest: './lexicons.manifest.json',\n * add: ['app.bsky.feed.post', 'app.bsky.actor.profile'],\n * save: true,\n * })\n * ```\n *\n * @example\n * Verify manifest in CI pipeline:\n * ```typescript\n * import { install } from '@atproto/lex-installer'\n *\n * // Throws if manifest is out of date\n * await install({\n * lexicons: './lexicons',\n * manifest: './lexicons.manifest.json',\n * ci: true,\n * })\n * ```\n *\n * @example\n * Install from specific AT URIs:\n * ```typescript\n * import { install } from '@atproto/lex-installer'\n *\n * await install({\n * lexicons: './lexicons',\n * manifest: './lexicons.manifest.json',\n * add: ['at://did:plc:z72i7hdynmk6r22z27h6tvur/app.bsky.feed.post'],\n * save: true,\n * })\n * ```\n */\nexport async function install(options: LexInstallOptions) {\n const manifest: LexiconsManifest | undefined = await readJsonFile(\n options.manifest,\n ).then(\n (json) => lexiconsManifestSchema.parse(json),\n (cause: unknown) => {\n if (isEnoentError(cause)) return undefined\n throw new Error('Failed to read lexicons manifest', { cause })\n },\n )\n\n const additions = new Set(options.add)\n\n // Perform the installation using the existing manifest as \"hint\"\n await using installer = new LexInstaller(options)\n\n await installer.install({ additions, manifest })\n\n // Verify lockfile\n if (options.ci && (!manifest || !installer.equals(manifest))) {\n throw new Error('Lexicons manifest is out of date')\n }\n\n // Save changes if requested\n if (options.save) {\n await installer.save()\n }\n}\n"]}
@@ -1,9 +1,10 @@
1
1
  import { LexiconDirectoryIndexer } from '@atproto/lex-builder';
2
- import { Cid } from '@atproto/lex-data';
3
- import { LexiconDocument } from '@atproto/lex-document';
4
- import { LexResolver, LexResolverOptions } from '@atproto/lex-resolver';
2
+ import type { Cid } from '@atproto/lex-data';
3
+ import type { LexiconDocument } from '@atproto/lex-document';
4
+ import type { LexResolverOptions } from '@atproto/lex-resolver';
5
+ import { LexResolver } from '@atproto/lex-resolver';
5
6
  import { AtUri, NSID } from '@atproto/syntax';
6
- import { LexiconsManifest } from './lexicons-manifest.js';
7
+ import type { LexiconsManifest } from './lexicons-manifest.js';
7
8
  import { NsidMap } from './nsid-map.js';
8
9
  import { NsidSet } from './nsid-set.js';
9
10
  /**
@@ -1 +1 @@
1
- {"version":3,"file":"lex-installer.d.ts","sourceRoot":"","sources":["../src/lex-installer.ts"],"names":[],"mappings":"AACA,OAAO,EAAE,uBAAuB,EAAE,MAAM,sBAAsB,CAAA;AAE9D,OAAO,EAAE,GAAG,EAAa,MAAM,mBAAmB,CAAA;AAClD,OAAO,EACL,eAAe,EAQhB,MAAM,uBAAuB,CAAA;AAC9B,OAAO,EAAE,WAAW,EAAE,kBAAkB,EAAE,MAAM,uBAAuB,CAAA;AAEvE,OAAO,EAAE,KAAK,EAAE,IAAI,EAAE,MAAM,iBAAiB,CAAA;AAE7C,OAAO,EACL,gBAAgB,EAEjB,MAAM,wBAAwB,CAAA;AAC/B,OAAO,EAAE,OAAO,EAAE,MAAM,eAAe,CAAA;AACvC,OAAO,EAAE,OAAO,EAAE,MAAM,eAAe,CAAA;AAEvC;;;;;;;;;;;;;;GAcG;AACH,MAAM,MAAM,mBAAmB,GAAG,kBAAkB,GAAG;IACrD;;;;OAIG;IACH,QAAQ,EAAE,MAAM,CAAA;IAEhB;;OAEG;IACH,QAAQ,EAAE,MAAM,CAAA;IAEhB;;;;OAIG;IACH,MAAM,CAAC,EAAE,OAAO,CAAA;CACjB,CAAA;AAED;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;GAyCG;AACH,qBAAa,YAAa,YAAW,eAAe;IAUtC,SAAS,CAAC,QAAQ,CAAC,OAAO,EAAE,mBAAmB;IAT3D,SAAS,CAAC,QAAQ,CAAC,eAAe,EAAE,WAAW,CAAA;IAC/C,SAAS,CAAC,QAAQ,CAAC,OAAO,EAAE,uBAAuB,CAAA;IACnD,SAAS,CAAC,QAAQ,CAAC,SAAS;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;OAAiC;IAC7D,SAAS,CAAC,QAAQ,CAAC,QAAQ,EAAE,gBAAgB,CAI5C;IAED,YAA+B,OAAO,EAAE,mBAAmB,EAK1D;IAEK,CAAC,MAAM,CAAC,YAAY,CAAC,IAAI,OAAO,CAAC,IAAI,CAAC,CAE3C;IAED;;;;;;;;OAQG;IACH,MAAM,CAAC,QAAQ,EAAE,gBAAgB,GAAG,OAAO,CAK1C;IAED;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;OAwCG;IACG,OAAO,CAAC,EACZ,SAAS,EACT,QAAQ,GACT,GAAE;QACD,SAAS,CAAC,EAAE,QAAQ,CAAC,MAAM,CAAC,CAAA;QAC5B,QAAQ,CAAC,EAAE,gBAAgB,CAAA;KACvB,GAAG,OAAO,CAAC,IAAI,CAAC,CAwErB;IAED,SAAS,CAAC,aAAa,IAAI,OAAO,CAYjC;IAED,UAAgB,eAAe,CAAC,IAAI,EAAE,IAAI;iBAM/B,eAAe;aACnB,KAAK;OAJX;IAED,UAAgB,cAAc,CAAC,GAAG,EAAE,KAAK,GAAG,OAAO,CAAC;QAClD,OAAO,EAAE,eAAe,CAAA;QACxB,GAAG,EAAE,KAAK,CAAA;KACX,CAAC,CAsBD;IAED;;;;;;;;OAQG;IACG,KAAK,CAAC,GAAG,EAAE,KAAK,GAAG,OAAO,CAAC;QAAE,OAAO,EAAE,eAAe,CAAC;QAAC,GAAG,EAAE,GAAG,CAAA;KAAE,CAAC,CAWvE;IAED;;;;;OAKG;IACG,IAAI,IAAI,OAAO,CAAC,IAAI,CAAC,CAK1B;CACF"}
1
+ {"version":3,"file":"lex-installer.d.ts","sourceRoot":"","sources":["../src/lex-installer.ts"],"names":[],"mappings":"AACA,OAAO,EAAE,uBAAuB,EAAE,MAAM,sBAAsB,CAAA;AAE9D,OAAO,KAAK,EAAE,GAAG,EAAE,MAAM,mBAAmB,CAAA;AAE5C,OAAO,KAAK,EACV,eAAe,EAQhB,MAAM,uBAAuB,CAAA;AAC9B,OAAO,KAAK,EAAE,kBAAkB,EAAE,MAAM,uBAAuB,CAAA;AAC/D,OAAO,EAAE,WAAW,EAAE,MAAM,uBAAuB,CAAA;AAEnD,OAAO,EAAE,KAAK,EAAE,IAAI,EAAE,MAAM,iBAAiB,CAAA;AAE7C,OAAO,KAAK,EAAE,gBAAgB,EAAE,MAAM,wBAAwB,CAAA;AAE9D,OAAO,EAAE,OAAO,EAAE,MAAM,eAAe,CAAA;AACvC,OAAO,EAAE,OAAO,EAAE,MAAM,eAAe,CAAA;AAEvC;;;;;;;;;;;;;;GAcG;AACH,MAAM,MAAM,mBAAmB,GAAG,kBAAkB,GAAG;IACrD;;;;OAIG;IACH,QAAQ,EAAE,MAAM,CAAA;IAEhB;;OAEG;IACH,QAAQ,EAAE,MAAM,CAAA;IAEhB;;;;OAIG;IACH,MAAM,CAAC,EAAE,OAAO,CAAA;CACjB,CAAA;AAED;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;GAyCG;AACH,qBAAa,YAAa,YAAW,eAAe;IAUtC,SAAS,CAAC,QAAQ,CAAC,OAAO,EAAE,mBAAmB;IAT3D,SAAS,CAAC,QAAQ,CAAC,eAAe,EAAE,WAAW,CAAA;IAC/C,SAAS,CAAC,QAAQ,CAAC,OAAO,EAAE,uBAAuB,CAAA;IACnD,SAAS,CAAC,QAAQ,CAAC,SAAS;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;OAAiC;IAC7D,SAAS,CAAC,QAAQ,CAAC,QAAQ,EAAE,gBAAgB,CAI5C;IAED,YAA+B,OAAO,EAAE,mBAAmB,EAK1D;IAEK,CAAC,MAAM,CAAC,YAAY,CAAC,IAAI,OAAO,CAAC,IAAI,CAAC,CAE3C;IAED;;;;;;;;OAQG;IACH,MAAM,CAAC,QAAQ,EAAE,gBAAgB,GAAG,OAAO,CAK1C;IAED;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;OAwCG;IACG,OAAO,CAAC,EACZ,SAAS,EACT,QAAQ,GACT,GAAE;QACD,SAAS,CAAC,EAAE,QAAQ,CAAC,MAAM,CAAC,CAAA;QAC5B,QAAQ,CAAC,EAAE,gBAAgB,CAAA;KACvB,GAAG,OAAO,CAAC,IAAI,CAAC,CAwErB;IAED,SAAS,CAAC,aAAa,IAAI,OAAO,CAYjC;IAED,UAAgB,eAAe,CAAC,IAAI,EAAE,IAAI;iBAM/B,eAAe;aACnB,KAAK;OAJX;IAED,UAAgB,cAAc,CAAC,GAAG,EAAE,KAAK,GAAG,OAAO,CAAC;QAClD,OAAO,EAAE,eAAe,CAAA;QACxB,GAAG,EAAE,KAAK,CAAA;KACX,CAAC,CAsBD;IAED;;;;;;;;OAQG;IACG,KAAK,CAAC,GAAG,EAAE,KAAK,GAAG,OAAO,CAAC;QAAE,OAAO,EAAE,eAAe,CAAC;QAAC,GAAG,EAAE,GAAG,CAAA;KAAE,CAAC,CAWvE;IAED;;;;;OAKG;IACG,IAAI,IAAI,OAAO,CAAC,IAAI,CAAC,CAK1B;CACF"}
@@ -5,7 +5,7 @@ import { lexEquals } from '@atproto/lex-data';
5
5
  import { LexResolver } from '@atproto/lex-resolver';
6
6
  import { AtUri, NSID } from '@atproto/syntax';
7
7
  import { isEnoentError, writeJsonFile } from './fs.js';
8
- import { normalizeLexiconsManifest, } from './lexicons-manifest.js';
8
+ import { normalizeLexiconsManifest } from './lexicons-manifest.js';
9
9
  import { NsidMap } from './nsid-map.js';
10
10
  import { NsidSet } from './nsid-set.js';
11
11
  /**
@@ -1 +1 @@
1
- {"version":3,"file":"lex-installer.js","sourceRoot":"","sources":["../src/lex-installer.ts"],"names":[],"mappings":"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","sourcesContent":["import { join } from 'node:path'\nimport { LexiconDirectoryIndexer } from '@atproto/lex-builder'\nimport { cidForLex } from '@atproto/lex-cbor'\nimport { Cid, lexEquals } from '@atproto/lex-data'\nimport {\n LexiconDocument,\n LexiconParameters,\n LexiconPermission,\n LexiconRef,\n LexiconRefUnion,\n LexiconUnknown,\n MainLexiconDefinition,\n NamedLexiconDefinition,\n} from '@atproto/lex-document'\nimport { LexResolver, LexResolverOptions } from '@atproto/lex-resolver'\nimport { AtUriString, NsidString } from '@atproto/lex-schema'\nimport { AtUri, NSID } from '@atproto/syntax'\nimport { isEnoentError, writeJsonFile } from './fs.js'\nimport {\n LexiconsManifest,\n normalizeLexiconsManifest,\n} from './lexicons-manifest.js'\nimport { NsidMap } from './nsid-map.js'\nimport { NsidSet } from './nsid-set.js'\n\n/**\n * Configuration options for the {@link LexInstaller} class.\n *\n * Extends {@link LexResolverOptions} with paths for lexicon storage\n * and manifest management.\n *\n * @example\n * ```typescript\n * const options: LexInstallerOptions = {\n * lexicons: './lexicons',\n * manifest: './lexicons.manifest.json',\n * update: false,\n * }\n * ```\n */\nexport type LexInstallerOptions = LexResolverOptions & {\n /**\n * Path to the directory where lexicon JSON files will be stored.\n * The directory structure mirrors the NSID hierarchy\n * (e.g., 'app.bsky.feed.post' becomes 'app/bsky/feed/post.json').\n */\n lexicons: string\n\n /**\n * Path to the manifest file that tracks installed lexicons and their resolutions.\n */\n manifest: string\n\n /**\n * When `true`, forces re-fetching of lexicons from the network even if they\n * already exist locally. Useful for updating to newer versions.\n * @default false\n */\n update?: boolean\n}\n\n/**\n * Manages the installation of Lexicon schemas from the AT Protocol network.\n *\n * The `LexInstaller` class handles fetching, caching, and organizing lexicon\n * documents. It tracks dependencies between lexicons and ensures all referenced\n * schemas are installed. The class implements `AsyncDisposable` for proper\n * resource cleanup.\n *\n * @example\n * Basic usage with async disposal:\n * ```typescript\n * import { LexInstaller } from '@atproto/lex-installer'\n *\n * await using installer = new LexInstaller({\n * lexicons: './lexicons',\n * manifest: './lexicons.manifest.json',\n * })\n *\n * await installer.install({\n * additions: ['app.bsky.feed.post'],\n * })\n *\n * await installer.save()\n * // Resources automatically cleaned up when block exits\n * ```\n *\n * @example\n * Manual disposal:\n * ```typescript\n * const installer = new LexInstaller({\n * lexicons: './lexicons',\n * manifest: './lexicons.manifest.json',\n * })\n *\n * try {\n * await installer.install({ additions: ['app.bsky.actor.profile'] })\n * await installer.save()\n * } finally {\n * await installer[Symbol.asyncDispose]()\n * }\n * ```\n */\nexport class LexInstaller implements AsyncDisposable {\n protected readonly lexiconResolver: LexResolver\n protected readonly indexer: LexiconDirectoryIndexer\n protected readonly documents = new NsidMap<LexiconDocument>()\n protected readonly manifest: LexiconsManifest = {\n version: 1,\n lexicons: [],\n resolutions: {},\n }\n\n constructor(protected readonly options: LexInstallerOptions) {\n this.lexiconResolver = new LexResolver(options)\n this.indexer = new LexiconDirectoryIndexer({\n lexicons: options.lexicons,\n })\n }\n\n async [Symbol.asyncDispose](): Promise<void> {\n await this.indexer[Symbol.asyncDispose]()\n }\n\n /**\n * Compares the current manifest state with another manifest for equality.\n *\n * Both manifests are normalized before comparison to ensure consistent\n * ordering of entries. Useful for detecting changes during CI verification.\n *\n * @param manifest - The manifest to compare against\n * @returns `true` if the manifests are equivalent, `false` otherwise\n */\n equals(manifest: LexiconsManifest): boolean {\n return lexEquals(\n normalizeLexiconsManifest(manifest),\n normalizeLexiconsManifest(this.manifest),\n )\n }\n\n /**\n * Installs lexicons and their dependencies.\n *\n * This method processes explicit additions and restores entries from an\n * existing manifest. It recursively resolves and installs all referenced\n * lexicons to ensure complete dependency trees.\n *\n * @param options - Installation options\n * @param options.additions - Iterable of lexicon identifiers to add.\n * Can be NSID strings or AT URIs.\n * @param options.manifest - Existing manifest to use as a baseline.\n * Previously resolved URIs are preserved unless explicitly overridden.\n *\n * @example\n * Install new lexicons:\n * ```typescript\n * await installer.install({\n * additions: ['app.bsky.feed.post', 'app.bsky.actor.profile'],\n * })\n * ```\n *\n * @example\n * Install with existing manifest as hint:\n * ```typescript\n * const existingManifest = await readJsonFile('./lexicons.manifest.json')\n * await installer.install({\n * additions: ['com.example.newLexicon'],\n * manifest: existingManifest,\n * })\n * ```\n *\n * @example\n * Install from specific AT URIs:\n * ```typescript\n * await installer.install({\n * additions: [\n * 'at://did:plc:z72i7hdynmk6r22z27h6tvur/app.bsky.feed.post',\n * ],\n * })\n * ```\n */\n async install({\n additions,\n manifest,\n }: {\n additions?: Iterable<string>\n manifest?: LexiconsManifest\n } = {}): Promise<void> {\n const roots = new NsidMap<AtUri | null>()\n\n // First, process explicit additions\n for (const lexicon of new Set(additions)) {\n const [nsid, uri]: [NSID, AtUri | null] = lexicon.startsWith('at://')\n ? ((uri) => [NSID.from(uri.rkey), uri])(new AtUri(lexicon))\n : [NSID.from(lexicon), null]\n\n if (roots.has(nsid)) {\n throw new Error(\n `Duplicate lexicon addition: ${nsid} (${roots.get(nsid) ?? lexicon})`,\n )\n }\n\n roots.set(nsid, uri)\n console.debug(`Adding new lexicon: ${nsid} (${uri ?? 'from NSID'})`)\n }\n\n // Next, restore previously existing manifest entries\n if (manifest) {\n for (const lexicon of manifest.lexicons) {\n const nsid = NSID.from(lexicon)\n\n // Skip entries already added explicitly\n if (!roots.has(nsid)) {\n const uri = manifest.resolutions[lexicon]\n ? new AtUri(manifest.resolutions[lexicon].uri)\n : null\n\n roots.set(nsid, uri)\n\n console.debug(\n `Adding lexicon from manifest: ${nsid} (${uri ?? 'from NSID'})`,\n )\n }\n }\n }\n\n // Install all root lexicons (and store them in the manifest)\n await Promise.all(\n Array.from(roots, async ([nsid, sourceUri]) => {\n console.debug(`Installing lexicon: ${nsid}`)\n\n const { lexicon: document } = sourceUri\n ? await this.installFromUri(sourceUri)\n : await this.installFromNsid(nsid)\n\n // Store the direct reference in the new manifest\n this.manifest.lexicons.push(document.id)\n }),\n )\n\n // Then recursively install all referenced lexicons\n let results: unknown[]\n do {\n results = await Promise.all(\n Array.from(this.getMissingIds(), async (nsid) => {\n console.debug(`Resolving dependency lexicon: ${nsid}`)\n\n const nsidStr = nsid.toString() as NsidString\n const resolvedUri = manifest?.resolutions[nsidStr]?.uri\n ? new AtUri(manifest.resolutions[nsidStr].uri)\n : null\n if (resolvedUri) {\n await this.installFromUri(resolvedUri)\n } else {\n await this.installFromNsid(nsid)\n }\n }),\n )\n } while (results.length > 0)\n }\n\n protected getMissingIds(): NsidSet {\n const missing = new NsidSet()\n\n for (const document of this.documents.values()) {\n for (const nsid of listDocumentNsidRefs(document)) {\n if (!this.documents.has(nsid)) {\n missing.add(nsid)\n }\n }\n }\n\n return missing\n }\n\n protected async installFromNsid(nsid: NSID) {\n const uri = await this.lexiconResolver.resolve(nsid)\n return this.installFromUri(uri)\n }\n\n protected async installFromUri(uri: AtUri): Promise<{\n lexicon: LexiconDocument\n uri: AtUri\n }> {\n const { lexicon, cid } = this.options.update\n ? await this.fetch(uri)\n : await this.indexer.get(uri.rkey).then(\n async (lexicon) => {\n console.debug(`Re-using existing lexicon ${uri.rkey} from indexer`)\n const cid = await cidForLex(lexicon)\n return { cid, lexicon }\n },\n (err) => {\n if (isEnoentError(err)) return this.fetch(uri)\n throw err\n },\n )\n\n this.documents.set(NSID.from(lexicon.id), lexicon)\n this.manifest.resolutions[lexicon.id] = {\n cid: cid.toString(),\n uri: uri.toString() as AtUriString,\n }\n\n return { lexicon, uri }\n }\n\n /**\n * Fetches a lexicon document from the network and saves it locally.\n *\n * The lexicon is retrieved from the specified AT URI, written to the\n * local lexicons directory, and its metadata is recorded for the manifest.\n *\n * @param uri - The AT URI pointing to the lexicon document\n * @returns An object containing the fetched lexicon document and its CID\n */\n async fetch(uri: AtUri): Promise<{ lexicon: LexiconDocument; cid: Cid }> {\n console.debug(`Fetching lexicon from ${uri}...`)\n\n const { lexicon, cid } = await this.lexiconResolver.fetch(uri, {\n noCache: this.options.update,\n })\n\n const basePath = join(this.options.lexicons, ...lexicon.id.split('.'))\n await writeJsonFile(`${basePath}.json`, lexicon)\n\n return { lexicon, cid }\n }\n\n /**\n * Saves the current manifest to disk.\n *\n * The manifest is normalized before saving to ensure consistent ordering\n * of entries, making it suitable for version control.\n */\n async save(): Promise<void> {\n await writeJsonFile(\n this.options.manifest,\n normalizeLexiconsManifest(this.manifest),\n )\n }\n}\n\nfunction* listDocumentNsidRefs(doc: LexiconDocument): Iterable<NSID> {\n try {\n for (const def of Object.values(doc.defs)) {\n if (def) {\n for (const ref of defRefs(def)) {\n const [nsid] = ref.split('#', 1)\n if (nsid) yield NSID.from(nsid)\n }\n }\n }\n } catch (cause) {\n throw new Error(`Failed to extract refs from lexicon ${doc.id}`, { cause })\n }\n}\n\nfunction* defRefs(\n def:\n | MainLexiconDefinition\n | NamedLexiconDefinition\n | LexiconPermission\n | LexiconUnknown\n | LexiconParameters\n | LexiconRef\n | LexiconRefUnion,\n): Iterable<string> {\n switch (def.type) {\n case 'string':\n if (def.knownValues) {\n for (const val of def.knownValues) {\n // Tokens ?\n const { length, 0: nsid, 1: hash } = val.split('#')\n if (length === 2 && hash) {\n try {\n NSID.from(nsid)\n yield val\n } catch {\n // ignore invalid nsid\n }\n }\n }\n }\n return\n case 'array':\n return yield* defRefs(def.items)\n case 'params':\n case 'object':\n for (const prop of Object.values(def.properties)) {\n yield* defRefs(prop)\n }\n return\n case 'union':\n yield* def.refs\n return\n case 'ref': {\n yield def.ref\n return\n }\n case 'record':\n yield* defRefs(def.record)\n return\n case 'procedure':\n if (def.input?.schema) {\n yield* defRefs(def.input.schema)\n }\n // fallthrough\n case 'query':\n if (def.output?.schema) {\n yield* defRefs(def.output.schema)\n }\n // fallthrough\n case 'subscription':\n if (def.parameters) {\n yield* defRefs(def.parameters)\n }\n if ('message' in def && def.message?.schema) {\n yield* defRefs(def.message.schema)\n }\n return\n case 'permission-set':\n for (const permission of def.permissions) {\n yield* defRefs(permission)\n }\n return\n case 'permission':\n if (def.resource === 'rpc') {\n if (Array.isArray(def.lxm)) {\n for (const lxm of def.lxm) {\n if (typeof lxm === 'string') {\n yield lxm\n }\n }\n }\n } else if (def.resource === 'repo') {\n if (Array.isArray(def.collection)) {\n for (const lxm of def.collection) {\n if (typeof lxm === 'string') {\n yield lxm\n }\n }\n }\n }\n return\n case 'boolean':\n case 'cid-link':\n case 'token':\n case 'bytes':\n case 'blob':\n case 'integer':\n case 'unknown':\n // @NOTE We explicitly list all types here to ensure exhaustiveness\n // causing TS to error if a new type is added without updating this switch\n return\n default:\n // @ts-expect-error\n throw new Error(`Unknown lexicon def type: ${def.type}`)\n }\n}\n"]}
1
+ {"version":3,"file":"lex-installer.js","sourceRoot":"","sources":["../src/lex-installer.ts"],"names":[],"mappings":"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","sourcesContent":["import { join } from 'node:path'\nimport { LexiconDirectoryIndexer } from '@atproto/lex-builder'\nimport { cidForLex } from '@atproto/lex-cbor'\nimport type { Cid } from '@atproto/lex-data'\nimport { lexEquals } from '@atproto/lex-data'\nimport type {\n LexiconDocument,\n LexiconParameters,\n LexiconPermission,\n LexiconRef,\n LexiconRefUnion,\n LexiconUnknown,\n MainLexiconDefinition,\n NamedLexiconDefinition,\n} from '@atproto/lex-document'\nimport type { LexResolverOptions } from '@atproto/lex-resolver'\nimport { LexResolver } from '@atproto/lex-resolver'\nimport type { AtUriString, NsidString } from '@atproto/lex-schema'\nimport { AtUri, NSID } from '@atproto/syntax'\nimport { isEnoentError, writeJsonFile } from './fs.js'\nimport type { LexiconsManifest } from './lexicons-manifest.js'\nimport { normalizeLexiconsManifest } from './lexicons-manifest.js'\nimport { NsidMap } from './nsid-map.js'\nimport { NsidSet } from './nsid-set.js'\n\n/**\n * Configuration options for the {@link LexInstaller} class.\n *\n * Extends {@link LexResolverOptions} with paths for lexicon storage\n * and manifest management.\n *\n * @example\n * ```typescript\n * const options: LexInstallerOptions = {\n * lexicons: './lexicons',\n * manifest: './lexicons.manifest.json',\n * update: false,\n * }\n * ```\n */\nexport type LexInstallerOptions = LexResolverOptions & {\n /**\n * Path to the directory where lexicon JSON files will be stored.\n * The directory structure mirrors the NSID hierarchy\n * (e.g., 'app.bsky.feed.post' becomes 'app/bsky/feed/post.json').\n */\n lexicons: string\n\n /**\n * Path to the manifest file that tracks installed lexicons and their resolutions.\n */\n manifest: string\n\n /**\n * When `true`, forces re-fetching of lexicons from the network even if they\n * already exist locally. Useful for updating to newer versions.\n * @default false\n */\n update?: boolean\n}\n\n/**\n * Manages the installation of Lexicon schemas from the AT Protocol network.\n *\n * The `LexInstaller` class handles fetching, caching, and organizing lexicon\n * documents. It tracks dependencies between lexicons and ensures all referenced\n * schemas are installed. The class implements `AsyncDisposable` for proper\n * resource cleanup.\n *\n * @example\n * Basic usage with async disposal:\n * ```typescript\n * import { LexInstaller } from '@atproto/lex-installer'\n *\n * await using installer = new LexInstaller({\n * lexicons: './lexicons',\n * manifest: './lexicons.manifest.json',\n * })\n *\n * await installer.install({\n * additions: ['app.bsky.feed.post'],\n * })\n *\n * await installer.save()\n * // Resources automatically cleaned up when block exits\n * ```\n *\n * @example\n * Manual disposal:\n * ```typescript\n * const installer = new LexInstaller({\n * lexicons: './lexicons',\n * manifest: './lexicons.manifest.json',\n * })\n *\n * try {\n * await installer.install({ additions: ['app.bsky.actor.profile'] })\n * await installer.save()\n * } finally {\n * await installer[Symbol.asyncDispose]()\n * }\n * ```\n */\nexport class LexInstaller implements AsyncDisposable {\n protected readonly lexiconResolver: LexResolver\n protected readonly indexer: LexiconDirectoryIndexer\n protected readonly documents = new NsidMap<LexiconDocument>()\n protected readonly manifest: LexiconsManifest = {\n version: 1,\n lexicons: [],\n resolutions: {},\n }\n\n constructor(protected readonly options: LexInstallerOptions) {\n this.lexiconResolver = new LexResolver(options)\n this.indexer = new LexiconDirectoryIndexer({\n lexicons: options.lexicons,\n })\n }\n\n async [Symbol.asyncDispose](): Promise<void> {\n await this.indexer[Symbol.asyncDispose]()\n }\n\n /**\n * Compares the current manifest state with another manifest for equality.\n *\n * Both manifests are normalized before comparison to ensure consistent\n * ordering of entries. Useful for detecting changes during CI verification.\n *\n * @param manifest - The manifest to compare against\n * @returns `true` if the manifests are equivalent, `false` otherwise\n */\n equals(manifest: LexiconsManifest): boolean {\n return lexEquals(\n normalizeLexiconsManifest(manifest),\n normalizeLexiconsManifest(this.manifest),\n )\n }\n\n /**\n * Installs lexicons and their dependencies.\n *\n * This method processes explicit additions and restores entries from an\n * existing manifest. It recursively resolves and installs all referenced\n * lexicons to ensure complete dependency trees.\n *\n * @param options - Installation options\n * @param options.additions - Iterable of lexicon identifiers to add.\n * Can be NSID strings or AT URIs.\n * @param options.manifest - Existing manifest to use as a baseline.\n * Previously resolved URIs are preserved unless explicitly overridden.\n *\n * @example\n * Install new lexicons:\n * ```typescript\n * await installer.install({\n * additions: ['app.bsky.feed.post', 'app.bsky.actor.profile'],\n * })\n * ```\n *\n * @example\n * Install with existing manifest as hint:\n * ```typescript\n * const existingManifest = await readJsonFile('./lexicons.manifest.json')\n * await installer.install({\n * additions: ['com.example.newLexicon'],\n * manifest: existingManifest,\n * })\n * ```\n *\n * @example\n * Install from specific AT URIs:\n * ```typescript\n * await installer.install({\n * additions: [\n * 'at://did:plc:z72i7hdynmk6r22z27h6tvur/app.bsky.feed.post',\n * ],\n * })\n * ```\n */\n async install({\n additions,\n manifest,\n }: {\n additions?: Iterable<string>\n manifest?: LexiconsManifest\n } = {}): Promise<void> {\n const roots = new NsidMap<AtUri | null>()\n\n // First, process explicit additions\n for (const lexicon of new Set(additions)) {\n const [nsid, uri]: [NSID, AtUri | null] = lexicon.startsWith('at://')\n ? ((uri) => [NSID.from(uri.rkey), uri])(new AtUri(lexicon))\n : [NSID.from(lexicon), null]\n\n if (roots.has(nsid)) {\n throw new Error(\n `Duplicate lexicon addition: ${nsid} (${roots.get(nsid) ?? lexicon})`,\n )\n }\n\n roots.set(nsid, uri)\n console.debug(`Adding new lexicon: ${nsid} (${uri ?? 'from NSID'})`)\n }\n\n // Next, restore previously existing manifest entries\n if (manifest) {\n for (const lexicon of manifest.lexicons) {\n const nsid = NSID.from(lexicon)\n\n // Skip entries already added explicitly\n if (!roots.has(nsid)) {\n const uri = manifest.resolutions[lexicon]\n ? new AtUri(manifest.resolutions[lexicon].uri)\n : null\n\n roots.set(nsid, uri)\n\n console.debug(\n `Adding lexicon from manifest: ${nsid} (${uri ?? 'from NSID'})`,\n )\n }\n }\n }\n\n // Install all root lexicons (and store them in the manifest)\n await Promise.all(\n Array.from(roots, async ([nsid, sourceUri]) => {\n console.debug(`Installing lexicon: ${nsid}`)\n\n const { lexicon: document } = sourceUri\n ? await this.installFromUri(sourceUri)\n : await this.installFromNsid(nsid)\n\n // Store the direct reference in the new manifest\n this.manifest.lexicons.push(document.id)\n }),\n )\n\n // Then recursively install all referenced lexicons\n let results: unknown[]\n do {\n results = await Promise.all(\n Array.from(this.getMissingIds(), async (nsid) => {\n console.debug(`Resolving dependency lexicon: ${nsid}`)\n\n const nsidStr = nsid.toString() as NsidString\n const resolvedUri = manifest?.resolutions[nsidStr]?.uri\n ? new AtUri(manifest.resolutions[nsidStr].uri)\n : null\n if (resolvedUri) {\n await this.installFromUri(resolvedUri)\n } else {\n await this.installFromNsid(nsid)\n }\n }),\n )\n } while (results.length > 0)\n }\n\n protected getMissingIds(): NsidSet {\n const missing = new NsidSet()\n\n for (const document of this.documents.values()) {\n for (const nsid of listDocumentNsidRefs(document)) {\n if (!this.documents.has(nsid)) {\n missing.add(nsid)\n }\n }\n }\n\n return missing\n }\n\n protected async installFromNsid(nsid: NSID) {\n const uri = await this.lexiconResolver.resolve(nsid)\n return this.installFromUri(uri)\n }\n\n protected async installFromUri(uri: AtUri): Promise<{\n lexicon: LexiconDocument\n uri: AtUri\n }> {\n const { lexicon, cid } = this.options.update\n ? await this.fetch(uri)\n : await this.indexer.get(uri.rkey).then(\n async (lexicon) => {\n console.debug(`Re-using existing lexicon ${uri.rkey} from indexer`)\n const cid = await cidForLex(lexicon)\n return { cid, lexicon }\n },\n (err) => {\n if (isEnoentError(err)) return this.fetch(uri)\n throw err\n },\n )\n\n this.documents.set(NSID.from(lexicon.id), lexicon)\n this.manifest.resolutions[lexicon.id] = {\n cid: cid.toString(),\n uri: uri.toString() as AtUriString,\n }\n\n return { lexicon, uri }\n }\n\n /**\n * Fetches a lexicon document from the network and saves it locally.\n *\n * The lexicon is retrieved from the specified AT URI, written to the\n * local lexicons directory, and its metadata is recorded for the manifest.\n *\n * @param uri - The AT URI pointing to the lexicon document\n * @returns An object containing the fetched lexicon document and its CID\n */\n async fetch(uri: AtUri): Promise<{ lexicon: LexiconDocument; cid: Cid }> {\n console.debug(`Fetching lexicon from ${uri}...`)\n\n const { lexicon, cid } = await this.lexiconResolver.fetch(uri, {\n noCache: this.options.update,\n })\n\n const basePath = join(this.options.lexicons, ...lexicon.id.split('.'))\n await writeJsonFile(`${basePath}.json`, lexicon)\n\n return { lexicon, cid }\n }\n\n /**\n * Saves the current manifest to disk.\n *\n * The manifest is normalized before saving to ensure consistent ordering\n * of entries, making it suitable for version control.\n */\n async save(): Promise<void> {\n await writeJsonFile(\n this.options.manifest,\n normalizeLexiconsManifest(this.manifest),\n )\n }\n}\n\nfunction* listDocumentNsidRefs(doc: LexiconDocument): Iterable<NSID> {\n try {\n for (const def of Object.values(doc.defs)) {\n if (def) {\n for (const ref of defRefs(def)) {\n const [nsid] = ref.split('#', 1)\n if (nsid) yield NSID.from(nsid)\n }\n }\n }\n } catch (cause) {\n throw new Error(`Failed to extract refs from lexicon ${doc.id}`, { cause })\n }\n}\n\nfunction* defRefs(\n def:\n | MainLexiconDefinition\n | NamedLexiconDefinition\n | LexiconPermission\n | LexiconUnknown\n | LexiconParameters\n | LexiconRef\n | LexiconRefUnion,\n): Iterable<string> {\n switch (def.type) {\n case 'string':\n if (def.knownValues) {\n for (const val of def.knownValues) {\n // Tokens ?\n const { length, 0: nsid, 1: hash } = val.split('#')\n if (length === 2 && hash) {\n try {\n NSID.from(nsid)\n yield val\n } catch {\n // ignore invalid nsid\n }\n }\n }\n }\n return\n case 'array':\n return yield* defRefs(def.items)\n case 'params':\n case 'object':\n for (const prop of Object.values(def.properties)) {\n yield* defRefs(prop)\n }\n return\n case 'union':\n yield* def.refs\n return\n case 'ref': {\n yield def.ref\n return\n }\n case 'record':\n yield* defRefs(def.record)\n return\n case 'procedure':\n if (def.input?.schema) {\n yield* defRefs(def.input.schema)\n }\n // fallthrough\n case 'query':\n if (def.output?.schema) {\n yield* defRefs(def.output.schema)\n }\n // fallthrough\n case 'subscription':\n if (def.parameters) {\n yield* defRefs(def.parameters)\n }\n if ('message' in def && def.message?.schema) {\n yield* defRefs(def.message.schema)\n }\n return\n case 'permission-set':\n for (const permission of def.permissions) {\n yield* defRefs(permission)\n }\n return\n case 'permission':\n if (def.resource === 'rpc') {\n if (Array.isArray(def.lxm)) {\n for (const lxm of def.lxm) {\n if (typeof lxm === 'string') {\n yield lxm\n }\n }\n }\n } else if (def.resource === 'repo') {\n if (Array.isArray(def.collection)) {\n for (const lxm of def.collection) {\n if (typeof lxm === 'string') {\n yield lxm\n }\n }\n }\n }\n return\n case 'boolean':\n case 'cid-link':\n case 'token':\n case 'bytes':\n case 'blob':\n case 'integer':\n case 'unknown':\n // @NOTE We explicitly list all types here to ensure exhaustiveness\n // causing TS to error if a new type is added without updating this switch\n return\n default:\n // @ts-expect-error\n throw new Error(`Unknown lexicon def type: ${def.type}`)\n }\n}\n"]}
@@ -27,11 +27,13 @@ declare class MappedMap<K, V, I = any> implements Map<K, V> {
27
27
  get(key: K): V | undefined;
28
28
  has(key: K): boolean;
29
29
  delete(key: K): boolean;
30
- values(): IterableIterator<V>;
31
- keys(): IterableIterator<K>;
32
- entries(): IterableIterator<[K, V]>;
30
+ values(): MapIterator<V>;
31
+ keys(): MapIterator<K>;
32
+ entries(): MapIterator<[K, V]>;
33
33
  forEach(callbackfn: (value: V, key: K, map: MappedMap<K, V>) => void, thisArg?: any): void;
34
- [Symbol.iterator](): IterableIterator<[K, V]>;
34
+ getOrInsert(key: K, defaultValue: V): V;
35
+ getOrInsertComputed(key: K, callback: (key: K) => V): V;
36
+ [Symbol.iterator](): MapIterator<[K, V]>;
35
37
  [Symbol.toStringTag]: string;
36
38
  }
37
39
  /**
@@ -64,9 +66,6 @@ declare class MappedMap<K, V, I = any> implements Map<K, V> {
64
66
  * ```
65
67
  */
66
68
  export declare class NsidMap<T> extends MappedMap<NSID, T, string> {
67
- /**
68
- * Creates a new empty NsidMap.
69
- */
70
69
  constructor();
71
70
  }
72
71
  export {};
@@ -1 +1 @@
1
- {"version":3,"file":"nsid-map.d.ts","sourceRoot":"","sources":["../src/nsid-map.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,IAAI,EAAE,MAAM,iBAAiB,CAAA;AAEtC;;;;;;;;;;GAUG;AACH,cAAM,SAAS,CAAC,CAAC,EAAE,CAAC,EAAE,CAAC,GAAG,GAAG,CAAE,YAAW,GAAG,CAAC,CAAC,EAAE,CAAC,CAAC;IAU/C,OAAO,CAAC,QAAQ,CAAC,SAAS;IAC1B,OAAO,CAAC,QAAQ,CAAC,SAAS;IAV5B,OAAO,CAAC,GAAG,CAAkB;IAE7B;;;;;OAKG;IACH,YACmB,SAAS,EAAE,CAAC,GAAG,EAAE,CAAC,KAAK,CAAC,EACxB,SAAS,EAAE,CAAC,GAAG,EAAE,CAAC,KAAK,CAAC,EACvC;IAEJ,IAAI,IAAI,IAAI,MAAM,CAEjB;IAED,KAAK,IAAI,IAAI,CAEZ;IAED,GAAG,CAAC,GAAG,EAAE,CAAC,EAAE,KAAK,EAAE,CAAC,GAAG,IAAI,CAG1B;IAED,GAAG,CAAC,GAAG,EAAE,CAAC,GAAG,CAAC,GAAG,SAAS,CAEzB;IAED,GAAG,CAAC,GAAG,EAAE,CAAC,GAAG,OAAO,CAEnB;IAED,MAAM,CAAC,GAAG,EAAE,CAAC,GAAG,OAAO,CAEtB;IAED,MAAM,IAAI,gBAAgB,CAAC,CAAC,CAAC,CAE5B;IAEA,IAAI,IAAI,gBAAgB,CAAC,CAAC,CAAC,CAI3B;IAEA,OAAO,IAAI,gBAAgB,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAInC;IAED,OAAO,CACL,UAAU,EAAE,CAAC,KAAK,EAAE,CAAC,EAAE,GAAG,EAAE,CAAC,EAAE,GAAG,EAAE,SAAS,CAAC,CAAC,EAAE,CAAC,CAAC,KAAK,IAAI,EAC5D,OAAO,CAAC,EAAE,GAAG,GACZ,IAAI,CAIN;IAED,CAAC,MAAM,CAAC,QAAQ,CAAC,IAAI,gBAAgB,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAE5C;IAED,CAAC,MAAM,CAAC,WAAW,CAAC,EAAE,MAAM,CAAc;CAC3C;AAED;;;;;;;;;;;;;;;;;;;;;;;;;;;;GA4BG;AACH,qBAAa,OAAO,CAAC,CAAC,CAAE,SAAQ,SAAS,CAAC,IAAI,EAAE,CAAC,EAAE,MAAM,CAAC;IACxD;;OAEG;IACH,cAKC;CACF"}
1
+ {"version":3,"file":"nsid-map.d.ts","sourceRoot":"","sources":["../src/nsid-map.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,IAAI,EAAE,MAAM,iBAAiB,CAAA;AAEtC;;;;;;;;;;GAUG;AACH,cAAM,SAAS,CAAC,CAAC,EAAE,CAAC,EAAE,CAAC,GAAG,GAAG,CAAE,YAAW,GAAG,CAAC,CAAC,EAAE,CAAC,CAAC;IAU/C,OAAO,CAAC,QAAQ,CAAC,SAAS;IAC1B,OAAO,CAAC,QAAQ,CAAC,SAAS;IAV5B,OAAO,CAAC,GAAG,CAAkB;IAE7B;;;;;OAKG;IACH,YACmB,SAAS,EAAE,CAAC,GAAG,EAAE,CAAC,KAAK,CAAC,EACxB,SAAS,EAAE,CAAC,GAAG,EAAE,CAAC,KAAK,CAAC,EACvC;IAEJ,IAAI,IAAI,IAAI,MAAM,CAEjB;IAED,KAAK,IAAI,IAAI,CAEZ;IAED,GAAG,CAAC,GAAG,EAAE,CAAC,EAAE,KAAK,EAAE,CAAC,GAAG,IAAI,CAG1B;IAED,GAAG,CAAC,GAAG,EAAE,CAAC,GAAG,CAAC,GAAG,SAAS,CAEzB;IAED,GAAG,CAAC,GAAG,EAAE,CAAC,GAAG,OAAO,CAEnB;IAED,MAAM,CAAC,GAAG,EAAE,CAAC,GAAG,OAAO,CAEtB;IAED,MAAM,IAAI,WAAW,CAAC,CAAC,CAAC,CAEvB;IAEA,IAAI,IAAI,WAAW,CAAC,CAAC,CAAC,CAItB;IAEA,OAAO,IAAI,WAAW,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAI9B;IAED,OAAO,CACL,UAAU,EAAE,CAAC,KAAK,EAAE,CAAC,EAAE,GAAG,EAAE,CAAC,EAAE,GAAG,EAAE,SAAS,CAAC,CAAC,EAAE,CAAC,CAAC,KAAK,IAAI,EAC5D,OAAO,CAAC,EAAE,GAAG,GACZ,IAAI,CAIN;IAED,WAAW,CAAC,GAAG,EAAE,CAAC,EAAE,YAAY,EAAE,CAAC,GAAG,CAAC,CAItC;IAED,mBAAmB,CAAC,GAAG,EAAE,CAAC,EAAE,QAAQ,EAAE,CAAC,GAAG,EAAE,CAAC,KAAK,CAAC,GAAG,CAAC,CAMtD;IAED,CAAC,MAAM,CAAC,QAAQ,CAAC,IAAI,WAAW,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAEvC;IAED,CAAC,MAAM,CAAC,WAAW,CAAC,EAAE,MAAM,CAAc;CAC3C;AAED;;;;;;;;;;;;;;;;;;;;;;;;;;;;GA4BG;AACH,qBAAa,OAAO,CAAC,CAAC,CAAE,SAAQ,SAAS,CAAC,IAAI,EAAE,CAAC,EAAE,MAAM,CAAC;IACxD,cAEC;CACF"}
package/dist/nsid-map.js CHANGED
@@ -62,6 +62,19 @@ class MappedMap {
62
62
  callbackfn.call(thisArg, value, key, this);
63
63
  }
64
64
  }
65
+ getOrInsert(key, defaultValue) {
66
+ if (this.has(key))
67
+ return this.get(key);
68
+ this.set(key, defaultValue);
69
+ return defaultValue;
70
+ }
71
+ getOrInsertComputed(key, callback) {
72
+ if (this.has(key))
73
+ return this.get(key);
74
+ const value = callback(key);
75
+ this.set(key, value);
76
+ return value;
77
+ }
65
78
  [Symbol.iterator]() {
66
79
  return this.entries();
67
80
  }
@@ -96,11 +109,14 @@ class MappedMap {
96
109
  * ```
97
110
  */
98
111
  export class NsidMap extends MappedMap {
99
- /**
100
- * Creates a new empty NsidMap.
101
- */
102
112
  constructor() {
103
- super((key) => key.toString(), (enc) => NSID.from(enc));
113
+ super(nsidToString, stringToNsid);
104
114
  }
105
115
  }
116
+ function nsidToString(nsid) {
117
+ return nsid.toString();
118
+ }
119
+ function stringToNsid(str) {
120
+ return NSID.from(str);
121
+ }
106
122
  //# sourceMappingURL=nsid-map.js.map
@@ -1 +1 @@
1
- {"version":3,"file":"nsid-map.js","sourceRoot":"","sources":["../src/nsid-map.ts"],"names":[],"mappings":";AAAA,OAAO,EAAE,IAAI,EAAE,MAAM,iBAAiB,CAAA;AAEtC;;;;;;;;;;GAUG;AACH,MAAM,SAAS;kBAoEZ,MAAM,CAAC,WAAW;IAjEnB;;;;;OAKG;IACH,YACmB,SAAwB,EACxB,SAAwB;QADxB,cAAS,GAAT,SAAS,CAAe;QACxB,cAAS,GAAT,SAAS,CAAe;QAVnC,QAAG,GAAG,IAAI,GAAG,EAAQ,CAAA;QAmE7B,QAAoB,GAAW,WAAW,CAAA;IAxDvC,CAAC;IAEJ,IAAI,IAAI;QACN,OAAO,IAAI,CAAC,GAAG,CAAC,IAAI,CAAA;IACtB,CAAC;IAED,KAAK;QACH,IAAI,CAAC,GAAG,CAAC,KAAK,EAAE,CAAA;IAClB,CAAC;IAED,GAAG,CAAC,GAAM,EAAE,KAAQ;QAClB,IAAI,CAAC,GAAG,CAAC,GAAG,CAAC,IAAI,CAAC,SAAS,CAAC,GAAG,CAAC,EAAE,KAAK,CAAC,CAAA;QACxC,OAAO,IAAI,CAAA;IACb,CAAC;IAED,GAAG,CAAC,GAAM;QACR,OAAO,IAAI,CAAC,GAAG,CAAC,GAAG,CAAC,IAAI,CAAC,SAAS,CAAC,GAAG,CAAC,CAAC,CAAA;IAC1C,CAAC;IAED,GAAG,CAAC,GAAM;QACR,OAAO,IAAI,CAAC,GAAG,CAAC,GAAG,CAAC,IAAI,CAAC,SAAS,CAAC,GAAG,CAAC,CAAC,CAAA;IAC1C,CAAC;IAED,MAAM,CAAC,GAAM;QACX,OAAO,IAAI,CAAC,GAAG,CAAC,MAAM,CAAC,IAAI,CAAC,SAAS,CAAC,GAAG,CAAC,CAAC,CAAA;IAC7C,CAAC;IAED,MAAM;QACJ,OAAO,IAAI,CAAC,GAAG,CAAC,MAAM,EAAE,CAAA;IAC1B,CAAC;IAED,CAAC,IAAI;QACH,KAAK,MAAM,GAAG,IAAI,IAAI,CAAC,GAAG,CAAC,IAAI,EAAE,EAAE,CAAC;YAClC,MAAM,IAAI,CAAC,SAAS,CAAC,GAAG,CAAC,CAAA;QAC3B,CAAC;IACH,CAAC;IAED,CAAC,OAAO;QACN,KAAK,MAAM,CAAC,GAAG,EAAE,KAAK,CAAC,IAAI,IAAI,CAAC,GAAG,CAAC,OAAO,EAAE,EAAE,CAAC;YAC9C,MAAM,CAAC,IAAI,CAAC,SAAS,CAAC,GAAG,CAAC,EAAE,KAAK,CAAC,CAAA;QACpC,CAAC;IACH,CAAC;IAED,OAAO,CACL,UAA4D,EAC5D,OAAa;QAEb,KAAK,MAAM,CAAC,GAAG,EAAE,KAAK,CAAC,IAAI,IAAI,EAAE,CAAC;YAChC,UAAU,CAAC,IAAI,CAAC,OAAO,EAAE,KAAK,EAAE,GAAG,EAAE,IAAI,CAAC,CAAA;QAC5C,CAAC;IACH,CAAC;IAED,CAAC,MAAM,CAAC,QAAQ,CAAC;QACf,OAAO,IAAI,CAAC,OAAO,EAAE,CAAA;IACvB,CAAC;CAGF;AAED;;;;;;;;;;;;;;;;;;;;;;;;;;;;GA4BG;AACH,MAAM,OAAO,OAAW,SAAQ,SAA0B;IACxD;;OAEG;IACH;QACE,KAAK,CACH,CAAC,GAAG,EAAE,EAAE,CAAC,GAAG,CAAC,QAAQ,EAAE,EACvB,CAAC,GAAG,EAAE,EAAE,CAAC,IAAI,CAAC,IAAI,CAAC,GAAG,CAAC,CACxB,CAAA;IACH,CAAC;CACF","sourcesContent":["import { NSID } from '@atproto/syntax'\n\n/**\n * A Map implementation that maps keys of type K to an internal representation I.\n *\n * Key identity is determined by the {@link Object.is} comparison of the\n * encoded keys. This is useful for complex key types that can be serialized\n * to a unique primitive representation (typically strings).\n *\n * @typeParam K - The external key type\n * @typeParam V - The value type stored in the map\n * @typeParam I - The internal encoded key type used for identity comparison\n */\nclass MappedMap<K, V, I = any> implements Map<K, V> {\n private map = new Map<I, V>()\n\n /**\n * Creates a new MappedMap with custom key encoding/decoding functions.\n *\n * @param encodeKey - Function to convert external keys to internal representation\n * @param decodeKey - Function to convert internal representation back to external keys\n */\n constructor(\n private readonly encodeKey: (key: K) => I,\n private readonly decodeKey: (enc: I) => K,\n ) {}\n\n get size(): number {\n return this.map.size\n }\n\n clear(): void {\n this.map.clear()\n }\n\n set(key: K, value: V): this {\n this.map.set(this.encodeKey(key), value)\n return this\n }\n\n get(key: K): V | undefined {\n return this.map.get(this.encodeKey(key))\n }\n\n has(key: K): boolean {\n return this.map.has(this.encodeKey(key))\n }\n\n delete(key: K): boolean {\n return this.map.delete(this.encodeKey(key))\n }\n\n values(): IterableIterator<V> {\n return this.map.values()\n }\n\n *keys(): IterableIterator<K> {\n for (const key of this.map.keys()) {\n yield this.decodeKey(key)\n }\n }\n\n *entries(): IterableIterator<[K, V]> {\n for (const [key, value] of this.map.entries()) {\n yield [this.decodeKey(key), value]\n }\n }\n\n forEach(\n callbackfn: (value: V, key: K, map: MappedMap<K, V>) => void,\n thisArg?: any,\n ): void {\n for (const [key, value] of this) {\n callbackfn.call(thisArg, value, key, this)\n }\n }\n\n [Symbol.iterator](): IterableIterator<[K, V]> {\n return this.entries()\n }\n\n [Symbol.toStringTag]: string = 'MappedMap'\n}\n\n/**\n * A Map specialized for using NSID (Namespaced Identifier) values as keys.\n *\n * NSIDs are compared by their string representation, allowing different\n * NSID object instances with the same value to be treated as the same key.\n *\n * @typeParam T - The value type stored in the map\n *\n * @example\n * ```typescript\n * import { NsidMap } from '@atproto/lex-installer'\n * import { NSID } from '@atproto/syntax'\n * import { LexiconDocument } from '@atproto/lex-document'\n *\n * const lexicons = new NsidMap<LexiconDocument>()\n *\n * // Store lexicon documents by NSID\n * lexicons.set(NSID.from('app.bsky.feed.post'), postLexicon)\n * lexicons.set(NSID.from('app.bsky.actor.profile'), profileLexicon)\n *\n * // Retrieve by NSID (different object instance works)\n * const doc = lexicons.get(NSID.from('app.bsky.feed.post'))\n *\n * // Iterate over entries\n * for (const [nsid, lexicon] of lexicons) {\n * console.log(`${nsid}: ${lexicon.description}`)\n * }\n * ```\n */\nexport class NsidMap<T> extends MappedMap<NSID, T, string> {\n /**\n * Creates a new empty NsidMap.\n */\n constructor() {\n super(\n (key) => key.toString(),\n (enc) => NSID.from(enc),\n )\n }\n}\n"]}
1
+ {"version":3,"file":"nsid-map.js","sourceRoot":"","sources":["../src/nsid-map.ts"],"names":[],"mappings":"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","sourcesContent":["import { NSID } from '@atproto/syntax'\n\n/**\n * A Map implementation that maps keys of type K to an internal representation I.\n *\n * Key identity is determined by the {@link Object.is} comparison of the\n * encoded keys. This is useful for complex key types that can be serialized\n * to a unique primitive representation (typically strings).\n *\n * @typeParam K - The external key type\n * @typeParam V - The value type stored in the map\n * @typeParam I - The internal encoded key type used for identity comparison\n */\nclass MappedMap<K, V, I = any> implements Map<K, V> {\n private map = new Map<I, V>()\n\n /**\n * Creates a new MappedMap with custom key encoding/decoding functions.\n *\n * @param encodeKey - Function to convert external keys to internal representation\n * @param decodeKey - Function to convert internal representation back to external keys\n */\n constructor(\n private readonly encodeKey: (key: K) => I,\n private readonly decodeKey: (enc: I) => K,\n ) {}\n\n get size(): number {\n return this.map.size\n }\n\n clear(): void {\n this.map.clear()\n }\n\n set(key: K, value: V): this {\n this.map.set(this.encodeKey(key), value)\n return this\n }\n\n get(key: K): V | undefined {\n return this.map.get(this.encodeKey(key))\n }\n\n has(key: K): boolean {\n return this.map.has(this.encodeKey(key))\n }\n\n delete(key: K): boolean {\n return this.map.delete(this.encodeKey(key))\n }\n\n values(): MapIterator<V> {\n return this.map.values()\n }\n\n *keys(): MapIterator<K> {\n for (const key of this.map.keys()) {\n yield this.decodeKey(key)\n }\n }\n\n *entries(): MapIterator<[K, V]> {\n for (const [key, value] of this.map.entries()) {\n yield [this.decodeKey(key), value]\n }\n }\n\n forEach(\n callbackfn: (value: V, key: K, map: MappedMap<K, V>) => void,\n thisArg?: any,\n ): void {\n for (const [key, value] of this) {\n callbackfn.call(thisArg, value, key, this)\n }\n }\n\n getOrInsert(key: K, defaultValue: V): V {\n if (this.has(key)) return this.get(key)!\n this.set(key, defaultValue)\n return defaultValue\n }\n\n getOrInsertComputed(key: K, callback: (key: K) => V): V {\n if (this.has(key)) return this.get(key)!\n\n const value = callback(key)\n this.set(key, value)\n return value\n }\n\n [Symbol.iterator](): MapIterator<[K, V]> {\n return this.entries()\n }\n\n [Symbol.toStringTag]: string = 'MappedMap'\n}\n\n/**\n * A Map specialized for using NSID (Namespaced Identifier) values as keys.\n *\n * NSIDs are compared by their string representation, allowing different\n * NSID object instances with the same value to be treated as the same key.\n *\n * @typeParam T - The value type stored in the map\n *\n * @example\n * ```typescript\n * import { NsidMap } from '@atproto/lex-installer'\n * import { NSID } from '@atproto/syntax'\n * import { LexiconDocument } from '@atproto/lex-document'\n *\n * const lexicons = new NsidMap<LexiconDocument>()\n *\n * // Store lexicon documents by NSID\n * lexicons.set(NSID.from('app.bsky.feed.post'), postLexicon)\n * lexicons.set(NSID.from('app.bsky.actor.profile'), profileLexicon)\n *\n * // Retrieve by NSID (different object instance works)\n * const doc = lexicons.get(NSID.from('app.bsky.feed.post'))\n *\n * // Iterate over entries\n * for (const [nsid, lexicon] of lexicons) {\n * console.log(`${nsid}: ${lexicon.description}`)\n * }\n * ```\n */\nexport class NsidMap<T> extends MappedMap<NSID, T, string> {\n constructor() {\n super(nsidToString, stringToNsid)\n }\n}\n\nfunction nsidToString(nsid: NSID): string {\n return nsid.toString()\n}\n\nfunction stringToNsid(str: string): NSID {\n return NSID.from(str)\n}\n"]}
@@ -25,11 +25,18 @@ export declare class MappedSet<K, I = any> implements Set<K> {
25
25
  add(val: K): this;
26
26
  has(val: K): boolean;
27
27
  delete(val: K): boolean;
28
- values(): IterableIterator<K>;
28
+ values(): SetIterator<K>;
29
29
  keys(): SetIterator<K>;
30
- entries(): IterableIterator<[K, K]>;
30
+ entries(): SetIterator<[K, K]>;
31
31
  forEach(callbackfn: (value: K, value2: K, set: Set<K>) => void, thisArg?: any): void;
32
- [Symbol.iterator](): IterableIterator<K>;
32
+ union<U>(other: ReadonlySetLike<U>): Set<K | U>;
33
+ intersection<U>(other: ReadonlySetLike<U>): Set<K & U>;
34
+ difference<U>(other: ReadonlySetLike<U>): Set<K>;
35
+ symmetricDifference<U>(other: ReadonlySetLike<U>): Set<K | U>;
36
+ isSubsetOf(other: ReadonlySetLike<unknown>): boolean;
37
+ isSupersetOf(other: ReadonlySetLike<unknown>): boolean;
38
+ isDisjointFrom(other: ReadonlySetLike<unknown>): boolean;
39
+ [Symbol.iterator](): SetIterator<K>;
33
40
  [Symbol.toStringTag]: string;
34
41
  }
35
42
  /**
@@ -1 +1 @@
1
- {"version":3,"file":"nsid-set.d.ts","sourceRoot":"","sources":["../src/nsid-set.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,IAAI,EAAE,MAAM,iBAAiB,CAAA;AAEtC;;;;;;;;;GASG;AACH,qBAAa,SAAS,CAAC,CAAC,EAAE,CAAC,GAAG,GAAG,CAAE,YAAW,GAAG,CAAC,CAAC,CAAC;IAUhD,OAAO,CAAC,QAAQ,CAAC,WAAW;IAC5B,OAAO,CAAC,QAAQ,CAAC,WAAW;IAV9B,OAAO,CAAC,GAAG,CAAe;IAE1B;;;;;OAKG;IACH,YACmB,WAAW,EAAE,CAAC,GAAG,EAAE,CAAC,KAAK,CAAC,EAC1B,WAAW,EAAE,CAAC,GAAG,EAAE,CAAC,KAAK,CAAC,EACzC;IAEJ,IAAI,IAAI,IAAI,MAAM,CAEjB;IAED,KAAK,IAAI,IAAI,CAEZ;IAED,GAAG,CAAC,GAAG,EAAE,CAAC,GAAG,IAAI,CAGhB;IAED,GAAG,CAAC,GAAG,EAAE,CAAC,GAAG,OAAO,CAEnB;IAED,MAAM,CAAC,GAAG,EAAE,CAAC,GAAG,OAAO,CAEtB;IAEA,MAAM,IAAI,gBAAgB,CAAC,CAAC,CAAC,CAI7B;IAED,IAAI,IAAI,WAAW,CAAC,CAAC,CAAC,CAErB;IAEA,OAAO,IAAI,gBAAgB,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAEnC;IAED,OAAO,CACL,UAAU,EAAE,CAAC,KAAK,EAAE,CAAC,EAAE,MAAM,EAAE,CAAC,EAAE,GAAG,EAAE,GAAG,CAAC,CAAC,CAAC,KAAK,IAAI,EACtD,OAAO,CAAC,EAAE,GAAG,GACZ,IAAI,CAIN;IAED,CAAC,MAAM,CAAC,QAAQ,CAAC,IAAI,gBAAgB,CAAC,CAAC,CAAC,CAEvC;IAED,CAAC,MAAM,CAAC,WAAW,CAAC,EAAE,MAAM,CAAc;CAC3C;AAED;;;;;;;;;;;;;;;;;;;;;;;;GAwBG;AACH,qBAAa,OAAQ,SAAQ,SAAS,CAAC,IAAI,EAAE,MAAM,CAAC;IAClD;;OAEG;IACH,cAKC;CACF"}
1
+ {"version":3,"file":"nsid-set.d.ts","sourceRoot":"","sources":["../src/nsid-set.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,IAAI,EAAE,MAAM,iBAAiB,CAAA;AAEtC;;;;;;;;;GASG;AACH,qBAAa,SAAS,CAAC,CAAC,EAAE,CAAC,GAAG,GAAG,CAAE,YAAW,GAAG,CAAC,CAAC,CAAC;IAUhD,OAAO,CAAC,QAAQ,CAAC,WAAW;IAC5B,OAAO,CAAC,QAAQ,CAAC,WAAW;IAV9B,OAAO,CAAC,GAAG,CAAe;IAE1B;;;;;OAKG;IACH,YACmB,WAAW,EAAE,CAAC,GAAG,EAAE,CAAC,KAAK,CAAC,EAC1B,WAAW,EAAE,CAAC,GAAG,EAAE,CAAC,KAAK,CAAC,EACzC;IAEJ,IAAI,IAAI,IAAI,MAAM,CAEjB;IAED,KAAK,IAAI,IAAI,CAEZ;IAED,GAAG,CAAC,GAAG,EAAE,CAAC,GAAG,IAAI,CAGhB;IAED,GAAG,CAAC,GAAG,EAAE,CAAC,GAAG,OAAO,CAEnB;IAED,MAAM,CAAC,GAAG,EAAE,CAAC,GAAG,OAAO,CAEtB;IAEA,MAAM,IAAI,WAAW,CAAC,CAAC,CAAC,CAIxB;IAED,IAAI,IAAI,WAAW,CAAC,CAAC,CAAC,CAErB;IAEA,OAAO,IAAI,WAAW,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAE9B;IAED,OAAO,CACL,UAAU,EAAE,CAAC,KAAK,EAAE,CAAC,EAAE,MAAM,EAAE,CAAC,EAAE,GAAG,EAAE,GAAG,CAAC,CAAC,CAAC,KAAK,IAAI,EACtD,OAAO,CAAC,EAAE,GAAG,GACZ,IAAI,CAIN;IAED,KAAK,CAAC,CAAC,EAAE,KAAK,EAAE,eAAe,CAAC,CAAC,CAAC,GAAG,GAAG,CAAC,CAAC,GAAG,CAAC,CAAC,CAM9C;IAED,YAAY,CAAC,CAAC,EAAE,KAAK,EAAE,eAAe,CAAC,CAAC,CAAC,GAAG,GAAG,CAAC,CAAC,GAAG,CAAC,CAAC,CAQrD;IAED,UAAU,CAAC,CAAC,EAAE,KAAK,EAAE,eAAe,CAAC,CAAC,CAAC,GAAG,GAAG,CAAC,CAAC,CAAC,CAQ/C;IAED,mBAAmB,CAAC,CAAC,EAAE,KAAK,EAAE,eAAe,CAAC,CAAC,CAAC,GAAG,GAAG,CAAC,CAAC,GAAG,CAAC,CAAC,CAa5D;IAED,UAAU,CAAC,KAAK,EAAE,eAAe,CAAC,OAAO,CAAC,GAAG,OAAO,CAKnD;IAED,YAAY,CAAC,KAAK,EAAE,eAAe,CAAC,OAAO,CAAC,GAAG,OAAO,CAOrD;IAED,cAAc,CAAC,KAAK,EAAE,eAAe,CAAC,OAAO,CAAC,GAAG,OAAO,CAOvD;IAED,CAAC,MAAM,CAAC,QAAQ,CAAC,IAAI,WAAW,CAAC,CAAC,CAAC,CAElC;IAED,CAAC,MAAM,CAAC,WAAW,CAAC,EAAE,MAAM,CAAc;CAC3C;AAED;;;;;;;;;;;;;;;;;;;;;;;;GAwBG;AACH,qBAAa,OAAQ,SAAQ,SAAS,CAAC,IAAI,EAAE,MAAM,CAAC;IAClD;;OAEG;IACH,cAKC;CACF"}
package/dist/nsid-set.js CHANGED
@@ -57,6 +57,72 @@ export class MappedSet {
57
57
  callbackfn.call(thisArg, val, val, this);
58
58
  }
59
59
  }
60
+ union(other) {
61
+ const result = new Set(this);
62
+ const it = other.keys();
63
+ let res;
64
+ while (!(res = it.next()).done)
65
+ result.add(res.value);
66
+ return result;
67
+ }
68
+ intersection(other) {
69
+ const result = new Set();
70
+ for (const val of this) {
71
+ if (other.has(val)) {
72
+ result.add(val);
73
+ }
74
+ }
75
+ return result;
76
+ }
77
+ difference(other) {
78
+ const result = new Set();
79
+ for (const val of this) {
80
+ if (!other.has(val)) {
81
+ result.add(val);
82
+ }
83
+ }
84
+ return result;
85
+ }
86
+ symmetricDifference(other) {
87
+ const result = new Set(this);
88
+ const it = other.keys();
89
+ let res;
90
+ while (!(res = it.next()).done) {
91
+ const val = res.value;
92
+ if (result.has(val)) {
93
+ result.delete(val);
94
+ }
95
+ else {
96
+ result.add(val);
97
+ }
98
+ }
99
+ return result;
100
+ }
101
+ isSubsetOf(other) {
102
+ for (const val of this) {
103
+ if (!other.has(val))
104
+ return false;
105
+ }
106
+ return true;
107
+ }
108
+ isSupersetOf(other) {
109
+ const it = other.keys();
110
+ let res;
111
+ while (!(res = it.next()).done) {
112
+ if (!this.has(res.value))
113
+ return false;
114
+ }
115
+ return true;
116
+ }
117
+ isDisjointFrom(other) {
118
+ const it = other.keys();
119
+ let res;
120
+ while (!(res = it.next()).done) {
121
+ if (this.has(res.value))
122
+ return false;
123
+ }
124
+ return true;
125
+ }
60
126
  [Symbol.iterator]() {
61
127
  return this.values();
62
128
  }
@@ -1 +1 @@
1
- {"version":3,"file":"nsid-set.js","sourceRoot":"","sources":["../src/nsid-set.ts"],"names":[],"mappings":";AAAA,OAAO,EAAE,IAAI,EAAE,MAAM,iBAAiB,CAAA;AAEtC;;;;;;;;;GASG;AACH,MAAM,OAAO,SAAS;kBA8DnB,MAAM,CAAC,WAAW;IA3DnB;;;;;OAKG;IACH,YACmB,WAA0B,EAC1B,WAA0B;QAD1B,gBAAW,GAAX,WAAW,CAAe;QAC1B,gBAAW,GAAX,WAAW,CAAe;QAVrC,QAAG,GAAG,IAAI,GAAG,EAAK,CAAA;QA6D1B,QAAoB,GAAW,WAAW,CAAA;IAlDvC,CAAC;IAEJ,IAAI,IAAI;QACN,OAAO,IAAI,CAAC,GAAG,CAAC,IAAI,CAAA;IACtB,CAAC;IAED,KAAK;QACH,IAAI,CAAC,GAAG,CAAC,KAAK,EAAE,CAAA;IAClB,CAAC;IAED,GAAG,CAAC,GAAM;QACR,IAAI,CAAC,GAAG,CAAC,GAAG,CAAC,IAAI,CAAC,WAAW,CAAC,GAAG,CAAC,CAAC,CAAA;QACnC,OAAO,IAAI,CAAA;IACb,CAAC;IAED,GAAG,CAAC,GAAM;QACR,OAAO,IAAI,CAAC,GAAG,CAAC,GAAG,CAAC,IAAI,CAAC,WAAW,CAAC,GAAG,CAAC,CAAC,CAAA;IAC5C,CAAC;IAED,MAAM,CAAC,GAAM;QACX,OAAO,IAAI,CAAC,GAAG,CAAC,MAAM,CAAC,IAAI,CAAC,WAAW,CAAC,GAAG,CAAC,CAAC,CAAA;IAC/C,CAAC;IAED,CAAC,MAAM;QACL,KAAK,MAAM,GAAG,IAAI,IAAI,CAAC,GAAG,CAAC,MAAM,EAAE,EAAE,CAAC;YACpC,MAAM,IAAI,CAAC,WAAW,CAAC,GAAG,CAAC,CAAA;QAC7B,CAAC;IACH,CAAC;IAED,IAAI;QACF,OAAO,IAAI,CAAC,MAAM,EAAE,CAAA;IACtB,CAAC;IAED,CAAC,OAAO;QACN,KAAK,MAAM,GAAG,IAAI,IAAI;YAAE,MAAM,CAAC,GAAG,EAAE,GAAG,CAAC,CAAA;IAC1C,CAAC;IAED,OAAO,CACL,UAAsD,EACtD,OAAa;QAEb,KAAK,MAAM,GAAG,IAAI,IAAI,EAAE,CAAC;YACvB,UAAU,CAAC,IAAI,CAAC,OAAO,EAAE,GAAG,EAAE,GAAG,EAAE,IAAI,CAAC,CAAA;QAC1C,CAAC;IACH,CAAC;IAED,CAAC,MAAM,CAAC,QAAQ,CAAC;QACf,OAAO,IAAI,CAAC,MAAM,EAAE,CAAA;IACtB,CAAC;CAGF;AAED;;;;;;;;;;;;;;;;;;;;;;;;GAwBG;AACH,MAAM,OAAO,OAAQ,SAAQ,SAAuB;IAClD;;OAEG;IACH;QACE,KAAK,CACH,CAAC,GAAG,EAAE,EAAE,CAAC,GAAG,CAAC,QAAQ,EAAE,EACvB,CAAC,GAAG,EAAE,EAAE,CAAC,IAAI,CAAC,IAAI,CAAC,GAAG,CAAC,CACxB,CAAA;IACH,CAAC;CACF","sourcesContent":["import { NSID } from '@atproto/syntax'\n\n/**\n * A Set implementation that maps values of type K to an internal representation I.\n *\n * Value identity is determined by the {@link Object.is} comparison of the\n * encoded values. This is useful for complex types that can be serialized\n * to a unique primitive representation (typically strings).\n *\n * @typeParam K - The external value type stored in the set\n * @typeParam I - The internal encoded type used for identity comparison\n */\nexport class MappedSet<K, I = any> implements Set<K> {\n private set = new Set<I>()\n\n /**\n * Creates a new MappedSet with custom encoding/decoding functions.\n *\n * @param encodeValue - Function to convert external values to internal representation\n * @param decodeValue - Function to convert internal representation back to external values\n */\n constructor(\n private readonly encodeValue: (val: K) => I,\n private readonly decodeValue: (enc: I) => K,\n ) {}\n\n get size(): number {\n return this.set.size\n }\n\n clear(): void {\n this.set.clear()\n }\n\n add(val: K): this {\n this.set.add(this.encodeValue(val))\n return this\n }\n\n has(val: K): boolean {\n return this.set.has(this.encodeValue(val))\n }\n\n delete(val: K): boolean {\n return this.set.delete(this.encodeValue(val))\n }\n\n *values(): IterableIterator<K> {\n for (const val of this.set.values()) {\n yield this.decodeValue(val)\n }\n }\n\n keys(): SetIterator<K> {\n return this.values()\n }\n\n *entries(): IterableIterator<[K, K]> {\n for (const val of this) yield [val, val]\n }\n\n forEach(\n callbackfn: (value: K, value2: K, set: Set<K>) => void,\n thisArg?: any,\n ): void {\n for (const val of this) {\n callbackfn.call(thisArg, val, val, this)\n }\n }\n\n [Symbol.iterator](): IterableIterator<K> {\n return this.values()\n }\n\n [Symbol.toStringTag]: string = 'MappedSet'\n}\n\n/**\n * A Set specialized for storing NSID (Namespaced Identifier) values.\n *\n * NSIDs are compared by their string representation, allowing different\n * NSID object instances with the same value to be treated as equal.\n *\n * @example\n * ```typescript\n * import { NsidSet } from '@atproto/lex-installer'\n * import { NSID } from '@atproto/syntax'\n *\n * const nsidSet = new NsidSet()\n *\n * nsidSet.add(NSID.from('app.bsky.feed.post'))\n * nsidSet.add(NSID.from('app.bsky.actor.profile'))\n *\n * // Check membership\n * nsidSet.has(NSID.from('app.bsky.feed.post')) // true\n *\n * // Iterate over NSIDs\n * for (const nsid of nsidSet) {\n * console.log(nsid.toString())\n * }\n * ```\n */\nexport class NsidSet extends MappedSet<NSID, string> {\n /**\n * Creates a new empty NsidSet.\n */\n constructor() {\n super(\n (val) => val.toString(),\n (enc) => NSID.from(enc),\n )\n }\n}\n"]}
1
+ {"version":3,"file":"nsid-set.js","sourceRoot":"","sources":["../src/nsid-set.ts"],"names":[],"mappings":";AAAA,OAAO,EAAE,IAAI,EAAE,MAAM,iBAAiB,CAAA;AAEtC;;;;;;;;;GASG;AACH,MAAM,OAAO,SAAS;kBAkInB,MAAM,CAAC,WAAW;IA/HnB;;;;;OAKG;IACH,YACmB,WAA0B,EAC1B,WAA0B;QAD1B,gBAAW,GAAX,WAAW,CAAe;QAC1B,gBAAW,GAAX,WAAW,CAAe;QAVrC,QAAG,GAAG,IAAI,GAAG,EAAK,CAAA;QAiI1B,QAAoB,GAAW,WAAW,CAAA;IAtHvC,CAAC;IAEJ,IAAI,IAAI;QACN,OAAO,IAAI,CAAC,GAAG,CAAC,IAAI,CAAA;IACtB,CAAC;IAED,KAAK;QACH,IAAI,CAAC,GAAG,CAAC,KAAK,EAAE,CAAA;IAClB,CAAC;IAED,GAAG,CAAC,GAAM;QACR,IAAI,CAAC,GAAG,CAAC,GAAG,CAAC,IAAI,CAAC,WAAW,CAAC,GAAG,CAAC,CAAC,CAAA;QACnC,OAAO,IAAI,CAAA;IACb,CAAC;IAED,GAAG,CAAC,GAAM;QACR,OAAO,IAAI,CAAC,GAAG,CAAC,GAAG,CAAC,IAAI,CAAC,WAAW,CAAC,GAAG,CAAC,CAAC,CAAA;IAC5C,CAAC;IAED,MAAM,CAAC,GAAM;QACX,OAAO,IAAI,CAAC,GAAG,CAAC,MAAM,CAAC,IAAI,CAAC,WAAW,CAAC,GAAG,CAAC,CAAC,CAAA;IAC/C,CAAC;IAED,CAAC,MAAM;QACL,KAAK,MAAM,GAAG,IAAI,IAAI,CAAC,GAAG,CAAC,MAAM,EAAE,EAAE,CAAC;YACpC,MAAM,IAAI,CAAC,WAAW,CAAC,GAAG,CAAC,CAAA;QAC7B,CAAC;IACH,CAAC;IAED,IAAI;QACF,OAAO,IAAI,CAAC,MAAM,EAAE,CAAA;IACtB,CAAC;IAED,CAAC,OAAO;QACN,KAAK,MAAM,GAAG,IAAI,IAAI;YAAE,MAAM,CAAC,GAAG,EAAE,GAAG,CAAC,CAAA;IAC1C,CAAC;IAED,OAAO,CACL,UAAsD,EACtD,OAAa;QAEb,KAAK,MAAM,GAAG,IAAI,IAAI,EAAE,CAAC;YACvB,UAAU,CAAC,IAAI,CAAC,OAAO,EAAE,GAAG,EAAE,GAAG,EAAE,IAAI,CAAC,CAAA;QAC1C,CAAC;IACH,CAAC;IAED,KAAK,CAAI,KAAyB;QAChC,MAAM,MAAM,GAAG,IAAI,GAAG,CAAQ,IAAI,CAAC,CAAA;QACnC,MAAM,EAAE,GAAG,KAAK,CAAC,IAAI,EAAE,CAAA;QACvB,IAAI,GAAsB,CAAA;QAC1B,OAAO,CAAC,CAAC,GAAG,GAAG,EAAE,CAAC,IAAI,EAAE,CAAC,CAAC,IAAI;YAAE,MAAM,CAAC,GAAG,CAAC,GAAG,CAAC,KAAK,CAAC,CAAA;QACrD,OAAO,MAAM,CAAA;IACf,CAAC;IAED,YAAY,CAAI,KAAyB;QACvC,MAAM,MAAM,GAAG,IAAI,GAAG,EAAS,CAAA;QAC/B,KAAK,MAAM,GAAG,IAAI,IAAI,EAAE,CAAC;YACvB,IAAI,KAAK,CAAC,GAAG,CAAC,GAAmB,CAAC,EAAE,CAAC;gBACnC,MAAM,CAAC,GAAG,CAAC,GAAuB,CAAC,CAAA;YACrC,CAAC;QACH,CAAC;QACD,OAAO,MAAM,CAAA;IACf,CAAC;IAED,UAAU,CAAI,KAAyB;QACrC,MAAM,MAAM,GAAG,IAAI,GAAG,EAAK,CAAA;QAC3B,KAAK,MAAM,GAAG,IAAI,IAAI,EAAE,CAAC;YACvB,IAAI,CAAC,KAAK,CAAC,GAAG,CAAC,GAAmB,CAAC,EAAE,CAAC;gBACpC,MAAM,CAAC,GAAG,CAAC,GAAG,CAAC,CAAA;YACjB,CAAC;QACH,CAAC;QACD,OAAO,MAAM,CAAA;IACf,CAAC;IAED,mBAAmB,CAAI,KAAyB;QAC9C,MAAM,MAAM,GAAG,IAAI,GAAG,CAAQ,IAAI,CAAC,CAAA;QACnC,MAAM,EAAE,GAAG,KAAK,CAAC,IAAI,EAAE,CAAA;QACvB,IAAI,GAAsB,CAAA;QAC1B,OAAO,CAAC,CAAC,GAAG,GAAG,EAAE,CAAC,IAAI,EAAE,CAAC,CAAC,IAAI,EAAE,CAAC;YAC/B,MAAM,GAAG,GAAG,GAAG,CAAC,KAAK,CAAA;YACrB,IAAI,MAAM,CAAC,GAAG,CAAC,GAAmB,CAAC,EAAE,CAAC;gBACpC,MAAM,CAAC,MAAM,CAAC,GAAmB,CAAC,CAAA;YACpC,CAAC;iBAAM,CAAC;gBACN,MAAM,CAAC,GAAG,CAAC,GAAG,CAAC,CAAA;YACjB,CAAC;QACH,CAAC;QACD,OAAO,MAAM,CAAA;IACf,CAAC;IAED,UAAU,CAAC,KAA+B;QACxC,KAAK,MAAM,GAAG,IAAI,IAAI,EAAE,CAAC;YACvB,IAAI,CAAC,KAAK,CAAC,GAAG,CAAC,GAAG,CAAC;gBAAE,OAAO,KAAK,CAAA;QACnC,CAAC;QACD,OAAO,IAAI,CAAA;IACb,CAAC;IAED,YAAY,CAAC,KAA+B;QAC1C,MAAM,EAAE,GAAG,KAAK,CAAC,IAAI,EAAE,CAAA;QACvB,IAAI,GAA4B,CAAA;QAChC,OAAO,CAAC,CAAC,GAAG,GAAG,EAAE,CAAC,IAAI,EAAE,CAAC,CAAC,IAAI,EAAE,CAAC;YAC/B,IAAI,CAAC,IAAI,CAAC,GAAG,CAAC,GAAG,CAAC,KAAU,CAAC;gBAAE,OAAO,KAAK,CAAA;QAC7C,CAAC;QACD,OAAO,IAAI,CAAA;IACb,CAAC;IAED,cAAc,CAAC,KAA+B;QAC5C,MAAM,EAAE,GAAG,KAAK,CAAC,IAAI,EAAE,CAAA;QACvB,IAAI,GAA4B,CAAA;QAChC,OAAO,CAAC,CAAC,GAAG,GAAG,EAAE,CAAC,IAAI,EAAE,CAAC,CAAC,IAAI,EAAE,CAAC;YAC/B,IAAI,IAAI,CAAC,GAAG,CAAC,GAAG,CAAC,KAAU,CAAC;gBAAE,OAAO,KAAK,CAAA;QAC5C,CAAC;QACD,OAAO,IAAI,CAAA;IACb,CAAC;IAED,CAAC,MAAM,CAAC,QAAQ,CAAC;QACf,OAAO,IAAI,CAAC,MAAM,EAAE,CAAA;IACtB,CAAC;CAGF;AAED;;;;;;;;;;;;;;;;;;;;;;;;GAwBG;AACH,MAAM,OAAO,OAAQ,SAAQ,SAAuB;IAClD;;OAEG;IACH;QACE,KAAK,CACH,CAAC,GAAG,EAAE,EAAE,CAAC,GAAG,CAAC,QAAQ,EAAE,EACvB,CAAC,GAAG,EAAE,EAAE,CAAC,IAAI,CAAC,IAAI,CAAC,GAAG,CAAC,CACxB,CAAA;IACH,CAAC;CACF","sourcesContent":["import { NSID } from '@atproto/syntax'\n\n/**\n * A Set implementation that maps values of type K to an internal representation I.\n *\n * Value identity is determined by the {@link Object.is} comparison of the\n * encoded values. This is useful for complex types that can be serialized\n * to a unique primitive representation (typically strings).\n *\n * @typeParam K - The external value type stored in the set\n * @typeParam I - The internal encoded type used for identity comparison\n */\nexport class MappedSet<K, I = any> implements Set<K> {\n private set = new Set<I>()\n\n /**\n * Creates a new MappedSet with custom encoding/decoding functions.\n *\n * @param encodeValue - Function to convert external values to internal representation\n * @param decodeValue - Function to convert internal representation back to external values\n */\n constructor(\n private readonly encodeValue: (val: K) => I,\n private readonly decodeValue: (enc: I) => K,\n ) {}\n\n get size(): number {\n return this.set.size\n }\n\n clear(): void {\n this.set.clear()\n }\n\n add(val: K): this {\n this.set.add(this.encodeValue(val))\n return this\n }\n\n has(val: K): boolean {\n return this.set.has(this.encodeValue(val))\n }\n\n delete(val: K): boolean {\n return this.set.delete(this.encodeValue(val))\n }\n\n *values(): SetIterator<K> {\n for (const val of this.set.values()) {\n yield this.decodeValue(val)\n }\n }\n\n keys(): SetIterator<K> {\n return this.values()\n }\n\n *entries(): SetIterator<[K, K]> {\n for (const val of this) yield [val, val]\n }\n\n forEach(\n callbackfn: (value: K, value2: K, set: Set<K>) => void,\n thisArg?: any,\n ): void {\n for (const val of this) {\n callbackfn.call(thisArg, val, val, this)\n }\n }\n\n union<U>(other: ReadonlySetLike<U>): Set<K | U> {\n const result = new Set<K | U>(this)\n const it = other.keys()\n let res: IteratorResult<U>\n while (!(res = it.next()).done) result.add(res.value)\n return result\n }\n\n intersection<U>(other: ReadonlySetLike<U>): Set<K & U> {\n const result = new Set<K & U>()\n for (const val of this) {\n if (other.has(val as unknown as U)) {\n result.add(val as unknown as K & U)\n }\n }\n return result\n }\n\n difference<U>(other: ReadonlySetLike<U>): Set<K> {\n const result = new Set<K>()\n for (const val of this) {\n if (!other.has(val as unknown as U)) {\n result.add(val)\n }\n }\n return result\n }\n\n symmetricDifference<U>(other: ReadonlySetLike<U>): Set<K | U> {\n const result = new Set<K | U>(this)\n const it = other.keys()\n let res: IteratorResult<U>\n while (!(res = it.next()).done) {\n const val = res.value\n if (result.has(val as unknown as K)) {\n result.delete(val as unknown as K)\n } else {\n result.add(val)\n }\n }\n return result\n }\n\n isSubsetOf(other: ReadonlySetLike<unknown>): boolean {\n for (const val of this) {\n if (!other.has(val)) return false\n }\n return true\n }\n\n isSupersetOf(other: ReadonlySetLike<unknown>): boolean {\n const it = other.keys()\n let res: IteratorResult<unknown>\n while (!(res = it.next()).done) {\n if (!this.has(res.value as K)) return false\n }\n return true\n }\n\n isDisjointFrom(other: ReadonlySetLike<unknown>): boolean {\n const it = other.keys()\n let res: IteratorResult<unknown>\n while (!(res = it.next()).done) {\n if (this.has(res.value as K)) return false\n }\n return true\n }\n\n [Symbol.iterator](): SetIterator<K> {\n return this.values()\n }\n\n [Symbol.toStringTag]: string = 'MappedSet'\n}\n\n/**\n * A Set specialized for storing NSID (Namespaced Identifier) values.\n *\n * NSIDs are compared by their string representation, allowing different\n * NSID object instances with the same value to be treated as equal.\n *\n * @example\n * ```typescript\n * import { NsidSet } from '@atproto/lex-installer'\n * import { NSID } from '@atproto/syntax'\n *\n * const nsidSet = new NsidSet()\n *\n * nsidSet.add(NSID.from('app.bsky.feed.post'))\n * nsidSet.add(NSID.from('app.bsky.actor.profile'))\n *\n * // Check membership\n * nsidSet.has(NSID.from('app.bsky.feed.post')) // true\n *\n * // Iterate over NSIDs\n * for (const nsid of nsidSet) {\n * console.log(nsid.toString())\n * }\n * ```\n */\nexport class NsidSet extends MappedSet<NSID, string> {\n /**\n * Creates a new empty NsidSet.\n */\n constructor() {\n super(\n (val) => val.toString(),\n (enc) => NSID.from(enc),\n )\n }\n}\n"]}
package/package.json CHANGED
@@ -1,9 +1,6 @@
1
1
  {
2
2
  "name": "@atproto/lex-installer",
3
- "version": "0.1.2",
4
- "engines": {
5
- "node": ">=22"
6
- },
3
+ "version": "0.1.4",
7
4
  "license": "MIT",
8
5
  "description": "Lexicon document packet manager for AT Lexicons",
9
6
  "keywords": [
@@ -19,10 +16,6 @@
19
16
  "directory": "packages/lex/lex-installer"
20
17
  },
21
18
  "files": [
22
- "./src",
23
- "./tsconfig.build.json",
24
- "./tsconfig.tests.json",
25
- "./tsconfig.json",
26
19
  "./dist",
27
20
  "./CHANGELOG.md"
28
21
  ],
@@ -34,15 +27,18 @@
34
27
  "default": "./dist/index.js"
35
28
  }
36
29
  },
30
+ "engines": {
31
+ "node": ">=22"
32
+ },
37
33
  "dependencies": {
38
34
  "tslib": "^2.8.1",
39
- "@atproto/lex-builder": "^0.1.4",
40
- "@atproto/lex-cbor": "^0.1.2",
41
- "@atproto/lex-document": "^0.1.2",
42
- "@atproto/lex-schema": "^0.1.5",
43
- "@atproto/syntax": "^0.6.3",
44
- "@atproto/lex-data": "^0.1.3",
45
- "@atproto/lex-resolver": "^0.1.2"
35
+ "@atproto/lex-builder": "^0.1.5",
36
+ "@atproto/lex-cbor": "^0.1.3",
37
+ "@atproto/lex-data": "^0.1.4",
38
+ "@atproto/lex-document": "^0.1.3",
39
+ "@atproto/lex-schema": "^0.1.6",
40
+ "@atproto/lex-resolver": "^0.1.4",
41
+ "@atproto/syntax": "^0.6.4"
46
42
  },
47
43
  "devDependencies": {
48
44
  "vitest": "^4.0.16"