noah-clarity 0.3.2 → 0.3.3

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.
package/dist/config.js CHANGED
@@ -1,21 +1,16 @@
1
- "use strict";
2
1
  /**
3
2
  * Configuration loader for contract addresses
4
3
  */
5
- Object.defineProperty(exports, "__esModule", { value: true });
6
- exports.TESTNET_CONTRACTS = void 0;
7
- exports.loadContractAddresses = loadContractAddresses;
8
- exports.createSDKConfig = createSDKConfig;
9
4
  /**
10
5
  * Default testnet contract addresses (deployed)
11
6
  */
12
- exports.TESTNET_CONTRACTS = {
7
+ export const TESTNET_CONTRACTS = {
13
8
  network: 'testnet',
14
9
  deployer: 'STVAH96MR73TP2FZG2W4X220MEB4NEMJHPMVYQNS',
15
10
  contracts: {
16
11
  'attester-registry': 'STVAH96MR73TP2FZG2W4X220MEB4NEMJHPMVYQNS.attester-registry',
17
12
  'attester-registry-trait': 'STVAH96MR73TP2FZG2W4X220MEB4NEMJHPMVYQNS.attester-registry-trait',
18
- 'kyc-registry': 'STVAH96MR73TP2FZG2W4X220MEB4NEMJHPMVYQNS.kyc-registry',
13
+ 'kyc-registry': 'STVAH96MR73TP2FZG2W4X220MEB4NEMJHPMVYQNS.kycs-registry',
19
14
  'revocation': 'STVAH96MR73TP2FZG2W4X220MEB4NEMJHPMVYQNS.revocation',
20
15
  },
21
16
  deployment_date: '2025-01-17',
@@ -26,14 +21,14 @@ exports.TESTNET_CONTRACTS = {
26
21
  * In browser environments, this can load from a static JSON file
27
22
  * In Node.js, can use fs to read the JSON file
28
23
  */
29
- function loadContractAddresses(network = 'testnet') {
24
+ export function loadContractAddresses(network = 'testnet') {
30
25
  // For now, return hardcoded testnet addresses
31
26
  // In production, you might want to:
32
27
  // 1. Load from a JSON file
33
28
  // 2. Fetch from a registry/API
34
29
  // 3. Use environment variables
35
30
  if (network === 'testnet') {
36
- return exports.TESTNET_CONTRACTS;
31
+ return TESTNET_CONTRACTS;
37
32
  }
38
33
  // TODO: Add mainnet addresses when deployed
39
34
  throw new Error(`Contract addresses for ${network} not yet configured`);
@@ -41,7 +36,7 @@ function loadContractAddresses(network = 'testnet') {
41
36
  /**
42
37
  * Create SDK config from contract addresses
43
38
  */
44
- function createSDKConfig(addresses, options) {
39
+ export function createSDKConfig(addresses, options) {
45
40
  return {
46
41
  kycRegistryAddress: addresses.contracts['kyc-registry'],
47
42
  attesterRegistryAddress: addresses.contracts['attester-registry'],
package/dist/contract.js CHANGED
@@ -1,12 +1,9 @@
1
- "use strict";
2
1
  /**
3
2
  * Clarity contract interaction helpers
4
3
  */
5
- Object.defineProperty(exports, "__esModule", { value: true });
6
- exports.KYCContract = void 0;
7
- const transactions_1 = require("@stacks/transactions");
8
- const network_1 = require("@stacks/network");
9
- class KYCContract {
4
+ import { makeContractCall, broadcastTransaction, AnchorMode, PostConditionMode, bufferCV, uintCV, principalCV, getAddressFromPrivateKey, cvToJSON, callReadOnlyFunction, } from '@stacks/transactions';
5
+ import { StacksTestnet, StacksMainnet } from '@stacks/network';
6
+ export class KYCContract {
10
7
  constructor(config) {
11
8
  this.config = config;
12
9
  this.network = this.getNetwork();
@@ -14,11 +11,11 @@ class KYCContract {
14
11
  getNetwork() {
15
12
  switch (this.config.network) {
16
13
  case 'mainnet':
17
- return new network_1.StacksMainnet();
14
+ return new StacksMainnet();
18
15
  case 'testnet':
19
- return new network_1.StacksTestnet();
16
+ return new StacksTestnet();
20
17
  default:
21
- return new network_1.StacksTestnet();
18
+ return new StacksTestnet();
22
19
  }
23
20
  }
24
21
  /**
@@ -28,9 +25,11 @@ class KYCContract {
28
25
  * @returns Transaction ID
29
26
  */
30
27
  async registerKYC(params, privateKey) {
31
- const senderAddress = (0, transactions_1.getAddressFromPrivateKey)(privateKey, this.network.version);
28
+ const senderAddress = getAddressFromPrivateKey(privateKey, this.network.version);
32
29
  // #region agent log
33
- fetch('http://127.0.0.1:7249/ingest/b239a7fb-669e-478f-b888-bd46beaadedf', { method: 'POST', headers: { 'Content-Type': 'application/json' }, body: JSON.stringify({ location: 'contract.ts:50', 'message': 'registerKYC entry', 'data': { senderAddress, network: this.network.coreApiUrl, attesterId: params.attesterId, commitmentLength: params.commitment.length, signatureLength: params.signature.length }, timestamp: Date.now(), sessionId: 'debug-session', runId: 'run1', hypothesisId: 'A' }) }).catch(() => { });
30
+ console.log('Transaction sender address (derived from private key):', senderAddress);
31
+ console.log('Network version:', this.network.version);
32
+ fetch('http://127.0.0.1:7249/ingest/b239a7fb-669e-478f-b888-bd46beaadedf', { method: 'POST', headers: { 'Content-Type': 'application/json' }, body: JSON.stringify({ location: 'contract.ts:50', 'message': 'registerKYC entry', 'data': { senderAddress, network: this.network.coreApiUrl, networkVersion: this.network.version, attesterId: params.attesterId, commitmentLength: params.commitment.length, signatureLength: params.signature.length }, timestamp: Date.now(), sessionId: 'debug-session', runId: 'run1', hypothesisId: 'A' }) }).catch(() => { });
34
33
  // #endregion agent log
35
34
  const { address, name } = this.parseContractAddress(this.config.kycRegistryAddress);
36
35
  // Ensure commitment is exactly 32 bytes (64 hex chars)
@@ -39,16 +38,16 @@ class KYCContract {
39
38
  if (commitmentBuffer.length !== 32) {
40
39
  throw new Error(`Invalid commitment length: expected 32 bytes, got ${commitmentBuffer.length}. Hex: ${commitmentHex.substring(0, 20)}...`);
41
40
  }
42
- // Ensure signature is exactly 65 bytes (130 hex chars)
41
+ // Ensure signature is 64 or 65 bytes (128 or 130 hex chars)
43
42
  const signatureHex = params.signature.replace('0x', '');
44
43
  const signatureBuffer = Buffer.from(signatureHex, 'hex');
45
- if (signatureBuffer.length !== 65) {
46
- throw new Error(`Invalid signature length: expected 65 bytes, got ${signatureBuffer.length}. Hex: ${signatureHex.substring(0, 20)}...`);
44
+ if (signatureBuffer.length !== 64 && signatureBuffer.length !== 65) {
45
+ throw new Error(`Invalid signature length: expected 64 or 65 bytes, got ${signatureBuffer.length}. Hex: ${signatureHex.substring(0, 20)}...`);
47
46
  }
48
47
  const functionArgs = [
49
- (0, transactions_1.bufferCV)(commitmentBuffer),
50
- (0, transactions_1.bufferCV)(signatureBuffer),
51
- (0, transactions_1.uintCV)(params.attesterId),
48
+ bufferCV(commitmentBuffer),
49
+ bufferCV(signatureBuffer),
50
+ uintCV(params.attesterId),
52
51
  ];
53
52
  const txOptions = {
54
53
  contractAddress: address,
@@ -58,14 +57,14 @@ class KYCContract {
58
57
  senderKey: privateKey,
59
58
  fee: 5000, // Increased from 1000 to 5000 microSTX (0.005 STX) for better reliability
60
59
  network: this.network,
61
- anchorMode: transactions_1.AnchorMode.Any,
62
- postConditionMode: transactions_1.PostConditionMode.Allow,
60
+ anchorMode: AnchorMode.Any,
61
+ postConditionMode: PostConditionMode.Allow,
63
62
  };
64
63
  // #region agent log
65
64
  fetch('http://127.0.0.1:7249/ingest/b239a7fb-669e-478f-b888-bd46beaadedf', { method: 'POST', headers: { 'Content-Type': 'application/json' }, body: JSON.stringify({ location: 'contract.ts:74', 'message': 'Transaction options before makeContractCall', 'data': { contractAddress: address, contractName: name, functionName: 'register-kyc', fee: txOptions.fee, anchorMode: txOptions.anchorMode, postConditionMode: txOptions.postConditionMode, networkUrl: this.network.coreApiUrl }, timestamp: Date.now(), sessionId: 'debug-session', runId: 'run1', hypothesisId: 'B' }) }).catch(() => { });
66
65
  // #endregion agent log
67
66
  try {
68
- const transaction = await (0, transactions_1.makeContractCall)(txOptions);
67
+ const transaction = await makeContractCall(txOptions);
69
68
  // #region agent log
70
69
  const serializedTx = transaction.serialize();
71
70
  const nonceValue = transaction.auth?.spendingCondition?.nonce;
@@ -76,10 +75,24 @@ class KYCContract {
76
75
  };
77
76
  fetch('http://127.0.0.1:7249/ingest/b239a7fb-669e-478f-b888-bd46beaadedf', { method: 'POST', headers: { 'Content-Type': 'application/json' }, body: JSON.stringify({ location: 'contract.ts:87', 'message': 'Transaction created, before broadcast', 'data': txData, timestamp: Date.now(), sessionId: 'debug-session', runId: 'run1', hypothesisId: 'A' }) }).catch(() => { });
78
77
  // #endregion agent log
79
- const broadcastResponse = await (0, transactions_1.broadcastTransaction)(transaction, this.network);
80
- return broadcastResponse.txid;
78
+ // #region agent log
79
+ fetch('http://127.0.0.1:7249/ingest/b239a7fb-669e-478f-b888-bd46beaadedf', { method: 'POST', headers: { 'Content-Type': 'application/json' }, body: JSON.stringify({ location: 'contract.ts:108', 'message': 'About to call broadcastTransaction', 'data': {}, timestamp: Date.now(), sessionId: 'debug-session', runId: 'run1', hypothesisId: 'D' }) }).catch(() => { });
80
+ // #endregion agent log
81
+ try {
82
+ const broadcastResponse = await broadcastTransaction(transaction, this.network);
83
+ return broadcastResponse.txid;
84
+ }
85
+ catch (broadcastError) {
86
+ // Log the error immediately with console.error to ensure we see it
87
+ console.error('broadcastTransaction error:', broadcastError);
88
+ // Re-throw to be caught by outer catch block
89
+ throw broadcastError;
90
+ }
81
91
  }
82
92
  catch (error) {
93
+ // #region agent log
94
+ fetch('http://127.0.0.1:7249/ingest/b239a7fb-669e-478f-b888-bd46beaadedf', { method: 'POST', headers: { 'Content-Type': 'application/json' }, body: JSON.stringify({ location: 'contract.ts:110', 'message': 'Caught error in registerKYC', 'data': { errorType: error?.constructor?.name, hasMessage: !!error?.message, message: error?.message?.substring(0, 200) }, timestamp: Date.now(), sessionId: 'debug-session', runId: 'run1', hypothesisId: 'C' }) }).catch(() => { });
95
+ // #endregion agent log
83
96
  // Helper function to safely serialize data (handles BigInt)
84
97
  const safeStringify = (obj) => {
85
98
  try {
@@ -140,8 +153,9 @@ class KYCContract {
140
153
  errorType: error?.constructor?.name,
141
154
  status: error?.status,
142
155
  statusText: error?.statusText,
156
+ message: error?.message,
143
157
  };
144
- fetch('http://127.0.0.1:7249/ingest/b239a7fb-669e-478f-b888-bd46beaadedf', { method: 'POST', headers: { 'Content-Type': 'application/json' }, body: safeStringify({ location: 'contract.ts:91', 'message': 'Error object structure', 'data': errorStructure, timestamp: Date.now(), sessionId: 'debug-session', runId: 'run1', hypothesisId: 'C' }) }).catch(() => { });
158
+ fetch('http://127.0.0.1:7249/ingest/b239a7fb-669e-478f-b888-bd46beaadedf', { method: 'POST', headers: { 'Content-Type': 'application/json' }, body: safeStringify({ location: 'contract.ts:135', 'message': 'Error object structure', 'data': errorStructure, timestamp: Date.now(), sessionId: 'debug-session', runId: 'run1', hypothesisId: 'C' }) }).catch(() => { });
145
159
  // #endregion agent log
146
160
  // Capture detailed error information
147
161
  let errorMessage = 'Transaction failed';
@@ -195,12 +209,27 @@ class KYCContract {
195
209
  fetch('http://127.0.0.1:7249/ingest/b239a7fb-669e-478f-b888-bd46beaadedf', { method: 'POST', headers: { 'Content-Type': 'application/json' }, body: safeStringify({ location: 'contract.ts:135', 'message': 'API response body', 'data': { responseBody: typeof responseBody === 'string' ? responseBody : safeStringify(responseBody) }, timestamp: Date.now(), sessionId: 'debug-session', runId: 'run1', hypothesisId: 'C' }) }).catch(() => { });
196
210
  }
197
211
  // #endregion agent log
212
+ // Extract error details from response body for user-friendly messages
213
+ let userFriendlyMessage = errorMessage;
214
+ if (responseBody && typeof responseBody === 'object') {
215
+ if (responseBody.reason === 'NotEnoughFunds') {
216
+ const expected = responseBody.reason_data?.expected;
217
+ const expectedStx = expected ? (parseInt(expected, 16) / 1000000).toFixed(6) : '0.005';
218
+ userFriendlyMessage = `Insufficient STX balance. You need at least ${expectedStx} STX to pay for the transaction fee. Please fund your account with STX and try again.`;
219
+ }
220
+ else if (responseBody.reason) {
221
+ userFriendlyMessage = `Transaction rejected: ${responseBody.reason}${responseBody.error ? ' - ' + responseBody.error : ''}`;
222
+ }
223
+ else if (responseBody.error) {
224
+ userFriendlyMessage = responseBody.error;
225
+ }
226
+ }
198
227
  // Log the full error for debugging (using safe extraction)
199
228
  const safeErrorDetails = safeExtract(errorDetails);
200
229
  console.error('Transaction broadcast error:', safeErrorDetails);
201
230
  // Provide detailed error message
202
- const detailedMessage = typeof responseBody === 'string' ? responseBody : (errorDetails.response || errorDetails.reason || errorDetails.apiError || errorDetails.data || errorMessage);
203
- throw new Error(`Transaction failed: ${detailedMessage}`);
231
+ const detailedMessage = userFriendlyMessage || (typeof responseBody === 'string' ? responseBody : (errorDetails.response || errorDetails.reason || errorDetails.apiError || errorDetails.data || errorMessage));
232
+ throw new Error(detailedMessage);
204
233
  }
205
234
  }
206
235
  /**
@@ -211,15 +240,15 @@ class KYCContract {
211
240
  async hasKYC(userPrincipal) {
212
241
  const { address, name } = this.parseContractAddress(this.config.kycRegistryAddress);
213
242
  try {
214
- const result = await (0, transactions_1.callReadOnlyFunction)({
243
+ const result = await callReadOnlyFunction({
215
244
  contractAddress: address,
216
245
  contractName: name,
217
246
  functionName: 'has-kyc?',
218
- functionArgs: [(0, transactions_1.principalCV)(userPrincipal)],
247
+ functionArgs: [principalCV(userPrincipal)],
219
248
  network: this.network,
220
249
  senderAddress: address, // Use contract address as sender for read-only calls
221
250
  });
222
- const jsonResult = (0, transactions_1.cvToJSON)(result);
251
+ const jsonResult = cvToJSON(result);
223
252
  // Result is (ok bool), so check if it's ok and the value is true
224
253
  if (jsonResult.type === 'responseOk') {
225
254
  const hasKYC = jsonResult.value.value === true;
@@ -252,15 +281,15 @@ class KYCContract {
252
281
  async getKYC(userPrincipal) {
253
282
  const { address, name } = this.parseContractAddress(this.config.kycRegistryAddress);
254
283
  try {
255
- const result = await (0, transactions_1.callReadOnlyFunction)({
284
+ const result = await callReadOnlyFunction({
256
285
  contractAddress: address,
257
286
  contractName: name,
258
287
  functionName: 'get-kyc',
259
- functionArgs: [(0, transactions_1.principalCV)(userPrincipal)],
288
+ functionArgs: [principalCV(userPrincipal)],
260
289
  network: this.network,
261
290
  senderAddress: address,
262
291
  });
263
- const jsonResult = (0, transactions_1.cvToJSON)(result);
292
+ const jsonResult = cvToJSON(result);
264
293
  // Result is (ok (some kyc-record)) or (ok none)
265
294
  if (jsonResult.type === 'responseOk' && jsonResult.value.type === 'optionalSome') {
266
295
  const record = jsonResult.value.value.value;
@@ -294,4 +323,3 @@ class KYCContract {
294
323
  };
295
324
  }
296
325
  }
297
- exports.KYCContract = KYCContract;
package/dist/index.js CHANGED
@@ -1,42 +1,22 @@
1
- "use strict";
2
1
  /**
3
2
  * Noah-v2 SDK
4
3
  * Main entry point for protocol integration
5
4
  */
6
- var __createBinding = (this && this.__createBinding) || (Object.create ? (function(o, m, k, k2) {
7
- if (k2 === undefined) k2 = k;
8
- var desc = Object.getOwnPropertyDescriptor(m, k);
9
- if (!desc || ("get" in desc ? !m.__esModule : desc.writable || desc.configurable)) {
10
- desc = { enumerable: true, get: function() { return m[k]; } };
11
- }
12
- Object.defineProperty(o, k2, desc);
13
- }) : (function(o, m, k, k2) {
14
- if (k2 === undefined) k2 = k;
15
- o[k2] = m[k];
16
- }));
17
- var __exportStar = (this && this.__exportStar) || function(m, exports) {
18
- for (var p in m) if (p !== "default" && !Object.prototype.hasOwnProperty.call(exports, p)) __createBinding(exports, m, p);
19
- };
20
- Object.defineProperty(exports, "__esModule", { value: true });
21
- exports.NoahSDK = exports.WalletHelper = exports.ProofService = exports.KYCContract = void 0;
22
- var contract_1 = require("./contract");
23
- Object.defineProperty(exports, "KYCContract", { enumerable: true, get: function () { return contract_1.KYCContract; } });
24
- var proof_1 = require("./proof");
25
- Object.defineProperty(exports, "ProofService", { enumerable: true, get: function () { return proof_1.ProofService; } });
26
- var wallet_1 = require("./wallet");
27
- Object.defineProperty(exports, "WalletHelper", { enumerable: true, get: function () { return wallet_1.WalletHelper; } });
28
- __exportStar(require("./types"), exports);
29
- const contract_2 = require("./contract");
30
- const proof_2 = require("./proof");
31
- const wallet_2 = require("./wallet");
5
+ export { KYCContract } from './contract';
6
+ export { ProofService } from './proof';
7
+ export { WalletHelper } from './wallet';
8
+ export * from './types';
9
+ import { KYCContract } from './contract';
10
+ import { ProofService } from './proof';
11
+ import { WalletHelper } from './wallet';
32
12
  /**
33
13
  * Main SDK class
34
14
  */
35
- class NoahSDK {
15
+ export class NoahSDK {
36
16
  constructor(config, walletConfig) {
37
- this.contract = new contract_2.KYCContract(config);
38
- this.proof = new proof_2.ProofService(config);
39
- this.wallet = new wallet_2.WalletHelper(walletConfig);
17
+ this.contract = new KYCContract(config);
18
+ this.proof = new ProofService(config);
19
+ this.wallet = new WalletHelper(walletConfig);
40
20
  }
41
21
  /**
42
22
  * Complete KYC registration flow
@@ -69,6 +49,5 @@ class NoahSDK {
69
49
  return txId;
70
50
  }
71
51
  }
72
- exports.NoahSDK = NoahSDK;
73
52
  // Default export
74
- exports.default = NoahSDK;
53
+ export default NoahSDK;
package/dist/proof.js CHANGED
@@ -1,10 +1,7 @@
1
- "use strict";
2
1
  /**
3
2
  * Proof generation and verification utilities
4
3
  */
5
- Object.defineProperty(exports, "__esModule", { value: true });
6
- exports.ProofService = void 0;
7
- class ProofService {
4
+ export class ProofService {
8
5
  constructor(config) {
9
6
  this.proverServiceUrl = config.proverServiceUrl || 'http://localhost:8080';
10
7
  this.attesterServiceUrl = config.attesterServiceUrl || 'http://localhost:8081';
@@ -92,4 +89,3 @@ class ProofService {
92
89
  return await this.generateProof(proofRequest);
93
90
  }
94
91
  }
95
- exports.ProofService = ProofService;
package/dist/types.js CHANGED
@@ -1,5 +1,4 @@
1
- "use strict";
2
1
  /**
3
2
  * Type definitions for Noah-v2 SDK
4
3
  */
5
- Object.defineProperty(exports, "__esModule", { value: true });
4
+ export {};
package/dist/wallet.js CHANGED
@@ -1,10 +1,7 @@
1
- "use strict";
2
1
  /**
3
2
  * Wallet integration helpers
4
3
  */
5
- Object.defineProperty(exports, "__esModule", { value: true });
6
- exports.WalletHelper = void 0;
7
- class WalletHelper {
4
+ export class WalletHelper {
8
5
  constructor(config) {
9
6
  this.config = config;
10
7
  }
@@ -31,4 +28,3 @@ class WalletHelper {
31
28
  return userData.profile.stxAddress.mainnet || userData.profile.stxAddress.testnet;
32
29
  }
33
30
  }
34
- exports.WalletHelper = WalletHelper;
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "noah-clarity",
3
- "version": "0.3.2",
3
+ "version": "0.3.3",
4
4
  "description": "TypeScript SDK for Noah-v2 KYC system on Stacks",
5
5
  "main": "dist/index.js",
6
6
  "types": "dist/index.d.ts",