ic-mops 1.12.0 → 2.0.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 (322) hide show
  1. package/.DS_Store +0 -0
  2. package/.eslintrc.json +7 -7
  3. package/CHANGELOG.md +6 -0
  4. package/api/actors.ts +41 -37
  5. package/api/downloadPackageFiles.ts +75 -61
  6. package/api/getHighestVersion.ts +5 -5
  7. package/api/index.ts +4 -4
  8. package/api/network.ts +19 -21
  9. package/api/resolveVersion.ts +14 -11
  10. package/bin/mops.js +1 -1
  11. package/bundle/bench/bench-canister.mo +109 -101
  12. package/bundle/bench/user-bench.mo +6 -6
  13. package/bundle/bin/mops.js +1 -1
  14. package/bundle/cli.js +797 -792
  15. package/bundle/cli.tgz +0 -0
  16. package/bundle/package.json +6 -5
  17. package/bundle/templates/mops-publish.yml +3 -3
  18. package/bundle/templates/mops-test.yml +3 -3
  19. package/bundle/templates/src/lib.mo +13 -13
  20. package/bundle/templates/test/lib.test.mo +2 -2
  21. package/bundle-package-json.ts +8 -8
  22. package/cache.ts +80 -65
  23. package/check-requirements.ts +49 -45
  24. package/cli.ts +577 -376
  25. package/commands/add.ts +142 -129
  26. package/commands/available-updates.ts +55 -41
  27. package/commands/bench/bench-canister.mo +114 -108
  28. package/commands/bench/user-bench.mo +6 -6
  29. package/commands/bench-replica.ts +146 -118
  30. package/commands/bench.ts +563 -497
  31. package/commands/build.ts +177 -0
  32. package/commands/bump.ts +68 -57
  33. package/commands/check-candid.ts +24 -0
  34. package/commands/docs-coverage.ts +124 -102
  35. package/commands/docs.ts +118 -108
  36. package/commands/format.ts +171 -155
  37. package/commands/init.ts +301 -275
  38. package/commands/install/install-all.ts +75 -62
  39. package/commands/install/install-dep.ts +43 -28
  40. package/commands/install/install-deps.ts +23 -15
  41. package/commands/install/install-local-dep.ts +42 -34
  42. package/commands/install/install-mops-dep.ts +154 -123
  43. package/commands/install/sync-local-cache.ts +39 -35
  44. package/commands/maintainer.ts +109 -99
  45. package/commands/outdated.ts +30 -24
  46. package/commands/owner.ts +107 -99
  47. package/commands/publish.ts +534 -443
  48. package/commands/remove.ts +119 -89
  49. package/commands/replica.ts +391 -316
  50. package/commands/search.ts +42 -36
  51. package/commands/self.ts +63 -56
  52. package/commands/sources.ts +66 -49
  53. package/commands/sync.ts +92 -75
  54. package/commands/template.ts +145 -102
  55. package/commands/test/mmf1.ts +146 -119
  56. package/commands/test/reporters/compact-reporter.ts +87 -84
  57. package/commands/test/reporters/files-reporter.ts +56 -51
  58. package/commands/test/reporters/reporter.ts +12 -6
  59. package/commands/test/reporters/silent-reporter.ts +58 -59
  60. package/commands/test/reporters/verbose-reporter.ts +66 -54
  61. package/commands/test/test.ts +498 -401
  62. package/commands/test/utils.ts +72 -67
  63. package/commands/toolchain/index.ts +363 -322
  64. package/commands/toolchain/moc.ts +78 -50
  65. package/commands/toolchain/pocket-ic.ts +41 -34
  66. package/commands/toolchain/toolchain-utils.ts +92 -72
  67. package/commands/toolchain/wasmtime.ts +37 -34
  68. package/commands/update.ts +82 -64
  69. package/commands/user.ts +90 -81
  70. package/commands/watch/deployer.ts +188 -152
  71. package/commands/watch/error-checker.ts +90 -80
  72. package/commands/watch/formatter.ts +72 -60
  73. package/commands/watch/generator.ts +116 -96
  74. package/commands/watch/globMoFiles.ts +13 -13
  75. package/commands/watch/parseDfxJson.ts +63 -57
  76. package/commands/watch/tester.ts +83 -65
  77. package/commands/watch/warning-checker.ts +149 -136
  78. package/commands/watch/watch.ts +123 -95
  79. package/dist/api/actors.d.ts +4 -4
  80. package/dist/api/actors.js +8 -8
  81. package/dist/api/downloadPackageFiles.d.ts +2 -2
  82. package/dist/api/downloadPackageFiles.js +10 -10
  83. package/dist/api/getHighestVersion.js +1 -1
  84. package/dist/api/index.d.ts +4 -4
  85. package/dist/api/index.js +4 -4
  86. package/dist/api/network.js +9 -9
  87. package/dist/api/resolveVersion.js +3 -3
  88. package/dist/bin/mops.js +1 -1
  89. package/dist/bundle-package-json.js +8 -8
  90. package/dist/cache.js +22 -17
  91. package/dist/check-requirements.js +11 -11
  92. package/dist/cli.js +283 -186
  93. package/dist/commands/add.d.ts +1 -1
  94. package/dist/commands/add.js +40 -37
  95. package/dist/commands/available-updates.d.ts +1 -1
  96. package/dist/commands/available-updates.js +18 -12
  97. package/dist/commands/bench/bench-canister.mo +114 -108
  98. package/dist/commands/bench/user-bench.mo +6 -6
  99. package/dist/commands/bench-replica.d.ts +4 -4
  100. package/dist/commands/bench-replica.js +45 -34
  101. package/dist/commands/bench.d.ts +5 -5
  102. package/dist/commands/bench.js +134 -118
  103. package/dist/commands/build.d.ts +7 -0
  104. package/dist/commands/build.js +121 -0
  105. package/dist/commands/bump.js +27 -18
  106. package/dist/commands/check-candid.d.ts +4 -0
  107. package/dist/commands/check-candid.js +15 -0
  108. package/dist/commands/docs-coverage.d.ts +1 -1
  109. package/dist/commands/docs-coverage.js +45 -31
  110. package/dist/commands/docs.d.ts +1 -1
  111. package/dist/commands/docs.js +39 -38
  112. package/dist/commands/format.js +31 -27
  113. package/dist/commands/init.js +102 -92
  114. package/dist/commands/install/install-all.d.ts +2 -2
  115. package/dist/commands/install/install-all.js +23 -21
  116. package/dist/commands/install/install-dep.d.ts +1 -1
  117. package/dist/commands/install/install-dep.js +21 -8
  118. package/dist/commands/install/install-deps.d.ts +1 -1
  119. package/dist/commands/install/install-deps.js +1 -1
  120. package/dist/commands/install/install-local-dep.js +11 -9
  121. package/dist/commands/install/install-mops-dep.d.ts +1 -1
  122. package/dist/commands/install/install-mops-dep.js +32 -27
  123. package/dist/commands/install/sync-local-cache.js +10 -10
  124. package/dist/commands/maintainer.js +21 -21
  125. package/dist/commands/outdated.js +12 -8
  126. package/dist/commands/owner.js +21 -21
  127. package/dist/commands/publish.js +148 -128
  128. package/dist/commands/remove.d.ts +1 -1
  129. package/dist/commands/remove.js +42 -30
  130. package/dist/commands/replica.d.ts +7 -7
  131. package/dist/commands/replica.js +85 -57
  132. package/dist/commands/search.js +15 -13
  133. package/dist/commands/self.js +31 -28
  134. package/dist/commands/sources.d.ts +5 -1
  135. package/dist/commands/sources.js +23 -17
  136. package/dist/commands/sync.d.ts +1 -1
  137. package/dist/commands/sync.js +38 -25
  138. package/dist/commands/template.js +66 -56
  139. package/dist/commands/test/mmf1.d.ts +3 -3
  140. package/dist/commands/test/mmf1.js +33 -31
  141. package/dist/commands/test/reporters/compact-reporter.d.ts +3 -3
  142. package/dist/commands/test/reporters/compact-reporter.js +19 -15
  143. package/dist/commands/test/reporters/files-reporter.d.ts +3 -3
  144. package/dist/commands/test/reporters/files-reporter.js +18 -14
  145. package/dist/commands/test/reporters/reporter.d.ts +2 -2
  146. package/dist/commands/test/reporters/silent-reporter.d.ts +3 -3
  147. package/dist/commands/test/reporters/silent-reporter.js +4 -4
  148. package/dist/commands/test/reporters/verbose-reporter.d.ts +3 -3
  149. package/dist/commands/test/reporters/verbose-reporter.js +17 -13
  150. package/dist/commands/test/test.d.ts +4 -4
  151. package/dist/commands/test/test.js +134 -112
  152. package/dist/commands/test/utils.d.ts +3 -3
  153. package/dist/commands/test/utils.js +17 -17
  154. package/dist/commands/toolchain/index.d.ts +1 -1
  155. package/dist/commands/toolchain/index.js +81 -69
  156. package/dist/commands/toolchain/moc.d.ts +1 -1
  157. package/dist/commands/toolchain/moc.js +48 -24
  158. package/dist/commands/toolchain/pocket-ic.js +12 -12
  159. package/dist/commands/toolchain/toolchain-utils.d.ts +2 -0
  160. package/dist/commands/toolchain/toolchain-utils.js +32 -23
  161. package/dist/commands/toolchain/wasmtime.js +11 -11
  162. package/dist/commands/update.d.ts +1 -1
  163. package/dist/commands/update.js +18 -14
  164. package/dist/commands/user.js +31 -28
  165. package/dist/commands/watch/deployer.d.ts +4 -4
  166. package/dist/commands/watch/deployer.js +45 -36
  167. package/dist/commands/watch/error-checker.d.ts +2 -2
  168. package/dist/commands/watch/error-checker.js +27 -27
  169. package/dist/commands/watch/formatter.d.ts +4 -4
  170. package/dist/commands/watch/formatter.js +17 -17
  171. package/dist/commands/watch/generator.d.ts +3 -3
  172. package/dist/commands/watch/generator.js +28 -23
  173. package/dist/commands/watch/globMoFiles.js +8 -8
  174. package/dist/commands/watch/parseDfxJson.d.ts +2 -2
  175. package/dist/commands/watch/parseDfxJson.js +9 -9
  176. package/dist/commands/watch/tester.d.ts +4 -4
  177. package/dist/commands/watch/tester.js +23 -21
  178. package/dist/commands/watch/warning-checker.d.ts +3 -3
  179. package/dist/commands/watch/warning-checker.js +36 -36
  180. package/dist/commands/watch/watch.js +45 -32
  181. package/dist/environments/nodejs/cli.d.ts +1 -0
  182. package/dist/environments/nodejs/cli.js +4 -0
  183. package/dist/environments/web/cli.d.ts +1 -0
  184. package/dist/environments/web/cli.js +4 -0
  185. package/dist/error.d.ts +1 -0
  186. package/dist/error.js +5 -0
  187. package/dist/fix-dist.js +5 -5
  188. package/dist/helpers/find-changelog-entry.js +8 -5
  189. package/dist/helpers/get-dep-name.js +2 -2
  190. package/dist/helpers/get-dfx-version.js +4 -4
  191. package/dist/helpers/get-moc-path.js +8 -7
  192. package/dist/helpers/get-moc-version.js +10 -7
  193. package/dist/helpers/get-package-id.js +2 -2
  194. package/dist/helpers/is-candid-compatible.d.ts +1 -0
  195. package/dist/helpers/is-candid-compatible.js +20 -0
  196. package/dist/integrity.d.ts +1 -1
  197. package/dist/integrity.js +47 -38
  198. package/dist/jest.config.d.ts +11 -0
  199. package/dist/jest.config.js +14 -0
  200. package/dist/mops.d.ts +6 -6
  201. package/dist/mops.js +87 -80
  202. package/dist/notify-installs.js +4 -4
  203. package/dist/package.json +9 -5
  204. package/dist/pem.d.ts +3 -3
  205. package/dist/pem.js +20 -12
  206. package/dist/release-cli.js +20 -20
  207. package/dist/resolve-packages.d.ts +1 -1
  208. package/dist/resolve-packages.js +52 -36
  209. package/dist/templates/mops-publish.yml +3 -3
  210. package/dist/templates/mops-test.yml +3 -3
  211. package/dist/templates/src/lib.mo +13 -13
  212. package/dist/templates/test/lib.test.mo +2 -2
  213. package/dist/templates.js +1 -1
  214. package/dist/tests/cli.test.d.ts +1 -0
  215. package/dist/tests/cli.test.js +63 -0
  216. package/dist/types.d.ts +14 -4
  217. package/dist/vessel.d.ts +2 -2
  218. package/dist/vessel.js +41 -34
  219. package/dist/wasm/pkg/bundler/package.json +20 -0
  220. package/dist/wasm/pkg/bundler/wasm.d.ts +3 -0
  221. package/dist/wasm/pkg/bundler/wasm.js +5 -0
  222. package/dist/wasm/pkg/bundler/wasm_bg.js +93 -0
  223. package/dist/wasm/pkg/bundler/wasm_bg.wasm +0 -0
  224. package/dist/wasm/pkg/bundler/wasm_bg.wasm.d.ts +8 -0
  225. package/dist/wasm/pkg/nodejs/package.json +14 -0
  226. package/dist/wasm/pkg/nodejs/wasm.d.ts +3 -0
  227. package/dist/wasm/pkg/nodejs/wasm.js +98 -0
  228. package/dist/wasm/pkg/nodejs/wasm_bg.wasm +0 -0
  229. package/dist/wasm/pkg/nodejs/wasm_bg.wasm.d.ts +8 -0
  230. package/dist/wasm/pkg/web/package.json +18 -0
  231. package/dist/wasm/pkg/web/wasm.d.ts +35 -0
  232. package/dist/wasm/pkg/web/wasm.js +191 -0
  233. package/dist/wasm/pkg/web/wasm_bg.wasm +0 -0
  234. package/dist/wasm/pkg/web/wasm_bg.wasm.d.ts +8 -0
  235. package/dist/wasm.d.ts +5 -0
  236. package/dist/wasm.js +10 -0
  237. package/environments/nodejs/cli.ts +6 -0
  238. package/environments/web/cli.ts +6 -0
  239. package/error.ts +6 -0
  240. package/fix-dist.ts +5 -5
  241. package/global.d.ts +3 -3
  242. package/helpers/find-changelog-entry.ts +26 -23
  243. package/helpers/get-dep-name.ts +5 -5
  244. package/helpers/get-dfx-version.ts +8 -9
  245. package/helpers/get-moc-path.ts +25 -26
  246. package/helpers/get-moc-version.ts +21 -19
  247. package/helpers/get-package-id.ts +4 -4
  248. package/helpers/is-candid-compatible.ts +22 -0
  249. package/integrity.ts +270 -236
  250. package/jest.config.js +14 -0
  251. package/mops.ts +238 -215
  252. package/notify-installs.ts +16 -17
  253. package/package.json +19 -10
  254. package/parallel.ts +28 -24
  255. package/pem.ts +55 -47
  256. package/release-cli.ts +73 -39
  257. package/resolve-packages.ts +231 -189
  258. package/templates/mops-publish.yml +3 -3
  259. package/templates/mops-test.yml +3 -3
  260. package/templates/src/lib.mo +13 -13
  261. package/templates/test/lib.test.mo +2 -2
  262. package/templates.ts +4 -4
  263. package/tests/__snapshots__/cli.test.ts.snap +202 -0
  264. package/tests/build/error/candid/bar.did +3 -0
  265. package/tests/build/error/dfx.json +12 -0
  266. package/tests/build/error/mops.toml +9 -0
  267. package/tests/build/error/src/Bar.mo +5 -0
  268. package/tests/build/error/src/Foo.mo +5 -0
  269. package/tests/build/success/.dfx/local/canister_ids.json +17 -0
  270. package/tests/build/success/.dfx/local/canisters/bar/bar.did +3 -0
  271. package/tests/build/success/.dfx/local/canisters/bar/bar.most +4 -0
  272. package/tests/build/success/.dfx/local/canisters/bar/bar.wasm +0 -0
  273. package/tests/build/success/.dfx/local/canisters/bar/constructor.did +3 -0
  274. package/tests/build/success/.dfx/local/canisters/bar/index.js +42 -0
  275. package/tests/build/success/.dfx/local/canisters/bar/init_args.txt +1 -0
  276. package/tests/build/success/.dfx/local/canisters/bar/service.did +3 -0
  277. package/tests/build/success/.dfx/local/canisters/bar/service.did.d.ts +7 -0
  278. package/tests/build/success/.dfx/local/canisters/bar/service.did.js +4 -0
  279. package/tests/build/success/.dfx/local/canisters/foo/constructor.did +3 -0
  280. package/tests/build/success/.dfx/local/canisters/foo/foo.did +3 -0
  281. package/tests/build/success/.dfx/local/canisters/foo/foo.most +4 -0
  282. package/tests/build/success/.dfx/local/canisters/foo/foo.wasm +0 -0
  283. package/tests/build/success/.dfx/local/canisters/foo/index.js +42 -0
  284. package/tests/build/success/.dfx/local/canisters/foo/init_args.txt +1 -0
  285. package/tests/build/success/.dfx/local/canisters/foo/service.did +3 -0
  286. package/tests/build/success/.dfx/local/canisters/foo/service.did.d.ts +7 -0
  287. package/tests/build/success/.dfx/local/canisters/foo/service.did.js +4 -0
  288. package/tests/build/success/.dfx/local/lsp/ucwa4-rx777-77774-qaada-cai.did +3 -0
  289. package/tests/build/success/.dfx/local/lsp/ulvla-h7777-77774-qaacq-cai.did +3 -0
  290. package/tests/build/success/.dfx/local/network-id +4 -0
  291. package/tests/build/success/candid/bar.did +3 -0
  292. package/tests/build/success/dfx.json +12 -0
  293. package/tests/build/success/mops.toml +9 -0
  294. package/tests/build/success/src/Bar.mo +5 -0
  295. package/tests/build/success/src/Foo.mo +5 -0
  296. package/tests/check-candid/a.did +3 -0
  297. package/tests/check-candid/b.did +5 -0
  298. package/tests/check-candid/c.did +3 -0
  299. package/tests/cli.test.ts +82 -0
  300. package/tsconfig.json +26 -19
  301. package/types.ts +41 -31
  302. package/vessel.ts +219 -187
  303. package/wasm/Cargo.lock +1475 -0
  304. package/wasm/Cargo.toml +28 -0
  305. package/wasm/pkg/bundler/package.json +20 -0
  306. package/wasm/pkg/bundler/wasm.d.ts +3 -0
  307. package/wasm/pkg/bundler/wasm.js +5 -0
  308. package/wasm/pkg/bundler/wasm_bg.js +93 -0
  309. package/wasm/pkg/bundler/wasm_bg.wasm +0 -0
  310. package/wasm/pkg/bundler/wasm_bg.wasm.d.ts +8 -0
  311. package/wasm/pkg/nodejs/package.json +14 -0
  312. package/wasm/pkg/nodejs/wasm.d.ts +3 -0
  313. package/wasm/pkg/nodejs/wasm.js +98 -0
  314. package/wasm/pkg/nodejs/wasm_bg.wasm +0 -0
  315. package/wasm/pkg/nodejs/wasm_bg.wasm.d.ts +8 -0
  316. package/wasm/pkg/web/package.json +18 -0
  317. package/wasm/pkg/web/wasm.d.ts +35 -0
  318. package/wasm/pkg/web/wasm.js +191 -0
  319. package/wasm/pkg/web/wasm_bg.wasm +0 -0
  320. package/wasm/pkg/web/wasm_bg.wasm.d.ts +8 -0
  321. package/wasm/src/lib.rs +17 -0
  322. package/wasm.ts +16 -0
@@ -0,0 +1,22 @@
1
+ import { readFile, access } from "node:fs/promises";
2
+ import path from "node:path";
3
+ import { getWasmBindings } from "../wasm.js";
4
+
5
+ export async function isCandidCompatible(
6
+ newPath: string,
7
+ originalPath: string,
8
+ ): Promise<boolean> {
9
+ try {
10
+ await access(newPath);
11
+ } catch {
12
+ throw new Error(`Candid file not found: ${newPath}`);
13
+ }
14
+ try {
15
+ await access(originalPath);
16
+ } catch {
17
+ throw new Error(`Candid file not found: ${originalPath}`);
18
+ }
19
+ const newText = await readFile(path.resolve(newPath), "utf8");
20
+ const originalText = await readFile(path.resolve(originalPath), "utf8");
21
+ return getWasmBindings().is_candid_compatible(newText, originalText);
22
+ }
package/integrity.ts CHANGED
@@ -1,278 +1,312 @@
1
- import process from 'node:process';
2
- import fs from 'node:fs';
3
- import path from 'node:path';
4
- import {sha256} from '@noble/hashes/sha256';
5
- import {bytesToHex} from '@noble/hashes/utils';
6
- import {getDependencyType, getRootDir, readConfig} from './mops.js';
7
- import {mainActor} from './api/actors.js';
8
- import {resolvePackages} from './resolve-packages.js';
9
- import {getPackageId} from './helpers/get-package-id.js';
1
+ import process from "node:process";
2
+ import fs from "node:fs";
3
+ import path from "node:path";
4
+ import { sha256 } from "@noble/hashes/sha256";
5
+ import { bytesToHex } from "@noble/hashes/utils";
6
+ import { getDependencyType, getRootDir, readConfig } from "./mops.js";
7
+ import { mainActor } from "./api/actors.js";
8
+ import { resolvePackages } from "./resolve-packages.js";
9
+ import { getPackageId } from "./helpers/get-package-id.js";
10
10
 
11
11
  type LockFileGeneric = {
12
- version : number;
12
+ version: number;
13
13
  };
14
14
 
15
15
  type LockFileV1 = {
16
- version : 1;
17
- mopsTomlHash : string;
18
- hashes : Record<string, Record<string, string>>;
16
+ version: 1;
17
+ mopsTomlHash: string;
18
+ hashes: Record<string, Record<string, string>>;
19
19
  };
20
20
 
21
21
  type LockFileV2 = {
22
- version : 2;
23
- mopsTomlDepsHash : string;
24
- hashes : Record<string, Record<string, string>>;
22
+ version: 2;
23
+ mopsTomlDepsHash: string;
24
+ hashes: Record<string, Record<string, string>>;
25
25
  };
26
26
 
27
27
  type LockFileV3 = {
28
- version : 3;
29
- mopsTomlDepsHash : string;
30
- hashes : Record<string, Record<string, string>>;
31
- deps : Record<string, string>;
28
+ version: 3;
29
+ mopsTomlDepsHash: string;
30
+ hashes: Record<string, Record<string, string>>;
31
+ deps: Record<string, string>;
32
32
  };
33
33
 
34
34
  type LockFile = LockFileV1 | LockFileV2 | LockFileV3;
35
35
 
36
- export async function checkIntegrity(lock ?: 'check' | 'update' | 'ignore') {
37
- let force = !!lock;
38
-
39
- if (!lock && !process.env['CI'] && fs.existsSync(path.join(getRootDir(), 'mops.lock'))) {
40
- lock = 'update';
41
- }
42
-
43
- if (!lock) {
44
- lock = process.env['CI'] ? 'check' : 'ignore';
45
- }
46
-
47
- if (lock === 'update') {
48
- await updateLockFile();
49
- await checkLockFile(force);
50
- }
51
- else if (lock === 'check') {
52
- await checkLockFile(force);
53
- }
36
+ export async function checkIntegrity(lock?: "check" | "update" | "ignore") {
37
+ let force = !!lock;
38
+
39
+ if (
40
+ !lock &&
41
+ !process.env["CI"] &&
42
+ fs.existsSync(path.join(getRootDir(), "mops.lock"))
43
+ ) {
44
+ lock = "update";
45
+ }
46
+
47
+ if (!lock) {
48
+ lock = process.env["CI"] ? "check" : "ignore";
49
+ }
50
+
51
+ if (lock === "update") {
52
+ await updateLockFile();
53
+ await checkLockFile(force);
54
+ } else if (lock === "check") {
55
+ await checkLockFile(force);
56
+ }
54
57
  }
55
58
 
56
- async function getFileHashesFromRegistry() : Promise<[string, [string, Uint8Array | number[]][]][]> {
57
- let packageIds = await getResolvedMopsPackageIds();
58
- let actor = await mainActor();
59
- let fileHashesByPackageIds = await actor.getFileHashesByPackageIds(packageIds);
60
- return fileHashesByPackageIds;
59
+ async function getFileHashesFromRegistry(): Promise<
60
+ [string, [string, Uint8Array | number[]][]][]
61
+ > {
62
+ let packageIds = await getResolvedMopsPackageIds();
63
+ let actor = await mainActor();
64
+ let fileHashesByPackageIds =
65
+ await actor.getFileHashesByPackageIds(packageIds);
66
+ return fileHashesByPackageIds;
61
67
  }
62
68
 
63
- async function getResolvedMopsPackageIds() : Promise<string[]> {
64
- let resolvedPackages = await resolvePackages();
65
- let packageIds = Object.entries(resolvedPackages)
66
- .filter(([_, version]) => getDependencyType(version) === 'mops')
67
- .map(([name, version]) => getPackageId(name, version));
68
- return packageIds;
69
+ async function getResolvedMopsPackageIds(): Promise<string[]> {
70
+ let resolvedPackages = await resolvePackages();
71
+ let packageIds = Object.entries(resolvedPackages)
72
+ .filter(([_, version]) => getDependencyType(version) === "mops")
73
+ .map(([name, version]) => getPackageId(name, version));
74
+ return packageIds;
69
75
  }
70
76
 
71
77
  // get hash of local file from '.mops' dir by fileId
72
- export function getLocalFileHash(fileId : string) : string {
73
- let rootDir = getRootDir();
74
- let file = path.join(rootDir, '.mops', fileId);
75
- if (!fs.existsSync(file)) {
76
- console.error(`Missing file ${fileId} in .mops dir`);
77
- process.exit(1);
78
- }
79
- let fileData = fs.readFileSync(file);
80
- return bytesToHex(sha256(fileData));
78
+ export function getLocalFileHash(fileId: string): string {
79
+ let rootDir = getRootDir();
80
+ let file = path.join(rootDir, ".mops", fileId);
81
+ if (!fs.existsSync(file)) {
82
+ console.error(`Missing file ${fileId} in .mops dir`);
83
+ process.exit(1);
84
+ }
85
+ let fileData = fs.readFileSync(file);
86
+ return bytesToHex(sha256(fileData));
81
87
  }
82
88
 
83
- function getMopsTomlHash() : string {
84
- return bytesToHex(sha256(fs.readFileSync(getRootDir() + '/mops.toml')));
89
+ function getMopsTomlHash(): string {
90
+ return bytesToHex(sha256(fs.readFileSync(getRootDir() + "/mops.toml")));
85
91
  }
86
92
 
87
- function getMopsTomlDepsHash() : string {
88
- let config = readConfig();
89
- let deps = config.dependencies || {};
90
- let devDeps = config['dev-dependencies'] || {};
91
- let allDeps = {...deps, ...devDeps};
92
- // sort allDeps by key
93
- let sortedDeps = Object.keys(allDeps).sort().reduce((acc, key) => {
94
- acc[key] = allDeps[key]?.version || allDeps[key]?.repo || allDeps[key]?.path || '';
95
- return acc;
96
- }, {} as Record<string, string>);
97
- return bytesToHex(sha256(JSON.stringify(sortedDeps)));
93
+ function getMopsTomlDepsHash(): string {
94
+ let config = readConfig();
95
+ let deps = config.dependencies || {};
96
+ let devDeps = config["dev-dependencies"] || {};
97
+ let allDeps = { ...deps, ...devDeps };
98
+ // sort allDeps by key
99
+ let sortedDeps = Object.keys(allDeps)
100
+ .sort()
101
+ .reduce(
102
+ (acc, key) => {
103
+ acc[key] =
104
+ allDeps[key]?.version ||
105
+ allDeps[key]?.repo ||
106
+ allDeps[key]?.path ||
107
+ "";
108
+ return acc;
109
+ },
110
+ {} as Record<string, string>,
111
+ );
112
+ return bytesToHex(sha256(JSON.stringify(sortedDeps)));
98
113
  }
99
114
 
100
115
  // compare hashes of local files with hashes from the registry
101
116
  export async function checkRemote() {
102
- let fileHashesFromRegistry = await getFileHashesFromRegistry();
103
-
104
- // eslint-disable-next-line @typescript-eslint/no-unused-vars
105
- for (let [_packageId, fileHashes] of fileHashesFromRegistry) {
106
- for (let [fileId, hash] of fileHashes) {
107
- let remoteHash = new Uint8Array(hash);
108
- let localHash = getLocalFileHash(fileId);
109
-
110
- if (localHash !== bytesToHex(remoteHash)) {
111
- console.error('Integrity check failed.');
112
- console.error(`Mismatched hash for ${fileId}: ${localHash} vs ${bytesToHex(remoteHash)}`);
113
- process.exit(1);
114
- }
115
- }
116
- }
117
+ let fileHashesFromRegistry = await getFileHashesFromRegistry();
118
+
119
+ // eslint-disable-next-line @typescript-eslint/no-unused-vars
120
+ for (let [_packageId, fileHashes] of fileHashesFromRegistry) {
121
+ for (let [fileId, hash] of fileHashes) {
122
+ let remoteHash = new Uint8Array(hash);
123
+ let localHash = getLocalFileHash(fileId);
124
+
125
+ if (localHash !== bytesToHex(remoteHash)) {
126
+ console.error("Integrity check failed.");
127
+ console.error(
128
+ `Mismatched hash for ${fileId}: ${localHash} vs ${bytesToHex(remoteHash)}`,
129
+ );
130
+ process.exit(1);
131
+ }
132
+ }
133
+ }
117
134
  }
118
135
 
119
- export function readLockFile() : LockFile | null {
120
- let rootDir = getRootDir();
121
- let lockFile = path.join(rootDir, 'mops.lock');
122
- if (fs.existsSync(lockFile)) {
123
- return JSON.parse(fs.readFileSync(lockFile).toString()) as LockFile;
124
- }
125
- return null;
136
+ export function readLockFile(): LockFile | null {
137
+ let rootDir = getRootDir();
138
+ let lockFile = path.join(rootDir, "mops.lock");
139
+ if (fs.existsSync(lockFile)) {
140
+ return JSON.parse(fs.readFileSync(lockFile).toString()) as LockFile;
141
+ }
142
+ return null;
126
143
  }
127
144
 
128
145
  // check if lock file exists and integrity of mopsTomlDepsHash
129
- export function checkLockFileLight() : boolean {
130
- let existingLockFileJson = readLockFile();
131
- if (existingLockFileJson) {
132
- let mopsTomlDepsHash = getMopsTomlDepsHash();
133
- if (existingLockFileJson.version === 3 && mopsTomlDepsHash === existingLockFileJson.mopsTomlDepsHash) {
134
- return true;
135
- }
136
- }
137
- return false;
146
+ export function checkLockFileLight(): boolean {
147
+ let existingLockFileJson = readLockFile();
148
+ if (existingLockFileJson) {
149
+ let mopsTomlDepsHash = getMopsTomlDepsHash();
150
+ if (
151
+ existingLockFileJson.version === 3 &&
152
+ mopsTomlDepsHash === existingLockFileJson.mopsTomlDepsHash
153
+ ) {
154
+ return true;
155
+ }
156
+ }
157
+ return false;
138
158
  }
139
159
 
140
160
  export async function updateLockFile() {
141
- // if lock file exists and mops.toml hasn't changed, don't update it
142
- if (checkLockFileLight()) {
143
- return;
144
- }
145
-
146
- let resolvedDeps = await resolvePackages();
147
-
148
- let fileHashes = await getFileHashesFromRegistry();
149
-
150
- let lockFileJson : LockFileV3 = {
151
- version: 3,
152
- mopsTomlDepsHash: getMopsTomlDepsHash(),
153
- deps: resolvedDeps,
154
- hashes: fileHashes.reduce((acc, [packageId, fileHashes]) => {
155
- acc[packageId] = fileHashes.reduce((acc, [fileId, hash]) => {
156
- acc[fileId] = bytesToHex(new Uint8Array(hash));
157
- return acc;
158
- }, {} as Record<string, string>);
159
- return acc;
160
- }, {} as Record<string, Record<string, string>>),
161
- };
162
-
163
- let rootDir = getRootDir();
164
- let lockFile = path.join(rootDir, 'mops.lock');
165
- fs.writeFileSync(lockFile, JSON.stringify(lockFileJson, null, 2));
161
+ // if lock file exists and mops.toml hasn't changed, don't update it
162
+ if (checkLockFileLight()) {
163
+ return;
164
+ }
165
+
166
+ let resolvedDeps = await resolvePackages();
167
+
168
+ let fileHashes = await getFileHashesFromRegistry();
169
+
170
+ let lockFileJson: LockFileV3 = {
171
+ version: 3,
172
+ mopsTomlDepsHash: getMopsTomlDepsHash(),
173
+ deps: resolvedDeps,
174
+ hashes: fileHashes.reduce(
175
+ (acc, [packageId, fileHashes]) => {
176
+ acc[packageId] = fileHashes.reduce(
177
+ (acc, [fileId, hash]) => {
178
+ acc[fileId] = bytesToHex(new Uint8Array(hash));
179
+ return acc;
180
+ },
181
+ {} as Record<string, string>,
182
+ );
183
+ return acc;
184
+ },
185
+ {} as Record<string, Record<string, string>>,
186
+ ),
187
+ };
188
+
189
+ let rootDir = getRootDir();
190
+ let lockFile = path.join(rootDir, "mops.lock");
191
+ fs.writeFileSync(lockFile, JSON.stringify(lockFileJson, null, 2));
166
192
  }
167
193
 
168
194
  // compare hashes of local files with hashes from the lock file
169
195
  export async function checkLockFile(force = false) {
170
- let supportedVersions = [1, 2, 3];
171
- let rootDir = getRootDir();
172
- let lockFile = path.join(rootDir, 'mops.lock');
173
-
174
- // check if lock file exists
175
- if (!fs.existsSync(lockFile)) {
176
- if (force) {
177
- console.error('Missing lock file. Run `mops install` to generate it.');
178
- process.exit(1);
179
- }
180
- return;
181
- }
182
-
183
- let lockFileJsonGeneric : LockFileGeneric = JSON.parse(fs.readFileSync(lockFile).toString());
184
- let packageIds = await getResolvedMopsPackageIds();
185
-
186
- // check lock file version
187
- if (!supportedVersions.includes(lockFileJsonGeneric.version)) {
188
- console.error('Integrity check failed');
189
- console.error(`Invalid lock file version: ${lockFileJsonGeneric.version}. Supported versions: ${supportedVersions.join(', ')}`);
190
- process.exit(1);
191
- }
192
-
193
- let lockFileJson = lockFileJsonGeneric as LockFile;
194
-
195
- // V1: check mops.toml hash
196
- if (lockFileJson.version === 1) {
197
- if (lockFileJson.mopsTomlHash !== getMopsTomlHash()) {
198
- console.error('Integrity check failed');
199
- console.error('Mismatched mops.toml hash');
200
- console.error(`Locked hash: ${lockFileJson.mopsTomlHash}`);
201
- console.error(`Actual hash: ${getMopsTomlHash()}`);
202
- process.exit(1);
203
- }
204
- }
205
-
206
- // V2, V3: check mops.toml deps hash
207
- if (lockFileJson.version === 2 || lockFileJson.version === 3) {
208
- if (lockFileJson.mopsTomlDepsHash !== getMopsTomlDepsHash()) {
209
- console.error('Integrity check failed');
210
- console.error('Mismatched mops.toml dependencies hash');
211
- console.error(`Locked hash: ${lockFileJson.mopsTomlDepsHash}`);
212
- console.error(`Actual hash: ${getMopsTomlDepsHash()}`);
213
- process.exit(1);
214
- }
215
- }
216
-
217
- // V3: check locked deps (including GitHub and local packages)
218
- if (lockFileJson.version === 3) {
219
- let lockedDeps = {...lockFileJson.deps};
220
- let resolvedDeps = await resolvePackages();
221
-
222
- for (let name of Object.keys(resolvedDeps)) {
223
- if (lockedDeps[name] !== resolvedDeps[name]) {
224
- console.error('Integrity check failed');
225
- console.error(`Mismatched package ${name}`);
226
- console.error(`Locked: ${lockedDeps[name]}`);
227
- console.error(`Actual: ${resolvedDeps[name]}`);
228
- process.exit(1);
229
- }
230
- }
231
- }
232
-
233
- // check number of packages
234
- if (Object.keys(lockFileJson.hashes).length !== packageIds.length) {
235
- console.error('Integrity check failed');
236
- console.error(`Mismatched number of resolved packages: ${JSON.stringify(Object.keys(lockFileJson.hashes).length)} vs ${JSON.stringify(packageIds.length)}`);
237
- process.exit(1);
238
- }
239
-
240
- // check if resolved packages are in the lock file
241
- for (let packageId of packageIds) {
242
- if (!(packageId in lockFileJson.hashes)) {
243
- console.error('Integrity check failed');
244
- console.error(`Missing package ${packageId} in lock file`);
245
- process.exit(1);
246
- }
247
- }
248
-
249
- for (let [packageId, hashes] of Object.entries(lockFileJson.hashes)) {
250
-
251
- // check if package is in resolved packages
252
- if (!packageIds.includes(packageId)) {
253
- console.error('Integrity check failed');
254
- console.error(`Package ${packageId} in lock file but not in resolved packages`);
255
- process.exit(1);
256
- }
257
-
258
- for (let [fileId, lockedHash] of Object.entries(hashes)) {
259
-
260
- // check if file belongs to package
261
- if (!fileId.startsWith(packageId)) {
262
- console.error('Integrity check failed');
263
- console.error(`File ${fileId} in lock file does not belong to package ${packageId}`);
264
- process.exit(1);
265
- }
266
-
267
- // local file hash vs hash from lock file
268
- let localHash = getLocalFileHash(fileId);
269
- if (lockedHash !== localHash) {
270
- console.error('Integrity check failed');
271
- console.error(`Mismatched hash for ${fileId}`);
272
- console.error(`Locked hash: ${lockedHash}`);
273
- console.error(`Actual hash: ${localHash}`);
274
- process.exit(1);
275
- }
276
- }
277
- }
278
- }
196
+ let supportedVersions = [1, 2, 3];
197
+ let rootDir = getRootDir();
198
+ let lockFile = path.join(rootDir, "mops.lock");
199
+
200
+ // check if lock file exists
201
+ if (!fs.existsSync(lockFile)) {
202
+ if (force) {
203
+ console.error("Missing lock file. Run `mops install` to generate it.");
204
+ process.exit(1);
205
+ }
206
+ return;
207
+ }
208
+
209
+ let lockFileJsonGeneric: LockFileGeneric = JSON.parse(
210
+ fs.readFileSync(lockFile).toString(),
211
+ );
212
+ let packageIds = await getResolvedMopsPackageIds();
213
+
214
+ // check lock file version
215
+ if (!supportedVersions.includes(lockFileJsonGeneric.version)) {
216
+ console.error("Integrity check failed");
217
+ console.error(
218
+ `Invalid lock file version: ${lockFileJsonGeneric.version}. Supported versions: ${supportedVersions.join(", ")}`,
219
+ );
220
+ process.exit(1);
221
+ }
222
+
223
+ let lockFileJson = lockFileJsonGeneric as LockFile;
224
+
225
+ // V1: check mops.toml hash
226
+ if (lockFileJson.version === 1) {
227
+ if (lockFileJson.mopsTomlHash !== getMopsTomlHash()) {
228
+ console.error("Integrity check failed");
229
+ console.error("Mismatched mops.toml hash");
230
+ console.error(`Locked hash: ${lockFileJson.mopsTomlHash}`);
231
+ console.error(`Actual hash: ${getMopsTomlHash()}`);
232
+ process.exit(1);
233
+ }
234
+ }
235
+
236
+ // V2, V3: check mops.toml deps hash
237
+ if (lockFileJson.version === 2 || lockFileJson.version === 3) {
238
+ if (lockFileJson.mopsTomlDepsHash !== getMopsTomlDepsHash()) {
239
+ console.error("Integrity check failed");
240
+ console.error("Mismatched mops.toml dependencies hash");
241
+ console.error(`Locked hash: ${lockFileJson.mopsTomlDepsHash}`);
242
+ console.error(`Actual hash: ${getMopsTomlDepsHash()}`);
243
+ process.exit(1);
244
+ }
245
+ }
246
+
247
+ // V3: check locked deps (including GitHub and local packages)
248
+ if (lockFileJson.version === 3) {
249
+ let lockedDeps = { ...lockFileJson.deps };
250
+ let resolvedDeps = await resolvePackages();
251
+
252
+ for (let name of Object.keys(resolvedDeps)) {
253
+ if (lockedDeps[name] !== resolvedDeps[name]) {
254
+ console.error("Integrity check failed");
255
+ console.error(`Mismatched package ${name}`);
256
+ console.error(`Locked: ${lockedDeps[name]}`);
257
+ console.error(`Actual: ${resolvedDeps[name]}`);
258
+ process.exit(1);
259
+ }
260
+ }
261
+ }
262
+
263
+ // check number of packages
264
+ if (Object.keys(lockFileJson.hashes).length !== packageIds.length) {
265
+ console.error("Integrity check failed");
266
+ console.error(
267
+ `Mismatched number of resolved packages: ${JSON.stringify(Object.keys(lockFileJson.hashes).length)} vs ${JSON.stringify(packageIds.length)}`,
268
+ );
269
+ process.exit(1);
270
+ }
271
+
272
+ // check if resolved packages are in the lock file
273
+ for (let packageId of packageIds) {
274
+ if (!(packageId in lockFileJson.hashes)) {
275
+ console.error("Integrity check failed");
276
+ console.error(`Missing package ${packageId} in lock file`);
277
+ process.exit(1);
278
+ }
279
+ }
280
+
281
+ for (let [packageId, hashes] of Object.entries(lockFileJson.hashes)) {
282
+ // check if package is in resolved packages
283
+ if (!packageIds.includes(packageId)) {
284
+ console.error("Integrity check failed");
285
+ console.error(
286
+ `Package ${packageId} in lock file but not in resolved packages`,
287
+ );
288
+ process.exit(1);
289
+ }
290
+
291
+ for (let [fileId, lockedHash] of Object.entries(hashes)) {
292
+ // check if file belongs to package
293
+ if (!fileId.startsWith(packageId)) {
294
+ console.error("Integrity check failed");
295
+ console.error(
296
+ `File ${fileId} in lock file does not belong to package ${packageId}`,
297
+ );
298
+ process.exit(1);
299
+ }
300
+
301
+ // local file hash vs hash from lock file
302
+ let localHash = getLocalFileHash(fileId);
303
+ if (lockedHash !== localHash) {
304
+ console.error("Integrity check failed");
305
+ console.error(`Mismatched hash for ${fileId}`);
306
+ console.error(`Locked hash: ${lockedHash}`);
307
+ console.error(`Actual hash: ${localHash}`);
308
+ process.exit(1);
309
+ }
310
+ }
311
+ }
312
+ }
package/jest.config.js ADDED
@@ -0,0 +1,14 @@
1
+ /** @type {import("jest").Config} **/
2
+ export default {
3
+ preset: "ts-jest/presets/default-esm",
4
+ testPathIgnorePatterns: [
5
+ "<rootDir>/node_modules/",
6
+ "<rootDir>/dist/",
7
+ "<rootDir>/bundle/",
8
+ "<rootDir>/commands/"
9
+ ],
10
+ transform: {
11
+ "^.+\\.tsx?$": ["ts-jest", { useESM: true }],
12
+ },
13
+ testTimeout: 60000,
14
+ };