@ledgerhq/live-common 34.38.1-hotfix.0 → 34.38.2-nightly.0

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 (256) hide show
  1. package/lib/__tests__/hw/getLatestFirmwareForDevice.js +4 -0
  2. package/lib/__tests__/hw/getLatestFirmwareForDevice.js.map +1 -1
  3. package/lib/__tests__/test-helpers/deviceInfos.d.ts.map +1 -1
  4. package/lib/__tests__/test-helpers/deviceInfos.js +5 -0
  5. package/lib/__tests__/test-helpers/deviceInfos.js.map +1 -1
  6. package/lib/apps/mock.d.ts +2 -32
  7. package/lib/apps/mock.d.ts.map +1 -1
  8. package/lib/apps/mock.js +3 -0
  9. package/lib/apps/mock.js.map +1 -1
  10. package/lib/apps/polyfill.d.ts +4 -1
  11. package/lib/apps/polyfill.d.ts.map +1 -1
  12. package/lib/bridge/cache.d.ts.map +1 -1
  13. package/lib/bridge/cache.js +2 -2
  14. package/lib/bridge/cache.js.map +1 -1
  15. package/lib/bridge/cache.test.d.ts +2 -0
  16. package/lib/bridge/cache.test.d.ts.map +1 -0
  17. package/lib/bridge/cache.test.js +63 -0
  18. package/lib/bridge/cache.test.js.map +1 -0
  19. package/lib/deposit/deposit.test.js +418 -74
  20. package/lib/deposit/deposit.test.js.map +1 -1
  21. package/lib/deposit/helper.d.ts +1 -0
  22. package/lib/deposit/helper.d.ts.map +1 -1
  23. package/lib/deposit/helper.js +19 -6
  24. package/lib/deposit/helper.js.map +1 -1
  25. package/lib/deviceSDK/tasks/getDeviceInfo.d.ts.map +1 -1
  26. package/lib/deviceSDK/tasks/getDeviceInfo.js +3 -1
  27. package/lib/deviceSDK/tasks/getDeviceInfo.js.map +1 -1
  28. package/lib/e2e/enum/Provider.d.ts +1 -1
  29. package/lib/e2e/enum/Provider.d.ts.map +1 -1
  30. package/lib/e2e/enum/Provider.js +1 -1
  31. package/lib/e2e/enum/Provider.js.map +1 -1
  32. package/lib/e2e/index.d.ts +5 -0
  33. package/lib/e2e/index.d.ts.map +1 -1
  34. package/lib/e2e/swap.d.ts.map +1 -1
  35. package/lib/e2e/swap.js +10 -7
  36. package/lib/e2e/swap.js.map +1 -1
  37. package/lib/env.react.d.ts +1 -1
  38. package/lib/env.react.d.ts.map +1 -1
  39. package/lib/featureFlags/defaultFeatures.d.ts.map +1 -1
  40. package/lib/featureFlags/defaultFeatures.js +35 -0
  41. package/lib/featureFlags/defaultFeatures.js.map +1 -1
  42. package/lib/featureFlags/useFeature.d.ts +1 -1
  43. package/lib/featureFlags/useFeature.d.ts.map +1 -1
  44. package/lib/hooks/useAppVersionBlockCheck.d.ts +11 -0
  45. package/lib/hooks/useAppVersionBlockCheck.d.ts.map +1 -0
  46. package/lib/hooks/useAppVersionBlockCheck.js +32 -0
  47. package/lib/hooks/useAppVersionBlockCheck.js.map +1 -0
  48. package/lib/hooks/useAppVersionBlockCheck.test.d.ts +2 -0
  49. package/lib/hooks/useAppVersionBlockCheck.test.d.ts.map +1 -0
  50. package/lib/hooks/useAppVersionBlockCheck.test.js +133 -0
  51. package/lib/hooks/useAppVersionBlockCheck.test.js.map +1 -0
  52. package/lib/hw/connectAppEventMapper.d.ts.map +1 -1
  53. package/lib/hw/connectAppEventMapper.js +3 -1
  54. package/lib/hw/connectAppEventMapper.js.map +1 -1
  55. package/lib/hw/connectManager.d.ts.map +1 -1
  56. package/lib/hw/connectManager.js +9 -0
  57. package/lib/hw/connectManager.js.map +1 -1
  58. package/lib/hw/customLockScreenLoad.d.ts.map +1 -1
  59. package/lib/hw/customLockScreenLoad.js +22 -18
  60. package/lib/hw/customLockScreenLoad.js.map +1 -1
  61. package/lib/hw/customLockScreenLoad.test.d.ts +2 -0
  62. package/lib/hw/customLockScreenLoad.test.d.ts.map +1 -0
  63. package/lib/hw/customLockScreenLoad.test.js +63 -0
  64. package/lib/hw/customLockScreenLoad.test.js.map +1 -0
  65. package/lib/hw/extractOnboardingState.d.ts +15 -2
  66. package/lib/hw/extractOnboardingState.d.ts.map +1 -1
  67. package/lib/hw/extractOnboardingState.js +67 -19
  68. package/lib/hw/extractOnboardingState.js.map +1 -1
  69. package/lib/hw/extractOnboardingState.test.js +96 -1
  70. package/lib/hw/extractOnboardingState.test.js.map +1 -1
  71. package/lib/hw/getDeviceInfo.d.ts.map +1 -1
  72. package/lib/hw/getDeviceInfo.js +3 -1
  73. package/lib/hw/getDeviceInfo.js.map +1 -1
  74. package/lib/hw/getGenuineCheckFromDeviceId.test.js +1 -0
  75. package/lib/hw/getGenuineCheckFromDeviceId.test.js.map +1 -1
  76. package/lib/hw/getOnboardingStatePolling.js +1 -1
  77. package/lib/hw/getOnboardingStatePolling.js.map +1 -1
  78. package/lib/hw/getOnboardingStatePolling.test.js +2 -0
  79. package/lib/hw/getOnboardingStatePolling.test.js.map +1 -1
  80. package/lib/hw/isFirmwareUpdateVersionSupported.test.js +2 -1
  81. package/lib/hw/isFirmwareUpdateVersionSupported.test.js.map +1 -1
  82. package/lib/mock/fixtures/aDeviceInfo.d.ts.map +1 -1
  83. package/lib/mock/fixtures/aDeviceInfo.js +1 -0
  84. package/lib/mock/fixtures/aDeviceInfo.js.map +1 -1
  85. package/lib/modularDrawer/__test__/useModularDrawerVisibility.test.d.ts +2 -0
  86. package/lib/modularDrawer/__test__/useModularDrawerVisibility.test.d.ts.map +1 -0
  87. package/lib/modularDrawer/__test__/useModularDrawerVisibility.test.js +107 -0
  88. package/lib/modularDrawer/__test__/useModularDrawerVisibility.test.js.map +1 -0
  89. package/lib/modularDrawer/enums.d.ts +8 -0
  90. package/lib/modularDrawer/enums.d.ts.map +1 -0
  91. package/lib/modularDrawer/enums.js +12 -0
  92. package/lib/modularDrawer/enums.js.map +1 -0
  93. package/lib/modularDrawer/useModularDrawerVisibility.d.ts +9 -0
  94. package/lib/modularDrawer/useModularDrawerVisibility.d.ts.map +1 -0
  95. package/lib/modularDrawer/useModularDrawerVisibility.js +18 -0
  96. package/lib/modularDrawer/useModularDrawerVisibility.js.map +1 -0
  97. package/lib/onboarding/hooks/useOnboardingStatePolling.test.js +2 -0
  98. package/lib/onboarding/hooks/useOnboardingStatePolling.test.js.map +1 -1
  99. package/lib/wallet-api/types.d.ts +1 -1
  100. package/lib/wallet-api/types.d.ts.map +1 -1
  101. package/lib/wallet-api/useDappLogic.d.ts.map +1 -1
  102. package/lib/wallet-api/useDappLogic.js +3 -24
  103. package/lib/wallet-api/useDappLogic.js.map +1 -1
  104. package/lib/wallet-api/utils/txTrackingHelper.d.ts +3 -0
  105. package/lib/wallet-api/utils/txTrackingHelper.d.ts.map +1 -0
  106. package/lib/wallet-api/utils/txTrackingHelper.js +16 -0
  107. package/lib/wallet-api/utils/txTrackingHelper.js.map +1 -0
  108. package/lib/wallet-api/utils/txTrackingHelper.test.d.ts +2 -0
  109. package/lib/wallet-api/utils/txTrackingHelper.test.d.ts.map +1 -0
  110. package/lib/wallet-api/utils/txTrackingHelper.test.js +70 -0
  111. package/lib/wallet-api/utils/txTrackingHelper.test.js.map +1 -0
  112. package/lib-es/__tests__/hw/getLatestFirmwareForDevice.js +4 -0
  113. package/lib-es/__tests__/hw/getLatestFirmwareForDevice.js.map +1 -1
  114. package/lib-es/__tests__/test-helpers/deviceInfos.d.ts.map +1 -1
  115. package/lib-es/__tests__/test-helpers/deviceInfos.js +5 -0
  116. package/lib-es/__tests__/test-helpers/deviceInfos.js.map +1 -1
  117. package/lib-es/apps/mock.d.ts +2 -32
  118. package/lib-es/apps/mock.d.ts.map +1 -1
  119. package/lib-es/apps/mock.js +3 -0
  120. package/lib-es/apps/mock.js.map +1 -1
  121. package/lib-es/apps/polyfill.d.ts +4 -1
  122. package/lib-es/apps/polyfill.d.ts.map +1 -1
  123. package/lib-es/bridge/cache.d.ts.map +1 -1
  124. package/lib-es/bridge/cache.js +2 -2
  125. package/lib-es/bridge/cache.js.map +1 -1
  126. package/lib-es/bridge/cache.test.d.ts +2 -0
  127. package/lib-es/bridge/cache.test.d.ts.map +1 -0
  128. package/lib-es/bridge/cache.test.js +38 -0
  129. package/lib-es/bridge/cache.test.js.map +1 -0
  130. package/lib-es/deposit/deposit.test.js +419 -75
  131. package/lib-es/deposit/deposit.test.js.map +1 -1
  132. package/lib-es/deposit/helper.d.ts +1 -0
  133. package/lib-es/deposit/helper.d.ts.map +1 -1
  134. package/lib-es/deposit/helper.js +18 -6
  135. package/lib-es/deposit/helper.js.map +1 -1
  136. package/lib-es/deviceSDK/tasks/getDeviceInfo.d.ts.map +1 -1
  137. package/lib-es/deviceSDK/tasks/getDeviceInfo.js +3 -1
  138. package/lib-es/deviceSDK/tasks/getDeviceInfo.js.map +1 -1
  139. package/lib-es/e2e/enum/Provider.d.ts +1 -1
  140. package/lib-es/e2e/enum/Provider.d.ts.map +1 -1
  141. package/lib-es/e2e/enum/Provider.js +1 -1
  142. package/lib-es/e2e/enum/Provider.js.map +1 -1
  143. package/lib-es/e2e/index.d.ts +5 -0
  144. package/lib-es/e2e/index.d.ts.map +1 -1
  145. package/lib-es/e2e/swap.d.ts.map +1 -1
  146. package/lib-es/e2e/swap.js +10 -7
  147. package/lib-es/e2e/swap.js.map +1 -1
  148. package/lib-es/env.react.d.ts +1 -1
  149. package/lib-es/env.react.d.ts.map +1 -1
  150. package/lib-es/featureFlags/defaultFeatures.d.ts.map +1 -1
  151. package/lib-es/featureFlags/defaultFeatures.js +35 -0
  152. package/lib-es/featureFlags/defaultFeatures.js.map +1 -1
  153. package/lib-es/featureFlags/useFeature.d.ts +1 -1
  154. package/lib-es/featureFlags/useFeature.d.ts.map +1 -1
  155. package/lib-es/hooks/useAppVersionBlockCheck.d.ts +11 -0
  156. package/lib-es/hooks/useAppVersionBlockCheck.d.ts.map +1 -0
  157. package/lib-es/hooks/useAppVersionBlockCheck.js +25 -0
  158. package/lib-es/hooks/useAppVersionBlockCheck.js.map +1 -0
  159. package/lib-es/hooks/useAppVersionBlockCheck.test.d.ts +2 -0
  160. package/lib-es/hooks/useAppVersionBlockCheck.test.d.ts.map +1 -0
  161. package/lib-es/hooks/useAppVersionBlockCheck.test.js +131 -0
  162. package/lib-es/hooks/useAppVersionBlockCheck.test.js.map +1 -0
  163. package/lib-es/hw/connectAppEventMapper.d.ts.map +1 -1
  164. package/lib-es/hw/connectAppEventMapper.js +3 -1
  165. package/lib-es/hw/connectAppEventMapper.js.map +1 -1
  166. package/lib-es/hw/connectManager.d.ts.map +1 -1
  167. package/lib-es/hw/connectManager.js +9 -0
  168. package/lib-es/hw/connectManager.js.map +1 -1
  169. package/lib-es/hw/customLockScreenLoad.d.ts.map +1 -1
  170. package/lib-es/hw/customLockScreenLoad.js +22 -18
  171. package/lib-es/hw/customLockScreenLoad.js.map +1 -1
  172. package/lib-es/hw/customLockScreenLoad.test.d.ts +2 -0
  173. package/lib-es/hw/customLockScreenLoad.test.d.ts.map +1 -0
  174. package/lib-es/hw/customLockScreenLoad.test.js +58 -0
  175. package/lib-es/hw/customLockScreenLoad.test.js.map +1 -0
  176. package/lib-es/hw/extractOnboardingState.d.ts +15 -2
  177. package/lib-es/hw/extractOnboardingState.d.ts.map +1 -1
  178. package/lib-es/hw/extractOnboardingState.js +66 -18
  179. package/lib-es/hw/extractOnboardingState.js.map +1 -1
  180. package/lib-es/hw/extractOnboardingState.test.js +97 -2
  181. package/lib-es/hw/extractOnboardingState.test.js.map +1 -1
  182. package/lib-es/hw/getDeviceInfo.d.ts.map +1 -1
  183. package/lib-es/hw/getDeviceInfo.js +3 -1
  184. package/lib-es/hw/getDeviceInfo.js.map +1 -1
  185. package/lib-es/hw/getGenuineCheckFromDeviceId.test.js +1 -0
  186. package/lib-es/hw/getGenuineCheckFromDeviceId.test.js.map +1 -1
  187. package/lib-es/hw/getOnboardingStatePolling.js +1 -1
  188. package/lib-es/hw/getOnboardingStatePolling.js.map +1 -1
  189. package/lib-es/hw/getOnboardingStatePolling.test.js +2 -0
  190. package/lib-es/hw/getOnboardingStatePolling.test.js.map +1 -1
  191. package/lib-es/hw/isFirmwareUpdateVersionSupported.test.js +2 -1
  192. package/lib-es/hw/isFirmwareUpdateVersionSupported.test.js.map +1 -1
  193. package/lib-es/mock/fixtures/aDeviceInfo.d.ts.map +1 -1
  194. package/lib-es/mock/fixtures/aDeviceInfo.js +1 -0
  195. package/lib-es/mock/fixtures/aDeviceInfo.js.map +1 -1
  196. package/lib-es/modularDrawer/__test__/useModularDrawerVisibility.test.d.ts +2 -0
  197. package/lib-es/modularDrawer/__test__/useModularDrawerVisibility.test.d.ts.map +1 -0
  198. package/lib-es/modularDrawer/__test__/useModularDrawerVisibility.test.js +105 -0
  199. package/lib-es/modularDrawer/__test__/useModularDrawerVisibility.test.js.map +1 -0
  200. package/lib-es/modularDrawer/enums.d.ts +8 -0
  201. package/lib-es/modularDrawer/enums.d.ts.map +1 -0
  202. package/lib-es/modularDrawer/enums.js +9 -0
  203. package/lib-es/modularDrawer/enums.js.map +1 -0
  204. package/lib-es/modularDrawer/useModularDrawerVisibility.d.ts +9 -0
  205. package/lib-es/modularDrawer/useModularDrawerVisibility.d.ts.map +1 -0
  206. package/lib-es/modularDrawer/useModularDrawerVisibility.js +14 -0
  207. package/lib-es/modularDrawer/useModularDrawerVisibility.js.map +1 -0
  208. package/lib-es/onboarding/hooks/useOnboardingStatePolling.test.js +2 -0
  209. package/lib-es/onboarding/hooks/useOnboardingStatePolling.test.js.map +1 -1
  210. package/lib-es/wallet-api/types.d.ts +1 -1
  211. package/lib-es/wallet-api/types.d.ts.map +1 -1
  212. package/lib-es/wallet-api/useDappLogic.d.ts.map +1 -1
  213. package/lib-es/wallet-api/useDappLogic.js +3 -24
  214. package/lib-es/wallet-api/useDappLogic.js.map +1 -1
  215. package/lib-es/wallet-api/utils/txTrackingHelper.d.ts +3 -0
  216. package/lib-es/wallet-api/utils/txTrackingHelper.d.ts.map +1 -0
  217. package/lib-es/wallet-api/utils/txTrackingHelper.js +12 -0
  218. package/lib-es/wallet-api/utils/txTrackingHelper.js.map +1 -0
  219. package/lib-es/wallet-api/utils/txTrackingHelper.test.d.ts +2 -0
  220. package/lib-es/wallet-api/utils/txTrackingHelper.test.d.ts.map +1 -0
  221. package/lib-es/wallet-api/utils/txTrackingHelper.test.js +68 -0
  222. package/lib-es/wallet-api/utils/txTrackingHelper.test.js.map +1 -0
  223. package/package.json +50 -50
  224. package/src/__tests__/hw/getLatestFirmwareForDevice.ts +8 -3
  225. package/src/__tests__/test-helpers/deviceInfos.ts +5 -0
  226. package/src/apps/mock.ts +5 -2
  227. package/src/bridge/cache.test.ts +46 -0
  228. package/src/bridge/cache.ts +5 -2
  229. package/src/deposit/deposit.test.ts +611 -136
  230. package/src/deposit/helper.ts +27 -9
  231. package/src/deviceSDK/tasks/getDeviceInfo.ts +3 -0
  232. package/src/e2e/enum/Provider.ts +1 -1
  233. package/src/e2e/swap.ts +12 -7
  234. package/src/featureFlags/defaultFeatures.ts +35 -0
  235. package/src/hooks/useAppVersionBlockCheck.test.ts +134 -0
  236. package/src/hooks/useAppVersionBlockCheck.ts +65 -0
  237. package/src/hw/connectAppEventMapper.ts +3 -1
  238. package/src/hw/connectManager.ts +18 -0
  239. package/src/hw/customLockScreenLoad.test.ts +86 -0
  240. package/src/hw/customLockScreenLoad.ts +31 -17
  241. package/src/hw/extractOnboardingState.test.ts +122 -2
  242. package/src/hw/extractOnboardingState.ts +81 -18
  243. package/src/hw/getDeviceInfo.ts +4 -1
  244. package/src/hw/getGenuineCheckFromDeviceId.test.ts +2 -1
  245. package/src/hw/getOnboardingStatePolling.test.ts +2 -0
  246. package/src/hw/getOnboardingStatePolling.ts +1 -1
  247. package/src/hw/isFirmwareUpdateVersionSupported.test.ts +3 -1
  248. package/src/mock/fixtures/aDeviceInfo.ts +1 -0
  249. package/src/modularDrawer/__test__/useModularDrawerVisibility.test.ts +149 -0
  250. package/src/modularDrawer/enums.ts +7 -0
  251. package/src/modularDrawer/useModularDrawerVisibility.ts +25 -0
  252. package/src/onboarding/hooks/useOnboardingStatePolling.test.ts +2 -0
  253. package/src/wallet-api/types.ts +1 -1
  254. package/src/wallet-api/useDappLogic.ts +4 -27
  255. package/src/wallet-api/utils/txTrackingHelper.test.ts +80 -0
  256. package/src/wallet-api/utils/txTrackingHelper.ts +14 -0
@@ -1,8 +1,12 @@
1
1
  import { CryptoOrTokenCurrency } from "@ledgerhq/types-cryptoassets";
2
2
  import { MappedAsset, CurrenciesByProviderId, GroupedCurrencies } from "./type";
3
- import { currenciesByMarketcap } from "../currencies";
3
+ import {
4
+ currenciesByMarketcap,
5
+ getCryptoCurrencyById,
6
+ getTokenById,
7
+ hasCryptoCurrencyId,
8
+ } from "../currencies";
4
9
  import { getMappedAssets } from "./api";
5
-
6
10
  export const loadCurrenciesByProvider = async (
7
11
  coinsAndTokensSupported: CryptoOrTokenCurrency[],
8
12
  ): Promise<GroupedCurrencies> => {
@@ -10,9 +14,9 @@ export const loadCurrenciesByProvider = async (
10
14
  currenciesByMarketcap(coinsAndTokensSupported),
11
15
  getMappedAssets(),
12
16
  ]);
17
+
13
18
  return groupCurrenciesByProvider(assets, sortedCurrenciesSupported);
14
19
  };
15
-
16
20
  export const groupCurrenciesByProvider = (
17
21
  assets: MappedAsset[],
18
22
  sortedCurrencies: CryptoOrTokenCurrency[],
@@ -23,7 +27,7 @@ export const groupCurrenciesByProvider = (
23
27
  assetsByLedgerId.set(asset.ledgerId.toLowerCase(), asset);
24
28
  }
25
29
  const assetsByProviderId: Map<string, CurrenciesByProviderId> = new Map();
26
- const sortedCryptoCurrenciesMap: Map<string, CryptoOrTokenCurrency> = new Map();
30
+ const sortedCryptoCurrencies: CryptoOrTokenCurrency[] = [];
27
31
  // iterate over currencies by preserving their order
28
32
  for (const ledgerCurrency of sortedCurrencies) {
29
33
  /// FIXME(LIVE-10508) drop usage of toLowerCase
@@ -39,23 +43,37 @@ export const groupCurrenciesByProvider = (
39
43
  } else {
40
44
  existingEntry.currenciesByNetwork.push(ledgerCurrency);
41
45
  }
42
- if (!sortedCryptoCurrenciesMap.has(ledgerCurrency.name)) {
43
- sortedCryptoCurrenciesMap.set(ledgerCurrency.name, ledgerCurrency);
44
- }
45
46
  }
46
47
  }
48
+
49
+ // in this case, the first currency of the provider is the one we want to display (Wasn't true)
50
+ // So we need to take the first crypto or token currency of each provider to fix that
51
+ for (const [, { currenciesByNetwork }] of assetsByProviderId.entries()) {
52
+ const firstCrypto = currenciesByNetwork.find(c => c.type === "CryptoCurrency");
53
+ const elem = firstCrypto ?? currenciesByNetwork.find(c => c.type === "TokenCurrency");
54
+ if (elem) {
55
+ sortedCryptoCurrencies.push(elem);
56
+ }
57
+ }
58
+
47
59
  return {
48
60
  currenciesByProvider: Array.from(assetsByProviderId.values()),
49
- sortedCryptoCurrencies: Array.from(sortedCryptoCurrenciesMap.values()),
61
+ sortedCryptoCurrencies,
50
62
  };
51
63
  };
52
64
 
53
65
  export const searchByProviderId = (list: MappedAsset[], providerId: string) =>
54
66
  list.filter(elem => elem.providerId.toLowerCase() === providerId.toLowerCase());
55
-
56
67
  export const searchByNameOrTicker = (list: MappedAsset[], nameOrTicker: string) =>
57
68
  list.filter(
58
69
  elem =>
59
70
  elem.name.toLowerCase().includes(nameOrTicker.toLowerCase()) ||
60
71
  elem.ticker.toLowerCase().includes(nameOrTicker.toLowerCase()),
61
72
  );
73
+
74
+ export const getTokenOrCryptoCurrencyById = (id: string): CryptoOrTokenCurrency => {
75
+ if (hasCryptoCurrencyId(id)) {
76
+ return getCryptoCurrencyById(id);
77
+ }
78
+ return getTokenById(id);
79
+ };
@@ -81,6 +81,7 @@ export const parseDeviceInfo = (firmwareInfo: FirmwareInfo): DeviceInfo => {
81
81
  bootloaderVersion,
82
82
  hardwareVersion,
83
83
  languageId,
84
+ charonState,
84
85
  } = firmwareInfo;
85
86
 
86
87
  const isOSU = rawVersion.includes("-osu");
@@ -130,6 +131,8 @@ export const parseDeviceInfo = (firmwareInfo: FirmwareInfo): DeviceInfo => {
130
131
  bootloaderVersion,
131
132
  hardwareVersion,
132
133
  languageId,
134
+ seFlags: flags,
135
+ charonState: charonState,
133
136
  };
134
137
 
135
138
  return deviceInfo;
@@ -9,7 +9,7 @@ export class Provider {
9
9
  static readonly CHANGELLY = new Provider("changelly", "Changelly", false, true, true);
10
10
  static readonly EXODUS = new Provider("exodus", "Exodus", false, true, true);
11
11
  static readonly ONE_INCH = new Provider("oneinch", "1inch", false, false, true);
12
- static readonly PARASWAP = new Provider("paraswap", "Paraswap", false, false, true);
12
+ static readonly VELORA = new Provider("velora", "Velora", false, false, true);
13
13
  static readonly MOONPAY = new Provider("moonpay", "MoonPay", true, false, true);
14
14
  static readonly THORCHAIN = new Provider("thorswap", "THORChain", false, true, false);
15
15
  static readonly UNISWAP = new Provider("uniswap", "Uniswap", false, false, false);
package/src/e2e/swap.ts CHANGED
@@ -3,7 +3,7 @@ import axios from "axios";
3
3
 
4
4
  export async function getMinimumSwapAmount(AccountFrom: Account, AccountTo: Account) {
5
5
  try {
6
- const { data } = await axios({
6
+ const requestConfig = {
7
7
  method: "GET",
8
8
  url: `https://swap-stg.ledger-test.com/v5/quote`,
9
9
  params: {
@@ -24,16 +24,21 @@ export async function getMinimumSwapAmount(AccountFrom: Account, AccountTo: Acco
24
24
  headers: {
25
25
  accept: "application/json",
26
26
  },
27
- });
27
+ };
28
28
 
29
- const minimumAmounts = data.map((item: any) => {
30
- return parseFloat(item.parameter.minAmount);
31
- });
29
+ const { data } = await axios(requestConfig);
30
+
31
+ const minimumAmounts = data
32
+ .filter((item: any) => item.parameter?.minAmount !== undefined)
33
+ .map((item: any) => parseFloat(item.parameter.minAmount));
32
34
 
33
35
  const validMinimumAmounts = minimumAmounts.filter((amount: number) => !isNaN(amount));
34
36
 
35
- const maxMinAmount = Math.max(...validMinimumAmounts);
36
- return maxMinAmount;
37
+ if (validMinimumAmounts.length === 0) {
38
+ throw new Error("No valid minimum amounts returned from swap quote API.");
39
+ }
40
+
41
+ return Math.max(...validMinimumAmounts);
37
42
  } catch (error) {
38
43
  console.error(error);
39
44
  }
@@ -619,6 +619,17 @@ export const DEFAULT_FEATURES: Features = {
619
619
  enableModularization: false,
620
620
  },
621
621
  },
622
+ llmModularDrawer: {
623
+ ...DEFAULT_FEATURE,
624
+ params: {
625
+ add_account: true,
626
+ earn_flow: true,
627
+ live_app: true,
628
+ receive_flow: true,
629
+ send_flow: true,
630
+ enableModularization: false,
631
+ },
632
+ },
622
633
  llNftSupport: DEFAULT_FEATURE,
623
634
  llNftEntryPoint: {
624
635
  ...DEFAULT_FEATURE,
@@ -632,6 +643,30 @@ export const DEFAULT_FEATURES: Features = {
632
643
  lldNetworkBasedAddAccount: DEFAULT_FEATURE,
633
644
  llmOfacGeoBlocking: DEFAULT_FEATURE,
634
645
  lldOfacGeoBlocking: DEFAULT_FEATURE,
646
+ llmDatadog: {
647
+ ...DEFAULT_FEATURE,
648
+ params: {
649
+ batchProcessingLevel: "MEDIUM",
650
+ batchSize: "MEDIUM",
651
+ bundleLogsWithRum: true,
652
+ bundleLogsWithTraces: true,
653
+ longTaskThresholdMs: 0,
654
+ nativeInteractionTracking: false,
655
+ nativeLongTaskThresholdMs: 0,
656
+ nativeViewTracking: false,
657
+ resourceTracingSamplingRate: 0,
658
+ serviceName: "Ledger Live Mobile (default)",
659
+ sessionSamplingRate: 0,
660
+ trackBackgroundEvents: false,
661
+ trackFrustrations: true,
662
+ trackErrors: false,
663
+ trackResources: false,
664
+ trackInteractions: false,
665
+ trackWatchdogTerminations: false,
666
+ uploadFrequency: "AVERAGE",
667
+ vitalsUpdateFrequency: "AVERAGE",
668
+ },
669
+ },
635
670
  };
636
671
 
637
672
  // Firebase SDK treat JSON values as strings
@@ -0,0 +1,134 @@
1
+ import { useAppVersionBlockCheck } from "./useAppVersionBlockCheck";
2
+
3
+ describe("useAppVersionBlockCheck", () => {
4
+ describe("LLM", () => {
5
+ it("should update if current version is not compatible on android", () => {
6
+ // given
7
+ const getConfigValue = () => ({
8
+ llm: {
9
+ android: [
10
+ {
11
+ minOsVersion: "32",
12
+ version: "2.0.3",
13
+ },
14
+ ],
15
+ },
16
+ });
17
+ // when
18
+ const { shouldUpdate } = useAppVersionBlockCheck({
19
+ appVersion: "2.0.1",
20
+ osVersion: "32",
21
+ platform: "android",
22
+ appKey: "llm",
23
+ getConfigValue,
24
+ });
25
+ //then
26
+ expect(shouldUpdate).toBe(true);
27
+ });
28
+ it("should update if current version is not compatible on ios", () => {
29
+ const getConfigValue = () => ({
30
+ llm: {
31
+ ios: [
32
+ {
33
+ minOsVersion: "32",
34
+ version: "2.0.3",
35
+ },
36
+ ],
37
+ },
38
+ });
39
+ // when
40
+ const { shouldUpdate } = useAppVersionBlockCheck({
41
+ appVersion: "2.0.1",
42
+ osVersion: "32",
43
+ platform: "ios",
44
+ appKey: "llm",
45
+ getConfigValue,
46
+ });
47
+ //then
48
+ expect(shouldUpdate).toBe(true);
49
+ });
50
+ it("should not update the app if current version is not compatible on android with another os version", () => {
51
+ // given
52
+ const getConfigValue = () => ({
53
+ llm: {
54
+ android: [
55
+ {
56
+ minOsVersion: "33",
57
+ version: "2.0.3",
58
+ },
59
+ ],
60
+ },
61
+ });
62
+ // when
63
+ const { shouldUpdate } = useAppVersionBlockCheck({
64
+ appVersion: "2.0.1",
65
+ osVersion: "32",
66
+ platform: "android",
67
+ appKey: "llm",
68
+ getConfigValue,
69
+ });
70
+ //then
71
+ expect(shouldUpdate).toBe(false);
72
+ });
73
+ it("should not update the app if current version is not compatible on ios with another os version", () => {
74
+ // given
75
+ const getConfigValue = () => ({
76
+ llm: {
77
+ ios: [
78
+ {
79
+ minOsVersion: "33",
80
+ version: "2.0.3",
81
+ },
82
+ ],
83
+ },
84
+ });
85
+ // when
86
+ const { shouldUpdate } = useAppVersionBlockCheck({
87
+ appVersion: "2.0.1",
88
+ osVersion: "32",
89
+ platform: "ios",
90
+ appKey: "llm",
91
+ getConfigValue,
92
+ });
93
+ //then
94
+ expect(shouldUpdate).toBe(false);
95
+ });
96
+ it.each([
97
+ ["android", "2.1.3"],
98
+ ["ios", "2.1.3"],
99
+ ["android", "2.1.3-rc.2"],
100
+ ["ios", "2.1.3-rc.2"],
101
+ ["android", "2.2.3-next.0"],
102
+ ["ios", "2.2.3-next.0"],
103
+ ["android", "2.0.3-rc2"],
104
+ ["ios", "2.0.3-rc2"],
105
+ ["android", "2.0.3-next.3"],
106
+ ["ios", "2.0.3-next.3"],
107
+ ])(
108
+ "should not update the app on %s for version %s compatible with 2.0.3",
109
+ (platform, appVersion) => {
110
+ // given
111
+ const getConfigValue = () => ({
112
+ llm: {
113
+ [platform]: [
114
+ {
115
+ minOsVersion: "32",
116
+ version: "2.0.3",
117
+ },
118
+ ],
119
+ },
120
+ });
121
+ // when
122
+ const { shouldUpdate } = useAppVersionBlockCheck({
123
+ appVersion,
124
+ osVersion: "32",
125
+ platform: platform as "ios" | "android",
126
+ appKey: "llm",
127
+ getConfigValue,
128
+ });
129
+ // then
130
+ expect(shouldUpdate).toBe(false);
131
+ },
132
+ );
133
+ });
134
+ });
@@ -0,0 +1,65 @@
1
+ import semver from "semver";
2
+ import { LiveConfig } from "@ledgerhq/live-config/LiveConfig";
3
+
4
+ type LLMMinVersionConfig = {
5
+ minOsVersion: string;
6
+ version: string;
7
+ };
8
+
9
+ type LLMinVersionConfig = {
10
+ lld: {
11
+ windows: string;
12
+ macOS: string;
13
+ linux: string;
14
+ };
15
+ llm: {
16
+ android: LLMMinVersionConfig[];
17
+ ios: LLMMinVersionConfig[];
18
+ };
19
+ };
20
+
21
+ const checkLLmVersion = (
22
+ appVersion: string,
23
+ osVersion: string,
24
+ platform: "ios" | "android",
25
+ llmMinVersionConfig: LLMinVersionConfig["llm"],
26
+ ) => {
27
+ if (!llmMinVersionConfig[platform]) {
28
+ return false;
29
+ }
30
+
31
+ return llmMinVersionConfig[platform]
32
+ .filter(minVersionConfig =>
33
+ semver.satisfies(semver.coerce(osVersion), `>=${minVersionConfig.minOsVersion}`),
34
+ )
35
+ .reduce((acc, curr) => {
36
+ return acc || semver.satisfies(appVersion, `<${curr.version}`);
37
+ }, false);
38
+ };
39
+
40
+ export const useAppVersionBlockCheck = ({
41
+ appVersion: uncoercedAppVersion,
42
+ appKey,
43
+ platform,
44
+ osVersion,
45
+ getConfigValue = LiveConfig.getValueByKey,
46
+ }: {
47
+ appVersion: string;
48
+ osVersion?: string;
49
+ appKey: "llm" | "lld";
50
+ platform: "ios" | "android" | "macOS" | "windows" | "linux";
51
+ getConfigValue?: typeof LiveConfig.getValueByKey;
52
+ }) => {
53
+ const llMinVersionConfig = getConfigValue("config_ll_min_version");
54
+ const appVersion = semver.coerce(uncoercedAppVersion)?.version || "";
55
+ let shouldUpdate = false;
56
+
57
+ if (!llMinVersionConfig) {
58
+ return { shouldUpdate };
59
+ }
60
+
61
+ if (appKey === "llm" && (platform === "android" || platform === "ios") && osVersion) {
62
+ shouldUpdate = checkLLmVersion(appVersion, osVersion, platform, llMinVersionConfig[appKey]);
63
+ }
64
+ return { shouldUpdate };
65
+ };
@@ -203,7 +203,9 @@ export class ConnectAppEventMapper {
203
203
  type: "install",
204
204
  name: installPlan.installPlan[installPlan.currentIndex]!.versionName,
205
205
  },
206
- installQueue: installPlan.installPlan.map(app => app.versionName),
206
+ installQueue: installPlan.installPlan
207
+ .map(app => app.versionName)
208
+ .slice(installPlan.currentIndex),
207
209
  });
208
210
  this.installPlan = installPlan;
209
211
  }
@@ -6,6 +6,8 @@ import {
6
6
  StatusCodes,
7
7
  LockedDeviceError,
8
8
  } from "@ledgerhq/errors";
9
+ import { isCharonSupported } from "@ledgerhq/device-core";
10
+ import { identifyTargetId } from "@ledgerhq/devices";
9
11
  import { DeviceInfo } from "@ledgerhq/types-live";
10
12
  import type Transport from "@ledgerhq/hw-transport";
11
13
  import type { DeviceManagementKit } from "@ledgerhq/device-management-kit";
@@ -21,6 +23,7 @@ import attemptToQuitApp, { AttemptToQuitAppEvent } from "./attemptToQuitApp";
21
23
  import { LockedDeviceEvent } from "./actions/types";
22
24
  import { ManagerRequest } from "./actions/manager";
23
25
  import { PrepareConnectManagerEventMapper } from "./connectManagerEventMapper";
26
+ import { extractOnboardingState, OnboardingStep } from "./extractOnboardingState";
24
27
 
25
28
  export type Input = {
26
29
  deviceId: string;
@@ -61,6 +64,21 @@ const cmd = (transport: Transport, { request }: Input): Observable<ConnectManage
61
64
  throw new DeviceNotOnboarded();
62
65
  }
63
66
 
67
+ if (
68
+ isCharonSupported(
69
+ deviceInfo.seVersion ?? "",
70
+ identifyTargetId(deviceInfo.seTargetId ?? 0)?.id,
71
+ )
72
+ ) {
73
+ const onboardingState = extractOnboardingState(
74
+ deviceInfo.seFlags,
75
+ deviceInfo.charonState,
76
+ );
77
+ if (onboardingState.currentOnboardingStep === OnboardingStep.BackupCharon) {
78
+ throw new DeviceNotOnboarded();
79
+ }
80
+ }
81
+
64
82
  if (deviceInfo.isBootloader) {
65
83
  return of({
66
84
  type: "bootloader",
@@ -0,0 +1,86 @@
1
+ import customLockScreenLoad from "./customLockScreenLoad";
2
+ import { DeviceModelId } from "@ledgerhq/devices";
3
+ import { CLSSupportedDeviceModelId } from "@ledgerhq/device-core";
4
+ import { lastValueFrom, of } from "rxjs";
5
+ import { ManagerNotEnoughSpaceError, StatusCodes, TransportError } from "@ledgerhq/errors";
6
+ import { ImageLoadRefusedOnDevice } from "../errors";
7
+
8
+ const mockTransport = {
9
+ send: jest.fn(),
10
+ getTraceContext: jest.fn(),
11
+ };
12
+ jest.mock("../deviceSDK/transports/core", () => ({
13
+ withTransport: () => callback => callback({ transportRef: { current: mockTransport } }),
14
+ }));
15
+ jest.mock("./getDeviceInfo", () => jest.fn(() => of([])));
16
+
17
+ describe("customLockScreenLoad", () => {
18
+ it("should load image on device", async () => {
19
+ // given
20
+ const request = {
21
+ deviceModelId: DeviceModelId.stax as CLSSupportedDeviceModelId,
22
+ hexImage: "hello_world",
23
+ };
24
+ mockTransport.send.mockResolvedValue(Buffer.from([0x42, 0x42, 0x43, 0x90, 0x00]));
25
+
26
+ // when
27
+ const ret = await lastValueFrom(await customLockScreenLoad({ deviceId: "deviceId", request }));
28
+
29
+ // then
30
+ expect(mockTransport.send).toHaveBeenNthCalledWith(
31
+ 1,
32
+ 0xe0,
33
+ 0x60,
34
+ 0x00,
35
+ 0x00,
36
+ Buffer.from([0x00, 0x00, 0x00, 0x08]),
37
+ [StatusCodes.NOT_ENOUGH_SPACE, StatusCodes.USER_REFUSED_ON_DEVICE, StatusCodes.OK],
38
+ );
39
+ expect(mockTransport.send).toHaveBeenNthCalledWith(
40
+ 2,
41
+ 0xe0,
42
+ 0x61,
43
+ 0x00,
44
+ 0x00,
45
+ Buffer.from([0x00, 0x00, 0x00, 0x00, 0x90, 0x01, 0xa0, 0x02, 0x21, 0x00, 0x00, 0x00]),
46
+ );
47
+ expect(mockTransport.send).toHaveBeenNthCalledWith(
48
+ 3,
49
+ 0xe0,
50
+ 0x62,
51
+ 0x00,
52
+ 0x00,
53
+ Buffer.from([]),
54
+ [0x9000, 0x5501],
55
+ );
56
+ expect(ret).toStrictEqual({
57
+ type: "imageLoaded",
58
+ imageSize: 1111638928,
59
+ imageHash: "424243",
60
+ });
61
+ });
62
+
63
+ it.each([
64
+ [
65
+ "user refused on device",
66
+ [0x55, 0x01],
67
+ new ImageLoadRefusedOnDevice("5501", { productName: "Ledger Stax" }),
68
+ ],
69
+ ["not enough space", [0x51, 0x02], new ManagerNotEnoughSpaceError()],
70
+ ["unexpected error", [0x42, 0x32], new TransportError("Unexpected device response", "4232")],
71
+ ])("should return an error if %s", async (_errorStr, statusCode, error) => {
72
+ // given
73
+ const request = {
74
+ deviceModelId: DeviceModelId.stax as CLSSupportedDeviceModelId,
75
+ hexImage: "hello_world",
76
+ };
77
+ mockTransport.send.mockResolvedValue(Buffer.from(statusCode));
78
+
79
+ // when
80
+ try {
81
+ await lastValueFrom(await customLockScreenLoad({ deviceId: "nanoX", request }));
82
+ } catch (err) {
83
+ expect(err).toStrictEqual(error);
84
+ }
85
+ });
86
+ });
@@ -10,7 +10,6 @@ import {
10
10
  } from "@ledgerhq/errors";
11
11
  import { getDeviceModel } from "@ledgerhq/devices";
12
12
 
13
- import { withDevice } from "./deviceAccess";
14
13
  import getDeviceInfo from "./getDeviceInfo";
15
14
  import { ImageLoadRefusedOnDevice, ImageCommitRefusedOnDevice } from "../errors";
16
15
  import getAppAndVersion from "./getAppAndVersion";
@@ -21,6 +20,8 @@ import customLockScreenFetchHash from "./customLockScreenFetchHash";
21
20
  import { gzip } from "pako";
22
21
  import { CLSSupportedDeviceModelId } from "../device/use-cases/isCustomLockScreenSupported";
23
22
  import { getScreenSpecs } from "../device/use-cases/screenSpecs";
23
+ import { DeviceDisconnectedWhileSendingError } from "@ledgerhq/device-management-kit";
24
+ import { withTransport } from "../deviceSDK/transports/core";
24
25
 
25
26
  const MAX_APDU_SIZE = 255;
26
27
  const COMPRESS_CHUNK_SIZE = 2048;
@@ -43,6 +44,17 @@ export type LoadImageEvent =
43
44
  imageHash: string;
44
45
  };
45
46
 
47
+ /**
48
+ * Type guard to check if the given error is a DeviceDisconnectedWhileSendingError.
49
+ * Ensures that the error is an object, is not null, and matches the expected structure.
50
+ * This is used to identify specific disconnection errors from the DMK device.
51
+ */
52
+ const isDmkDeviceDisconnectedError = (err: unknown): err is DeviceDisconnectedWhileSendingError =>
53
+ typeof err === "object" &&
54
+ err !== null &&
55
+ (err instanceof DeviceDisconnectedWhileSendingError ||
56
+ ("_tag" in err && err._tag === "DeviceDisconnectedWhileSendingError"));
57
+
46
58
  export type LoadimageResult = {
47
59
  imageHash: string;
48
60
  imageSize: number;
@@ -72,14 +84,14 @@ export default function loadImage({ deviceId, request }: Input): Observable<Load
72
84
  const { hexImage, padImage = true, deviceModelId } = request;
73
85
  const screenSpecs = getScreenSpecs(deviceModelId);
74
86
 
75
- const sub = withDevice(deviceId)(
76
- transport =>
87
+ const sub = withTransport(deviceId)(
88
+ ({ transportRef }) =>
77
89
  new Observable(subscriber => {
78
90
  const timeoutSub = of<LoadImageEvent>({ type: "unresponsiveDevice" })
79
91
  .pipe(delay(1000))
80
92
  .subscribe(e => subscriber.next(e));
81
93
 
82
- const sub = from(getDeviceInfo(transport))
94
+ const sub = from(getDeviceInfo(transportRef.current))
83
95
  .pipe(
84
96
  mergeMap(async () => {
85
97
  timeoutSub.unsubscribe();
@@ -96,11 +108,14 @@ export default function loadImage({ deviceId, request }: Input): Observable<Load
96
108
  imageSize.writeUIntBE(imageLength, 0, 4);
97
109
 
98
110
  subscriber.next({ type: "loadImagePermissionRequested" });
99
- const createImageResponse = await transport.send(0xe0, 0x60, 0x00, 0x00, imageSize, [
100
- StatusCodes.NOT_ENOUGH_SPACE,
101
- StatusCodes.USER_REFUSED_ON_DEVICE,
102
- StatusCodes.OK,
103
- ]);
111
+ const createImageResponse = await transportRef.current.send(
112
+ 0xe0,
113
+ 0x60,
114
+ 0x00,
115
+ 0x00,
116
+ imageSize,
117
+ [StatusCodes.NOT_ENOUGH_SPACE, StatusCodes.USER_REFUSED_ON_DEVICE, StatusCodes.OK],
118
+ );
104
119
 
105
120
  const createImageStatus = createImageResponse.readUInt16BE(
106
121
  createImageResponse.length - 2,
@@ -140,13 +155,13 @@ export default function loadImage({ deviceId, request }: Input): Observable<Load
140
155
  chunkOffsetBuffer.writeUIntBE(currentOffset, 0, 4);
141
156
 
142
157
  const apduData = Buffer.concat([chunkOffsetBuffer, chunkDataBuffer]);
143
- await transport.send(0xe0, 0x61, 0x00, 0x00, apduData);
158
+ await transportRef.current.send(0xe0, 0x61, 0x00, 0x00, apduData);
144
159
  currentOffset += chunkSize;
145
160
  }
146
161
 
147
162
  subscriber.next({ type: "commitImagePermissionRequested" });
148
163
 
149
- const commitResponse = await transport.send(
164
+ const commitResponse = await transportRef.current.send(
150
165
  0xe0,
151
166
  0x62,
152
167
  0x00,
@@ -172,10 +187,10 @@ export default function loadImage({ deviceId, request }: Input): Observable<Load
172
187
  }
173
188
 
174
189
  // Fetch image size
175
- const imageBytes = await customLockScreenFetchSize(transport);
190
+ const imageBytes = await customLockScreenFetchSize(transportRef.current);
176
191
 
177
192
  // Fetch image hash
178
- const imageHash = await customLockScreenFetchHash(transport);
193
+ const imageHash = await customLockScreenFetchHash(transportRef.current);
179
194
 
180
195
  subscriber.next({
181
196
  type: "imageLoaded",
@@ -192,10 +207,10 @@ export default function loadImage({ deviceId, request }: Input): Observable<Load
192
207
  e instanceof TransportStatusError &&
193
208
  [0x6e00, 0x6d00, 0x6e01, 0x6d01, 0x6d02].includes(e.statusCode))
194
209
  ) {
195
- return from(getAppAndVersion(transport)).pipe(
210
+ return from(getAppAndVersion(transportRef.current)).pipe(
196
211
  concatMap(appAndVersion => {
197
212
  return !isDashboardName(appAndVersion.name)
198
- ? attemptToQuitApp(transport, appAndVersion)
213
+ ? attemptToQuitApp(transportRef.current, appAndVersion)
199
214
  : of<LoadImageEvent>({
200
215
  type: "appDetected",
201
216
  });
@@ -213,9 +228,8 @@ export default function loadImage({ deviceId, request }: Input): Observable<Load
213
228
  };
214
229
  }),
215
230
  ).pipe(
216
- // timeout(5000),
217
231
  catchError(err => {
218
- if (err.name === "TimeoutError") {
232
+ if (err.name === "TimeoutError" || isDmkDeviceDisconnectedError(err)) {
219
233
  return throwError(() => new DisconnectedDevice());
220
234
  }
221
235
  return throwError(() => err);