@ibgib/core-gib 0.1.4 → 0.1.8

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 (156) hide show
  1. package/README.md +26 -0
  2. package/dist/assumptions.respec.mjs.map +1 -1
  3. package/dist/common/alias/alias-helper.mjs +1 -1
  4. package/dist/common/alias/alias-helper.mjs.map +1 -1
  5. package/dist/common/comment/comment-helper.mjs.map +1 -1
  6. package/dist/common/display/display-helper.mjs.map +1 -1
  7. package/dist/common/display/display-types.d.mts +1 -1
  8. package/dist/common/display/display-types.d.mts.map +1 -1
  9. package/dist/common/encrypt/encrypt-helper.mjs.map +1 -1
  10. package/dist/common/encrypt/encrypt-types.d.mts +1 -1
  11. package/dist/common/encrypt/encrypt-types.d.mts.map +1 -1
  12. package/dist/common/error/error-helper.mjs.map +1 -1
  13. package/dist/common/form/form-helper.mjs.map +1 -1
  14. package/dist/common/form/form-items.d.mts.map +1 -1
  15. package/dist/common/import-export/import-export-helper.web.mjs.map +1 -1
  16. package/dist/common/link/link-helper.mjs.map +1 -1
  17. package/dist/common/meta-stone/meta-stone-helper.mjs.map +1 -1
  18. package/dist/common/meta-stone/meta-stone.respec.mjs.map +1 -1
  19. package/dist/common/other/graph-helper.mjs +3 -3
  20. package/dist/common/other/graph-helper.mjs.map +1 -1
  21. package/dist/common/other/ibgib-helper.mjs.map +1 -1
  22. package/dist/common/other/ibgib-helper.respec.mjs.map +1 -1
  23. package/dist/common/other/other-constants.mjs +4 -4
  24. package/dist/common/other/other-constants.mjs.map +1 -1
  25. package/dist/common/other/other-helper.web.mjs.map +1 -1
  26. package/dist/common/other/other-types.d.mts +10 -10
  27. package/dist/common/other/other-types.d.mts.map +1 -1
  28. package/dist/common/other/svg-helper.mjs.map +1 -1
  29. package/dist/common/pic/pic-helper.mjs.map +1 -1
  30. package/dist/common/pubsub/observable/observable-base-v1.mjs +1 -1
  31. package/dist/common/pubsub/observable/observable-base-v1.mjs.map +1 -1
  32. package/dist/common/pubsub/observable/observable-event/observable-event-helper.mjs.map +1 -1
  33. package/dist/common/pubsub/observable/observable-helper.mjs.map +1 -1
  34. package/dist/common/pubsub/observable/observable-types.d.mts +1 -1
  35. package/dist/common/pubsub/observable/observable-types.d.mts.map +1 -1
  36. package/dist/common/pubsub/observer/observer-helper.mjs.map +1 -1
  37. package/dist/common/pubsub/observer/observer-types.d.mts.map +1 -1
  38. package/dist/common/pubsub/subject/subject-helper.mjs.map +1 -1
  39. package/dist/common/pubsub/subject/subject-types.d.mts +1 -1
  40. package/dist/common/pubsub/subject/subject-types.d.mts.map +1 -1
  41. package/dist/common/pubsub/subject/subject-v1.mjs.map +1 -1
  42. package/dist/common/pubsub/subject/subject.respec.mjs.map +1 -1
  43. package/dist/common/pubsub/subscription/subscription-helper.mjs.map +1 -1
  44. package/dist/common/pubsub/subscription/subscription-types.d.mts.map +1 -1
  45. package/dist/common/pubsub/subscription/subscription-v1.mjs.map +1 -1
  46. package/dist/common/secret/secret-helper.mjs.map +1 -1
  47. package/dist/common/secret/secret-types.d.mts +1 -1
  48. package/dist/common/secret/secret-types.d.mts.map +1 -1
  49. package/dist/common/secret/secret.respec.mjs +1 -1
  50. package/dist/common/secret/secret.respec.mjs.map +1 -1
  51. package/dist/common/tag/tag-helper.mjs.map +1 -1
  52. package/dist/core-helper.respec.mjs.map +1 -1
  53. package/dist/keystone/keystone-config-builder.d.mts +77 -0
  54. package/dist/keystone/keystone-config-builder.d.mts.map +1 -0
  55. package/dist/keystone/keystone-config-builder.mjs +157 -0
  56. package/dist/keystone/keystone-config-builder.mjs.map +1 -0
  57. package/dist/keystone/keystone-constants.d.mts +36 -0
  58. package/dist/keystone/keystone-constants.d.mts.map +1 -0
  59. package/dist/keystone/keystone-constants.mjs +39 -0
  60. package/dist/keystone/keystone-constants.mjs.map +1 -0
  61. package/dist/keystone/keystone-helpers.d.mts +117 -0
  62. package/dist/keystone/keystone-helpers.d.mts.map +1 -0
  63. package/dist/keystone/keystone-helpers.mjs +455 -0
  64. package/dist/keystone/keystone-helpers.mjs.map +1 -0
  65. package/dist/keystone/keystone-service-v1.d.mts +77 -0
  66. package/dist/keystone/keystone-service-v1.d.mts.map +1 -0
  67. package/dist/keystone/keystone-service-v1.mjs +502 -0
  68. package/dist/keystone/keystone-service-v1.mjs.map +1 -0
  69. package/dist/keystone/keystone-service-v1.respec.d.mts +2 -0
  70. package/dist/keystone/keystone-service-v1.respec.d.mts.map +1 -0
  71. package/dist/keystone/keystone-service-v1.respec.mjs +460 -0
  72. package/dist/keystone/keystone-service-v1.respec.mjs.map +1 -0
  73. package/dist/keystone/keystone-types.d.mts +248 -0
  74. package/dist/keystone/keystone-types.d.mts.map +1 -0
  75. package/dist/keystone/keystone-types.mjs +50 -0
  76. package/dist/keystone/keystone-types.mjs.map +1 -0
  77. package/dist/keystone/strategy/hash-reveal-v1/hash-reveal-v1.d.mts +35 -0
  78. package/dist/keystone/strategy/hash-reveal-v1/hash-reveal-v1.d.mts.map +1 -0
  79. package/dist/keystone/strategy/hash-reveal-v1/hash-reveal-v1.mjs +107 -0
  80. package/dist/keystone/strategy/hash-reveal-v1/hash-reveal-v1.mjs.map +1 -0
  81. package/dist/keystone/strategy/keystone-strategy-factory.d.mts +15 -0
  82. package/dist/keystone/strategy/keystone-strategy-factory.d.mts.map +1 -0
  83. package/dist/keystone/strategy/keystone-strategy-factory.mjs +26 -0
  84. package/dist/keystone/strategy/keystone-strategy-factory.mjs.map +1 -0
  85. package/dist/keystone/strategy/keystone-strategy.d.mts +48 -0
  86. package/dist/keystone/strategy/keystone-strategy.d.mts.map +1 -0
  87. package/dist/keystone/strategy/keystone-strategy.mjs +14 -0
  88. package/dist/keystone/strategy/keystone-strategy.mjs.map +1 -0
  89. package/dist/respec-gib.node.mjs +3 -1
  90. package/dist/respec-gib.node.mjs.map +1 -1
  91. package/dist/spec-helper.node.respec.d.mts.map +1 -1
  92. package/dist/spec-helper.node.respec.mjs +4 -6
  93. package/dist/spec-helper.node.respec.mjs.map +1 -1
  94. package/dist/timeline/timeline-api.mjs +12 -12
  95. package/dist/timeline/timeline-api.mjs.map +1 -1
  96. package/dist/witness/anonymous-fn/anonymous-fn-helper.mjs.map +1 -1
  97. package/dist/witness/anonymous-fn/anonymous-fn-v1.mjs.map +1 -1
  98. package/dist/witness/app/app-base-v1.mjs.map +1 -1
  99. package/dist/witness/app/app-helper.mjs.map +1 -1
  100. package/dist/witness/app/app-types.d.mts.map +1 -1
  101. package/dist/witness/factory/dynamic-form-factory-base.mjs.map +1 -1
  102. package/dist/witness/light-witness-base-v1.mjs.map +1 -1
  103. package/dist/witness/robbot/robbot-base-v1.mjs +1 -1
  104. package/dist/witness/robbot/robbot-base-v1.mjs.map +1 -1
  105. package/dist/witness/robbot/robbot-helper.mjs.map +1 -1
  106. package/dist/witness/robbot/robbot-types.d.mts +20 -20
  107. package/dist/witness/robbot/robbot-types.d.mts.map +1 -1
  108. package/dist/witness/space/bootstrap/bootstrap-helper.mjs.map +1 -1
  109. package/dist/witness/space/filesystem-space/filesystem-space-v1.mjs.map +1 -1
  110. package/dist/witness/space/filesystem-space/filesystem-space-v1.respec.mjs.map +1 -1
  111. package/dist/witness/space/filesystem-space/node-filesystem-space/node-filesystem-space-helper.mjs.map +1 -1
  112. package/dist/witness/space/filesystem-space/node-filesystem-space/node-filesystem-space-types.d.mts.map +1 -1
  113. package/dist/witness/space/filesystem-space/node-filesystem-space/node-filesystem-space-v1.mjs +1 -1
  114. package/dist/witness/space/filesystem-space/node-filesystem-space/node-filesystem-space-v1.mjs.map +1 -1
  115. package/dist/witness/space/filesystem-space/node-filesystem-space/respec/testSpace_createAndInit.node-filesystem-space-v1.respec.mjs.map +1 -1
  116. package/dist/witness/space/filesystem-space/node-filesystem-space/respec/testSpace_persistTransformResult.node-filesystem-space-v1.respec.mjs.map +1 -1
  117. package/dist/witness/space/filesystem-space/node-filesystem-space/respec/testSpace_putGetDelete.node-filesystem-space-v1.respec.mjs.map +1 -1
  118. package/dist/witness/space/filesystem-space/node-filesystem-space/respec/testSpace_registerNewIbGib_GetLatest.node-filesystem-space-v1.respec.mjs.map +1 -1
  119. package/dist/witness/space/inner-space/inner-space-v1.mjs.map +1 -1
  120. package/dist/witness/space/inner-space/inner-space-v1.respec.mjs.map +1 -1
  121. package/dist/witness/space/metaspace/metaspace-base.mjs +1 -1
  122. package/dist/witness/space/metaspace/metaspace-base.mjs.map +1 -1
  123. package/dist/witness/space/metaspace/metaspace-innerspace/metaspace-innerspace-helper.mjs.map +1 -1
  124. package/dist/witness/space/metaspace/metaspace-innerspace/metaspace-innerspace.mjs.map +1 -1
  125. package/dist/witness/space/outer-space/outer-space-helper.mjs.map +1 -1
  126. package/dist/witness/space/outer-space/outer-space-types.d.mts.map +1 -1
  127. package/dist/witness/space/outer-space/outer-space-types.mjs +1 -1
  128. package/dist/witness/space/outer-space/outer-space-types.mjs.map +1 -1
  129. package/dist/witness/space/reconciliation-space/reconciliation-space-base.mjs.map +1 -1
  130. package/dist/witness/space/reconciliation-space/reconciliation-space-helper.mjs.map +1 -1
  131. package/dist/witness/space/space-base-v1.mjs.map +1 -1
  132. package/dist/witness/space/space-constants.mjs +4 -4
  133. package/dist/witness/space/space-constants.mjs.map +1 -1
  134. package/dist/witness/space/space-helper.mjs +2 -2
  135. package/dist/witness/space/space-helper.mjs.map +1 -1
  136. package/dist/witness/space/space-respec-helper.mjs.map +1 -1
  137. package/dist/witness/space/space-types.d.mts +4 -4
  138. package/dist/witness/space/space-types.d.mts.map +1 -1
  139. package/dist/witness/witness-base-v1.mjs.map +1 -1
  140. package/dist/witness/witness-form-builder.mjs.map +1 -1
  141. package/dist/witness/witness-helper.mjs.map +1 -1
  142. package/dist/witness/witness-with-context/witness-with-context-base-v1.mjs.map +1 -1
  143. package/package.json +6 -5
  144. package/src/keystone/README.md +162 -0
  145. package/src/keystone/keystone-config-builder.mts +187 -0
  146. package/src/keystone/keystone-constants.mts +44 -0
  147. package/src/keystone/keystone-helpers.mts +571 -0
  148. package/src/keystone/keystone-service-v1.mts +611 -0
  149. package/src/keystone/keystone-service-v1.respec.mts +555 -0
  150. package/src/keystone/keystone-types.mts +315 -0
  151. package/src/keystone/strategy/hash-reveal-v1/hash-reveal-v1.mts +146 -0
  152. package/src/keystone/strategy/keystone-strategy-factory.mts +35 -0
  153. package/src/keystone/strategy/keystone-strategy.mts +71 -0
  154. package/src/respec-gib.node.mts +3 -1
  155. package/src/spec-helper.node.respec.mts +4 -6
  156. package/src/witness/robbot/robbot-base-v1.mts +1 -1
@@ -0,0 +1,315 @@
1
+ import { IbGib_V1, IbGibData_V1, IbGibRel8ns_V1 } from "@ibgib/ts-gib/dist/V1/types.mjs";
2
+
3
+ import { KEYSTONE_ATOM } from "./keystone-constants.mjs";
4
+
5
+ /**
6
+ * The discriminator for the mechanism.
7
+ * 'hash-reveal-v1': Standard Hash chain (Sigma-like).
8
+ */
9
+ export type KeystoneChallengeType =
10
+ | 'hash-reveal-v1'
11
+ // | 'decrypt-v1' // Future
12
+ // | 'pow-v1'; // Future
13
+ ;
14
+
15
+ // ===========================================================================
16
+ // CONFIGURATION
17
+ // ===========================================================================
18
+
19
+ // #region KeystoneReplenishStrategy
20
+ /**
21
+ * replaces each used challenge, "topping up" the pool to the pool's size
22
+ */
23
+ export const KEYSTONE_REPLENISH_STRATEGY_TOP_UP = 'top-up';
24
+ /**
25
+ * replaces the entire pool with the new challenges
26
+ */
27
+ export const KEYSTONE_REPLENISH_STRATEGY_REPLACE_ALL = 'replace-all';
28
+ /**
29
+ * do not replenish, only consume
30
+ *
31
+ * ## intent
32
+ * adding this for revocation
33
+ */
34
+ export const KEYSTONE_REPLENISH_STRATEGY_CONSUME = 'consume';
35
+ /**
36
+ * Deletes ALL challenges in the pool, regardless of how many were used.
37
+ * The "Nuclear Option" for revocation.
38
+ */
39
+ export const KEYSTONE_REPLENISH_STRATEGY_SCORCHED_EARTH = 'scorched-earth';
40
+ export type KeystoneReplenishStrategy =
41
+ | typeof KEYSTONE_REPLENISH_STRATEGY_TOP_UP
42
+ | typeof KEYSTONE_REPLENISH_STRATEGY_REPLACE_ALL
43
+ | typeof KEYSTONE_REPLENISH_STRATEGY_CONSUME
44
+ | typeof KEYSTONE_REPLENISH_STRATEGY_SCORCHED_EARTH
45
+ ;
46
+ /**
47
+ * @see {@link KeystonePoolBehavior.replenish}
48
+ */
49
+ export const KeystoneReplenishStrategy = {
50
+ /**
51
+ * @see {@link KEYSTONE_REPLENISH_STRATEGY_TOP_UP}
52
+ */
53
+ topUp: KEYSTONE_REPLENISH_STRATEGY_TOP_UP,
54
+ /**
55
+ * @see {@link KEYSTONE_REPLENISH_STRATEGY_REPLACE_ALL}
56
+ */
57
+ replaceAll: KEYSTONE_REPLENISH_STRATEGY_REPLACE_ALL,
58
+ /**
59
+ * @see {@link KEYSTONE_REPLENISH_STRATEGY_CONSUME}
60
+ */
61
+ consume: KEYSTONE_REPLENISH_STRATEGY_CONSUME,
62
+ /**
63
+ * @see {@link KEYSTONE_REPLENISH_STRATEGY_SCORCHED_EARTH}
64
+ */
65
+ scorchedEarth: KEYSTONE_REPLENISH_STRATEGY_SCORCHED_EARTH,
66
+ } satisfies { [key: string]: KeystoneReplenishStrategy };
67
+ export const KEYSTONE_REPLENISH_STRATEGY_VALID_VALUES = Object.values(KeystoneReplenishStrategy);
68
+ export function isKeystoneReplenishStrategy(x: any): x is KeystoneReplenishStrategy {
69
+ return KEYSTONE_REPLENISH_STRATEGY_VALID_VALUES.includes(x);
70
+ }
71
+ // #endregion KeystoneReplenishStrategy
72
+
73
+ export interface KeystonePoolBehavior {
74
+ /**
75
+ * Target number of challenges to maintain in the pool.
76
+ */
77
+ size: number;
78
+
79
+ /**
80
+ * How do we fill the void left by consumed challenges?
81
+ */
82
+ replenish: KeystoneReplenishStrategy;
83
+
84
+ /**
85
+ * Minimum number of challenges to consume from the "front" (oldest) of the pool.
86
+ * Mitigates sequence prediction attacks if high, allows strictly ordered audit if used alone.
87
+ */
88
+ selectSequentially: number;
89
+
90
+ /**
91
+ * Minimum number of challenges to consume randomly from the remainder.
92
+ * Mitigates pre-computation attacks on the sequence.
93
+ */
94
+ selectRandomly: number;
95
+
96
+ /**
97
+ * Number of hex characters from the Target's Gib to match.
98
+ * @default 0
99
+ */
100
+ targetBindingChars: number;
101
+ }
102
+
103
+ export interface KeystonePoolConfigBase {
104
+ /**
105
+ * The ID of the pool this config belongs to.
106
+ */
107
+ id: string;
108
+
109
+ type: KeystoneChallengeType;
110
+ /**
111
+ * Unique salt for this pool's derivation path from the Master Secret.
112
+ */
113
+ salt: string;
114
+ behavior: KeystonePoolBehavior;
115
+ /**
116
+ * The list of Verbs (primitive ibGib addresses) this pool is authorized to sign.
117
+ * e.g. ["revoke^gib", "admin^gib"]
118
+ *
119
+ * If undefined or empty, this pool is considered a "General/Default" pool
120
+ * and can sign any verb NOT explicitly claimed by another pool (implementation detail of selection)
121
+ * or simply any verb at all (permissive).
122
+ *
123
+ * For V1 Security: If this is set, Validation MUST enforce it.
124
+ */
125
+ allowedVerbs: string[];
126
+ }
127
+
128
+ export interface KeystonePoolConfig_HashV1 extends KeystonePoolConfigBase {
129
+ type: 'hash-reveal-v1';
130
+ algo: 'SHA-256' | 'SHA-512';
131
+ rounds: number;
132
+ }
133
+
134
+ export type KeystonePoolConfig = KeystonePoolConfig_HashV1;
135
+
136
+ // ===========================================================================
137
+ // CHALLENGES (Public Puzzles)
138
+ // ===========================================================================
139
+
140
+ export interface KeystoneChallengeBase {
141
+ type: KeystoneChallengeType;
142
+ }
143
+
144
+ export interface KeystoneChallenge_HashV1 extends KeystoneChallengeBase {
145
+ id: string;
146
+ type: 'hash-reveal-v1';
147
+ /**
148
+ * The hash that must be matched by the solution.
149
+ */
150
+ hash: string;
151
+ }
152
+
153
+ export type KeystoneChallenge = KeystoneChallenge_HashV1;
154
+
155
+ // ===========================================================================
156
+ // SOLUTIONS (Private Answers revealed in Proofs)
157
+ // ===========================================================================
158
+
159
+ export interface KeystoneSolutionBase {
160
+ type: KeystoneChallengeType;
161
+ /**
162
+ * The ID of the pool this solution comes from.
163
+ */
164
+ poolId: string;
165
+ /**
166
+ * The ID of the specific challenge being solved.
167
+ */
168
+ challengeId: string;
169
+ }
170
+
171
+ export interface KeystoneSolution_HashV1 extends KeystoneSolutionBase {
172
+ type: 'hash-reveal-v1';
173
+ /**
174
+ * The Pre-image value.
175
+ */
176
+ value: string;
177
+ }
178
+
179
+ export type KeystoneSolution = KeystoneSolution_HashV1;
180
+
181
+ // ===========================================================================
182
+ // HIGH-LEVEL STRUCTURES
183
+ // ===========================================================================
184
+
185
+ /**
186
+ * A container for a set of challenges.
187
+ */
188
+ export interface KeystoneChallengePool {
189
+ /**
190
+ * Unique ID (e.g. "default", "admin").
191
+ */
192
+ id: string;
193
+
194
+ /**
195
+ * Parameterization of this pool.
196
+ *
197
+ * Signing and validating this pool must observe this config.
198
+ */
199
+ config: KeystonePoolConfig;
200
+
201
+ /**
202
+ * Default claim values for this pool.
203
+ * Useful for "verb-stones".
204
+ */
205
+ defaultClaim?: Partial<KeystoneClaim>;
206
+
207
+ /**
208
+ * The currently active challenges.
209
+ * Key: The unique Challenge ID (e.g. "poolSalt_0").
210
+ */
211
+ challenges: { [challengeId: string]: KeystoneChallenge };
212
+
213
+ /**
214
+ * Explicit Buckets for Target Binding.
215
+ * Key: Hex Character ('0'-'f').
216
+ * Value: Array of Challenge IDs that satisfy this bucket.
217
+ * Note: A single ID may appear in multiple buckets (Coverage Strategy).
218
+ */
219
+ bindingMap: { [hexChar: string]: string[] };
220
+ }
221
+
222
+ /**
223
+ * Semantic intent.
224
+ */
225
+ export interface KeystoneClaim {
226
+ target: string; // ibGib address
227
+ verb: string; // ibGib address (primitive)
228
+ scope?: string; // ibGib address (primitive)
229
+ }
230
+
231
+ /**
232
+ * Authorization Proof.
233
+ */
234
+ export interface KeystoneProof {
235
+ id?: string;
236
+
237
+ /**
238
+ * The claim being made.
239
+ */
240
+ claim: Partial<KeystoneClaim>;
241
+
242
+ /**
243
+ * The solutions required to validate this claim.
244
+ */
245
+ solutions: KeystoneSolution[];
246
+
247
+ /**
248
+ * The list of specific Challenge IDs that were mandatorily requested
249
+ * by the verifier/context during the signing process.
250
+ * Essential for deterministic validation.
251
+ */
252
+ requiredChallengeIds?: string[];
253
+ }
254
+
255
+ /**
256
+ * Revocation Context.
257
+ */
258
+ export interface KeystoneRevocationInfo {
259
+ reason: string;
260
+ proof: KeystoneProof;
261
+ }
262
+
263
+ // ===========================================================================
264
+ // TOP LEVEL IBGIB DATA
265
+ // ===========================================================================
266
+
267
+ export interface KeystoneIbInfo_V1 {
268
+ atom: typeof KEYSTONE_ATOM;
269
+ }
270
+
271
+ export interface KeystoneData_V1 extends IbGibData_V1 {
272
+ /**
273
+ * The pools containing the FUTURE challenges.
274
+ * (Always topped up in V1 implementation).
275
+ */
276
+ challengePools: KeystoneChallengePool[];
277
+
278
+ /**
279
+ * The proofs authorizing THIS frame's evolution.
280
+ */
281
+ proofs: KeystoneProof[];
282
+
283
+ /**
284
+ * If present, this Keystone is dead.
285
+ */
286
+ revocationInfo?: KeystoneRevocationInfo;
287
+
288
+ /**
289
+ * Ephemeral details specific to this frame's creation context.
290
+ * Meant to be observed on this frame, but NOT automatically carried forward
291
+ * to the next frame's data during evolution.
292
+ */
293
+ frameDetails?: any;
294
+ }
295
+
296
+ export interface KeystoneRel8ns_V1 extends IbGibRel8ns_V1 {
297
+ // Standard ibGib relations (ancestor, past, etc.)
298
+ // Specific hard-links for composite keystones go here later.
299
+ }
300
+
301
+ export interface KeystoneIbGib_V1 extends IbGib_V1<KeystoneData_V1, KeystoneRel8ns_V1> { }
302
+
303
+ export interface DeterministicResult {
304
+ /**
305
+ * The Set of IDs that MUST be present in the solution.
306
+ * Includes Alice's Demands + Target Binding Matches + FIFO.
307
+ */
308
+ mandatoryIds: Set<string>;
309
+
310
+ /**
311
+ * The IDs remaining in the pool that are valid candidates for
312
+ * the Random/Stochastic step.
313
+ */
314
+ availableIds: string[];
315
+ }
@@ -0,0 +1,146 @@
1
+ import { hash } from '@ibgib/helper-gib/dist/helpers/utils-helper.mjs';
2
+ import { KeystoneStrategy } from '../keystone-strategy.mjs';
3
+ import {
4
+ KeystonePoolConfig_HashV1,
5
+ KeystoneChallenge_HashV1,
6
+ KeystoneSolution_HashV1
7
+ } from '../../keystone-types.mjs';
8
+
9
+ /**
10
+ * The concrete implementation of the "Salted Wrap" Hash Reveal strategy.
11
+ */
12
+ export class KeystoneStrategy_HashRevealV1 extends KeystoneStrategy<
13
+ KeystonePoolConfig_HashV1,
14
+ KeystoneChallenge_HashV1,
15
+ KeystoneSolution_HashV1
16
+ > {
17
+
18
+ /**
19
+ * Derives Pool Secret = Hash(PoolSalt + MasterSecret + PoolSalt) ^ Rounds
20
+ */
21
+ override async derivePoolSecret({
22
+ masterSecret
23
+ }: {
24
+ masterSecret: string
25
+ }): Promise<string> {
26
+ const lc = `[${KeystoneStrategy_HashRevealV1.name}.${this.derivePoolSecret.name}]`;
27
+ try {
28
+ const { salt, rounds, algo } = this.config;
29
+ // Map algo string to HashAlgorithm type if needed,
30
+ // assuming config.algo matches the helper's expected inputs.
31
+
32
+ let current = masterSecret;
33
+ for (let i = 0; i < rounds; i++) {
34
+ current = await hash({
35
+ s: `${salt}${current}${salt}`,
36
+ algorithm: algo
37
+ });
38
+ }
39
+ return current;
40
+ } catch (error) {
41
+ console.error(`${lc} Error deriving pool secret: ${error.message}`);
42
+ throw error;
43
+ }
44
+ }
45
+
46
+ /**
47
+ * Solution Value = Hash(IndexSalt + PoolSecret + IndexSalt) ^ Rounds
48
+ */
49
+ override async generateSolution({
50
+ poolSecret,
51
+ poolId,
52
+ challengeId,
53
+ }: {
54
+ poolSecret: string;
55
+ poolId: string;
56
+ challengeId: string;
57
+ }): Promise<KeystoneSolution_HashV1> {
58
+ const lc = `[${KeystoneStrategy_HashRevealV1.name}.${this.generateSolution.name}]`;
59
+ try {
60
+ const { rounds, algo } = this.config;
61
+
62
+ // The Index Salt is the unique identifier for this slot
63
+ const indexSalt = challengeId;
64
+
65
+ let current = poolSecret;
66
+ for (let i = 0; i < rounds; i++) {
67
+ current = await hash({
68
+ s: `${indexSalt}${current}${indexSalt}`,
69
+ algorithm: algo
70
+ });
71
+ }
72
+
73
+ return {
74
+ type: 'hash-reveal-v1',
75
+ poolId,
76
+ challengeId,
77
+ value: current
78
+ };
79
+ } catch (error) {
80
+ console.error(`${lc} ${error.message}`);
81
+ throw error;
82
+ }
83
+ }
84
+
85
+ /**
86
+ * Challenge Hash = Hash(IndexSalt + SolutionValue + IndexSalt) ^ Rounds
87
+ */
88
+ override async generateChallenge({
89
+ solution,
90
+ }: {
91
+ solution: KeystoneSolution_HashV1;
92
+ }): Promise<KeystoneChallenge_HashV1> {
93
+ const lc = `[${KeystoneStrategy_HashRevealV1.name}.${this.generateChallenge.name}]`;
94
+ try {
95
+ const { rounds, algo } = this.config;
96
+ const { challengeId, value } = solution;
97
+ const indexSalt = challengeId;
98
+
99
+ let current = value;
100
+ for (let i = 0; i < rounds; i++) {
101
+ current = await hash({
102
+ s: `${indexSalt}${current}${indexSalt}`,
103
+ algorithm: algo
104
+ });
105
+ }
106
+
107
+ return {
108
+ id: challengeId,
109
+ type: 'hash-reveal-v1',
110
+ hash: current
111
+ };
112
+ } catch (error) {
113
+ console.error(`${lc} ${error.message}`);
114
+ throw error;
115
+ }
116
+ }
117
+
118
+ /**
119
+ * Re-generates the challenge from the candidate solution and compares.
120
+ */
121
+ override async validateSolution({
122
+ solution,
123
+ challenge,
124
+ }: {
125
+ solution: KeystoneSolution_HashV1;
126
+ challenge: KeystoneChallenge_HashV1;
127
+ }): Promise<boolean> {
128
+ const lc = `[${KeystoneStrategy_HashRevealV1.name}.${this.validateSolution.name}]`;
129
+ try {
130
+ // 1. Check Type Compatibility
131
+ if (solution.type !== 'hash-reveal-v1' || challenge.type !== 'hash-reveal-v1') {
132
+ console.warn(`${lc} Mismatched types provided.`);
133
+ return false;
134
+ }
135
+
136
+ // 2. Generate the expected challenge hash from the solution provided
137
+ const calculatedChallenge = await this.generateChallenge({ solution });
138
+
139
+ // 3. Compare
140
+ return calculatedChallenge.hash === challenge.hash;
141
+ } catch (error) {
142
+ console.error(`${lc} ${error.message}`);
143
+ return false; // Fail closed
144
+ }
145
+ }
146
+ }
@@ -0,0 +1,35 @@
1
+ import {
2
+ KeystonePoolConfig
3
+ } from '../keystone-types.mjs';
4
+ import { KeystoneStrategyAny } from './keystone-strategy.mjs';
5
+ import { KeystoneStrategy_HashRevealV1 } from './hash-reveal-v1/hash-reveal-v1.mjs';
6
+
7
+ export class KeystoneStrategyFactory {
8
+
9
+ /**
10
+ * Instantiates the appropriate concrete KeystoneStrategy based on the
11
+ * provided configuration type.
12
+ *
13
+ * @param config The configuration object for the pool (contains 'type').
14
+ * @returns An instance of the specific strategy class.
15
+ */
16
+ static create({
17
+ config,
18
+ }: {
19
+ config: KeystonePoolConfig,
20
+ }): KeystoneStrategyAny {
21
+ const lc = `[${KeystoneStrategyFactory.name}.create]`;
22
+ try {
23
+ switch (config.type) {
24
+ case 'hash-reveal-v1':
25
+ return new KeystoneStrategy_HashRevealV1(config);
26
+
27
+ default:
28
+ throw new Error(`Unknown strategy type: ${(config as any).type} (E: 4e3c2f7129a241c1b687555e678c1065)`);
29
+ }
30
+ } catch (error) {
31
+ console.error(`${lc} ${error.message}`);
32
+ throw error;
33
+ }
34
+ }
35
+ }
@@ -0,0 +1,71 @@
1
+ import {
2
+ KeystonePoolConfigBase,
3
+ KeystoneChallengeBase,
4
+ KeystoneSolutionBase
5
+ } from '../keystone-types.mjs';
6
+
7
+ /**
8
+ * Abstract base class for all Keystone Challenge Strategies.
9
+ *
10
+ * @template TConfig The specific configuration interface (e.g. HashV1).
11
+ * @template TChallenge The specific public challenge interface.
12
+ * @template TSolution The specific private solution interface.
13
+ */
14
+ export abstract class KeystoneStrategy<
15
+ TConfig extends KeystonePoolConfigBase,
16
+ TChallenge extends KeystoneChallengeBase,
17
+ TSolution extends KeystoneSolutionBase
18
+ > {
19
+ constructor(protected config: TConfig) {}
20
+
21
+ /**
22
+ * Derives the secret specific to this pool from the master keystone secret.
23
+ * This isolates the pool so the master secret is never used directly
24
+ * in challenge generation.
25
+ */
26
+ abstract derivePoolSecret({
27
+ masterSecret
28
+ }: {
29
+ masterSecret: string
30
+ }): Promise<string>;
31
+
32
+ /**
33
+ * Generates the private solution (Pre-image) for a specific challenge ID.
34
+ *
35
+ * @returns The concrete solution object (not just the value string).
36
+ */
37
+ abstract generateSolution({
38
+ poolSecret,
39
+ poolId,
40
+ challengeId,
41
+ }: {
42
+ poolSecret: string;
43
+ poolId: string;
44
+ challengeId: string;
45
+ }): Promise<TSolution>;
46
+
47
+ /**
48
+ * Generates the public challenge from a given solution.
49
+ * Used when creating the pool (Top Up) or verifying a solution.
50
+ */
51
+ abstract generateChallenge({
52
+ solution,
53
+ }: {
54
+ solution: TSolution;
55
+ }): Promise<TChallenge>;
56
+
57
+ /**
58
+ * Validates that a given solution mathematically solves the given challenge.
59
+ *
60
+ * @returns true if valid, false otherwise.
61
+ */
62
+ abstract validateSolution({
63
+ solution,
64
+ challenge,
65
+ }: {
66
+ solution: TSolution;
67
+ challenge: TChallenge;
68
+ }): Promise<boolean>;
69
+ }
70
+
71
+ export type KeystoneStrategyAny = KeystoneStrategy<any,any,any>;
@@ -1,4 +1,5 @@
1
1
  import { readdir, open } from 'node:fs/promises';
2
+ import { pathToFileURL } from 'node:url';
2
3
  import { statSync } from 'node:fs';
3
4
  import * as pathUtils from 'path';
4
5
 
@@ -95,7 +96,8 @@ if (logalot) { console.log(`respecPaths found:\n${respecPaths}`); }
95
96
  for (let i = 0; i < respecPaths.length; i++) {
96
97
  const respecPath = respecPaths[i];
97
98
  if (logalot) { console.log(respecPath); }
98
- const esm = await import(respecPath);
99
+ const respecPathUrl = pathToFileURL(respecPath).href;
100
+ const esm = await import(respecPathUrl);
99
101
  if (logalot) { console.log(pretty(Object.keys(esm))); }
100
102
  }
101
103
 
@@ -1,4 +1,5 @@
1
1
  import { default as pathUtils } from 'path';
2
+ import { fileURLToPath } from 'node:url';
2
3
 
3
4
  import { delay, getUUID, } from '@ibgib/helper-gib/dist/helpers/utils-helper.mjs';
4
5
 
@@ -11,12 +12,9 @@ import { delay, getUUID, } from '@ibgib/helper-gib/dist/helpers/utils-helper.mjs
11
12
  export async function getCurrentFilename(importMetaUrl: string): Promise<string> {
12
13
  const lc = `[${getCurrentFilename.name}]`;
13
14
  try {
14
- const pieces = importMetaUrl.split(pathUtils.sep);
15
- let filename = pieces.at(-1)?.replace(/\.respec\.mjs$/, '')
16
- if (!filename) {
17
- console.warn(`filename not able to be gotten?`);
18
- filename = (new Date()).toTimeString() + (await getUUID());
19
- }
15
+ const filePath = fileURLToPath(importMetaUrl);
16
+ const filenameWithExt = pathUtils.basename(filePath);
17
+ const filename = filenameWithExt.replace(/\.respec\.mjs$/, '');
20
18
  return `ibgib${pathUtils.sep}${filename}`;
21
19
  } catch (error) {
22
20
  console.error(`${lc} ${error.message}`);
@@ -694,7 +694,7 @@ export abstract class RobbotBase_V1<
694
694
  // todo: adjust to use the cacheIbGibs (not get them if already have in cache, but still return them in this fn's result)
695
695
  for (let i = 0; i < rel8nNames.length; i++) {
696
696
  const rel8nName = rel8nNames[i];
697
- const rel8dAddrs: IbGibAddr[] = this.rel8ns ? (this.rel8ns[rel8nName] ?? []) : undefined ?? [];
697
+ const rel8dAddrs: IbGibAddr[] = this.rel8ns?.[rel8nName] ?? [];
698
698
 
699
699
  if (rel8dAddrs.length > 0) {
700
700
  const resGet = await getFromSpace({ addrs: rel8dAddrs, space });