@defisaver/automation-sdk 3.3.18 → 3.3.19-sub-fetching-dev

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 (55) hide show
  1. package/cjs/automation/private/StrategiesAutomation.d.ts +5 -1
  2. package/cjs/automation/private/StrategiesAutomation.js +19 -2
  3. package/cjs/automation/private/StrategiesAutomation.test.js +55 -0
  4. package/cjs/constants/index.js +35 -0
  5. package/cjs/services/apiSubscriptionsService.d.ts +7 -0
  6. package/cjs/services/apiSubscriptionsService.js +33 -0
  7. package/cjs/services/apiSubscriptionsService.test.d.ts +1 -0
  8. package/cjs/services/apiSubscriptionsService.test.js +69 -0
  9. package/cjs/services/ethereumService.test.js +4 -7
  10. package/cjs/services/strategiesService.js +40 -9
  11. package/cjs/services/strategiesService.test.js +0 -1
  12. package/cjs/services/strategySubService.d.ts +4 -0
  13. package/cjs/services/strategySubService.js +24 -0
  14. package/cjs/services/strategySubService.test.js +295 -0
  15. package/cjs/services/subDataService.d.ts +38 -0
  16. package/cjs/services/subDataService.js +76 -2
  17. package/cjs/services/subDataService.test.js +494 -4
  18. package/cjs/types/enums.d.ts +15 -2
  19. package/cjs/types/enums.js +15 -1
  20. package/cjs/types/index.d.ts +29 -3
  21. package/esm/automation/private/StrategiesAutomation.d.ts +5 -1
  22. package/esm/automation/private/StrategiesAutomation.js +20 -3
  23. package/esm/automation/private/StrategiesAutomation.test.js +56 -1
  24. package/esm/constants/index.js +35 -0
  25. package/esm/services/apiSubscriptionsService.d.ts +7 -0
  26. package/esm/services/apiSubscriptionsService.js +29 -0
  27. package/esm/services/apiSubscriptionsService.test.d.ts +1 -0
  28. package/esm/services/apiSubscriptionsService.test.js +67 -0
  29. package/esm/services/ethereumService.test.js +4 -7
  30. package/esm/services/strategiesService.js +40 -9
  31. package/esm/services/strategiesService.test.js +0 -1
  32. package/esm/services/strategySubService.d.ts +4 -0
  33. package/esm/services/strategySubService.js +24 -0
  34. package/esm/services/strategySubService.test.js +295 -0
  35. package/esm/services/subDataService.d.ts +38 -0
  36. package/esm/services/subDataService.js +74 -0
  37. package/esm/services/subDataService.test.js +494 -4
  38. package/esm/types/enums.d.ts +15 -2
  39. package/esm/types/enums.js +14 -0
  40. package/esm/types/index.d.ts +29 -3
  41. package/package.json +1 -1
  42. package/src/automation/private/StrategiesAutomation.test.ts +70 -1
  43. package/src/automation/private/StrategiesAutomation.ts +25 -1
  44. package/src/constants/index.ts +35 -0
  45. package/src/services/apiSubscriptionsService.test.ts +75 -0
  46. package/src/services/apiSubscriptionsService.ts +33 -0
  47. package/src/services/ethereumService.test.ts +5 -8
  48. package/src/services/strategiesService.test.ts +0 -1
  49. package/src/services/strategiesService.ts +43 -10
  50. package/src/services/strategySubService.test.ts +382 -0
  51. package/src/services/strategySubService.ts +87 -0
  52. package/src/services/subDataService.test.ts +608 -4
  53. package/src/services/subDataService.ts +107 -0
  54. package/src/types/enums.ts +14 -0
  55. package/src/types/index.ts +31 -2
@@ -1,6 +1,6 @@
1
1
  import type Web3 from 'web3';
2
2
  import type { PastEventOptions } from 'web3-eth-contract';
3
- import type { Position, Interfaces, EthereumAddress, SubscriptionOptions, Contract, ParseData, BlockNumber } from '../../types';
3
+ import type { Position, Interfaces, EthereumAddress, SubscriptionOptions, Contract, ParseData, BlockNumber, ApiSubscriptionRecord } from '../../types';
4
4
  import type { StrategyModel, Subscribe, SubStorage, UpdateData } from '../../types/contracts/generated/SubStorage';
5
5
  import type { ChainId } from '../../types/enums';
6
6
  import Automation from './Automation';
@@ -30,6 +30,10 @@ export default class StrategiesAutomation extends Automation {
30
30
  protected mergeSubs(_subscriptions: (Position.Automated | null)[]): Position.Automated[];
31
31
  protected _getSubscriptions(addresses?: EthereumAddress[], options?: SubscriptionOptions): Promise<(Position.Automated | null)[]>;
32
32
  getSubscriptions(options?: SubscriptionOptions): Promise<(Position.Automated | null)[]>;
33
+ /**
34
+ * @description Parses subscriptions returned by the automation API (GET /v1/subscriptions)
35
+ */
36
+ parseSubscriptionsFromApi(records: ApiSubscriptionRecord[], options?: SubscriptionOptions): (Position.Automated | null)[];
33
37
  getSubscriptionsFor(addresses: EthereumAddress[], options?: SubscriptionOptions): Promise<(Position.Automated | null)[]>;
34
38
  }
35
39
  export {};
@@ -19,6 +19,7 @@ const utils_1 = require("../../services/utils");
19
19
  const contractService_1 = require("../../services/contractService");
20
20
  const ethereumService_1 = require("../../services/ethereumService");
21
21
  const strategiesService_1 = require("../../services/strategiesService");
22
+ const apiSubscriptionsService_1 = require("../../services/apiSubscriptionsService");
22
23
  const Automation_1 = __importDefault(require("./Automation"));
23
24
  class StrategiesAutomation extends Automation_1.default {
24
25
  constructor(args) {
@@ -126,9 +127,11 @@ class StrategiesAutomation extends Automation_1.default {
126
127
  if (mergePairIndex !== -1) {
127
128
  const mergePair = mergeExtension[mergePairIndex];
128
129
  mergeExtension.splice(mergePairIndex, 1);
129
- subscriptions.push(Object.assign(Object.assign(Object.assign({}, mergePair), current), {
130
+ subscriptions.push(Object.assign(Object.assign(Object.assign(Object.assign(Object.assign({}, mergePair), current), {
130
131
  // @ts-ignore
131
- blockNumber: decimal_js_1.default.max(mergePair.blockNumber, current.blockNumber).toNumber(), subIds: [current.subId, mergePair.subId], isEnabled: mergePair.isEnabled || current.isEnabled, specific: Object.assign(Object.assign({}, mergePair.specific), current.specific) }));
132
+ blockNumber: decimal_js_1.default.max(mergePair.blockNumber, current.blockNumber).toNumber(), subIds: [current.subId, mergePair.subId], isEnabled: mergePair.isEnabled || current.isEnabled }), (0, utils_1.addToObjectIf)((0, utils_1.isDefined)(current.status), {
133
+ status: mergePair.status === enums_1.SubscriptionStatus.Active ? enums_1.SubscriptionStatus.Active : current.status,
134
+ })), { specific: Object.assign(Object.assign({}, mergePair.specific), current.specific) }));
132
135
  }
133
136
  else {
134
137
  subscriptions.push(Object.assign(Object.assign({}, current), { subIds: [current.subId] }));
@@ -189,6 +192,20 @@ class StrategiesAutomation extends Automation_1.default {
189
192
  return this._getSubscriptions(undefined, options);
190
193
  });
191
194
  }
195
+ /**
196
+ * @description Parses subscriptions returned by the automation API (GET /v1/subscriptions)
197
+ */
198
+ parseSubscriptionsFromApi(records, options) {
199
+ const filtered = (options === null || options === void 0 ? void 0 : options.enabledOnly) ? records.filter((record) => record.is_enabled) : records;
200
+ let subscriptions = filtered.map((record) => {
201
+ const position = this.getParsedSubscriptions((0, apiSubscriptionsService_1.parseDataFromApiSubscription)(record, this.chainId));
202
+ return position && Object.assign(Object.assign({}, position), { status: record.status });
203
+ });
204
+ if (options === null || options === void 0 ? void 0 : options.mergeSubs) {
205
+ subscriptions = this.mergeSubs(subscriptions);
206
+ }
207
+ return (options === null || options === void 0 ? void 0 : options.unexpiredOnly) ? this.removeExpiredSubscriptions(subscriptions) : subscriptions;
208
+ }
192
209
  getSubscriptionsFor(addresses, options) {
193
210
  return __awaiter(this, void 0, void 0, function* () {
194
211
  return this._getSubscriptions(addresses, options);
@@ -693,4 +693,59 @@ describe('Feature: StrategiesAutomation.ts', () => {
693
693
  (0, chai_1.expect)(loneBoost === null || loneBoost === void 0 ? void 0 : loneBoost.subId).to.equal(1);
694
694
  });
695
695
  }));
696
+ describe('When testing StrategiesAutomation.parseSubscriptionsFromApi', () => {
697
+ const strategiesAutomation = new StrategiesAutomation_1.default({
698
+ chainId: enums_1.ChainId.Ethereum,
699
+ provider: Web3_1,
700
+ providerFork: null,
701
+ });
702
+ const owner = '0x9cB7E19861665366011899d74E75d4F2A419aEeD';
703
+ const subData = [
704
+ '0x0000000000000000000000000000000000000000000000001bc16d674ec80000',
705
+ '0x0000000000000000000000000000000000000000000000000000000000000001',
706
+ '0x0000000000000000000000000000000000000000000000000000000000000001',
707
+ '0x0000000000000000000000000000000000000000000000000000000000000000',
708
+ ];
709
+ // Aave V3 leverage management: repay (bundle 8, ratio under) and boost (bundle 9, ratio over) for the same owner and market
710
+ const repay = {
711
+ id: 379,
712
+ wallet: owner,
713
+ wallet_type: 'safe',
714
+ is_enabled: true,
715
+ invalid: false,
716
+ status: enums_1.SubscriptionStatus.Active,
717
+ is_bundle: true,
718
+ strategy_or_bundle_id: 8,
719
+ strategy_ids: [34, 35],
720
+ sub_data_hash: '0xafa4d200be62f171b57b1ae0f4e8348d1ac3f6d0812ad6da74a2adae8037dde1',
721
+ trigger_data: ['0000000000000000000000009cb7e19861665366011899d74e75d4f2a419aeed0000000000000000000000002f39d218133afab8f2b819b1066c7e434ad94e9e00000000000000000000000000000000000000000000000019ac8532c27900000000000000000000000000000000000000000000000000000000000000000001'],
722
+ sub_data: subData,
723
+ block_number: 18015756,
724
+ additional_triggers: null,
725
+ };
726
+ const boost = Object.assign(Object.assign({}, repay), { id: 380, is_enabled: false, status: enums_1.SubscriptionStatus.Disabled, strategy_or_bundle_id: 9, sub_data_hash: '0x1111111111111111111111111111111111111111111111111111111111111111', trigger_data: ['0000000000000000000000009cb7e19861665366011899d74e75d4f2a419aeed0000000000000000000000002f39d218133afab8f2b819b1066c7e434ad94e9e0000000000000000000000000000000000000000000000002386f26fc10000000000000000000000000000000000000000000000000000000000000000000000'] });
727
+ it('Given API records should return parsed positions carrying the API status', () => {
728
+ const positions = strategiesAutomation.parseSubscriptionsFromApi([repay, boost]);
729
+ (0, chai_1.expect)(positions).to.have.length(2);
730
+ (0, chai_1.expect)(positions.map((p) => p === null || p === void 0 ? void 0 : p.subId)).to.eql([379, 380]);
731
+ (0, chai_1.expect)(positions.map((p) => p === null || p === void 0 ? void 0 : p.status)).to.eql([enums_1.SubscriptionStatus.Active, enums_1.SubscriptionStatus.Disabled]);
732
+ (0, chai_1.expect)(positions.map((p) => p === null || p === void 0 ? void 0 : p.isEnabled)).to.eql([true, false]);
733
+ });
734
+ it('Given mergeSubs option should merge the repay and boost pair and keep the active status', () => {
735
+ var _a, _b, _c;
736
+ const positions = strategiesAutomation.parseSubscriptionsFromApi([repay, boost], { mergeSubs: true });
737
+ (0, chai_1.expect)(positions).to.have.length(1);
738
+ (0, chai_1.expect)((_a = positions[0]) === null || _a === void 0 ? void 0 : _a.subIds).to.eql([379, 380]);
739
+ (0, chai_1.expect)((_b = positions[0]) === null || _b === void 0 ? void 0 : _b.isEnabled).to.equal(true);
740
+ (0, chai_1.expect)((_c = positions[0]) === null || _c === void 0 ? void 0 : _c.status).to.equal(enums_1.SubscriptionStatus.Active);
741
+ });
742
+ it('Given enabledOnly option should drop disabled records before parsing', () => {
743
+ const positions = strategiesAutomation.parseSubscriptionsFromApi([repay, boost], { enabledOnly: true });
744
+ (0, chai_1.expect)(positions.map((p) => p === null || p === void 0 ? void 0 : p.subId)).to.eql([379]);
745
+ });
746
+ it('Given a record of an unknown strategy should return null for it', () => {
747
+ const positions = strategiesAutomation.parseSubscriptionsFromApi([Object.assign(Object.assign({}, repay), { strategy_or_bundle_id: 9999 })]);
748
+ (0, chai_1.expect)(positions).to.eql([null]);
749
+ });
750
+ });
696
751
  });
@@ -122,6 +122,11 @@ exports.MAINNET_STRATEGIES_INFO = {
122
122
  strategyId: enums_1.Strategies.Identifiers.CollateralSwitch,
123
123
  protocol: exports.PROTOCOLS.Spark,
124
124
  },
125
+ [enums_1.Strategies.MainnetIds.SPARK_GENERIC_FL_COLLATERAL_SWITCH]: {
126
+ strategyOrBundleId: enums_1.Strategies.MainnetIds.SPARK_GENERIC_FL_COLLATERAL_SWITCH,
127
+ strategyId: enums_1.Strategies.Identifiers.EoaCollateralSwitch,
128
+ protocol: exports.PROTOCOLS.Spark,
129
+ },
125
130
  };
126
131
  exports.OPTIMISM_STRATEGIES_INFO = {
127
132
  [enums_1.Strategies.OptimismIds.EXCHANGE_DCA]: {
@@ -549,6 +554,31 @@ exports.MAINNET_BUNDLES_INFO = {
549
554
  strategyId: enums_1.Strategies.Identifiers.EoaCloseOnPrice,
550
555
  protocol: exports.PROTOCOLS.AaveV4,
551
556
  },
557
+ [enums_1.Bundles.MainnetIds.SPARK_EOA_REPAY]: {
558
+ strategyOrBundleId: enums_1.Bundles.MainnetIds.SPARK_EOA_REPAY,
559
+ strategyId: enums_1.Strategies.Identifiers.EoaRepay,
560
+ protocol: exports.PROTOCOLS.Spark,
561
+ },
562
+ [enums_1.Bundles.MainnetIds.SPARK_EOA_BOOST]: {
563
+ strategyOrBundleId: enums_1.Bundles.MainnetIds.SPARK_EOA_BOOST,
564
+ strategyId: enums_1.Strategies.Identifiers.EoaBoost,
565
+ protocol: exports.PROTOCOLS.Spark,
566
+ },
567
+ [enums_1.Bundles.MainnetIds.SPARK_EOA_CLOSE]: {
568
+ strategyOrBundleId: enums_1.Bundles.MainnetIds.SPARK_EOA_CLOSE,
569
+ strategyId: enums_1.Strategies.Identifiers.EoaCloseOnPrice,
570
+ protocol: exports.PROTOCOLS.Spark,
571
+ },
572
+ [enums_1.Bundles.MainnetIds.SPARK_EOA_REPAY_ON_PRICE]: {
573
+ strategyOrBundleId: enums_1.Bundles.MainnetIds.SPARK_EOA_REPAY_ON_PRICE,
574
+ strategyId: enums_1.Strategies.Identifiers.EoaRepayOnPrice,
575
+ protocol: exports.PROTOCOLS.Spark,
576
+ },
577
+ [enums_1.Bundles.MainnetIds.SPARK_EOA_BOOST_ON_PRICE]: {
578
+ strategyOrBundleId: enums_1.Bundles.MainnetIds.SPARK_EOA_BOOST_ON_PRICE,
579
+ strategyId: enums_1.Strategies.Identifiers.EoaBoostOnPrice,
580
+ protocol: exports.PROTOCOLS.Spark,
581
+ },
552
582
  [enums_1.Bundles.MainnetIds.MAKER_SW_LIQUIDATION_PROTECTION]: {
553
583
  strategyOrBundleId: enums_1.Bundles.MainnetIds.MAKER_SW_LIQUIDATION_PROTECTION,
554
584
  strategyId: enums_1.Strategies.Identifiers.LiquidationProtection,
@@ -624,6 +654,11 @@ exports.MAINNET_BUNDLES_INFO = {
624
654
  strategyId: enums_1.Strategies.Identifiers.EoaCloseOnPrice,
625
655
  protocol: exports.PROTOCOLS.MorphoBlue,
626
656
  },
657
+ [enums_1.Bundles.MainnetIds.SPARK_EOA_LIQUIDATION_PROTECTION]: {
658
+ strategyOrBundleId: enums_1.Bundles.MainnetIds.SPARK_EOA_LIQUIDATION_PROTECTION,
659
+ strategyId: enums_1.Strategies.Identifiers.EoaLiquidationProtection,
660
+ protocol: exports.PROTOCOLS.Spark,
661
+ },
627
662
  };
628
663
  exports.OPTIMISM_BUNDLES_INFO = {
629
664
  [enums_1.Bundles.OptimismIds.AAVE_V3_REPAY]: {
@@ -0,0 +1,7 @@
1
+ import type { ApiSubscriptionRecord, ParseData } from '../types';
2
+ import type { ChainId } from '../types/enums';
3
+ /**
4
+ * @description Maps a subscription record returned by the automation API to the data
5
+ * the parser expects from Subscribe events and SubStorage (trigger data is stored without 0x prefix)
6
+ */
7
+ export declare function parseDataFromApiSubscription(record: ApiSubscriptionRecord, chainId: ChainId): ParseData;
@@ -0,0 +1,33 @@
1
+ "use strict";
2
+ Object.defineProperty(exports, "__esModule", { value: true });
3
+ exports.parseDataFromApiSubscription = void 0;
4
+ function addHexPrefix(value) {
5
+ return value.startsWith('0x') ? value : `0x${value}`;
6
+ }
7
+ /**
8
+ * @description Maps a subscription record returned by the automation API to the data
9
+ * the parser expects from Subscribe events and SubStorage (trigger data is stored without 0x prefix)
10
+ */
11
+ function parseDataFromApiSubscription(record, chainId) {
12
+ return {
13
+ chainId,
14
+ blockNumber: record.block_number,
15
+ subscriptionEventData: {
16
+ subId: record.id.toString(),
17
+ proxy: record.wallet,
18
+ subHash: record.sub_data_hash,
19
+ subStruct: {
20
+ strategyOrBundleId: record.strategy_or_bundle_id.toString(),
21
+ isBundle: record.is_bundle,
22
+ triggerData: record.trigger_data.map(addHexPrefix),
23
+ subData: record.sub_data.map(addHexPrefix),
24
+ },
25
+ },
26
+ strategiesSubsData: {
27
+ userProxy: record.wallet,
28
+ isEnabled: record.is_enabled,
29
+ strategySubHash: record.sub_data_hash,
30
+ },
31
+ };
32
+ }
33
+ exports.parseDataFromApiSubscription = parseDataFromApiSubscription;
@@ -0,0 +1 @@
1
+ import '../configuration';
@@ -0,0 +1,69 @@
1
+ "use strict";
2
+ Object.defineProperty(exports, "__esModule", { value: true });
3
+ const chai_1 = require("chai");
4
+ const enums_1 = require("../types/enums");
5
+ require("../configuration");
6
+ const apiSubscriptionsService_1 = require("./apiSubscriptionsService");
7
+ const strategiesService_1 = require("./strategiesService");
8
+ describe('Feature: apiSubscriptionsService.ts', () => {
9
+ describe('When testing apiSubscriptionsService.parseDataFromApiSubscription', () => {
10
+ // same subscription as in strategiesService.test.ts, in the shape the automation API returns it
11
+ const record = {
12
+ id: 379,
13
+ wallet: '0x9cB7E19861665366011899d74E75d4F2A419aEeD',
14
+ wallet_type: 'safe',
15
+ is_enabled: true,
16
+ invalid: false,
17
+ status: enums_1.SubscriptionStatus.Active,
18
+ is_bundle: true,
19
+ strategy_or_bundle_id: 8,
20
+ strategy_ids: [34, 35],
21
+ sub_data_hash: '0xafa4d200be62f171b57b1ae0f4e8348d1ac3f6d0812ad6da74a2adae8037dde1',
22
+ trigger_data: [
23
+ '0000000000000000000000009cb7e19861665366011899d74e75d4f2a419aeed0000000000000000000000002f39d218133afab8f2b819b1066c7e434ad94e9e00000000000000000000000000000000000000000000000019ac8532c27900000000000000000000000000000000000000000000000000000000000000000001',
24
+ ],
25
+ sub_data: [
26
+ '0x0000000000000000000000000000000000000000000000001bc16d674ec80000',
27
+ '0x0000000000000000000000000000000000000000000000000000000000000001',
28
+ '0x0000000000000000000000000000000000000000000000000000000000000001',
29
+ '0x0000000000000000000000000000000000000000000000000000000000000000',
30
+ ],
31
+ block_number: 18015756,
32
+ additional_triggers: null,
33
+ };
34
+ const fromEvents = {
35
+ chainId: enums_1.ChainId.Ethereum,
36
+ blockNumber: 18015756,
37
+ subscriptionEventData: {
38
+ subId: '379',
39
+ proxy: '0x9cB7E19861665366011899d74E75d4F2A419aEeD',
40
+ subHash: '0xafa4d200be62f171b57b1ae0f4e8348d1ac3f6d0812ad6da74a2adae8037dde1',
41
+ subStruct: {
42
+ strategyOrBundleId: '8',
43
+ isBundle: true,
44
+ triggerData: [
45
+ '0x0000000000000000000000009cb7e19861665366011899d74e75d4f2a419aeed0000000000000000000000002f39d218133afab8f2b819b1066c7e434ad94e9e00000000000000000000000000000000000000000000000019ac8532c27900000000000000000000000000000000000000000000000000000000000000000001',
46
+ ],
47
+ subData: record.sub_data,
48
+ },
49
+ },
50
+ strategiesSubsData: {
51
+ userProxy: '0x9cB7E19861665366011899d74E75d4F2A419aEeD',
52
+ isEnabled: true,
53
+ strategySubHash: '0xafa4d200be62f171b57b1ae0f4e8348d1ac3f6d0812ad6da74a2adae8037dde1',
54
+ },
55
+ };
56
+ it('Given an API record should return the same parse data as Subscribe event and SubStorage would', () => {
57
+ (0, chai_1.expect)((0, apiSubscriptionsService_1.parseDataFromApiSubscription)(record, enums_1.ChainId.Ethereum)).to.eql(fromEvents);
58
+ });
59
+ it('Given an API record the parsed position should match the one parsed from events', () => {
60
+ const fromApi = (0, strategiesService_1.parseStrategiesAutomatedPosition)((0, apiSubscriptionsService_1.parseDataFromApiSubscription)(record, enums_1.ChainId.Ethereum));
61
+ (0, chai_1.expect)(fromApi).to.not.equal(null);
62
+ (0, chai_1.expect)(fromApi).to.eql((0, strategiesService_1.parseStrategiesAutomatedPosition)(fromEvents));
63
+ });
64
+ it('Given a disabled record should keep it disabled', () => {
65
+ const parseData = (0, apiSubscriptionsService_1.parseDataFromApiSubscription)(Object.assign(Object.assign({}, record), { is_enabled: false }), enums_1.ChainId.Ethereum);
66
+ (0, chai_1.expect)(parseData.strategiesSubsData.isEnabled).to.equal(false);
67
+ });
68
+ });
69
+ });
@@ -14,6 +14,7 @@ var __importDefault = (this && this.__importDefault) || function (mod) {
14
14
  Object.defineProperty(exports, "__esModule", { value: true });
15
15
  const web3_1 = __importDefault(require("web3"));
16
16
  const chai_1 = require("chai");
17
+ const lodash_1 = require("lodash");
17
18
  const tokens_1 = require("@defisaver/tokens");
18
19
  const enums_1 = require("../types/enums");
19
20
  require("../configuration");
@@ -101,7 +102,6 @@ describe('Feature: ethereumService.ts', () => {
101
102
  'address': '0x5f98805A4E8be255a32880FDeC7F6728C6568bA0',
102
103
  'blockHash': '0xb92cab2569456dbfbdb853d2c67d72c9a7580543dbcb55d483a77322b40755a4',
103
104
  'blockNumber': 15166163,
104
- 'blockTimestamp': '0x62d53ad8',
105
105
  'event': 'Transfer',
106
106
  'id': 'log_e2258e3a',
107
107
  'logIndex': 385,
@@ -128,7 +128,7 @@ describe('Feature: ethereumService.ts', () => {
128
128
  },
129
129
  ],
130
130
  [
131
- (0, contractService_1.makeErc20Contract)(Web3_1, (0, tokens_1.getAssetInfo)('LUSD').address, enums_1.ChainId.Ethereum),
131
+ Object.assign(Object.assign({}, (0, contractService_1.makeErc20Contract)(Web3_1, (0, tokens_1.getAssetInfo)('LUSD').address, enums_1.ChainId.Ethereum)), { createdBlock: 15166163 }),
132
132
  null,
133
133
  'Transfer',
134
134
  {
@@ -147,7 +147,6 @@ describe('Feature: ethereumService.ts', () => {
147
147
  'address': '0xDA10009cBd5D07dd0CeCc66161FC93D7c9000da1',
148
148
  'blockHash': '0xacb0213af63b4c17c436f084a96d1ac385641a59a9a4cf014ae3337cbe545aa7',
149
149
  'blockNumber': 5353002,
150
- 'blockTimestamp': '0x624c1a5b',
151
150
  'event': 'Transfer',
152
151
  'id': 'log_f49645b8',
153
152
  'logIndex': 1,
@@ -193,7 +192,6 @@ describe('Feature: ethereumService.ts', () => {
193
192
  'address': '0xDA10009cBd5D07dd0CeCc66161FC93D7c9000da1',
194
193
  'blockHash': '0xacb0213af63b4c17c436f084a96d1ac385641a59a9a4cf014ae3337cbe545aa7',
195
194
  'blockNumber': 5353002,
196
- 'blockTimestamp': '0x624c1a5b',
197
195
  'event': 'Transfer',
198
196
  'id': 'log_f49645b8',
199
197
  'logIndex': 1,
@@ -236,9 +234,8 @@ describe('Feature: ethereumService.ts', () => {
236
234
  ];
237
235
  examples.forEach(([expected, actual]) => {
238
236
  it(`Given ${actual} should return expected value: ${JSON.stringify(expected)}`, () => __awaiter(void 0, void 0, void 0, function* () {
239
- const data = yield (0, ethereumService_1.getEventsFromContract)(...actual);
240
- console.log(data);
241
- (0, chai_1.expect)(yield (0, ethereumService_1.getEventsFromContract)(...actual)).to.eql(expected);
237
+ const events = yield (0, ethereumService_1.getEventsFromContract)(...actual);
238
+ (0, chai_1.expect)(events.map((event) => (0, lodash_1.omit)(event, 'blockTimestamp'))).to.eql(expected);
242
239
  }));
243
240
  });
244
241
  });
@@ -359,11 +359,17 @@ function parseAaveV3CollateralSwitch(position, parseData) {
359
359
  function parseSparkCollateralSwitch(position, parseData) {
360
360
  const _position = (0, lodash_1.cloneDeep)(position);
361
361
  const { subStruct } = parseData.subscriptionEventData;
362
+ const isEOA = _position.strategy.strategyId.includes('eoa');
362
363
  const triggerData = triggerService.sparkQuotePriceTrigger.decode(subStruct.triggerData);
363
- const subData = subDataService.sparkCollateralSwitchSubData.decode(subStruct.subData);
364
+ const subData = isEOA
365
+ ? subDataService.sparkGenericFLCollateralSwitchSubData.decode(subStruct.subData)
366
+ : subDataService.sparkCollateralSwitchSubData.decode(subStruct.subData);
364
367
  _position.strategyData.decoded.triggerData = triggerData;
365
368
  _position.strategyData.decoded.subData = subData;
366
369
  _position.positionId = (0, utils_1.getPositionId)(_position.chainId, _position.protocol.id, _position.owner, subData.marketAddr);
370
+ _position.strategy.strategyId = isEOA
371
+ ? enums_1.Strategies.Identifiers.EoaCollateralSwitch
372
+ : enums_1.Strategies.Identifiers.CollateralSwitch;
367
373
  return _position;
368
374
  }
369
375
  function parseAaveV4LeverageManagement(position, parseData) {
@@ -775,19 +781,22 @@ function parseSparkLeverageManagement(position, parseData) {
775
781
  const _position = (0, lodash_1.cloneDeep)(position);
776
782
  const { subStruct, subId, subHash } = parseData.subscriptionEventData;
777
783
  const { isEnabled } = parseData.strategiesSubsData;
784
+ const isEOA = _position.strategy.strategyId.includes('eoa');
778
785
  const triggerData = triggerService.sparkRatioTrigger.decode(subStruct.triggerData);
779
- const subData = subDataService.legacySparkLeverageManagementSubData.decode(subStruct.subData);
786
+ const subData = isEOA
787
+ ? subDataService.sparkGenericLeverageManagementSubData.decode(subStruct.subData)
788
+ : subDataService.legacySparkLeverageManagementSubData.decode(subStruct.subData);
780
789
  _position.strategyData.decoded.triggerData = triggerData;
781
790
  _position.strategyData.decoded.subData = subData;
782
791
  _position.positionId = (0, utils_1.getPositionId)(_position.chainId, _position.protocol.id, _position.owner, triggerData.market);
783
- const isRepay = _position.strategy.strategyId === enums_1.Strategies.Identifiers.Repay;
792
+ const isRepay = [enums_1.Strategies.Identifiers.Repay, enums_1.Strategies.Identifiers.EoaRepay].includes(_position.strategy.strategyId);
784
793
  if (isRepay) {
785
794
  _position.specific = {
786
795
  triggerRepayRatio: triggerData.ratio,
787
796
  targetRepayRatio: subData.targetRatio,
788
797
  repayEnabled: isEnabled,
789
798
  subId1: Number(subId),
790
- mergeWithId: enums_1.Strategies.Identifiers.Boost,
799
+ mergeWithId: isEOA ? enums_1.Strategies.Identifiers.EoaBoost : enums_1.Strategies.Identifiers.Boost,
791
800
  subHashRepay: subHash,
792
801
  };
793
802
  }
@@ -797,19 +806,24 @@ function parseSparkLeverageManagement(position, parseData) {
797
806
  targetBoostRatio: subData.targetRatio,
798
807
  boostEnabled: isEnabled,
799
808
  subId2: Number(subId),
800
- mergeId: enums_1.Strategies.Identifiers.Boost,
809
+ mergeId: isEOA ? enums_1.Strategies.Identifiers.EoaBoost : enums_1.Strategies.Identifiers.Boost,
801
810
  subHashBoost: subHash,
802
811
  };
803
812
  }
804
- _position.strategy.strategyId = enums_1.Strategies.IdOverrides.LeverageManagement;
813
+ _position.strategy.strategyId = isEOA
814
+ ? enums_1.Strategies.IdOverrides.EoaLeverageManagement
815
+ : enums_1.Strategies.IdOverrides.LeverageManagement;
805
816
  return _position;
806
817
  }
807
818
  function parseSparkLiquidationProtection(position, parseData) {
808
819
  const _position = (0, lodash_1.cloneDeep)(position);
809
820
  const { subStruct, subId, subHash } = parseData.subscriptionEventData;
810
821
  const { isEnabled } = parseData.strategiesSubsData;
822
+ const isEOA = _position.strategy.strategyId.includes('eoa');
811
823
  const triggerData = triggerService.sparkRatioTrigger.decode(subStruct.triggerData);
812
- const subData = subDataService.sparkLiquidationProtectionSubData.decode(subStruct.subData);
824
+ const subData = isEOA
825
+ ? subDataService.sparkGenericLiquidationProtectionSubData.decode(subStruct.subData)
826
+ : subDataService.sparkLiquidationProtectionSubData.decode(subStruct.subData);
813
827
  _position.strategyData.decoded.triggerData = triggerData;
814
828
  _position.strategyData.decoded.subData = subData;
815
829
  _position.positionId = (0, utils_1.getPositionId)(_position.chainId, _position.protocol.id, _position.owner, triggerData.market);
@@ -820,14 +834,19 @@ function parseSparkLiquidationProtection(position, parseData) {
820
834
  subId1: Number(subId),
821
835
  subHashRepay: subHash,
822
836
  };
823
- _position.strategy.strategyId = enums_1.Strategies.IdOverrides.LiquidationProtection;
837
+ _position.strategy.strategyId = isEOA
838
+ ? enums_1.Strategies.IdOverrides.EoaLiquidationProtection
839
+ : enums_1.Strategies.IdOverrides.LiquidationProtection;
824
840
  return _position;
825
841
  }
826
842
  function parseSparkLeverageManagementOnPrice(position, parseData) {
827
843
  const _position = (0, lodash_1.cloneDeep)(position);
828
844
  const { subStruct } = parseData.subscriptionEventData;
845
+ const isEOA = _position.strategy.strategyId.includes('eoa');
829
846
  const triggerData = triggerService.sparkQuotePriceTrigger.decode(subStruct.triggerData);
830
- const subData = subDataService.sparkLeverageManagementOnPriceSubData.decode(subStruct.subData);
847
+ const subData = isEOA
848
+ ? subDataService.sparkLeverageManagementOnPriceGenericSubData.decode(subStruct.subData)
849
+ : subDataService.sparkLeverageManagementOnPriceSubData.decode(subStruct.subData);
831
850
  _position.strategyData.decoded.triggerData = triggerData;
832
851
  _position.strategyData.decoded.subData = subData;
833
852
  _position.positionId = (0, utils_1.getPositionId)(_position.chainId, _position.protocol.id, _position.owner, subData.marketAddr);
@@ -844,6 +863,9 @@ function parseSparkLeverageManagementOnPrice(position, parseData) {
844
863
  price: triggerData.price,
845
864
  ratioState: triggerData.ratioState,
846
865
  };
866
+ _position.strategy.strategyId = isEOA
867
+ ? enums_1.Strategies.IdOverrides.EoaLeverageManagementOnPrice
868
+ : enums_1.Strategies.IdOverrides.LeverageManagementOnPrice;
847
869
  return _position;
848
870
  }
849
871
  function parseSparkCloseOnPrice(position, parseData) {
@@ -851,9 +873,11 @@ function parseSparkCloseOnPrice(position, parseData) {
851
873
  const { subStruct } = parseData.subscriptionEventData;
852
874
  const triggerData = triggerService.sparkQuotePriceRangeTrigger.decode(subStruct.triggerData);
853
875
  const subData = subDataService.sparkCloseGenericSubData.decode(subStruct.subData);
876
+ const isEOA = _position.strategy.strategyId.includes('eoa');
854
877
  _position.strategyData.decoded.triggerData = triggerData;
855
878
  _position.strategyData.decoded.subData = subData;
856
879
  _position.positionId = (0, utils_1.getPositionId)(_position.chainId, _position.protocol.id, _position.owner, subData.marketAddr);
880
+ _position.strategy.strategyId = isEOA ? enums_1.Strategies.Identifiers.EoaCloseOnPrice : enums_1.Strategies.Identifiers.CloseOnPrice;
857
881
  const { takeProfitType, stopLossType } = (0, utils_1.getStopLossAndTakeProfitTypeByCloseStrategyType)(+subData.closeType);
858
882
  _position.specific = {
859
883
  collAsset: subData.collAsset,
@@ -1276,8 +1300,15 @@ const parsingMethodsMapping = {
1276
1300
  [enums_1.Strategies.Identifiers.RepayOnPrice]: parseSparkLeverageManagementOnPrice,
1277
1301
  [enums_1.Strategies.Identifiers.BoostOnPrice]: parseSparkLeverageManagementOnPrice,
1278
1302
  [enums_1.Strategies.Identifiers.CloseOnPrice]: parseSparkCloseOnPrice,
1303
+ [enums_1.Strategies.Identifiers.EoaRepay]: parseSparkLeverageManagement,
1304
+ [enums_1.Strategies.Identifiers.EoaBoost]: parseSparkLeverageManagement,
1305
+ [enums_1.Strategies.Identifiers.EoaRepayOnPrice]: parseSparkLeverageManagementOnPrice,
1306
+ [enums_1.Strategies.Identifiers.EoaBoostOnPrice]: parseSparkLeverageManagementOnPrice,
1307
+ [enums_1.Strategies.Identifiers.EoaCloseOnPrice]: parseSparkCloseOnPrice,
1279
1308
  [enums_1.Strategies.Identifiers.CollateralSwitch]: parseSparkCollateralSwitch,
1309
+ [enums_1.Strategies.Identifiers.EoaCollateralSwitch]: parseSparkCollateralSwitch,
1280
1310
  [enums_1.Strategies.Identifiers.LiquidationProtection]: parseSparkLiquidationProtection,
1311
+ [enums_1.Strategies.Identifiers.EoaLiquidationProtection]: parseSparkLiquidationProtection,
1281
1312
  },
1282
1313
  [enums_1.ProtocolIdentifiers.StrategiesAutomation.CrvUSD]: {
1283
1314
  [enums_1.Strategies.Identifiers.Repay]: parseCrvUSDLeverageManagement,
@@ -83,7 +83,6 @@ describe('Feature: strategiesService.ts', () => {
83
83
  subId: '379',
84
84
  proxy: '0x9cb7e19861665366011899d74e75d4f2a419aeed',
85
85
  subHash: '0xafa4d200be62f171b57b1ae0f4e8348d1ac3f6d0812ad6da74a2adae8037dde1',
86
- // @ts-ignore
87
86
  subStruct: {
88
87
  strategyOrBundleId: '8',
89
88
  isBundle: true,
@@ -93,7 +93,11 @@ export declare const sparkEncode: {
93
93
  closeOnPriceGeneric(strategyOrBundleId: number, collAsset: EthereumAddress, collAssetId: number, debtAsset: EthereumAddress, debtAssetId: number, marketAddr: EthereumAddress, user: EthereumAddress, stopLossPrice?: number, stopLossType?: CloseToAssetType, takeProfitPrice?: number, takeProfitType?: CloseToAssetType): (number | boolean | string[])[];
94
94
  leverageManagement(strategyOrBundleId: number, market: EthereumAddress, user: EthereumAddress, ratioState: RatioState, targetRatio: number, triggerRatio: number): (number | boolean | string[])[];
95
95
  liquidationProtection(strategyOrBundleId: number, market: EthereumAddress, user: EthereumAddress, ratioState: RatioState, targetRatio: number, triggerRatio: number): (number | boolean | string[])[];
96
+ leverageManagementGeneric(strategyOrBundleId: number, market: EthereumAddress, user: EthereumAddress, ratioState: RatioState, targetRatio: number, triggerRatio: number): (number | boolean | string[])[];
97
+ liquidationProtectionGeneric(strategyOrBundleId: number, market: EthereumAddress, user: EthereumAddress, ratioState: RatioState, targetRatio: number, triggerRatio: number): (number | boolean | string[])[];
98
+ leverageManagementOnPriceGeneric(strategyOrBundleId: number, price: number, ratioState: RatioState, collAsset: EthereumAddress, collAssetId: number, debtAsset: EthereumAddress, debtAssetId: number, marketAddr: EthereumAddress, targetRatio: number, user: EthereumAddress): (number | boolean | string[])[];
96
99
  collateralSwitch(strategyOrBundleId: number, fromAsset: EthereumAddress, fromAssetId: number, toAsset: EthereumAddress, toAssetId: number, marketAddr: EthereumAddress, amountToSwitch: string, baseTokenAddress: EthereumAddress, quoteTokenAddress: EthereumAddress, price: number, state: RatioState): (number | boolean | string[])[];
100
+ collateralSwitchGeneric(strategyOrBundleId: number, fromAsset: EthereumAddress, fromAssetId: number, toAsset: EthereumAddress, toAssetId: number, marketAddr: EthereumAddress, amountToSwitch: string, user: EthereumAddress, baseTokenAddress: EthereumAddress, quoteTokenAddress: EthereumAddress, price: number, state: RatioState): (number | boolean | string[])[];
97
101
  };
98
102
  export declare const crvUSDEncode: {
99
103
  leverageManagement(owner: EthereumAddress, controllerAddr: EthereumAddress, ratioState: RatioState, targetRatio: number, triggerRatio: number, collTokenAddr: EthereumAddress, crvUSDAddr: EthereumAddress): (boolean | string[] | Bundles.MainnetIds)[];
@@ -276,12 +276,36 @@ exports.sparkEncode = {
276
276
  const triggerData = triggerService.sparkRatioTrigger.encode(user, market, triggerRatio, ratioState);
277
277
  return [strategyOrBundleId, isBundle, triggerData, subData];
278
278
  },
279
+ leverageManagementGeneric(strategyOrBundleId, market, user, ratioState, targetRatio, triggerRatio) {
280
+ const isBundle = true;
281
+ const subData = subDataService.sparkGenericLeverageManagementSubData.encode(targetRatio, ratioState, market, user);
282
+ const triggerData = triggerService.sparkRatioTrigger.encode(user, market, triggerRatio, ratioState);
283
+ return [strategyOrBundleId, isBundle, triggerData, subData];
284
+ },
285
+ liquidationProtectionGeneric(strategyOrBundleId, market, user, ratioState, targetRatio, triggerRatio) {
286
+ const isBundle = true;
287
+ const subData = subDataService.sparkGenericLiquidationProtectionSubData.encode(targetRatio, ratioState, market, user);
288
+ const triggerData = triggerService.sparkRatioTrigger.encode(user, market, triggerRatio, ratioState);
289
+ return [strategyOrBundleId, isBundle, triggerData, subData];
290
+ },
291
+ leverageManagementOnPriceGeneric(strategyOrBundleId, price, ratioState, collAsset, collAssetId, debtAsset, debtAssetId, marketAddr, targetRatio, user) {
292
+ const isBundle = true;
293
+ const subData = subDataService.sparkLeverageManagementOnPriceGenericSubData.encode(collAsset, collAssetId, debtAsset, debtAssetId, marketAddr, targetRatio, user);
294
+ const triggerData = triggerService.sparkQuotePriceTrigger.encode(collAsset, debtAsset, price, ratioState);
295
+ return [strategyOrBundleId, isBundle, triggerData, subData];
296
+ },
279
297
  collateralSwitch(strategyOrBundleId, fromAsset, fromAssetId, toAsset, toAssetId, marketAddr, amountToSwitch, baseTokenAddress, quoteTokenAddress, price, state) {
280
298
  const isBundle = false;
281
299
  const subDataEncoded = subDataService.sparkCollateralSwitchSubData.encode(fromAsset, fromAssetId, toAsset, toAssetId, marketAddr, amountToSwitch);
282
300
  const triggerDataEncoded = triggerService.sparkQuotePriceTrigger.encode(baseTokenAddress, quoteTokenAddress, price, state);
283
301
  return [strategyOrBundleId, isBundle, triggerDataEncoded, subDataEncoded];
284
302
  },
303
+ collateralSwitchGeneric(strategyOrBundleId, fromAsset, fromAssetId, toAsset, toAssetId, marketAddr, amountToSwitch, user, baseTokenAddress, quoteTokenAddress, price, state) {
304
+ const isBundle = false;
305
+ const subDataEncoded = subDataService.sparkGenericFLCollateralSwitchSubData.encode(fromAsset, fromAssetId, toAsset, toAssetId, marketAddr, amountToSwitch, user);
306
+ const triggerDataEncoded = triggerService.sparkQuotePriceTrigger.encode(baseTokenAddress, quoteTokenAddress, price, state);
307
+ return [strategyOrBundleId, isBundle, triggerDataEncoded, subDataEncoded];
308
+ },
285
309
  };
286
310
  exports.crvUSDEncode = {
287
311
  leverageManagement(owner, controllerAddr, ratioState, targetRatio, triggerRatio, collTokenAddr, crvUSDAddr) {