@leofcoin/chain 1.4.79 → 1.4.80

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.
@@ -1,2 +1,2 @@
1
- export { N as default } from './node-browser-44a01a16.js';
1
+ export { N as default } from './node-browser-3cbee72b.js';
2
2
  import './index-c3f4012c.js';
package/exports/chain.js CHANGED
@@ -8,11 +8,11 @@ import EasyWorker from '@vandeurenglenn/easy-worker';
8
8
 
9
9
  const limit = 1800;
10
10
  const transactionLimit = 1800;
11
- const requestTimeout = 30_000;
12
- const syncTimeout = 30_000;
11
+ const requestTimeout = 30000;
12
+ const syncTimeout = 30000;
13
13
  class Protocol {
14
14
  version;
15
- resolveTimeout = 30_000;
15
+ resolveTimeout = 30000;
16
16
  get limit() {
17
17
  return limit;
18
18
  }
@@ -178,7 +178,7 @@ class Transaction extends Protocol {
178
178
  result.status === 'fulfilled' ? resolve(result.hash) : reject({ hash: result.hash, error: result.error });
179
179
  setTimeout(async () => {
180
180
  pubsub.unsubscribe(`transaction.completed.${hash}`, completed);
181
- }, 10_000);
181
+ }, 10000);
182
182
  };
183
183
  pubsub.subscribe(`transaction.completed.${hash}`, completed);
184
184
  }
@@ -198,250 +198,269 @@ class Transaction extends Protocol {
198
198
  * @extends {Transaction}
199
199
  */
200
200
  class Contract extends Transaction {
201
- constructor() {
202
- super();
203
- }
204
- async init() {
205
- }
206
- /**
207
- *
208
- * @param {Address} creator
209
- * @param {String} contract
210
- * @param {Array} constructorParameters
211
- * @returns lib.createContractMessage
212
- */
213
- async createContractMessage(creator, contract, constructorParameters = []) {
214
- return createContractMessage(creator, contract, constructorParameters);
215
- }
216
- /**
217
- *
218
- * @param {Address} creator
219
- * @param {String} contract
220
- * @param {Array} constructorParameters
221
- * @returns {Address}
222
- */
223
- async createContractAddress(creator, contract, constructorParameters = []) {
224
- contract = await this.createContractMessage(creator, contract, constructorParameters);
225
- return contract.hash();
226
- }
227
- /**
228
- *
229
- * @param {String} contract
230
- * @param {Array} parameters
231
- * @returns
232
- */
233
- async deployContract(contract, constructorParameters = []) {
234
- const message = await createContractMessage(peernet.selectedAccount, contract, constructorParameters);
235
- try {
236
- await contractStore.put(await message.hash(), message.encoded);
237
- }
238
- catch (error) {
239
- throw error;
240
- }
241
- return this.createTransactionFrom(peernet.selectedAccount, addresses.contractFactory, 'registerContract', [await message.hash()]);
242
- }
243
- async deployContractMessage(message) {
244
- }
201
+ constructor() {
202
+ super();
203
+ }
204
+
205
+ async init() {
206
+
207
+ }
208
+
209
+ /**
210
+ *
211
+ * @param {Address} creator
212
+ * @param {String} contract
213
+ * @param {Array} constructorParameters
214
+ * @returns lib.createContractMessage
215
+ */
216
+ async createContractMessage(creator, contract, constructorParameters = []) {
217
+ return createContractMessage(creator, contract, constructorParameters)
218
+ }
219
+
220
+ /**
221
+ *
222
+ * @param {Address} creator
223
+ * @param {String} contract
224
+ * @param {Array} constructorParameters
225
+ * @returns {Address}
226
+ */
227
+ async createContractAddress(creator, contract, constructorParameters = []) {
228
+ contract = await this.createContractMessage(creator, contract, constructorParameters);
229
+ return contract.hash()
230
+ }
231
+
232
+ /**
233
+ *
234
+ * @param {String} contract
235
+ * @param {Array} parameters
236
+ * @returns
237
+ */
238
+ async deployContract(contract, constructorParameters = []) {
239
+ const message = await createContractMessage(peernet.selectedAccount, contract, constructorParameters);
240
+ try {
241
+ await contractStore.put(await message.hash(), message.encoded);
242
+ } catch (error) {
243
+ throw error
244
+ }
245
+ return this.createTransactionFrom(peernet.selectedAccount, addresses.contractFactory, 'registerContract', [await message.hash()])
246
+ }
247
+
248
+ async deployContractMessage(message) {
249
+
250
+ }
251
+
252
+
245
253
  }
246
254
 
247
255
  // import State from './state'
256
+
248
257
  class Machine {
249
- #contracts = {};
250
- #nonces = {};
251
- lastBlock = { index: 0, hash: '0x0', previousHash: '0x0' };
252
- constructor(blocks) {
253
- return this.#init(blocks);
254
- }
255
- #createMessage(sender = peernet.selectedAccount) {
256
- return {
257
- sender,
258
- call: this.execute,
259
- staticCall: this.get.bind(this)
260
- };
258
+ #contracts = {}
259
+ #nonces = {}
260
+ lastBlock = {index: 0, hash: '0x0', previousHash: '0x0'}
261
+
262
+ constructor(blocks) {
263
+ return this.#init(blocks)
264
+ }
265
+
266
+ #createMessage(sender = peernet.selectedAccount) {
267
+ return {
268
+ sender,
269
+ call: this.execute,
270
+ staticCall: this.get.bind(this)
261
271
  }
262
- async #onmessage(data) {
263
- switch (data.type) {
264
- case 'contractError': {
265
- console.warn(`removing contract ${await data.hash()}`);
266
- await contractStore.delete(await data.hash());
267
- break;
268
- }
269
- case 'initError': {
270
- console.error(`init error: ${data.message}`);
271
- break;
272
- }
273
- case 'executionError': {
274
- // console.warn(`error executing transaction ${data.message}`);
275
- pubsub.publish(data.id, { error: data.message });
276
- break;
277
- }
278
- case 'debug': {
279
- for (const message of data.messages)
280
- debug(message);
281
- break;
282
- }
283
- case 'machine-ready': {
284
- this.lastBlock = data.lastBlock;
285
- pubsub.publish('machine.ready', true);
286
- break;
287
- }
288
- case 'response': {
289
- pubsub.publish(data.id, data.value || false);
290
- break;
291
- }
272
+ }
273
+
274
+ async #onmessage(data) {
275
+ switch (data.type) {
276
+ case 'contractError': {
277
+ console.warn(`removing contract ${await data.hash()}`);
278
+ await contractStore.delete(await data.hash());
279
+ break
280
+ }
281
+
282
+ case 'initError': {
283
+ console.error(`init error: ${data.message}`);
284
+ break
285
+ }
286
+
287
+ case 'executionError': {
288
+ // console.warn(`error executing transaction ${data.message}`);
289
+ pubsub.publish(data.id, {error: data.message});
290
+ break
291
+ }
292
+
293
+ case 'debug': {
294
+ for (const message of data.messages) debug(message);
295
+ break
296
+ }
297
+ case 'machine-ready': {
298
+ this.lastBlock = data.lastBlock;
299
+ pubsub.publish('machine.ready', true);
300
+ break
301
+ }
302
+ case 'response': {
303
+ pubsub.publish(data.id, data.value || false);
304
+ break
305
+ }
306
+ }
307
+
308
+ }
309
+
310
+ async #init(blocks) {
311
+ return new Promise(async (resolve) => {
312
+ const machineReady = () => {
313
+ pubsub.unsubscribe('machine.ready', machineReady);
314
+ resolve(this);
315
+ };
316
+ pubsub.subscribe('machine.ready', machineReady);
317
+
318
+ this.worker = await new EasyWorker('node_modules/@leofcoin/workers/src/machine-worker.js', {serialization: 'advanced', type:'module'});
319
+ this.worker.onmessage(this.#onmessage.bind(this));
320
+ // const blocks = await blockStore.values()
321
+ const contracts = await Promise.all([
322
+ contractStore.get(contractFactory),
323
+ contractStore.get(nativeToken),
324
+ contractStore.get(validators),
325
+ contractStore.get(nameService)
326
+ ]);
327
+
328
+ const message = {
329
+ type: 'init',
330
+ input: {
331
+ contracts,
332
+ blocks,
333
+ peerid: peernet.peerId
292
334
  }
293
- }
294
- async #init(blocks) {
295
- return new Promise(async (resolve) => {
296
- const machineReady = () => {
297
- pubsub.unsubscribe('machine.ready', machineReady);
298
- resolve(this);
299
- };
300
- pubsub.subscribe('machine.ready', machineReady);
301
- this.worker = await new EasyWorker('node_modules/@leofcoin/workers/src/machine-worker.js', { serialization: 'advanced', type: 'module' });
302
- this.worker.onmessage(this.#onmessage.bind(this));
303
- // const blocks = await blockStore.values()
304
- const contracts = await Promise.all([
305
- contractStore.get(contractFactory),
306
- contractStore.get(nativeToken),
307
- contractStore.get(validators),
308
- contractStore.get(nameService)
309
- ]);
310
- const message = {
311
- type: 'init',
312
- input: {
313
- contracts,
314
- blocks,
315
- peerid: peernet.peerId
316
- }
317
- };
318
- this.worker.postMessage(message);
319
- });
320
- }
321
- async #runContract(contractMessage) {
322
- const hash = await contractMessage.hash();
323
- return new Promise((resolve, reject) => {
324
- const id = randombytes(20).toString('hex');
325
- const onmessage = message => {
326
- pubsub.unsubscribe(id, onmessage);
327
- if (message?.error)
328
- reject(message.error);
329
- else
330
- resolve(message);
331
- };
332
- pubsub.subscribe(id, onmessage);
333
- this.worker.postMessage({
334
- type: 'run',
335
- id,
336
- input: {
337
- decoded: contractMessage.decoded,
338
- encoded: contractMessage.encoded,
339
- hash
340
- }
341
- });
342
- });
343
- }
344
- /**
345
- *
346
- * @param {Address} contract
347
- * @param {String} method
348
- * @param {Array} parameters
349
- * @returns Promise<message>
350
- */
351
- async execute(contract, method, parameters) {
352
- try {
353
- if (contract === contractFactory && method === 'registerContract') {
354
- if (await this.has(parameters[0]))
355
- throw new Error(`duplicate contract @${parameters[0]}`);
356
- let message;
357
- if (!await contractStore.has(parameters[0])) {
358
- message = await peernet.get(parameters[0], 'contract');
359
- message = await new ContractMessage(message);
360
- await contractStore.put(await message.hash(), message.encoded);
361
- }
362
- if (!message) {
363
- message = await contractStore.get(parameters[0]);
364
- message = await new ContractMessage(message);
365
- }
366
- if (!await this.has(await message.hash()))
367
- await this.#runContract(message);
368
- }
335
+ };
336
+ this.worker.postMessage(message);
337
+ })
338
+
339
+ }
340
+
341
+ async #runContract(contractMessage) {
342
+ const hash = await contractMessage.hash();
343
+ return new Promise((resolve, reject) => {
344
+ const id = randombytes(20).toString('hex');
345
+ const onmessage = message => {
346
+ pubsub.unsubscribe(id, onmessage);
347
+ if (message?.error) reject(message.error);
348
+ else resolve(message);
349
+ };
350
+ pubsub.subscribe(id, onmessage);
351
+ this.worker.postMessage({
352
+ type: 'run',
353
+ id,
354
+ input: {
355
+ decoded: contractMessage.decoded,
356
+ encoded: contractMessage.encoded,
357
+ hash
369
358
  }
370
- catch (error) {
371
- throw new Error(`contract deployment failed for ${parameters[0]}\n${error.message}`);
359
+ });
360
+ })
361
+
362
+ }
363
+
364
+ /**
365
+ *
366
+ * @param {Address} contract
367
+ * @param {String} method
368
+ * @param {Array} parameters
369
+ * @returns Promise<message>
370
+ */
371
+ async execute(contract, method, parameters) {
372
+ try {
373
+ if (contract === contractFactory && method === 'registerContract') {
374
+ if (await this.has(parameters[0])) throw new Error(`duplicate contract @${parameters[0]}`)
375
+ let message;
376
+ if (!await contractStore.has(parameters[0])) {
377
+ message = await peernet.get(parameters[0], 'contract');
378
+ message = await new ContractMessage(message);
379
+ await contractStore.put(await message.hash(), message.encoded);
372
380
  }
373
- return new Promise((resolve, reject) => {
374
- const id = randombytes(20).toString('hex');
375
- const onmessage = message => {
376
- pubsub.unsubscribe(id, onmessage);
377
- if (message?.error)
378
- reject(message.error);
379
- else
380
- resolve(message);
381
- };
382
- pubsub.subscribe(id, onmessage);
383
- this.worker.postMessage({
384
- type: 'execute',
385
- id,
386
- input: {
387
- contract,
388
- method,
389
- params: parameters
390
- }
391
- });
392
- });
393
- }
394
- get(contract, method, parameters) {
395
- return new Promise((resolve, reject) => {
396
- const id = randombytes(20).toString();
397
- const onmessage = message => {
398
- pubsub.unsubscribe(id, onmessage);
399
- resolve(message);
400
- };
401
- pubsub.subscribe(id, onmessage);
402
- this.worker.postMessage({
403
- type: 'get',
404
- id,
405
- input: {
406
- contract,
407
- method,
408
- params: parameters
409
- }
410
- });
411
- });
412
- }
413
- async has(address) {
414
- return new Promise((resolve, reject) => {
415
- const id = randombytes(20).toString('hex');
416
- const onmessage = message => {
417
- pubsub.unsubscribe(id, onmessage);
418
- if (message?.error)
419
- reject(message.error);
420
- else
421
- resolve(message);
422
- };
423
- pubsub.subscribe(id, onmessage);
424
- this.worker.postMessage({
425
- type: 'has',
426
- id,
427
- input: {
428
- address
429
- }
430
- });
431
- });
432
- }
433
- async delete(hash) {
434
- return contractStore.delete(hash);
435
- }
436
- /**
437
- *
438
- * @returns Promise
439
- */
440
- async deleteAll() {
441
- let hashes = await contractStore.get();
442
- hashes = Object.keys(hashes).map(hash => this.delete(hash));
443
- return Promise.all(hashes);
444
- }
381
+ if (!message) {
382
+ message = await contractStore.get(parameters[0]);
383
+ message = await new ContractMessage(message);
384
+ }
385
+ if (!await this.has(await message.hash())) await this.#runContract(message);
386
+ }
387
+ } catch (error) {
388
+ throw new Error(`contract deployment failed for ${parameters[0]}\n${error.message}`)
389
+ }
390
+ return new Promise((resolve, reject) => {
391
+ const id = randombytes(20).toString('hex');
392
+ const onmessage = message => {
393
+ pubsub.unsubscribe(id, onmessage);
394
+ if (message?.error) reject(message.error);
395
+ else resolve(message);
396
+ };
397
+ pubsub.subscribe(id, onmessage);
398
+ this.worker.postMessage({
399
+ type: 'execute',
400
+ id,
401
+ input: {
402
+ contract,
403
+ method,
404
+ params: parameters
405
+ }
406
+ });
407
+ })
408
+
409
+ }
410
+
411
+ get(contract, method, parameters) {
412
+ return new Promise((resolve, reject) => {
413
+ const id = randombytes(20).toString();
414
+ const onmessage = message => {
415
+ pubsub.unsubscribe(id, onmessage);
416
+ resolve(message);
417
+ };
418
+ pubsub.subscribe(id, onmessage);
419
+ this.worker.postMessage({
420
+ type: 'get',
421
+ id,
422
+ input: {
423
+ contract,
424
+ method,
425
+ params: parameters
426
+ }
427
+ });
428
+ })
429
+ }
430
+
431
+
432
+ async has(address) {
433
+ return new Promise((resolve, reject) => {
434
+ const id = randombytes(20).toString('hex');
435
+ const onmessage = message => {
436
+ pubsub.unsubscribe(id, onmessage);
437
+ if (message?.error) reject(message.error);
438
+ else resolve(message);
439
+ };
440
+ pubsub.subscribe(id, onmessage);
441
+ this.worker.postMessage({
442
+ type: 'has',
443
+ id,
444
+ input: {
445
+ address
446
+ }
447
+ });
448
+ })
449
+ }
450
+
451
+ async delete(hash) {
452
+ return contractStore.delete(hash)
453
+ }
454
+
455
+ /**
456
+ *
457
+ * @returns Promise
458
+ */
459
+ async deleteAll() {
460
+ let hashes = await contractStore.get();
461
+ hashes = Object.keys(hashes).map(hash => this.delete(hash));
462
+ return Promise.all(hashes)
463
+ }
445
464
  }
446
465
 
447
466
  class Jobber {
@@ -548,7 +567,7 @@ class State extends Contract {
548
567
  super();
549
568
  }
550
569
  async init() {
551
- this.jobber = new Jobber(30_000);
570
+ this.jobber = new Jobber(30000);
552
571
  if (super.init)
553
572
  await super.init();
554
573
  await globalThis.peernet.addRequestHandler('lastBlock', this.#lastBlockHandler.bind(this));
@@ -912,7 +931,7 @@ class Chain extends State {
912
931
  console.log('epoch');
913
932
  const validators = await this.staticCall(addresses.validators, 'validators');
914
933
  console.log({ validators });
915
- if (!validators[globalThis.globalThis.peernet.selectedAccount]?.active)
934
+ if (!validators[peernet.selectedAccount]?.active)
916
935
  return;
917
936
  const start = Date.now();
918
937
  try {
@@ -994,6 +1013,7 @@ class Chain extends State {
994
1013
  globalThis.peernet.subscribe('add-block', this.#addBlock.bind(this));
995
1014
  globalThis.peernet.subscribe('invalid-transaction', this.#invalidTransaction.bind(this));
996
1015
  globalThis.peernet.subscribe('send-transaction', this.#sendTransaction.bind(this));
1016
+ globalThis.peernet.subscribe('add-transaction', this.#addTransaction.bind(this));
997
1017
  globalThis.peernet.subscribe('validator:timeout', this.#validatorTimeout.bind(this));
998
1018
  globalThis.pubsub.subscribe('peer:connected', this.#peerConnected.bind(this));
999
1019
  // todo some functions rely on state
@@ -1011,6 +1031,9 @@ class Chain extends State {
1011
1031
  }, validatorInfo.timeout);
1012
1032
  this.#jail.push(validatorInfo.address);
1013
1033
  }
1034
+ #addTransaction(message) {
1035
+ console.log(message);
1036
+ }
1014
1037
  async #prepareRequest(request) {
1015
1038
  let node = await new globalThis.peernet.protos['peernet-request']({ request });
1016
1039
  return globalThis.peernet.prepareMessage(node);
@@ -1025,13 +1048,26 @@ class Chain extends State {
1025
1048
  if (!peer.version || peer.version !== this.version)
1026
1049
  return;
1027
1050
  const lastBlock = await this.#makeRequest(peer, 'lastBlock');
1051
+ let transactionsInPool = await this.#makeRequest(peer, 'transactionPool');
1052
+ const transactions = await globalThis.transactionPoolStore.keys();
1053
+ console.log({ transactionsInPool });
1054
+ const transactionsToGet = [];
1055
+ for (const key of transactionsInPool) {
1056
+ if (!transactions.includes(key))
1057
+ transactionsToGet.push(transactionPoolStore.put(key, (await peernet.get(key))));
1058
+ }
1059
+ await Promise.all(transactionsToGet);
1028
1060
  if (Object.keys(lastBlock).length > 0) {
1029
1061
  if (!this.lastBlock || !this.blocks[this.blocks.length - 1]?.loaded || lastBlock && lastBlock.index > this.lastBlock?.index || !this.loaded && !this.resolving) {
1030
1062
  this.knownBlocks = await this.#makeRequest(peer, 'knownBlocks');
1031
1063
  await this.syncChain(lastBlock);
1032
1064
  // if (await this.hasTransactionToHandle() && this.#participating) this.#runEpoch()
1033
1065
  }
1066
+ else if (!this.knownBlocks)
1067
+ this.knownBlocks = await this.#makeRequest(peer, 'knownBlocks');
1034
1068
  }
1069
+ if (this.#participating)
1070
+ this.#runEpoch();
1035
1071
  }
1036
1072
  #epochTimeout;
1037
1073
  async #transactionPoolHandler() {
@@ -0,0 +1,13 @@
1
+ export default class SyncController {
2
+ #private;
3
+ get busy(): boolean;
4
+ get loading(): boolean;
5
+ get resolving(): boolean;
6
+ get fullyResolved(): boolean;
7
+ get fullyLoaded(): boolean;
8
+ constructor();
9
+ /**
10
+ * Resolves/rejects a promise or rejects on timeout
11
+ */
12
+ resolve(): void;
13
+ }
@@ -0,0 +1 @@
1
+ export type Address = string;
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@leofcoin/chain",
3
- "version": "1.4.79",
3
+ "version": "1.4.80",
4
4
  "description": "Official javascript implementation",
5
5
  "exports": {
6
6
  "./node": "./exports/node.js",
@@ -14,6 +14,7 @@
14
14
  ],
15
15
  "scripts": {
16
16
  "np": "np",
17
+ "watch": "rollup -c -w",
17
18
  "lint": "eslint src --fix",
18
19
  "c": "rollup -c",
19
20
  "w": "rollup -c -w",