@reown/appkit-coinbase-react-native 0.0.0-accounts-canary.1-20251023174733
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.
- package/lib/commonjs/connectors/CoinbaseConnector.js +136 -0
- package/lib/commonjs/connectors/CoinbaseConnector.js.map +1 -0
- package/lib/commonjs/index.js +13 -0
- package/lib/commonjs/index.js.map +1 -0
- package/lib/commonjs/package.json +1 -0
- package/lib/commonjs/providers/CoinbaseProvider.js +92 -0
- package/lib/commonjs/providers/CoinbaseProvider.js.map +1 -0
- package/lib/commonjs/types.js +6 -0
- package/lib/commonjs/types.js.map +1 -0
- package/lib/commonjs/utils.js +41 -0
- package/lib/commonjs/utils.js.map +1 -0
- package/lib/module/connectors/CoinbaseConnector.js +131 -0
- package/lib/module/connectors/CoinbaseConnector.js.map +1 -0
- package/lib/module/index.js +4 -0
- package/lib/module/index.js.map +1 -0
- package/lib/module/providers/CoinbaseProvider.js +86 -0
- package/lib/module/providers/CoinbaseProvider.js.map +1 -0
- package/lib/module/types.js +4 -0
- package/lib/module/types.js.map +1 -0
- package/lib/module/utils.js +36 -0
- package/lib/module/utils.js.map +1 -0
- package/lib/typescript/connectors/CoinbaseConnector.d.ts +22 -0
- package/lib/typescript/connectors/CoinbaseConnector.d.ts.map +1 -0
- package/lib/typescript/index.d.ts +3 -0
- package/lib/typescript/index.d.ts.map +1 -0
- package/lib/typescript/providers/CoinbaseProvider.d.ts +18 -0
- package/lib/typescript/providers/CoinbaseProvider.d.ts.map +1 -0
- package/lib/typescript/types.d.ts +17 -0
- package/lib/typescript/types.d.ts.map +1 -0
- package/lib/typescript/utils.d.ts +14 -0
- package/lib/typescript/utils.d.ts.map +1 -0
- package/package.json +51 -0
- package/src/connectors/CoinbaseConnector.ts +171 -0
- package/src/index.ts +2 -0
- package/src/providers/CoinbaseProvider.ts +106 -0
- package/src/types.ts +24 -0
- package/src/utils.ts +48 -0
|
@@ -0,0 +1,136 @@
|
|
|
1
|
+
"use strict";
|
|
2
|
+
|
|
3
|
+
Object.defineProperty(exports, "__esModule", {
|
|
4
|
+
value: true
|
|
5
|
+
});
|
|
6
|
+
exports.CoinbaseConnector = void 0;
|
|
7
|
+
var _appkitCommonReactNative = require("@reown/appkit-common-react-native");
|
|
8
|
+
var _utils = require("../utils");
|
|
9
|
+
var _CoinbaseProvider = require("../providers/CoinbaseProvider");
|
|
10
|
+
const SESSION_KEY = '@appkit/coinbase-connector/session';
|
|
11
|
+
class CoinbaseConnector extends _appkitCommonReactNative.WalletConnector {
|
|
12
|
+
static SUPPORTED_NAMESPACE = 'eip155';
|
|
13
|
+
constructor(config) {
|
|
14
|
+
super({
|
|
15
|
+
type: 'coinbase'
|
|
16
|
+
});
|
|
17
|
+
this.config = config ?? {};
|
|
18
|
+
}
|
|
19
|
+
async init(ops) {
|
|
20
|
+
super.init(ops);
|
|
21
|
+
const redirect = ops.metadata.redirect?.universal ?? ops.metadata.redirect?.native;
|
|
22
|
+
if (!redirect) {
|
|
23
|
+
throw new Error('CoinbaseConnector: Redirect link not found in metadata');
|
|
24
|
+
}
|
|
25
|
+
this.provider = new _CoinbaseProvider.CoinbaseProvider({
|
|
26
|
+
redirect,
|
|
27
|
+
// use config storage, as it needs to be mmkv-compatible
|
|
28
|
+
storage: this.config.storage,
|
|
29
|
+
jsonRpcUrl: this.config.jsonRpcUrl
|
|
30
|
+
});
|
|
31
|
+
await this.restoreSession();
|
|
32
|
+
}
|
|
33
|
+
async connect(opts) {
|
|
34
|
+
const accounts = await this.getProvider().connect();
|
|
35
|
+
if (opts?.defaultNetwork && opts.defaultNetwork.chainNamespace === CoinbaseConnector.SUPPORTED_NAMESPACE) {
|
|
36
|
+
await this.switchNetwork(opts.defaultNetwork);
|
|
37
|
+
}
|
|
38
|
+
const namespaces = (0, _utils.getCoinbaseNamespace)(opts?.namespaces, accounts);
|
|
39
|
+
this.namespaces = namespaces;
|
|
40
|
+
this.saveSession(namespaces);
|
|
41
|
+
return this.namespaces;
|
|
42
|
+
}
|
|
43
|
+
async disconnect() {
|
|
44
|
+
await super.disconnect();
|
|
45
|
+
this.deleteSession();
|
|
46
|
+
}
|
|
47
|
+
getProvider() {
|
|
48
|
+
if (!this.provider) {
|
|
49
|
+
throw new Error('CoinbaseConnector: Provider not initialized. Call init() first.');
|
|
50
|
+
}
|
|
51
|
+
return this.provider;
|
|
52
|
+
}
|
|
53
|
+
getNamespaces() {
|
|
54
|
+
if (!this.namespaces) {
|
|
55
|
+
throw new Error('CoinbaseConnector: Namespaces not initialized');
|
|
56
|
+
}
|
|
57
|
+
return this.namespaces;
|
|
58
|
+
}
|
|
59
|
+
getChainId() {
|
|
60
|
+
const hexChainId = this.getProvider().getChainId();
|
|
61
|
+
const chainId = _appkitCommonReactNative.StringUtil.hexToString(hexChainId);
|
|
62
|
+
return `${CoinbaseConnector.SUPPORTED_NAMESPACE}:${chainId}`;
|
|
63
|
+
}
|
|
64
|
+
getWalletInfo() {
|
|
65
|
+
return {
|
|
66
|
+
name: 'Coinbase Wallet',
|
|
67
|
+
type: 'external'
|
|
68
|
+
};
|
|
69
|
+
}
|
|
70
|
+
getProperties() {
|
|
71
|
+
return undefined;
|
|
72
|
+
}
|
|
73
|
+
async switchNetwork(network) {
|
|
74
|
+
const provider = this.getProvider();
|
|
75
|
+
const chainId_ = _appkitCommonReactNative.NumberUtil.convertNumericToHexString(network.id);
|
|
76
|
+
try {
|
|
77
|
+
await provider.request({
|
|
78
|
+
method: 'wallet_switchEthereumChain',
|
|
79
|
+
params: [{
|
|
80
|
+
chainId: chainId_
|
|
81
|
+
}]
|
|
82
|
+
});
|
|
83
|
+
} catch (error) {
|
|
84
|
+
// Indicates chain is not added to provider
|
|
85
|
+
if (error?.code === 4902) {
|
|
86
|
+
try {
|
|
87
|
+
await provider.request({
|
|
88
|
+
method: 'wallet_addEthereumChain',
|
|
89
|
+
params: [{
|
|
90
|
+
chainId: chainId_,
|
|
91
|
+
chainName: network.name,
|
|
92
|
+
nativeCurrency: network.nativeCurrency,
|
|
93
|
+
rpcUrls: [network.rpcUrls.default?.http[0] ?? ''],
|
|
94
|
+
blockExplorerUrls: [network.blockExplorers?.default.url]
|
|
95
|
+
}]
|
|
96
|
+
});
|
|
97
|
+
} catch (e) {
|
|
98
|
+
console.warn('CoinbaseConnector: switchNetwork error', e);
|
|
99
|
+
throw e;
|
|
100
|
+
}
|
|
101
|
+
}
|
|
102
|
+
console.warn('CoinbaseConnector: switchNetwork error', error);
|
|
103
|
+
throw error;
|
|
104
|
+
}
|
|
105
|
+
}
|
|
106
|
+
deleteSession() {
|
|
107
|
+
const storage = this.getStorage();
|
|
108
|
+
storage.removeItem(SESSION_KEY);
|
|
109
|
+
}
|
|
110
|
+
saveSession(namespaces) {
|
|
111
|
+
const storage = this.getStorage();
|
|
112
|
+
storage.setItem(SESSION_KEY, {
|
|
113
|
+
namespaces
|
|
114
|
+
});
|
|
115
|
+
}
|
|
116
|
+
async restoreSession() {
|
|
117
|
+
const storage = this.getStorage();
|
|
118
|
+
const session = await storage.getItem(SESSION_KEY);
|
|
119
|
+
if (!session) {
|
|
120
|
+
return false;
|
|
121
|
+
}
|
|
122
|
+
const {
|
|
123
|
+
namespaces
|
|
124
|
+
} = session;
|
|
125
|
+
this.namespaces = namespaces;
|
|
126
|
+
return true;
|
|
127
|
+
}
|
|
128
|
+
getStorage() {
|
|
129
|
+
if (!this.storage) {
|
|
130
|
+
throw new Error('CoinbaseConnector: Storage not initialized');
|
|
131
|
+
}
|
|
132
|
+
return this.storage;
|
|
133
|
+
}
|
|
134
|
+
}
|
|
135
|
+
exports.CoinbaseConnector = CoinbaseConnector;
|
|
136
|
+
//# sourceMappingURL=CoinbaseConnector.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"names":["_appkitCommonReactNative","require","_utils","_CoinbaseProvider","SESSION_KEY","CoinbaseConnector","WalletConnector","SUPPORTED_NAMESPACE","constructor","config","type","init","ops","redirect","metadata","universal","native","Error","provider","CoinbaseProvider","storage","jsonRpcUrl","restoreSession","connect","opts","accounts","getProvider","defaultNetwork","chainNamespace","switchNetwork","namespaces","getCoinbaseNamespace","saveSession","disconnect","deleteSession","getNamespaces","getChainId","hexChainId","chainId","StringUtil","hexToString","getWalletInfo","name","getProperties","undefined","network","chainId_","NumberUtil","convertNumericToHexString","id","request","method","params","error","code","chainName","nativeCurrency","rpcUrls","default","http","blockExplorerUrls","blockExplorers","url","e","console","warn","getStorage","removeItem","setItem","session","getItem","exports"],"sourceRoot":"../../../src","sources":["connectors/CoinbaseConnector.ts"],"mappings":"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","ignoreList":[]}
|
|
@@ -0,0 +1,13 @@
|
|
|
1
|
+
"use strict";
|
|
2
|
+
|
|
3
|
+
Object.defineProperty(exports, "__esModule", {
|
|
4
|
+
value: true
|
|
5
|
+
});
|
|
6
|
+
Object.defineProperty(exports, "CoinbaseConnector", {
|
|
7
|
+
enumerable: true,
|
|
8
|
+
get: function () {
|
|
9
|
+
return _CoinbaseConnector.CoinbaseConnector;
|
|
10
|
+
}
|
|
11
|
+
});
|
|
12
|
+
var _CoinbaseConnector = require("./connectors/CoinbaseConnector");
|
|
13
|
+
//# sourceMappingURL=index.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"names":["_CoinbaseConnector","require"],"sourceRoot":"../../src","sources":["index.ts"],"mappings":";;;;;;;;;;;AAAA,IAAAA,kBAAA,GAAAC,OAAA","ignoreList":[]}
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"type":"commonjs"}
|
|
@@ -0,0 +1,92 @@
|
|
|
1
|
+
"use strict";
|
|
2
|
+
|
|
3
|
+
Object.defineProperty(exports, "__esModule", {
|
|
4
|
+
value: true
|
|
5
|
+
});
|
|
6
|
+
exports.CoinbaseProvider = void 0;
|
|
7
|
+
var _events = _interopRequireDefault(require("events"));
|
|
8
|
+
var _appkitCommonReactNative = require("@reown/appkit-common-react-native");
|
|
9
|
+
var _walletMobileSdk = require("@coinbase/wallet-mobile-sdk");
|
|
10
|
+
function _interopRequireDefault(e) { return e && e.__esModule ? e : { default: e }; }
|
|
11
|
+
class CoinbaseProvider extends _events.default {
|
|
12
|
+
chainChangedListeners = new Map();
|
|
13
|
+
constructor(config) {
|
|
14
|
+
super();
|
|
15
|
+
this.config = config;
|
|
16
|
+
(0, _walletMobileSdk.configure)({
|
|
17
|
+
hostURL: new URL('https://wallet.coinbase.com/wsegue'),
|
|
18
|
+
callbackURL: new URL(this.config.redirect),
|
|
19
|
+
// App Universal Link
|
|
20
|
+
hostPackageName: 'org.toshi'
|
|
21
|
+
});
|
|
22
|
+
this.provider = new _walletMobileSdk.WalletMobileSDKEVMProvider({
|
|
23
|
+
...this.config,
|
|
24
|
+
jsonRpcUrl: this.config.jsonRpcUrl,
|
|
25
|
+
storage: this.config.storage
|
|
26
|
+
});
|
|
27
|
+
}
|
|
28
|
+
async connect() {
|
|
29
|
+
try {
|
|
30
|
+
let accounts = [];
|
|
31
|
+
const isConnected = this.provider.connected;
|
|
32
|
+
if (!isConnected) {
|
|
33
|
+
accounts = await this.provider.request({
|
|
34
|
+
method: 'eth_requestAccounts',
|
|
35
|
+
params: []
|
|
36
|
+
});
|
|
37
|
+
} else {
|
|
38
|
+
accounts = this.provider.selectedAddress ? [this.provider.selectedAddress] : [];
|
|
39
|
+
}
|
|
40
|
+
return accounts;
|
|
41
|
+
} catch (error) {
|
|
42
|
+
console.warn('CoinbaseProvider: connect error', error);
|
|
43
|
+
throw error;
|
|
44
|
+
}
|
|
45
|
+
}
|
|
46
|
+
async disconnect() {
|
|
47
|
+
this.provider.disconnect();
|
|
48
|
+
return Promise.resolve();
|
|
49
|
+
}
|
|
50
|
+
request(args) {
|
|
51
|
+
return this.provider.request(args);
|
|
52
|
+
}
|
|
53
|
+
getChainId() {
|
|
54
|
+
return this.provider.chainId;
|
|
55
|
+
}
|
|
56
|
+
onChainChanged(hexChainId) {
|
|
57
|
+
const chainId = _appkitCommonReactNative.StringUtil.hexToString(hexChainId);
|
|
58
|
+
this.emit('chainChanged', {
|
|
59
|
+
chainId
|
|
60
|
+
});
|
|
61
|
+
}
|
|
62
|
+
on(event, listener) {
|
|
63
|
+
if (event === 'chainChanged') {
|
|
64
|
+
// Create middleware that formats the chain ID before calling the original listener
|
|
65
|
+
const chainChangedMiddleware = hexChainId => {
|
|
66
|
+
const chainId = _appkitCommonReactNative.StringUtil.hexToString(hexChainId);
|
|
67
|
+
listener(chainId);
|
|
68
|
+
};
|
|
69
|
+
|
|
70
|
+
// Store the mapping between original listener and middleware
|
|
71
|
+
this.chainChangedListeners.set(listener, chainChangedMiddleware);
|
|
72
|
+
return this.provider.on('chainChanged', chainChangedMiddleware);
|
|
73
|
+
}
|
|
74
|
+
return this.provider.on(event, listener);
|
|
75
|
+
}
|
|
76
|
+
off(event, listener) {
|
|
77
|
+
if (event === 'chainChanged') {
|
|
78
|
+
// Get the middleware wrapper for this listener
|
|
79
|
+
const middleware = this.chainChangedListeners.get(listener);
|
|
80
|
+
if (middleware) {
|
|
81
|
+
// Remove the middleware from the provider
|
|
82
|
+
this.provider.off('chainChanged', middleware);
|
|
83
|
+
// Remove the mapping
|
|
84
|
+
this.chainChangedListeners.delete(listener);
|
|
85
|
+
return this;
|
|
86
|
+
}
|
|
87
|
+
}
|
|
88
|
+
return this.provider.off(event, listener);
|
|
89
|
+
}
|
|
90
|
+
}
|
|
91
|
+
exports.CoinbaseProvider = CoinbaseProvider;
|
|
92
|
+
//# sourceMappingURL=CoinbaseProvider.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"names":["_events","_interopRequireDefault","require","_appkitCommonReactNative","_walletMobileSdk","e","__esModule","default","CoinbaseProvider","EventEmitter","chainChangedListeners","Map","constructor","config","configure","hostURL","URL","callbackURL","redirect","hostPackageName","provider","WalletMobileSDKEVMProvider","jsonRpcUrl","storage","connect","accounts","isConnected","connected","request","method","params","selectedAddress","error","console","warn","disconnect","Promise","resolve","args","getChainId","chainId","onChainChanged","hexChainId","StringUtil","hexToString","emit","on","event","listener","chainChangedMiddleware","set","off","middleware","get","delete","exports"],"sourceRoot":"../../../src","sources":["providers/CoinbaseProvider.ts"],"mappings":"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","ignoreList":[]}
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"names":[],"sourceRoot":"../../src","sources":["types.ts"],"mappings":"","ignoreList":[]}
|
|
@@ -0,0 +1,41 @@
|
|
|
1
|
+
"use strict";
|
|
2
|
+
|
|
3
|
+
Object.defineProperty(exports, "__esModule", {
|
|
4
|
+
value: true
|
|
5
|
+
});
|
|
6
|
+
exports.COINBASE_METHODS = void 0;
|
|
7
|
+
exports.getCoinbaseNamespace = getCoinbaseNamespace;
|
|
8
|
+
const COINBASE_METHODS = exports.COINBASE_METHODS = {
|
|
9
|
+
REQUEST_ACCOUNTS: 'eth_requestAccounts',
|
|
10
|
+
SIGN_TRANSACTION: 'eth_signTransaction',
|
|
11
|
+
SEND_TRANSACTION: 'eth_sendTransaction',
|
|
12
|
+
SIGN_MESSAGE: 'personal_sign',
|
|
13
|
+
SIGN_TYPED_DATA_V3: 'eth_signTypedData_v3',
|
|
14
|
+
SIGN_TYPED_DATA_V4: 'eth_signTypedData_v4',
|
|
15
|
+
SWITCH_CHAIN: 'wallet_switchEthereumChain',
|
|
16
|
+
ADD_ETHEREUM_CHAIN: 'wallet_addEthereumChain',
|
|
17
|
+
WATCH_ASSET: 'wallet_watchAsset'
|
|
18
|
+
};
|
|
19
|
+
function getCoinbaseNamespace(namespaces, accounts) {
|
|
20
|
+
if (!namespaces || !accounts) {
|
|
21
|
+
throw new Error('CoinbaseConnector: Namespaces or accounts not found');
|
|
22
|
+
}
|
|
23
|
+
const namespace = namespaces['eip155'];
|
|
24
|
+
if (!namespace) {
|
|
25
|
+
throw new Error('CoinbaseConnector: Namespace not found');
|
|
26
|
+
}
|
|
27
|
+
let caipAddresses = [];
|
|
28
|
+
for (const account of accounts) {
|
|
29
|
+
namespace.chains?.forEach(chain => {
|
|
30
|
+
caipAddresses.push(`${chain}:${account}`);
|
|
31
|
+
});
|
|
32
|
+
}
|
|
33
|
+
return {
|
|
34
|
+
['eip155']: {
|
|
35
|
+
...namespace,
|
|
36
|
+
methods: Object.values(COINBASE_METHODS),
|
|
37
|
+
accounts: caipAddresses
|
|
38
|
+
}
|
|
39
|
+
};
|
|
40
|
+
}
|
|
41
|
+
//# sourceMappingURL=utils.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"names":["COINBASE_METHODS","exports","REQUEST_ACCOUNTS","SIGN_TRANSACTION","SEND_TRANSACTION","SIGN_MESSAGE","SIGN_TYPED_DATA_V3","SIGN_TYPED_DATA_V4","SWITCH_CHAIN","ADD_ETHEREUM_CHAIN","WATCH_ASSET","getCoinbaseNamespace","namespaces","accounts","Error","namespace","caipAddresses","account","chains","forEach","chain","push","methods","Object","values"],"sourceRoot":"../../src","sources":["utils.ts"],"mappings":";;;;;;;AAMO,MAAMA,gBAAgB,GAAAC,OAAA,CAAAD,gBAAA,GAAG;EAC9BE,gBAAgB,EAAE,qBAAqB;EACvCC,gBAAgB,EAAE,qBAAqB;EACvCC,gBAAgB,EAAE,qBAAqB;EACvCC,YAAY,EAAE,eAAe;EAC7BC,kBAAkB,EAAE,sBAAsB;EAC1CC,kBAAkB,EAAE,sBAAsB;EAC1CC,YAAY,EAAE,4BAA4B;EAC1CC,kBAAkB,EAAE,yBAAyB;EAC7CC,WAAW,EAAE;AACf,CAAU;AAEH,SAASC,oBAAoBA,CAClCC,UAA+B,EAC/BC,QAAmB,EACP;EACZ,IAAI,CAACD,UAAU,IAAI,CAACC,QAAQ,EAAE;IAC5B,MAAM,IAAIC,KAAK,CAAC,qDAAqD,CAAC;EACxE;EAEA,MAAMC,SAAS,GAAGH,UAAU,CAAC,QAAQ,CAAC;EAEtC,IAAI,CAACG,SAAS,EAAE;IACd,MAAM,IAAID,KAAK,CAAC,wCAAwC,CAAC;EAC3D;EAEA,IAAIE,aAA4B,GAAG,EAAE;EAErC,KAAK,MAAMC,OAAO,IAAIJ,QAAQ,EAAE;IAC9BE,SAAS,CAACG,MAAM,EAAEC,OAAO,CAACC,KAAK,IAAI;MACjCJ,aAAa,CAACK,IAAI,CAAC,GAAGD,KAAK,IAAIH,OAAO,EAAE,CAAC;IAC3C,CAAC,CAAC;EACJ;EAEA,OAAO;IACL,CAAC,QAAQ,GAAG;MACV,GAAGF,SAAS;MACZO,OAAO,EAAEC,MAAM,CAACC,MAAM,CAACxB,gBAAgB,CAAC;MACxCa,QAAQ,EAAEG;IACZ;EACF,CAAC;AACH","ignoreList":[]}
|
|
@@ -0,0 +1,131 @@
|
|
|
1
|
+
"use strict";
|
|
2
|
+
|
|
3
|
+
import { WalletConnector, NumberUtil, StringUtil } from '@reown/appkit-common-react-native';
|
|
4
|
+
import { getCoinbaseNamespace } from '../utils';
|
|
5
|
+
import { CoinbaseProvider } from '../providers/CoinbaseProvider';
|
|
6
|
+
const SESSION_KEY = '@appkit/coinbase-connector/session';
|
|
7
|
+
export class CoinbaseConnector extends WalletConnector {
|
|
8
|
+
static SUPPORTED_NAMESPACE = 'eip155';
|
|
9
|
+
constructor(config) {
|
|
10
|
+
super({
|
|
11
|
+
type: 'coinbase'
|
|
12
|
+
});
|
|
13
|
+
this.config = config ?? {};
|
|
14
|
+
}
|
|
15
|
+
async init(ops) {
|
|
16
|
+
super.init(ops);
|
|
17
|
+
const redirect = ops.metadata.redirect?.universal ?? ops.metadata.redirect?.native;
|
|
18
|
+
if (!redirect) {
|
|
19
|
+
throw new Error('CoinbaseConnector: Redirect link not found in metadata');
|
|
20
|
+
}
|
|
21
|
+
this.provider = new CoinbaseProvider({
|
|
22
|
+
redirect,
|
|
23
|
+
// use config storage, as it needs to be mmkv-compatible
|
|
24
|
+
storage: this.config.storage,
|
|
25
|
+
jsonRpcUrl: this.config.jsonRpcUrl
|
|
26
|
+
});
|
|
27
|
+
await this.restoreSession();
|
|
28
|
+
}
|
|
29
|
+
async connect(opts) {
|
|
30
|
+
const accounts = await this.getProvider().connect();
|
|
31
|
+
if (opts?.defaultNetwork && opts.defaultNetwork.chainNamespace === CoinbaseConnector.SUPPORTED_NAMESPACE) {
|
|
32
|
+
await this.switchNetwork(opts.defaultNetwork);
|
|
33
|
+
}
|
|
34
|
+
const namespaces = getCoinbaseNamespace(opts?.namespaces, accounts);
|
|
35
|
+
this.namespaces = namespaces;
|
|
36
|
+
this.saveSession(namespaces);
|
|
37
|
+
return this.namespaces;
|
|
38
|
+
}
|
|
39
|
+
async disconnect() {
|
|
40
|
+
await super.disconnect();
|
|
41
|
+
this.deleteSession();
|
|
42
|
+
}
|
|
43
|
+
getProvider() {
|
|
44
|
+
if (!this.provider) {
|
|
45
|
+
throw new Error('CoinbaseConnector: Provider not initialized. Call init() first.');
|
|
46
|
+
}
|
|
47
|
+
return this.provider;
|
|
48
|
+
}
|
|
49
|
+
getNamespaces() {
|
|
50
|
+
if (!this.namespaces) {
|
|
51
|
+
throw new Error('CoinbaseConnector: Namespaces not initialized');
|
|
52
|
+
}
|
|
53
|
+
return this.namespaces;
|
|
54
|
+
}
|
|
55
|
+
getChainId() {
|
|
56
|
+
const hexChainId = this.getProvider().getChainId();
|
|
57
|
+
const chainId = StringUtil.hexToString(hexChainId);
|
|
58
|
+
return `${CoinbaseConnector.SUPPORTED_NAMESPACE}:${chainId}`;
|
|
59
|
+
}
|
|
60
|
+
getWalletInfo() {
|
|
61
|
+
return {
|
|
62
|
+
name: 'Coinbase Wallet',
|
|
63
|
+
type: 'external'
|
|
64
|
+
};
|
|
65
|
+
}
|
|
66
|
+
getProperties() {
|
|
67
|
+
return undefined;
|
|
68
|
+
}
|
|
69
|
+
async switchNetwork(network) {
|
|
70
|
+
const provider = this.getProvider();
|
|
71
|
+
const chainId_ = NumberUtil.convertNumericToHexString(network.id);
|
|
72
|
+
try {
|
|
73
|
+
await provider.request({
|
|
74
|
+
method: 'wallet_switchEthereumChain',
|
|
75
|
+
params: [{
|
|
76
|
+
chainId: chainId_
|
|
77
|
+
}]
|
|
78
|
+
});
|
|
79
|
+
} catch (error) {
|
|
80
|
+
// Indicates chain is not added to provider
|
|
81
|
+
if (error?.code === 4902) {
|
|
82
|
+
try {
|
|
83
|
+
await provider.request({
|
|
84
|
+
method: 'wallet_addEthereumChain',
|
|
85
|
+
params: [{
|
|
86
|
+
chainId: chainId_,
|
|
87
|
+
chainName: network.name,
|
|
88
|
+
nativeCurrency: network.nativeCurrency,
|
|
89
|
+
rpcUrls: [network.rpcUrls.default?.http[0] ?? ''],
|
|
90
|
+
blockExplorerUrls: [network.blockExplorers?.default.url]
|
|
91
|
+
}]
|
|
92
|
+
});
|
|
93
|
+
} catch (e) {
|
|
94
|
+
console.warn('CoinbaseConnector: switchNetwork error', e);
|
|
95
|
+
throw e;
|
|
96
|
+
}
|
|
97
|
+
}
|
|
98
|
+
console.warn('CoinbaseConnector: switchNetwork error', error);
|
|
99
|
+
throw error;
|
|
100
|
+
}
|
|
101
|
+
}
|
|
102
|
+
deleteSession() {
|
|
103
|
+
const storage = this.getStorage();
|
|
104
|
+
storage.removeItem(SESSION_KEY);
|
|
105
|
+
}
|
|
106
|
+
saveSession(namespaces) {
|
|
107
|
+
const storage = this.getStorage();
|
|
108
|
+
storage.setItem(SESSION_KEY, {
|
|
109
|
+
namespaces
|
|
110
|
+
});
|
|
111
|
+
}
|
|
112
|
+
async restoreSession() {
|
|
113
|
+
const storage = this.getStorage();
|
|
114
|
+
const session = await storage.getItem(SESSION_KEY);
|
|
115
|
+
if (!session) {
|
|
116
|
+
return false;
|
|
117
|
+
}
|
|
118
|
+
const {
|
|
119
|
+
namespaces
|
|
120
|
+
} = session;
|
|
121
|
+
this.namespaces = namespaces;
|
|
122
|
+
return true;
|
|
123
|
+
}
|
|
124
|
+
getStorage() {
|
|
125
|
+
if (!this.storage) {
|
|
126
|
+
throw new Error('CoinbaseConnector: Storage not initialized');
|
|
127
|
+
}
|
|
128
|
+
return this.storage;
|
|
129
|
+
}
|
|
130
|
+
}
|
|
131
|
+
//# sourceMappingURL=CoinbaseConnector.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"names":["WalletConnector","NumberUtil","StringUtil","getCoinbaseNamespace","CoinbaseProvider","SESSION_KEY","CoinbaseConnector","SUPPORTED_NAMESPACE","constructor","config","type","init","ops","redirect","metadata","universal","native","Error","provider","storage","jsonRpcUrl","restoreSession","connect","opts","accounts","getProvider","defaultNetwork","chainNamespace","switchNetwork","namespaces","saveSession","disconnect","deleteSession","getNamespaces","getChainId","hexChainId","chainId","hexToString","getWalletInfo","name","getProperties","undefined","network","chainId_","convertNumericToHexString","id","request","method","params","error","code","chainName","nativeCurrency","rpcUrls","default","http","blockExplorerUrls","blockExplorers","url","e","console","warn","getStorage","removeItem","setItem","session","getItem"],"sourceRoot":"../../../src","sources":["connectors/CoinbaseConnector.ts"],"mappings":";;AAAA,SACEA,eAAe,EAUfC,UAAU,EACVC,UAAU,QACL,mCAAmC;AAC1C,SAASC,oBAAoB,QAAQ,UAAU;AAC/C,SAASC,gBAAgB,QAAQ,+BAA+B;AAGhE,MAAMC,WAAW,GAAG,oCAAoC;AAExD,OAAO,MAAMC,iBAAiB,SAASN,eAAe,CAAC;EACrD,OAAwBO,mBAAmB,GAAmB,QAAQ;EAGtEC,WAAWA,CAACC,MAAgC,EAAE;IAC5C,KAAK,CAAC;MAAEC,IAAI,EAAE;IAAW,CAAC,CAAC;IAC3B,IAAI,CAACD,MAAM,GAAGA,MAAM,IAAI,CAAC,CAAC;EAC5B;EAEA,MAAeE,IAAIA,CAACC,GAAyB,EAAE;IAC7C,KAAK,CAACD,IAAI,CAACC,GAAG,CAAC;IAEf,MAAMC,QAAQ,GAAGD,GAAG,CAACE,QAAQ,CAACD,QAAQ,EAAEE,SAAS,IAAIH,GAAG,CAACE,QAAQ,CAACD,QAAQ,EAAEG,MAAM;IAClF,IAAI,CAACH,QAAQ,EAAE;MACb,MAAM,IAAII,KAAK,CAAC,wDAAwD,CAAC;IAC3E;IAEA,IAAI,CAACC,QAAQ,GAAG,IAAId,gBAAgB,CAAC;MACnCS,QAAQ;MACR;MACAM,OAAO,EAAE,IAAI,CAACV,MAAM,CAACU,OAAO;MAC5BC,UAAU,EAAE,IAAI,CAACX,MAAM,CAACW;IAC1B,CAAC,CAAC;IAEF,MAAM,IAAI,CAACC,cAAc,CAAC,CAAC;EAC7B;EAEA,MAAeC,OAAOA,CACpBC,IAA4D,EAC3B;IACjC,MAAMC,QAAQ,GAAG,MAAM,IAAI,CAACC,WAAW,CAAC,CAAC,CAACH,OAAO,CAAC,CAAC;IAEnD,IACEC,IAAI,EAAEG,cAAc,IACpBH,IAAI,CAACG,cAAc,CAACC,cAAc,KAAKrB,iBAAiB,CAACC,mBAAmB,EAC5E;MACA,MAAM,IAAI,CAACqB,aAAa,CAACL,IAAI,CAACG,cAAc,CAAC;IAC/C;IAEA,MAAMG,UAAU,GAAG1B,oBAAoB,CAACoB,IAAI,EAAEM,UAAU,EAAEL,QAAQ,CAAC;IACnE,IAAI,CAACK,UAAU,GAAGA,UAAU;IAC5B,IAAI,CAACC,WAAW,CAACD,UAAU,CAAC;IAE5B,OAAO,IAAI,CAACA,UAAU;EACxB;EAEA,MAAeE,UAAUA,CAAA,EAAkB;IACzC,MAAM,KAAK,CAACA,UAAU,CAAC,CAAC;IACxB,IAAI,CAACC,aAAa,CAAC,CAAC;EACtB;EAESP,WAAWA,CAAA,EAAqB;IACvC,IAAI,CAAC,IAAI,CAACP,QAAQ,EAAE;MAClB,MAAM,IAAID,KAAK,CAAC,iEAAiE,CAAC;IACpF;IAEA,OAAO,IAAI,CAACC,QAAQ;EACtB;EAESe,aAAaA,CAAA,EAAe;IACnC,IAAI,CAAC,IAAI,CAACJ,UAAU,EAAE;MACpB,MAAM,IAAIZ,KAAK,CAAC,+CAA+C,CAAC;IAClE;IAEA,OAAO,IAAI,CAACY,UAAU;EACxB;EAESK,UAAUA,CAAA,EAA8B;IAC/C,MAAMC,UAAU,GAAG,IAAI,CAACV,WAAW,CAAC,CAAC,CAACS,UAAU,CAAC,CAAC;IAClD,MAAME,OAAO,GAAGlC,UAAU,CAACmC,WAAW,CAACF,UAAU,CAAC;IAElD,OAAO,GAAG7B,iBAAiB,CAACC,mBAAmB,IAAI6B,OAAO,EAAE;EAC9D;EAESE,aAAaA,CAAA,EAA2B;IAC/C,OAAO;MACLC,IAAI,EAAE,iBAAiB;MACvB7B,IAAI,EAAE;IACR,CAAC;EACH;EAES8B,aAAaA,CAAA,EAAqC;IACzD,OAAOC,SAAS;EAClB;EAEA,MAAeb,aAAaA,CAACc,OAAsB,EAAiB;IAClE,MAAMxB,QAAQ,GAAG,IAAI,CAACO,WAAW,CAAC,CAAC;IACnC,MAAMkB,QAAQ,GAAG1C,UAAU,CAAC2C,yBAAyB,CAACF,OAAO,CAACG,EAAE,CAAC;IAEjE,IAAI;MACF,MAAM3B,QAAQ,CAAC4B,OAAO,CAAC;QACrBC,MAAM,EAAE,4BAA4B;QACpCC,MAAM,EAAE,CAAC;UAAEZ,OAAO,EAAEO;QAAS,CAAC;MAChC,CAAC,CAAC;IACJ,CAAC,CAAC,OAAOM,KAAU,EAAE;MACnB;MACA,IAAIA,KAAK,EAAEC,IAAI,KAAK,IAAI,EAAE;QACxB,IAAI;UACF,MAAMhC,QAAQ,CAAC4B,OAAO,CAAC;YACrBC,MAAM,EAAE,yBAAyB;YACjCC,MAAM,EAAE,CACN;cACEZ,OAAO,EAAEO,QAAQ;cACjBQ,SAAS,EAAET,OAAO,CAACH,IAAI;cACvBa,cAAc,EAAEV,OAAO,CAACU,cAAc;cACtCC,OAAO,EAAE,CAACX,OAAO,CAACW,OAAO,CAACC,OAAO,EAAEC,IAAI,CAAC,CAAC,CAAC,IAAI,EAAE,CAAC;cACjDC,iBAAiB,EAAE,CAACd,OAAO,CAACe,cAAc,EAAEH,OAAO,CAACI,GAAG;YACzD,CAAC;UAEL,CAAC,CAAC;QACJ,CAAC,CAAC,OAAOC,CAAC,EAAE;UACVC,OAAO,CAACC,IAAI,CAAC,wCAAwC,EAAEF,CAAC,CAAC;UACzD,MAAMA,CAAC;QACT;MACF;MACAC,OAAO,CAACC,IAAI,CAAC,wCAAwC,EAAEZ,KAAK,CAAC;MAC7D,MAAMA,KAAK;IACb;EACF;EAEQjB,aAAaA,CAAA,EAAS;IAC5B,MAAMb,OAAO,GAAG,IAAI,CAAC2C,UAAU,CAAC,CAAC;IACjC3C,OAAO,CAAC4C,UAAU,CAAC1D,WAAW,CAAC;EACjC;EAEQyB,WAAWA,CAACD,UAAsB,EAAQ;IAChD,MAAMV,OAAO,GAAG,IAAI,CAAC2C,UAAU,CAAC,CAAC;IACjC3C,OAAO,CAAC6C,OAAO,CAAkB3D,WAAW,EAAE;MAAEwB;IAAW,CAAC,CAAC;EAC/D;EAEA,MAAeR,cAAcA,CAAA,EAAqB;IAChD,MAAMF,OAAO,GAAG,IAAI,CAAC2C,UAAU,CAAC,CAAC;IACjC,MAAMG,OAAO,GAAG,MAAM9C,OAAO,CAAC+C,OAAO,CAAkB7D,WAAW,CAAC;IACnE,IAAI,CAAC4D,OAAO,EAAE;MACZ,OAAO,KAAK;IACd;IAEA,MAAM;MAAEpC;IAAW,CAAC,GAAGoC,OAAO;IAC9B,IAAI,CAACpC,UAAU,GAAGA,UAAU;IAE5B,OAAO,IAAI;EACb;EAEQiC,UAAUA,CAAA,EAAY;IAC5B,IAAI,CAAC,IAAI,CAAC3C,OAAO,EAAE;MACjB,MAAM,IAAIF,KAAK,CAAC,4CAA4C,CAAC;IAC/D;IAEA,OAAO,IAAI,CAACE,OAAO;EACrB;AACF","ignoreList":[]}
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"names":["CoinbaseConnector"],"sourceRoot":"../../src","sources":["index.ts"],"mappings":";;AAAA,SAASA,iBAAiB,QAAQ,gCAAgC","ignoreList":[]}
|
|
@@ -0,0 +1,86 @@
|
|
|
1
|
+
"use strict";
|
|
2
|
+
|
|
3
|
+
import EventEmitter from 'events';
|
|
4
|
+
import { StringUtil } from '@reown/appkit-common-react-native';
|
|
5
|
+
import { configure, WalletMobileSDKEVMProvider } from '@coinbase/wallet-mobile-sdk';
|
|
6
|
+
export class CoinbaseProvider extends EventEmitter {
|
|
7
|
+
chainChangedListeners = new Map();
|
|
8
|
+
constructor(config) {
|
|
9
|
+
super();
|
|
10
|
+
this.config = config;
|
|
11
|
+
configure({
|
|
12
|
+
hostURL: new URL('https://wallet.coinbase.com/wsegue'),
|
|
13
|
+
callbackURL: new URL(this.config.redirect),
|
|
14
|
+
// App Universal Link
|
|
15
|
+
hostPackageName: 'org.toshi'
|
|
16
|
+
});
|
|
17
|
+
this.provider = new WalletMobileSDKEVMProvider({
|
|
18
|
+
...this.config,
|
|
19
|
+
jsonRpcUrl: this.config.jsonRpcUrl,
|
|
20
|
+
storage: this.config.storage
|
|
21
|
+
});
|
|
22
|
+
}
|
|
23
|
+
async connect() {
|
|
24
|
+
try {
|
|
25
|
+
let accounts = [];
|
|
26
|
+
const isConnected = this.provider.connected;
|
|
27
|
+
if (!isConnected) {
|
|
28
|
+
accounts = await this.provider.request({
|
|
29
|
+
method: 'eth_requestAccounts',
|
|
30
|
+
params: []
|
|
31
|
+
});
|
|
32
|
+
} else {
|
|
33
|
+
accounts = this.provider.selectedAddress ? [this.provider.selectedAddress] : [];
|
|
34
|
+
}
|
|
35
|
+
return accounts;
|
|
36
|
+
} catch (error) {
|
|
37
|
+
console.warn('CoinbaseProvider: connect error', error);
|
|
38
|
+
throw error;
|
|
39
|
+
}
|
|
40
|
+
}
|
|
41
|
+
async disconnect() {
|
|
42
|
+
this.provider.disconnect();
|
|
43
|
+
return Promise.resolve();
|
|
44
|
+
}
|
|
45
|
+
request(args) {
|
|
46
|
+
return this.provider.request(args);
|
|
47
|
+
}
|
|
48
|
+
getChainId() {
|
|
49
|
+
return this.provider.chainId;
|
|
50
|
+
}
|
|
51
|
+
onChainChanged(hexChainId) {
|
|
52
|
+
const chainId = StringUtil.hexToString(hexChainId);
|
|
53
|
+
this.emit('chainChanged', {
|
|
54
|
+
chainId
|
|
55
|
+
});
|
|
56
|
+
}
|
|
57
|
+
on(event, listener) {
|
|
58
|
+
if (event === 'chainChanged') {
|
|
59
|
+
// Create middleware that formats the chain ID before calling the original listener
|
|
60
|
+
const chainChangedMiddleware = hexChainId => {
|
|
61
|
+
const chainId = StringUtil.hexToString(hexChainId);
|
|
62
|
+
listener(chainId);
|
|
63
|
+
};
|
|
64
|
+
|
|
65
|
+
// Store the mapping between original listener and middleware
|
|
66
|
+
this.chainChangedListeners.set(listener, chainChangedMiddleware);
|
|
67
|
+
return this.provider.on('chainChanged', chainChangedMiddleware);
|
|
68
|
+
}
|
|
69
|
+
return this.provider.on(event, listener);
|
|
70
|
+
}
|
|
71
|
+
off(event, listener) {
|
|
72
|
+
if (event === 'chainChanged') {
|
|
73
|
+
// Get the middleware wrapper for this listener
|
|
74
|
+
const middleware = this.chainChangedListeners.get(listener);
|
|
75
|
+
if (middleware) {
|
|
76
|
+
// Remove the middleware from the provider
|
|
77
|
+
this.provider.off('chainChanged', middleware);
|
|
78
|
+
// Remove the mapping
|
|
79
|
+
this.chainChangedListeners.delete(listener);
|
|
80
|
+
return this;
|
|
81
|
+
}
|
|
82
|
+
}
|
|
83
|
+
return this.provider.off(event, listener);
|
|
84
|
+
}
|
|
85
|
+
}
|
|
86
|
+
//# sourceMappingURL=CoinbaseProvider.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"names":["EventEmitter","StringUtil","configure","WalletMobileSDKEVMProvider","CoinbaseProvider","chainChangedListeners","Map","constructor","config","hostURL","URL","callbackURL","redirect","hostPackageName","provider","jsonRpcUrl","storage","connect","accounts","isConnected","connected","request","method","params","selectedAddress","error","console","warn","disconnect","Promise","resolve","args","getChainId","chainId","onChainChanged","hexChainId","hexToString","emit","on","event","listener","chainChangedMiddleware","set","off","middleware","get","delete"],"sourceRoot":"../../../src","sources":["providers/CoinbaseProvider.ts"],"mappings":"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","ignoreList":[]}
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"names":[],"sourceRoot":"../../src","sources":["types.ts"],"mappings":"","ignoreList":[]}
|
|
@@ -0,0 +1,36 @@
|
|
|
1
|
+
"use strict";
|
|
2
|
+
|
|
3
|
+
export const COINBASE_METHODS = {
|
|
4
|
+
REQUEST_ACCOUNTS: 'eth_requestAccounts',
|
|
5
|
+
SIGN_TRANSACTION: 'eth_signTransaction',
|
|
6
|
+
SEND_TRANSACTION: 'eth_sendTransaction',
|
|
7
|
+
SIGN_MESSAGE: 'personal_sign',
|
|
8
|
+
SIGN_TYPED_DATA_V3: 'eth_signTypedData_v3',
|
|
9
|
+
SIGN_TYPED_DATA_V4: 'eth_signTypedData_v4',
|
|
10
|
+
SWITCH_CHAIN: 'wallet_switchEthereumChain',
|
|
11
|
+
ADD_ETHEREUM_CHAIN: 'wallet_addEthereumChain',
|
|
12
|
+
WATCH_ASSET: 'wallet_watchAsset'
|
|
13
|
+
};
|
|
14
|
+
export function getCoinbaseNamespace(namespaces, accounts) {
|
|
15
|
+
if (!namespaces || !accounts) {
|
|
16
|
+
throw new Error('CoinbaseConnector: Namespaces or accounts not found');
|
|
17
|
+
}
|
|
18
|
+
const namespace = namespaces['eip155'];
|
|
19
|
+
if (!namespace) {
|
|
20
|
+
throw new Error('CoinbaseConnector: Namespace not found');
|
|
21
|
+
}
|
|
22
|
+
let caipAddresses = [];
|
|
23
|
+
for (const account of accounts) {
|
|
24
|
+
namespace.chains?.forEach(chain => {
|
|
25
|
+
caipAddresses.push(`${chain}:${account}`);
|
|
26
|
+
});
|
|
27
|
+
}
|
|
28
|
+
return {
|
|
29
|
+
['eip155']: {
|
|
30
|
+
...namespace,
|
|
31
|
+
methods: Object.values(COINBASE_METHODS),
|
|
32
|
+
accounts: caipAddresses
|
|
33
|
+
}
|
|
34
|
+
};
|
|
35
|
+
}
|
|
36
|
+
//# sourceMappingURL=utils.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"names":["COINBASE_METHODS","REQUEST_ACCOUNTS","SIGN_TRANSACTION","SEND_TRANSACTION","SIGN_MESSAGE","SIGN_TYPED_DATA_V3","SIGN_TYPED_DATA_V4","SWITCH_CHAIN","ADD_ETHEREUM_CHAIN","WATCH_ASSET","getCoinbaseNamespace","namespaces","accounts","Error","namespace","caipAddresses","account","chains","forEach","chain","push","methods","Object","values"],"sourceRoot":"../../src","sources":["utils.ts"],"mappings":";;AAMA,OAAO,MAAMA,gBAAgB,GAAG;EAC9BC,gBAAgB,EAAE,qBAAqB;EACvCC,gBAAgB,EAAE,qBAAqB;EACvCC,gBAAgB,EAAE,qBAAqB;EACvCC,YAAY,EAAE,eAAe;EAC7BC,kBAAkB,EAAE,sBAAsB;EAC1CC,kBAAkB,EAAE,sBAAsB;EAC1CC,YAAY,EAAE,4BAA4B;EAC1CC,kBAAkB,EAAE,yBAAyB;EAC7CC,WAAW,EAAE;AACf,CAAU;AAEV,OAAO,SAASC,oBAAoBA,CAClCC,UAA+B,EAC/BC,QAAmB,EACP;EACZ,IAAI,CAACD,UAAU,IAAI,CAACC,QAAQ,EAAE;IAC5B,MAAM,IAAIC,KAAK,CAAC,qDAAqD,CAAC;EACxE;EAEA,MAAMC,SAAS,GAAGH,UAAU,CAAC,QAAQ,CAAC;EAEtC,IAAI,CAACG,SAAS,EAAE;IACd,MAAM,IAAID,KAAK,CAAC,wCAAwC,CAAC;EAC3D;EAEA,IAAIE,aAA4B,GAAG,EAAE;EAErC,KAAK,MAAMC,OAAO,IAAIJ,QAAQ,EAAE;IAC9BE,SAAS,CAACG,MAAM,EAAEC,OAAO,CAACC,KAAK,IAAI;MACjCJ,aAAa,CAACK,IAAI,CAAC,GAAGD,KAAK,IAAIH,OAAO,EAAE,CAAC;IAC3C,CAAC,CAAC;EACJ;EAEA,OAAO;IACL,CAAC,QAAQ,GAAG;MACV,GAAGF,SAAS;MACZO,OAAO,EAAEC,MAAM,CAACC,MAAM,CAACvB,gBAAgB,CAAC;MACxCY,QAAQ,EAAEG;IACZ;EACF,CAAC;AACH","ignoreList":[]}
|
|
@@ -0,0 +1,22 @@
|
|
|
1
|
+
import { WalletConnector, type AppKitNetwork, type CaipNetworkId, type ConnectionProperties, type ConnectOptions, type ConnectorInitOptions, type Namespaces, type WalletInfo } from '@reown/appkit-common-react-native';
|
|
2
|
+
import { CoinbaseProvider } from '../providers/CoinbaseProvider';
|
|
3
|
+
import type { CoinbaseConnectorConfig } from '../types';
|
|
4
|
+
export declare class CoinbaseConnector extends WalletConnector {
|
|
5
|
+
private static readonly SUPPORTED_NAMESPACE;
|
|
6
|
+
private config;
|
|
7
|
+
constructor(config?: CoinbaseConnectorConfig);
|
|
8
|
+
init(ops: ConnectorInitOptions): Promise<void>;
|
|
9
|
+
connect(opts?: Pick<ConnectOptions, 'namespaces' | 'defaultNetwork'>): Promise<Namespaces | undefined>;
|
|
10
|
+
disconnect(): Promise<void>;
|
|
11
|
+
getProvider(): CoinbaseProvider;
|
|
12
|
+
getNamespaces(): Namespaces;
|
|
13
|
+
getChainId(): CaipNetworkId | undefined;
|
|
14
|
+
getWalletInfo(): WalletInfo | undefined;
|
|
15
|
+
getProperties(): ConnectionProperties | undefined;
|
|
16
|
+
switchNetwork(network: AppKitNetwork): Promise<void>;
|
|
17
|
+
private deleteSession;
|
|
18
|
+
private saveSession;
|
|
19
|
+
restoreSession(): Promise<boolean>;
|
|
20
|
+
private getStorage;
|
|
21
|
+
}
|
|
22
|
+
//# sourceMappingURL=CoinbaseConnector.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"CoinbaseConnector.d.ts","sourceRoot":"","sources":["../../../src/connectors/CoinbaseConnector.ts"],"names":[],"mappings":"AAAA,OAAO,EACL,eAAe,EACf,KAAK,aAAa,EAClB,KAAK,aAAa,EAElB,KAAK,oBAAoB,EACzB,KAAK,cAAc,EACnB,KAAK,oBAAoB,EACzB,KAAK,UAAU,EACf,KAAK,UAAU,EAIhB,MAAM,mCAAmC,CAAC;AAE3C,OAAO,EAAE,gBAAgB,EAAE,MAAM,+BAA+B,CAAC;AACjE,OAAO,KAAK,EAAE,uBAAuB,EAAmB,MAAM,UAAU,CAAC;AAIzE,qBAAa,iBAAkB,SAAQ,eAAe;IACpD,OAAO,CAAC,MAAM,CAAC,QAAQ,CAAC,mBAAmB,CAA4B;IACvE,OAAO,CAAC,MAAM,CAA0B;gBAE5B,MAAM,CAAC,EAAE,uBAAuB;IAK7B,IAAI,CAAC,GAAG,EAAE,oBAAoB;IAkB9B,OAAO,CACpB,IAAI,CAAC,EAAE,IAAI,CAAC,cAAc,EAAE,YAAY,GAAG,gBAAgB,CAAC,GAC3D,OAAO,CAAC,UAAU,GAAG,SAAS,CAAC;IAiBnB,UAAU,IAAI,OAAO,CAAC,IAAI,CAAC;IAKjC,WAAW,IAAI,gBAAgB;IAQ/B,aAAa,IAAI,UAAU;IAQ3B,UAAU,IAAI,aAAa,GAAG,SAAS;IAOvC,aAAa,IAAI,UAAU,GAAG,SAAS;IAOvC,aAAa,IAAI,oBAAoB,GAAG,SAAS;IAI3C,aAAa,CAAC,OAAO,EAAE,aAAa,GAAG,OAAO,CAAC,IAAI,CAAC;IAmCnE,OAAO,CAAC,aAAa;IAKrB,OAAO,CAAC,WAAW;IAKJ,cAAc,IAAI,OAAO,CAAC,OAAO,CAAC;IAajD,OAAO,CAAC,UAAU;CAOnB"}
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"index.d.ts","sourceRoot":"","sources":["../../src/index.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,iBAAiB,EAAE,MAAM,gCAAgC,CAAC;AACnE,YAAY,EAAE,uBAAuB,EAAE,MAAM,SAAS,CAAC"}
|
|
@@ -0,0 +1,18 @@
|
|
|
1
|
+
/// <reference types="node" />
|
|
2
|
+
import EventEmitter from 'events';
|
|
3
|
+
import { type Provider, type RequestArguments } from '@reown/appkit-common-react-native';
|
|
4
|
+
import type { CoinbaseProviderConfig } from '../types';
|
|
5
|
+
export declare class CoinbaseProvider extends EventEmitter implements Provider {
|
|
6
|
+
private readonly config;
|
|
7
|
+
private provider;
|
|
8
|
+
private chainChangedListeners;
|
|
9
|
+
constructor(config: CoinbaseProviderConfig);
|
|
10
|
+
connect<T = string[]>(): Promise<T>;
|
|
11
|
+
disconnect(): Promise<void>;
|
|
12
|
+
request<T = unknown>(args: RequestArguments): Promise<T>;
|
|
13
|
+
getChainId(): `0x${string}`;
|
|
14
|
+
onChainChanged(hexChainId: `0x${string}`): void;
|
|
15
|
+
on(event: string, listener: (args?: any) => void): any;
|
|
16
|
+
off(event: string, listener: (args?: any) => void): any;
|
|
17
|
+
}
|
|
18
|
+
//# sourceMappingURL=CoinbaseProvider.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"CoinbaseProvider.d.ts","sourceRoot":"","sources":["../../../src/providers/CoinbaseProvider.ts"],"names":[],"mappings":";AAAA,OAAO,YAAY,MAAM,QAAQ,CAAC;AAClC,OAAO,EACL,KAAK,QAAQ,EACb,KAAK,gBAAgB,EAEtB,MAAM,mCAAmC,CAAC;AAE3C,OAAO,KAAK,EAAE,sBAAsB,EAAE,MAAM,UAAU,CAAC;AAEvD,qBAAa,gBAAiB,SAAQ,YAAa,YAAW,QAAQ;IACpE,OAAO,CAAC,QAAQ,CAAC,MAAM,CAAyB;IAChD,OAAO,CAAC,QAAQ,CAA6B;IAC7C,OAAO,CAAC,qBAAqB,CAGzB;gBAEQ,MAAM,EAAE,sBAAsB;IAepC,OAAO,CAAC,CAAC,GAAG,MAAM,EAAE,KAAK,OAAO,CAAC,CAAC,CAAC;IAqBnC,UAAU,IAAI,OAAO,CAAC,IAAI,CAAC;IAMjC,OAAO,CAAC,CAAC,GAAG,OAAO,EAAE,IAAI,EAAE,gBAAgB,GAAG,OAAO,CAAC,CAAC,CAAC;IAIxD,UAAU,IAAI,KAAK,MAAM,EAAE;IAI3B,cAAc,CAAC,UAAU,EAAE,KAAK,MAAM,EAAE,GAAG,IAAI;IAKtC,EAAE,CAAC,KAAK,EAAE,MAAM,EAAE,QAAQ,EAAE,CAAC,IAAI,CAAC,EAAE,GAAG,KAAK,IAAI,GAAG,GAAG;IAiBtD,GAAG,CAAC,KAAK,EAAE,MAAM,EAAE,QAAQ,EAAE,CAAC,IAAI,CAAC,EAAE,GAAG,KAAK,IAAI,GAAG,GAAG;CAgBjE"}
|
|
@@ -0,0 +1,17 @@
|
|
|
1
|
+
import type { MMKV } from 'react-native-mmkv';
|
|
2
|
+
import type { Namespaces } from '@reown/appkit-common-react-native';
|
|
3
|
+
import type { KVStorage, WalletMobileSDKProviderOptions } from '@coinbase/wallet-mobile-sdk/build/WalletMobileSDKEVMProvider';
|
|
4
|
+
import type { COINBASE_METHODS } from './utils';
|
|
5
|
+
export type CoinbaseProviderConfig = Omit<WalletMobileSDKProviderOptions, 'chainId' | 'address'> & {
|
|
6
|
+
redirect: string;
|
|
7
|
+
};
|
|
8
|
+
export type Values<T> = T[keyof T];
|
|
9
|
+
export type CoinbaseMethod = Values<typeof COINBASE_METHODS>;
|
|
10
|
+
export type CoinbaseSession = {
|
|
11
|
+
namespaces: Namespaces;
|
|
12
|
+
};
|
|
13
|
+
export type CoinbaseConnectorConfig = {
|
|
14
|
+
storage?: KVStorage | MMKV;
|
|
15
|
+
jsonRpcUrl?: string;
|
|
16
|
+
};
|
|
17
|
+
//# sourceMappingURL=types.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"types.d.ts","sourceRoot":"","sources":["../../src/types.ts"],"names":[],"mappings":"AAAA,OAAO,KAAK,EAAE,IAAI,EAAE,MAAM,mBAAmB,CAAC;AAC9C,OAAO,KAAK,EAAE,UAAU,EAAE,MAAM,mCAAmC,CAAC;AACpE,OAAO,KAAK,EACV,SAAS,EACT,8BAA8B,EAC/B,MAAM,8DAA8D,CAAC;AACtE,OAAO,KAAK,EAAE,gBAAgB,EAAE,MAAM,SAAS,CAAC;AAEhD,MAAM,MAAM,sBAAsB,GAAG,IAAI,CAAC,8BAA8B,EAAE,SAAS,GAAG,SAAS,CAAC,GAAG;IACjG,QAAQ,EAAE,MAAM,CAAC;CAClB,CAAC;AAEF,MAAM,MAAM,MAAM,CAAC,CAAC,IAAI,CAAC,CAAC,MAAM,CAAC,CAAC,CAAC;AAEnC,MAAM,MAAM,cAAc,GAAG,MAAM,CAAC,OAAO,gBAAgB,CAAC,CAAC;AAE7D,MAAM,MAAM,eAAe,GAAG;IAC5B,UAAU,EAAE,UAAU,CAAC;CACxB,CAAC;AAEF,MAAM,MAAM,uBAAuB,GAAG;IACpC,OAAO,CAAC,EAAE,SAAS,GAAG,IAAI,CAAC;IAC3B,UAAU,CAAC,EAAE,MAAM,CAAC;CACrB,CAAC"}
|
|
@@ -0,0 +1,14 @@
|
|
|
1
|
+
import type { Namespaces, ProposalNamespaces } from '@reown/appkit-common-react-native';
|
|
2
|
+
export declare const COINBASE_METHODS: {
|
|
3
|
+
readonly REQUEST_ACCOUNTS: "eth_requestAccounts";
|
|
4
|
+
readonly SIGN_TRANSACTION: "eth_signTransaction";
|
|
5
|
+
readonly SEND_TRANSACTION: "eth_sendTransaction";
|
|
6
|
+
readonly SIGN_MESSAGE: "personal_sign";
|
|
7
|
+
readonly SIGN_TYPED_DATA_V3: "eth_signTypedData_v3";
|
|
8
|
+
readonly SIGN_TYPED_DATA_V4: "eth_signTypedData_v4";
|
|
9
|
+
readonly SWITCH_CHAIN: "wallet_switchEthereumChain";
|
|
10
|
+
readonly ADD_ETHEREUM_CHAIN: "wallet_addEthereumChain";
|
|
11
|
+
readonly WATCH_ASSET: "wallet_watchAsset";
|
|
12
|
+
};
|
|
13
|
+
export declare function getCoinbaseNamespace(namespaces?: ProposalNamespaces, accounts?: string[]): Namespaces;
|
|
14
|
+
//# sourceMappingURL=utils.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"utils.d.ts","sourceRoot":"","sources":["../../src/utils.ts"],"names":[],"mappings":"AAAA,OAAO,KAAK,EAEV,UAAU,EACV,kBAAkB,EACnB,MAAM,mCAAmC,CAAC;AAE3C,eAAO,MAAM,gBAAgB;;;;;;;;;;CAUnB,CAAC;AAEX,wBAAgB,oBAAoB,CAClC,UAAU,CAAC,EAAE,kBAAkB,EAC/B,QAAQ,CAAC,EAAE,MAAM,EAAE,GAClB,UAAU,CA0BZ"}
|
package/package.json
ADDED
|
@@ -0,0 +1,51 @@
|
|
|
1
|
+
{
|
|
2
|
+
"name": "@reown/appkit-coinbase-react-native",
|
|
3
|
+
"version": "0.0.0-accounts-canary.1-20251023174733",
|
|
4
|
+
"main": "lib/commonjs/index.js",
|
|
5
|
+
"types": "lib/typescript/index.d.ts",
|
|
6
|
+
"module": "lib/module/index.js",
|
|
7
|
+
"react-native": "src/index.ts",
|
|
8
|
+
"source": "src/index.ts",
|
|
9
|
+
"scripts": {
|
|
10
|
+
"build": "bob build",
|
|
11
|
+
"clean": "rm -rf lib",
|
|
12
|
+
"test": "jest --passWithNoTests",
|
|
13
|
+
"lint": "eslint . --ext .js,.jsx,.ts,.tsx"
|
|
14
|
+
},
|
|
15
|
+
"files": [
|
|
16
|
+
"src",
|
|
17
|
+
"lib"
|
|
18
|
+
],
|
|
19
|
+
"keywords": [
|
|
20
|
+
"web3",
|
|
21
|
+
"crypto",
|
|
22
|
+
"appkit",
|
|
23
|
+
"walletconnect",
|
|
24
|
+
"react-native",
|
|
25
|
+
"coinbase"
|
|
26
|
+
],
|
|
27
|
+
"repository": "https://github.com/reown-com/appkit-react-native",
|
|
28
|
+
"author": "Reown (https://discord.gg/reown)",
|
|
29
|
+
"homepage": "https://reown.com/appkit",
|
|
30
|
+
"license": "SEE LICENSE IN LICENSE.md",
|
|
31
|
+
"bugs": {
|
|
32
|
+
"url": "https://github.com/reown-com/appkit-react-native/issues"
|
|
33
|
+
},
|
|
34
|
+
"publishConfig": {
|
|
35
|
+
"registry": "https://registry.npmjs.org/",
|
|
36
|
+
"access": "public",
|
|
37
|
+
"provenance": true
|
|
38
|
+
},
|
|
39
|
+
"dependencies": {
|
|
40
|
+
"@reown/appkit-common-react-native": "0.0.0-accounts-canary.1-20251023174733"
|
|
41
|
+
},
|
|
42
|
+
"peerDependencies": {
|
|
43
|
+
"@coinbase/wallet-mobile-sdk": ">=1.1.2",
|
|
44
|
+
"react": ">=18",
|
|
45
|
+
"react-native": ">=0.72"
|
|
46
|
+
},
|
|
47
|
+
"eslintIgnore": [
|
|
48
|
+
"node_modules/",
|
|
49
|
+
"lib/"
|
|
50
|
+
]
|
|
51
|
+
}
|
|
@@ -0,0 +1,171 @@
|
|
|
1
|
+
import {
|
|
2
|
+
WalletConnector,
|
|
3
|
+
type AppKitNetwork,
|
|
4
|
+
type CaipNetworkId,
|
|
5
|
+
type ChainNamespace,
|
|
6
|
+
type ConnectionProperties,
|
|
7
|
+
type ConnectOptions,
|
|
8
|
+
type ConnectorInitOptions,
|
|
9
|
+
type Namespaces,
|
|
10
|
+
type WalletInfo,
|
|
11
|
+
type Storage,
|
|
12
|
+
NumberUtil,
|
|
13
|
+
StringUtil
|
|
14
|
+
} from '@reown/appkit-common-react-native';
|
|
15
|
+
import { getCoinbaseNamespace } from '../utils';
|
|
16
|
+
import { CoinbaseProvider } from '../providers/CoinbaseProvider';
|
|
17
|
+
import type { CoinbaseConnectorConfig, CoinbaseSession } from '../types';
|
|
18
|
+
|
|
19
|
+
const SESSION_KEY = '@appkit/coinbase-connector/session';
|
|
20
|
+
|
|
21
|
+
export class CoinbaseConnector extends WalletConnector {
|
|
22
|
+
private static readonly SUPPORTED_NAMESPACE: ChainNamespace = 'eip155';
|
|
23
|
+
private config: CoinbaseConnectorConfig;
|
|
24
|
+
|
|
25
|
+
constructor(config?: CoinbaseConnectorConfig) {
|
|
26
|
+
super({ type: 'coinbase' });
|
|
27
|
+
this.config = config ?? {};
|
|
28
|
+
}
|
|
29
|
+
|
|
30
|
+
override async init(ops: ConnectorInitOptions) {
|
|
31
|
+
super.init(ops);
|
|
32
|
+
|
|
33
|
+
const redirect = ops.metadata.redirect?.universal ?? ops.metadata.redirect?.native;
|
|
34
|
+
if (!redirect) {
|
|
35
|
+
throw new Error('CoinbaseConnector: Redirect link not found in metadata');
|
|
36
|
+
}
|
|
37
|
+
|
|
38
|
+
this.provider = new CoinbaseProvider({
|
|
39
|
+
redirect,
|
|
40
|
+
// use config storage, as it needs to be mmkv-compatible
|
|
41
|
+
storage: this.config.storage,
|
|
42
|
+
jsonRpcUrl: this.config.jsonRpcUrl
|
|
43
|
+
});
|
|
44
|
+
|
|
45
|
+
await this.restoreSession();
|
|
46
|
+
}
|
|
47
|
+
|
|
48
|
+
override async connect(
|
|
49
|
+
opts?: Pick<ConnectOptions, 'namespaces' | 'defaultNetwork'>
|
|
50
|
+
): Promise<Namespaces | undefined> {
|
|
51
|
+
const accounts = await this.getProvider().connect();
|
|
52
|
+
|
|
53
|
+
if (
|
|
54
|
+
opts?.defaultNetwork &&
|
|
55
|
+
opts.defaultNetwork.chainNamespace === CoinbaseConnector.SUPPORTED_NAMESPACE
|
|
56
|
+
) {
|
|
57
|
+
await this.switchNetwork(opts.defaultNetwork);
|
|
58
|
+
}
|
|
59
|
+
|
|
60
|
+
const namespaces = getCoinbaseNamespace(opts?.namespaces, accounts);
|
|
61
|
+
this.namespaces = namespaces;
|
|
62
|
+
this.saveSession(namespaces);
|
|
63
|
+
|
|
64
|
+
return this.namespaces;
|
|
65
|
+
}
|
|
66
|
+
|
|
67
|
+
override async disconnect(): Promise<void> {
|
|
68
|
+
await super.disconnect();
|
|
69
|
+
this.deleteSession();
|
|
70
|
+
}
|
|
71
|
+
|
|
72
|
+
override getProvider(): CoinbaseProvider {
|
|
73
|
+
if (!this.provider) {
|
|
74
|
+
throw new Error('CoinbaseConnector: Provider not initialized. Call init() first.');
|
|
75
|
+
}
|
|
76
|
+
|
|
77
|
+
return this.provider as CoinbaseProvider;
|
|
78
|
+
}
|
|
79
|
+
|
|
80
|
+
override getNamespaces(): Namespaces {
|
|
81
|
+
if (!this.namespaces) {
|
|
82
|
+
throw new Error('CoinbaseConnector: Namespaces not initialized');
|
|
83
|
+
}
|
|
84
|
+
|
|
85
|
+
return this.namespaces;
|
|
86
|
+
}
|
|
87
|
+
|
|
88
|
+
override getChainId(): CaipNetworkId | undefined {
|
|
89
|
+
const hexChainId = this.getProvider().getChainId();
|
|
90
|
+
const chainId = StringUtil.hexToString(hexChainId);
|
|
91
|
+
|
|
92
|
+
return `${CoinbaseConnector.SUPPORTED_NAMESPACE}:${chainId}` as CaipNetworkId;
|
|
93
|
+
}
|
|
94
|
+
|
|
95
|
+
override getWalletInfo(): WalletInfo | undefined {
|
|
96
|
+
return {
|
|
97
|
+
name: 'Coinbase Wallet',
|
|
98
|
+
type: 'external'
|
|
99
|
+
};
|
|
100
|
+
}
|
|
101
|
+
|
|
102
|
+
override getProperties(): ConnectionProperties | undefined {
|
|
103
|
+
return undefined;
|
|
104
|
+
}
|
|
105
|
+
|
|
106
|
+
override async switchNetwork(network: AppKitNetwork): Promise<void> {
|
|
107
|
+
const provider = this.getProvider();
|
|
108
|
+
const chainId_ = NumberUtil.convertNumericToHexString(network.id);
|
|
109
|
+
|
|
110
|
+
try {
|
|
111
|
+
await provider.request({
|
|
112
|
+
method: 'wallet_switchEthereumChain',
|
|
113
|
+
params: [{ chainId: chainId_ }]
|
|
114
|
+
});
|
|
115
|
+
} catch (error: any) {
|
|
116
|
+
// Indicates chain is not added to provider
|
|
117
|
+
if (error?.code === 4902) {
|
|
118
|
+
try {
|
|
119
|
+
await provider.request({
|
|
120
|
+
method: 'wallet_addEthereumChain',
|
|
121
|
+
params: [
|
|
122
|
+
{
|
|
123
|
+
chainId: chainId_,
|
|
124
|
+
chainName: network.name,
|
|
125
|
+
nativeCurrency: network.nativeCurrency,
|
|
126
|
+
rpcUrls: [network.rpcUrls.default?.http[0] ?? ''],
|
|
127
|
+
blockExplorerUrls: [network.blockExplorers?.default.url]
|
|
128
|
+
}
|
|
129
|
+
]
|
|
130
|
+
});
|
|
131
|
+
} catch (e) {
|
|
132
|
+
console.warn('CoinbaseConnector: switchNetwork error', e);
|
|
133
|
+
throw e;
|
|
134
|
+
}
|
|
135
|
+
}
|
|
136
|
+
console.warn('CoinbaseConnector: switchNetwork error', error);
|
|
137
|
+
throw error;
|
|
138
|
+
}
|
|
139
|
+
}
|
|
140
|
+
|
|
141
|
+
private deleteSession(): void {
|
|
142
|
+
const storage = this.getStorage();
|
|
143
|
+
storage.removeItem(SESSION_KEY);
|
|
144
|
+
}
|
|
145
|
+
|
|
146
|
+
private saveSession(namespaces: Namespaces): void {
|
|
147
|
+
const storage = this.getStorage();
|
|
148
|
+
storage.setItem<CoinbaseSession>(SESSION_KEY, { namespaces });
|
|
149
|
+
}
|
|
150
|
+
|
|
151
|
+
override async restoreSession(): Promise<boolean> {
|
|
152
|
+
const storage = this.getStorage();
|
|
153
|
+
const session = await storage.getItem<CoinbaseSession>(SESSION_KEY);
|
|
154
|
+
if (!session) {
|
|
155
|
+
return false;
|
|
156
|
+
}
|
|
157
|
+
|
|
158
|
+
const { namespaces } = session;
|
|
159
|
+
this.namespaces = namespaces;
|
|
160
|
+
|
|
161
|
+
return true;
|
|
162
|
+
}
|
|
163
|
+
|
|
164
|
+
private getStorage(): Storage {
|
|
165
|
+
if (!this.storage) {
|
|
166
|
+
throw new Error('CoinbaseConnector: Storage not initialized');
|
|
167
|
+
}
|
|
168
|
+
|
|
169
|
+
return this.storage;
|
|
170
|
+
}
|
|
171
|
+
}
|
package/src/index.ts
ADDED
|
@@ -0,0 +1,106 @@
|
|
|
1
|
+
import EventEmitter from 'events';
|
|
2
|
+
import {
|
|
3
|
+
type Provider,
|
|
4
|
+
type RequestArguments,
|
|
5
|
+
StringUtil
|
|
6
|
+
} from '@reown/appkit-common-react-native';
|
|
7
|
+
import { configure, WalletMobileSDKEVMProvider } from '@coinbase/wallet-mobile-sdk';
|
|
8
|
+
import type { CoinbaseProviderConfig } from '../types';
|
|
9
|
+
|
|
10
|
+
export class CoinbaseProvider extends EventEmitter implements Provider {
|
|
11
|
+
private readonly config: CoinbaseProviderConfig;
|
|
12
|
+
private provider: WalletMobileSDKEVMProvider;
|
|
13
|
+
private chainChangedListeners = new Map<
|
|
14
|
+
(args?: any) => void,
|
|
15
|
+
(hexChainId: `0x${string}`) => void
|
|
16
|
+
>();
|
|
17
|
+
|
|
18
|
+
constructor(config: CoinbaseProviderConfig) {
|
|
19
|
+
super();
|
|
20
|
+
this.config = config;
|
|
21
|
+
configure({
|
|
22
|
+
hostURL: new URL('https://wallet.coinbase.com/wsegue'),
|
|
23
|
+
callbackURL: new URL(this.config.redirect), // App Universal Link
|
|
24
|
+
hostPackageName: 'org.toshi'
|
|
25
|
+
});
|
|
26
|
+
this.provider = new WalletMobileSDKEVMProvider({
|
|
27
|
+
...this.config,
|
|
28
|
+
jsonRpcUrl: this.config.jsonRpcUrl,
|
|
29
|
+
storage: this.config.storage
|
|
30
|
+
});
|
|
31
|
+
}
|
|
32
|
+
|
|
33
|
+
async connect<T = string[]>(): Promise<T> {
|
|
34
|
+
try {
|
|
35
|
+
let accounts: string[] = [];
|
|
36
|
+
const isConnected = this.provider.connected;
|
|
37
|
+
|
|
38
|
+
if (!isConnected) {
|
|
39
|
+
accounts = await this.provider.request({
|
|
40
|
+
method: 'eth_requestAccounts',
|
|
41
|
+
params: []
|
|
42
|
+
});
|
|
43
|
+
} else {
|
|
44
|
+
accounts = this.provider.selectedAddress ? [this.provider.selectedAddress] : [];
|
|
45
|
+
}
|
|
46
|
+
|
|
47
|
+
return accounts as T;
|
|
48
|
+
} catch (error) {
|
|
49
|
+
console.warn('CoinbaseProvider: connect error', error);
|
|
50
|
+
|
|
51
|
+
throw error;
|
|
52
|
+
}
|
|
53
|
+
}
|
|
54
|
+
async disconnect(): Promise<void> {
|
|
55
|
+
this.provider.disconnect();
|
|
56
|
+
|
|
57
|
+
return Promise.resolve();
|
|
58
|
+
}
|
|
59
|
+
|
|
60
|
+
request<T = unknown>(args: RequestArguments): Promise<T> {
|
|
61
|
+
return this.provider.request(args);
|
|
62
|
+
}
|
|
63
|
+
|
|
64
|
+
getChainId(): `0x${string}` {
|
|
65
|
+
return this.provider.chainId as `0x${string}`;
|
|
66
|
+
}
|
|
67
|
+
|
|
68
|
+
onChainChanged(hexChainId: `0x${string}`): void {
|
|
69
|
+
const chainId = StringUtil.hexToString(hexChainId);
|
|
70
|
+
this.emit('chainChanged', { chainId });
|
|
71
|
+
}
|
|
72
|
+
|
|
73
|
+
override on(event: string, listener: (args?: any) => void): any {
|
|
74
|
+
if (event === 'chainChanged') {
|
|
75
|
+
// Create middleware that formats the chain ID before calling the original listener
|
|
76
|
+
const chainChangedMiddleware = (hexChainId: `0x${string}`) => {
|
|
77
|
+
const chainId = StringUtil.hexToString(hexChainId);
|
|
78
|
+
listener(chainId);
|
|
79
|
+
};
|
|
80
|
+
|
|
81
|
+
// Store the mapping between original listener and middleware
|
|
82
|
+
this.chainChangedListeners.set(listener, chainChangedMiddleware);
|
|
83
|
+
|
|
84
|
+
return this.provider.on('chainChanged', chainChangedMiddleware);
|
|
85
|
+
}
|
|
86
|
+
|
|
87
|
+
return this.provider.on(event, listener);
|
|
88
|
+
}
|
|
89
|
+
|
|
90
|
+
override off(event: string, listener: (args?: any) => void): any {
|
|
91
|
+
if (event === 'chainChanged') {
|
|
92
|
+
// Get the middleware wrapper for this listener
|
|
93
|
+
const middleware = this.chainChangedListeners.get(listener);
|
|
94
|
+
if (middleware) {
|
|
95
|
+
// Remove the middleware from the provider
|
|
96
|
+
this.provider.off('chainChanged', middleware);
|
|
97
|
+
// Remove the mapping
|
|
98
|
+
this.chainChangedListeners.delete(listener);
|
|
99
|
+
|
|
100
|
+
return this;
|
|
101
|
+
}
|
|
102
|
+
}
|
|
103
|
+
|
|
104
|
+
return this.provider.off(event, listener);
|
|
105
|
+
}
|
|
106
|
+
}
|
package/src/types.ts
ADDED
|
@@ -0,0 +1,24 @@
|
|
|
1
|
+
import type { MMKV } from 'react-native-mmkv';
|
|
2
|
+
import type { Namespaces } from '@reown/appkit-common-react-native';
|
|
3
|
+
import type {
|
|
4
|
+
KVStorage,
|
|
5
|
+
WalletMobileSDKProviderOptions
|
|
6
|
+
} from '@coinbase/wallet-mobile-sdk/build/WalletMobileSDKEVMProvider';
|
|
7
|
+
import type { COINBASE_METHODS } from './utils';
|
|
8
|
+
|
|
9
|
+
export type CoinbaseProviderConfig = Omit<WalletMobileSDKProviderOptions, 'chainId' | 'address'> & {
|
|
10
|
+
redirect: string;
|
|
11
|
+
};
|
|
12
|
+
|
|
13
|
+
export type Values<T> = T[keyof T];
|
|
14
|
+
|
|
15
|
+
export type CoinbaseMethod = Values<typeof COINBASE_METHODS>;
|
|
16
|
+
|
|
17
|
+
export type CoinbaseSession = {
|
|
18
|
+
namespaces: Namespaces;
|
|
19
|
+
};
|
|
20
|
+
|
|
21
|
+
export type CoinbaseConnectorConfig = {
|
|
22
|
+
storage?: KVStorage | MMKV;
|
|
23
|
+
jsonRpcUrl?: string;
|
|
24
|
+
};
|
package/src/utils.ts
ADDED
|
@@ -0,0 +1,48 @@
|
|
|
1
|
+
import type {
|
|
2
|
+
CaipAddress,
|
|
3
|
+
Namespaces,
|
|
4
|
+
ProposalNamespaces
|
|
5
|
+
} from '@reown/appkit-common-react-native';
|
|
6
|
+
|
|
7
|
+
export const COINBASE_METHODS = {
|
|
8
|
+
REQUEST_ACCOUNTS: 'eth_requestAccounts',
|
|
9
|
+
SIGN_TRANSACTION: 'eth_signTransaction',
|
|
10
|
+
SEND_TRANSACTION: 'eth_sendTransaction',
|
|
11
|
+
SIGN_MESSAGE: 'personal_sign',
|
|
12
|
+
SIGN_TYPED_DATA_V3: 'eth_signTypedData_v3',
|
|
13
|
+
SIGN_TYPED_DATA_V4: 'eth_signTypedData_v4',
|
|
14
|
+
SWITCH_CHAIN: 'wallet_switchEthereumChain',
|
|
15
|
+
ADD_ETHEREUM_CHAIN: 'wallet_addEthereumChain',
|
|
16
|
+
WATCH_ASSET: 'wallet_watchAsset'
|
|
17
|
+
} as const;
|
|
18
|
+
|
|
19
|
+
export function getCoinbaseNamespace(
|
|
20
|
+
namespaces?: ProposalNamespaces,
|
|
21
|
+
accounts?: string[]
|
|
22
|
+
): Namespaces {
|
|
23
|
+
if (!namespaces || !accounts) {
|
|
24
|
+
throw new Error('CoinbaseConnector: Namespaces or accounts not found');
|
|
25
|
+
}
|
|
26
|
+
|
|
27
|
+
const namespace = namespaces['eip155'];
|
|
28
|
+
|
|
29
|
+
if (!namespace) {
|
|
30
|
+
throw new Error('CoinbaseConnector: Namespace not found');
|
|
31
|
+
}
|
|
32
|
+
|
|
33
|
+
let caipAddresses: CaipAddress[] = [];
|
|
34
|
+
|
|
35
|
+
for (const account of accounts) {
|
|
36
|
+
namespace.chains?.forEach(chain => {
|
|
37
|
+
caipAddresses.push(`${chain}:${account}`);
|
|
38
|
+
});
|
|
39
|
+
}
|
|
40
|
+
|
|
41
|
+
return {
|
|
42
|
+
['eip155']: {
|
|
43
|
+
...namespace,
|
|
44
|
+
methods: Object.values(COINBASE_METHODS),
|
|
45
|
+
accounts: caipAddresses
|
|
46
|
+
}
|
|
47
|
+
};
|
|
48
|
+
}
|