@fulmenhq/tsfulmen 0.3.3 → 0.4.1

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (123) hide show
  1. package/CHANGELOG.md +76 -1
  2. package/README.md +30 -1
  3. package/config/crucible-ts/taxonomy/metrics.yaml +1 -1
  4. package/dist/appidentity/index.js +9 -2209
  5. package/dist/appidentity/index.js.map +1 -1
  6. package/dist/assets/index.d.ts +184 -0
  7. package/dist/assets/index.js +4 -0
  8. package/dist/assets/index.js.map +1 -0
  9. package/dist/bin/prometheus-cli.js +15 -9139
  10. package/dist/bin/prometheus-cli.js.map +1 -1
  11. package/dist/bin/schema-cli.js +4 -6098
  12. package/dist/bin/schema-cli.js.map +1 -1
  13. package/dist/bin/signals-cli.js +15 -1910
  14. package/dist/bin/signals-cli.js.map +1 -1
  15. package/dist/chunk-24BAF63H.js +194 -0
  16. package/dist/chunk-24BAF63H.js.map +1 -0
  17. package/dist/chunk-3HISR2XI.js +36 -0
  18. package/dist/chunk-3HISR2XI.js.map +1 -0
  19. package/dist/chunk-56F2EEAG.js +328 -0
  20. package/dist/chunk-56F2EEAG.js.map +1 -0
  21. package/dist/chunk-5HZEJGZ5.js +725 -0
  22. package/dist/chunk-5HZEJGZ5.js.map +1 -0
  23. package/dist/chunk-7YWACZEJ.js +837 -0
  24. package/dist/chunk-7YWACZEJ.js.map +1 -0
  25. package/dist/chunk-BCO3FUUO.js +682 -0
  26. package/dist/chunk-BCO3FUUO.js.map +1 -0
  27. package/dist/chunk-GOTEQYAD.js +410 -0
  28. package/dist/chunk-GOTEQYAD.js.map +1 -0
  29. package/dist/chunk-HY6JQOFN.js +32 -0
  30. package/dist/chunk-HY6JQOFN.js.map +1 -0
  31. package/dist/chunk-LMNAUTW7.js +43 -0
  32. package/dist/chunk-LMNAUTW7.js.map +1 -0
  33. package/dist/chunk-LWAH2UG7.js +103 -0
  34. package/dist/chunk-LWAH2UG7.js.map +1 -0
  35. package/dist/chunk-OHE2AOH4.js +273 -0
  36. package/dist/chunk-OHE2AOH4.js.map +1 -0
  37. package/dist/chunk-P3DNOZOG.js +1488 -0
  38. package/dist/chunk-P3DNOZOG.js.map +1 -0
  39. package/dist/chunk-PQ6TKPUN.js +27 -0
  40. package/dist/chunk-PQ6TKPUN.js.map +1 -0
  41. package/dist/chunk-QCCN6POA.js +211 -0
  42. package/dist/chunk-QCCN6POA.js.map +1 -0
  43. package/dist/chunk-QGTNV4U2.js +985 -0
  44. package/dist/chunk-QGTNV4U2.js.map +1 -0
  45. package/dist/chunk-RSLFR4TO.js +631 -0
  46. package/dist/chunk-RSLFR4TO.js.map +1 -0
  47. package/dist/chunk-SNV5WG5V.js +9412 -0
  48. package/dist/chunk-SNV5WG5V.js.map +1 -0
  49. package/dist/chunk-UP2VWCW5.js +33 -0
  50. package/dist/chunk-UP2VWCW5.js.map +1 -0
  51. package/dist/chunk-VJIGX7MH.js +208 -0
  52. package/dist/chunk-VJIGX7MH.js.map +1 -0
  53. package/dist/chunk-WCCMRVZF.js +130 -0
  54. package/dist/chunk-WCCMRVZF.js.map +1 -0
  55. package/dist/chunk-WSMVLWLB.js +269 -0
  56. package/dist/chunk-WSMVLWLB.js.map +1 -0
  57. package/dist/config/index.js +6 -1220
  58. package/dist/config/index.js.map +1 -1
  59. package/dist/crucible/fulpack/index.js +2 -25
  60. package/dist/crucible/fulpack/index.js.map +1 -1
  61. package/dist/crucible/index.js +13 -1129
  62. package/dist/crucible/index.js.map +1 -1
  63. package/dist/docscribe/index.js +2 -680
  64. package/dist/docscribe/index.js.map +1 -1
  65. package/dist/errors/index.js +5 -1831
  66. package/dist/errors/index.js.map +1 -1
  67. package/dist/errors-D7KXV3QW.js +4 -0
  68. package/dist/errors-D7KXV3QW.js.map +1 -0
  69. package/dist/errors-R7ZODJXS.js +8 -0
  70. package/dist/errors-R7ZODJXS.js.map +1 -0
  71. package/dist/export-EA3RNQNS.js +6 -0
  72. package/dist/export-EA3RNQNS.js.map +1 -0
  73. package/dist/foundry/index.js +340 -3949
  74. package/dist/foundry/index.js.map +1 -1
  75. package/dist/foundry/similarity/index.js +3 -134
  76. package/dist/foundry/similarity/index.js.map +1 -1
  77. package/dist/fulencode/index.js +3 -319
  78. package/dist/fulencode/index.js.map +1 -1
  79. package/dist/fulhash/index.js +3 -611
  80. package/dist/fulhash/index.js.map +1 -1
  81. package/dist/fulpack/index.js +3 -1515
  82. package/dist/fulpack/index.js.map +1 -1
  83. package/dist/hash-YOJYVOWH.js +4 -0
  84. package/dist/hash-YOJYVOWH.js.map +1 -0
  85. package/dist/index.d.ts +1 -1
  86. package/dist/index.js +14 -4395
  87. package/dist/index.js.map +1 -1
  88. package/dist/loader-VP2ZIC4O.js +9 -0
  89. package/dist/loader-VP2ZIC4O.js.map +1 -0
  90. package/dist/logging/index.js +2 -723
  91. package/dist/logging/index.js.map +1 -1
  92. package/dist/pathfinder/index.js +18 -2341
  93. package/dist/pathfinder/index.js.map +1 -1
  94. package/dist/prom-client-PNEBGD3G.js +4801 -0
  95. package/dist/prom-client-PNEBGD3G.js.map +1 -0
  96. package/dist/reports/license-inventory.csv +1 -1
  97. package/dist/schema/index.d.ts +19 -6
  98. package/dist/schema/index.js +4 -6148
  99. package/dist/schema/index.js.map +1 -1
  100. package/dist/signals/index.js +8 -2767
  101. package/dist/signals/index.js.map +1 -1
  102. package/dist/similarity/index.js +3 -134
  103. package/dist/similarity/index.js.map +1 -1
  104. package/dist/telemetry/http/index.js +9 -930
  105. package/dist/telemetry/http/index.js.map +1 -1
  106. package/dist/telemetry/index.js +4 -1561
  107. package/dist/telemetry/index.js.map +1 -1
  108. package/dist/telemetry/prometheus/index.js +7 -8422
  109. package/dist/telemetry/prometheus/index.js.map +1 -1
  110. package/dist/validator-I3ASDVDB.js +6 -0
  111. package/dist/validator-I3ASDVDB.js.map +1 -0
  112. package/package.json +5 -1
  113. package/schemas/crucible-ts/library/module-manifest/v1.0.0/module-manifest.schema.json +1 -1
  114. package/schemas/crucible-ts/observability/logging/v1.0.0/definitions.schema.json +1 -1
  115. package/schemas/crucible-ts/observability/logging/v1.0.0/log-event.schema.json +13 -13
  116. package/schemas/crucible-ts/observability/logging/v1.0.0/logger-config.schema.json +2 -2
  117. package/schemas/crucible-ts/observability/logging/v1.0.0/logging-policy.schema.json +1 -1
  118. package/schemas/crucible-ts/observability/logging/v1.0.0/middleware-config.schema.json +2 -2
  119. package/schemas/crucible-ts/observability/logging/v1.0.0/severity-filter.schema.json +3 -3
  120. package/schemas/crucible-ts/upstream/3leaps/crucible/PROVENANCE.md +3 -3
  121. package/schemas/crucible-ts/upstream/3leaps/crucible/docs/catalog/classifiers/README.md +1 -1
  122. package/schemas/crucible-ts/upstream/3leaps/crucible/docs/standards/classifiers-framework.md +1 -1
  123. package/schemas/crucible-ts/upstream/3leaps/crucible/docs/standards/data-sensitivity-classification.md +1 -1
@@ -0,0 +1,43 @@
1
+ import { loadIdentity } from './chunk-VJIGX7MH.js';
2
+
3
+ // src/appidentity/helpers.ts
4
+ async function getBinaryName(options) {
5
+ const identity = await loadIdentity(options);
6
+ return identity.app.binary_name;
7
+ }
8
+ async function getVendor(options) {
9
+ const identity = await loadIdentity(options);
10
+ return identity.app.vendor;
11
+ }
12
+ async function getEnvPrefix(options) {
13
+ const identity = await loadIdentity(options);
14
+ return identity.app.env_prefix;
15
+ }
16
+ async function getConfigName(options) {
17
+ const identity = await loadIdentity(options);
18
+ return identity.app.config_name;
19
+ }
20
+ async function getTelemetryNamespace(options) {
21
+ const identity = await loadIdentity(options);
22
+ return identity.metadata?.telemetry_namespace ?? identity.app.binary_name;
23
+ }
24
+ async function getConfigIdentifiers(options) {
25
+ const identity = await loadIdentity(options);
26
+ return Object.freeze({
27
+ vendor: identity.app.vendor,
28
+ configName: identity.app.config_name
29
+ });
30
+ }
31
+ async function buildEnvVar(key, options) {
32
+ const envPrefix = await getEnvPrefix(options);
33
+ const normalizedKey = key.toUpperCase().replace(/[^A-Z0-9_]/g, "_");
34
+ return `${envPrefix}${normalizedKey}`;
35
+ }
36
+ async function getEnvVar(key, options) {
37
+ const envVarName = await buildEnvVar(key, options);
38
+ return process.env[envVarName];
39
+ }
40
+
41
+ export { buildEnvVar, getBinaryName, getConfigIdentifiers, getConfigName, getEnvPrefix, getEnvVar, getTelemetryNamespace, getVendor };
42
+ //# sourceMappingURL=chunk-LMNAUTW7.js.map
43
+ //# sourceMappingURL=chunk-LMNAUTW7.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"sources":["../src/appidentity/helpers.ts"],"names":[],"mappings":";;;AAwBA,eAAsB,cAAc,OAAA,EAAgD;AAClF,EAAA,MAAM,QAAA,GAAW,MAAM,YAAA,CAAa,OAAO,CAAA;AAC3C,EAAA,OAAO,SAAS,GAAA,CAAI,WAAA;AACtB;AAQA,eAAsB,UAAU,OAAA,EAAgD;AAC9E,EAAA,MAAM,QAAA,GAAW,MAAM,YAAA,CAAa,OAAO,CAAA;AAC3C,EAAA,OAAO,SAAS,GAAA,CAAI,MAAA;AACtB;AAQA,eAAsB,aAAa,OAAA,EAAgD;AACjF,EAAA,MAAM,QAAA,GAAW,MAAM,YAAA,CAAa,OAAO,CAAA;AAC3C,EAAA,OAAO,SAAS,GAAA,CAAI,UAAA;AACtB;AAQA,eAAsB,cAAc,OAAA,EAAgD;AAClF,EAAA,MAAM,QAAA,GAAW,MAAM,YAAA,CAAa,OAAO,CAAA;AAC3C,EAAA,OAAO,SAAS,GAAA,CAAI,WAAA;AACtB;AAUA,eAAsB,sBAAsB,OAAA,EAAgD;AAC1F,EAAA,MAAM,QAAA,GAAW,MAAM,YAAA,CAAa,OAAO,CAAA;AAC3C,EAAA,OAAO,QAAA,CAAS,QAAA,EAAU,mBAAA,IAAuB,QAAA,CAAS,GAAA,CAAI,WAAA;AAChE;AAWA,eAAsB,qBACpB,OAAA,EAC4B;AAC5B,EAAA,MAAM,QAAA,GAAW,MAAM,YAAA,CAAa,OAAO,CAAA;AAC3C,EAAA,OAAO,OAAO,MAAA,CAAO;AAAA,IACnB,MAAA,EAAQ,SAAS,GAAA,CAAI,MAAA;AAAA,IACrB,UAAA,EAAY,SAAS,GAAA,CAAI;AAAA,GAC1B,CAAA;AACH;AAkBA,eAAsB,WAAA,CAAY,KAAa,OAAA,EAAgD;AAC7F,EAAA,MAAM,SAAA,GAAY,MAAM,YAAA,CAAa,OAAO,CAAA;AAE5C,EAAA,MAAM,gBAAgB,GAAA,CAAI,WAAA,EAAY,CAAE,OAAA,CAAQ,eAAe,GAAG,CAAA;AAClE,EAAA,OAAO,CAAA,EAAG,SAAS,CAAA,EAAG,aAAa,CAAA,CAAA;AACrC;AAWA,eAAsB,SAAA,CACpB,KACA,OAAA,EAC6B;AAC7B,EAAA,MAAM,UAAA,GAAa,MAAM,WAAA,CAAY,GAAA,EAAK,OAAO,CAAA;AACjD,EAAA,OAAO,OAAA,CAAQ,IAAI,UAAU,CAAA;AAC/B","file":"chunk-LMNAUTW7.js","sourcesContent":["/**\n * Application Identity Helpers\n *\n * Convenience functions for accessing identity fields\n * All helpers use loadIdentity() under the hood for caching benefits\n */\n\nimport { loadIdentity } from \"./loader.js\";\nimport type { LoadIdentityOptions } from \"./types.js\";\n\n/**\n * Config identifiers for path construction\n */\nexport interface ConfigIdentifiers {\n readonly vendor: string;\n readonly configName: string;\n}\n\n/**\n * Get the binary name from app identity\n *\n * @param options - Load options (optional)\n * @returns Binary name (e.g., 'myapp')\n */\nexport async function getBinaryName(options?: LoadIdentityOptions): Promise<string> {\n const identity = await loadIdentity(options);\n return identity.app.binary_name;\n}\n\n/**\n * Get the vendor namespace from app identity\n *\n * @param options - Load options (optional)\n * @returns Vendor namespace (e.g., 'acmecorp')\n */\nexport async function getVendor(options?: LoadIdentityOptions): Promise<string> {\n const identity = await loadIdentity(options);\n return identity.app.vendor;\n}\n\n/**\n * Get the environment variable prefix from app identity\n *\n * @param options - Load options (optional)\n * @returns Env prefix (e.g., 'MYAPP_')\n */\nexport async function getEnvPrefix(options?: LoadIdentityOptions): Promise<string> {\n const identity = await loadIdentity(options);\n return identity.app.env_prefix;\n}\n\n/**\n * Get the config directory name from app identity\n *\n * @param options - Load options (optional)\n * @returns Config name (e.g., 'myapp')\n */\nexport async function getConfigName(options?: LoadIdentityOptions): Promise<string> {\n const identity = await loadIdentity(options);\n return identity.app.config_name;\n}\n\n/**\n * Get the telemetry namespace from app identity\n *\n * Falls back to binary_name if telemetry_namespace is not specified\n *\n * @param options - Load options (optional)\n * @returns Telemetry namespace (e.g., 'acmecorp_myapp' or 'myapp')\n */\nexport async function getTelemetryNamespace(options?: LoadIdentityOptions): Promise<string> {\n const identity = await loadIdentity(options);\n return identity.metadata?.telemetry_namespace ?? identity.app.binary_name;\n}\n\n/**\n * Get config identifiers for path construction\n *\n * Returns vendor and configName for building config paths like:\n * ~/.config/{vendor}/{configName}/config.yaml\n *\n * @param options - Load options (optional)\n * @returns Frozen config identifiers { vendor, configName }\n */\nexport async function getConfigIdentifiers(\n options?: LoadIdentityOptions,\n): Promise<ConfigIdentifiers> {\n const identity = await loadIdentity(options);\n return Object.freeze({\n vendor: identity.app.vendor,\n configName: identity.app.config_name,\n });\n}\n\n/**\n * Build environment variable name with app prefix\n *\n * Constructs env var names like: MYAPP_DATABASE_URL\n * Normalizes invalid characters (anything outside [A-Z0-9_]) to underscores\n * for conventional env var naming.\n *\n * Examples:\n * - 'database-url' → 'MYAPP_DATABASE_URL'\n * - 'my.config' → 'MYAPP_MY_CONFIG'\n * - 'log_level' → 'MYAPP_LOG_LEVEL'\n *\n * @param key - Environment variable key (will be uppercased and normalized)\n * @param options - Load options (optional)\n * @returns Full environment variable name (e.g., 'MYAPP_DATABASE_URL')\n */\nexport async function buildEnvVar(key: string, options?: LoadIdentityOptions): Promise<string> {\n const envPrefix = await getEnvPrefix(options);\n // Uppercase and replace any non-alphanumeric/underscore characters with underscores\n const normalizedKey = key.toUpperCase().replace(/[^A-Z0-9_]/g, \"_\");\n return `${envPrefix}${normalizedKey}`;\n}\n\n/**\n * Get environment variable value using app prefix\n *\n * Convenience wrapper around process.env using buildEnvVar\n *\n * @param key - Environment variable key (will be uppercased)\n * @param options - Load options (optional)\n * @returns Environment variable value or undefined\n */\nexport async function getEnvVar(\n key: string,\n options?: LoadIdentityOptions,\n): Promise<string | undefined> {\n const envVarName = await buildEnvVar(key, options);\n return process.env[envVarName];\n}\n"]}
@@ -0,0 +1,103 @@
1
+ import { FoundryCatalogError } from './chunk-3HISR2XI.js';
2
+ import { substringSimilarity, jaro_winkler, damerau_levenshtein, osa_distance, levenshtein, normalize as normalize$1, score as score$1, suggest as suggest$1 } from '@3leaps/string-metrics-wasm';
3
+
4
+ function distance(a, b, metric = "levenshtein") {
5
+ switch (metric) {
6
+ case "levenshtein":
7
+ return levenshtein(a, b);
8
+ case "damerau_osa":
9
+ return osa_distance(a, b);
10
+ case "damerau_unrestricted":
11
+ return damerau_levenshtein(a, b);
12
+ case "jaro_winkler":
13
+ return jaro_winkler(a, b);
14
+ case "substring":
15
+ return substringSimilarity(a, b).score;
16
+ default:
17
+ throw new Error(
18
+ `Invalid metric '${metric}': must be one of: levenshtein, damerau_osa, damerau_unrestricted, jaro_winkler, substring`
19
+ );
20
+ }
21
+ }
22
+
23
+ // src/foundry/similarity/errors.ts
24
+ var SimilarityError = class extends FoundryCatalogError {
25
+ constructor(message, cause) {
26
+ super(message, "similarity", cause);
27
+ this.name = "SimilarityError";
28
+ }
29
+ };
30
+ function toNormalizationLocale(locale) {
31
+ if (!locale) {
32
+ return void 0;
33
+ }
34
+ if (locale === "tr" || locale === "az" || locale === "lt") {
35
+ return locale;
36
+ }
37
+ return void 0;
38
+ }
39
+ function normalize(value, preset = "default", locale) {
40
+ if (typeof preset === "object") {
41
+ const targetPreset = preset.stripAccents ? "aggressive" : "default";
42
+ const targetLocale = toNormalizationLocale(preset.locale ?? locale);
43
+ return normalize$1(value, targetPreset, targetLocale);
44
+ }
45
+ return normalize$1(value, preset, toNormalizationLocale(locale));
46
+ }
47
+ function casefold(value, locale) {
48
+ if (locale === "tr") {
49
+ return value.toLocaleLowerCase("tr-TR");
50
+ }
51
+ return value.toLowerCase();
52
+ }
53
+ function stripAccents(value) {
54
+ return value.normalize("NFD").replace(/[\u0300-\u036f]/g, "");
55
+ }
56
+ function equalsIgnoreCase(a, b, options) {
57
+ return normalize(a, options) === normalize(b, options);
58
+ }
59
+ function score(a, b, metric = "levenshtein") {
60
+ if (metric === "substring") {
61
+ return substringSimilarity(a, b).score;
62
+ }
63
+ return score$1(a, b, metric);
64
+ }
65
+ var DEFAULT_MIN_SCORE = 0.6;
66
+ var DEFAULT_MAX_SUGGESTIONS = 3;
67
+ var DEFAULT_METRIC = "levenshtein";
68
+ var DEFAULT_NORMALIZE_PRESET = "default";
69
+ function suggest(input, candidates, options) {
70
+ const metric = options?.metric ?? DEFAULT_METRIC;
71
+ const minScore = options?.minScore ?? DEFAULT_MIN_SCORE;
72
+ const maxSuggestions = options?.maxSuggestions ?? DEFAULT_MAX_SUGGESTIONS;
73
+ let normalizePreset = options?.normalizePreset ?? DEFAULT_NORMALIZE_PRESET;
74
+ if (options?.normalize === false) {
75
+ normalizePreset = "none";
76
+ } else if (options?.normalize === true && !options?.normalizePreset) {
77
+ normalizePreset = "default";
78
+ }
79
+ const wasmOptions = {
80
+ metric,
81
+ normalizePreset,
82
+ minScore,
83
+ maxSuggestions,
84
+ preferPrefix: options?.preferPrefix,
85
+ jaroPrefixScale: options?.jaroPrefixScale,
86
+ jaroMaxPrefix: options?.jaroMaxPrefix
87
+ };
88
+ const results = suggest$1(input, candidates, wasmOptions);
89
+ return results.map((r) => ({
90
+ value: r.value,
91
+ score: r.score,
92
+ matchedRange: r.matchedRange,
93
+ reason: r.reason,
94
+ normalizedValue: r.normalizedValue
95
+ }));
96
+ }
97
+
98
+ // src/foundry/similarity/index.ts
99
+ var VERSION = "2.0.0";
100
+
101
+ export { SimilarityError, VERSION, casefold, distance, equalsIgnoreCase, normalize, score, stripAccents, suggest };
102
+ //# sourceMappingURL=chunk-LWAH2UG7.js.map
103
+ //# sourceMappingURL=chunk-LWAH2UG7.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"sources":["../src/foundry/similarity/distance.ts","../src/foundry/similarity/errors.ts","../src/foundry/similarity/normalization.ts","../src/foundry/similarity/score.ts","../src/foundry/similarity/suggest.ts","../src/foundry/similarity/index.ts"],"names":["wasmNormalize","substringSimilarity","wasmScore","wasmSuggest"],"mappings":"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","file":"chunk-LWAH2UG7.js","sourcesContent":["/**\n * Distance calculation with multiple metric support.\n *\n * Implements Crucible Foundry Similarity Standard v2.0.0 with WASM-backed metrics.\n *\n * @module foundry/similarity/distance\n */\n\nimport {\n damerau_levenshtein,\n jaro_winkler,\n levenshtein,\n osa_distance,\n substringSimilarity,\n} from \"@3leaps/string-metrics-wasm\";\nimport type { MetricType } from \"./types.js\";\n\n/**\n * Calculate edit distance between two strings using specified metric.\n *\n * @param a - First string\n * @param b - Second string\n * @param metric - Distance metric (default: \"levenshtein\")\n * @returns Edit distance as non-negative integer (or similarity score for jaro_winkler/substring)\n *\n * @example\n * distance(\"kitten\", \"sitting\") // 3\n * distance(\"abcd\", \"abdc\", \"damerau_osa\") // 1\n * distance(\"CA\", \"ABC\", \"damerau_unrestricted\") // 2\n * distance(\"hello world\", \"world\", \"substring\") // 0.625 (as score, not distance)\n */\nexport function distance(a: string, b: string, metric: MetricType = \"levenshtein\"): number {\n switch (metric) {\n case \"levenshtein\":\n return levenshtein(a, b);\n case \"damerau_osa\":\n return osa_distance(a, b);\n case \"damerau_unrestricted\":\n return damerau_levenshtein(a, b);\n case \"jaro_winkler\":\n return jaro_winkler(a, b);\n case \"substring\":\n // Returns similarity score (not distance) with longest common substring\n return substringSimilarity(a, b).score;\n default:\n throw new Error(\n `Invalid metric '${metric}': must be one of: levenshtein, damerau_osa, damerau_unrestricted, jaro_winkler, substring`,\n );\n }\n}\n","import { FoundryCatalogError } from \"../errors.js\";\n\nexport class SimilarityError extends FoundryCatalogError {\n constructor(message: string, cause?: Error) {\n super(message, \"similarity\", cause);\n this.name = \"SimilarityError\";\n }\n}\n","/**\n * Unicode-aware text normalization utilities.\n *\n * Implements Crucible Foundry Similarity Standard v2.0.0 with normalization presets.\n *\n * @module foundry/similarity/normalization\n */\n\nimport {\n type NormalizationLocale,\n type NormalizationPreset as WasmNormalizationPreset,\n normalize as wasmNormalize,\n} from \"@3leaps/string-metrics-wasm\";\nimport type { NormalizationPreset, NormalizeOptions } from \"./types.js\";\n\nfunction toNormalizationLocale(locale?: string): NormalizationLocale | undefined {\n if (!locale) {\n return undefined;\n }\n\n if (locale === \"tr\" || locale === \"az\" || locale === \"lt\") {\n return locale;\n }\n\n return undefined;\n}\n\n/**\n * Apply normalization preset to text.\n *\n * @param value - Text to normalize\n * @param preset - Normalization preset (\"none\" | \"minimal\" | \"default\" | \"aggressive\")\n * @param locale - Optional locale for locale-aware casefolding (e.g., \"tr\" for Turkish)\n * @returns Normalized text\n *\n * @example\n * normalize(\" Café-Zürich! \", \"aggressive\") // \"cafezurich\"\n * normalize(\" Hello \", \"minimal\") // \"Hello\"\n * normalize(\"İstanbul\", \"default\", \"tr\") // \"istanbul\"\n */\nexport function normalize(\n value: string,\n preset: NormalizationPreset | NormalizeOptions = \"default\",\n locale?: string,\n): string {\n // Handle legacy NormalizeOptions interface for backward compatibility\n if (typeof preset === \"object\") {\n // Map old options to preset and extract locale\n const targetPreset = preset.stripAccents ? \"aggressive\" : \"default\";\n const targetLocale = toNormalizationLocale(preset.locale ?? locale);\n return wasmNormalize(value, targetPreset, targetLocale);\n }\n\n return wasmNormalize(value, preset as WasmNormalizationPreset, toNormalizationLocale(locale));\n}\n\n/**\n * Unicode-aware case folding.\n *\n * @param value - Text to casefold\n * @param locale - Optional locale (e.g., \"tr\" for Turkish)\n * @returns Lowercase text\n */\nexport function casefold(value: string, locale?: string): string {\n if (locale === \"tr\") {\n return value.toLocaleLowerCase(\"tr-TR\");\n }\n return value.toLowerCase();\n}\n\n/**\n * Strip diacritical marks from text.\n *\n * @param value - Text to process\n * @returns Text with accents removed\n */\nexport function stripAccents(value: string): string {\n return value.normalize(\"NFD\").replace(/[\\u0300-\\u036f]/g, \"\");\n}\n\n/**\n * Compare strings ignoring case and optionally accents.\n *\n * @param a - First string\n * @param b - Second string\n * @param options - Normalization options\n * @returns True if strings are equal after normalization\n */\nexport function equalsIgnoreCase(a: string, b: string, options?: NormalizeOptions): boolean {\n return normalize(a, options) === normalize(b, options);\n}\n","/**\n * Normalized similarity score with metric selection.\n *\n * Implements Crucible Foundry Similarity Standard v2.0.0.\n *\n * @module foundry/similarity/score\n */\n\nimport {\n type SimilarityMetric,\n substringSimilarity,\n score as wasmScore,\n} from \"@3leaps/string-metrics-wasm\";\nimport type { MetricType } from \"./types.js\";\n\n/**\n * Calculate normalized similarity score between two strings.\n *\n * Returns a value between 0.0 (completely different) and 1.0 (identical).\n * For distance-based metrics: 1 - distance / max(len(a), len(b))\n * For jaro_winkler and substring: direct similarity score\n *\n * @param a - First string\n * @param b - Second string\n * @param metric - Similarity metric (default: \"levenshtein\")\n * @returns Similarity score in range [0.0, 1.0]\n *\n * @example\n * score(\"kitten\", \"sitting\") // 0.5714...\n * score(\"hello\", \"hallo\", \"jaro_winkler\") // 0.88\n * score(\"hello world\", \"world\", \"substring\") // 0.625\n */\nexport function score(a: string, b: string, metric: MetricType = \"levenshtein\"): number {\n // Special case: substring uses different API to get proper longest common substring\n if (metric === \"substring\") {\n return substringSimilarity(a, b).score;\n }\n\n // All other metrics supported directly by WASM score function\n return wasmScore(a, b, metric as SimilarityMetric);\n}\n","/**\n * Suggestion API with fuzzy matching and configurable metrics.\n *\n * Implements Crucible Foundry Similarity Standard v2.0.0.\n *\n * @module foundry/similarity/suggest\n */\n\nimport { type SuggestMetric, suggest as wasmSuggest } from \"@3leaps/string-metrics-wasm\";\nimport type { Suggestion, SuggestOptions } from \"./types.js\";\n\nconst DEFAULT_MIN_SCORE = 0.6;\nconst DEFAULT_MAX_SUGGESTIONS = 3;\nconst DEFAULT_METRIC = \"levenshtein\";\nconst DEFAULT_NORMALIZE_PRESET = \"default\";\n\n/**\n * Generate ranked suggestions from candidate list based on similarity.\n *\n * @param input - Input string to match against\n * @param candidates - List of candidate strings\n * @param options - Suggestion options (metric, thresholds, normalization)\n * @returns Array of suggestions sorted by score (descending)\n *\n * @example\n * suggest(\"docscrib\", [\"docscribe\", \"crucible\"], { metric: \"levenshtein\" })\n * // [{ value: \"docscribe\", score: 0.889, ... }]\n */\nexport function suggest(\n input: string,\n candidates: readonly string[],\n options?: SuggestOptions,\n): Suggestion[] {\n const metric = options?.metric ?? DEFAULT_METRIC;\n const minScore = options?.minScore ?? DEFAULT_MIN_SCORE;\n const maxSuggestions = options?.maxSuggestions ?? DEFAULT_MAX_SUGGESTIONS;\n\n // Handle legacy 'normalize' boolean option\n let normalizePreset = options?.normalizePreset ?? DEFAULT_NORMALIZE_PRESET;\n if (options?.normalize === false) {\n normalizePreset = \"none\";\n } else if (options?.normalize === true && !options?.normalizePreset) {\n normalizePreset = \"default\";\n }\n\n // Pass metric name directly to WASM library (it handles \"substring\" correctly)\n const wasmOptions = {\n metric: metric as SuggestMetric,\n normalizePreset,\n minScore,\n maxSuggestions,\n preferPrefix: options?.preferPrefix,\n jaroPrefixScale: options?.jaroPrefixScale,\n jaroMaxPrefix: options?.jaroMaxPrefix,\n };\n\n const results = wasmSuggest(input, candidates as string[], wasmOptions);\n\n // Map WASM results to our Suggestion interface\n return results.map((r) => ({\n value: r.value,\n score: r.score,\n matchedRange: r.matchedRange as [number, number] | undefined,\n reason: r.reason,\n normalizedValue: r.normalizedValue,\n }));\n}\n","/**\n * Foundry similarity module - Text similarity and normalization utilities\n *\n * Implements the Crucible Foundry Text Similarity & Normalization Standard v2.0.0 (2025.10.3).\n *\n * @module foundry/similarity\n */\n\nexport const VERSION = \"2.0.0\";\n\nexport { distance } from \"./distance.js\";\nexport { SimilarityError } from \"./errors.js\";\nexport {\n casefold,\n equalsIgnoreCase,\n normalize,\n stripAccents,\n} from \"./normalization.js\";\nexport { score } from \"./score.js\";\nexport { suggest } from \"./suggest.js\";\n\nexport type {\n MetricType,\n NormalizationPreset,\n NormalizeOptions,\n Suggestion,\n SuggestOptions,\n} from \"./types.js\";\n"]}
@@ -0,0 +1,273 @@
1
+ import { createCRC32, crc32, xxhash128 } from 'hash-wasm';
2
+ import { createHash } from 'crypto';
3
+
4
+ // src/crucible/fulhash/types.ts
5
+ var Algorithm = /* @__PURE__ */ ((Algorithm2) => {
6
+ Algorithm2["XXH3_128"] = "xxh3-128";
7
+ Algorithm2["SHA256"] = "sha256";
8
+ Algorithm2["CRC32"] = "crc32";
9
+ Algorithm2["CRC32C"] = "crc32c";
10
+ return Algorithm2;
11
+ })(Algorithm || {});
12
+ function hexToBytes(hex) {
13
+ const bytes = new Uint8Array(4);
14
+ for (let i = 0; i < 4; i++) {
15
+ bytes[i] = Number.parseInt(hex.substr(i * 2, 2), 16);
16
+ }
17
+ return bytes;
18
+ }
19
+ async function hashBytes(data) {
20
+ const hex = await crc32(data);
21
+ return hexToBytes(hex);
22
+ }
23
+ async function hashString(str, encoding = "utf8") {
24
+ if (encoding !== "utf8") {
25
+ const buf = Buffer.from(str, encoding);
26
+ const hex2 = await crc32(buf);
27
+ return hexToBytes(hex2);
28
+ }
29
+ const hex = await crc32(str);
30
+ return hexToBytes(hex);
31
+ }
32
+ async function createHasher() {
33
+ const hasher = await createCRC32();
34
+ return hasher;
35
+ }
36
+ var CRC32C_POLYNOMIAL = 2197175160;
37
+ function hexToBytes2(hex) {
38
+ const bytes = new Uint8Array(4);
39
+ for (let i = 0; i < 4; i++) {
40
+ bytes[i] = Number.parseInt(hex.substr(i * 2, 2), 16);
41
+ }
42
+ return bytes;
43
+ }
44
+ async function hashBytes2(data) {
45
+ const hex = await crc32(data, CRC32C_POLYNOMIAL);
46
+ return hexToBytes2(hex);
47
+ }
48
+ async function hashString2(str, encoding = "utf8") {
49
+ if (encoding !== "utf8") {
50
+ const buf = Buffer.from(str, encoding);
51
+ const hex2 = await crc32(buf, CRC32C_POLYNOMIAL);
52
+ return hexToBytes2(hex2);
53
+ }
54
+ const hex = await crc32(str, CRC32C_POLYNOMIAL);
55
+ return hexToBytes2(hex);
56
+ }
57
+ async function createHasher2() {
58
+ const hasher = await createCRC32(CRC32C_POLYNOMIAL);
59
+ return hasher;
60
+ }
61
+ function hashBytes3(data) {
62
+ const hash2 = createHash("sha256");
63
+ hash2.update(data);
64
+ return new Uint8Array(hash2.digest());
65
+ }
66
+ function hashString3(str, encoding = "utf8") {
67
+ const hash2 = createHash("sha256");
68
+ hash2.update(str, encoding);
69
+ return new Uint8Array(hash2.digest());
70
+ }
71
+
72
+ // src/fulhash/errors.ts
73
+ var FulHashError = class _FulHashError extends Error {
74
+ constructor(message) {
75
+ super(message);
76
+ this.name = "FulHashError";
77
+ Object.setPrototypeOf(this, _FulHashError.prototype);
78
+ }
79
+ };
80
+ var UnsupportedAlgorithmError = class _UnsupportedAlgorithmError extends FulHashError {
81
+ constructor(algorithm, supportedAlgorithms) {
82
+ super(
83
+ `Unsupported algorithm "${algorithm}". Supported algorithms: ${supportedAlgorithms.join(", ")}`
84
+ );
85
+ this.name = "UnsupportedAlgorithmError";
86
+ Object.setPrototypeOf(this, _UnsupportedAlgorithmError.prototype);
87
+ }
88
+ };
89
+ var InvalidChecksumError = class _InvalidChecksumError extends FulHashError {
90
+ constructor(checksum, reason) {
91
+ super(`Invalid checksum "${checksum}": ${reason}. Expected format: algorithm:hex`);
92
+ this.name = "InvalidChecksumError";
93
+ Object.setPrototypeOf(this, _InvalidChecksumError.prototype);
94
+ }
95
+ };
96
+ var InvalidChecksumFormatError = class _InvalidChecksumFormatError extends InvalidChecksumError {
97
+ constructor(checksum, reason) {
98
+ super(checksum, reason);
99
+ this.name = "InvalidChecksumFormatError";
100
+ Object.setPrototypeOf(this, _InvalidChecksumFormatError.prototype);
101
+ }
102
+ };
103
+ var DigestStateError = class _DigestStateError extends FulHashError {
104
+ constructor(operation) {
105
+ super(`Cannot ${operation}: digest already finalized. Call reset() to reuse hasher.`);
106
+ this.name = "DigestStateError";
107
+ Object.setPrototypeOf(this, _DigestStateError.prototype);
108
+ }
109
+ };
110
+
111
+ // src/fulhash/algorithms/xxh3.ts
112
+ function hexToBytes3(hex) {
113
+ const bytes = new Uint8Array(16);
114
+ for (let i = 0; i < 16; i++) {
115
+ bytes[i] = Number.parseInt(hex.substr(i * 2, 2), 16);
116
+ }
117
+ return bytes;
118
+ }
119
+ async function hashBytes4(data) {
120
+ const hex = await xxhash128(data);
121
+ return hexToBytes3(hex);
122
+ }
123
+ async function hashString4(str, encoding = "utf8") {
124
+ if (encoding !== "utf8") {
125
+ throw new FulHashError(
126
+ "XXH3-128 only supports UTF-8 encoding. Use utf8 encoding or convert data to Uint8Array."
127
+ );
128
+ }
129
+ const hex = await xxhash128(str);
130
+ return hexToBytes3(hex);
131
+ }
132
+
133
+ // src/fulhash/digest.ts
134
+ var Digest = class _Digest {
135
+ algorithm;
136
+ _bytes;
137
+ hex;
138
+ formatted;
139
+ constructor(algorithm, bytes) {
140
+ this.algorithm = algorithm;
141
+ this._bytes = new Uint8Array(bytes);
142
+ this.hex = Array.from(this._bytes).map((b) => b.toString(16).padStart(2, "0")).join("");
143
+ this.formatted = `${this.algorithm}:${this.hex}`;
144
+ Object.freeze(this);
145
+ }
146
+ get bytes() {
147
+ return Array.from(this._bytes);
148
+ }
149
+ toJSON() {
150
+ return {
151
+ algorithm: this.algorithm,
152
+ hex: this.hex,
153
+ formatted: this.formatted
154
+ };
155
+ }
156
+ toString() {
157
+ return this.formatted;
158
+ }
159
+ static parse(formatted) {
160
+ if (!formatted.includes(":")) {
161
+ throw new InvalidChecksumFormatError(formatted, "missing separator");
162
+ }
163
+ const [algorithmStr, hex] = formatted.split(":", 2);
164
+ if (!algorithmStr || !hex) {
165
+ throw new InvalidChecksumFormatError(formatted, "invalid format");
166
+ }
167
+ const algorithm = algorithmStr;
168
+ if (!Object.values(Algorithm).includes(algorithm)) {
169
+ throw new UnsupportedAlgorithmError(algorithm, Object.values(Algorithm));
170
+ }
171
+ if (!/^[0-9a-f]+$/.test(hex)) {
172
+ throw new InvalidChecksumError(
173
+ formatted,
174
+ "hex must contain only lowercase hexadecimal characters"
175
+ );
176
+ }
177
+ let expectedLength;
178
+ switch (algorithm) {
179
+ case "xxh3-128" /* XXH3_128 */:
180
+ expectedLength = 32;
181
+ break;
182
+ case "sha256" /* SHA256 */:
183
+ expectedLength = 64;
184
+ break;
185
+ case "crc32" /* CRC32 */:
186
+ case "crc32c" /* CRC32C */:
187
+ expectedLength = 8;
188
+ break;
189
+ default:
190
+ throw new UnsupportedAlgorithmError(algorithm, Object.values(Algorithm));
191
+ }
192
+ if (hex.length !== expectedLength) {
193
+ throw new InvalidChecksumError(
194
+ formatted,
195
+ `invalid hex length for ${algorithm}: expected ${expectedLength}, got ${hex.length}`
196
+ );
197
+ }
198
+ const bytes = new Uint8Array(hex.length / 2);
199
+ for (let i = 0; i < hex.length; i += 2) {
200
+ bytes[i / 2] = Number.parseInt(hex.slice(i, i + 2), 16);
201
+ }
202
+ return new _Digest(algorithm, bytes);
203
+ }
204
+ equals(other) {
205
+ if (this.algorithm !== other.algorithm) {
206
+ return false;
207
+ }
208
+ if (this.hex !== other.hex) {
209
+ return false;
210
+ }
211
+ return true;
212
+ }
213
+ static async verify(data, checksum) {
214
+ const expected = _Digest.parse(checksum);
215
+ const { hash: hash2 } = await import('./hash-YOJYVOWH.js');
216
+ const actual = await hash2(data, { algorithm: expected.algorithm });
217
+ return actual.equals(expected);
218
+ }
219
+ };
220
+
221
+ // src/fulhash/hash.ts
222
+ async function hash(input, options) {
223
+ const algorithm = options?.algorithm ?? "xxh3-128" /* XXH3_128 */;
224
+ const encoding = options?.encoding ?? "utf8";
225
+ let bytes;
226
+ switch (algorithm) {
227
+ case "sha256" /* SHA256 */:
228
+ if (typeof input === "string") {
229
+ bytes = hashString3(input, encoding);
230
+ } else {
231
+ bytes = hashBytes3(input);
232
+ }
233
+ break;
234
+ case "xxh3-128" /* XXH3_128 */:
235
+ if (typeof input === "string") {
236
+ if (encoding !== "utf8") {
237
+ bytes = await hashBytes4(Buffer.from(input, encoding));
238
+ } else {
239
+ bytes = await hashString4(input, "utf8");
240
+ }
241
+ } else {
242
+ bytes = await hashBytes4(input);
243
+ }
244
+ break;
245
+ case "crc32" /* CRC32 */:
246
+ if (typeof input === "string") {
247
+ bytes = await hashString(input, encoding);
248
+ } else {
249
+ bytes = await hashBytes(input);
250
+ }
251
+ break;
252
+ case "crc32c" /* CRC32C */:
253
+ if (typeof input === "string") {
254
+ bytes = await hashString2(input, encoding);
255
+ } else {
256
+ bytes = await hashBytes2(input);
257
+ }
258
+ break;
259
+ default:
260
+ throw new UnsupportedAlgorithmError(algorithm, Object.values(Algorithm));
261
+ }
262
+ return new Digest(algorithm, bytes);
263
+ }
264
+ async function hashString5(str, options) {
265
+ return hash(str, options);
266
+ }
267
+ async function hashBytes5(data, options) {
268
+ return hash(data, options);
269
+ }
270
+
271
+ export { Algorithm, Digest, DigestStateError, FulHashError, InvalidChecksumError, InvalidChecksumFormatError, UnsupportedAlgorithmError, createHasher, createHasher2, hash, hashBytes5 as hashBytes, hashString5 as hashString };
272
+ //# sourceMappingURL=chunk-OHE2AOH4.js.map
273
+ //# sourceMappingURL=chunk-OHE2AOH4.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"sources":["../src/crucible/fulhash/types.ts","../src/fulhash/algorithms/crc32.ts","../src/fulhash/algorithms/crc32c.ts","../src/fulhash/algorithms/sha256.ts","../src/fulhash/errors.ts","../src/fulhash/algorithms/xxh3.ts","../src/fulhash/digest.ts","../src/fulhash/hash.ts"],"names":["Algorithm","hex","hexToBytes","hashBytes","crc32","hashString","createHasher","createCRC32","hash"],"mappings":"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","file":"chunk-OHE2AOH4.js","sourcesContent":["/**\n * FulHash Types\n * Code generated by scripts/codegen/generate-fulhash-types.ts; DO NOT EDIT.\n */\n\n/**\n * Supported hashing algorithms for FulHash\n */\nexport enum Algorithm {\n /**\n * XXH3 (128-bit)\n * Fast non-cryptographic hash (default). Excellent collision resistance, extremely high throughput (50GB/s+).\n */\n XXH3_128 = \"xxh3-128\",\n\n /**\n * SHA-256\n * Cryptographic security standard. Resistant to intentional collisions. Use for security verification.\n */\n SHA256 = \"sha256\",\n\n /**\n * CRC-32 (IEEE)\n * 32-bit Cyclic Redundancy Check. Standard for GZIP/ZIP/PNG legacy format interoperability.\n */\n CRC32 = \"crc32\",\n\n /**\n * CRC-32C (Castagnoli)\n * 32-bit CRC (Castagnoli). HW accelerated (SSE4.2/ARMv8). Use for cloud storage (GCS, AWS) and networking.\n */\n CRC32C = \"crc32c\",\n}\n\n/**\n * Standard digest payload returned by FulHash helpers\n */\nexport interface Digest {\n /**\n * Hash algorithm identifier\n */\n algorithm: \"xxh3-128\" | \"crc32\" | \"crc32c\" | \"sha256\";\n\n /**\n * Lowercase hexadecimal representation of the digest\n */\n hex: string;\n\n /**\n * Canonical string representation '<algorithm>:<hex>'\n */\n formatted: string;\n\n /**\n * Raw digest bytes (optional)\n */\n bytes?: number[];\n}\n","import type { IHasher } from \"hash-wasm\";\nimport { crc32, createCRC32 } from \"hash-wasm\";\n\n// Local definition to avoid importing from hash-wasm/dist/lib/util which is not a public export\ntype IDataType =\n | string\n | Uint8Array\n | Uint16Array\n | Uint32Array\n | Int8Array\n | Int16Array\n | Int32Array\n | Float32Array\n | Float64Array\n | DataView\n | ArrayBuffer\n | SharedArrayBuffer;\n\n/**\n * Convert hex string to Uint8Array\n * @internal\n */\nfunction hexToBytes(hex: string): Uint8Array {\n const bytes = new Uint8Array(4);\n for (let i = 0; i < 4; i++) {\n bytes[i] = Number.parseInt(hex.substr(i * 2, 2), 16);\n }\n return bytes;\n}\n\nexport async function hashBytes(data: Uint8Array): Promise<Uint8Array> {\n const hex = await crc32(data);\n return hexToBytes(hex);\n}\n\nexport async function hashString(\n str: string,\n encoding: BufferEncoding = \"utf8\",\n): Promise<Uint8Array> {\n if (encoding !== \"utf8\") {\n // hash-wasm only supports string input as UTF-8\n // For other encodings, convert to Buffer first\n const buf = Buffer.from(str, encoding);\n const hex = await crc32(buf);\n return hexToBytes(hex);\n }\n const hex = await crc32(str);\n return hexToBytes(hex);\n}\n\n// Ensure the hasher we return respects the IHasher interface correctly\ninterface CRC32Hasher extends IHasher {\n update(data: IDataType): IHasher;\n}\n\nexport async function createHasher(): Promise<CRC32Hasher> {\n const hasher = await createCRC32();\n return hasher as unknown as CRC32Hasher;\n}\n","import type { IHasher } from \"hash-wasm\";\nimport { crc32, createCRC32 } from \"hash-wasm\";\n\n// Local definition to avoid importing from hash-wasm/dist/lib/util\ntype IDataType =\n | string\n | Uint8Array\n | Uint16Array\n | Uint32Array\n | Int8Array\n | Int16Array\n | Int32Array\n | Float32Array\n | Float64Array\n | DataView\n | ArrayBuffer\n | SharedArrayBuffer;\n\nconst CRC32C_POLYNOMIAL = 0x82f63b78;\n\n/**\n * Convert hex string to Uint8Array\n * @internal\n */\nfunction hexToBytes(hex: string): Uint8Array {\n const bytes = new Uint8Array(4);\n for (let i = 0; i < 4; i++) {\n bytes[i] = Number.parseInt(hex.substr(i * 2, 2), 16);\n }\n return bytes;\n}\n\nexport async function hashBytes(data: Uint8Array): Promise<Uint8Array> {\n const hex = await crc32(data, CRC32C_POLYNOMIAL);\n return hexToBytes(hex);\n}\n\nexport async function hashString(\n str: string,\n encoding: BufferEncoding = \"utf8\",\n): Promise<Uint8Array> {\n if (encoding !== \"utf8\") {\n const buf = Buffer.from(str, encoding);\n const hex = await crc32(buf, CRC32C_POLYNOMIAL);\n return hexToBytes(hex);\n }\n const hex = await crc32(str, CRC32C_POLYNOMIAL);\n return hexToBytes(hex);\n}\n\ninterface CRC32Hasher extends IHasher {\n update(data: IDataType): IHasher;\n}\n\nexport async function createHasher(): Promise<CRC32Hasher> {\n const hasher = await createCRC32(CRC32C_POLYNOMIAL);\n return hasher as unknown as CRC32Hasher;\n}\n","/**\n * SHA-256 algorithm adapter using Node.js crypto module\n */\n\nimport { createHash } from \"node:crypto\";\n\nexport function hashBytes(data: Uint8Array): Uint8Array {\n const hash = createHash(\"sha256\");\n hash.update(data);\n return new Uint8Array(hash.digest());\n}\n\nexport function hashString(str: string, encoding: BufferEncoding = \"utf8\"): Uint8Array {\n const hash = createHash(\"sha256\");\n hash.update(str, encoding);\n return new Uint8Array(hash.digest());\n}\n","/**\n * Error classes for FulHash module\n */\n\nexport class FulHashError extends Error {\n constructor(message: string) {\n super(message);\n this.name = \"FulHashError\";\n Object.setPrototypeOf(this, FulHashError.prototype);\n }\n}\n\nexport class UnsupportedAlgorithmError extends FulHashError {\n constructor(algorithm: string, supportedAlgorithms: string[]) {\n super(\n `Unsupported algorithm \"${algorithm}\". Supported algorithms: ${supportedAlgorithms.join(\", \")}`,\n );\n this.name = \"UnsupportedAlgorithmError\";\n Object.setPrototypeOf(this, UnsupportedAlgorithmError.prototype);\n }\n}\n\nexport class InvalidChecksumError extends FulHashError {\n constructor(checksum: string, reason: string) {\n super(`Invalid checksum \"${checksum}\": ${reason}. Expected format: algorithm:hex`);\n this.name = \"InvalidChecksumError\";\n Object.setPrototypeOf(this, InvalidChecksumError.prototype);\n }\n}\n\nexport class InvalidChecksumFormatError extends InvalidChecksumError {\n constructor(checksum: string, reason: string) {\n super(checksum, reason);\n this.name = \"InvalidChecksumFormatError\";\n Object.setPrototypeOf(this, InvalidChecksumFormatError.prototype);\n }\n}\n\nexport class DigestStateError extends FulHashError {\n constructor(operation: string) {\n super(`Cannot ${operation}: digest already finalized. Call reset() to reuse hasher.`);\n this.name = \"DigestStateError\";\n Object.setPrototypeOf(this, DigestStateError.prototype);\n }\n}\n","import { xxhash128 } from \"hash-wasm\";\nimport { FulHashError } from \"../errors.js\";\n\n/**\n * Convert hex string to Uint8Array\n * @internal\n */\nfunction hexToBytes(hex: string): Uint8Array {\n const bytes = new Uint8Array(16);\n for (let i = 0; i < 16; i++) {\n bytes[i] = Number.parseInt(hex.substr(i * 2, 2), 16);\n }\n return bytes;\n}\n\n/**\n * Hash bytes using XXH3-128 algorithm\n *\n * Uses the cached hash-wasm xxhash128() helper for optimal performance.\n * The WASM module is initialized once and reused across all calls.\n *\n * @param data - Input data as Uint8Array\n * @returns Hash digest as Uint8Array (16 bytes)\n */\nexport async function hashBytes(data: Uint8Array): Promise<Uint8Array> {\n // Use cached xxhash128 helper - returns hex string\n const hex = await xxhash128(data);\n return hexToBytes(hex);\n}\n\n/**\n * Hash string using XXH3-128 algorithm\n *\n * Uses the cached hash-wasm xxhash128() helper for optimal performance.\n * The WASM module is initialized once and reused across all calls.\n *\n * @param str - Input string\n * @param encoding - Character encoding (only 'utf8' supported)\n * @returns Hash digest as Uint8Array (16 bytes)\n */\nexport async function hashString(\n str: string,\n encoding: \"utf8\" | \"utf16le\" = \"utf8\",\n): Promise<Uint8Array> {\n if (encoding !== \"utf8\") {\n throw new FulHashError(\n \"XXH3-128 only supports UTF-8 encoding. Use utf8 encoding or convert data to Uint8Array.\",\n );\n }\n\n // Use cached xxhash128 helper directly on string\n const hex = await xxhash128(str);\n return hexToBytes(hex);\n}\n","/**\n * Digest implementation - immutable hash result container\n */\n\nimport { Algorithm, type Digest as DigestInterface } from \"../crucible/fulhash/types.js\";\nimport {\n InvalidChecksumError,\n InvalidChecksumFormatError,\n UnsupportedAlgorithmError,\n} from \"./errors.js\";\n\nexport class Digest implements DigestInterface {\n readonly algorithm: Algorithm;\n private readonly _bytes: Uint8Array;\n readonly hex: string;\n readonly formatted: string;\n\n constructor(algorithm: Algorithm, bytes: Uint8Array) {\n this.algorithm = algorithm;\n this._bytes = new Uint8Array(bytes);\n this.hex = Array.from(this._bytes)\n .map((b) => b.toString(16).padStart(2, \"0\"))\n .join(\"\");\n this.formatted = `${this.algorithm}:${this.hex}`;\n Object.freeze(this);\n }\n\n get bytes(): number[] {\n return Array.from(this._bytes);\n }\n\n toJSON(): object {\n return {\n algorithm: this.algorithm,\n hex: this.hex,\n formatted: this.formatted,\n };\n }\n\n toString(): string {\n return this.formatted;\n }\n\n static parse(formatted: string): Digest {\n if (!formatted.includes(\":\")) {\n throw new InvalidChecksumFormatError(formatted, \"missing separator\");\n }\n\n const [algorithmStr, hex] = formatted.split(\":\", 2);\n\n if (!algorithmStr || !hex) {\n throw new InvalidChecksumFormatError(formatted, \"invalid format\");\n }\n\n const algorithm = algorithmStr as Algorithm;\n if (!Object.values(Algorithm).includes(algorithm)) {\n throw new UnsupportedAlgorithmError(algorithm, Object.values(Algorithm));\n }\n\n if (!/^[0-9a-f]+$/.test(hex)) {\n throw new InvalidChecksumError(\n formatted,\n \"hex must contain only lowercase hexadecimal characters\",\n );\n }\n\n let expectedLength: number;\n switch (algorithm) {\n case Algorithm.XXH3_128:\n expectedLength = 32;\n break;\n case Algorithm.SHA256:\n expectedLength = 64;\n break;\n case Algorithm.CRC32:\n case Algorithm.CRC32C:\n expectedLength = 8;\n break;\n default:\n // Should have been caught by Object.values check, but TS safety\n throw new UnsupportedAlgorithmError(algorithm, Object.values(Algorithm));\n }\n\n if (hex.length !== expectedLength) {\n throw new InvalidChecksumError(\n formatted,\n `invalid hex length for ${algorithm}: expected ${expectedLength}, got ${hex.length}`,\n );\n }\n\n const bytes = new Uint8Array(hex.length / 2);\n for (let i = 0; i < hex.length; i += 2) {\n bytes[i / 2] = Number.parseInt(hex.slice(i, i + 2), 16);\n }\n\n return new Digest(algorithm, bytes);\n }\n\n equals(other: Digest): boolean {\n if (this.algorithm !== other.algorithm) {\n return false;\n }\n if (this.hex !== other.hex) {\n return false;\n }\n return true;\n }\n\n static async verify(data: string | Uint8Array, checksum: string): Promise<boolean> {\n const expected = Digest.parse(checksum);\n const { hash } = await import(\"./hash.js\");\n const actual = await hash(data, { algorithm: expected.algorithm });\n return actual.equals(expected);\n }\n}\n","/**\n * Block hashing helpers for one-shot hashing operations\n */\n\nimport { Algorithm } from \"../crucible/fulhash/types.js\";\nimport * as crc32 from \"./algorithms/crc32.js\";\nimport * as crc32c from \"./algorithms/crc32c.js\";\nimport * as sha256 from \"./algorithms/sha256.js\";\nimport * as xxh3 from \"./algorithms/xxh3.js\";\nimport type { HashOptions } from \"./definitions.js\";\nimport { Digest } from \"./digest.js\";\nimport { UnsupportedAlgorithmError } from \"./errors.js\";\n\nexport async function hash(input: string | Uint8Array, options?: HashOptions): Promise<Digest> {\n const algorithm = options?.algorithm ?? Algorithm.XXH3_128;\n const encoding = options?.encoding ?? \"utf8\";\n\n let bytes: Uint8Array;\n\n switch (algorithm) {\n case Algorithm.SHA256:\n if (typeof input === \"string\") {\n bytes = sha256.hashString(input, encoding);\n } else {\n bytes = sha256.hashBytes(input);\n }\n break;\n case Algorithm.XXH3_128:\n if (typeof input === \"string\") {\n if (encoding !== \"utf8\") {\n // Fallback via buffer if non-utf8 is requested, as xxh3-wasm is utf8 only\n bytes = await xxh3.hashBytes(Buffer.from(input, encoding));\n } else {\n bytes = await xxh3.hashString(input, \"utf8\");\n }\n } else {\n bytes = await xxh3.hashBytes(input);\n }\n break;\n case Algorithm.CRC32:\n if (typeof input === \"string\") {\n bytes = await crc32.hashString(input, encoding);\n } else {\n bytes = await crc32.hashBytes(input);\n }\n break;\n case Algorithm.CRC32C:\n if (typeof input === \"string\") {\n bytes = await crc32c.hashString(input, encoding);\n } else {\n bytes = await crc32c.hashBytes(input);\n }\n break;\n default:\n throw new UnsupportedAlgorithmError(algorithm, Object.values(Algorithm));\n }\n\n return new Digest(algorithm, bytes);\n}\n\nexport async function hashString(str: string, options?: HashOptions): Promise<Digest> {\n return hash(str, options);\n}\n\nexport async function hashBytes(data: Uint8Array, options?: HashOptions): Promise<Digest> {\n return hash(data, options);\n}\n"]}