@cartridge/controller 0.11.2 → 0.11.3

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (59) hide show
  1. package/.turbo/turbo-build$colon$deps.log +18 -18
  2. package/.turbo/turbo-build.log +16 -16
  3. package/dist/iframe/base.d.ts +0 -1
  4. package/dist/index.d.ts +1 -0
  5. package/dist/index.js +1854 -811
  6. package/dist/index.js.map +1 -1
  7. package/dist/node/index.cjs +1 -1
  8. package/dist/node/index.cjs.map +1 -1
  9. package/dist/node/index.d.cts +1 -1
  10. package/dist/node/index.d.ts +1 -1
  11. package/dist/node/index.js +1 -1
  12. package/dist/node/index.js.map +1 -1
  13. package/dist/{provider-s-80NdXp.js → provider-DCZ6z1Gs.js} +38 -24
  14. package/dist/provider-DCZ6z1Gs.js.map +1 -0
  15. package/dist/session.js +2 -2
  16. package/dist/stats.html +1 -1
  17. package/dist/toast/components/close-button.d.ts +1 -0
  18. package/dist/toast/components/progress-bar.d.ts +6 -0
  19. package/dist/toast/index.d.ts +57 -0
  20. package/dist/toast/styles.d.ts +1 -0
  21. package/dist/toast/types.d.ts +39 -0
  22. package/dist/toast/utils/progress-bar.d.ts +9 -0
  23. package/dist/toast/utils.d.ts +8 -0
  24. package/dist/toast/variants/achievement.d.ts +3 -0
  25. package/dist/toast/variants/error.d.ts +3 -0
  26. package/dist/toast/variants/index.d.ts +6 -0
  27. package/dist/toast/variants/marketplace.d.ts +3 -0
  28. package/dist/toast/variants/network-switch.d.ts +3 -0
  29. package/dist/toast/variants/quest.d.ts +3 -0
  30. package/dist/toast/variants/transaction.d.ts +3 -0
  31. package/dist/types.d.ts +3 -3
  32. package/dist/utils.d.ts +1 -0
  33. package/dist/wallets/index.d.ts +1 -0
  34. package/dist/wallets/phantom-evm/index.d.ts +7 -0
  35. package/dist/wallets/types.d.ts +2 -2
  36. package/package.json +2 -3
  37. package/src/iframe/base.ts +2 -20
  38. package/src/index.ts +1 -0
  39. package/src/toast/components/close-button.ts +82 -0
  40. package/src/toast/components/progress-bar.ts +60 -0
  41. package/src/toast/index.ts +263 -0
  42. package/src/toast/styles.ts +142 -0
  43. package/src/toast/types.ts +67 -0
  44. package/src/toast/utils/progress-bar.ts +23 -0
  45. package/src/toast/utils.ts +65 -0
  46. package/src/toast/variants/achievement.ts +244 -0
  47. package/src/toast/variants/error.ts +107 -0
  48. package/src/toast/variants/index.ts +6 -0
  49. package/src/toast/variants/marketplace.ts +145 -0
  50. package/src/toast/variants/network-switch.ts +72 -0
  51. package/src/toast/variants/quest.ts +164 -0
  52. package/src/toast/variants/transaction.ts +256 -0
  53. package/src/types.ts +1 -0
  54. package/src/utils.ts +15 -0
  55. package/src/wallets/bridge.ts +4 -0
  56. package/src/wallets/index.ts +1 -0
  57. package/src/wallets/phantom-evm/index.ts +8 -0
  58. package/src/wallets/types.ts +5 -1
  59. package/dist/provider-s-80NdXp.js.map +0 -1
@@ -0,0 +1,164 @@
1
+ import { QuestToastOptions } from "../types";
2
+ import { CloseButton } from "../components/close-button";
3
+
4
+ // Inject quest toast specific styles
5
+ export function injectQuestStyles(targetDoc: Document): void {
6
+ if (targetDoc.getElementById("cartridge-toast-quest-styles")) {
7
+ return;
8
+ }
9
+
10
+ const style = targetDoc.createElement("style");
11
+ style.id = "cartridge-toast-quest-styles";
12
+ style.textContent = `
13
+ /* Quest Toast */
14
+ .cartridge-toast.quest {
15
+ background-color: #161A17;
16
+ border-radius: 8px;
17
+ width: 360px;
18
+ padding: 12px;
19
+ padding-bottom: 16px;
20
+ display: flex;
21
+ align-items: center;
22
+ justify-content: space-between;
23
+ position: relative;
24
+ overflow: hidden;
25
+ min-height: 52px;
26
+ box-sizing: border-box;
27
+ }
28
+
29
+ .cartridge-toast.quest .image-content-container {
30
+ display: flex;
31
+ align-items: center;
32
+ gap: 8px;
33
+ flex: 1;
34
+ }
35
+
36
+ .cartridge-toast.quest .image {
37
+ width: 30px;
38
+ height: 30px;
39
+ aspect-ratio: 1/1;
40
+ }
41
+
42
+ .cartridge-toast.quest .image-container {
43
+ display: flex;
44
+ padding: 5px;
45
+ justify-content: center;
46
+ align-items: center;
47
+ gap: 10px;
48
+ border-radius: 4px;
49
+ background: #161A17;
50
+ }
51
+
52
+ .cartridge-toast.quest .content {
53
+ display: flex;
54
+ height: 40px;
55
+ flex-direction: column;
56
+ justify-content: center;
57
+ align-items: flex-start;
58
+ gap: 2px;
59
+ }
60
+
61
+ .cartridge-toast.quest .title {
62
+ color: #FFF;
63
+ font-family: Inter;
64
+ font-size: 14px;
65
+ font-style: normal;
66
+ font-weight: 500;
67
+ line-height: 20px;
68
+ }
69
+
70
+ .cartridge-toast.quest .subtitle {
71
+ color: #808080;
72
+ font-family: Inter;
73
+ font-size: 12px;
74
+ font-style: normal;
75
+ font-weight: 400;
76
+ line-height: 16px;
77
+ }
78
+
79
+ .cartridge-toast.quest .xp-section-container {
80
+ display: flex;
81
+ padding: 10px;
82
+ flex-direction: column;
83
+ align-items: flex-start;
84
+ gap: 10px;
85
+ }
86
+
87
+ .cartridge-toast.quest .xp-section {
88
+ display: flex;
89
+ align-items: center;
90
+ gap: 2px;
91
+ align-self: stretch;
92
+ }
93
+
94
+ .cartridge-toast.quest .xp-section .xp-icon {
95
+ width: 20px;
96
+ height: 20px;
97
+ aspect-ratio: 1/1;
98
+ }
99
+
100
+ .cartridge-toast.quest .xp-section .xp-amount {
101
+ color: #FFF;
102
+ /* Inter/Regular 14px */
103
+ font-family: Inter;
104
+ font-size: 14px;
105
+ font-style: normal;
106
+ font-weight: 400;
107
+ line-height: 20px; /* 142.857% */
108
+ }
109
+ `;
110
+ targetDoc.head.appendChild(style);
111
+ }
112
+
113
+ // Create quest toast element
114
+ export function createQuestToast(options: QuestToastOptions): HTMLElement {
115
+ const toast = document.createElement("div");
116
+ toast.className = "cartridge-toast quest";
117
+
118
+ const imageContentContainer = document.createElement("div");
119
+ imageContentContainer.className = "image-content-container";
120
+
121
+ const imageContainer = document.createElement("div");
122
+ imageContainer.className = "image-container";
123
+
124
+ const icon = getQuestIcon();
125
+ icon.className = "image";
126
+ imageContainer.appendChild(icon);
127
+
128
+ const content = document.createElement("div");
129
+ content.className = "content";
130
+
131
+ const title = document.createElement("p");
132
+ title.className = "title";
133
+ title.textContent = options.title;
134
+
135
+ const subtitle = document.createElement("p");
136
+ subtitle.className = "subtitle";
137
+ subtitle.textContent = options.subtitle || "Earned!";
138
+
139
+ content.appendChild(title);
140
+ content.appendChild(subtitle);
141
+
142
+ imageContentContainer.appendChild(imageContainer);
143
+ imageContentContainer.appendChild(content);
144
+
145
+ const closeButton = CloseButton(false);
146
+
147
+ toast.appendChild(imageContentContainer);
148
+ toast.appendChild(closeButton);
149
+
150
+ return toast;
151
+ }
152
+
153
+ const getQuestIcon = () => {
154
+ const container = document.createElement("div");
155
+ const svg = document.createElementNS("http://www.w3.org/2000/svg", "svg");
156
+ svg.setAttribute("width", "34");
157
+ svg.setAttribute("height", "34");
158
+ svg.setAttribute("viewBox", "0 0 30 30");
159
+ svg.style.width = "100%";
160
+ svg.style.height = "100%";
161
+ svg.innerHTML = `<path d="M3 6.5V8C3 8.55312 3.44687 9 4 9H4.5H6V6.5C6 5.67188 5.32812 5 4.5 5C3.67188 5 3 5.67188 3 6.5ZM6.5 5C6.8125 5.41875 7 5.9375 7 6.5V16C7 17.1031 7.89687 18 9 18C10.1031 18 11 17.1031 11 16V15.8344C11 14.8219 11.8219 14 12.8344 14H18V8C18 6.34375 16.6562 5 15 5H6.5ZM17.5 19C19.4344 19 21 17.4344 21 15.5C21 15.225 20.775 15 20.5 15H12.8344C12.375 15 12 15.3719 12 15.8344V16C12 17.6562 10.6562 19 9 19H14.5H17.5Z" fill="white"/>`;
162
+ container.appendChild(svg);
163
+ return container;
164
+ };
@@ -0,0 +1,256 @@
1
+ import { TransactionToastOptions } from "../types";
2
+ import { CloseButton } from "../components/close-button";
3
+
4
+ // Inject transaction toast specific styles
5
+ export function injectTransactionStyles(targetDoc: Document): void {
6
+ if (targetDoc.getElementById("cartridge-toast-transaction-styles")) {
7
+ return;
8
+ }
9
+
10
+ const style = targetDoc.createElement("style");
11
+ style.id = "cartridge-toast-transaction-styles";
12
+ style.textContent = `
13
+ /* Transaction Toast */
14
+ .cartridge-toast.transaction {
15
+ background-color: #161A17;
16
+ border-radius: 8px;
17
+ position: relative;
18
+ overflow: hidden;
19
+ }
20
+
21
+ /* Expanded State */
22
+ .cartridge-toast.transaction.expanded {
23
+ width: 360px;
24
+ }
25
+
26
+ .cartridge-toast.transaction.expanded .toast-content {
27
+ display: flex;
28
+ align-items: center;
29
+ justify-content: space-between;
30
+ width: 100%;
31
+ gap: 8px;
32
+ box-sizing: border-box;
33
+ }
34
+
35
+ .cartridge-toast.transaction.expanded .label-bar {
36
+ display: flex;
37
+ align-items: center;
38
+ padding: 12px;
39
+ gap: 8px;
40
+ flex: 1 0 0;
41
+ }
42
+
43
+ .cartridge-toast.transaction.expanded .label-bar .label-container {
44
+ display: flex;
45
+ align-items: center;
46
+ gap: 8px;
47
+ }
48
+
49
+ .cartridge-toast.transaction.expanded .label-bar .icon-container {
50
+ width: 24px;
51
+ height: 24px;
52
+ display: flex;
53
+ align-items: center;
54
+ justify-content: center;
55
+ }
56
+
57
+ .cartridge-toast.transaction.expanded .label-bar p.status {
58
+ color: #FFF;
59
+ font-family: Inter;
60
+ font-size: 14px;
61
+ font-style: normal;
62
+ font-weight: 500;
63
+ line-height: 20px;
64
+ margin: 0;
65
+ }
66
+
67
+ .cartridge-toast.transaction.expanded .label-bar .activity-feed-container {
68
+ display: flex;
69
+ padding: 2px;
70
+ align-items: center;
71
+ border-radius: 2px;
72
+ background: rgba(0, 0, 0, 0.08);
73
+ }
74
+
75
+ .cartridge-toast.transaction.expanded .label-bar .activity-icon {
76
+ width: 16px;
77
+ height: 16px;
78
+ display: flex;
79
+ align-items: center;
80
+ justify-content: center;
81
+ }
82
+
83
+ .cartridge-toast.transaction.expanded .label-bar .activity-label-container {
84
+ display: flex;
85
+ padding: 0 2px;
86
+ justify-content: center;
87
+ align-items: center;
88
+ }
89
+
90
+ .cartridge-toast.transaction.expanded .label-bar span.activity-label {
91
+ color: #3F3;
92
+ font-family: Inter;
93
+ font-size: 12px;
94
+ font-style: normal;
95
+ font-weight: 400;
96
+ line-height: 16px;
97
+ }
98
+
99
+ .cartridge-toast.transaction.expanded .close-button-container {
100
+ display: flex;
101
+ align-items: center;
102
+ }
103
+
104
+ /* Progress Bar - will be added dynamically */
105
+ .cartridge-toast.transaction .cartridge-toast-progress-bar {
106
+ background: rgba(255, 255, 255, 0.1);
107
+ }
108
+
109
+ .cartridge-toast.transaction .cartridge-toast-progress-bar-fill {
110
+ background: #3F3;
111
+ }
112
+
113
+ /* Collapsed State */
114
+ .cartridge-toast.transaction.collapsed {
115
+ display: inline-flex;
116
+ padding: 10px;
117
+ align-items: center;
118
+ justify-content: center;
119
+ }
120
+
121
+ .cartridge-toast.transaction.collapsed .collapsed-icon {
122
+ width: 28px;
123
+ height: 28px;
124
+ display: flex;
125
+ align-items: center;
126
+ justify-content: center;
127
+ }
128
+
129
+ /* Spinner Animation */
130
+ @keyframes spin {
131
+ from {
132
+ transform: rotate(0deg);
133
+ }
134
+ to {
135
+ transform: rotate(360deg);
136
+ }
137
+ }
138
+
139
+ .cartridge-toast.transaction .icon-container.spinning,
140
+ .cartridge-toast.transaction .collapsed-icon.spinning {
141
+ animation: spin 1s linear infinite;
142
+ }
143
+ `;
144
+ targetDoc.head.appendChild(style);
145
+ }
146
+
147
+ // Create transaction toast element
148
+ export function createTransactionToast(
149
+ options: TransactionToastOptions,
150
+ ): HTMLElement {
151
+ const toast = document.createElement("div");
152
+ toast.className = `cartridge-toast transaction ${options.isExpanded ? "expanded" : "collapsed"}`;
153
+
154
+ if (options.isExpanded) {
155
+ // Create main content container
156
+ const toastContent = document.createElement("div");
157
+ toastContent.className = "toast-content";
158
+
159
+ // Create label bar
160
+ const labelBar = document.createElement("div");
161
+ labelBar.className = "label-bar";
162
+
163
+ const labelContainer = document.createElement("div");
164
+ labelContainer.className = "label-container";
165
+
166
+ // Create icon container
167
+ const iconContainer = document.createElement("div");
168
+ iconContainer.className = "icon-container";
169
+ if (options.status === "confirming") {
170
+ iconContainer.classList.add("spinning");
171
+ iconContainer.innerHTML = `
172
+ <svg xmlns="http://www.w3.org/2000/svg" width="24" height="24" viewBox="0 0 24 24" fill="none">
173
+ <path d="M11.1111 5.77756C11.1111 5.28673 11.5083 4.88867 12 4.88867C15.9278 4.88867 19.1111 8.07201 19.1111 11.9998C19.1111 13.2942 18.7639 14.5109 18.1583 15.5553C17.9139 15.9803 17.3694 16.1276 16.9194 15.8803C16.5194 15.6359 16.375 15.0914 16.6194 14.6414C17.0722 13.8831 17.3333 12.972 17.3333 11.9748C17.3333 9.03034 14.9444 6.64145 12 6.64145C11.5083 6.64145 11.1111 6.26839 11.1111 5.75256V5.77756Z" fill="white"/>
174
+ <path opacity="0.25" d="M11.975 6.66645C9.03058 6.66645 6.64169 9.03034 6.64169 11.9998C6.64169 14.9442 9.03058 17.3331 11.975 17.3331C13.9472 17.3331 15.6472 16.2914 16.5806 14.7331L16.5834 14.7359C16.3917 15.1498 16.5417 15.647 16.9195 15.8803C17.3695 16.1276 17.9139 15.9803 18.1584 15.5553C18.1639 15.547 18.1695 15.5387 18.1722 15.5303C16.9472 17.6692 14.6417 19.1109 12 19.1109C8.07225 19.1109 4.88892 15.9276 4.88892 11.9998C4.88892 8.07201 8.07225 4.88867 12 4.88867C11.5084 4.88867 11.1111 5.28673 11.1111 5.77756C11.1111 6.26839 11.5084 6.66645 12 6.66645H11.975Z" fill="white" fill-opacity="0.64"/>
175
+ </svg>
176
+ `;
177
+ } else {
178
+ iconContainer.innerHTML = `
179
+ <svg xmlns="http://www.w3.org/2000/svg" width="24" height="24" viewBox="0 0 24 24" fill="none">
180
+ <path d="M8.36382 18.5465L4 14.1827L5.45427 12.7284L8.36382 15.638L18.5457 5.45508L20 6.91032L8.36382 18.5465Z" fill="#33FF33"/>
181
+ </svg>
182
+ `;
183
+ }
184
+
185
+ // Create status text
186
+ const status = document.createElement("p");
187
+ status.className = "status";
188
+ status.textContent =
189
+ options.status === "confirming" ? "Confirming" : "Confirmed";
190
+
191
+ labelContainer.appendChild(iconContainer);
192
+ labelContainer.appendChild(status);
193
+
194
+ // Add activity label if provided
195
+ if (options.label) {
196
+ const activityFeedContainer = document.createElement("div");
197
+ activityFeedContainer.className = "activity-feed-container";
198
+
199
+ const activityIcon = document.createElement("div");
200
+ activityIcon.className = "activity-icon";
201
+ activityIcon.innerHTML = `
202
+ <svg xmlns="http://www.w3.org/2000/svg" width="16" height="16" viewBox="0 0 16 16" fill="none">
203
+ <path d="M7.985 4.0002C8.23167 3.99353 8.45 4.1552 8.515 4.39353L9.74833 8.91353L10.0433 8.32353C10.2233 7.96187 10.5933 7.73353 10.9967 7.73353H12.8C13.095 7.73353 13.3333 7.97187 13.3333 8.26687C13.3333 8.56187 13.095 8.8002 12.8 8.8002H10.9967L10.0767 10.6385C9.97833 10.8369 9.76667 10.9519 9.54667 10.9302C9.32667 10.9085 9.14333 10.7535 9.085 10.5402L8.06167 6.78853L6.92167 12.1119C6.87 12.3519 6.66333 12.5252 6.41833 12.5335C6.17333 12.5419 5.955 12.3819 5.88833 12.1469L4.93167 8.8002H3.2C2.905 8.8002 2.66667 8.56187 2.66667 8.26687C2.66667 7.97187 2.905 7.73353 3.2 7.73353H4.93167C5.40833 7.73353 5.82667 8.04853 5.95667 8.50687L6.32667 9.8002L7.47833 4.42187C7.53 4.18187 7.74 4.00687 7.985 4.0002Z" fill="#33FF33"/>
204
+ </svg>
205
+ `;
206
+
207
+ const activityLabelContainer = document.createElement("div");
208
+ activityLabelContainer.className = "activity-label-container";
209
+
210
+ const activityLabel = document.createElement("span");
211
+ activityLabel.className = "activity-label";
212
+ activityLabel.textContent = options.label;
213
+
214
+ activityLabelContainer.appendChild(activityLabel);
215
+ activityFeedContainer.appendChild(activityIcon);
216
+ activityFeedContainer.appendChild(activityLabelContainer);
217
+ labelContainer.appendChild(activityFeedContainer);
218
+ }
219
+
220
+ labelBar.appendChild(labelContainer);
221
+ toastContent.appendChild(labelBar);
222
+
223
+ // Create close button
224
+ const closeButtonContainer = document.createElement("div");
225
+ closeButtonContainer.className = "close-button-container";
226
+ const closeButton = CloseButton();
227
+ closeButtonContainer.appendChild(closeButton);
228
+ toastContent.appendChild(closeButtonContainer);
229
+
230
+ toast.appendChild(toastContent);
231
+ } else {
232
+ // Collapsed state
233
+ const collapsedIcon = document.createElement("div");
234
+ collapsedIcon.className = "collapsed-icon";
235
+
236
+ if (options.status === "confirming") {
237
+ collapsedIcon.classList.add("spinning");
238
+ collapsedIcon.innerHTML = `
239
+ <svg xmlns="http://www.w3.org/2000/svg" width="28" height="28" viewBox="0 0 28 28" fill="none">
240
+ <path d="M12.9629 6.74016C12.9629 6.16752 13.4264 5.70312 14 5.70312C18.5824 5.70312 22.2963 9.41701 22.2963 13.9994C22.2963 15.5096 21.8912 16.9291 21.1847 18.1476C20.8995 18.6434 20.2643 18.8152 19.7393 18.5267C19.2727 18.2416 19.1041 17.6064 19.3893 17.0814C19.9176 16.1966 20.2222 15.1337 20.2222 13.9703C20.2222 10.5351 17.4352 7.74803 14 7.74803C13.4264 7.74803 12.9629 7.3128 12.9629 6.711V6.74016Z" fill="white"/>
241
+ <path opacity="0.25" d="M13.9709 7.7772C10.5357 7.7772 7.74864 10.5351 7.74864 13.9994C7.74864 17.4346 10.5357 20.2216 13.9709 20.2216C16.2718 20.2216 18.2551 19.0064 19.344 17.1883L19.3473 17.1916C19.1236 17.6744 19.2986 18.2545 19.7394 18.5267C20.2644 18.8152 20.8996 18.6434 21.1848 18.1476C21.1912 18.1378 21.1977 18.1281 21.201 18.1184C19.7718 20.6138 17.082 22.2957 14 22.2957C9.41762 22.2957 5.70374 18.5818 5.70374 13.9994C5.70374 9.41701 9.41762 5.70312 14 5.70312C13.4264 5.70312 12.963 6.16752 12.963 6.74016C12.963 7.3128 13.4264 7.7772 14 7.7772H13.9709Z" fill="white" fill-opacity="0.64"/>
242
+ </svg>
243
+ `;
244
+ } else {
245
+ collapsedIcon.innerHTML = `
246
+ <svg xmlns="http://www.w3.org/2000/svg" width="28" height="28" viewBox="0 0 28 28" fill="none">
247
+ <path d="M9.75779 21.6366L4.66667 16.5455L6.36332 14.8489L9.75779 18.2433L21.6367 6.36328L23.3333 8.06107L9.75779 21.6366Z" fill="#33FF33"/>
248
+ </svg>
249
+ `;
250
+ }
251
+
252
+ toast.appendChild(collapsedIcon);
253
+ }
254
+
255
+ return toast;
256
+ }
package/src/types.ts CHANGED
@@ -253,6 +253,7 @@ export type ProfileContextTypeVariant =
253
253
  | "inventory"
254
254
  | "trophies"
255
255
  | "achievements"
256
+ | "quests"
256
257
  | "leaderboard"
257
258
  | "activity";
258
259
 
package/src/utils.ts CHANGED
@@ -214,3 +214,18 @@ export function isMobile() {
214
214
  navigator.maxTouchPoints > 0
215
215
  );
216
216
  }
217
+
218
+ // Sanitize image src to prevent XSS
219
+ export function sanitizeImageSrc(src: string): string {
220
+ // Allow only http/https URLs (absolute)
221
+ try {
222
+ const url = new URL(src, window.location.origin);
223
+ if (url.protocol === "http:" || url.protocol === "https:") {
224
+ return url.href;
225
+ }
226
+ } catch (_) {
227
+ // If invalid, fall through to fallback src below
228
+ }
229
+ // Fallback image (transparent pixel or default)
230
+ return "data:image/gif;base64,R0lGODlhAQABAAAAACH5BAEKAAEALAAAAAABAAEAAAICTAEAOw==";
231
+ }
@@ -3,6 +3,7 @@ import { ArgentWallet } from "./argent";
3
3
  import { BaseWallet } from "./base";
4
4
  import { MetaMaskWallet } from "./metamask";
5
5
  import { PhantomWallet } from "./phantom";
6
+ import { PhantomEVMWallet } from "./phantom-evm";
6
7
  import { RabbyWallet } from "./rabby";
7
8
  import {
8
9
  ExternalWallet,
@@ -28,6 +29,9 @@ export class WalletBridge {
28
29
  const phantom = new PhantomWallet();
29
30
  this.walletAdapters.set("phantom", phantom);
30
31
 
32
+ const phantomEvm = new PhantomEVMWallet();
33
+ this.walletAdapters.set("phantom-evm", phantomEvm);
34
+
31
35
  const argent = new ArgentWallet();
32
36
  this.walletAdapters.set("argent", argent);
33
37
 
@@ -5,6 +5,7 @@ export * from "./bridge";
5
5
  export * from "./ethereum-base";
6
6
  export * from "./metamask";
7
7
  export * from "./phantom";
8
+ export * from "./phantom-evm";
8
9
  export * from "./rabby";
9
10
  export * from "./types";
10
11
  export * from "./platform";
@@ -0,0 +1,8 @@
1
+ import { ExternalWalletType } from "../types";
2
+ import { EthereumWalletBase } from "../ethereum-base";
3
+
4
+ export class PhantomEVMWallet extends EthereumWalletBase {
5
+ readonly type: ExternalWalletType = "phantom-evm";
6
+ readonly rdns = "app.phantom";
7
+ readonly displayName = "Phantom";
8
+ }
@@ -1,4 +1,8 @@
1
- export const AUTH_EXTERNAL_WALLETS = ["metamask", "rabby"] as const;
1
+ export const AUTH_EXTERNAL_WALLETS = [
2
+ "metamask",
3
+ "rabby",
4
+ "phantom-evm",
5
+ ] as const;
2
6
  export type AuthExternalWallet = (typeof AUTH_EXTERNAL_WALLETS)[number];
3
7
 
4
8
  export const EXTRA_EXTERNAL_WALLETS = [
@@ -1 +0,0 @@
1
- {"version":3,"file":"provider-s-80NdXp.js","sources":["../src/wallets/types.ts","../src/types.ts","../src/utils.ts","../src/constants.ts","../src/errors.ts","../../../node_modules/.pnpm/@starknet-io+types-js@0.8.4/node_modules/@starknet-io/types-js/dist/esm/wallet-api/constants.js","../src/icon.ts","../src/mutex.ts","../src/provider.ts"],"sourcesContent":["export const AUTH_EXTERNAL_WALLETS = [\"metamask\", \"rabby\"] as const;\nexport type AuthExternalWallet = (typeof AUTH_EXTERNAL_WALLETS)[number];\n\nexport const EXTRA_EXTERNAL_WALLETS = [\n \"argent\",\n \"braavos\",\n \"phantom\",\n \"base\",\n] as const;\nexport type ExtraExternalWallet = (typeof EXTRA_EXTERNAL_WALLETS)[number];\n\nexport const EXTERNAL_WALLETS = [\n ...AUTH_EXTERNAL_WALLETS,\n ...EXTRA_EXTERNAL_WALLETS,\n] as const;\n\nexport type ExternalWalletType = (typeof EXTERNAL_WALLETS)[number];\n\nexport type ExternalPlatform =\n | \"starknet\"\n | \"ethereum\"\n | \"solana\"\n | \"base\"\n | \"arbitrum\"\n | \"optimism\";\n\nexport interface ExternalWallet {\n type: ExternalWalletType;\n available: boolean;\n version?: string;\n chainId?: string;\n name?: string;\n platform?: ExternalPlatform;\n connectedAccounts?: string[];\n}\n\nexport interface ExternalWalletResponse<T = unknown> {\n success: boolean;\n wallet: ExternalWalletType;\n result?: T;\n error?: string;\n account?: string;\n}\n\nexport interface WalletAdapter {\n type: ExternalWalletType;\n platform: ExternalPlatform | undefined;\n\n // Methods\n isAvailable(): boolean;\n getInfo(): ExternalWallet;\n getConnectedAccounts(): string[];\n connect(): Promise<ExternalWalletResponse<any>>;\n signMessage?(\n message: string,\n address?: string,\n ): Promise<ExternalWalletResponse<any>>;\n signTypedData?(data: any): Promise<ExternalWalletResponse<any>>;\n sendTransaction(tx: any): Promise<ExternalWalletResponse<any>>;\n getBalance(tokenAddress?: string): Promise<ExternalWalletResponse<any>>;\n switchChain(chainId: string): Promise<boolean>;\n waitForTransaction(\n txHash: string,\n timeoutMs?: number,\n ): Promise<ExternalWalletResponse<any>>;\n disconnect?(): void;\n}\n","import { Policy, SessionPolicies } from \"@cartridge/presets\";\nimport {\n AddInvokeTransactionResult,\n ChainId,\n Signature,\n TypedData,\n} from \"@starknet-io/types-js\";\nimport {\n Abi,\n BigNumberish,\n Call,\n constants,\n InvocationsDetails,\n} from \"starknet\";\nimport { KeychainIFrame } from \"./iframe\";\nimport {\n AUTH_EXTERNAL_WALLETS,\n EXTERNAL_WALLETS,\n ExternalWallet,\n ExternalWalletResponse,\n ExternalWalletType,\n} from \"./wallets/types\";\n\nexport type KeychainSession = {\n chainId: constants.StarknetChainId;\n policies: Policy[];\n maxFee: BigNumberish;\n expiresAt: bigint;\n credentials: {\n authorization: string[];\n privateKey: string;\n };\n};\n\nexport const EMBEDDED_WALLETS = [\n \"google\",\n \"webauthn\",\n \"discord\",\n \"walletconnect\",\n \"password\",\n] as const;\n\nexport type EmbeddedWallet = (typeof EMBEDDED_WALLETS)[number];\n\nexport const ALL_AUTH_OPTIONS = [\n ...EMBEDDED_WALLETS,\n ...EXTERNAL_WALLETS,\n] as const;\n\nexport type AuthOption = (typeof ALL_AUTH_OPTIONS)[number];\n\nexport const IMPLEMENTED_AUTH_OPTIONS = [\n ...EMBEDDED_WALLETS,\n ...AUTH_EXTERNAL_WALLETS,\n];\n\nexport type AuthOptions = (typeof IMPLEMENTED_AUTH_OPTIONS)[number][];\n\nexport enum ResponseCodes {\n SUCCESS = \"SUCCESS\",\n NOT_CONNECTED = \"NOT_CONNECTED\",\n ERROR = \"ERROR\",\n CANCELED = \"CANCELED\",\n USER_INTERACTION_REQUIRED = \"USER_INTERACTION_REQUIRED\",\n}\n\nexport type ConnectError = {\n code: ResponseCodes;\n message: string;\n error?: ControllerError;\n};\n\nexport type ControllerError = {\n code: Number;\n message: string;\n data?: any;\n};\n\nexport type ConnectReply = {\n code: ResponseCodes.SUCCESS;\n address: string;\n policies?: SessionPolicies;\n};\n\nexport type ExecuteReply =\n | (AddInvokeTransactionResult & {\n code: ResponseCodes.SUCCESS;\n })\n | {\n code: ResponseCodes.USER_INTERACTION_REQUIRED;\n };\n\nexport type ProbeReply = {\n code: ResponseCodes.SUCCESS;\n address: string;\n rpcUrl?: string;\n};\n\nexport type DeployReply = {\n code: ResponseCodes.SUCCESS;\n transaction_hash: string;\n};\n\nexport type IFrames = {\n keychain?: KeychainIFrame;\n version?: number;\n};\n\nexport interface LookupRequest {\n usernames?: string[];\n addresses?: string[];\n}\n\nexport interface LookupResult {\n username: string;\n addresses: string[];\n}\n\nexport interface LookupResponse {\n results: LookupResult[];\n}\n\nexport enum FeeSource {\n PAYMASTER = \"PAYMASTER\",\n CREDITS = \"CREDITS\",\n}\n\ntype ContractAddress = string;\ntype CartridgeID = string;\nexport type ControllerAccounts = Record<ContractAddress, CartridgeID>;\n\nexport interface Keychain {\n probe(rpcUrl: string): Promise<ProbeReply | ConnectError>;\n connect(signupOptions?: AuthOptions): Promise<ConnectReply | ConnectError>;\n disconnect(): void;\n\n reset(): void;\n revoke(origin: string): void;\n\n deploy(): Promise<DeployReply | ConnectError>;\n execute(\n calls: Call | Call[],\n abis?: Abi[],\n transactionsDetail?: InvocationsDetails,\n sync?: boolean,\n feeSource?: any,\n error?: ControllerError,\n ): Promise<ExecuteReply | ConnectError>;\n signMessage(\n typedData: TypedData,\n account: string,\n async?: boolean,\n ): Promise<Signature | ConnectError>;\n openSettings(): Promise<void | ConnectError>;\n session(): Promise<KeychainSession>;\n sessions(): Promise<{\n [key: string]: KeychainSession;\n }>;\n delegateAccount(): string;\n username(): string;\n openPurchaseCredits(): void;\n openExecute(calls: Call[]): Promise<void>;\n switchChain(rpcUrl: string): Promise<void>;\n openStarterPack(\n id: string | number,\n options?: StarterpackOptions,\n ): Promise<void>;\n navigate(path: string): Promise<void>;\n\n // External wallet methods\n externalDetectWallets(): Promise<ExternalWallet[]>;\n externalConnectWallet(\n type: ExternalWalletType,\n address?: string,\n ): Promise<ExternalWalletResponse>;\n externalSignMessage(\n type: ExternalWalletType,\n message: string,\n ): Promise<ExternalWalletResponse>;\n externalSignTypedData(\n type: ExternalWalletType,\n // eslint-disable-next-line @typescript-eslint/no-explicit-any\n data: any,\n ): Promise<ExternalWalletResponse>;\n externalGetBalance(\n type: ExternalWalletType,\n tokenAddress?: string,\n ): Promise<ExternalWalletResponse>;\n externalSwitchChain(\n type: ExternalWalletType,\n chainId: string,\n ): Promise<boolean>;\n}\n\nexport interface Profile {\n navigate(path: string): void;\n switchChain(rpcUrl: string): Promise<void>;\n}\n\nexport interface Modal {\n open: () => void;\n close: () => void;\n}\n\n/**\n * Options for configuring the controller\n */\nexport type ControllerOptions = ProviderOptions & KeychainOptions;\n\nexport type IFrameOptions = {\n /** The ID of the starter pack to use */\n starterPackId?: string;\n /** The preset to use */\n preset?: string;\n};\n\nexport type Chain = {\n rpcUrl: string;\n};\n\nexport type ProviderOptions = {\n defaultChainId?: ChainId;\n chains?: Chain[];\n};\n\nexport type KeychainOptions = IFrameOptions & {\n policies?: SessionPolicies;\n /** The URL of keychain */\n url?: string;\n /** The origin of keychain */\n origin?: string;\n /** The RPC URL to use (derived from defaultChainId) */\n rpcUrl?: string;\n /** Propagate transaction errors back to caller instead of showing modal */\n propagateSessionErrors?: boolean;\n /** The fee source to use for execute from outside */\n feeSource?: FeeSource;\n /** Signup options (the order of the options is reflected in the UI. It's recommended to group socials and wallets together ) */\n signupOptions?: AuthOptions;\n /** When true, manually provided policies will override preset policies. Default is false. */\n shouldOverridePresetPolicies?: boolean;\n /** The project name of Slot instance. */\n slot?: string;\n /** The namespace to use to fetch trophies data from indexer. Will be mandatory once profile page is in production */\n namespace?: string;\n /** The tokens to be listed on Inventory modal */\n tokens?: Tokens;\n /** When true, defer iframe mounting until connect() is called. Reduces initial load and resource fetching. */\n lazyload?: boolean;\n};\n\nexport type ProfileContextTypeVariant =\n | \"inventory\"\n | \"trophies\"\n | \"achievements\"\n | \"leaderboard\"\n | \"activity\";\n\nexport type Token = \"eth\" | \"strk\" | \"lords\" | \"usdc\" | \"usdt\";\n\nexport type Tokens = {\n erc20?: Token[];\n};\n\nexport type OpenOptions = {\n /** The URL to redirect to after authentication (defaults to current page) */\n redirectUrl?: string;\n};\n\nexport type StarterpackOptions = {\n /** The preimage to use */\n preimage?: string;\n};\n","import { Policy } from \"@cartridge/controller-wasm/controller\";\nimport { Policies, SessionPolicies } from \"@cartridge/presets\";\nimport { ChainId } from \"@starknet-io/types-js\";\nimport {\n addAddressPadding,\n Call,\n CallData,\n constants,\n getChecksumAddress,\n hash,\n shortString,\n typedData,\n TypedDataRevision,\n} from \"starknet\";\nimport { ParsedSessionPolicies } from \"./policies\";\n\n// Whitelist of allowed property names to prevent prototype pollution\nconst ALLOWED_PROPERTIES = new Set([\n \"contracts\",\n \"messages\",\n \"target\",\n \"method\",\n \"name\",\n \"description\",\n \"types\",\n \"domain\",\n \"primaryType\",\n]);\n\nfunction validatePropertyName(prop: string): void {\n if (!ALLOWED_PROPERTIES.has(prop)) {\n throw new Error(`Invalid property name: ${prop}`);\n }\n}\n\nfunction safeObjectAccess<T>(obj: any, prop: string): T {\n validatePropertyName(prop);\n return obj[prop];\n}\n\nexport function normalizeCalls(calls: Call | Call[]) {\n return toArray(calls).map((call) => {\n return {\n entrypoint: call.entrypoint,\n contractAddress: addAddressPadding(call.contractAddress),\n calldata: CallData.toHex(call.calldata),\n };\n });\n}\n\nexport function toSessionPolicies(policies: Policies): SessionPolicies {\n return Array.isArray(policies)\n ? policies.reduce<SessionPolicies>(\n (prev, p) => {\n if (safeObjectAccess<string>(p, \"target\")) {\n const target = getChecksumAddress(\n safeObjectAccess<string>(p, \"target\"),\n );\n const entrypoint = safeObjectAccess<string>(p, \"method\");\n const contracts = safeObjectAccess<Record<string, any>>(\n prev,\n \"contracts\",\n );\n const item = {\n name: humanizeString(entrypoint),\n entrypoint: entrypoint,\n description: safeObjectAccess<string>(p, \"description\"),\n };\n\n if (target in contracts) {\n const methods = toArray(contracts[target].methods);\n contracts[target] = {\n methods: [...methods, item],\n };\n } else {\n contracts[target] = {\n methods: [item],\n };\n }\n } else {\n const messages = safeObjectAccess<any[]>(prev, \"messages\");\n messages.push(p);\n }\n\n return prev;\n },\n { contracts: {}, messages: [] },\n )\n : policies;\n}\n\nexport function toWasmPolicies(policies: ParsedSessionPolicies): Policy[] {\n return [\n ...Object.entries(policies.contracts ?? {}).flatMap(\n ([target, { methods }]) =>\n toArray(methods).map((m) => ({\n target,\n method: hash.getSelectorFromName(m.entrypoint),\n authorized: m.authorized,\n })),\n ),\n ...(policies.messages ?? []).map((p) => {\n const domainHash = typedData.getStructHash(\n p.types,\n \"StarknetDomain\",\n p.domain,\n TypedDataRevision.ACTIVE,\n );\n const typeHash = typedData.getTypeHash(\n p.types,\n p.primaryType,\n TypedDataRevision.ACTIVE,\n );\n\n return {\n scope_hash: hash.computePoseidonHash(domainHash, typeHash),\n authorized: p.authorized,\n };\n }),\n ];\n}\n\nexport function toArray<T>(val: T | T[]): T[] {\n return Array.isArray(val) ? val : [val];\n}\n\nexport function humanizeString(str: string): string {\n return (\n str\n // Convert from camelCase or snake_case\n .replace(/([a-z])([A-Z])/g, \"$1 $2\") // camelCase to spaces\n .replace(/_/g, \" \") // snake_case to spaces\n .toLowerCase()\n // Capitalize first letter\n .replace(/^\\w/, (c) => c.toUpperCase())\n );\n}\n\nexport function parseChainId(url: URL): ChainId {\n const parts = url.pathname.split(\"/\");\n\n // Handle localhost URLs by making a synchronous call to getChainId\n if (\n url.hostname === \"localhost\" ||\n url.hostname === \"127.0.0.1\" ||\n url.hostname === \"0.0.0.0\"\n ) {\n // Check if we're in a browser environment\n if (typeof XMLHttpRequest === \"undefined\") {\n // In Node.js environment (like tests), we can't make synchronous HTTP calls\n // For now, we'll use a placeholder chainId for localhost in tests\n console.warn(\n `Cannot make synchronous HTTP call in Node.js environment for ${url.toString()}`,\n );\n return shortString.encodeShortString(\"LOCALHOST\") as ChainId;\n }\n\n // Use a synchronous XMLHttpRequest to get the chain ID\n const xhr = new XMLHttpRequest();\n xhr.open(\"POST\", url.toString(), false); // false makes it synchronous\n xhr.setRequestHeader(\"Content-Type\", \"application/json\");\n\n const requestBody = JSON.stringify({\n jsonrpc: \"2.0\",\n method: \"starknet_chainId\",\n params: [],\n id: 1,\n });\n\n try {\n xhr.send(requestBody);\n\n if (xhr.status === 200) {\n const response = JSON.parse(xhr.responseText);\n if (response.result) {\n return response.result as ChainId;\n }\n }\n\n throw new Error(\n `Failed to get chain ID from ${url.toString()}: ${xhr.status} ${xhr.statusText}`,\n );\n } catch (error) {\n throw new Error(`Failed to connect to ${url.toString()}: ${error}`);\n }\n }\n\n if (parts.includes(\"starknet\")) {\n if (parts.includes(\"mainnet\")) {\n return constants.StarknetChainId.SN_MAIN;\n } else if (parts.includes(\"sepolia\")) {\n return constants.StarknetChainId.SN_SEPOLIA;\n }\n } else if (parts.length >= 3) {\n const projectName = parts[2];\n if (parts.includes(\"katana\")) {\n return shortString.encodeShortString(\n `WP_${projectName.toUpperCase().replace(/-/g, \"_\")}`,\n ) as ChainId;\n } else if (parts.includes(\"mainnet\")) {\n return shortString.encodeShortString(\n `GG_${projectName.toUpperCase().replace(/-/g, \"_\")}`,\n ) as ChainId;\n }\n }\n\n throw new Error(`Chain ${url.toString()} not supported`);\n}\n\nexport function isMobile() {\n return (\n window.matchMedia(\"(max-width: 768px)\").matches ||\n \"ontouchstart\" in window ||\n navigator.maxTouchPoints > 0\n );\n}\n","export const KEYCHAIN_URL = \"https://x.cartridge.gg\";\nexport const PROFILE_URL = \"https://profile.cartridge.gg\";\nexport const API_URL = \"https://api.cartridge.gg\";\n","export class NotReadyToConnect extends Error {\n constructor() {\n super(\"Not ready to connect\");\n\n Object.setPrototypeOf(this, NotReadyToConnect.prototype);\n }\n}\n","export const Permission = {\n ACCOUNTS: 'accounts',\n};\n//# sourceMappingURL=constants.js.map","export const icon =\n \"data:image/svg+xml;base64,PHN2ZyB3aWR0aD0iODAwIiBoZWlnaHQ9IjgwMCIgdmlld0JveD0iMCAwIDgwMCA4MDAiIGZpbGw9Im5vbmUiIHhtbG5zPSJodHRwOi8vd3d3LnczLm9yZy8yMDAwL3N2ZyI+CjxnIGZpbHRlcj0idXJsKCNmaWx0ZXIwX2RfNTExMl83ODIpIj4KPHBhdGggZD0iTTQ2OS4yMzYgNzBDNDgyLjM5IDcwIDQ5My4wNTMgODAuNjYzIDQ5My4wNTMgOTMuODE2NFYxNDcuMTQ3TDUxNS4zMzggMTQ3LjE0N0w1MTUuNDI4IDE0Ny4xNDdMNTE1LjU1NCAxNDcuMTQ3TDUxNS44MjYgMTQ3LjE0OUM1MTYuMDE2IDE0Ny4xNTEgNTE2LjIyNSAxNDcuMTUzIDUxNi40NTEgMTQ3LjE1N0M1MTYuOTA0IDE0Ny4xNjQgNTE3LjQyOCAxNDcuMTc2IDUxOC4wMiAxNDcuMTk1QzUxOS4yMDEgMTQ3LjIzNCA1MjAuNjYgMTQ3LjMwNCA1MjIuMzYxIDE0Ny40MjRDNTI1Ljc0MSAxNDcuNjYzIDUzMC4xODUgMTQ4LjExNCA1MzUuMzYzIDE0OC45NjlDNTQ1LjAwMSAxNTAuNTYyIDU1OC41NTYgMTUzLjc4IDU3Mi45MTggMTYwLjYwM0w3MzAuNDIgMjI2LjY3MUw3MzIuMTAxIDIyNy41MDVDNzcxLjc4NyAyNDcuMTc3IDc4OS45OTMgMjg2LjI5NiA3ODkuOTkzIDMyMi4wMzZWNTg1Ljg2NUM3ODkuOTkzIDU4Ni4wNTQgNzg5Ljk5NCA1ODYuMjU0IDc4OS45OTQgNTg2LjQ2M0w3ODkuOTk2IDU4Ni45MTNDNzkwLjAzOCA1OTcuMDk2IDc5MC4xNjEgNjI2Ljk5NiA3NjQuMjMxIDY1Mi44MjNMNzE0Ljc2IDcwMi4wOTVMNzE0LjY0MSA3MDIuMjE1QzcwNC42MDEgNzEyLjI3NSA2OTIuMTIzIDcyMC42NTIgNjc2LjI4NCA3MjQuODc5QzY2NC4zOSA3MjguMDU0IDY1Mi44MjcgNzI3Ljk2NiA2NDguNjM3IDcyNy45MzRMNjQ4LjYxOSA3MjcuOTMzQzY0OC40MDkgNzI3LjkzMiA2NDguMjE5IDcyNy45MyA2NDguMDQ3IDcyNy45M0w2NDcuNzUyIDcyNy45MjlINDgwLjcyMUM0NzQuMDk0IDcyNy45MjkgNDY4LjcyMSA3MjIuNTU2IDQ2OC43MjEgNzE1LjkyOVY2NjguMzg4SDMyOC41ODZDMzI4LjU4NiA2NzIuNjI5IDMyOC41NzIgNjk4LjA1MiAzMjguNTYxIDcxNS45NDRDMzI4LjU1NyA3MjIuNTY5IDMyMy4xODYgNzI3LjkyOSAzMTYuNTYxIDcyNy45MjlIMTUyLjI0NkMxNTIuMTA0IDcyNy45MjkgMTUxLjk0MiA3MjcuOTI5IDE1MS43NjIgNzI3LjkzMUwxNTEuMzYyIDcyNy45MzRDMTQ3LjE3MiA3MjcuOTY2IDEzNS42MDkgNzI4LjA1NCAxMjMuNzE0IDcyNC44NzlDMTA3Ljg3MyA3MjAuNjUxIDk1LjM5MzggNzEyLjI3MiA4NS4zNTI5IDcwMi4yMUw4NS4yMzg2IDcwMi4wOTVMMzUuNjcgNjUyLjcyNUwzNS41NzIzIDY1Mi42MjdDOS44NjI0MiA2MjYuNzggOS45NjY3IDU5Ny4xODUgMTAuMDAzIDU4Ni44NzRDMTAuMDA0MyA1ODYuNTEzIDEwLjAwNTUgNTg2LjE3NyAxMC4wMDU1IDU4NS44NjVWMzIyLjAzNkMxMC4wMDU1IDI4Ni40MyAyOC4xNjYyIDI0Ny4xOTkgNjcuODk3NyAyMjcuNTA1TDY5LjU3OSAyMjYuNjcxTDIyNy4wODEgMTYwLjYwM0MyNDEuNDQzIDE1My43OCAyNTQuOTk4IDE1MC41NjIgMjY0LjYzNiAxNDguOTY5QzI2OS44MTQgMTQ4LjExNCAyNzQuMjU4IDE0Ny42NjMgMjc3LjYzOCAxNDcuNDI0QzI3OS4zMzggMTQ3LjMwNCAyODAuNzk4IDE0Ny4yMzQgMjgxLjk3OSAxNDcuMTk1QzI4Mi41NzEgMTQ3LjE3NiAyODMuMDk1IDE0Ny4xNjQgMjgzLjU0NyAxNDcuMTU3TDI4My45MTcgMTQ3LjE1MkwyODQuMTczIDE0Ny4xNDlMMjg0LjQ0NSAxNDcuMTQ3TDI4NC41NzEgMTQ3LjE0N0wyODQuNjYgMTQ3LjE0N0wzMDYuOTQyIDE0Ny4xNDdWOTMuODE2NEMzMDYuOTQyIDgwLjY2MyAzMTcuNjA1IDcwIDMzMC43NTggNzBINDY5LjIzNloiIGZpbGw9IiMxOTFBMUEiLz4KPHBhdGggZD0iTTM2Ni40ODMgMTI5LjU0SDQzMy41MTJWMjA2LjY4N0gzNjYuNDgzVjEyOS41NFoiIGZpbGw9IiNGQkNCNEEiLz4KPHBhdGggZD0iTTI2OS4wMSA2MDIuNDI5SDE0NC4wMDhDMTM1Ljc2OCA2MDIuNDI5IDEzNS43NjggNTk0LjE0NiAxMzUuNzY4IDU5NC4xNDZWMjgwLjg1QzEzNS43NjggMjgwLjg1IDEzNS43NjggMjcyLjY0NCAxNDQuMDA4IDI3Mi42NDRIMzY2LjQ4M0wzNjYuNDgzIDIwNi42ODdIMjg0LjY5QzI4NC42OSAyMDYuNjg3IDI2OC4xMzQgMjA2LjY4NyAyNTEuNTc5IDIxNC44OTNMOTQuMzQxNCAyODAuODVDNzcuNzg2MSAyODkuMDU3IDY5LjU0NjkgMzA1LjYyMyA2OS41NDY5IDMyMi4wMzVWNTg1Ljg2M0M2OS41NDY5IDU5NC4xNDcgNjkuNTQ2OSA2MDIuMzUzIDc3Ljc4NjEgNjEwLjYzNkwxMjcuNDUyIDY2MC4xMDRDMTM1LjY5MSA2NjguMzg3IDE0MS45MjggNjY4LjM4NyAxNTIuMjQ3IDY2OC4zODdIMjY5LjAyOUMyNjkuMDM3IDY0OC4zNCAyNjkuMDQ2IDYyNC42NTUgMjY5LjA1NCA2MDIuODg3SDUyOC4wMTNWNjY4LjM4N0g2NDcuNzUzQzY1OC4wNzEgNjY4LjM4NyA2NjQuMzA4IDY2OC4zODcgNjcyLjU0NyA2NjAuMTA0TDcyMi4yMTMgNjEwLjYzNkM3MzAuNDUzIDYwMi40MjkgNzMwLjQ1MyA1OTQuMTQ3IDczMC40NTMgNTg1Ljg2M1YzMjIuMDM1QzczMC40NTMgMzA1LjU0NiA3MjIuMjEzIDI4OS4wNTcgNzA1LjY1OCAyODAuODVMNTQ4LjQyMSAyMTQuODkzQzUzMS44NjUgMjA2LjY4NyA1MTUuMzEgMjA2LjY4NyA1MTUuMzEgMjA2LjY4N0g0MzMuNTEyTDQzMy41MTIgMjcyLjY0NEg2NTYuMDY5QzY2NC4zMDggMjcyLjY0NCA2NjQuMzA4IDI4MC44NSA2NjQuMzA4IDI4MC44NVY1OTQuMTQ2QzY2NC4zMDggNTk0LjE0NiA2NjQuMzA4IDYwMi40MjkgNjU2LjA2OSA2MDIuNDI5SDUyOC4yNjJWNTM3LjM5NkgyNjkuMDc1QzI2OS4wNzUgNTQzLjcwNyAyNjkuMDE3IDU5Ni45MTIgMjY5LjAxIDYwMi40MjlaIiBmaWxsPSIjRkJDQjRBIi8+CjxwYXRoIGQ9Ik0yNjkuMDA5IDQzNi4xNzJINTI4LjI2MlYzNzAuNjgxSDI2OS4wNzVDMjY5LjA3NSAzNzcuMzczIDI2OS4wMDkgNDM2Ljc4OCAyNjkuMDA5IDQzNi4xNzJaIiBmaWxsPSIjRkJDQjRBIi8+CjwvZz4KPGRlZnM+CjxmaWx0ZXIgaWQ9ImZpbHRlcjBfZF81MTEyXzc4MiIgeD0iLTQiIHk9IjAiIHdpZHRoPSI4MDgiIGhlaWdodD0iODA4IiBmaWx0ZXJVbml0cz0idXNlclNwYWNlT25Vc2UiIGNvbG9yLWludGVycG9sYXRpb24tZmlsdGVycz0ic1JHQiI+CjxmZUZsb29kIGZsb29kLW9wYWNpdHk9IjAiIHJlc3VsdD0iQmFja2dyb3VuZEltYWdlRml4Ii8+CjxmZUNvbG9yTWF0cml4IGluPSJTb3VyY2VBbHBoYSIgdHlwZT0ibWF0cml4IiB2YWx1ZXM9IjAgMCAwIDAgMCAwIDAgMCAwIDAgMCAwIDAgMCAwIDAgMCAwIDEyNyAwIiByZXN1bHQ9ImhhcmRBbHBoYSIvPgo8ZmVPZmZzZXQgZHk9IjQiLz4KPGZlR2F1c3NpYW5CbHVyIHN0ZERldmlhdGlvbj0iMiIvPgo8ZmVDb21wb3NpdGUgaW4yPSJoYXJkQWxwaGEiIG9wZXJhdG9yPSJvdXQiLz4KPGZlQ29sb3JNYXRyaXggdHlwZT0ibWF0cml4IiB2YWx1ZXM9IjAgMCAwIDAgMCAwIDAgMCAwIDAgMCAwIDAgMCAwIDAgMCAwIDAuMjUgMCIvPgo8ZmVCbGVuZCBtb2RlPSJub3JtYWwiIGluMj0iQmFja2dyb3VuZEltYWdlRml4IiByZXN1bHQ9ImVmZmVjdDFfZHJvcFNoYWRvd181MTEyXzc4MiIvPgo8ZmVCbGVuZCBtb2RlPSJub3JtYWwiIGluPSJTb3VyY2VHcmFwaGljIiBpbjI9ImVmZmVjdDFfZHJvcFNoYWRvd181MTEyXzc4MiIgcmVzdWx0PSJzaGFwZSIvPgo8L2ZpbHRlcj4KPC9kZWZzPgo8L3N2Zz4K\";\n","function releaseStub() {}\n\n/**\n * A simple mutual exclusion lock. It allows you to obtain and release a lock,\n * ensuring that only one task can access a critical section at a time.\n */\nexport class Mutex {\n private m_lastPromise: Promise<void> = Promise.resolve();\n\n /**\n * Acquire lock\n * @param [bypass=false] option to skip lock acquisition\n */\n public async obtain(bypass = false): Promise<() => void> {\n let release = releaseStub;\n if (bypass) return release;\n const lastPromise = this.m_lastPromise;\n this.m_lastPromise = new Promise<void>((resolve) => (release = resolve));\n await lastPromise;\n return release;\n }\n}\n","import {\n AddInvokeTransactionParameters,\n AddStarknetChainParameters,\n Permission,\n RequestAccountsParameters,\n RequestFn,\n StarknetWindowObject,\n SwitchStarknetChainParameters,\n TypedData,\n UNEXPECTED_ERROR,\n WalletEventHandlers,\n WalletEventListener,\n WalletEvents,\n} from \"@starknet-io/types-js\";\nimport { WalletAccount } from \"starknet\";\nimport manifest from \"../package.json\";\n\nimport { icon } from \"./icon\";\nimport { Mutex } from \"./mutex\";\n\nconst mutex = new Mutex();\n\nexport default abstract class BaseProvider implements StarknetWindowObject {\n public id = \"controller\";\n public name = \"Controller\";\n public version = manifest.version;\n public icon = icon;\n\n public account?: WalletAccount;\n public subscriptions: WalletEvents[] = [];\n\n private _probePromise: Promise<WalletAccount | undefined> | null = null;\n\n protected async safeProbe(): Promise<WalletAccount | undefined> {\n // If we already have an account, return it\n if (this.account) {\n return this.account;\n }\n\n // If we're already probing, wait for the existing probe\n if (this._probePromise) {\n return this._probePromise;\n }\n\n const release = await mutex.obtain();\n return await new Promise<WalletAccount | undefined>(async (resolve) => {\n try {\n this._probePromise = this.probe();\n const result = await this._probePromise;\n resolve(result);\n } finally {\n this._probePromise = null;\n }\n }).finally(() => {\n release();\n });\n }\n\n request: RequestFn = async (call) => {\n switch (call.type) {\n case \"wallet_getPermissions\":\n await this.safeProbe();\n\n if (this.account) {\n return [Permission.ACCOUNTS];\n }\n\n return [];\n\n case \"wallet_requestAccounts\": {\n if (this.account) {\n return [this.account.address];\n }\n\n const silentMode =\n call.params && (call.params as RequestAccountsParameters).silent_mode;\n\n this.account = await this.safeProbe();\n\n if (!this.account && !silentMode) {\n this.account = await this.connect();\n }\n\n if (this.account) {\n return [this.account.address];\n }\n\n return [];\n }\n\n case \"wallet_watchAsset\":\n throw {\n code: 63,\n message: \"An unexpected error occurred\",\n data: \"wallet_watchAsset not implemented\",\n } as UNEXPECTED_ERROR;\n\n case \"wallet_addStarknetChain\": {\n let params = call.params as AddStarknetChainParameters;\n return this.addStarknetChain(params);\n }\n\n case \"wallet_switchStarknetChain\": {\n let params = call.params as SwitchStarknetChainParameters;\n return this.switchStarknetChain(params.chainId);\n }\n\n case \"wallet_requestChainId\":\n if (!this.account) {\n throw {\n code: 63,\n message: \"An unexpected error occurred\",\n data: \"Account not initialized\",\n } as UNEXPECTED_ERROR;\n }\n\n return await this.account.getChainId();\n\n case \"wallet_deploymentData\":\n throw {\n code: 63,\n message: \"An unexpected error occurred\",\n data: \"wallet_deploymentData not implemented\",\n } as UNEXPECTED_ERROR;\n\n case \"wallet_addInvokeTransaction\":\n if (!this.account) {\n throw {\n code: 63,\n message: \"An unexpected error occurred\",\n data: \"Account not initialized\",\n } as UNEXPECTED_ERROR;\n }\n\n let params = call.params as AddInvokeTransactionParameters;\n return await this.account.execute(\n params.calls.map((call) => ({\n contractAddress: call.contract_address,\n entrypoint: call.entry_point,\n calldata: call.calldata,\n })),\n );\n\n case \"wallet_addDeclareTransaction\":\n throw {\n code: 63,\n message: \"An unexpected error occurred\",\n data: \"wallet_addDeclareTransaction not implemented\",\n } as UNEXPECTED_ERROR;\n\n case \"wallet_signTypedData\": {\n if (!this.account) {\n throw {\n code: 63,\n message: \"An unexpected error occurred\",\n data: \"Account not initialized\",\n } as UNEXPECTED_ERROR;\n }\n\n return await this.account.signMessage(call.params as TypedData);\n }\n\n case \"wallet_supportedSpecs\":\n return [];\n case \"wallet_supportedWalletApi\":\n return [];\n default:\n throw {\n code: 63,\n message: \"An unexpected error occurred\",\n data: `Unknown RPC call type: ${call.type}`,\n } as UNEXPECTED_ERROR;\n }\n };\n\n on: WalletEventListener = <E extends keyof WalletEventHandlers>(\n event: E,\n handler: WalletEventHandlers[E],\n ): void => {\n if (event !== \"accountsChanged\" && event !== \"networkChanged\") {\n throw new Error(`Unknown event: ${event}`);\n }\n this.subscriptions.push({ type: event, handler } as WalletEvents);\n };\n\n off: WalletEventListener = <E extends keyof WalletEventHandlers>(\n event: E,\n handler: WalletEventHandlers[E],\n ): void => {\n if (event !== \"accountsChanged\" && event !== \"networkChanged\") {\n throw new Error(`Unknown event: ${event}`);\n }\n const idx = this.subscriptions.findIndex(\n (sub) => sub.type === event && sub.handler === handler,\n );\n if (idx >= 0) {\n this.subscriptions.splice(idx, 1);\n }\n };\n\n protected emitNetworkChanged(chainId: string) {\n this.subscriptions\n .filter((sub) => sub.type === \"networkChanged\")\n .forEach((sub) => {\n (sub.handler as WalletEventHandlers[\"networkChanged\"])(chainId);\n });\n }\n\n protected emitAccountsChanged(accounts: string[]) {\n this.subscriptions\n .filter((sub) => sub.type === \"accountsChanged\")\n .forEach((sub) => {\n (sub.handler as WalletEventHandlers[\"accountsChanged\"])(accounts);\n });\n }\n\n abstract probe(): Promise<WalletAccount | undefined>;\n abstract connect(): Promise<WalletAccount | undefined>;\n abstract switchStarknetChain(chainId: string): Promise<boolean>;\n abstract addStarknetChain(\n chain: AddStarknetChainParameters,\n ): Promise<boolean>;\n}\n"],"names":["AUTH_EXTERNAL_WALLETS","EXTRA_EXTERNAL_WALLETS","EXTERNAL_WALLETS","EMBEDDED_WALLETS","ALL_AUTH_OPTIONS","IMPLEMENTED_AUTH_OPTIONS","ResponseCodes","FeeSource","ALLOWED_PROPERTIES","validatePropertyName","prop","safeObjectAccess","obj","normalizeCalls","calls","toArray","call","addAddressPadding","CallData","toSessionPolicies","policies","prev","p","target","getChecksumAddress","entrypoint","contracts","item","humanizeString","methods","toWasmPolicies","m","hash","domainHash","typedData","TypedDataRevision","typeHash","val","str","c","parseChainId","url","parts","shortString","xhr","requestBody","response","error","constants","projectName","isMobile","KEYCHAIN_URL","API_URL","NotReadyToConnect","Permission","icon","releaseStub","Mutex","bypass","release","lastPromise","resolve","mutex","BaseProvider","manifest","result","silentMode","params","event","handler","idx","sub","chainId","accounts"],"mappings":"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","x_google_ignoreList":[5]}