@bitpay-labs/bitcore-wallet-service 11.8.1 → 11.8.2

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (84) hide show
  1. package/package.json +2 -2
  2. package/src/bws.ts +2 -0
  3. package/src/lib/common/utils.ts +6 -0
  4. package/src/lib/expressapp.ts +63 -2378
  5. package/src/lib/model/txproposal.ts +14 -10
  6. package/src/lib/routes/advertisements.ts +151 -0
  7. package/src/lib/routes/blockchain.ts +152 -0
  8. package/src/lib/routes/context.ts +149 -0
  9. package/src/lib/routes/maintenance.ts +111 -0
  10. package/src/lib/routes/moralis.ts +89 -0
  11. package/src/lib/routes/notifications.ts +135 -0
  12. package/src/lib/routes/services.ts +528 -0
  13. package/src/lib/routes/setup.ts +86 -0
  14. package/src/lib/routes/transactions.ts +196 -0
  15. package/src/lib/routes/walletdata.ts +167 -0
  16. package/src/lib/routes/wallets.ts +289 -0
  17. package/src/lib/server.ts +24 -1
  18. package/src/lib/storage.ts +3 -0
  19. package/ts_build/package.json +4 -4
  20. package/ts_build/src/bws.js +3 -0
  21. package/ts_build/src/bws.js.map +1 -1
  22. package/ts_build/src/lib/common/index.d.ts +1 -0
  23. package/ts_build/src/lib/common/index.d.ts.map +1 -1
  24. package/ts_build/src/lib/common/utils.d.ts +1 -0
  25. package/ts_build/src/lib/common/utils.d.ts.map +1 -1
  26. package/ts_build/src/lib/common/utils.js +6 -0
  27. package/ts_build/src/lib/common/utils.js.map +1 -1
  28. package/ts_build/src/lib/expressapp.d.ts.map +1 -1
  29. package/ts_build/src/lib/expressapp.js +64 -2224
  30. package/ts_build/src/lib/expressapp.js.map +1 -1
  31. package/ts_build/src/lib/model/txproposal.d.ts +1 -4
  32. package/ts_build/src/lib/model/txproposal.d.ts.map +1 -1
  33. package/ts_build/src/lib/model/txproposal.js +13 -9
  34. package/ts_build/src/lib/model/txproposal.js.map +1 -1
  35. package/ts_build/src/lib/routes/advertisements.d.ts +11 -0
  36. package/ts_build/src/lib/routes/advertisements.d.ts.map +1 -0
  37. package/ts_build/src/lib/routes/advertisements.js +119 -0
  38. package/ts_build/src/lib/routes/advertisements.js.map +1 -0
  39. package/ts_build/src/lib/routes/blockchain.d.ts +13 -0
  40. package/ts_build/src/lib/routes/blockchain.d.ts.map +1 -0
  41. package/ts_build/src/lib/routes/blockchain.js +159 -0
  42. package/ts_build/src/lib/routes/blockchain.js.map +1 -0
  43. package/ts_build/src/lib/routes/context.d.ts +12 -0
  44. package/ts_build/src/lib/routes/context.d.ts.map +1 -0
  45. package/ts_build/src/lib/routes/context.js +115 -0
  46. package/ts_build/src/lib/routes/context.js.map +1 -0
  47. package/ts_build/src/lib/routes/maintenance.d.ts +10 -0
  48. package/ts_build/src/lib/routes/maintenance.d.ts.map +1 -0
  49. package/ts_build/src/lib/routes/maintenance.js +131 -0
  50. package/ts_build/src/lib/routes/maintenance.js.map +1 -0
  51. package/ts_build/src/lib/routes/moralis.d.ts +9 -0
  52. package/ts_build/src/lib/routes/moralis.d.ts.map +1 -0
  53. package/ts_build/src/lib/routes/moralis.js +78 -0
  54. package/ts_build/src/lib/routes/moralis.js.map +1 -0
  55. package/ts_build/src/lib/routes/notifications.d.ts +10 -0
  56. package/ts_build/src/lib/routes/notifications.d.ts.map +1 -0
  57. package/ts_build/src/lib/routes/notifications.js +120 -0
  58. package/ts_build/src/lib/routes/notifications.js.map +1 -0
  59. package/ts_build/src/lib/routes/services.d.ts +11 -0
  60. package/ts_build/src/lib/routes/services.d.ts.map +1 -0
  61. package/ts_build/src/lib/routes/services.js +430 -0
  62. package/ts_build/src/lib/routes/services.js.map +1 -0
  63. package/ts_build/src/lib/routes/setup.d.ts +4 -0
  64. package/ts_build/src/lib/routes/setup.d.ts.map +1 -0
  65. package/ts_build/src/lib/routes/setup.js +79 -0
  66. package/ts_build/src/lib/routes/setup.js.map +1 -0
  67. package/ts_build/src/lib/routes/transactions.d.ts +9 -0
  68. package/ts_build/src/lib/routes/transactions.d.ts.map +1 -0
  69. package/ts_build/src/lib/routes/transactions.js +188 -0
  70. package/ts_build/src/lib/routes/transactions.js.map +1 -0
  71. package/ts_build/src/lib/routes/walletdata.d.ts +10 -0
  72. package/ts_build/src/lib/routes/walletdata.d.ts.map +1 -0
  73. package/ts_build/src/lib/routes/walletdata.js +186 -0
  74. package/ts_build/src/lib/routes/walletdata.js.map +1 -0
  75. package/ts_build/src/lib/routes/wallets.d.ts +13 -0
  76. package/ts_build/src/lib/routes/wallets.d.ts.map +1 -0
  77. package/ts_build/src/lib/routes/wallets.js +292 -0
  78. package/ts_build/src/lib/routes/wallets.js.map +1 -0
  79. package/ts_build/src/lib/server.d.ts.map +1 -1
  80. package/ts_build/src/lib/server.js +19 -1
  81. package/ts_build/src/lib/server.js.map +1 -1
  82. package/ts_build/src/lib/storage.d.ts.map +1 -1
  83. package/ts_build/src/lib/storage.js +3 -0
  84. package/ts_build/src/lib/storage.js.map +1 -1
@@ -1,29 +1,25 @@
1
1
  import path from 'path';
2
- import * as async from 'async';
3
- import compression from 'compression';
4
- import cors from 'cors';
5
2
  import express from 'express';
6
- import RateLimit from 'express-rate-limit';
7
- import _ from 'lodash';
8
- import rp from 'request-promise-native';
9
3
  import 'source-map-support/register';
10
4
  import config from '../config';
11
5
  import * as Types from '../types/expressapp';
12
- import { Common } from './common';
13
- import { ClientError } from './errors/clienterror';
14
- import { Errors } from './errors/errordefinitions';
15
- import { logger, transports } from './logger';
6
+ import { logger } from './logger';
16
7
  import { AaveRouter } from './routes/aave';
8
+ import { registerAdvertisementRoutes } from './routes/advertisements';
9
+ import { registerBlockchainRoutes } from './routes/blockchain';
10
+ import { createRouteHelpers } from './routes/context';
17
11
  import { error } from './routes/helpers';
12
+ import { registerMaintenanceRoutes } from './routes/maintenance';
18
13
  import { createWalletLimiter } from './routes/middleware/createWalletLimiter';
19
- import { LogMiddleware } from './routes/middleware/log';
14
+ import { registerMoralisRoutes } from './routes/moralis';
15
+ import { registerNotificationRoutes } from './routes/notifications';
16
+ import { registerServiceRoutes } from './routes/services';
17
+ import { createEstimateFeeLimiter, setupAppMiddleware } from './routes/setup';
18
+ import { registerTransactionRoutes } from './routes/transactions';
20
19
  import { TssRouter } from './routes/tss';
20
+ import { registerWalletDataRoutes } from './routes/walletdata';
21
+ import { registerWalletRoutes } from './routes/wallets';
21
22
  import { WalletService } from './server';
22
- import { Stats } from './stats';
23
- import type { GetAddressesOpts } from '../types/server';
24
-
25
- const Defaults = Common.Defaults;
26
- const Utils = Common.Utils;
27
23
 
28
24
  export class ExpressApp {
29
25
  app: express.Express;
@@ -42,723 +38,39 @@ export class ExpressApp {
42
38
  */
43
39
  start(opts, cb) {
44
40
  opts = opts || {};
45
-
46
- this.app.use(compression());
47
-
48
- this.app.use((req, res, next) => {
49
- res.setHeader('Access-Control-Allow-Origin', '*');
50
- res.setHeader('Access-Control-Allow-Methods', 'GET, POST, OPTIONS, PUT, DELETE');
51
- res.setHeader(
52
- 'Access-Control-Allow-Headers',
53
- 'x-signature,x-identity,x-identities,x-session,x-client-version,x-wallet-id,X-Requested-With,Content-Type,Authorization'
54
- );
55
- res.setHeader('x-service-version', WalletService.getServiceVersion());
56
- next();
57
- });
58
- const allowCORS = (req, res, next) => {
59
- if ('OPTIONS' == req.method) {
60
- res.sendStatus(200);
61
- res.end();
62
- return;
63
- }
64
- next();
65
- };
66
- this.app.use(allowCORS);
67
- this.app.enable('trust proxy');
68
-
69
- // handle `abort` https://nodejs.org/api/http.html#http_event_abort
70
- this.app.use((req, res, next) => {
71
- req.on('abort', () => {
72
- logger.warn('Request aborted by the client');
73
- });
74
- next();
75
- });
76
-
77
- const POST_LIMIT = 1024 * 100; // Max POST 100 KB
78
- const POST_LIMIT_LARGE = 2 * 1024 * 1024; // Max POST 2 MB
79
-
80
- this.app.use((req, res, next) => {
81
- if (req.path.includes('/txproposals') || req.path.includes('/tss/')) {
82
- // Pushing a lot of utxos to txproposals can make the request much bigger than 100 MB
83
- return express.json({ limit: POST_LIMIT_LARGE })(req, res, next);
84
- } else {
85
- return express.json({ limit: POST_LIMIT })(req, res, next);
86
- }
87
- });
88
-
89
- this.app.use((req, res, next) => {
90
- if (config.maintenanceOpts.maintenanceMode === true) {
91
- // send a 503 error, with a message to the bitpay status page
92
- const errorCode = 503;
93
- const errorMessage = 'BWS down for maintenance';
94
- res.status(503).send({ code: errorCode, message: errorMessage });
95
- } else {
96
- next();
97
- }
98
- });
99
-
100
- if (opts.disableLogs) {
101
- for (const transport of transports) {
102
- transport.level = 'error';
103
- }
104
- } else {
105
- this.app.use(LogMiddleware());
106
- // morgan.token('walletId', function getId(req) {
107
- // return req.walletId ? '<' + req.walletId + '>' : '<>';
108
- // });
109
-
110
- // const logFormat =
111
- // ':walletId :remote-addr :date[iso] ":method :url" :status :res[content-length] :response-time ":user-agent" ';
112
- // const logOpts = {
113
- // skip(req, res) {
114
- // if (res.statusCode != 200) return false;
115
- // return req.path.indexOf('/notifications/') >= 0;
116
- // },
117
- // stream: logger.stream
118
- // };
119
-
120
- // this.app.use(morgan(logFormat, logOpts));
121
- }
41
+ setupAppMiddleware(this.app, opts);
122
42
 
123
43
  const router = express.Router();
124
44
 
125
45
  error.setOpts(opts);
126
46
  const returnError: Types.ReturnErrorFn = error.returnError.bind(error);
47
+ const {
48
+ getServer,
49
+ getServerWithAuth,
50
+ getServerWithMultiAuth,
51
+ logDeprecated,
52
+ setPublicCache
53
+ } = createRouteHelpers(returnError);
127
54
 
128
- const logDeprecated: Types.LogDeprecatedFn = req => {
129
- logger.warn('DEPRECATED', req.method, req.url, '(' + req.header('x-client-version') + ')');
130
- };
131
-
132
- const getCredentials: Types.GetCredentialsFn = req => {
133
- const identity = req.header('x-identity');
134
- if (!identity) return;
135
-
136
- return {
137
- copayerId: identity,
138
- signature: req.header('x-signature'),
139
- session: req.header('x-session')
140
- };
141
- };
142
-
143
- const getServer: Types.GetServerFn = (req, _res) => {
144
- const opts = {
145
- clientVersion: req.header('x-client-version'),
146
- userAgent: req.header('user-agent')
147
- };
148
- return WalletService.getInstance(opts);
149
- };
150
-
151
- const getServerWithAuth: Types.GetServerWithAuthFn = async (req, res, opts, cb) => {
152
- if (typeof opts === 'function') {
153
- cb = opts;
154
- opts = {};
155
- }
156
- opts = (opts || {}) as Types.ServerOpts;
157
-
158
- const credentials = getCredentials(req);
159
- if (!credentials)
160
- return returnError(Errors.NOT_AUTHORIZED, res, req);
161
-
162
- const reqUrl = req.redirectedUrl || req.url;
163
-
164
- const auth = {
165
- copayerId: credentials.copayerId,
166
- message: req.method.toLowerCase() + '|' + reqUrl + '|' + JSON.stringify(req.body),
167
- signature: credentials.signature,
168
- clientVersion: req.header('x-client-version'),
169
- userAgent: req.header('user-agent'),
170
- walletId: req.header('x-wallet-id'),
171
- session: undefined
172
- };
173
- if (opts.allowSession) {
174
- auth.session = credentials.session;
175
- }
176
- try {
177
- const server: WalletService = await new Promise((resolve, reject) => {
178
- WalletService.getInstanceWithAuth(auth, (err, server) => {
179
- if (err) {
180
- return reject(err);
181
- }
182
-
183
- if (opts.onlySupportStaff && !server.copayerIsSupportStaff) {
184
- return reject(Errors.NOT_AUTHORIZED);
185
- }
186
-
187
- if (server.copayerIsSupportStaff) {
188
- req.isSupportStaff = true;
189
- }
190
-
191
- if (opts.onlyMarketingStaff && !server.copayerIsMarketingStaff) {
192
- return reject(Errors.NOT_AUTHORIZED);
193
- }
194
-
195
- // For logging
196
- req.walletId = server.walletId;
197
- req.copayerId = server.copayerId;
198
-
199
- return resolve(server);
200
- });
201
- });
202
- if (cb) {
203
- return cb(server);
204
- }
205
- return server;
206
- } catch (err) {
207
- if (opts.silentFailure) {
208
- if (cb) {
209
- return cb(null, err);
210
- }
211
- throw err;
212
- }
213
- return returnError(err, res, req);
214
- }
215
- };
216
-
217
- /**
218
- * @description process simultaneous requests based on multiple identities that have the same key, hence, the same signature
219
- * @param {Request} req
220
- * @param {Response} res
221
- * @param {Object} opts
222
- * @returns Array<Promise>
223
- */
224
- const getServerWithMultiAuth: Types.GetServerWithMultiAuthFn = (req, res, opts = {}) => {
225
- const identities = req.headers['x-identities'] ? req.headers['x-identities'].split(',') : false;
226
- const signature = req.headers['x-signature'];
227
- if (!identities || !signature) {
228
- throw Errors.NOT_AUTHORIZED;
229
- }
230
-
231
- if (!Array.isArray(identities)) {
232
- throw Errors.NOT_AUTHORIZED;
233
- }
234
-
235
- // return a list of promises that we can await or chain
236
- return identities.map(
237
- id =>
238
- new Promise((resolve, reject) =>
239
- getServerWithAuth(
240
- Object.assign(req, {
241
- headers: {
242
- ...req.headers,
243
- 'x-identity': id
244
- }
245
- }),
246
- res,
247
- opts,
248
- (server, err) => (err ? reject(err) : resolve(server))
249
- )
250
- )
251
- );
252
- };
253
-
254
-
255
- const ONE_MINUTE = 60;
256
- // See https://support.cloudflare.com/hc/en-us/articles/115003206852-Understanding-Origin-Cache-Control
257
- // Case: "▶Cache an asset with revalidation, but allow stale responses if origin server is unreachable"
258
- function SetPublicCache(res: express.Response, seconds: number) {
259
- res.setHeader('Cache-Control', `public, max-age=${seconds}, stale-if-error=${10 * seconds}`);
260
- }
261
-
262
- // retrieve latest version of copay
263
- router.get('/latest-version', async (req, res) => {
264
- SetPublicCache(res, 10 * ONE_MINUTE);
265
- try {
266
- res.setHeader('User-Agent', 'copay');
267
- const options = {
268
- uri: 'https://api.github.com/repos/bitpay/wallet/releases/latest',
269
- headers: {
270
- 'User-Agent': 'Copay'
271
- },
272
- json: true
273
- };
274
-
275
- let server: WalletService;
276
- try {
277
- server = getServer(req, res);
278
- } catch (ex) {
279
- return returnError(ex, res, req);
280
- }
281
- server.storage.checkAndUseGlobalCache(
282
- 'latest-copay-version',
283
- Defaults.COPAY_VERSION_CACHE_DURATION,
284
- async (err, version) => {
285
- if (err) {
286
- res.send(err);
287
- }
288
- if (version) {
289
- res.json({ version });
290
- } else {
291
- try {
292
- const htmlString = await rp(options);
293
- if (htmlString['tag_name']) {
294
- server.storage.storeGlobalCache('latest-copay-version', htmlString['tag_name'], () => {
295
- res.json({ version: htmlString['tag_name'] });
296
- });
297
- }
298
- } catch (err) {
299
- res.send(err);
300
- }
301
- }
302
- }
303
- );
304
- } catch (err) {
305
- res.send(err);
306
- }
307
- });
308
-
309
- // DEPRECATED
310
- router.post('/v1/wallets/', createWalletLimiter(opts), (req, res) => {
311
- logDeprecated(req);
312
- return returnError(new ClientError('BIP45 wallet creation no longer supported'), res, req);
313
- });
314
-
315
- router.post('/v2/wallets/', createWalletLimiter(opts), (req, res) => {
316
- let server: WalletService;
317
- try {
318
- server = getServer(req, res);
319
- } catch (ex) {
320
- return returnError(ex, res, req);
321
- }
322
- server.createWallet(req.body, (err, walletId) => {
323
- if (err) return returnError(err, res, req);
324
- res.json({
325
- walletId
326
- });
327
- });
328
- });
329
-
330
- router.put('/v1/copayers/:id/', (req, res) => {
331
- req.body.copayerId = req.params['id'];
332
- let server: WalletService;
333
- try {
334
- server = getServer(req, res);
335
- } catch (ex) {
336
- return returnError(ex, res, req);
337
- }
338
- server.addAccess(req.body, (err, result) => {
339
- if (err) return returnError(err, res, req);
340
- res.json(result);
341
- });
342
- });
343
-
344
- // DEPRECATED
345
- router.post('/v1/wallets/:id/copayers/', (req, res) => {
346
- logDeprecated(req);
347
- return returnError(new ClientError('BIP45 wallet creation no longer supported'), res, req);
348
- });
349
-
350
- router.post('/v2/wallets/:id/copayers/', (req, res) => {
351
- req.body.walletId = req.params['id'];
352
- let server: WalletService;
353
- try {
354
- server = getServer(req, res);
355
- } catch (ex) {
356
- return returnError(ex, res, req);
357
- }
358
- server.joinWallet(req.body, (err, result) => {
359
- if (err) return returnError(err, res, req);
360
-
361
- res.json(result);
362
- });
363
- });
364
-
365
- // DEPRECATED
366
- router.get('/v1/wallets/', (req, res) => {
367
- logDeprecated(req);
368
- getServerWithAuth(req, res, server => {
369
- server.getStatus(
370
- {
371
- includeExtendedInfo: true
372
- },
373
- (err, status) => {
374
- if (err) return returnError(err, res, req);
375
- res.json(status);
376
- }
377
- );
378
- });
379
- });
380
-
381
- // DEPRECATED
382
- router.get('/v2/wallets/', (req, res) => {
383
- getServerWithAuth(req, res, server => {
384
- const opts = { includeExtendedInfo: false, twoStep: false };
385
- if (req.query.includeExtendedInfo == '1') opts.includeExtendedInfo = true;
386
- if (req.query.twoStep == '1') opts.twoStep = true;
387
-
388
- server.getStatus(opts, (err, status) => {
389
- if (err) return returnError(err, res, req);
390
- res.json(status);
391
- });
392
- });
393
- });
394
-
395
- router.get('/v3/wallets/', (req, res) => {
396
- getServerWithAuth(req, res, server => {
397
- const opts = {
398
- includeExtendedInfo: false,
399
- twoStep: false,
400
- includeServerMessages: false,
401
- tokenAddress: req.query.tokenAddress,
402
- multisigContractAddress: req.query.multisigContractAddress,
403
- network: req.query.network
404
- };
405
- if (req.query.includeExtendedInfo == '1') opts.includeExtendedInfo = true;
406
- if (req.query.twoStep == '1') opts.twoStep = true;
407
- if (req.query.serverMessageArray == '1') opts.includeServerMessages = true;
408
- server.getStatus(opts, (err, status) => {
409
- if (err) return returnError(err, res, req);
410
- res.json(status);
411
- });
412
- });
413
- });
414
-
415
- router.get('/v1/wallets/all/', async (req, res) => {
416
- let responses;
417
- const includeExtendedInfo = req.query.includeExtendedInfo == '1';
418
- const twoStep = req.query.twoStep == '1';
419
- const silentFailure = req.query.silentFailure == '1';
420
- const includeServerMessages = req.query.serverMessageArray == '1';
421
-
422
- const buildOpts = (req, copayerId) => {
423
- const getParam = (param, returnArray = false) => {
424
- // Handle old client params
425
- const value = req.query[`${copayerId}:${param}`] || req.query[copayerId]?.[param];
426
- if (returnArray) {
427
- return Array.isArray(value) ? value : value ? [value] : null;
428
- }
429
- return value ? value : null;
430
- };
431
- const opts = {
432
- includeExtendedInfo,
433
- twoStep,
434
- silentFailure,
435
- includeServerMessages,
436
- tokenAddresses: getParam('tokenAddress', true) as string[] | null,
437
- multisigContractAddress: getParam('multisigContractAddress') as string | null,
438
- network: getParam('network') as string | null
439
- };
440
- return opts;
441
- };
442
-
443
- try {
444
- responses = await Promise.all(
445
- getServerWithMultiAuth(req, res, { silentFailure }).map(promise =>
446
- promise.then(
447
- (server: WalletService) =>
448
- new Promise(resolve => {
449
- const options = buildOpts(req, server.copayerId);
450
- if (options.tokenAddresses) {
451
- // add a null entry to array so we can get the chain balance
452
- options.tokenAddresses.unshift(null);
453
- return async.concat(
454
- options.tokenAddresses,
455
- (tokenAddress, cb) => {
456
- const optsClone = JSON.parse(JSON.stringify(options));
457
- optsClone.tokenAddresses = null;
458
- optsClone.tokenAddress = tokenAddress;
459
- return server.getStatus(optsClone, (err, status) => {
460
- const result = {
461
- walletId: server.walletId,
462
- tokenAddress: optsClone.tokenAddress,
463
- success: true,
464
- ...(err ? { success: false, message: err.message } : {}),
465
- status
466
- };
467
- if (err && err.message)
468
- logger.error(
469
- `An error occurred retrieving wallet status - id: ${server.walletId} - token address: ${optsClone.tokenAddress} - err: ${err.message}`
470
- );
471
- cb(null, [result]); // do not throw error, continue with next wallets
472
- });
473
- },
474
- (err, result) => {
475
- return resolve(result);
476
- }
477
- );
478
- } else {
479
- return server.getStatus(options, (err, status) => {
480
- return resolve([
481
- {
482
- walletId: server.walletId,
483
- tokenAddress: null,
484
- success: true,
485
- ...(err ? { success: false, message: err.message } : {}),
486
- status
487
- }
488
- ]);
489
- });
490
- }
491
- }),
492
- ({ message }) => Promise.resolve({ success: false, error: message })
493
- )
494
- .catch(err => {
495
- if (!silentFailure) {
496
- returnError(err, res, req);
497
- }
498
- })
499
- )
500
- );
501
- } catch (err) {
502
- return returnError(err, res, req);
503
- }
504
-
505
- return res.json(_.flatten(responses));
506
- });
507
-
508
- router.post('/v1/wallets/exist', async (req, res) => {
509
- try {
510
- const copayers = req.body.copayers;
511
- if (!copayers || !Array.isArray(copayers)) {
512
- logger.info('Invalid request to /v1/wallets/exist - copayers should be an array');
513
- return res.json([]);
514
- }
515
-
516
- const storage = WalletService.getStorage();
517
- const existing = await Promise.all<{ copayerId: string; verified: boolean }>(copayers.map(c => new Promise((resolve) => {
518
- storage.fetchCopayerLookup(c.copayerId, (err, copayer) => {
519
- if (err || !copayer) {
520
- return resolve({ copayerId: c.copayerId, verified: false });
521
- }
522
- const verified = copayer.requestPubKeys.some(pubkey => Utils.verifyMessage(c.copayerId, c.signature, pubkey.key));
523
- return resolve({ copayerId: c.copayerId, verified });
524
- });
525
- })));
526
- return res.json(existing.filter(e => e.verified).map(e => e.copayerId));
527
- } catch (err) {
528
- return returnError(err, res, req);
529
- }
530
- });
531
-
532
- router.get('/v1/wallets/:identifier/', (req, res) => {
533
- getServerWithAuth(
534
- req,
535
- res,
536
- {
537
- onlySupportStaff: true
538
- },
539
- server => {
540
- const opts = {
541
- identifier: req.params['identifier'],
542
- walletCheck: ['1', 'true'].includes(req.query['walletCheck'])
543
- };
544
- server.getWalletFromIdentifier(opts, (err, wallet) => {
545
- if (err) return returnError(err, res, req);
546
- if (!wallet) return res.end();
547
-
548
- server.walletId = wallet.id;
549
- const opts = { includeExtendedInfo: false };
550
- if (req.query.includeExtendedInfo == '1') opts.includeExtendedInfo = true;
551
- server.getStatus(opts, (err, status) => {
552
- if (err) return returnError(err, res, req);
553
- res.json(status);
554
- });
555
- });
556
- }
557
- );
558
- });
559
-
560
- router.get('/v1/preferences/', (req, res) => {
561
- getServerWithAuth(req, res, server => {
562
- server.getPreferences({}, (err, preferences) => {
563
- if (err) return returnError(err, res, req);
564
- res.json(preferences);
565
- });
566
- });
567
- });
568
-
569
- router.put('/v1/preferences', (req, res) => {
570
- getServerWithAuth(req, res, server => {
571
- server.savePreferences(req.body, (err, result) => {
572
- if (err) return returnError(err, res, req);
573
- res.json(result);
574
- });
575
- });
576
- });
577
-
578
- // DEPRECATED (do not use cashaddr)
579
- router.get('/v1/txproposals/', (req, res) => {
580
- getServerWithAuth(req, res, server => {
581
- server.getPendingTxs({ noCashAddr: true }, (err, pendings) => {
582
- if (err) return returnError(err, res, req);
583
- res.json(pendings);
584
- });
585
- });
586
- });
587
-
588
- router.get('/v2/txproposals/', (req, res) => {
589
- getServerWithAuth(req, res, server => {
590
- server.getPendingTxs({}, (err, pendings) => {
591
- if (err) return returnError(err, res, req);
592
- res.json(pendings);
593
- });
594
- });
595
- });
596
-
597
- // DEPRECATED
598
- router.post('/v1/txproposals/', (req, res) => {
599
- const err = Errors.UPGRADE_NEEDED;
600
- return returnError(err, res, req);
601
- });
602
-
603
- // DEPRECATED, no cash addr
604
- router.post('/v2/txproposals/', (req, res) => {
605
- getServerWithAuth(req, res, server => {
606
- req.body.noCashAddr = true;
607
- req.body.txpVersion = 3;
608
- server.createTx(req.body, (err, txp) => {
609
- if (err) return returnError(err, res, req);
610
- res.json(txp);
611
- });
612
- });
613
- });
614
-
615
- router.post('/v3/txproposals/', (req, res) => {
616
- getServerWithAuth(req, res, server => {
617
- req.body.txpVersion = 3;
618
- server.createTx(req.body, (err, txp) => {
619
- if (err) return returnError(err, res, req);
620
- res.json(txp);
621
- });
622
- });
623
- });
624
-
625
- // create advertisement
626
- router.post('/v1/advertisements/', (req, res) => {
627
- getServerWithAuth(
628
- req,
629
- res,
630
- {
631
- onlyMarketingStaff: true
632
- },
633
- server => {
634
- server.createAdvert(req.body, (err, advert) => {
635
- if (err) {
636
- return returnError(err, res, req);
637
- }
638
- if (advert) res.json(advert);
639
- });
640
- }
641
- );
642
- });
643
-
644
- router.get('/v1/advertisements/', (req, res) => {
645
- let server: WalletService;
646
- const testing = req.query.testing;
647
-
648
- try {
649
- server = getServer(req, res);
650
- } catch (ex) {
651
- return returnError(ex, res, req);
652
- }
653
-
654
- if (testing) {
655
- server.getTestingAdverts(req.body, (err, ads) => {
656
- if (err) returnError(err, res, req);
657
- res.json(ads);
658
- });
659
- } else {
660
- SetPublicCache(res, 5 * ONE_MINUTE);
661
- server.getAdverts(req.body, (err, ads) => {
662
- if (err) returnError(err, res, req);
663
- res.json(ads);
664
- });
665
- }
666
- });
667
-
668
- router.get('/v1/advertisements/:adId/', (req, res) => {
669
- let server: WalletService;
670
-
671
- try {
672
- server = getServer(req, res);
673
- } catch (ex) {
674
- return returnError(ex, res, req);
675
- }
676
-
677
- const opts = { adId: req.params['adId'] };
678
-
679
- if (req.params['adId']) {
680
- server.getAdvert(opts, (err, ad) => {
681
- if (err) returnError(err, res, req);
682
- res.json(ad);
683
- });
684
- }
685
- });
686
-
687
- router.get('/v1/advertisements/country/:country', (req, res) => {
688
- let server: WalletService;
689
- const country = req.params['country'];
690
-
691
- const opts = { country };
692
-
693
- try {
694
- server = getServer(req, res);
695
- } catch (ex) {
696
- return returnError(ex, res, req);
697
- }
698
-
699
- server.getAdvertsByCountry(opts, (err, ads) => {
700
- if (err) returnError(err, res, req);
701
- res.json(ads);
702
- });
703
- });
704
-
705
- router.post('/v1/advertisements/:adId/activate', (req, res) => {
706
- const opts = { adId: req.params['adId'] };
707
-
708
- getServerWithAuth(
709
- req,
710
- res,
711
- {
712
- onlyMarketingStaff: true
713
- },
714
- server => {
715
- if (req.params['adId']) {
716
- server.activateAdvert(opts, (err, _ad) => {
717
- if (err) returnError(err, res, req);
718
- res.json({ advertisementId: opts.adId, message: 'advert activated' });
719
- });
720
- }
721
- }
722
- );
55
+ registerWalletRoutes(router, {
56
+ createWalletLimiter: createWalletLimiter(opts),
57
+ getServer,
58
+ getServerWithAuth,
59
+ getServerWithMultiAuth,
60
+ logDeprecated,
61
+ returnError
723
62
  });
724
63
 
725
- router.post('/v1/advertisements/:adId/deactivate', (req, res) => {
726
- const opts = { adId: req.params['adId'] };
727
-
728
- getServerWithAuth(
729
- req,
730
- res,
731
- {
732
- onlyMarketingStaff: true
733
- },
734
- server => {
735
- if (req.params['adId']) {
736
- server.deactivateAdvert(opts, (err, _ad) => {
737
- if (err) returnError(err, res, req);
738
- res.json({ advertisementId: opts.adId, message: 'advert deactivated' });
739
- });
740
- }
741
- }
742
- );
64
+ registerTransactionRoutes(router, {
65
+ getServerWithAuth,
66
+ returnError
743
67
  });
744
68
 
745
- router.delete('/v1/advertisements/:adId/', (req, res) => {
746
- getServerWithAuth(
747
- req,
748
- res,
749
- {
750
- onlyMarketingStaff: true
751
- },
752
- server => {
753
- req.body.adId = req.params['adId'];
754
- server.removeAdvert(req.body, (err, removedAd) => {
755
- if (err) returnError(err, res, req);
756
- if (removedAd) {
757
- res.json(removedAd);
758
- }
759
- });
760
- }
761
- );
69
+ registerAdvertisementRoutes(router, {
70
+ getServer,
71
+ getServerWithAuth,
72
+ setPublicCache,
73
+ returnError
762
74
  });
763
75
 
764
76
  /* THIS WAS NEVED ENABLED YET NOW 2020-04-07
@@ -773,1678 +85,51 @@ export class ExpressApp {
773
85
  });
774
86
 
775
87
  */
88
+ const estimateFeeLimiter = createEstimateFeeLimiter(opts);
776
89
 
777
- // DEPRECATED
778
- router.post('/v1/addresses/', (req, res) => {
779
- logDeprecated(req);
780
- getServerWithAuth(req, res, server => {
781
- server.createAddress(
782
- {
783
- ignoreMaxGap: true
784
- },
785
- (err, address) => {
786
- if (err) return returnError(err, res, req);
787
- res.json(address);
788
- }
789
- );
790
- });
791
- });
792
-
793
- // DEPRECATED
794
- router.post('/v2/addresses/', (req, res) => {
795
- logDeprecated(req);
796
- getServerWithAuth(req, res, server => {
797
- server.createAddress(
798
- {
799
- ignoreMaxGap: true
800
- },
801
- (err, address) => {
802
- if (err) return returnError(err, res, req);
803
- res.json(address);
804
- }
805
- );
806
- });
807
- });
808
-
809
- // DEPRECATED (no cashaddr by default)
810
- router.post('/v3/addresses/', (req, res) => {
811
- getServerWithAuth(req, res, server => {
812
- let opts = req.body;
813
- opts = opts || {};
814
- opts.noCashAddr = true;
815
- server.createAddress(opts, (err, address) => {
816
- if (err) return returnError(err, res, req);
817
- res.json(address);
818
- });
819
- });
820
- });
821
-
822
- router.post('/v4/addresses/', (req, res) => {
823
- getServerWithAuth(req, res, server => {
824
- server.createAddress(req.body, (err, address) => {
825
- if (err) return returnError(err, res, req);
826
- res.json(address);
827
- });
828
- });
829
- });
830
-
831
- // DEPRECATED (default noChange=1)
832
- router.get('/v1/addresses/', (req, res) => {
833
- logDeprecated(req);
834
- req.query.noChange = req.query.noChange ?? '1'; // default to no change addresses (backward compatibility)
835
- req.redirectedUrl = req.url;
836
- req.url = '/v2/addresses?' + Object.entries(req.query).map(([key, value]) => `${key}=${value}`).join('&');
837
- router.handle(req, res);
838
- });
839
-
840
- router.get('/v2/addresses/', (req, res) => {
841
- getServerWithAuth(req, res, server => {
842
- const opts: GetAddressesOpts = {};
843
- if (req.query.limit) opts.limit = +req.query.limit;
844
- if (req.query.skip) opts.skip = +req.query.skip;
845
- opts.reverse = req.query.reverse == '1';
846
- if (req.query.addresses) {
847
- opts.addresses = Array.isArray(req.query.addresses)
848
- ? req.query.addresses
849
- : req.query.addresses.split(',');
850
- }
851
- opts.noChange = Utils.castToBool(req.query.noChange);
852
-
853
- server.getAddresses(opts, (err, addresses) => {
854
- if (err) return returnError(err, res, req);
855
- res.json(addresses);
856
- });
857
- });
858
- });
859
-
860
- router.get('/v1/balance/', (req, res) => {
861
- getServerWithAuth(req, res, server => {
862
- const opts: { coin?: string; twoStep?: boolean; tokenAddress?: string; multisigContractAddress?: string } = {};
863
- if (req.query.coin) opts.coin = req.query.coin as string;
864
- if (req.query.twoStep == '1') opts.twoStep = true;
865
- if (req.query.tokenAddress) opts.tokenAddress = req.query.tokenAddress as string;
866
- if (req.query.multisigContractAddress)
867
- opts.multisigContractAddress = req.query.multisigContractAddress as string;
868
-
869
- server.getBalance(opts, (err, balance) => {
870
- if (err) return returnError(err, res, req);
871
- res.json(balance);
872
- });
873
- });
874
- });
875
-
876
- let estimateFeeLimiter;
877
-
878
- if (Defaults.RateLimit.estimateFee && !opts.ignoreRateLimiter) {
879
- logger.info(
880
- 'Limiting estimate fee per IP: %o req/h',
881
- ((Defaults.RateLimit.estimateFee.max / Defaults.RateLimit.estimateFee.windowMs) * 60 * 60 * 1000).toFixed(2)
882
- );
883
- estimateFeeLimiter = new RateLimit(Defaults.RateLimit.estimateFee);
884
- // router.use(/\/v\d+\/wallets\/$/, createWalletLimiter)
885
- } else {
886
- estimateFeeLimiter = (req, res, next) => {
887
- next();
888
- };
889
- }
890
-
891
- // DEPRECATED
892
- router.get('/v1/feelevels/', estimateFeeLimiter, (req, res) => {
893
- SetPublicCache(res, 1 * ONE_MINUTE);
894
- logDeprecated(req);
895
- const opts: { network?: string } = {};
896
- if (req.query.network) opts.network = req.query.network as string;
897
- let server: WalletService;
898
- try {
899
- server = getServer(req, res);
900
- } catch (ex) {
901
- return returnError(ex, res, req);
902
- }
903
- server.getFeeLevels(opts, (err, feeLevels) => {
904
- if (err) return returnError(err, res, req);
905
- _.each(feeLevels, feeLevel => {
906
- feeLevel.feePerKB = feeLevel.feePerKb;
907
- delete feeLevel.feePerKb;
908
- });
909
- res.json(feeLevels);
910
- });
911
- });
912
-
913
- router.get('/v2/feelevels/', (req, res) => {
914
- const opts: { coin?: string; network?: string; chain?: string } = {};
915
- SetPublicCache(res, 1 * ONE_MINUTE);
916
-
917
- if (req.query.coin) opts.coin = req.query.coin as string;
918
- if (req.query.chain || req.query.coin) opts.chain = (req.query.chain || req.query.coin) as string;
919
- if (req.query.network) opts.network = req.query.network as string;
920
-
921
- let server: WalletService;
922
- try {
923
- server = getServer(req, res);
924
- } catch (ex) {
925
- return returnError(ex, res, req);
926
- }
927
- server.getFeeLevels(opts, (err, feeLevels) => {
928
- if (err) return returnError(err, res, req);
929
- res.json(feeLevels);
930
- });
931
- });
932
-
933
- router.post('/v3/estimateGas/', (req, res) => {
934
- getServerWithAuth(req, res, async server => {
935
- try {
936
- const gasLimit = await server.estimateGas(req.body);
937
- res.json(gasLimit);
938
- } catch (err) {
939
- returnError(err, res, req);
940
- }
941
- });
942
- });
943
-
944
- // DEPRECATED
945
- router.post('/v1/ethmultisig/', (req, res) => {
946
- getServerWithAuth(req, res, async server => {
947
- try {
948
- const multisigContractInstantiationInfo = await server.getMultisigContractInstantiationInfo(req.body);
949
- res.json(multisigContractInstantiationInfo);
950
- } catch (err) {
951
- returnError(err, res, req);
952
- }
953
- });
954
- });
955
-
956
- // DEPRECATED
957
- router.post('/v1/ethmultisig/info', (req, res) => {
958
- getServerWithAuth(req, res, async server => {
959
- try {
960
- const multisigContractInfo = await server.getMultisigContractInfo(req.body);
961
- res.json(multisigContractInfo);
962
- } catch (err) {
963
- returnError(err, res, req);
964
- }
965
- });
966
- });
967
-
968
- router.post('/v1/multisig/', (req, res) => {
969
- getServerWithAuth(req, res, async server => {
970
- try {
971
- const multisigContractInstantiationInfo = await server.getMultisigContractInstantiationInfo(req.body);
972
- res.json(multisigContractInstantiationInfo);
973
- } catch (err) {
974
- returnError(err, res, req);
975
- }
976
- });
977
- });
978
-
979
- router.post('/v1/multisig/info', (req, res) => {
980
- getServerWithAuth(req, res, async server => {
981
- try {
982
- const multisigContractInfo = await server.getMultisigContractInfo(req.body);
983
- res.json(multisigContractInfo);
984
- } catch (err) {
985
- returnError(err, res, req);
986
- }
987
- });
988
- });
989
-
990
- router.post('/v1/token/info', (req, res) => {
991
- getServerWithAuth(req, res, async server => {
992
- try {
993
- const tokenContractInfo = await server.getTokenContractInfo(req.body);
994
- res.json(tokenContractInfo);
995
- } catch (err) {
996
- returnError(err, res, req);
997
- }
998
- });
999
- });
1000
-
1001
- router.post('/v1/token/allowance', async (req, res) => {
1002
- try {
1003
- const server = getServer(req, res);
1004
- const allowance = await server.getTokenAllowance(req.body);
1005
- res.json(allowance);
1006
- } catch (err) {
1007
- returnError(err, res, req);
1008
- }
1009
- });
1010
-
1011
- router.get('/v1/sendmaxinfo/', (req, res) => {
1012
- getServerWithAuth(req, res, server => {
1013
- const q = req.query;
1014
- const opts: {
1015
- feePerKb?: number;
1016
- feeLevel?: number;
1017
- returnInputs?: boolean;
1018
- excludeUnconfirmedUtxos?: boolean;
1019
- } = {};
1020
- if (q.feePerKb) opts.feePerKb = +q.feePerKb;
1021
- if (q.feeLevel) opts.feeLevel = Number(q.feeLevel);
1022
- if (q.excludeUnconfirmedUtxos == '1') opts.excludeUnconfirmedUtxos = true;
1023
- if (q.returnInputs == '1') opts.returnInputs = true;
1024
- server.getSendMaxInfo(opts, (err, info) => {
1025
- if (err) return returnError(err, res, req);
1026
- res.json(info);
1027
- });
1028
- });
1029
- });
1030
-
1031
- router.get('/v1/utxos/', (req, res) => {
1032
- const opts: { addresses?: string[] } = {};
1033
- const addresses = req.query.addresses;
1034
- if (addresses && _.isString(addresses)) opts.addresses = (req.query.addresses as string).split(',');
1035
- getServerWithAuth(req, res, server => {
1036
- server.getUtxos(opts, (err, utxos) => {
1037
- if (err) return returnError(err, res, req);
1038
- res.json(utxos);
1039
- });
1040
- });
90
+ registerBlockchainRoutes(router, {
91
+ estimateFeeLimiter,
92
+ getServer,
93
+ getServerWithAuth,
94
+ logDeprecated,
95
+ setPublicCache,
96
+ returnError
1041
97
  });
1042
98
 
1043
- router.get('/v1/txcoins/', (req, res) => {
1044
- const txId = req.query.txId;
1045
- getServerWithAuth(req, res, server => {
1046
- server.getCoinsForTx({ txId }, (err, coins) => {
1047
- if (err) return returnError(err, res, req);
1048
- res.json(coins);
1049
- });
1050
- });
99
+ registerWalletDataRoutes(router, {
100
+ getServerWithAuth,
101
+ logDeprecated,
102
+ returnError
1051
103
  });
1052
104
 
1053
- router.post('/v1/broadcast_raw/', (req, res) => {
1054
- getServerWithAuth(req, res, server => {
1055
- server.broadcastRawTx(req.body, (err, txid) => {
1056
- if (err) return returnError(err, res, req);
1057
- res.json(txid);
1058
- res.end();
1059
- });
1060
- });
105
+ registerNotificationRoutes(router, {
106
+ getServerWithAuth,
107
+ logDeprecated,
108
+ returnError
1061
109
  });
1062
110
 
1063
- // DEPRECATEED
1064
- router.post('/v1/txproposals/:id/signatures/', (req, res) => {
1065
- getServerWithAuth(req, res, server => {
1066
- req.body.maxTxpVersion = 3;
1067
- req.body.txProposalId = req.params['id'];
1068
- server.signTx(req.body, (err, txp) => {
1069
- if (err) return returnError(err, res, req);
1070
- res.json(txp);
1071
- res.end();
1072
- });
1073
- });
111
+ registerMaintenanceRoutes(router, {
112
+ getServerWithAuth,
113
+ setPublicCache,
114
+ returnError
1074
115
  });
1075
116
 
1076
- // We created a new endpoint that support BCH schnorr signatues
1077
- // so we can safely throw the error "UPGRADE NEEDED" if an old
1078
- // client tries to post ECDSA signatures to a Schnorr TXP.
1079
- // (using the old /v1/txproposal method): if (txp.signingMethod === 'schnorr' && !opts.supportBchSchnorr) return cb(Errors.UPGRADE_NEEDED);
1080
- router.post('/v2/txproposals/:id/signatures/', (req, res) => {
1081
- getServerWithAuth(req, res, server => {
1082
- req.body.txProposalId = req.params['id'];
1083
- req.body.maxTxpVersion = 3;
1084
- req.body.supportBchSchnorr = true;
1085
- server.signTx(req.body, (err, txp) => {
1086
- if (err) return returnError(err, res, req);
1087
- res.json(txp);
1088
- res.end();
1089
- });
1090
- });
117
+ registerServiceRoutes(router, {
118
+ getServer,
119
+ getServerWithAuth,
120
+ setPublicCache,
121
+ returnError
1091
122
  });
1092
123
 
1093
- /* THIS WAS NEVED ENABLED YET NOW 2020-04-07 (see above)
1094
- router.post('/v3/txproposals/:id/signatures/', (req, res) => {
1095
- getServerWithAuth(req, res, server => {
1096
- req.body.txProposalId = req.params['id'];
1097
- req.body.maxTxpVersion = 4;
1098
- server.signTx(req.body, (err, txp) => {
1099
- if (err) return returnError(err, res, req);
1100
- res.json(txp);
1101
- res.end();
1102
- });
1103
- });
1104
- });
1105
- */
1106
-
1107
- router.post('/v1/txproposals/:id/prepare/', (req, res) => {
1108
- getServerWithAuth(req, res, server => {
1109
- req.body.txProposalId = req.params['id'];
1110
- server.prepareTx(req.body, (err, txp) => {
1111
- if (err) return returnError(err, res, req);
1112
- res.json(txp);
1113
- res.end();
1114
- });
1115
- });
1116
- });
1117
-
1118
-
1119
-
1120
- //
1121
- router.post('/v1/txproposals/:id/publish/', (req, res) => {
1122
- getServerWithAuth(req, res, server => {
1123
- req.body.txProposalId = req.params['id'];
1124
- req.body.noCashAddr = true;
1125
- server.publishTx(req.body, (err, txp) => {
1126
- if (err) return returnError(err, res, req);
1127
- res.json(txp);
1128
- res.end();
1129
- });
1130
- });
1131
- });
1132
-
1133
- router.post('/v2/txproposals/:id/publish/', (req, res) => {
1134
- getServerWithAuth(req, res, server => {
1135
- req.body.txProposalId = req.params['id'];
1136
- server.publishTx(req.body, (err, txp) => {
1137
- if (err) return returnError(err, res, req);
1138
- res.json(txp);
1139
- res.end();
1140
- });
1141
- });
1142
- });
1143
-
1144
- // TODO Check HTTP verb and URL name
1145
- router.post('/v1/txproposals/:id/broadcast/', (req, res) => {
1146
- getServerWithAuth(req, res, server => {
1147
- req.body.txProposalId = req.params['id'];
1148
- server.broadcastTx(req.body, (err, txp) => {
1149
- if (err) return returnError(err, res, req);
1150
- res.json(txp);
1151
- res.end();
1152
- });
1153
- });
1154
- });
1155
-
1156
- router.post('/v1/txproposals/:id/rejections', (req, res) => {
1157
- getServerWithAuth(req, res, server => {
1158
- req.body.txProposalId = req.params['id'];
1159
- server.rejectTx(req.body, (err, txp) => {
1160
- if (err) return returnError(err, res, req);
1161
- res.json(txp);
1162
- res.end();
1163
- });
1164
- });
1165
- });
1166
-
1167
- router.delete('/v1/txproposals/:id/', (req, res) => {
1168
- getServerWithAuth(req, res, server => {
1169
- req.body.txProposalId = req.params['id'];
1170
- server.removePendingTx(req.body, err => {
1171
- if (err) return returnError(err, res, req);
1172
- res.json({
1173
- success: true
1174
- });
1175
- res.end();
1176
- });
1177
- });
1178
- });
1179
-
1180
- router.get('/v1/txproposals/:id/', (req, res) => {
1181
- getServerWithAuth(req, res, server => {
1182
- req.body.txProposalId = req.params['id'];
1183
- server.getTx(req.body, (err, tx) => {
1184
- if (err) return returnError(err, res, req);
1185
- res.json(tx);
1186
- res.end();
1187
- });
1188
- });
1189
- });
1190
-
1191
- router.get('/v1/txproposalsbyhash/:id/', (req, res) => {
1192
- getServerWithAuth(req, res, server => {
1193
- req.body.txid = req.params['id'];
1194
- server.getTxByHash(req.body, (err, tx) => {
1195
- if (err) return returnError(err, res, req);
1196
- res.json(tx);
1197
- res.end();
1198
- });
1199
- });
1200
- });
1201
-
1202
- router.get('/v1/txhistory/', (req, res) => {
1203
- getServerWithAuth(req, res, server => {
1204
- const opts: {
1205
- skip?: number;
1206
- limit?: number;
1207
- reverse?: boolean;
1208
- includeExtendedInfo?: boolean;
1209
- tokenAddress?: string;
1210
- multisigContractAddress?: string;
1211
- } = {};
1212
- if (req.query.skip) opts.skip = +req.query.skip;
1213
- if (req.query.limit) opts.limit = +req.query.limit;
1214
- if (req.query.reverse == '1') opts.reverse = true;
1215
- if (req.query.tokenAddress) opts.tokenAddress = req.query.tokenAddress as string;
1216
- if (req.query.multisigContractAddress)
1217
- opts.multisigContractAddress = req.query.multisigContractAddress as string;
1218
- if (req.query.includeExtendedInfo == '1') opts.includeExtendedInfo = true;
1219
-
1220
- server.getTxHistory(opts, (err, txs) => {
1221
- if (err) return returnError(err, res, req);
1222
- res.json(txs);
1223
- res.end();
1224
- });
1225
- });
1226
- });
1227
-
1228
- router.post('/v1/addresses/scan/', (req, res) => {
1229
- getServerWithAuth(req, res, server => {
1230
- req.body = req.body || {};
1231
- req.body.startIdx = server.copayerIsSupportStaff ? Number(req.body.startIdx) : null;
1232
- server.startScan(req.body, (err, started) => {
1233
- if (err) return returnError(err, res, req);
1234
- res.json(started);
1235
- res.end();
1236
- });
1237
- });
1238
- });
1239
-
1240
- // Retrive stats DO NOT UPDATE THEM
1241
- // To update them run /updatestats
1242
- router.get('/v1/stats/', (req, res) => {
1243
- SetPublicCache(res, 1 * ONE_MINUTE);
1244
- const opts: {
1245
- network?: string;
1246
- coin?: string;
1247
- from?: string;
1248
- to?: string;
1249
- } = {};
1250
-
1251
- if (req.query.network) opts.network = req.query.network as string;
1252
- if (req.query.coin) opts.coin = req.query.coin as string;
1253
- if (req.query.from) opts.from = req.query.from as string;
1254
- if (req.query.to) opts.to = req.query.to as string;
1255
-
1256
- const stats = new Stats(opts);
1257
- stats.run((err, data) => {
1258
- if (err) return returnError(err, res, req);
1259
- res.json(data);
1260
- res.end();
1261
- });
1262
- });
1263
-
1264
- router.get('/v1/version/', (req, res) => {
1265
- SetPublicCache(res, 1 * ONE_MINUTE);
1266
- res.json({
1267
- serviceVersion: WalletService.getServiceVersion()
1268
- });
1269
- res.end();
1270
- });
1271
-
1272
- router.post('/v1/login/', (req, res) => {
1273
- getServerWithAuth(req, res, server => {
1274
- server.login({}, (err, session) => {
1275
- if (err) return returnError(err, res, req);
1276
- res.json(session);
1277
- });
1278
- });
1279
- });
1280
-
1281
- router.post('/v1/logout/', (req, res) => {
1282
- getServerWithAuth(req, res, server => {
1283
- server.logout({}, err => {
1284
- if (err) return returnError(err, res, req);
1285
- res.end();
1286
- });
1287
- });
1288
- });
1289
-
1290
- router.get('/v1/notifications/', (req, res) => {
1291
- getServerWithAuth(
1292
- req,
1293
- res,
1294
- {
1295
- allowSession: true
1296
- },
1297
- server => {
1298
- const timeSpan = req.query.timeSpan
1299
- ? Math.min(+req.query.timeSpan || 0, Defaults.MAX_NOTIFICATIONS_TIMESPAN)
1300
- : Defaults.NOTIFICATIONS_TIMESPAN;
1301
- const opts = {
1302
- minTs: +Date.now() - timeSpan * 1000,
1303
- notificationId: req.query.notificationId
1304
- };
1305
-
1306
- server.getNotifications(opts, (err, notifications) => {
1307
- if (err) return returnError(err, res, req);
1308
- res.json(notifications);
1309
- });
1310
- }
1311
- );
1312
- });
1313
-
1314
- router.get('/v1/txnotes/:txid', (req, res) => {
1315
- getServerWithAuth(req, res, server => {
1316
- const opts = {
1317
- txid: req.params['txid']
1318
- };
1319
- server.getTxNote(opts, (err, note) => {
1320
- if (err) return returnError(err, res, req);
1321
- res.json(note);
1322
- });
1323
- });
1324
- });
1325
-
1326
- router.put('/v1/txnotes/:txid/', (req, res) => {
1327
- req.body.txid = req.params['txid'];
1328
- getServerWithAuth(req, res, server => {
1329
- server.editTxNote(req.body, (err, note) => {
1330
- if (err) return returnError(err, res, req);
1331
- res.json(note);
1332
- });
1333
- });
1334
- });
1335
-
1336
- router.get('/v1/txnotes/', (req, res) => {
1337
- getServerWithAuth(req, res, server => {
1338
- const opts: { minTs?: number } = {};
1339
- if (req.query.minTs && _.isNumber(+req.query.minTs)) {
1340
- opts.minTs = +req.query.minTs;
1341
- }
1342
- server.getTxNotes(opts, (err, notes) => {
1343
- if (err) return returnError(err, res, req);
1344
- res.json(notes);
1345
- });
1346
- });
1347
- });
1348
-
1349
- router.get('/v1/nonce/:address', (req, res) => {
1350
- getServerWithAuth(req, res, async server => {
1351
- const opts = {
1352
- coin: req.query.coin || 'eth',
1353
- chain: req.query.chain,
1354
- network: req.query.network || 'livenet',
1355
- address: req.params['address']
1356
- };
1357
- try {
1358
- const nonce = await server.getNonce(opts);
1359
- res.json(nonce);
1360
- } catch (err) {
1361
- returnError(err, res, req);
1362
- }
1363
- });
1364
- });
1365
-
1366
- router.post('/v1/clearcache/', (req, res) => {
1367
- getServerWithAuth(req, res, server => {
1368
- const opts = req.query;
1369
- server.clearWalletCache(opts).then(val => {
1370
- if (val) {
1371
- res.sendStatus(200);
1372
- } else {
1373
- res.sendStatus(500);
1374
- }
1375
- });
1376
- });
1377
- });
1378
-
1379
- router.get('/v1/fiatrates/:code/', (req, res) => {
1380
- SetPublicCache(res, 5 * ONE_MINUTE);
1381
- let server: WalletService;
1382
- const opts = {
1383
- code: req.params['code'],
1384
- coin: req.query.coin || 'btc',
1385
- ts: req.query.ts ? +req.query.ts : null
1386
- };
1387
- try {
1388
- server = getServer(req, res);
1389
- } catch (ex) {
1390
- return returnError(ex, res, req);
1391
- }
1392
- server.getFiatRate(opts, (err, rates) => {
1393
- if (err) return returnError(err, res, req);
1394
- res.json(rates);
1395
- });
1396
- });
1397
-
1398
- router.get('/v2/fiatrates/:code/', (req, res) => {
1399
- SetPublicCache(res, 5 * ONE_MINUTE);
1400
- let server: WalletService;
1401
- const opts = {
1402
- code: req.params['code'],
1403
- ts: req.query.ts ? +req.query.ts : null
1404
- };
1405
- try {
1406
- server = getServer(req, res);
1407
- } catch (ex) {
1408
- return returnError(ex, res, req);
1409
- }
1410
- server.getHistoricalRates(opts, (err, rates) => {
1411
- if (err) return returnError(err, res, req);
1412
- res.json(rates);
1413
- });
1414
- });
1415
-
1416
- router.get('/v3/fiatrates/', (req, res) => {
1417
- SetPublicCache(res, 5 * ONE_MINUTE);
1418
- let server: WalletService;
1419
- const opts = {
1420
- code: req.query.code || null,
1421
- ts: req.query.ts ? +req.query.ts : null
1422
- };
1423
- try {
1424
- server = getServer(req, res);
1425
- } catch (ex) {
1426
- return returnError(ex, res, req);
1427
- }
1428
- server.getFiatRates(opts, (err, rates) => {
1429
- if (err) return returnError(err, res, req);
1430
- res.json(rates);
1431
- });
1432
- });
1433
-
1434
- router.get('/v3/fiatrates/:coin/', (req, res) => {
1435
- SetPublicCache(res, 5 * ONE_MINUTE);
1436
- let server: WalletService;
1437
- const opts = {
1438
- coin: req.params['coin'],
1439
- code: req.query.code || null,
1440
- ts: req.query.ts ? +req.query.ts : null
1441
- };
1442
- try {
1443
- server = getServer(req, res);
1444
- } catch (ex) {
1445
- return returnError(ex, res, req);
1446
- }
1447
- server.getFiatRatesByCoin(opts, (err, rates) => {
1448
- if (err) return returnError(err, res, req);
1449
- res.json(rates);
1450
- });
1451
- });
1452
-
1453
- router.get('/v4/fiatrates/:code/', (req, res) => {
1454
- SetPublicCache(res, 5 * ONE_MINUTE);
1455
- let server: WalletService;
1456
- try {
1457
- server = getServer(req, res);
1458
- } catch (ex) {
1459
- return returnError(ex, res, req);
1460
- }
1461
- server.externalServices.coinGecko.coinGeckoGetFiatRates(req)
1462
- .then(response => {
1463
- res.json(response);
1464
- })
1465
- .catch(err => {
1466
- return returnError(err ?? 'unknown', res, req);
1467
- });
1468
- });
1469
-
1470
- // DEPRECATED
1471
- router.post('/v1/pushnotifications/subscriptions/', (req, res) => {
1472
- getServerWithAuth(req, res, server => {
1473
- server.pushNotificationsSubscribe(req.body, (err, response) => {
1474
- if (err) return returnError(err, res, req);
1475
- res.json(response);
1476
- });
1477
- });
1478
- });
1479
-
1480
- router.post('/v2/pushnotifications/subscriptions/', (req, res) => {
1481
- getServerWithAuth(req, res, server => {
1482
- server.pushNotificationsBrazeSubscribe(req.body, (err, response) => {
1483
- if (err) return returnError(err, res, req);
1484
- res.json(response);
1485
- });
1486
- });
1487
- });
1488
-
1489
- // DEPRECATED
1490
- router.delete('/v1/pushnotifications/subscriptions/', (req, res) => {
1491
- logDeprecated(req);
1492
- getServerWithAuth(req, res, server => {
1493
- server.pushNotificationsUnsubscribe(
1494
- {
1495
- token: 'dummy'
1496
- },
1497
- (err, response) => {
1498
- if (err) return returnError(err, res, req);
1499
- res.json(response);
1500
- }
1501
- );
1502
- });
1503
- });
1504
-
1505
- // DEPRECATED
1506
- router.delete('/v2/pushnotifications/subscriptions/:token', (req, res) => {
1507
- const opts = {
1508
- token: req.params['token']
1509
- };
1510
- getServerWithAuth(req, res, server => {
1511
- server.pushNotificationsUnsubscribe(opts, (err, response) => {
1512
- if (err) return returnError(err, res, req);
1513
- res.json(response);
1514
- });
1515
- });
1516
- });
1517
-
1518
- router.delete('/v3/pushnotifications/subscriptions/:externalUserId', (req, res) => {
1519
- const opts = {
1520
- externalUserId: req.params['externalUserId']
1521
- };
1522
- getServerWithAuth(req, res, server => {
1523
- server.pushNotificationsBrazeUnsubscribe(opts, (err, response) => {
1524
- if (err) return returnError(err, res, req);
1525
- res.json(response);
1526
- });
1527
- });
1528
- });
1529
-
1530
- router.post('/v1/txconfirmations/', (req, res) => {
1531
- getServerWithAuth(req, res, server => {
1532
- server.txConfirmationSubscribe(req.body, (err, response) => {
1533
- if (err) return returnError(err, res, req);
1534
- res.json(response);
1535
- });
1536
- });
1537
- });
1538
-
1539
- router.delete('/v1/txconfirmations/:txid', (req, res) => {
1540
- const opts = {
1541
- txid: req.params['txid']
1542
- };
1543
- getServerWithAuth(req, res, server => {
1544
- server.txConfirmationUnsubscribe(opts, (err, response) => {
1545
- if (err) return returnError(err, res, req);
1546
- res.json(response);
1547
- });
1548
- });
1549
- });
1550
-
1551
- router.get('/v1/services', (req, res) => {
1552
- let server: WalletService;
1553
- try {
1554
- server = getServer(req, res);
1555
- } catch (ex) {
1556
- return returnError(ex, res, req);
1557
- }
1558
- const opts = req.query;
1559
- server.getServicesData(opts, (err, response) => {
1560
- if (err) return returnError(err, res, req);
1561
- res.json(response);
1562
- });
1563
- });
1564
-
1565
- router.post('/v1/service/checkAvailability', (req, res) => {
1566
- let server: WalletService, response;
1567
- try {
1568
- server = getServer(req, res);
1569
- response = server.checkServiceAvailability(req);
1570
- return res.json(response);
1571
- } catch (ex) {
1572
- return returnError(ex, res, req);
1573
- }
1574
- });
1575
-
1576
- router.post('/v1/service/banxa/getCoins', async (req, res) => {
1577
- let server: WalletService, response;
1578
- try {
1579
- server = getServer(req, res);
1580
- response = await server.externalServices.banxa.banxaGetCoins(req);
1581
- return res.json(response);
1582
- } catch (ex) {
1583
- return returnError(ex, res, req);
1584
- }
1585
- });
1586
-
1587
- router.post('/v1/service/banxa/paymentMethods', async (req, res) => {
1588
- let server: WalletService, response;
1589
- try {
1590
- server = getServer(req, res);
1591
- response = await server.externalServices.banxa.banxaGetPaymentMethods(req);
1592
- return res.json(response);
1593
- } catch (ex) {
1594
- return returnError(ex, res, req);
1595
- }
1596
- });
1597
-
1598
- router.post('/v1/service/banxa/quote', (req, res) => {
1599
- getServerWithAuth(req, res, async server => {
1600
- let response;
1601
- try {
1602
- response = await server.externalServices.banxa.banxaGetQuote(req);
1603
- return res.json(response);
1604
- } catch (ex) {
1605
- return returnError(ex, res, req);
1606
- }
1607
- });
1608
- });
1609
-
1610
- router.post('/v1/service/banxa/createOrder', (req, res) => {
1611
- getServerWithAuth(req, res, async server => {
1612
- let response;
1613
- try {
1614
- response = await server.externalServices.banxa.banxaCreateOrder(req);
1615
- return res.json(response);
1616
- } catch (ex) {
1617
- return returnError(ex, res, req);
1618
- }
1619
- });
1620
- });
1621
-
1622
- router.post('/v1/service/banxa/getOrder', async (req, res) => {
1623
- let server: WalletService, response;
1624
- try {
1625
- server = getServer(req, res);
1626
- response = await server.externalServices.banxa.banxaGetOrder(req);
1627
- return res.json(response);
1628
- } catch (ex) {
1629
- return returnError(ex, res, req);
1630
- }
1631
- });
1632
-
1633
- router.post('/v1/service/moonpay/getCurrencies', async (req, res) => {
1634
- let server: WalletService, response;
1635
- try {
1636
- server = getServer(req, res);
1637
- response = await server.externalServices.moonpay.moonpayGetCurrencies(req);
1638
- return res.json(response);
1639
- } catch (ex) {
1640
- return returnError(ex, res, req);
1641
- }
1642
- });
1643
-
1644
- router.post('/v1/service/moonpay/quote', (req, res) => {
1645
- getServerWithAuth(req, res, async server => {
1646
- let response;
1647
- try {
1648
- response = await server.externalServices.moonpay.moonpayGetQuote(req);
1649
- return res.json(response);
1650
- } catch (ex) {
1651
- return returnError(ex, res, req);
1652
- }
1653
- });
1654
- });
1655
-
1656
- router.post('/v1/service/moonpay/sellQuote', (req, res) => {
1657
- getServerWithAuth(req, res, async server => {
1658
- let response;
1659
- try {
1660
- response = await server.externalServices.moonpay.moonpayGetSellQuote(req);
1661
- return res.json(response);
1662
- } catch (ex) {
1663
- return returnError(ex, res, req);
1664
- }
1665
- });
1666
- });
1667
-
1668
- router.post('/v1/service/moonpay/currencyLimits', async (req, res) => {
1669
- let server: WalletService, response;
1670
- try {
1671
- server = getServer(req, res);
1672
- response = await server.externalServices.moonpay.moonpayGetCurrencyLimits(req);
1673
- return res.json(response);
1674
- } catch (ex) {
1675
- return returnError(ex, res, req);
1676
- }
1677
- });
1678
-
1679
- router.post('/v1/service/moonpay/signedPaymentUrl', (req, res) => {
1680
- getServerWithAuth(req, res, server => {
1681
- let response;
1682
- try {
1683
- response = server.externalServices.moonpay.moonpayGetSignedPaymentUrl(req);
1684
- return res.json(response);
1685
- } catch (ex) {
1686
- return returnError(ex, res, req);
1687
- }
1688
- });
1689
- });
1690
-
1691
- router.post('/v1/service/moonpay/sellSignedPaymentUrl', (req, res) => {
1692
- getServerWithAuth(req, res, async server => {
1693
- let response;
1694
- try {
1695
- response = await server.externalServices.moonpay.moonpayGetSellSignedPaymentUrl(req);
1696
- return res.json(response);
1697
- } catch (ex) {
1698
- return returnError(ex, res, req);
1699
- }
1700
- });
1701
- });
1702
-
1703
- router.post('/v1/service/moonpay/transactionDetails', async (req, res) => {
1704
- let server: WalletService, response;
1705
- try {
1706
- server = getServer(req, res);
1707
- response = await server.externalServices.moonpay.moonpayGetTransactionDetails(req);
1708
- return res.json(response);
1709
- } catch (ex) {
1710
- return returnError(ex, res, req);
1711
- }
1712
- });
1713
-
1714
- router.post('/v1/service/moonpay/sellTransactionDetails', async (req, res) => {
1715
- let server: WalletService, response;
1716
- try {
1717
- server = getServer(req, res);
1718
- response = await server.externalServices.moonpay.moonpayGetSellTransactionDetails(req);
1719
- return res.json(response);
1720
- } catch (ex) {
1721
- return returnError(ex, res, req);
1722
- }
1723
- });
1724
-
1725
- router.post('/v1/service/moonpay/cancelSellTransaction', (req, res) => {
1726
- getServerWithAuth(req, res, async server => {
1727
- let response;
1728
- try {
1729
- response = await server.externalServices.moonpay.moonpayCancelSellTransaction(req);
1730
- return res.json(response);
1731
- } catch (ex) {
1732
- return returnError(ex, res, req);
1733
- }
1734
- });
1735
- });
1736
-
1737
- router.post('/v1/service/moonpay/accountDetails', async (req, res) => {
1738
- let server: WalletService, response;
1739
- try {
1740
- server = getServer(req, res);
1741
- response = await server.externalServices.moonpay.moonpayGetAccountDetails(req);
1742
- return res.json(response);
1743
- } catch (ex) {
1744
- return returnError(ex, res, req);
1745
- }
1746
- });
1747
-
1748
- router.post('/v1/service/ramp/quote', (req, res) => {
1749
- getServerWithAuth(req, res, async server => {
1750
- let response;
1751
- try {
1752
- response = await server.externalServices.ramp.rampGetQuote(req);
1753
- return res.json(response);
1754
- } catch (ex) {
1755
- return returnError(ex, res, req);
1756
- }
1757
- });
1758
- });
1759
-
1760
- router.post('/v1/service/ramp/sellQuote', (req, res) => {
1761
- getServerWithAuth(req, res, async server => {
1762
- let response;
1763
- try {
1764
- response = await server.externalServices.ramp.rampGetSellQuote(req);
1765
- return res.json(response);
1766
- } catch (ex) {
1767
- return returnError(ex, res, req);
1768
- }
1769
- });
1770
- });
1771
-
1772
- router.post('/v1/service/ramp/signedPaymentUrl', (req, res) => {
1773
- getServerWithAuth(req, res, async server => {
1774
- let response;
1775
- try {
1776
- response = await server.externalServices.ramp.rampGetSignedPaymentUrl(req);
1777
- return res.json(response);
1778
- } catch (ex) {
1779
- return returnError(ex, res, req);
1780
- }
1781
- });
1782
- });
1783
-
1784
- router.post('/v1/service/ramp/assets', async (req, res) => {
1785
- let server: WalletService, response;
1786
- try {
1787
- server = getServer(req, res);
1788
- response = await server.externalServices.ramp.rampGetAssets(req);
1789
- return res.json(response);
1790
- } catch (ex) {
1791
- return returnError(ex, res, req);
1792
- }
1793
- });
1794
-
1795
- router.post('/v1/service/ramp/sellTransactionDetails', async (req, res) => {
1796
- let server, response;
1797
- try {
1798
- server = getServer(req, res);
1799
- response = await server.externalServices.ramp.rampGetSellTransactionDetails(req);
1800
- return res.json(response);
1801
- } catch (ex) {
1802
- return returnError(ex, res, req);
1803
- }
1804
- });
1805
-
1806
- router.post('/v1/service/sardine/quote', (req, res) => {
1807
- getServerWithAuth(req, res, server => {
1808
- server.externalServices.sardine
1809
- .sardineGetQuote(req)
1810
- .then(response => {
1811
- res.json(response);
1812
- })
1813
- .catch(err => {
1814
- return returnError(err ?? 'unknown', res, req);
1815
- });
1816
- });
1817
- });
1818
-
1819
- router.post('/v1/service/sardine/getToken', (req, res) => {
1820
- getServerWithAuth(req, res, server => {
1821
- server.externalServices.sardine
1822
- .sardineGetToken(req)
1823
- .then(response => {
1824
- res.json(response);
1825
- })
1826
- .catch(err => {
1827
- return returnError(err ?? 'unknown', res, req);
1828
- });
1829
- });
1830
- });
1831
-
1832
- router.post('/v1/service/sardine/getSupportedTokens', async (req, res) => {
1833
- let server: WalletService, response;
1834
- try {
1835
- server = getServer(req, res);
1836
- response = await server.externalServices.sardine.sardineGetSupportedTokens(req);
1837
- return res.json(response);
1838
- } catch (ex) {
1839
- return returnError(ex, res, req);
1840
- }
1841
- });
1842
-
1843
- router.post('/v1/service/sardine/currencyLimits', (req, res) => {
1844
- let server: WalletService;
1845
- try {
1846
- server = getServer(req, res);
1847
- } catch (ex) {
1848
- return returnError(ex, res, req);
1849
- }
1850
-
1851
- server.externalServices.sardine
1852
- .sardineGetCurrencyLimits(req)
1853
- .then(response => {
1854
- res.json(response);
1855
- })
1856
- .catch(err => {
1857
- return returnError(err ?? 'unknown', res, req);
1858
- });
1859
- });
1860
-
1861
- router.post('/v1/service/sardine/ordersDetails', (req, res) => {
1862
- let server: WalletService;
1863
- try {
1864
- server = getServer(req, res);
1865
- } catch (ex) {
1866
- return returnError(ex, res, req);
1867
- }
1868
-
1869
- server.externalServices.sardine
1870
- .sardineGetOrdersDetails(req)
1871
- .then(response => {
1872
- res.json(response);
1873
- })
1874
- .catch(err => {
1875
- return returnError(err ?? 'unknown', res, req);
1876
- });
1877
- });
1878
-
1879
- router.post('/v1/service/simplex/getCurrencies', (req, res) => {
1880
- let server: WalletService;
1881
- try {
1882
- server = getServer(req, res);
1883
- } catch (ex) {
1884
- return returnError(ex, res, req);
1885
- }
1886
-
1887
- server.externalServices.simplex
1888
- .simplexGetCurrencies(req)
1889
- .then(response => {
1890
- res.json(response);
1891
- })
1892
- .catch(err => {
1893
- return returnError(err ?? 'unknown', res, req);
1894
- });
1895
- });
1896
-
1897
- router.post('/v1/service/simplex/quote', (req, res) => {
1898
- getServerWithAuth(req, res, server => {
1899
- server.externalServices.simplex
1900
- .simplexGetQuote(req)
1901
- .then(response => {
1902
- res.json(response);
1903
- })
1904
- .catch(err => {
1905
- return returnError(err ?? 'unknown', res, req);
1906
- });
1907
- });
1908
- });
1909
-
1910
- router.post('/v1/service/simplex/sellQuote', (req, res) => {
1911
- getServerWithAuth(req, res, server => {
1912
- server.externalServices.simplex
1913
- .simplexGetSellQuote(req)
1914
- .then(response => {
1915
- res.json(response);
1916
- })
1917
- .catch(err => {
1918
- return returnError(err ?? 'unknown', res, req);
1919
- });
1920
- });
1921
- });
1922
-
1923
- router.post('/v1/service/simplex/paymentRequest', (req, res) => {
1924
- getServerWithAuth(req, res, server => {
1925
- server.externalServices.simplex
1926
- .simplexPaymentRequest(req)
1927
- .then(response => {
1928
- res.json(response);
1929
- })
1930
- .catch(err => {
1931
- return returnError(err ?? 'unknown', res, req);
1932
- });
1933
- });
1934
- });
1935
-
1936
- router.post('/v1/service/simplex/sellPaymentRequest', (req, res) => {
1937
- getServerWithAuth(req, res, server => {
1938
- server.externalServices.simplex
1939
- .simplexSellPaymentRequest(req)
1940
- .then(response => {
1941
- res.json(response);
1942
- })
1943
- .catch(err => {
1944
- return returnError(err ?? 'unknown', res, req);
1945
- });
1946
- });
1947
- });
1948
-
1949
- router.get('/v1/service/simplex/events', (req, res) => {
1950
- getServerWithAuth(req, res, server => {
1951
- const opts = { env: req.query.env };
1952
- server.externalServices.simplex
1953
- .simplexGetEvents(opts)
1954
- .then(response => {
1955
- res.json(response);
1956
- })
1957
- .catch(err => {
1958
- return returnError(err ?? 'unknown', res, req);
1959
- });
1960
- });
1961
- });
1962
-
1963
- router.post('/v1/service/thorswap/supportedChains', (req, res) => {
1964
- let server: WalletService;
1965
- try {
1966
- server = getServer(req, res);
1967
- } catch (ex) {
1968
- return returnError(ex, res, req);
1969
- }
1970
-
1971
- server.externalServices.thorswap
1972
- .thorswapGetSupportedChains(req)
1973
- .then(response => {
1974
- res.json(response);
1975
- })
1976
- .catch(err => {
1977
- return returnError(err ?? 'unknown', res, req);
1978
- });
1979
- });
1980
-
1981
- router.post('/v1/service/thorswap/cryptoCurrencies', (req, res) => {
1982
- let server: WalletService;
1983
- try {
1984
- server = getServer(req, res);
1985
- } catch (ex) {
1986
- return returnError(ex, res, req);
1987
- }
1988
-
1989
- server.externalServices.thorswap
1990
- .thorswapGetCryptoCurrencies(req)
1991
- .then(response => {
1992
- res.json(response);
1993
- })
1994
- .catch(err => {
1995
- return returnError(err ?? 'unknown', res, req);
1996
- });
1997
- });
1998
-
1999
- router.post('/v1/service/thorswap/getSwapQuote', (req, res) => {
2000
- getServerWithAuth(req, res, async server => {
2001
- let response;
2002
- try {
2003
- response = await server.externalServices.thorswap.thorswapGetSwapQuote(req);
2004
- return res.json(response);
2005
- } catch (ex) {
2006
- return returnError(ex, res, req);
2007
- }
2008
- });
2009
- });
2010
-
2011
- router.post('/v1/service/thorswap/getSwapTx', (req, res) => {
2012
- let server: WalletService;
2013
- try {
2014
- server = getServer(req, res);
2015
- } catch (ex) {
2016
- return returnError(ex, res, req);
2017
- }
2018
-
2019
- server.externalServices.thorswap
2020
- .thorswapGetSwapTx(req)
2021
- .then(response => {
2022
- res.json(response);
2023
- })
2024
- .catch(err => {
2025
- return returnError(err ?? 'unknown', res, req);
2026
- });
2027
- });
2028
-
2029
- router.post('/v1/service/transak/getAccessToken', (req, res) => {
2030
- getServerWithAuth(req, res, async server => {
2031
- let response;
2032
- try {
2033
- response = await server.externalServices.transak.transakGetAccessToken(req);
2034
- return res.json(response);
2035
- } catch (ex) {
2036
- return returnError(ex, res, req);
2037
- }
2038
- });
2039
- });
2040
-
2041
- router.post('/v1/service/transak/cryptoCurrencies', (req, res) => {
2042
- let server: WalletService;
2043
- try {
2044
- server = getServer(req, res);
2045
- } catch (ex) {
2046
- return returnError(ex, res, req);
2047
- }
2048
-
2049
- server.externalServices.transak
2050
- .transakGetCryptoCurrencies(req)
2051
- .then(response => {
2052
- res.json(response);
2053
- })
2054
- .catch(err => {
2055
- return returnError(err ?? 'unknown', res, req);
2056
- });
2057
- });
2058
-
2059
- router.post('/v1/service/transak/fiatCurrencies', (req, res) => {
2060
- let server: WalletService;
2061
- try {
2062
- server = getServer(req, res);
2063
- } catch (ex) {
2064
- return returnError(ex, res, req);
2065
- }
2066
-
2067
- server.externalServices.transak
2068
- .transakGetFiatCurrencies(req)
2069
- .then(response => {
2070
- res.json(response);
2071
- })
2072
- .catch(err => {
2073
- return returnError(err ?? 'unknown', res, req);
2074
- });
2075
- });
2076
-
2077
- router.post('/v1/service/transak/quote', (req, res) => {
2078
- getServerWithAuth(req, res, async server => {
2079
- let response;
2080
- try {
2081
- response = await server.externalServices.transak.transakGetQuote(req);
2082
- return res.json(response);
2083
- } catch (ex) {
2084
- return returnError(ex, res, req);
2085
- }
2086
- });
2087
- });
2088
-
2089
- router.post('/v1/service/transak/signedPaymentUrl', (req, res) => {
2090
- getServerWithAuth(req, res, async server => {
2091
- let response;
2092
- try {
2093
- response = await server.externalServices.transak.transakGetSignedPaymentUrl(req);
2094
- return res.json(response);
2095
- } catch (ex) {
2096
- return returnError(ex, res, req);
2097
- }
2098
- });
2099
- });
2100
-
2101
- router.post('/v1/service/transak/orderDetails', (req, res) => {
2102
- let server: WalletService;
2103
- try {
2104
- server = getServer(req, res);
2105
- } catch (ex) {
2106
- return returnError(ex, res, req);
2107
- }
2108
-
2109
- server.externalServices.transak
2110
- .transakGetOrderDetails(req)
2111
- .then(response => {
2112
- res.json(response);
2113
- })
2114
- .catch(err => {
2115
- return returnError(err ?? 'unknown', res, req);
2116
- });
2117
- });
2118
-
2119
- router.post('/v1/service/wyre/walletOrderQuotation', (req, res) => {
2120
- getServerWithAuth(req, res, server => {
2121
- server.externalServices.wyre
2122
- .wyreWalletOrderQuotation(req)
2123
- .then(response => {
2124
- res.json(response);
2125
- })
2126
- .catch(err => {
2127
- return returnError(err ?? 'unknown', res, req);
2128
- });
2129
- });
2130
- });
2131
-
2132
- router.post('/v1/service/wyre/walletOrderReservation', (req, res) => {
2133
- getServerWithAuth(req, res, server => {
2134
- server.externalServices.wyre
2135
- .wyreWalletOrderReservation(req)
2136
- .then(response => {
2137
- res.json(response);
2138
- })
2139
- .catch(err => {
2140
- return returnError(err ?? 'unknown', res, req);
2141
- });
2142
- });
2143
- });
2144
-
2145
- router.post('/v1/service/changelly/getCurrencies', (req, res) => {
2146
- let server: WalletService;
2147
- try {
2148
- server = getServer(req, res);
2149
- } catch (ex) {
2150
- return returnError(ex, res, req);
2151
- }
2152
- server.externalServices.changelly
2153
- .changellyGetCurrencies(req)
2154
- .then(response => {
2155
- res.json(response);
2156
- })
2157
- .catch(err => {
2158
- return returnError(err ?? 'unknown', res, req);
2159
- });
2160
- });
2161
-
2162
- router.post('/v1/service/changelly/getPairsParams', (req, res) => {
2163
- getServerWithAuth(req, res, server => {
2164
- server.externalServices.changelly
2165
- .changellyGetPairsParams(req)
2166
- .then(response => {
2167
- res.json(response);
2168
- })
2169
- .catch(err => {
2170
- return returnError(err ?? 'unknown', res, req);
2171
- });
2172
- });
2173
- });
2174
-
2175
- router.post('/v1/service/changelly/getFixRateForAmount', (req, res) => {
2176
- getServerWithAuth(req, res, server => {
2177
- server.externalServices.changelly
2178
- .changellyGetFixRateForAmount(req)
2179
- .then(response => {
2180
- res.json(response);
2181
- })
2182
- .catch(err => {
2183
- return returnError(err ?? 'unknown', res, req);
2184
- });
2185
- });
2186
- });
2187
-
2188
- router.post('/v1/service/changelly/createFixTransaction', (req, res) => {
2189
- getServerWithAuth(req, res, server => {
2190
- server.externalServices.changelly
2191
- .changellyCreateFixTransaction(req)
2192
- .then(response => {
2193
- res.json(response);
2194
- })
2195
- .catch(err => {
2196
- return returnError(err ?? 'unknown', res, req);
2197
- });
2198
- });
2199
- });
2200
-
2201
- router.post('/v1/service/changelly/getTransactions', (req, res) => {
2202
- let server: WalletService;
2203
- try {
2204
- server = getServer(req, res);
2205
- } catch (ex) {
2206
- return returnError(ex, res, req);
2207
- }
2208
- server.externalServices.changelly
2209
- .changellyGetTransactions(req)
2210
- .then(response => {
2211
- res.json(response);
2212
- })
2213
- .catch(err => {
2214
- return returnError(err ?? 'unknown', res, req);
2215
- });
2216
- });
2217
-
2218
- router.post('/v1/service/changelly/getStatus', (req, res) => {
2219
- let server: WalletService;
2220
- try {
2221
- server = getServer(req, res);
2222
- } catch (ex) {
2223
- return returnError(ex, res, req);
2224
- }
2225
- server.externalServices.changelly
2226
- .changellyGetStatus(req)
2227
- .then(response => {
2228
- res.json(response);
2229
- })
2230
- .catch(err => {
2231
- return returnError(err ?? 'unknown', res, req);
2232
- });
2233
- });
2234
-
2235
- router.get('/v1/service/oneInch/getReferrerFee', (req, res) => {
2236
- let server: WalletService;
2237
- try {
2238
- server = getServer(req, res);
2239
- } catch (ex) {
2240
- return returnError(ex, res, req);
2241
- }
2242
- server.externalServices.oneInch
2243
- .oneInchGetReferrerFee(req)
2244
- .then(response => {
2245
- res.json(response);
2246
- })
2247
- .catch(err => {
2248
- return returnError(err ?? 'unknown', res, req);
2249
- });
2250
- });
2251
-
2252
- router.post('/v1/service/oneInch/getSwap/:chain?', (req, res) => {
2253
- getServerWithAuth(req, res, server => {
2254
- server.externalServices.oneInch
2255
- .oneInchGetSwap(req)
2256
- .then(response => {
2257
- res.json(response);
2258
- })
2259
- .catch(err => {
2260
- return returnError(err ?? 'unknown', res, req);
2261
- });
2262
- });
2263
- });
2264
-
2265
- router.get('/v1/service/oneInch/getTokens/:chain?', (req, res) => {
2266
- SetPublicCache(res, 1 * ONE_MINUTE);
2267
- let server: WalletService;
2268
- try {
2269
- server = getServer(req, res);
2270
- } catch (ex) {
2271
- return returnError(ex, res, req);
2272
- }
2273
- server.externalServices.coinGecko.coinGeckoGetTokens(req)
2274
- .then(response => {
2275
- res.json(response);
2276
- })
2277
- .catch(err => {
2278
- return returnError(err ?? 'unknown', res, req);
2279
- });
2280
- });
2281
-
2282
- router.get('/v1/marketstats/:code/', (req, res) => {
2283
- SetPublicCache(res, 5 * ONE_MINUTE);
2284
- let server: WalletService;
2285
- try {
2286
- server = getServer(req, res);
2287
- } catch (ex) {
2288
- return returnError(ex, res, req);
2289
- }
2290
- server.externalServices.coinGecko.coinGeckoGetMarketStats(req)
2291
- .then(response => {
2292
- res.json(response);
2293
- })
2294
- .catch(err => {
2295
- return returnError(err ?? 'unknown', res, req);
2296
- });
2297
- });
2298
-
2299
- router.get('/v1/services/dex/getSpenderApprovalWhitelist', (req, res) => {
2300
- let server: WalletService;
2301
- try {
2302
- server = getServer(req, res);
2303
- } catch (ex) {
2304
- return returnError(ex, res, req);
2305
- }
2306
-
2307
- server.getSpenderApprovalWhitelist((err, response) => {
2308
- if (err) return returnError(err, res, req);
2309
- res.json(response);
2310
- });
2311
- });
2312
-
2313
- const moralisCorsOptions = {
2314
- origin: (origin, cb) => {
2315
- const moralisWhiteList = config.moralis?.whitelist ?? [];
2316
- if (moralisWhiteList.indexOf(origin) !== -1) {
2317
- cb(null, true);
2318
- } else {
2319
- cb(new Error('Not allowed by CORS'));
2320
- }
2321
- },
2322
- };
2323
-
2324
- router.post('/v1/moralis/getWalletTokenBalances', cors(moralisCorsOptions), (req, res) => {
2325
- let server: WalletService;
2326
- try {
2327
- server = getServer(req, res);
2328
- } catch (ex) {
2329
- return returnError(ex, res, req);
2330
- }
2331
-
2332
- server.moralisGetWalletTokenBalances(req)
2333
- .then(response => {
2334
- res.json(response);
2335
- })
2336
- .catch(err => {
2337
- return returnError(err ?? 'unknown', res, req);
2338
- });
2339
- });
2340
-
2341
- router.post('/v1/moralis/moralisGetTokenAllowance', cors(moralisCorsOptions), (req, res) => {
2342
- let server: WalletService;
2343
- try {
2344
- server = getServer(req, res);
2345
- } catch (ex) {
2346
- return returnError(ex, res, req);
2347
- }
2348
-
2349
- server.moralisGetTokenAllowance(req)
2350
- .then(response => {
2351
- res.json(response);
2352
- })
2353
- .catch(err => {
2354
- return returnError(err ?? 'unknown', res, req);
2355
- });
2356
- });
2357
-
2358
- router.post('/v1/moralis/moralisGetNativeBalance', cors(moralisCorsOptions), (req, res) => {
2359
- let server: WalletService;
2360
- try {
2361
- server = getServer(req, res);
2362
- } catch (ex) {
2363
- return returnError(ex, res, req);
2364
- }
2365
-
2366
- server.moralisGetNativeBalance(req)
2367
- .then(response => {
2368
- res.json(response);
2369
- })
2370
- .catch(err => {
2371
- return returnError(err ?? 'unknown', res, req);
2372
- });
2373
- });
2374
-
2375
- router.post('/v1/moralis/GetTokenPrice', cors(moralisCorsOptions), (req, res) => {
2376
- let server: WalletService;
2377
- try {
2378
- server = getServer(req, res);
2379
- } catch (ex) {
2380
- return returnError(ex, res, req);
2381
- }
2382
-
2383
- server.moralisGetTokenPrice(req)
2384
- .then(response => {
2385
- res.json(response);
2386
- })
2387
- .catch(err => {
2388
- return returnError(err ?? 'unknown', res, req);
2389
- });
2390
- });
2391
-
2392
- router.post('/v1/moralis/getMultipleERC20TokenPrices', cors(moralisCorsOptions), (req, res) => {
2393
- let server: WalletService;
2394
- try {
2395
- server = getServer(req, res);
2396
- } catch (ex) {
2397
- return returnError(ex, res, req);
2398
- }
2399
-
2400
- server.moralisGetMultipleERC20TokenPrices(req)
2401
- .then(response => {
2402
- res.json(response);
2403
- })
2404
- .catch(err => {
2405
- return returnError(err ?? 'unknown', res, req);
2406
- });
2407
- });
2408
-
2409
- router.post('/v1/moralis/getERC20TokenBalancesWithPricesByWallet', cors(moralisCorsOptions), (req, res) => {
2410
- let server: WalletService;
2411
- try {
2412
- server = getServer(req, res);
2413
- } catch (ex) {
2414
- return returnError(ex, res, req);
2415
- }
2416
-
2417
- server.moralisGetERC20TokenBalancesWithPricesByWallet(req)
2418
- .then(response => {
2419
- res.json(response);
2420
- })
2421
- .catch(err => {
2422
- return returnError(err ?? 'unknown', res, req);
2423
- });
2424
- });
2425
-
2426
- router.post('/v1/moralis/getSolWalletPortfolio', cors(moralisCorsOptions), (req, res) => {
2427
- let server: WalletService;
2428
- try {
2429
- server = getServer(req, res);
2430
- } catch (ex) {
2431
- return returnError(ex, res, req);
2432
- }
2433
-
2434
- server.moralisGetSolWalletPortfolio(req)
2435
- .then(response => {
2436
- res.json(response);
2437
- })
2438
- .catch(err => {
2439
- return returnError(err ?? 'unknown', res, req);
2440
- });
124
+ registerMoralisRoutes(router, {
125
+ getServer,
126
+ returnError
2441
127
  });
2442
128
 
2443
129
  /** Imported routes */
2444
130
  router.use(new AaveRouter({ returnError, getServer }).router);
2445
131
  router.use(new TssRouter({ returnError, opts }).router);
2446
132
 
2447
-
2448
133
  // Set no-cache by default
2449
134
  this.app.use((req, res, next) => {
2450
135
  res.setHeader('Cache-Control', 'no-store');