coinbase 0.0.1 → 4.2.3

Sign up to get free protection for your applications and to get access to all the features.
Files changed (53) hide show
  1. checksums.yaml +4 -4
  2. data/.gitignore +2 -0
  3. data/.travis.yml +7 -0
  4. data/CONTRIBUTING.md +53 -0
  5. data/Gemfile +4 -0
  6. data/LICENSE +201 -0
  7. data/README.md +621 -0
  8. data/Rakefile +6 -0
  9. data/bin/console +14 -0
  10. data/bin/setup +7 -0
  11. data/coinbase.gemspec +26 -0
  12. data/lib/coinbase/util.rb +16 -0
  13. data/lib/coinbase/wallet/adapters/em_http.rb +78 -0
  14. data/lib/coinbase/wallet/adapters/net_http.rb +68 -0
  15. data/lib/coinbase/wallet/api_client.rb +755 -0
  16. data/lib/coinbase/wallet/api_errors.rb +120 -0
  17. data/lib/coinbase/wallet/api_response.rb +41 -0
  18. data/lib/coinbase/wallet/ca-coinbase.crt +101 -0
  19. data/lib/coinbase/wallet/client.rb +101 -0
  20. data/lib/coinbase/wallet/coinbase-callback.pub +14 -0
  21. data/lib/coinbase/wallet/models/account.rb +193 -0
  22. data/lib/coinbase/wallet/models/address.rb +12 -0
  23. data/lib/coinbase/wallet/models/api_object.rb +46 -0
  24. data/lib/coinbase/wallet/models/checkout.rb +19 -0
  25. data/lib/coinbase/wallet/models/order.rb +12 -0
  26. data/lib/coinbase/wallet/models/transaction.rb +21 -0
  27. data/lib/coinbase/wallet/models/transfer.rb +13 -0
  28. data/lib/coinbase/wallet/models/user.rb +15 -0
  29. data/lib/coinbase/wallet/version.rb +5 -0
  30. data/lib/coinbase/wallet.rb +24 -156
  31. data/spec/account_spec.rb +199 -0
  32. data/spec/callback_signature_verification_spec.rb +16 -0
  33. data/spec/clients/client_spec.rb +34 -0
  34. data/spec/clients/oauth_client_spec.rb +56 -0
  35. data/spec/endpoints_spec.rb +352 -0
  36. data/spec/error_spec.rb +137 -0
  37. data/spec/models/address_spec.rb +26 -0
  38. data/spec/models/api_object_spec.rb +70 -0
  39. data/spec/models/checkout_spec.rb +52 -0
  40. data/spec/models/current_user_spec.rb +29 -0
  41. data/spec/models/order_spec.rb +52 -0
  42. data/spec/models/request_spec.rb +47 -0
  43. data/spec/models/transfer_spec.rb +64 -0
  44. data/spec/models/user_spec.rb +24 -0
  45. data/spec/spec_helper.rb +13 -0
  46. metadata +67 -112
  47. data/lib/coinbase/address.rb +0 -127
  48. data/lib/coinbase/asset.rb +0 -20
  49. data/lib/coinbase/balance_map.rb +0 -48
  50. data/lib/coinbase/constants.rb +0 -38
  51. data/lib/coinbase/network.rb +0 -55
  52. data/lib/coinbase/transfer.rb +0 -153
  53. data/lib/coinbase.rb +0 -18
@@ -0,0 +1,755 @@
1
+ module Coinbase
2
+ module Wallet
3
+ class APIClient
4
+ def auth_headers(method, path, body)
5
+ raise NotImplementedError, "APIClient is not intended to be used directly"
6
+ end
7
+
8
+ #
9
+ # Market Data
10
+ #
11
+ def currencies(params = {})
12
+ out = nil
13
+ get("/v2/currencies", params) do |resp|
14
+ out = resp.data.map { |item| APIObject.new(self, item) }
15
+ yield(out, resp) if block_given?
16
+ end
17
+ out
18
+ end
19
+
20
+ def exchange_rates(params = {})
21
+ out = nil
22
+ get("/v2/exchange-rates", params) do |resp|
23
+ out = APIObject.new(self, resp.data)
24
+ yield(out, resp) if block_given?
25
+ end
26
+ out
27
+ end
28
+
29
+ def buy_price(params = {})
30
+ out = nil
31
+ pair = determine_currency_pair(params)
32
+
33
+ get("/v2/prices/#{pair}/buy", params) do |resp|
34
+ out = APIObject.new(self, resp.data)
35
+ yield(out, resp) if block_given?
36
+ end
37
+ out
38
+ end
39
+
40
+ def sell_price(params = {})
41
+ out = nil
42
+ pair = determine_currency_pair(params)
43
+
44
+ get("/v2/prices/#{pair}/sell", params) do |resp|
45
+ out = APIObject.new(self, resp.data)
46
+ yield(out, resp) if block_given?
47
+ end
48
+ out
49
+ end
50
+
51
+ def spot_price(params = {})
52
+ out = nil
53
+ pair = determine_currency_pair(params)
54
+
55
+ get("/v2/prices/#{pair}/spot", params) do |resp|
56
+ out = APIObject.new(self, resp.data)
57
+ yield(out, resp) if block_given?
58
+ end
59
+ out
60
+ end
61
+
62
+ def historic_prices(params = {})
63
+ out = nil
64
+ get("/v2/prices/historic", params) do |resp|
65
+ out = APIObject.new(self, resp.data)
66
+ yield(out, resp) if block_given?
67
+ end
68
+ out
69
+ end
70
+
71
+ def time(params = {})
72
+ out = nil
73
+ get("/v2/time", params) do |resp|
74
+ out = APIObject.new(self, resp.data)
75
+ yield(out, resp) if block_given?
76
+ end
77
+ out
78
+ end
79
+
80
+ #
81
+ # Users
82
+ #
83
+ def user(user_id, params = {})
84
+ out = nil
85
+ get("/v2/users/#{user_id}", params) do |resp|
86
+ out = User.new(self, resp.data)
87
+ yield(out, resp) if block_given?
88
+ end
89
+ out
90
+ end
91
+
92
+ def current_user(params = {})
93
+ out = nil
94
+ get("/v2/user", params) do |resp|
95
+ out = CurrentUser.new(self, resp.data)
96
+ yield(out, resp) if block_given?
97
+ end
98
+ out
99
+ end
100
+
101
+ def auth_info(params = {})
102
+ out = nil
103
+ get("/v2/user/auth", params) do |resp|
104
+ out = APIObject.new(self, resp.data)
105
+ yield(out, resp) if block_given?
106
+ end
107
+ out
108
+ end
109
+
110
+ def update_current_user(params = {})
111
+ out = nil
112
+ put("/v2/user", params) do |resp|
113
+ out = CurrentUser.new(self, resp.data)
114
+ yield(out, resp) if block_given?
115
+ end
116
+ out
117
+ end
118
+
119
+ #
120
+ # Accounts
121
+ #
122
+ def accounts(params = {})
123
+ out = nil
124
+ get("/v2/accounts", params) do |resp|
125
+ out = resp.data.map { |item| Account.new(self, item) }
126
+ yield(out, resp) if block_given?
127
+ end
128
+ out
129
+ end
130
+
131
+ def account(account_id, params = {})
132
+ out = nil
133
+ get("/v2/accounts/#{account_id}", params) do |resp|
134
+ out = Account.new(self, resp.data)
135
+ yield(out, resp) if block_given?
136
+ end
137
+ out
138
+ end
139
+
140
+ def primary_account(params = {})
141
+ out = nil
142
+ get("/v2/accounts/primary", params) do |resp|
143
+ out = Account.new(self, resp.data)
144
+ yield(out, resp) if block_given?
145
+ end
146
+ out
147
+ end
148
+
149
+ def set_primary_account(account_id, params = {})
150
+ out = nil
151
+ post("/v2/accounts/#{account_id}/primary", params) do |resp|
152
+ out = Account.new(self, resp.data)
153
+ yield(out, resp) if block_given?
154
+ end
155
+ out
156
+ end
157
+
158
+ def create_account(params = {})
159
+ out = nil
160
+ post("/v2/accounts", params) do |resp|
161
+ out = Account.new(self, resp.data)
162
+ yield(out, resp) if block_given?
163
+ end
164
+ out
165
+ end
166
+
167
+ def update_account(account_id, params = {})
168
+ out = nil
169
+ put("/v2/accounts/#{account_id}", params) do |resp|
170
+ out = Account.new(self, resp.data)
171
+ yield(out, resp) if block_given?
172
+ end
173
+ out
174
+ end
175
+
176
+ def delete_account(account_id, params = {})
177
+ out = nil
178
+ delete("/v2/accounts/#{account_id}", params) do |resp|
179
+ out = APIObject.new(self, resp.data)
180
+ yield(out, resp) if block_given?
181
+ end
182
+ out
183
+ end
184
+
185
+ #
186
+ # Notifications
187
+ #
188
+ def notifications(params = {})
189
+ out = nil
190
+ get("/v2/notifications", params) do |resp|
191
+ out = resp.data.map { |item| APIObject.new(self, item) }
192
+ yield(out, resp) if block_given?
193
+ end
194
+ out
195
+ end
196
+
197
+ def notification(notification_id, params = {})
198
+ out = nil
199
+ get("/v2/notifications/#{notification_id}", params) do |resp|
200
+ out = APIObject.new(self, resp.data)
201
+ yield(out, resp) if block_given?
202
+ end
203
+ out
204
+ end
205
+
206
+
207
+ #
208
+ # Addresses
209
+ #
210
+ def addresses(account_id, params = {})
211
+ out = nil
212
+ get("/v2/accounts/#{account_id}/addresses", params) do |resp|
213
+ out = resp.data.map { |item| Address.new(self, item) }
214
+ yield(out, resp) if block_given?
215
+ end
216
+ out
217
+ end
218
+
219
+ def address(account_id, address_id, params = {})
220
+ out = nil
221
+ get("/v2/accounts/#{account_id}/addresses/#{address_id}", params) do |resp|
222
+ out = Address.new(self, resp.data)
223
+ yield(out, resp) if block_given?
224
+ end
225
+ out
226
+ end
227
+
228
+ def address_transactions(account_id, address_id, params = {})
229
+ out = nil
230
+ get("/v2/accounts/#{account_id}/addresses/#{address_id}/transactions", params) do |resp|
231
+ out = resp.data.map { |item| Transaction.new(self, item) }
232
+ yield(out, resp) if block_given?
233
+ end
234
+ out
235
+ end
236
+
237
+ def create_address(account_id, params = {})
238
+ out = nil
239
+ post("/v2/accounts/#{account_id}/addresses", params) do |resp|
240
+ out = Address.new(self, resp.data)
241
+ yield(out, resp) if block_given?
242
+ end
243
+ out
244
+ end
245
+
246
+ #
247
+ # Transactions
248
+ #
249
+ def transactions(account_id, params = {})
250
+ out = nil
251
+ get("/v2/accounts/#{account_id}/transactions", params) do |resp|
252
+ out = resp.data.map { |item| Transaction.new(self, item) }
253
+ yield(out, resp) if block_given?
254
+ end
255
+ out
256
+ end
257
+
258
+ def transaction(account_id, transaction_id, params = {})
259
+ out = nil
260
+ get("/v2/accounts/#{account_id}/transactions/#{transaction_id}", params) do |resp|
261
+ out = Transaction.new(self, resp.data)
262
+ yield(out, resp) if block_given?
263
+ end
264
+ out
265
+ end
266
+
267
+ def send(account_id, params = {})
268
+ [ :to, :amount ].each do |param|
269
+ raise APIError, "Missing parameter: #{param}" unless params.include? param
270
+ end
271
+ params['type'] = 'send'
272
+
273
+ out = nil
274
+ post("/v2/accounts/#{account_id}/transactions", params) do |resp|
275
+ out = Transaction.new(self, resp.data)
276
+ yield(out, resp) if block_given?
277
+ end
278
+ out
279
+ end
280
+
281
+ def transfer(account_id, params = {})
282
+ [ :to, :amount ].each do |param|
283
+ raise APIError, "Missing parameter: #{param}" unless params.include? param
284
+ end
285
+ params['type'] = 'transfer'
286
+
287
+ out = nil
288
+ post("/v2/accounts/#{account_id}/transactions", params) do |resp|
289
+ out = Transaction.new(self, resp.data)
290
+ yield(out, resp) if block_given?
291
+ end
292
+ out
293
+ end
294
+
295
+ def request(account_id, params = {})
296
+ [ :to, :amount, :currency ].each do |param|
297
+ raise APIError, "Missing parameter: #{param}" unless params.include? param
298
+ end
299
+ params['type'] = 'request'
300
+
301
+ out = nil
302
+ post("/v2/accounts/#{account_id}/transactions", params) do |resp|
303
+ out = Request.new(self, resp.data)
304
+ yield(out, resp) if block_given?
305
+ end
306
+ out
307
+ end
308
+
309
+ def resend_request(account_id, transaction_id, params = {})
310
+ out = nil
311
+ post("/v2/accounts/#{account_id}/transactions/#{transaction_id}/resend", params) do |resp|
312
+ out = APIObject.new(self, resp.data)
313
+ yield(out, resp) if block_given?
314
+ end
315
+ out
316
+ end
317
+
318
+ def cancel_request(account_id, transaction_id, params = {})
319
+ out = nil
320
+ delete("/v2/accounts/#{account_id}/transactions/#{transaction_id}", params) do |resp|
321
+ out = APIObject.new(self, resp.data)
322
+ yield(out, resp) if block_given?
323
+ end
324
+ out
325
+ end
326
+
327
+ def complete_request(account_id, transaction_id, params = {})
328
+ out = nil
329
+ post("/v2/accounts/#{account_id}/transactions/#{transaction_id}/complete", params) do |resp|
330
+ out = APIObject.new(self, resp.data)
331
+ yield(out, resp) if block_given?
332
+ end
333
+ out
334
+ end
335
+
336
+ #
337
+ # Buys
338
+ #
339
+ def list_buys(account_id, params={})
340
+ out = nil
341
+ get("/v2/accounts/#{account_id}/buys", params) do |resp|
342
+ out = resp.data.map { |item| Transfer.new(self, item) }
343
+ yield(out, resp) if block_given?
344
+ end
345
+ out
346
+ end
347
+
348
+ def list_buy(account_id, transaction_id, params = {})
349
+ out = nil
350
+ get("/v2/accounts/#{account_id}/buys/#{transaction_id}", params) do |resp|
351
+ out = Transfer.new(self, resp.data)
352
+ yield(out, resp) if block_given?
353
+ end
354
+ out
355
+ end
356
+
357
+ def buy(account_id, params = {})
358
+ raise APIError, "Missing parameter: 'amount' or 'total'" unless params.include? :amount or params.include? :total
359
+
360
+ out = nil
361
+ post("/v2/accounts/#{account_id}/buys", params) do |resp|
362
+ out = Transfer.new(self, resp.data)
363
+ yield(out, resp) if block_given?
364
+ end
365
+ out
366
+ end
367
+
368
+ def commit_buy(account_id, transaction_id, params = {})
369
+ out = nil
370
+ post("/v2/accounts/#{account_id}/buys/#{transaction_id}/commit", params) do |resp|
371
+ out = Transfer.new(self, resp.data)
372
+ yield(out, resp) if block_given?
373
+ end
374
+ out
375
+ end
376
+
377
+ #
378
+ # Sells
379
+ #
380
+ def list_sells(account_id, params = {})
381
+ out = nil
382
+ get("/v2/accounts/#{account_id}/sells", params) do |resp|
383
+ out = resp.data.map { |item| Transfer.new(self, item) }
384
+ yield(out, resp) if block_given?
385
+ end
386
+ out
387
+ end
388
+
389
+ def list_sell(account_id, transaction_id, params = {})
390
+ out = nil
391
+ get("/v2/accounts/#{account_id}/sells/#{transaction_id}", params) do |resp|
392
+ out = Transfer.new(self, resp.data)
393
+ yield(out, resp) if block_given?
394
+ end
395
+ out
396
+ end
397
+
398
+ def sell(account_id, params = {})
399
+ raise APIError, "Missing parameter: 'amount' or 'total'" unless params.include? :amount or params.include? :total
400
+
401
+ out = nil
402
+ post("/v2/accounts/#{account_id}/sells", params) do |resp|
403
+ out = Transfer.new(self, resp.data)
404
+ yield(out, resp) if block_given?
405
+ end
406
+ out
407
+ end
408
+
409
+ def commit_sell(account_id, transaction_id, params = {})
410
+ out = nil
411
+ post("/v2/accounts/#{account_id}/sells/#{transaction_id}/commit", params) do |resp|
412
+ out = Transfer.new(self, resp.data)
413
+ yield(out, resp) if block_given?
414
+ end
415
+ out
416
+ end
417
+
418
+ #
419
+ # Deposits
420
+ #
421
+ def list_deposits(account_id, params={})
422
+ out = nil
423
+ get("/v2/accounts/#{account_id}/deposits", params) do |resp|
424
+ out = resp.data.map { |item| Transfer.new(self, item) }
425
+ yield(out, resp) if block_given?
426
+ end
427
+ out
428
+ end
429
+
430
+ def list_deposit(account_id, transaction_id, params = {})
431
+ out = nil
432
+ get("/v2/accounts/#{account_id}/deposits/#{transaction_id}", params) do |resp|
433
+ out = Transfer.new(self, resp.data)
434
+ yield(out, resp) if block_given?
435
+ end
436
+ out
437
+ end
438
+
439
+ def deposit(account_id, params = {})
440
+ [ :amount ].each do |param|
441
+ raise APIError, "Missing parameter: #{param}" unless params.include? param
442
+ end
443
+
444
+ out = nil
445
+ post("/v2/accounts/#{account_id}/deposits", params) do |resp|
446
+ out = Transfer.new(self, resp.data)
447
+ yield(out, resp) if block_given?
448
+ end
449
+ out
450
+ end
451
+
452
+ def commit_deposit(account_id, transaction_id, params = {})
453
+ out = nil
454
+ post("/v2/accounts/#{account_id}/deposits/#{transaction_id}/commit", params) do |resp|
455
+ out = APIObject.new(self, resp.data)
456
+ yield(out, resp) if block_given?
457
+ end
458
+ out
459
+ end
460
+
461
+ #
462
+ # withdrawals
463
+ #
464
+ def list_withdrawals(account_id, params={})
465
+ out = nil
466
+ get("/v2/accounts/#{account_id}/withdrawals", params) do |resp|
467
+ out = resp.data.map { |item| Transfer.new(self, item) }
468
+ yield(out, resp) if block_given?
469
+ end
470
+ out
471
+ end
472
+
473
+ def list_withdrawal(account_id, transaction_id, params = {})
474
+ out = nil
475
+ get("/v2/accounts/#{account_id}/withdrawals/#{transaction_id}", params) do |resp|
476
+ out = Transfer.new(self, resp.data)
477
+ yield(out, resp) if block_given?
478
+ end
479
+ out
480
+ end
481
+
482
+ def withdraw(account_id, params = {})
483
+ [ :amount ].each do |param|
484
+ raise APIError, "Missing parameter: #{param}" unless params.include? param
485
+ end
486
+
487
+ out = nil
488
+ post("/v2/accounts/#{account_id}/withdrawals", params) do |resp|
489
+ out = Transfer.new(self, resp.data)
490
+ yield(out, resp) if block_given?
491
+ end
492
+ out
493
+ end
494
+
495
+ def commit_withdrawal(account_id, transaction_id, params = {})
496
+ out = nil
497
+ post("/v2/accounts/#{account_id}/withdrawals/#{transaction_id}/commit", params) do |resp|
498
+ out = APIObject.new(self, resp.data)
499
+ yield(out, resp) if block_given?
500
+ end
501
+ out
502
+ end
503
+
504
+ #
505
+ # Payment Methods
506
+ #
507
+ def payment_methods(params = {})
508
+ out = nil
509
+ get("/v2/payment-methods", params) do |resp|
510
+ out = resp.data.map { |item| APIObject.new(self, item) }
511
+ yield(out, resp) if block_given?
512
+ end
513
+ out
514
+ end
515
+
516
+ def payment_method(payment_method_id, params = {})
517
+ out = nil
518
+ get("/v2/payment-methods/#{payment_method_id}", params) do |resp|
519
+ out = APIObject.new(self, resp.data)
520
+ yield(out, resp) if block_given?
521
+ end
522
+ out
523
+ end
524
+
525
+ #
526
+ # Merchants
527
+ #
528
+ def merchant(merchant_id, params = {})
529
+ out = nil
530
+ get("/v2/merchants/#{merchant_id}", params) do |resp|
531
+ out = APIObject.new(self, resp.data)
532
+ yield(out, resp) if block_given?
533
+ end
534
+ out
535
+ end
536
+
537
+ #
538
+ # Orders
539
+ #
540
+ def orders(params = {})
541
+ out = nil
542
+ get("/v2/orders", params) do |resp|
543
+ out = resp.data.map { |item| Order.new(self, item) }
544
+ yield(out, resp) if block_given?
545
+ end
546
+ out
547
+ end
548
+
549
+ def order(order_id, params = {})
550
+ out = nil
551
+ get("/v2/orders/#{order_id}", params) do |resp|
552
+ out = Order.new(self, resp.data)
553
+ yield(out, resp) if block_given?
554
+ end
555
+ out
556
+ end
557
+
558
+ def create_order(params = {})
559
+ [ :amount, :currency, :name ].each do |param|
560
+ fail APIError, "Missing parameter: #{param}" unless params.include? param
561
+ end
562
+
563
+ out = nil
564
+ post("/v2/orders", params) do |resp|
565
+ out = Order.new(self, resp.data)
566
+ yield(out, resp) if block_given?
567
+ end
568
+ out
569
+ end
570
+
571
+ def refund_order(order_id, params={})
572
+ [ :currency ].each do |param|
573
+ fail APIError, "Missing parameter: #{param}" unless params.include? param
574
+ end
575
+
576
+ out = nil
577
+ post("/v2/orders/#{order_id}/refund", params) do |resp|
578
+ out = Order.new(self, resp.data)
579
+ yield(out, resp) if block_given?
580
+ end
581
+ out
582
+ end
583
+
584
+ #
585
+ # Checkouts
586
+ #
587
+ def checkouts(params = {})
588
+ out = nil
589
+ get("/v2/checkouts", params) do |resp|
590
+ out = resp.data.map { |item| Checkout.new(self, item) }
591
+ yield(out, resp) if block_given?
592
+ end
593
+ out
594
+ end
595
+
596
+ def checkout(checkout_id, params = {})
597
+ out = nil
598
+ get("/v2/checkouts/#{checkout_id}", params) do |resp|
599
+ out = Checkout.new(self, resp.data)
600
+ yield(out, resp) if block_given?
601
+ end
602
+ out
603
+ end
604
+
605
+ def create_checkout(params = {})
606
+ [ :amount, :currency, :name ].each do |param|
607
+ fail APIError, "Missing parameter: #{param}" unless params.include? param
608
+ end
609
+
610
+ out = nil
611
+ post("/v2/checkouts", params) do |resp|
612
+ out = Checkout.new(self, resp.data)
613
+ yield(out, resp) if block_given?
614
+ end
615
+ out
616
+ end
617
+
618
+ def checkout_orders(checkout_id, params = {})
619
+ out = nil
620
+ get("/v2/checkouts/#{checkout_id}/orders", params) do |resp|
621
+ out = resp.data.map { |item| Order.new(self, item) }
622
+ yield(out, resp) if block_given?
623
+ end
624
+ out
625
+ end
626
+
627
+ def create_checkout_order(checkout_id, params={})
628
+ out = nil
629
+ post("/v2/checkouts/#{checkout_id}/orders", params) do |resp|
630
+ out = Order.new(self, resp.data)
631
+ yield(out, resp) if block_given?
632
+ end
633
+ out
634
+ end
635
+
636
+ #
637
+ # HTTP Stuff
638
+ #
639
+ def get(path, params)
640
+ uri = path
641
+ if params.count > 0
642
+ uri += "?#{URI.encode_www_form(params)}"
643
+ end
644
+
645
+ headers = {}
646
+ if params.has_key? :two_factor_token
647
+ headers['CB-2FA-TOKEN'] = params[:two_factor_token]
648
+ params.delete(:two_factor_token)
649
+ end
650
+
651
+ http_verb('GET', uri, nil, headers) do |resp|
652
+ if params[:fetch_all] == true &&
653
+ resp.body.has_key?('pagination') &&
654
+ resp.body['pagination']['next_uri'] != nil
655
+ params[:starting_after] = resp.body['data'].last['id']
656
+ get(path, params) do |page|
657
+ body = resp.body
658
+ body['data'] += page.data
659
+ resp.body = body
660
+ yield(resp)
661
+ end
662
+ else
663
+ yield(resp)
664
+ end
665
+ end
666
+ end
667
+
668
+ def put(path, params)
669
+ headers = {}
670
+ if params.has_key? :two_factor_token
671
+ headers['CB-2FA-TOKEN'] = params[:two_factor_token]
672
+ params.delete(:two_factor_token)
673
+ end
674
+
675
+ http_verb('PUT', path, params.to_json, headers) do |resp|
676
+ yield(resp)
677
+ end
678
+ end
679
+
680
+ def post(path, params)
681
+ headers = {}
682
+ if params.has_key? :two_factor_token
683
+ headers['CB-2FA-TOKEN'] = params[:two_factor_token]
684
+ params.delete(:two_factor_token)
685
+ end
686
+
687
+ http_verb('POST', path, params.to_json, headers) do |resp|
688
+ yield(resp)
689
+ end
690
+ end
691
+
692
+ def delete(path, params)
693
+ headers = {}
694
+ if params.has_key? :two_factor_token
695
+ headers['CB-2FA-TOKEN'] = params[:two_factor_token]
696
+ params.delete(:two_factor_token)
697
+ end
698
+
699
+ http_verb('DELETE', path, nil, headers) do |resp|
700
+ yield(resp)
701
+ end
702
+ end
703
+
704
+ CALLBACK_DIGEST = OpenSSL::Digest.new("SHA256")
705
+ def self.verify_callback(body, signature)
706
+ return false unless callback_signing_public_key
707
+ callback_signing_public_key.verify(CALLBACK_DIGEST, signature.unpack("m0")[0], body)
708
+ rescue OpenSSL::PKey::RSAError, ArgumentError
709
+ false
710
+ end
711
+
712
+ def self.callback_signing_public_key
713
+ @@callback_signing_public_key ||= nil
714
+ return @@callback_signing_public_key if @@callback_signing_public_key
715
+ path = File.expand_path(File.join(File.dirname(__FILE__), 'coinbase-callback.pub'))
716
+ @@callback_signing_public_key = OpenSSL::PKey::RSA.new(File.read(path))
717
+ end
718
+
719
+ def callback_signing_public_key
720
+ Coinbase::Wallet::APIClient.callback_signing_public_key
721
+ end
722
+
723
+ def verify_callback(body, signature)
724
+ Coinbase::Wallet::APIClient.verify_callback(body, signature)
725
+ end
726
+
727
+ def self.whitelisted_certificates
728
+ path = File.expand_path(File.join(File.dirname(__FILE__), 'ca-coinbase.crt'))
729
+
730
+ certs = [ [] ]
731
+ File.readlines(path).each do |line|
732
+ next if ["\n","#"].include?(line[0])
733
+ certs.last << line
734
+ certs << [] if line == "-----END CERTIFICATE-----\n"
735
+ end
736
+
737
+ result = OpenSSL::X509::Store.new
738
+
739
+ certs.each do |lines|
740
+ next if lines.empty?
741
+ cert = OpenSSL::X509::Certificate.new(lines.join)
742
+ result.add_cert(cert)
743
+ end
744
+
745
+ result
746
+ end
747
+
748
+ private
749
+
750
+ def determine_currency_pair(params)
751
+ Coinbase::Util.determine_currency_pair(params)
752
+ end
753
+ end
754
+ end
755
+ end