cipher-kit 2.0.0 → 2.1.0

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 (40) hide show
  1. package/README.md +25 -27
  2. package/dist/{chunk-3UX5MZ2P.cjs → chunk-BHG5RSUV.cjs} +22 -20
  3. package/dist/chunk-BHG5RSUV.cjs.map +1 -0
  4. package/dist/{chunk-4MFF6V3R.js → chunk-CRTOKS3Q.js} +76 -41
  5. package/dist/chunk-CRTOKS3Q.js.map +1 -0
  6. package/dist/{chunk-N2EW2FDZ.cjs → chunk-HMTHK2IY.cjs} +183 -148
  7. package/dist/chunk-HMTHK2IY.cjs.map +1 -0
  8. package/dist/{chunk-ACFPMIXO.js → chunk-RAEBT46G.js} +75 -40
  9. package/dist/chunk-RAEBT46G.js.map +1 -0
  10. package/dist/{chunk-FKSYSPJR.js → chunk-RUTGDMVR.js} +21 -20
  11. package/dist/chunk-RUTGDMVR.js.map +1 -0
  12. package/dist/{chunk-CVCDAHDW.cjs → chunk-UVEMRK5F.cjs} +189 -154
  13. package/dist/chunk-UVEMRK5F.cjs.map +1 -0
  14. package/dist/{export-BMvZq46v.d.ts → export-5hmOiU0J.d.cts} +194 -20
  15. package/dist/{export-CQNsJFh_.d.cts → export-BF9wW56f.d.ts} +194 -20
  16. package/dist/{export-llM6c7Do.d.ts → export-DVERZibl.d.cts} +194 -20
  17. package/dist/{export-55tHE0Bw.d.cts → export-w8sBcKXw.d.ts} +194 -20
  18. package/dist/index.cjs +12 -12
  19. package/dist/index.cjs.map +1 -1
  20. package/dist/index.d.cts +3 -3
  21. package/dist/index.d.ts +3 -3
  22. package/dist/index.js +3 -3
  23. package/dist/index.js.map +1 -1
  24. package/dist/node.cjs +33 -33
  25. package/dist/node.d.cts +2 -2
  26. package/dist/node.d.ts +2 -2
  27. package/dist/node.js +2 -2
  28. package/dist/{validate-EHuJC5QQ.d.cts → validate-B3uHoP8n.d.cts} +26 -38
  29. package/dist/{validate-EHuJC5QQ.d.ts → validate-B3uHoP8n.d.ts} +26 -38
  30. package/dist/web-api.cjs +33 -33
  31. package/dist/web-api.d.cts +2 -2
  32. package/dist/web-api.d.ts +2 -2
  33. package/dist/web-api.js +2 -2
  34. package/package.json +6 -7
  35. package/dist/chunk-3UX5MZ2P.cjs.map +0 -1
  36. package/dist/chunk-4MFF6V3R.js.map +0 -1
  37. package/dist/chunk-ACFPMIXO.js.map +0 -1
  38. package/dist/chunk-CVCDAHDW.cjs.map +0 -1
  39. package/dist/chunk-FKSYSPJR.js.map +0 -1
  40. package/dist/chunk-N2EW2FDZ.cjs.map +0 -1
@@ -24,22 +24,22 @@ var ENCRYPTION_ALGORITHMS = Object.freeze({
24
24
  function $isStr(x, min = 1) {
25
25
  return x !== null && x !== void 0 && typeof x === "string" && x.trim().length >= min;
26
26
  }
27
- function $isObj(x) {
27
+ function $isPlainObj(x) {
28
28
  if (typeof x !== "object" || x === null || x === void 0) return false;
29
29
  const proto = Object.getPrototypeOf(x);
30
30
  return proto === Object.prototype || proto === null;
31
31
  }
32
- function $isLooseObj(x) {
32
+ function $isObj(x) {
33
33
  return typeof x === "object" && x !== null && x !== void 0;
34
34
  }
35
35
  var expectedKeys = /* @__PURE__ */ new Set(["platform", "digest", "algorithm", "key"]);
36
36
  function $isSecretKey(x, platform) {
37
- if (!$isLooseObj(x) || platform !== "node" && platform !== "web" || x.platform !== platform) return null;
37
+ if (!$isObj(x) || platform !== "node" && platform !== "web" || x.platform !== platform) return null;
38
38
  const keys = Object.keys(x);
39
39
  if (keys.length !== expectedKeys.size) return null;
40
40
  for (const key of keys) if (!expectedKeys.has(key)) return null;
41
41
  for (const key of expectedKeys) if (!Object.hasOwn(x, key)) return null;
42
- if (typeof x.digest !== "string" || !(x.digest in DIGEST_ALGORITHMS) || typeof x.algorithm !== "string" || !(x.algorithm in ENCRYPTION_ALGORITHMS) || !$isLooseObj(x.key) || x.key.type !== "secret") {
42
+ if (typeof x.digest !== "string" || !(x.digest in DIGEST_ALGORITHMS) || typeof x.algorithm !== "string" || !(x.algorithm in ENCRYPTION_ALGORITHMS) || !$isObj(x.key) || x.key.type !== "secret") {
43
43
  return null;
44
44
  }
45
45
  const algorithm = ENCRYPTION_ALGORITHMS[x.algorithm];
@@ -49,7 +49,7 @@ function $isSecretKey(x, platform) {
49
49
  }
50
50
  return Object.freeze({ ...x, injected: algorithm });
51
51
  }
52
- if (!$isLooseObj(x.key.algorithm) || x.key.algorithm.name !== algorithm.web || typeof x.key.algorithm.length === "number" && x.key.algorithm.length !== algorithm.keyBytes * 8 || typeof x.key.extractable !== "boolean" || !Array.isArray(x.key.usages) || x.key.usages.length !== 2 || !(x.key.usages.includes("encrypt") && x.key.usages.includes("decrypt"))) {
52
+ if (!$isObj(x.key.algorithm) || x.key.algorithm.name !== algorithm.web || typeof x.key.algorithm.length === "number" && x.key.algorithm.length !== algorithm.keyBytes * 8 || typeof x.key.extractable !== "boolean" || !Array.isArray(x.key.usages) || x.key.usages.length !== 2 || !(x.key.usages.includes("encrypt") && x.key.usages.includes("decrypt"))) {
53
53
  return null;
54
54
  }
55
55
  return Object.freeze({ ...x, injected: algorithm });
@@ -59,7 +59,7 @@ var ENCRYPTED_REGEX = Object.freeze({
59
59
  web: /^([^.]+)\.([^.]+)\.$/,
60
60
  general: /^([^.]+)\.([^.]+)(?:\.([^.]+))?\.$/
61
61
  });
62
- function matchPattern(data, format) {
62
+ function matchEncryptedPattern(data, format) {
63
63
  if (typeof data !== "string") return false;
64
64
  if (!(format in ENCRYPTED_REGEX)) throw new Error(`Unknown format: ${format}`);
65
65
  return ENCRYPTED_REGEX[format].test(data);
@@ -67,7 +67,7 @@ function matchPattern(data, format) {
67
67
 
68
68
  // src/helpers/error.ts
69
69
  function $ok(result) {
70
- if ($isObj(result)) return { success: true, ...result };
70
+ if ($isPlainObj(result)) return { success: true, ...result };
71
71
  return { success: true, result };
72
72
  }
73
73
  function $err(err) {
@@ -95,30 +95,31 @@ function title(platform, title2) {
95
95
  // src/helpers/object.ts
96
96
  function $stringifyObj(obj) {
97
97
  try {
98
- if (!$isObj(obj)) return $err({ msg: "Invalid object", desc: "Input is not a plain object" });
98
+ if (!$isPlainObj(obj)) return $err({ msg: "Invalid object", desc: "Input is not a plain object" });
99
99
  return $ok(JSON.stringify(obj));
100
100
  } catch (error) {
101
101
  return $err({ msg: "Utility: Stringify error", desc: $fmtError(error) });
102
102
  }
103
103
  }
104
- function tryStringifyObj(obj) {
105
- return $stringifyObj(obj);
106
- }
107
- function stringifyObj(obj) {
108
- const { result, error } = $stringifyObj(obj);
109
- if (error) throw new Error($fmtResultErr(error));
110
- return result;
111
- }
112
104
  function $parseToObj(str) {
113
105
  try {
114
106
  if (!$isStr(str)) return $err({ msg: "Utility: Invalid input", desc: "Input is not a valid string" });
115
107
  const obj = JSON.parse(str);
116
- if (!$isObj(obj)) return $err({ msg: "Utility: Invalid object format", desc: "Parsed data is not a plain object" });
108
+ if (!$isPlainObj(obj))
109
+ return $err({ msg: "Utility: Invalid object format", desc: "Parsed data is not a plain object" });
117
110
  return $ok({ result: obj });
118
111
  } catch (error) {
119
112
  return $err({ msg: "Utility: Invalid format", desc: $fmtError(error) });
120
113
  }
121
114
  }
115
+ function tryStringifyObj(obj) {
116
+ return $stringifyObj(obj);
117
+ }
118
+ function stringifyObj(obj) {
119
+ const { result, error } = $stringifyObj(obj);
120
+ if (error) throw new Error($fmtResultErr(error));
121
+ return result;
122
+ }
122
123
  function tryParseToObj(str) {
123
124
  return $parseToObj(str);
124
125
  }
@@ -128,6 +129,6 @@ function parseToObj(str) {
128
129
  return result;
129
130
  }
130
131
 
131
- export { $err, $fmtError, $fmtResultErr, $isSecretKey, $isStr, $ok, $parseToObj, $stringifyObj, CIPHER_ENCODING, DIGEST_ALGORITHMS, ENCODING, ENCRYPTED_REGEX, ENCRYPTION_ALGORITHMS, __export, matchPattern, parseToObj, stringifyObj, title, tryParseToObj, tryStringifyObj };
132
- //# sourceMappingURL=chunk-FKSYSPJR.js.map
133
- //# sourceMappingURL=chunk-FKSYSPJR.js.map
132
+ export { $err, $fmtError, $fmtResultErr, $isPlainObj, $isSecretKey, $isStr, $ok, $parseToObj, $stringifyObj, CIPHER_ENCODING, DIGEST_ALGORITHMS, ENCODING, ENCRYPTED_REGEX, ENCRYPTION_ALGORITHMS, __export, matchEncryptedPattern, parseToObj, stringifyObj, title, tryParseToObj, tryStringifyObj };
133
+ //# sourceMappingURL=chunk-RUTGDMVR.js.map
134
+ //# sourceMappingURL=chunk-RUTGDMVR.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"sources":["../src/helpers/consts.ts","../src/helpers/validate.ts","../src/helpers/error.ts","../src/helpers/object.ts"],"names":["title"],"mappings":";;;;;;;;;AAAO,IAAM,QAAA,GAAW,OAAO,MAAA,CAAO,CAAC,UAAU,WAAA,EAAa,KAAA,EAAO,MAAA,EAAQ,QAAQ,CAAU;AAExF,IAAM,kBAAkB,MAAA,CAAO,MAAA,CAAO,CAAC,QAAA,EAAU,WAAA,EAAa,KAAK,CAAU;AAE7E,IAAM,iBAAA,GAAoB,OAAO,MAAA,CAAO;AAAA,EAC7C,MAAA,EAAQ,EAAE,IAAA,EAAM,QAAA,EAAU,KAAK,SAAA,EAAU;AAAA,EACzC,MAAA,EAAQ,EAAE,IAAA,EAAM,QAAA,EAAU,KAAK,SAAA,EAAU;AAAA,EACzC,MAAA,EAAQ,EAAE,IAAA,EAAM,QAAA,EAAU,KAAK,SAAA;AACjC,CAAU;AAEH,IAAM,qBAAA,GAAwB,OAAO,MAAA,CAAO;AAAA,EACjD,SAAA,EAAW,EAAE,QAAA,EAAU,EAAA,EAAI,UAAU,EAAA,EAAI,IAAA,EAAM,aAAA,EAAe,GAAA,EAAK,SAAA,EAAU;AAAA,EAC7E,SAAA,EAAW,EAAE,QAAA,EAAU,EAAA,EAAI,UAAU,EAAA,EAAI,IAAA,EAAM,aAAA,EAAe,GAAA,EAAK,SAAA,EAAU;AAAA,EAC7E,SAAA,EAAW,EAAE,QAAA,EAAU,EAAA,EAAI,UAAU,EAAA,EAAI,IAAA,EAAM,aAAA,EAAe,GAAA,EAAK,SAAA;AACrE,CAAU;;;ACVH,SAAS,MAAA,CAAO,CAAA,EAAY,GAAA,GAAM,CAAA,EAAgB;AACvD,EAAA,OAAO,CAAA,KAAM,IAAA,IAAQ,CAAA,KAAM,MAAA,IAAa,OAAO,MAAM,QAAA,IAAY,CAAA,CAAE,IAAA,EAAK,CAAE,MAAA,IAAU,GAAA;AACtF;AAEO,SAAS,YAAwD,CAAA,EAAoB;AAC1F,EAAA,IAAI,OAAO,CAAA,KAAM,QAAA,IAAY,MAAM,IAAA,IAAQ,CAAA,KAAM,QAAW,OAAO,KAAA;AACnE,EAAA,MAAM,KAAA,GAAQ,MAAA,CAAO,cAAA,CAAe,CAAC,CAAA;AACrC,EAAA,OAAO,KAAA,KAAU,MAAA,CAAO,SAAA,IAAa,KAAA,KAAU,IAAA;AACjD;AAEO,SAAS,OAAO,CAAA,EAA0C;AAC/D,EAAA,OAAO,OAAO,CAAA,KAAM,QAAA,IAAY,CAAA,KAAM,QAAQ,CAAA,KAAM,MAAA;AACtD;AAMA,IAAM,YAAA,uBAAmB,GAAA,CAAI,CAAC,YAAY,QAAA,EAAU,WAAA,EAAa,KAAK,CAAC,CAAA;AAEhE,SAAS,YAAA,CACd,GACA,QAAA,EACoC;AACpC,EAAA,IAAI,CAAC,MAAA,CAAO,CAAC,CAAA,IAAM,QAAA,KAAa,MAAA,IAAU,QAAA,KAAa,KAAA,IAAU,CAAA,CAAE,QAAA,KAAa,QAAA,EAAU,OAAO,IAAA;AAEjG,EAAA,MAAM,IAAA,GAAO,MAAA,CAAO,IAAA,CAAK,CAAC,CAAA;AAC1B,EAAA,IAAI,IAAA,CAAK,MAAA,KAAW,YAAA,CAAa,IAAA,EAAM,OAAO,IAAA;AAC9C,EAAA,KAAA,MAAW,GAAA,IAAO,MAAM,IAAI,CAAC,aAAa,GAAA,CAAI,GAAG,GAAG,OAAO,IAAA;AAC3D,EAAA,KAAA,MAAW,GAAA,IAAO,cAAc,IAAI,CAAC,OAAO,MAAA,CAAO,CAAA,EAAG,GAAG,CAAA,EAAG,OAAO,IAAA;AAEnE,EAAA,IACE,OAAO,CAAA,CAAE,MAAA,KAAW,QAAA,IACpB,EAAE,EAAE,MAAA,IAAU,iBAAA,CAAA,IACd,OAAO,CAAA,CAAE,SAAA,KAAc,QAAA,IACvB,EAAE,CAAA,CAAE,SAAA,IAAa,qBAAA,CAAA,IACjB,CAAC,MAAA,CAAO,CAAA,CAAE,GAAG,CAAA,IACb,CAAA,CAAE,GAAA,CAAI,IAAA,KAAS,QAAA,EACf;AACA,IAAA,OAAO,IAAA;AAAA,EACT;AAEA,EAAA,MAAM,SAAA,GAAY,qBAAA,CAAsB,CAAA,CAAE,SAA+C,CAAA;AAEzF,EAAA,IAAI,aAAa,MAAA,EAAQ;AACvB,IAAA,IACE,EAAE,CAAA,CAAE,GAAA,YAAe,UAAA,CAAW,cAC7B,OAAO,CAAA,CAAE,GAAA,CAAI,gBAAA,KAAqB,QAAA,IAAY,CAAA,CAAE,GAAA,CAAI,gBAAA,KAAqB,UAAU,QAAA,EACpF;AACA,MAAA,OAAO,IAAA;AAAA,IACT;AACA,IAAA,OAAO,OAAO,MAAA,CAAO,EAAE,GAAG,CAAA,EAAG,QAAA,EAAU,WAAW,CAAA;AAAA,EACpD;AAEA,EAAA,IACE,CAAC,MAAA,CAAO,CAAA,CAAE,GAAA,CAAI,SAAS,KACvB,CAAA,CAAE,GAAA,CAAI,SAAA,CAAU,IAAA,KAAS,SAAA,CAAU,GAAA,IAClC,OAAO,CAAA,CAAE,GAAA,CAAI,SAAA,CAAU,MAAA,KAAW,QAAA,IAAY,CAAA,CAAE,GAAA,CAAI,SAAA,CAAU,MAAA,KAAW,SAAA,CAAU,QAAA,GAAW,CAAA,IAC/F,OAAO,CAAA,CAAE,IAAI,WAAA,KAAgB,SAAA,IAC7B,CAAC,KAAA,CAAM,OAAA,CAAQ,CAAA,CAAE,IAAI,MAAM,CAAA,IAC3B,CAAA,CAAE,GAAA,CAAI,MAAA,CAAO,MAAA,KAAW,KACxB,EAAE,CAAA,CAAE,GAAA,CAAI,MAAA,CAAO,QAAA,CAAS,SAAS,CAAA,IAAK,CAAA,CAAE,GAAA,CAAI,MAAA,CAAO,QAAA,CAAS,SAAS,CAAA,CAAA,EACrE;AACA,IAAA,OAAO,IAAA;AAAA,EACT;AACA,EAAA,OAAO,OAAO,MAAA,CAAO,EAAE,GAAG,CAAA,EAAG,QAAA,EAAU,WAAW,CAAA;AACpD;AAeO,IAAM,eAAA,GAAkB,OAAO,MAAA,CAAO;AAAA,EAC3C,IAAA,EAAM,+BAAA;AAAA,EACN,GAAA,EAAK,sBAAA;AAAA,EACL,OAAA,EAAS;AACX,CAAC;AA8BM,SAAS,qBAAA,CAAsB,MAAc,MAAA,EAA6C;AAC/F,EAAA,IAAI,OAAO,IAAA,KAAS,QAAA,EAAU,OAAO,KAAA;AACrC,EAAA,IAAI,EAAE,UAAU,eAAA,CAAA,EAAkB,MAAM,IAAI,KAAA,CAAM,CAAA,gBAAA,EAAmB,MAAM,CAAA,CAAE,CAAA;AAC7E,EAAA,OAAO,eAAA,CAAgB,MAAM,CAAA,CAAE,IAAA,CAAK,IAAI,CAAA;AAC1C;;;AC9EO,SAAS,IAAO,MAAA,EAAuB;AAC5C,EAAA,IAAI,WAAA,CAAY,MAAM,CAAA,EAAG,OAAO,EAAE,OAAA,EAAS,IAAA,EAAM,GAAI,MAAA,EAAsB;AAC3E,EAAA,OAAO,EAAE,OAAA,EAAS,IAAA,EAAM,MAAA,EAAO;AACjC;AAIO,SAAS,KAAK,GAAA,EAA0E;AAC7F,EAAA,OAAO;AAAA,IACL,OAAA,EAAS,KAAA;AAAA,IACT,KAAA,EAAO;AAAA,MACL,OAAA,EAAS,KAAA,IAAS,GAAA,GAAM,GAAA,CAAI,MAAM,GAAA,CAAI,OAAA;AAAA,MACtC,WAAA,EAAa,MAAA,IAAU,GAAA,GAAM,GAAA,CAAI,OAAO,GAAA,CAAI;AAAA;AAC9C,GACF;AACF;AAEO,SAAS,UAAU,KAAA,EAAwB;AAChD,EAAA,IAAI,OAAO,KAAA,KAAU,QAAA,EAAU,OAAO,KAAA;AACtC,EAAA,IAAI,KAAA,YAAiB,KAAA,EAAO,OAAO,KAAA,CAAM,OAAA;AACzC,EAAA,OAAO,OAAO,KAAK,CAAA;AACrB;AAEO,SAAS,cAAc,GAAA,EAAoC;AAChE,EAAA,IAAI,CAAC,KAAK,OAAO,eAAA;AACjB,EAAA,OAAO,CAAA,EAAG,GAAA,CAAI,OAAO,CAAA,GAAA,EAAM,IAAI,WAAW,CAAA,CAAA;AAC5C;AAEO,SAAS,KAAA,CAAM,UAA0BA,MAAAA,EAAuB;AACrE,EAAA,OAAO,GAAG,QAAA,KAAa,KAAA,GAAQ,gBAAA,GAAmB,mBAAmB,MAAMA,MAAK,CAAA,CAAA;AAClF;;;ACxEO,SAAS,cAA0D,GAAA,EAAwB;AAChG,EAAA,IAAI;AACF,IAAA,IAAI,CAAC,WAAA,CAAY,GAAG,CAAA,EAAG,OAAO,IAAA,CAAK,EAAE,GAAA,EAAK,gBAAA,EAAkB,IAAA,EAAM,6BAAA,EAA+B,CAAA;AACjG,IAAA,OAAO,GAAA,CAAI,IAAA,CAAK,SAAA,CAAU,GAAG,CAAC,CAAA;AAAA,EAChC,SAAS,KAAA,EAAO;AACd,IAAA,OAAO,IAAA,CAAK,EAAE,GAAA,EAAK,0BAAA,EAA4B,MAAM,SAAA,CAAU,KAAK,GAAG,CAAA;AAAA,EACzE;AACF;AAEO,SAAS,YAAwD,GAAA,EAAoC;AAC1G,EAAA,IAAI;AACF,IAAA,IAAI,CAAC,MAAA,CAAO,GAAG,CAAA,EAAG,OAAO,IAAA,CAAK,EAAE,GAAA,EAAK,wBAAA,EAA0B,IAAA,EAAM,6BAAA,EAA+B,CAAA;AACpG,IAAA,MAAM,GAAA,GAAM,IAAA,CAAK,KAAA,CAAM,GAAG,CAAA;AAE1B,IAAA,IAAI,CAAC,YAAY,GAAG,CAAA;AAClB,MAAA,OAAO,KAAK,EAAE,GAAA,EAAK,gCAAA,EAAkC,IAAA,EAAM,qCAAqC,CAAA;AAClG,IAAA,OAAO,GAAA,CAAI,EAAE,MAAA,EAAQ,GAAA,EAAU,CAAA;AAAA,EACjC,SAAS,KAAA,EAAO;AACd,IAAA,OAAO,IAAA,CAAK,EAAE,GAAA,EAAK,yBAAA,EAA2B,MAAM,SAAA,CAAU,KAAK,GAAG,CAAA;AAAA,EACxE;AACF;AAwBO,SAAS,gBAA4D,GAAA,EAAwB;AAClG,EAAA,OAAO,cAAc,GAAG,CAAA;AAC1B;AAsBO,SAAS,aAAyD,GAAA,EAAgB;AACvF,EAAA,MAAM,EAAE,MAAA,EAAQ,KAAA,EAAM,GAAI,cAAc,GAAG,CAAA;AAC3C,EAAA,IAAI,OAAO,MAAM,IAAI,KAAA,CAAM,aAAA,CAAc,KAAK,CAAC,CAAA;AAC/C,EAAA,OAAO,MAAA;AACT;AAsBO,SAAS,cAA0D,GAAA,EAAoC;AAC5G,EAAA,OAAO,YAAe,GAAG,CAAA;AAC3B;AAoBO,SAAS,WAAuD,GAAA,EAAgB;AACrF,EAAA,MAAM,EAAE,MAAA,EAAQ,KAAA,EAAM,GAAI,YAAe,GAAG,CAAA;AAC5C,EAAA,IAAI,OAAO,MAAM,IAAI,KAAA,CAAM,aAAA,CAAc,KAAK,CAAC,CAAA;AAC/C,EAAA,OAAO,MAAA;AACT","file":"chunk-RUTGDMVR.js","sourcesContent":["export const ENCODING = Object.freeze([\"base64\", \"base64url\", \"hex\", \"utf8\", \"latin1\"] as const);\r\n\r\nexport const CIPHER_ENCODING = Object.freeze([\"base64\", \"base64url\", \"hex\"] as const);\r\n\r\nexport const DIGEST_ALGORITHMS = Object.freeze({\r\n sha256: { node: \"sha256\", web: \"SHA-256\" },\r\n sha384: { node: \"sha384\", web: \"SHA-384\" },\r\n sha512: { node: \"sha512\", web: \"SHA-512\" },\r\n} as const);\r\n\r\nexport const ENCRYPTION_ALGORITHMS = Object.freeze({\r\n aes256gcm: { keyBytes: 32, ivLength: 12, node: \"aes-256-gcm\", web: \"AES-GCM\" },\r\n aes192gcm: { keyBytes: 24, ivLength: 12, node: \"aes-192-gcm\", web: \"AES-GCM\" },\r\n aes128gcm: { keyBytes: 16, ivLength: 12, node: \"aes-128-gcm\", web: \"AES-GCM\" },\r\n} as const);\r\n","import nodeCrypto from \"node:crypto\";\r\nimport type { SecretKey } from \"~/helpers/types\";\r\nimport { DIGEST_ALGORITHMS, ENCRYPTION_ALGORITHMS } from \"./consts\";\r\n\r\nexport function $isStr(x: unknown, min = 1): x is string {\r\n return x !== null && x !== undefined && typeof x === \"string\" && x.trim().length >= min;\r\n}\r\n\r\nexport function $isPlainObj<T extends object = Record<string, unknown>>(x: unknown): x is T {\r\n if (typeof x !== \"object\" || x === null || x === undefined) return false;\r\n const proto = Object.getPrototypeOf(x);\r\n return proto === Object.prototype || proto === null;\r\n}\r\n\r\nexport function $isObj(x: unknown): x is Record<string, unknown> {\r\n return typeof x === \"object\" && x !== null && x !== undefined;\r\n}\r\n\r\ntype InjectedSecretKey<Platform extends \"web\" | \"node\"> = SecretKey<Platform> & {\r\n readonly injected: (typeof ENCRYPTION_ALGORITHMS)[keyof typeof ENCRYPTION_ALGORITHMS];\r\n};\r\n\r\nconst expectedKeys = new Set([\"platform\", \"digest\", \"algorithm\", \"key\"]);\r\n\r\nexport function $isSecretKey<Platform extends \"node\" | \"web\">(\r\n x: unknown,\r\n platform: Platform,\r\n): InjectedSecretKey<Platform> | null {\r\n if (!$isObj(x) || (platform !== \"node\" && platform !== \"web\") || x.platform !== platform) return null;\r\n\r\n const keys = Object.keys(x);\r\n if (keys.length !== expectedKeys.size) return null;\r\n for (const key of keys) if (!expectedKeys.has(key)) return null;\r\n for (const key of expectedKeys) if (!Object.hasOwn(x, key)) return null;\r\n\r\n if (\r\n typeof x.digest !== \"string\" ||\r\n !(x.digest in DIGEST_ALGORITHMS) ||\r\n typeof x.algorithm !== \"string\" ||\r\n !(x.algorithm in ENCRYPTION_ALGORITHMS) ||\r\n !$isObj(x.key) ||\r\n x.key.type !== \"secret\"\r\n ) {\r\n return null;\r\n }\r\n\r\n const algorithm = ENCRYPTION_ALGORITHMS[x.algorithm as keyof typeof ENCRYPTION_ALGORITHMS];\r\n\r\n if (platform === \"node\") {\r\n if (\r\n !(x.key instanceof nodeCrypto.KeyObject) ||\r\n (typeof x.key.symmetricKeySize === \"number\" && x.key.symmetricKeySize !== algorithm.keyBytes)\r\n ) {\r\n return null;\r\n }\r\n return Object.freeze({ ...x, injected: algorithm }) as InjectedSecretKey<Platform>;\r\n }\r\n\r\n if (\r\n !$isObj(x.key.algorithm) ||\r\n x.key.algorithm.name !== algorithm.web ||\r\n (typeof x.key.algorithm.length === \"number\" && x.key.algorithm.length !== algorithm.keyBytes * 8) ||\r\n typeof x.key.extractable !== \"boolean\" ||\r\n !Array.isArray(x.key.usages) ||\r\n x.key.usages.length !== 2 ||\r\n !(x.key.usages.includes(\"encrypt\") && x.key.usages.includes(\"decrypt\"))\r\n ) {\r\n return null;\r\n }\r\n return Object.freeze({ ...x, injected: algorithm }) as InjectedSecretKey<Platform>;\r\n}\r\n\r\n/**\r\n * Regular expressions for encrypted data patterns.\r\n *\r\n * - **node**: `\"iv.cipher.tag.\"` (three dot-separated parts plus a trailing dot)\r\n * - **web**: `\"iv.cipherWithTag.\"` (two parts plus a trailing dot)\r\n * - **general**: accepts both shapes (2 or 3 parts) with a trailing dot\r\n *\r\n * Each part is any non-empty string without dots.\r\n *\r\n * ### 🍼 Explain Like I'm Five\r\n * You have a secret code you want to check. Before you check it,\r\n * you make sure it looks how a secret code should look.\r\n */\r\nexport const ENCRYPTED_REGEX = Object.freeze({\r\n node: /^([^.]+)\\.([^.]+)\\.([^.]+)\\.$/,\r\n web: /^([^.]+)\\.([^.]+)\\.$/,\r\n general: /^([^.]+)\\.([^.]+)(?:\\.([^.]+))?\\.$/,\r\n});\r\n\r\n/**\r\n * Checks if a string matches an expected encrypted payload shape.\r\n *\r\n * - **node**: `\"iv.cipher.tag.\"` (three dot-separated parts plus a trailing dot)\r\n * - **web**: `\"iv.cipherWithTag.\"` (two parts plus a trailing dot)\r\n * - **general**: accepts both shapes (2 or 3 parts) with a trailing dot\r\n *\r\n * Each part is any non-empty string without dots.\r\n *\r\n * This validates only the **shape**, not whether content is valid base64/hex, etc.\r\n *\r\n * ### 🍼 Explain Like I'm Five\r\n * You have a secret code you want to check. Before you check it,\r\n * you make sure it looks how a secret code should look.\r\n *\r\n * @param data - The string to test.\r\n * @param format - Which layout to check: `'node'`, `'web'`, or `'general'`.\r\n * @returns `true` if the string matches the pattern; otherwise `false`.\r\n * @throws {Error} If an unknown `format` is provided.\r\n *\r\n * @example\r\n * ```ts\r\n * matchEncryptedPattern(\"abc.def.ghi.\", \"node\"); // true\r\n * matchEncryptedPattern(\"abc.def.\", \"web\"); // true\r\n * matchEncryptedPattern(\"abc.def.\", \"node\"); // false\r\n * matchEncryptedPattern(\"abc.def.ghi.\", \"general\"); // true\r\n * ```\r\n */\r\nexport function matchEncryptedPattern(data: string, format: \"general\" | \"node\" | \"web\"): boolean {\r\n if (typeof data !== \"string\") return false;\r\n if (!(format in ENCRYPTED_REGEX)) throw new Error(`Unknown format: ${format}`);\r\n return ENCRYPTED_REGEX[format].test(data);\r\n}\r\n","import { $isPlainObj } from \"./validate\";\r\n\r\n/**\r\n * Standardized error object for the `Result` type.\r\n * Always has a brief `message` and a more detailed `description`.\r\n */\r\nexport interface ResultErr {\r\n readonly message: string;\r\n readonly description: string;\r\n}\r\n\r\n/**\r\n * Discriminated union for functions that can succeed or fail.\r\n *\r\n * - On **success**:\r\n * - If `T` is an object - properties of `T` are **spread** into the result\r\n * along with `success: true`.\r\n * - Otherwise - `{ success: true, result: T }`.\r\n * - On **failure**: `{ success: false, error: E }`.\r\n *\r\n * @example\r\n * ```ts\r\n * // Primitive result\r\n * function getNum(): Result<number> {\r\n * return $ok(42);\r\n * }\r\n * const r1 = getNum();\r\n * if (r1.success) console.log(r1.result); // 42\r\n *\r\n * // Object result (spread)\r\n * function getObject(): Result<{ name: string; age: number }> {\r\n * return $ok({ name: 'Alice', age: 30 });\r\n * }\r\n * const r2 = getObject();\r\n * if (r2.success) console.log(r2.name, r2.age); // 'Alice' 30\r\n * ```\r\n */\r\nexport type Result<T, E = ResultErr> = T extends object\r\n ?\r\n | ({ readonly [K in keyof T]: T[K] } & { readonly success: true; readonly error?: undefined })\r\n | ({ readonly [K in keyof T]?: undefined } & { readonly success: false; readonly error: E })\r\n :\r\n | { readonly success: true; readonly result: T; readonly error?: undefined }\r\n | { readonly success: false; readonly error: E; readonly result?: undefined };\r\n\r\nexport function $ok<T>(result?: T): Result<T> {\r\n if ($isPlainObj(result)) return { success: true, ...(result as T & object) } as Result<T>;\r\n return { success: true, result } as Result<T>;\r\n}\r\n\r\nexport function $err(err: { msg: string; desc: string }): Result<never, ResultErr>;\r\nexport function $err(err: ResultErr): Result<never, ResultErr>;\r\nexport function $err(err: { msg: string; desc: string } | ResultErr): Result<never, ResultErr> {\r\n return {\r\n success: false,\r\n error: {\r\n message: \"msg\" in err ? err.msg : err.message,\r\n description: \"desc\" in err ? err.desc : err.description,\r\n },\r\n } as Result<never, ResultErr>;\r\n}\r\n\r\nexport function $fmtError(error: unknown): string {\r\n if (typeof error === \"string\") return error;\r\n if (error instanceof Error) return error.message;\r\n return String(error);\r\n}\r\n\r\nexport function $fmtResultErr(err: ResultErr | undefined): string {\r\n if (!err) return \"Unknown error\";\r\n return `${err.message} - ${err.description}`;\r\n}\r\n\r\nexport function title(platform: \"web\" | \"node\", title: string): string {\r\n return `${platform === \"web\" ? \"Crypto Web API\" : \"Crypto NodeJS API\"} - ${title}`;\r\n}\r\n","import { $err, $fmtError, $fmtResultErr, $ok, type Result } from \"./error\";\r\nimport { $isPlainObj, $isStr } from \"./validate\";\r\n\r\nexport function $stringifyObj<T extends object = Record<string, unknown>>(obj: T): Result<string> {\r\n try {\r\n if (!$isPlainObj(obj)) return $err({ msg: \"Invalid object\", desc: \"Input is not a plain object\" });\r\n return $ok(JSON.stringify(obj));\r\n } catch (error) {\r\n return $err({ msg: \"Utility: Stringify error\", desc: $fmtError(error) });\r\n }\r\n}\r\n\r\nexport function $parseToObj<T extends object = Record<string, unknown>>(str: string): Result<{ result: T }> {\r\n try {\r\n if (!$isStr(str)) return $err({ msg: \"Utility: Invalid input\", desc: \"Input is not a valid string\" });\r\n const obj = JSON.parse(str);\r\n\r\n if (!$isPlainObj(obj))\r\n return $err({ msg: \"Utility: Invalid object format\", desc: \"Parsed data is not a plain object\" });\r\n return $ok({ result: obj as T });\r\n } catch (error) {\r\n return $err({ msg: \"Utility: Invalid format\", desc: $fmtError(error) });\r\n }\r\n}\r\n\r\n/**\r\n * Safely serializes a plain object to JSON without throwing.\r\n *\r\n * Wraps `JSON.stringify` and returns a `Result` containing the JSON string or an error.\r\n * Only plain objects (POJOs) are accepted. Class instances, Maps, Sets, etc. are rejected.\r\n *\r\n * ### 🍼 Explain Like I'm Five\r\n * You have a box of toys (your object) and take a photo of it (a JSON string)\r\n * so you can send it to a friend.\r\n *\r\n * @template T - Plain object type to serialize.\r\n * @param obj - The object to stringify (must be a plain object).\r\n * @returns A `Result` with the JSON string on success, or an error.\r\n *\r\n * @example\r\n * ```ts\r\n * const { result, error, success } = tryStringifyObj({ a: 1 });\r\n *\r\n * if (success) console.log(result); // \"{\\\"a\\\":1}\"\r\n * else console.error(error); // { message: \"...\", description: \"...\" }\r\n * ```\r\n */\r\nexport function tryStringifyObj<T extends object = Record<string, unknown>>(obj: T): Result<string> {\r\n return $stringifyObj(obj);\r\n}\r\n\r\n/**\r\n * Serializes a plain object to JSON (throwing).\r\n *\r\n * Wraps `JSON.stringify` and returns the result or throws an error.\r\n * Only plain objects (POJOs) are accepted. Class instances, Maps, Sets, etc. are rejected.\r\n *\r\n * ### 🍼 Explain Like I'm Five\r\n * You have a box of toys (your object) and take a photo of it (a JSON string)\r\n * so you can send it to a friend.\r\n *\r\n * @template T - Plain object type to serialize.\r\n * @param obj - The object to stringify (must be a plain object).\r\n * @returns JSON string representation of the object.\r\n * @throws {Error} If `obj` is not a plain object or serialization fails.\r\n *\r\n * @example\r\n * ```ts\r\n * const json = stringifyObj({ a: 1 }); // \"{\\\"a\\\":1}\"\r\n * ```\r\n */\r\nexport function stringifyObj<T extends object = Record<string, unknown>>(obj: T): string {\r\n const { result, error } = $stringifyObj(obj);\r\n if (error) throw new Error($fmtResultErr(error));\r\n return result;\r\n}\r\n\r\n/**\r\n * Safely parses a JSON string to a plain object (non-throwing).\r\n *\r\n * Wraps `JSON.parse` and returns a `Result` containing the parsed object, or an error.\r\n *\r\n * ### 🍼 Explain Like I'm Five\r\n * You rebuild your toy box (an object) from a photo you took (a JSON string).\r\n *\r\n * @template T - The expected object type.\r\n * @param str - The JSON string to parse.\r\n * @returns A `Result` with the parsed object on success, or an error.\r\n *\r\n * @example\r\n * ```ts\r\n * const {result, error, success} = tryParseToObj<{ a: number }>('{\"a\":1}');\r\n *\r\n * if (success) console.log(result); // { a: 1 }\r\n * else console.error(error) // { message: \"...\", description: \"...\" }\r\n * ```\r\n */\r\nexport function tryParseToObj<T extends object = Record<string, unknown>>(str: string): Result<{ result: T }> {\r\n return $parseToObj<T>(str);\r\n}\r\n\r\n/**\r\n * Parses a JSON string to a plain object (throwing).\r\n *\r\n * Wraps `JSON.parse` and returns the parsed object, or throws on failure.\r\n *\r\n * ### 🍼 Explain Like I'm Five\r\n * You rebuild your toy box (an object) from a photo you took (a JSON string).\r\n *\r\n * @template T - The expected object type.\r\n * @param str - The JSON string to parse.\r\n * @returns The parsed plain object.\r\n * @throws {Error} If the string can’t be parsed or doesn’t represent a plain object.\r\n *\r\n * @example\r\n * ```ts\r\n * const obj = parseToObj<{ a: number }>('{\"a\":1}'); // obj.a === 1\r\n * ```\r\n */\r\nexport function parseToObj<T extends object = Record<string, unknown>>(str: string): T {\r\n const { result, error } = $parseToObj<T>(str);\r\n if (error) throw new Error($fmtResultErr(error));\r\n return result;\r\n}\r\n"]}