@acala-network/chopsticks-testing 1.2.0 → 1.2.1

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
@@ -26,6 +26,12 @@ export type RedactOptions = {
26
26
  removeKeys?: RegExp;
27
27
  /** Regex pattern for keys that should not be redacted */
28
28
  noRedactKeys?: RegExp;
29
+ /** Redact options for specific keys */
30
+ overrides?: Record<string, RedactOptions>;
31
+ noRedact?: false;
32
+ } | {
33
+ /** Do not redact any values */
34
+ noRedact: true;
29
35
  };
30
36
  /**
31
37
  * Function type for test assertions
@@ -107,6 +113,31 @@ export declare class Checker {
107
113
  */
108
114
  toMatchObject(value: any, msg?: string): Promise<void>;
109
115
  }
116
+ /**
117
+ * Creates a set of checking utilities with provided options
118
+ * @param options - Options for setting up checks
119
+ * @returns Object containing various checking utilities
120
+ */
121
+ export declare const setupCheck: (options: {
122
+ expectFn: ExpectFn;
123
+ redactOptions?: RedactOptions;
124
+ extraCheck?: (value: any) => Promise<void> | void;
125
+ }) => {
126
+ check: (value: any, msg?: string) => Checker;
127
+ checkEvents: ({ events }: {
128
+ events: Promise<Codec[] | Codec>;
129
+ }, ...filters: EventFilter[]) => Checker;
130
+ checkSystemEvents: ({ api }: {
131
+ api: ApiPromise;
132
+ }, ...filters: EventFilter[]) => Checker;
133
+ checkUmp: ({ api }: {
134
+ api: ApiPromise;
135
+ }) => Checker;
136
+ checkHrmp: ({ api }: {
137
+ api: ApiPromise;
138
+ }) => Checker;
139
+ checkHex: (value: any, msg?: string) => Checker;
140
+ };
110
141
  /**
111
142
  * Creates a set of checking utilities with a provided assertion function
112
143
  * @param expectFn - Function for making test assertions
package/dist/cjs/check.js CHANGED
@@ -12,6 +12,9 @@ _export(exports, {
12
12
  get Checker () {
13
13
  return Checker;
14
14
  },
15
+ get setupCheck () {
16
+ return setupCheck;
17
+ },
15
18
  get withExpect () {
16
19
  return withExpect;
17
20
  }
@@ -84,7 +87,7 @@ function _class_private_method_init(obj, privateSet) {
84
87
  * Converts Codec data to JSON format
85
88
  * @param codec - Codec data to convert
86
89
  */ const toJson = (codec)=>processCodecOrArray(codec, (c)=>c?.toJSON?.() ?? c);
87
- var _expectFn = /*#__PURE__*/ new WeakMap(), _value = /*#__PURE__*/ new WeakMap(), _pipeline = /*#__PURE__*/ new WeakMap(), _extraChecks = /*#__PURE__*/ new WeakMap(), _format = /*#__PURE__*/ new WeakMap(), _message = /*#__PURE__*/ new WeakMap(), _redactOptions = /*#__PURE__*/ new WeakMap(), _redact = /*#__PURE__*/ new WeakSet();
90
+ var _expectFn = /*#__PURE__*/ new WeakMap(), _value = /*#__PURE__*/ new WeakMap(), _pipeline = /*#__PURE__*/ new WeakMap(), _extraChecks = /*#__PURE__*/ new WeakMap(), _format = /*#__PURE__*/ new WeakMap(), _message = /*#__PURE__*/ new WeakMap(), _redactOptions = /*#__PURE__*/ new WeakMap(), _redact = /*#__PURE__*/ new WeakSet(), __redact = /*#__PURE__*/ new WeakSet();
88
91
  class Checker {
89
92
  /** Convert the checked value to human-readable format */ toHuman() {
90
93
  _class_private_field_set(this, _format, 'human');
@@ -136,10 +139,14 @@ class Checker {
136
139
  number: 2,
137
140
  hash: true
138
141
  }) {
139
- _class_private_field_set(this, _redactOptions, {
140
- ..._class_private_field_get(this, _redactOptions),
141
- ...options
142
- });
142
+ if (options.noRedact) {
143
+ _class_private_field_set(this, _redactOptions, undefined);
144
+ } else {
145
+ _class_private_field_set(this, _redactOptions, {
146
+ ..._class_private_field_get(this, _redactOptions),
147
+ ...options
148
+ });
149
+ }
143
150
  return this;
144
151
  }
145
152
  /**
@@ -214,6 +221,7 @@ class Checker {
214
221
  * @param message - Optional message for assertions
215
222
  */ constructor(expectFn, value, message){
216
223
  _class_private_method_init(this, _redact);
224
+ _class_private_method_init(this, __redact);
217
225
  _class_private_field_init(this, _expectFn, {
218
226
  writable: true,
219
227
  value: void 0
@@ -251,11 +259,23 @@ function redact(value) {
251
259
  if (!_class_private_field_get(this, _redactOptions)) {
252
260
  return value;
253
261
  }
254
- const redactNumber = _class_private_field_get(this, _redactOptions).number === true || typeof _class_private_field_get(this, _redactOptions).number === 'number';
255
- const precision = redactNumber ? typeof _class_private_field_get(this, _redactOptions).number === 'number' ? _class_private_field_get(this, _redactOptions).number : 0 : 0;
256
- const redactHash = _class_private_field_get(this, _redactOptions).hash === true;
257
- const redactHex = _class_private_field_get(this, _redactOptions).hex === true;
258
- const redactAddress = _class_private_field_get(this, _redactOptions).address === true;
262
+ return _class_private_method_get(this, __redact, _redact).call(this, value, _class_private_field_get(this, _redactOptions), 50);
263
+ }
264
+ function _redact(obj, options, depth) {
265
+ if (depth <= 0) {
266
+ return obj;
267
+ }
268
+ if (obj == null) {
269
+ return obj;
270
+ }
271
+ if (options.noRedact) {
272
+ return obj;
273
+ }
274
+ const redactNumber = options.number === true || typeof options.number === 'number';
275
+ const precision = redactNumber ? typeof options.number === 'number' ? options.number : 0 : 0;
276
+ const redactHash = options.hash === true;
277
+ const redactHex = options.hex === true;
278
+ const redactAddress = options.address === true;
259
279
  const processNumber = (value)=>{
260
280
  if (precision > 0) {
261
281
  const rounded = Number.parseFloat(value.toPrecision(precision));
@@ -266,82 +286,89 @@ function redact(value) {
266
286
  }
267
287
  return '(number)';
268
288
  };
269
- const process = (obj, depth)=>{
270
- if (depth <= 0) {
271
- return obj;
289
+ if (Array.isArray(obj)) {
290
+ return obj.map((x)=>_class_private_method_get(this, __redact, _redact).call(this, x, options, depth - 1));
291
+ }
292
+ if (redactNumber && typeof obj === 'number') {
293
+ return processNumber(obj);
294
+ }
295
+ if (typeof obj === 'string') {
296
+ if (redactNumber && obj.match(/0x000000[0-9a-f]{26}/)) {
297
+ // this is very likely u128 encoded in hex
298
+ const num = Number.parseInt(obj);
299
+ return processNumber(num);
272
300
  }
273
- if (obj == null) {
274
- return obj;
301
+ if (redactHash && obj.match(/0x[0-9a-f]{64}/)) {
302
+ return '(hash)';
275
303
  }
276
- if (Array.isArray(obj)) {
277
- return obj.map((x)=>process(x, depth - 1));
304
+ if (redactHex && obj.match(/0x[0-9a-f]+/)) {
305
+ return '(hex)';
278
306
  }
279
- if (redactNumber && typeof obj === 'number') {
280
- return processNumber(obj);
307
+ if (redactAddress && obj.match(/^[1-9A-HJ-NP-Za-km-z]{46,48}$/)) {
308
+ return '(address)';
281
309
  }
282
- if (typeof obj === 'string') {
283
- if (redactNumber && obj.match(/0x000000[0-9a-f]{26}/)) {
284
- // this is very likely u128 encoded in hex
285
- const num = Number.parseInt(obj);
286
- return processNumber(num);
287
- }
288
- if (redactHash && obj.match(/0x[0-9a-f]{64}/)) {
289
- return '(hash)';
290
- }
291
- if (redactHex && obj.match(/0x[0-9a-f]+/)) {
292
- return '(hex)';
310
+ if (redactNumber && obj.match(/^-?[\d,]+$/)) {
311
+ const num = Number.parseInt(obj.replace(/,/g, ''));
312
+ return processNumber(num);
313
+ }
314
+ return obj;
315
+ }
316
+ if (typeof obj === 'object') {
317
+ return Object.fromEntries(Object.entries(obj).filter(([k])=>{
318
+ if (options.removeKeys?.test(k)) {
319
+ return false;
293
320
  }
294
- if (redactAddress && obj.match(/^[1-9A-HJ-NP-Za-km-z]{46,48}$/)) {
295
- return '(address)';
321
+ return true;
322
+ }).map(([k, v])=>{
323
+ if (options.noRedactKeys?.test(k)) {
324
+ return [
325
+ k,
326
+ v
327
+ ];
296
328
  }
297
- if (redactNumber && obj.match(/^-?[\d,]+$/)) {
298
- const num = Number.parseInt(obj.replace(/,/g, ''));
299
- return processNumber(num);
329
+ if (options.overrides?.[k]) {
330
+ return [
331
+ k,
332
+ _class_private_method_get(this, __redact, _redact).call(this, v, options.overrides[k], depth - 1)
333
+ ];
300
334
  }
301
- return obj;
302
- }
303
- if (typeof obj === 'object') {
304
- return Object.fromEntries(Object.entries(obj).filter(([k])=>{
305
- if (_class_private_field_get(this, _redactOptions)?.removeKeys?.test(k)) {
306
- return false;
307
- }
308
- return true;
309
- }).map(([k, v])=>{
310
- if (_class_private_field_get(this, _redactOptions)?.noRedactKeys?.test(k)) {
311
- return [
312
- k,
313
- v
314
- ];
315
- }
316
- if (_class_private_field_get(this, _redactOptions)?.redactKeys?.test(k)) {
317
- return [
318
- k,
319
- '(redacted)'
320
- ];
321
- }
335
+ if (options.redactKeys?.test(k)) {
322
336
  return [
323
337
  k,
324
- process(v, depth - 1)
338
+ '(redacted)'
325
339
  ];
326
- }));
327
- }
328
- return obj;
329
- };
330
- return process(value, 50);
340
+ }
341
+ return [
342
+ k,
343
+ _class_private_method_get(this, __redact, _redact).call(this, v, options, depth - 1)
344
+ ];
345
+ }));
346
+ }
347
+ return obj;
331
348
  }
332
- const withExpect = (expectFn)=>{
349
+ const setupCheck = (options)=>{
350
+ const { expectFn, redactOptions, extraCheck } = options;
333
351
  /**
334
352
  * Create a new Checker instance
335
353
  * @param value - Value to check
336
354
  * @param msg - Optional message for assertions
337
355
  */ const check = (value, msg)=>{
356
+ let checker;
338
357
  if (value instanceof Checker) {
358
+ checker = value;
339
359
  if (msg) {
340
- return value.message(msg);
360
+ checker = checker.message(msg);
341
361
  }
342
- return value;
362
+ } else {
363
+ checker = new Checker(expectFn, value, msg);
364
+ }
365
+ if (redactOptions) {
366
+ checker = checker.redact(redactOptions);
343
367
  }
344
- return new Checker(expectFn, value, msg);
368
+ if (extraCheck) {
369
+ checker = checker.check(extraCheck);
370
+ }
371
+ return checker;
345
372
  };
346
373
  /**
347
374
  * Check blockchain events with filtering and redaction
@@ -378,3 +405,8 @@ const withExpect = (expectFn)=>{
378
405
  checkHex
379
406
  };
380
407
  };
408
+ const withExpect = (expectFn)=>{
409
+ return setupCheck({
410
+ expectFn
411
+ });
412
+ };
@@ -26,6 +26,12 @@ export type RedactOptions = {
26
26
  removeKeys?: RegExp;
27
27
  /** Regex pattern for keys that should not be redacted */
28
28
  noRedactKeys?: RegExp;
29
+ /** Redact options for specific keys */
30
+ overrides?: Record<string, RedactOptions>;
31
+ noRedact?: false;
32
+ } | {
33
+ /** Do not redact any values */
34
+ noRedact: true;
29
35
  };
30
36
  /**
31
37
  * Function type for test assertions
@@ -107,6 +113,31 @@ export declare class Checker {
107
113
  */
108
114
  toMatchObject(value: any, msg?: string): Promise<void>;
109
115
  }
116
+ /**
117
+ * Creates a set of checking utilities with provided options
118
+ * @param options - Options for setting up checks
119
+ * @returns Object containing various checking utilities
120
+ */
121
+ export declare const setupCheck: (options: {
122
+ expectFn: ExpectFn;
123
+ redactOptions?: RedactOptions;
124
+ extraCheck?: (value: any) => Promise<void> | void;
125
+ }) => {
126
+ check: (value: any, msg?: string) => Checker;
127
+ checkEvents: ({ events }: {
128
+ events: Promise<Codec[] | Codec>;
129
+ }, ...filters: EventFilter[]) => Checker;
130
+ checkSystemEvents: ({ api }: {
131
+ api: ApiPromise;
132
+ }, ...filters: EventFilter[]) => Checker;
133
+ checkUmp: ({ api }: {
134
+ api: ApiPromise;
135
+ }) => Checker;
136
+ checkHrmp: ({ api }: {
137
+ api: ApiPromise;
138
+ }) => Checker;
139
+ checkHex: (value: any, msg?: string) => Checker;
140
+ };
110
141
  /**
111
142
  * Creates a set of checking utilities with a provided assertion function
112
143
  * @param expectFn - Function for making test assertions
package/dist/esm/check.js CHANGED
@@ -87,21 +87,37 @@
87
87
  number: 2,
88
88
  hash: true
89
89
  }) {
90
- this.#redactOptions = {
91
- ...this.#redactOptions,
92
- ...options
93
- };
90
+ if (options.noRedact) {
91
+ this.#redactOptions = undefined;
92
+ } else {
93
+ this.#redactOptions = {
94
+ ...this.#redactOptions,
95
+ ...options
96
+ };
97
+ }
94
98
  return this;
95
99
  }
96
100
  #redact(value) {
97
101
  if (!this.#redactOptions) {
98
102
  return value;
99
103
  }
100
- const redactNumber = this.#redactOptions.number === true || typeof this.#redactOptions.number === 'number';
101
- const precision = redactNumber ? typeof this.#redactOptions.number === 'number' ? this.#redactOptions.number : 0 : 0;
102
- const redactHash = this.#redactOptions.hash === true;
103
- const redactHex = this.#redactOptions.hex === true;
104
- const redactAddress = this.#redactOptions.address === true;
104
+ return this.#_redact(value, this.#redactOptions, 50);
105
+ }
106
+ #_redact(obj, options, depth) {
107
+ if (depth <= 0) {
108
+ return obj;
109
+ }
110
+ if (obj == null) {
111
+ return obj;
112
+ }
113
+ if (options.noRedact) {
114
+ return obj;
115
+ }
116
+ const redactNumber = options.number === true || typeof options.number === 'number';
117
+ const precision = redactNumber ? typeof options.number === 'number' ? options.number : 0 : 0;
118
+ const redactHash = options.hash === true;
119
+ const redactHex = options.hex === true;
120
+ const redactAddress = options.address === true;
105
121
  const processNumber = (value)=>{
106
122
  if (precision > 0) {
107
123
  const rounded = Number.parseFloat(value.toPrecision(precision));
@@ -112,68 +128,65 @@
112
128
  }
113
129
  return '(number)';
114
130
  };
115
- const process = (obj, depth)=>{
116
- if (depth <= 0) {
117
- return obj;
131
+ if (Array.isArray(obj)) {
132
+ return obj.map((x)=>this.#_redact(x, options, depth - 1));
133
+ }
134
+ if (redactNumber && typeof obj === 'number') {
135
+ return processNumber(obj);
136
+ }
137
+ if (typeof obj === 'string') {
138
+ if (redactNumber && obj.match(/0x000000[0-9a-f]{26}/)) {
139
+ // this is very likely u128 encoded in hex
140
+ const num = Number.parseInt(obj);
141
+ return processNumber(num);
118
142
  }
119
- if (obj == null) {
120
- return obj;
143
+ if (redactHash && obj.match(/0x[0-9a-f]{64}/)) {
144
+ return '(hash)';
121
145
  }
122
- if (Array.isArray(obj)) {
123
- return obj.map((x)=>process(x, depth - 1));
146
+ if (redactHex && obj.match(/0x[0-9a-f]+/)) {
147
+ return '(hex)';
124
148
  }
125
- if (redactNumber && typeof obj === 'number') {
126
- return processNumber(obj);
149
+ if (redactAddress && obj.match(/^[1-9A-HJ-NP-Za-km-z]{46,48}$/)) {
150
+ return '(address)';
127
151
  }
128
- if (typeof obj === 'string') {
129
- if (redactNumber && obj.match(/0x000000[0-9a-f]{26}/)) {
130
- // this is very likely u128 encoded in hex
131
- const num = Number.parseInt(obj);
132
- return processNumber(num);
133
- }
134
- if (redactHash && obj.match(/0x[0-9a-f]{64}/)) {
135
- return '(hash)';
136
- }
137
- if (redactHex && obj.match(/0x[0-9a-f]+/)) {
138
- return '(hex)';
152
+ if (redactNumber && obj.match(/^-?[\d,]+$/)) {
153
+ const num = Number.parseInt(obj.replace(/,/g, ''));
154
+ return processNumber(num);
155
+ }
156
+ return obj;
157
+ }
158
+ if (typeof obj === 'object') {
159
+ return Object.fromEntries(Object.entries(obj).filter(([k])=>{
160
+ if (options.removeKeys?.test(k)) {
161
+ return false;
139
162
  }
140
- if (redactAddress && obj.match(/^[1-9A-HJ-NP-Za-km-z]{46,48}$/)) {
141
- return '(address)';
163
+ return true;
164
+ }).map(([k, v])=>{
165
+ if (options.noRedactKeys?.test(k)) {
166
+ return [
167
+ k,
168
+ v
169
+ ];
142
170
  }
143
- if (redactNumber && obj.match(/^-?[\d,]+$/)) {
144
- const num = Number.parseInt(obj.replace(/,/g, ''));
145
- return processNumber(num);
171
+ if (options.overrides?.[k]) {
172
+ return [
173
+ k,
174
+ this.#_redact(v, options.overrides[k], depth - 1)
175
+ ];
146
176
  }
147
- return obj;
148
- }
149
- if (typeof obj === 'object') {
150
- return Object.fromEntries(Object.entries(obj).filter(([k])=>{
151
- if (this.#redactOptions?.removeKeys?.test(k)) {
152
- return false;
153
- }
154
- return true;
155
- }).map(([k, v])=>{
156
- if (this.#redactOptions?.noRedactKeys?.test(k)) {
157
- return [
158
- k,
159
- v
160
- ];
161
- }
162
- if (this.#redactOptions?.redactKeys?.test(k)) {
163
- return [
164
- k,
165
- '(redacted)'
166
- ];
167
- }
177
+ if (options.redactKeys?.test(k)) {
168
178
  return [
169
179
  k,
170
- process(v, depth - 1)
180
+ '(redacted)'
171
181
  ];
172
- }));
173
- }
174
- return obj;
175
- };
176
- return process(value, 50);
182
+ }
183
+ return [
184
+ k,
185
+ this.#_redact(v, options, depth - 1)
186
+ ];
187
+ }));
188
+ }
189
+ return obj;
177
190
  }
178
191
  /**
179
192
  * Add a transformation function to the processing pipeline
@@ -242,22 +255,32 @@
242
255
  }
243
256
  }
244
257
  /**
245
- * Creates a set of checking utilities with a provided assertion function
246
- * @param expectFn - Function for making test assertions
258
+ * Creates a set of checking utilities with provided options
259
+ * @param options - Options for setting up checks
247
260
  * @returns Object containing various checking utilities
248
- */ export const withExpect = (expectFn)=>{
261
+ */ export const setupCheck = (options)=>{
262
+ const { expectFn, redactOptions, extraCheck } = options;
249
263
  /**
250
264
  * Create a new Checker instance
251
265
  * @param value - Value to check
252
266
  * @param msg - Optional message for assertions
253
267
  */ const check = (value, msg)=>{
268
+ let checker;
254
269
  if (value instanceof Checker) {
270
+ checker = value;
255
271
  if (msg) {
256
- return value.message(msg);
272
+ checker = checker.message(msg);
257
273
  }
258
- return value;
274
+ } else {
275
+ checker = new Checker(expectFn, value, msg);
276
+ }
277
+ if (redactOptions) {
278
+ checker = checker.redact(redactOptions);
259
279
  }
260
- return new Checker(expectFn, value, msg);
280
+ if (extraCheck) {
281
+ checker = checker.check(extraCheck);
282
+ }
283
+ return checker;
261
284
  };
262
285
  /**
263
286
  * Check blockchain events with filtering and redaction
@@ -294,3 +317,12 @@
294
317
  checkHex
295
318
  };
296
319
  };
320
+ /**
321
+ * Creates a set of checking utilities with a provided assertion function
322
+ * @param expectFn - Function for making test assertions
323
+ * @returns Object containing various checking utilities
324
+ */ export const withExpect = (expectFn)=>{
325
+ return setupCheck({
326
+ expectFn
327
+ });
328
+ };
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@acala-network/chopsticks-testing",
3
- "version": "1.2.0",
3
+ "version": "1.2.1",
4
4
  "author": "Acala Developers <hello@acala.network>",
5
5
  "license": "Apache-2.0",
6
6
  "type": "module",
@@ -13,13 +13,13 @@
13
13
  "depcheck": "npx depcheck"
14
14
  },
15
15
  "dependencies": {
16
- "@acala-network/chopsticks-utils": "1.2.0",
16
+ "@acala-network/chopsticks-utils": "1.2.1",
17
17
  "@polkadot/api": "^16.4.1",
18
18
  "@polkadot/types": "^16.4.1"
19
19
  },
20
20
  "devDependencies": {
21
21
  "@swc/cli": "0.7.8",
22
- "@swc/core": "^1.12.11",
22
+ "@swc/core": "^1.12.14",
23
23
  "typescript": "^5.8.3"
24
24
  },
25
25
  "files": [