agentvault 1.0.1 → 1.0.2

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 (292) hide show
  1. package/.claude/settings.local.json +9 -0
  2. package/dist/cli/commands/approve.js +5 -5
  3. package/dist/cli/commands/archive.js +5 -5
  4. package/dist/cli/commands/backup.js +5 -5
  5. package/dist/cli/commands/cloud-backup.js +12 -12
  6. package/dist/cli/commands/decrypt.js +2 -2
  7. package/dist/cli/commands/deploy.js +1 -1
  8. package/dist/cli/commands/exec.js +2 -2
  9. package/dist/cli/commands/fetch.js +4 -4
  10. package/dist/cli/commands/inference.js +5 -5
  11. package/dist/cli/commands/init.d.ts +1 -1
  12. package/dist/cli/commands/init.js +16 -16
  13. package/dist/cli/commands/list.js +4 -4
  14. package/dist/cli/commands/package.js +2 -2
  15. package/dist/cli/commands/profile.js +1 -1
  16. package/dist/cli/commands/rebuild.js +2 -2
  17. package/dist/cli/commands/show.js +1 -1
  18. package/dist/cli/commands/status.d.ts +1 -1
  19. package/dist/cli/commands/status.js +8 -8
  20. package/dist/cli/commands/trace.js +1 -1
  21. package/dist/cli/commands/wallet-export.js +1 -1
  22. package/dist/cli/commands/wallet-sign.js +1 -1
  23. package/dist/cli/commands/wallet.d.ts +1 -1
  24. package/dist/cli/commands/wallet.js +1 -1
  25. package/dist/cli/index.d.ts +2 -2
  26. package/dist/cli/index.js +3 -3
  27. package/dist/src/archival/archive-manager.d.ts +85 -0
  28. package/dist/src/archival/archive-manager.js +294 -0
  29. package/dist/src/archival/arweave-client.d.ts +88 -0
  30. package/dist/src/archival/arweave-client.js +223 -0
  31. package/dist/src/archival/index.d.ts +8 -0
  32. package/{src/archival/index.ts → dist/src/archival/index.js} +1 -1
  33. package/dist/src/backup/backup.d.ts +67 -0
  34. package/dist/src/backup/backup.js +231 -0
  35. package/dist/src/backup/index.d.ts +7 -0
  36. package/{src/backup/index.ts → dist/src/backup/index.js} +1 -1
  37. package/dist/src/cloud-storage/cloud-sync.d.ts +49 -0
  38. package/dist/src/cloud-storage/cloud-sync.js +372 -0
  39. package/dist/src/cloud-storage/index.d.ts +11 -0
  40. package/{src/cloud-storage/index.ts → dist/src/cloud-storage/index.js} +1 -1
  41. package/dist/src/cloud-storage/provider-detector.d.ts +34 -0
  42. package/dist/src/cloud-storage/provider-detector.js +158 -0
  43. package/{src/cloud-storage/types.ts → dist/src/cloud-storage/types.d.ts} +40 -53
  44. package/dist/src/cloud-storage/types.js +10 -0
  45. package/dist/src/debugging/index.d.ts +6 -0
  46. package/{src/debugging/index.ts → dist/src/debugging/index.js} +1 -1
  47. package/dist/src/debugging/logs.d.ts +32 -0
  48. package/dist/src/debugging/logs.js +158 -0
  49. package/dist/src/debugging/types.d.ts +91 -0
  50. package/dist/src/debugging/types.js +5 -0
  51. package/dist/src/deployment/deployer.d.ts +52 -0
  52. package/dist/src/deployment/deployer.js +211 -0
  53. package/dist/src/deployment/icpClient.d.ts +144 -0
  54. package/dist/src/deployment/icpClient.js +545 -0
  55. package/dist/src/deployment/index.d.ts +11 -0
  56. package/dist/src/deployment/index.js +14 -0
  57. package/dist/src/deployment/promotion.d.ts +32 -0
  58. package/dist/src/deployment/promotion.js +114 -0
  59. package/dist/src/deployment/types.d.ts +101 -0
  60. package/dist/src/deployment/types.js +5 -0
  61. package/dist/src/icp/batch.d.ts +112 -0
  62. package/dist/src/icp/batch.js +273 -0
  63. package/dist/src/icp/cycles.d.ts +29 -0
  64. package/{src/icp/cycles.ts → dist/src/icp/cycles.js} +8 -22
  65. package/dist/src/icp/environment.d.ts +60 -0
  66. package/dist/src/icp/environment.js +183 -0
  67. package/dist/src/icp/icpcli.d.ts +204 -0
  68. package/dist/src/icp/icpcli.js +374 -0
  69. package/dist/src/icp/icwasm.d.ts +94 -0
  70. package/dist/src/icp/icwasm.js +197 -0
  71. package/dist/src/icp/identity.d.ts +50 -0
  72. package/{src/icp/identity.ts → dist/src/icp/identity.js} +15 -28
  73. package/dist/src/icp/index.d.ts +16 -0
  74. package/dist/src/icp/index.js +20 -0
  75. package/dist/src/icp/optimization.d.ts +16 -0
  76. package/dist/src/icp/optimization.js +225 -0
  77. package/dist/src/icp/tokens.d.ts +24 -0
  78. package/{src/icp/tokens.ts → dist/src/icp/tokens.js} +5 -12
  79. package/dist/src/icp/tool-detector.d.ts +31 -0
  80. package/dist/src/icp/tool-detector.js +104 -0
  81. package/dist/src/icp/types.d.ts +493 -0
  82. package/dist/src/icp/types.js +7 -0
  83. package/dist/src/index.d.ts +12 -0
  84. package/dist/src/index.js +18 -0
  85. package/dist/src/inference/bittensor-client.d.ts +108 -0
  86. package/dist/src/inference/bittensor-client.js +224 -0
  87. package/dist/src/inference/index.d.ts +8 -0
  88. package/{src/inference/index.ts → dist/src/inference/index.js} +1 -1
  89. package/dist/src/inference/inference-manager.d.ts +76 -0
  90. package/dist/src/inference/inference-manager.js +228 -0
  91. package/dist/src/metrics/index.d.ts +7 -0
  92. package/{src/metrics/index.ts → dist/src/metrics/index.js} +1 -1
  93. package/dist/src/metrics/metrics.d.ts +39 -0
  94. package/dist/src/metrics/metrics.js +129 -0
  95. package/dist/src/monitoring/alerting.d.ts +51 -0
  96. package/dist/src/monitoring/alerting.js +169 -0
  97. package/dist/src/monitoring/health.d.ts +40 -0
  98. package/dist/src/monitoring/health.js +164 -0
  99. package/dist/src/monitoring/index.d.ts +10 -0
  100. package/dist/src/monitoring/index.js +12 -0
  101. package/dist/src/monitoring/info.d.ts +15 -0
  102. package/dist/src/monitoring/info.js +109 -0
  103. package/dist/src/monitoring/types.d.ts +93 -0
  104. package/dist/src/monitoring/types.js +7 -0
  105. package/dist/src/network/index.d.ts +5 -0
  106. package/{src/network/index.ts → dist/src/network/index.js} +1 -1
  107. package/dist/src/network/network-config.d.ts +31 -0
  108. package/dist/src/network/network-config.js +109 -0
  109. package/dist/src/packaging/compiler.d.ts +61 -0
  110. package/dist/src/packaging/compiler.js +562 -0
  111. package/dist/src/packaging/config-persistence.d.ts +46 -0
  112. package/dist/src/packaging/config-persistence.js +108 -0
  113. package/dist/src/packaging/config-schemas.d.ts +115 -0
  114. package/dist/src/packaging/config-schemas.js +43 -0
  115. package/dist/src/packaging/detector.d.ts +26 -0
  116. package/dist/src/packaging/detector.js +193 -0
  117. package/dist/src/packaging/index.d.ts +16 -0
  118. package/dist/src/packaging/index.js +22 -0
  119. package/dist/src/packaging/packager.d.ts +31 -0
  120. package/dist/src/packaging/packager.js +90 -0
  121. package/dist/src/packaging/parsers/clawdbot.d.ts +19 -0
  122. package/dist/src/packaging/parsers/clawdbot.js +231 -0
  123. package/dist/src/packaging/parsers/cline.d.ts +26 -0
  124. package/dist/src/packaging/parsers/cline.js +185 -0
  125. package/dist/src/packaging/parsers/generic.d.ts +27 -0
  126. package/dist/src/packaging/parsers/generic.js +228 -0
  127. package/dist/src/packaging/parsers/goose.d.ts +26 -0
  128. package/dist/src/packaging/parsers/goose.js +175 -0
  129. package/dist/src/packaging/parsers/index.d.ts +11 -0
  130. package/{src/packaging/parsers/index.ts → dist/src/packaging/parsers/index.js} +1 -1
  131. package/dist/src/packaging/serializer.d.ts +108 -0
  132. package/dist/src/packaging/serializer.js +153 -0
  133. package/dist/src/packaging/types.d.ts +131 -0
  134. package/dist/src/packaging/types.js +5 -0
  135. package/dist/src/packaging/wasmedge-compiler.d.ts +76 -0
  136. package/dist/src/packaging/wasmedge-compiler.js +349 -0
  137. package/dist/src/security/index.d.ts +11 -0
  138. package/{src/security/index.ts → dist/src/security/index.js} +1 -4
  139. package/dist/src/security/multisig.d.ts +102 -0
  140. package/dist/src/security/multisig.js +283 -0
  141. package/dist/src/security/types.d.ts +207 -0
  142. package/dist/src/security/types.js +217 -0
  143. package/dist/src/security/vetkeys.d.ts +179 -0
  144. package/dist/src/security/vetkeys.js +499 -0
  145. package/dist/src/testing/index.d.ts +6 -0
  146. package/{src/testing/index.ts → dist/src/testing/index.js} +1 -1
  147. package/dist/src/testing/local-runner.d.ts +23 -0
  148. package/dist/src/testing/local-runner.js +226 -0
  149. package/dist/src/testing/types.d.ts +98 -0
  150. package/dist/src/testing/types.js +5 -0
  151. package/dist/src/wallet/cbor-serializer.d.ts +82 -0
  152. package/dist/src/wallet/cbor-serializer.js +282 -0
  153. package/dist/src/wallet/chain-dispatcher.d.ts +112 -0
  154. package/dist/src/wallet/chain-dispatcher.js +241 -0
  155. package/dist/src/wallet/cross-chain-aggregator.d.ts +119 -0
  156. package/dist/src/wallet/cross-chain-aggregator.js +235 -0
  157. package/dist/src/wallet/index.d.ts +16 -0
  158. package/dist/src/wallet/index.js +22 -0
  159. package/dist/src/wallet/key-derivation.d.ts +117 -0
  160. package/dist/src/wallet/key-derivation.js +325 -0
  161. package/dist/src/wallet/providers/base-provider.d.ts +111 -0
  162. package/dist/src/wallet/providers/base-provider.js +58 -0
  163. package/dist/src/wallet/providers/cketh-provider.d.ts +104 -0
  164. package/dist/src/wallet/providers/cketh-provider.js +343 -0
  165. package/dist/src/wallet/providers/polkadot-provider.d.ts +115 -0
  166. package/dist/src/wallet/providers/polkadot-provider.js +407 -0
  167. package/dist/src/wallet/providers/solana-provider.d.ts +102 -0
  168. package/dist/src/wallet/providers/solana-provider.js +393 -0
  169. package/dist/src/wallet/transaction-queue.d.ts +133 -0
  170. package/dist/src/wallet/transaction-queue.js +195 -0
  171. package/dist/src/wallet/types.d.ts +167 -0
  172. package/dist/src/wallet/types.js +5 -0
  173. package/dist/src/wallet/vetkeys-adapter.d.ts +134 -0
  174. package/dist/src/wallet/vetkeys-adapter.js +313 -0
  175. package/dist/src/wallet/wallet-manager.d.ts +202 -0
  176. package/dist/src/wallet/wallet-manager.js +451 -0
  177. package/dist/src/wallet/wallet-storage.d.ts +131 -0
  178. package/dist/src/wallet/wallet-storage.js +274 -0
  179. package/macos-wallet-app/AgentVaultWallet/App/AgentVaultWalletApp.swift +54 -0
  180. package/macos-wallet-app/AgentVaultWallet/Models/AppState.swift +102 -0
  181. package/macos-wallet-app/AgentVaultWallet/Models/Chain.swift +121 -0
  182. package/macos-wallet-app/AgentVaultWallet/Models/Wallet.swift +98 -0
  183. package/macos-wallet-app/AgentVaultWallet/Resources/AgentVaultWallet.entitlements +27 -0
  184. package/macos-wallet-app/AgentVaultWallet/Resources/Info.plist +69 -0
  185. package/macos-wallet-app/AgentVaultWallet/Services/BackupService.swift +270 -0
  186. package/macos-wallet-app/AgentVaultWallet/Services/CLIBridge.swift +367 -0
  187. package/macos-wallet-app/AgentVaultWallet/Services/CryptoService.swift +157 -0
  188. package/macos-wallet-app/AgentVaultWallet/Services/FileService.swift +120 -0
  189. package/macos-wallet-app/AgentVaultWallet/Services/KeychainService.swift +219 -0
  190. package/macos-wallet-app/AgentVaultWallet/Utilities/Constants.swift +44 -0
  191. package/macos-wallet-app/AgentVaultWallet/Utilities/Extensions.swift +115 -0
  192. package/macos-wallet-app/AgentVaultWallet/ViewModels/BackupViewModel.swift +237 -0
  193. package/macos-wallet-app/AgentVaultWallet/ViewModels/CreateWalletViewModel.swift +137 -0
  194. package/macos-wallet-app/AgentVaultWallet/ViewModels/ImportWalletViewModel.swift +179 -0
  195. package/macos-wallet-app/AgentVaultWallet/ViewModels/WalletStore.swift +286 -0
  196. package/macos-wallet-app/AgentVaultWallet/Views/Backup/BackupView.swift +235 -0
  197. package/macos-wallet-app/AgentVaultWallet/Views/Backup/RestoreView.swift +316 -0
  198. package/macos-wallet-app/AgentVaultWallet/Views/Create/CreateWalletFlow.swift +438 -0
  199. package/macos-wallet-app/AgentVaultWallet/Views/Import/ImportWalletFlow.swift +399 -0
  200. package/macos-wallet-app/AgentVaultWallet/Views/MainView.swift +134 -0
  201. package/macos-wallet-app/AgentVaultWallet/Views/Settings/SettingsView.swift +276 -0
  202. package/macos-wallet-app/AgentVaultWallet/Views/Sidebar/SidebarView.swift +133 -0
  203. package/macos-wallet-app/AgentVaultWallet/Views/Wallet/DashboardView.swift +233 -0
  204. package/macos-wallet-app/AgentVaultWallet/Views/Wallet/WalletDetailView.swift +281 -0
  205. package/macos-wallet-app/AgentVaultWallet/Views/Wallet/WalletListView.swift +280 -0
  206. package/macos-wallet-app/AgentVaultWallet/Views/Welcome/WelcomeView.swift +176 -0
  207. package/macos-wallet-app/Makefile +47 -0
  208. package/macos-wallet-app/project.yml +40 -0
  209. package/macos-wallet-app/setup.sh +73 -0
  210. package/package.json +10 -2
  211. package/backups/agentvault-backup-test-agent-2026-02-12T17-54-28-967Z.json +0 -28
  212. package/backups/agentvault-backup-test-agent-2026-02-12T17-54-29-032Z.backup +0 -1
  213. package/backups/agentvault-backup-test-agent-2026-02-12T17-57-42-373Z.json +0 -28
  214. package/backups/agentvault-backup-test-agent-2026-02-12T17-57-42-428Z.backup +0 -1
  215. package/backups/agentvault-backup-test-agent-2026-02-12T18-52-25-132Z.json +0 -28
  216. package/backups/agentvault-backup-test-agent-2026-02-12T18-52-25-247Z.backup +0 -1
  217. package/backups/agentvault-backup-test-agent-2026-02-12T18-54-09-216Z.json +0 -28
  218. package/backups/agentvault-backup-test-agent-2026-02-12T18-54-09-283Z.backup +0 -1
  219. package/backups/agentvault-backup-test-agent-2026-02-12T22-18-22-772Z.backup +0 -1
  220. package/backups/agentvault-backup-test-agent-2026-02-12T22-18-22-793Z.json +0 -28
  221. package/backups/test-backup.json +0 -28
  222. package/scripts/dev-dashboard.mjs +0 -84
  223. package/site/README.md +0 -63
  224. package/site/docusaurus.config.ts +0 -148
  225. package/site/package-lock.json +0 -18383
  226. package/site/package.json +0 -47
  227. package/site/sidebars.ts +0 -86
  228. package/site/static/.gitkeep +0 -0
  229. package/site/static/img/logo.svg +0 -28
  230. package/site/static/img/og-image.svg +0 -35
  231. package/src/archival/archive-manager.ts +0 -372
  232. package/src/archival/arweave-client.ts +0 -289
  233. package/src/backup/backup.ts +0 -315
  234. package/src/cloud-storage/cloud-sync.ts +0 -461
  235. package/src/cloud-storage/provider-detector.ts +0 -198
  236. package/src/debugging/logs.ts +0 -193
  237. package/src/debugging/types.ts +0 -100
  238. package/src/deployment/deployer.ts +0 -274
  239. package/src/deployment/icpClient.ts +0 -620
  240. package/src/deployment/index.ts +0 -46
  241. package/src/deployment/promotion.ts +0 -161
  242. package/src/deployment/types.ts +0 -111
  243. package/src/icp/batch.ts +0 -374
  244. package/src/icp/environment.ts +0 -215
  245. package/src/icp/icpcli.ts +0 -438
  246. package/src/icp/icwasm.ts +0 -222
  247. package/src/icp/index.ts +0 -94
  248. package/src/icp/optimization.ts +0 -242
  249. package/src/icp/tool-detector.ts +0 -110
  250. package/src/icp/types.ts +0 -574
  251. package/src/index.ts +0 -25
  252. package/src/inference/bittensor-client.ts +0 -304
  253. package/src/inference/inference-manager.ts +0 -327
  254. package/src/metrics/metrics.ts +0 -186
  255. package/src/monitoring/alerting.ts +0 -190
  256. package/src/monitoring/health.ts +0 -197
  257. package/src/monitoring/index.ts +0 -38
  258. package/src/monitoring/info.ts +0 -114
  259. package/src/monitoring/types.ts +0 -99
  260. package/src/network/network-config.ts +0 -129
  261. package/src/packaging/compiler.ts +0 -647
  262. package/src/packaging/config-persistence.ts +0 -135
  263. package/src/packaging/config-schemas.ts +0 -156
  264. package/src/packaging/detector.ts +0 -220
  265. package/src/packaging/index.ts +0 -90
  266. package/src/packaging/packager.ts +0 -118
  267. package/src/packaging/parsers/clawdbot.ts +0 -278
  268. package/src/packaging/parsers/cline.ts +0 -223
  269. package/src/packaging/parsers/generic.ts +0 -266
  270. package/src/packaging/parsers/goose.ts +0 -214
  271. package/src/packaging/serializer.ts +0 -260
  272. package/src/packaging/types.ts +0 -144
  273. package/src/packaging/wasmedge-compiler.ts +0 -406
  274. package/src/security/multisig.ts +0 -415
  275. package/src/security/types.ts +0 -416
  276. package/src/security/vetkeys.ts +0 -655
  277. package/src/testing/local-runner.ts +0 -264
  278. package/src/testing/types.ts +0 -104
  279. package/src/wallet/cbor-serializer.ts +0 -323
  280. package/src/wallet/chain-dispatcher.ts +0 -313
  281. package/src/wallet/cross-chain-aggregator.ts +0 -346
  282. package/src/wallet/index.ts +0 -76
  283. package/src/wallet/key-derivation.ts +0 -425
  284. package/src/wallet/providers/base-provider.ts +0 -154
  285. package/src/wallet/providers/cketh-provider.ts +0 -434
  286. package/src/wallet/providers/polkadot-provider.ts +0 -503
  287. package/src/wallet/providers/solana-provider.ts +0 -490
  288. package/src/wallet/transaction-queue.ts +0 -284
  289. package/src/wallet/types.ts +0 -178
  290. package/src/wallet/vetkeys-adapter.ts +0 -431
  291. package/src/wallet/wallet-manager.ts +0 -597
  292. package/src/wallet/wallet-storage.ts +0 -380
@@ -0,0 +1,438 @@
1
+ import SwiftUI
2
+
3
+ /// Multi-step wizard for creating a new wallet
4
+ struct CreateWalletFlow: View {
5
+ @EnvironmentObject var walletStore: WalletStore
6
+ @EnvironmentObject var appState: AppState
7
+ @StateObject private var vm = CreateWalletViewModel()
8
+ @Environment(\.dismiss) private var dismiss
9
+
10
+ var body: some View {
11
+ VStack(spacing: 0) {
12
+ // Header with step indicator
13
+ header
14
+ Divider()
15
+
16
+ // Step content
17
+ ScrollView {
18
+ stepContent
19
+ .padding(24)
20
+ .frame(maxWidth: .infinity)
21
+ }
22
+
23
+ Divider()
24
+
25
+ // Footer with navigation buttons
26
+ footer
27
+ }
28
+ .background(.background)
29
+ }
30
+
31
+ private var header: some View {
32
+ VStack(spacing: 12) {
33
+ Text("Create New Wallet")
34
+ .font(.title2.bold())
35
+
36
+ // Step progress
37
+ HStack(spacing: 4) {
38
+ ForEach(0..<5) { step in
39
+ RoundedRectangle(cornerRadius: 2)
40
+ .fill(step <= vm.currentStep.rawValue ? Color.accentColor : Color.secondary.opacity(0.2))
41
+ .frame(height: 3)
42
+ }
43
+ }
44
+ .padding(.horizontal, 32)
45
+
46
+ Text(vm.currentStep.title)
47
+ .font(.subheadline)
48
+ .foregroundStyle(.secondary)
49
+ }
50
+ .padding(.top, 20)
51
+ .padding(.bottom, 12)
52
+ }
53
+
54
+ @ViewBuilder
55
+ private var stepContent: some View {
56
+ switch vm.currentStep {
57
+ case .selectChain:
58
+ ChainPickerView(selectedChain: $vm.selectedChain)
59
+
60
+ case .generating:
61
+ VStack(spacing: 20) {
62
+ ProgressView()
63
+ .scaleEffect(1.5)
64
+ Text("Generating your \(vm.selectedChain.displayName) wallet...")
65
+ .foregroundStyle(.secondary)
66
+ }
67
+ .frame(maxWidth: .infinity, minHeight: 200)
68
+
69
+ case .showMnemonic:
70
+ MnemonicDisplayView(words: vm.mnemonicWords, chain: vm.selectedChain)
71
+
72
+ case .confirmMnemonic:
73
+ MnemonicConfirmView(
74
+ confirmWordIndices: vm.confirmWordIndices,
75
+ mnemonicWords: vm.mnemonicWords,
76
+ confirmationInput: $vm.confirmationInput,
77
+ isValid: vm.isConfirmationValid
78
+ )
79
+
80
+ case .nameWallet:
81
+ WalletNameInputView(
82
+ name: $vm.walletName,
83
+ chain: vm.selectedChain,
84
+ defaultName: "\(vm.selectedChain.displayName) Wallet"
85
+ )
86
+
87
+ case .complete:
88
+ WalletCreatedView(wallet: vm.createdWallet, chain: vm.selectedChain)
89
+ }
90
+
91
+ // Error message
92
+ if let error = vm.errorMessage {
93
+ HStack {
94
+ Image(systemName: "exclamationmark.triangle.fill")
95
+ .foregroundStyle(.red)
96
+ Text(error)
97
+ .font(.callout)
98
+ .foregroundStyle(.red)
99
+ }
100
+ .padding()
101
+ .background(.red.opacity(0.1), in: RoundedRectangle(cornerRadius: 8))
102
+ }
103
+ }
104
+
105
+ private var footer: some View {
106
+ HStack {
107
+ if vm.currentStep != .selectChain && vm.currentStep != .generating && vm.currentStep != .complete {
108
+ Button("Back") {
109
+ vm.goBack()
110
+ }
111
+ .buttonStyle(.bordered)
112
+ }
113
+
114
+ Spacer()
115
+
116
+ if vm.currentStep == .complete {
117
+ Button("Done") {
118
+ dismiss()
119
+ }
120
+ .buttonStyle(.borderedProminent)
121
+ } else if vm.currentStep == .selectChain {
122
+ HStack(spacing: 12) {
123
+ Button("Cancel") { dismiss() }
124
+ .buttonStyle(.bordered)
125
+
126
+ Button("Next") {
127
+ Task {
128
+ await vm.generateWallet(store: walletStore)
129
+ }
130
+ }
131
+ .buttonStyle(.borderedProminent)
132
+ }
133
+ } else if vm.currentStep == .showMnemonic {
134
+ Button("I've Backed It Up") {
135
+ vm.goToNext()
136
+ }
137
+ .buttonStyle(.borderedProminent)
138
+ } else if vm.currentStep == .confirmMnemonic {
139
+ Button("Verify") {
140
+ if vm.isConfirmationValid {
141
+ vm.goToNext()
142
+ }
143
+ }
144
+ .buttonStyle(.borderedProminent)
145
+ .disabled(!vm.isConfirmationValid)
146
+ } else if vm.currentStep == .nameWallet {
147
+ Button("Finish") {
148
+ if let wallet = vm.createdWallet, !vm.walletName.isEmpty {
149
+ walletStore.renameWallet(wallet, to: vm.walletName)
150
+ }
151
+ vm.goToNext()
152
+ }
153
+ .buttonStyle(.borderedProminent)
154
+ .disabled(!vm.canProceed)
155
+ }
156
+ }
157
+ .padding(16)
158
+ }
159
+ }
160
+
161
+ // MARK: - Chain Picker
162
+
163
+ struct ChainPickerView: View {
164
+ @Binding var selectedChain: Chain
165
+
166
+ var body: some View {
167
+ VStack(spacing: 16) {
168
+ Text("Which blockchain network?")
169
+ .font(.headline)
170
+
171
+ VStack(spacing: 12) {
172
+ ForEach(Chain.allCases) { chain in
173
+ ChainCard(chain: chain, isSelected: selectedChain == chain)
174
+ .onTapGesture { selectedChain = chain }
175
+ }
176
+ }
177
+ }
178
+ }
179
+ }
180
+
181
+ struct ChainCard: View {
182
+ let chain: Chain
183
+ let isSelected: Bool
184
+
185
+ var body: some View {
186
+ HStack(spacing: 16) {
187
+ ZStack {
188
+ RoundedRectangle(cornerRadius: 12)
189
+ .fill(
190
+ LinearGradient(colors: chain.gradientColors, startPoint: .topLeading, endPoint: .bottomTrailing)
191
+ )
192
+ .frame(width: 48, height: 48)
193
+
194
+ Image(systemName: chain.iconName)
195
+ .font(.title2)
196
+ .foregroundStyle(.white)
197
+ }
198
+
199
+ VStack(alignment: .leading, spacing: 4) {
200
+ Text(chain.displayName)
201
+ .font(.headline)
202
+ Text(chain.symbol)
203
+ .font(.caption)
204
+ .foregroundStyle(.secondary)
205
+ }
206
+
207
+ Spacer()
208
+
209
+ if isSelected {
210
+ Image(systemName: "checkmark.circle.fill")
211
+ .font(.title2)
212
+ .foregroundStyle(.accentColor)
213
+ }
214
+ }
215
+ .padding(16)
216
+ .background(
217
+ RoundedRectangle(cornerRadius: 12)
218
+ .fill(isSelected ? Color.accentColor.opacity(0.08) : Color.clear)
219
+ )
220
+ .overlay(
221
+ RoundedRectangle(cornerRadius: 12)
222
+ .stroke(isSelected ? Color.accentColor : Color.secondary.opacity(0.2), lineWidth: isSelected ? 2 : 1)
223
+ )
224
+ }
225
+ }
226
+
227
+ // MARK: - Mnemonic Display
228
+
229
+ struct MnemonicDisplayView: View {
230
+ let words: [String]
231
+ let chain: Chain
232
+
233
+ var body: some View {
234
+ VStack(spacing: 20) {
235
+ HStack {
236
+ Image(systemName: "exclamationmark.triangle.fill")
237
+ .foregroundStyle(.orange)
238
+ Text("Write down these words in order. This is the ONLY way to recover your wallet.")
239
+ .font(.callout)
240
+ }
241
+ .padding()
242
+ .background(.orange.opacity(0.1), in: RoundedRectangle(cornerRadius: 8))
243
+
244
+ MnemonicGridView(words: words)
245
+
246
+ Button("Copy to Clipboard") {
247
+ let phrase = words.joined(separator: " ")
248
+ NSPasteboard.general.clearContents()
249
+ NSPasteboard.general.setString(phrase, forType: .string)
250
+
251
+ // Auto-clear after 60 seconds
252
+ DispatchQueue.main.asyncAfter(deadline: .now() + 60) {
253
+ NSPasteboard.general.clearContents()
254
+ }
255
+ }
256
+ .buttonStyle(.bordered)
257
+ .controlSize(.small)
258
+
259
+ Text("Clipboard will be cleared automatically after 60 seconds.")
260
+ .font(.caption2)
261
+ .foregroundStyle(.tertiary)
262
+ }
263
+ }
264
+ }
265
+
266
+ /// Grid display of mnemonic words with numbered positions
267
+ struct MnemonicGridView: View {
268
+ let words: [String]
269
+
270
+ private let columns = [
271
+ GridItem(.flexible(), spacing: 8),
272
+ GridItem(.flexible(), spacing: 8),
273
+ GridItem(.flexible(), spacing: 8),
274
+ ]
275
+
276
+ var body: some View {
277
+ LazyVGrid(columns: columns, spacing: 8) {
278
+ ForEach(Array(words.enumerated()), id: \.offset) { index, word in
279
+ HStack(spacing: 6) {
280
+ Text("\(index + 1)")
281
+ .font(.caption2.monospacedDigit())
282
+ .foregroundStyle(.tertiary)
283
+ .frame(width: 20, alignment: .trailing)
284
+
285
+ Text(word)
286
+ .font(.system(.body, design: .monospaced))
287
+ .frame(maxWidth: .infinity, alignment: .leading)
288
+ }
289
+ .padding(.horizontal, 10)
290
+ .padding(.vertical, 8)
291
+ .background(.quaternary, in: RoundedRectangle(cornerRadius: 6))
292
+ }
293
+ }
294
+ }
295
+ }
296
+
297
+ // MARK: - Mnemonic Confirm
298
+
299
+ struct MnemonicConfirmView: View {
300
+ let confirmWordIndices: [Int]
301
+ let mnemonicWords: [String]
302
+ @Binding var confirmationInput: String
303
+ let isValid: Bool
304
+
305
+ var body: some View {
306
+ VStack(spacing: 20) {
307
+ Text("Verify your backup")
308
+ .font(.headline)
309
+
310
+ Text("Enter the following words from your recovery phrase to confirm you've saved it.")
311
+ .font(.callout)
312
+ .foregroundStyle(.secondary)
313
+ .multilineTextAlignment(.center)
314
+
315
+ VStack(spacing: 12) {
316
+ ForEach(Array(confirmWordIndices.enumerated()), id: \.offset) { i, wordIndex in
317
+ HStack {
318
+ Text("Word #\(wordIndex + 1):")
319
+ .font(.callout.bold())
320
+ .frame(width: 80, alignment: .trailing)
321
+
322
+ TextField("Enter word", text: Binding(
323
+ get: {
324
+ let parts = confirmationInput.components(separatedBy: " ")
325
+ return i < parts.count ? parts[i] : ""
326
+ },
327
+ set: { newValue in
328
+ var parts = confirmationInput.components(separatedBy: " ")
329
+ while parts.count <= i { parts.append("") }
330
+ parts[i] = newValue.lowercased().trimmingCharacters(in: .whitespaces)
331
+ confirmationInput = parts.joined(separator: " ")
332
+ }
333
+ ))
334
+ .textFieldStyle(.roundedBorder)
335
+ .font(.system(.body, design: .monospaced))
336
+ }
337
+ }
338
+ }
339
+ .padding()
340
+ .background(.quaternary.opacity(0.5), in: RoundedRectangle(cornerRadius: 12))
341
+
342
+ if isValid {
343
+ HStack {
344
+ Image(systemName: "checkmark.circle.fill")
345
+ .foregroundStyle(.green)
346
+ Text("All words match!")
347
+ .foregroundStyle(.green)
348
+ }
349
+ }
350
+ }
351
+ }
352
+ }
353
+
354
+ // MARK: - Wallet Name Input
355
+
356
+ struct WalletNameInputView: View {
357
+ @Binding var name: String
358
+ let chain: Chain
359
+ let defaultName: String
360
+
361
+ var body: some View {
362
+ VStack(spacing: 20) {
363
+ Image(systemName: chain.iconName)
364
+ .font(.system(size: 40))
365
+ .foregroundStyle(chain.color)
366
+
367
+ Text("Name Your Wallet")
368
+ .font(.headline)
369
+
370
+ Text("Give your wallet a friendly name to identify it easily.")
371
+ .font(.callout)
372
+ .foregroundStyle(.secondary)
373
+ .multilineTextAlignment(.center)
374
+
375
+ TextField(defaultName, text: $name)
376
+ .textFieldStyle(.roundedBorder)
377
+ .font(.title3)
378
+ .frame(maxWidth: 300)
379
+ .multilineTextAlignment(.center)
380
+ .onAppear {
381
+ if name.isEmpty { name = defaultName }
382
+ }
383
+ }
384
+ }
385
+ }
386
+
387
+ // MARK: - Wallet Created Success
388
+
389
+ struct WalletCreatedView: View {
390
+ let wallet: Wallet?
391
+ let chain: Chain
392
+
393
+ var body: some View {
394
+ VStack(spacing: 20) {
395
+ Image(systemName: "checkmark.circle.fill")
396
+ .font(.system(size: 56))
397
+ .foregroundStyle(.green)
398
+
399
+ Text("Wallet Created!")
400
+ .font(.title2.bold())
401
+
402
+ if let wallet = wallet {
403
+ VStack(spacing: 12) {
404
+ InfoRow(label: "Network", value: chain.displayName)
405
+ InfoRow(label: "Name", value: wallet.name)
406
+ InfoRow(label: "Address", value: wallet.shortAddress)
407
+ }
408
+ .padding()
409
+ .background(.quaternary.opacity(0.5), in: RoundedRectangle(cornerRadius: 12))
410
+
411
+ Button("Copy Address") {
412
+ NSPasteboard.general.clearContents()
413
+ NSPasteboard.general.setString(wallet.address, forType: .string)
414
+ }
415
+ .buttonStyle(.bordered)
416
+ .controlSize(.small)
417
+ }
418
+ }
419
+ }
420
+ }
421
+
422
+ struct InfoRow: View {
423
+ let label: String
424
+ let value: String
425
+
426
+ var body: some View {
427
+ HStack {
428
+ Text(label)
429
+ .font(.callout)
430
+ .foregroundStyle(.secondary)
431
+ Spacer()
432
+ Text(value)
433
+ .font(.callout.monospaced())
434
+ .lineLimit(1)
435
+ .truncationMode(.middle)
436
+ }
437
+ }
438
+ }