qbo_api 1.8.5 → 2.0.1
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.
- checksums.yaml +4 -4
- data/.gitignore +1 -0
- data/.travis.yml +6 -3
- data/README.md +68 -94
- data/example/base.rb +1 -0
- data/example/oauth2.rb +15 -2
- data/example/public/connect-to-qbo.svg +1 -0
- data/example/views/oauth2.erb +4 -14
- data/lib/qbo_api/api_methods.rb +2 -12
- data/lib/qbo_api/attachment.rb +20 -5
- data/lib/qbo_api/configuration.rb +0 -1
- data/lib/qbo_api/connection.rb +3 -31
- data/lib/qbo_api/entity.rb +0 -2
- data/lib/qbo_api/error.rb +5 -1
- data/lib/qbo_api/raise_http_exception.rb +4 -3
- data/lib/qbo_api/supporting.rb +0 -2
- data/lib/qbo_api/util.rb +0 -1
- data/lib/qbo_api/version.rb +1 -1
- data/lib/qbo_api.rb +2 -2
- data/qbo_api.gemspec +4 -3
- metadata +31 -20
- data/.env.example_app.oauth1 +0 -2
- data/example/oauth.rb +0 -62
- data/lib/qbo_api/connection/oauth1.rb +0 -60
- data/lib/qbo_api/connection/oauth2.rb +0 -24
checksums.yaml
CHANGED
|
@@ -1,7 +1,7 @@
|
|
|
1
1
|
---
|
|
2
2
|
SHA256:
|
|
3
|
-
metadata.gz:
|
|
4
|
-
data.tar.gz:
|
|
3
|
+
metadata.gz: 922f5a2dd0bb1020d9366c1a993686aa5febdb50e54a5b4c2a6160e572612def
|
|
4
|
+
data.tar.gz: '032848b350e352d8edaf376cd49b41fbaae20bccf902473d775e90c513fc0ff5'
|
|
5
5
|
SHA512:
|
|
6
|
-
metadata.gz:
|
|
7
|
-
data.tar.gz:
|
|
6
|
+
metadata.gz: c4f17dcf8f2fe0680c34dbb8cf9c864d7d42887f291a968023e1538902a8460cc13d968f669777b53efbc21000d1db44b6e78d21ad8619514dd62c7c0375ba10
|
|
7
|
+
data.tar.gz: f2d7a86d02a465e6cc9ce8de0110c250c0e500a5d02b7e0cbc402e3cae37ae11832592ecef08d6c58de8735fd0081fbc8adae277efff3698416fc40da4d02274
|
data/.gitignore
CHANGED
data/.travis.yml
CHANGED
|
@@ -1,8 +1,12 @@
|
|
|
1
1
|
sudo: false
|
|
2
2
|
language: ruby
|
|
3
3
|
rvm:
|
|
4
|
-
- 2.
|
|
5
|
-
- 2.
|
|
4
|
+
- 2.6.8
|
|
5
|
+
- 2.7.4
|
|
6
|
+
- 3.0.2
|
|
7
|
+
|
|
8
|
+
before_install:
|
|
9
|
+
- gem install bundler
|
|
6
10
|
|
|
7
11
|
before_script:
|
|
8
12
|
- cp .env.test .env
|
|
@@ -10,7 +14,6 @@ before_script:
|
|
|
10
14
|
script:
|
|
11
15
|
- bundle exec rspec spec/
|
|
12
16
|
|
|
13
|
-
|
|
14
17
|
notifications:
|
|
15
18
|
email:
|
|
16
19
|
- christian@minimul.com
|
data/README.md
CHANGED
|
@@ -1,20 +1,11 @@
|
|
|
1
1
|
# QboApi
|
|
2
2
|
|
|
3
3
|
Ruby client for the QuickBooks Online API version 3.
|
|
4
|
-
- Built on top of the excellent Faraday gem.
|
|
5
4
|
- JSON only support.
|
|
6
5
|
- Please don't ask about XML support. [Intuit has stated](https://github.com/ruckus/quickbooks-ruby/issues/257#issuecomment-126834454) that JSON is the primary data format for the QuickBooks API (v3 and beyond). This gem will specialize in JSON only. The [`quickbooks-ruby`](https://github.com/ruckus/quickbooks-ruby) gem has fantastic support for those who favor XML.
|
|
7
6
|
- Features specs built directly against a QuickBooks Online Sandbox via the VCR gem.
|
|
8
7
|
- Robust error handling.
|
|
9
8
|
|
|
10
|
-
## Tutorials and Screencasts
|
|
11
|
-
- <a href="http://minimul.com/introducing-a-new-ruby-quickbooks-online-client.html" target="_blank">Why qbo_api is a better choice </a> than the <a href="https://github.com/ruckus/quickbooks-ruby" target="_blank">quickbooks-ruby</a> gem.
|
|
12
|
-
- <a href="http://minimul.com/getting-started-with-the-modern-ruby-quickbooks-online-client-qbo_api-part-1.html" target="_blank">Part 1</a>: Learn how to spin up the <a href="https://github.com/minimul/qbo_api#spin-up-an-example">example app</a>.
|
|
13
|
-
- <a href="http://minimul.com/the-modern-ruby-quickbooks-client-part-2.html" target="_blank">Part 2</a>: <a href="https://github.com/minimul/qbo_api#running-the-specs">Running the specs</a> to aid you in understanding a QuickBooks API transaction.
|
|
14
|
-
- <a href="http://minimul.com/the-modern-ruby-quickbooks-client-contributing.html" target="_blank">Part 3</a>: <a href="https://github.com/minimul/qbo_api#creating-new-specs-or-modifying-existing-spec-that-have-been-recorded-using-the-vcr-gem">Contributing to the gem</a>.
|
|
15
|
-
### Important Note: The videos are out of date.
|
|
16
|
-
If you signed up for a Intuit developer account after July 17th, 2017 then you will have to
|
|
17
|
-
follow <a href='#OAuth2-example'>OAuth2: Spin up an example</a>
|
|
18
9
|
## The Book
|
|
19
10
|
|
|
20
11
|
<a href="https://leanpub.com/minimul-qbo-guide-vol-1" target="_blank">
|
|
@@ -22,7 +13,7 @@ follow <a href='#OAuth2-example'>OAuth2: Spin up an example</a>
|
|
|
22
13
|
</a>
|
|
23
14
|
|
|
24
15
|
|
|
25
|
-
## Ruby >= 2.
|
|
16
|
+
## Ruby >= 2.6 required
|
|
26
17
|
|
|
27
18
|
## Installation
|
|
28
19
|
|
|
@@ -43,41 +34,22 @@ Or install it yourself as:
|
|
|
43
34
|
## Usage
|
|
44
35
|
|
|
45
36
|
### Initialize
|
|
46
|
-
#### OAuth
|
|
47
|
-
```ruby
|
|
48
|
-
q = account.qbo_account # or wherever you are storing the OAuth creds
|
|
49
|
-
qbo_api = QboApi.new(token: q.token,
|
|
50
|
-
token_secret: q.secret,
|
|
51
|
-
realm_id: q.companyid,
|
|
52
|
-
consumer_key: '*****',
|
|
53
|
-
consumer_secret: '********')
|
|
54
|
-
```
|
|
55
|
-
#### OAuth2
|
|
56
37
|
```ruby
|
|
57
38
|
qbo_api = QboApi.new(access_token: 'REWR342532asdfae!$4asdfa', realm_id: 32095430444)
|
|
39
|
+
- qbo_api.get :customer, 1
|
|
58
40
|
```
|
|
59
41
|
|
|
60
|
-
### Super fast way to use QboApi
|
|
42
|
+
### Super fast way to use QboApi as long as Ruby >= 2.5 is installed
|
|
61
43
|
```
|
|
62
44
|
- cd ~/<local dir>
|
|
63
45
|
- git clone git@github.com:minimul/qbo_api.git && cd qbo_api
|
|
64
46
|
- bundle
|
|
65
47
|
- bin/console
|
|
66
48
|
- QboApi.production = true
|
|
67
|
-
-
|
|
68
|
-
-
|
|
69
|
-
token_secret:"g8wcyQEtwxxxxxxm",
|
|
70
|
-
realm_id: "12314xxxxxx7",
|
|
71
|
-
consumer_key: "qyprdwzcxxxxxxbIWsIMIy9PYI",
|
|
72
|
-
consumer_secret: "CyDN4wpxxxxxxxPMv7hDhmh4")
|
|
73
|
-
- # OAuth 2
|
|
74
|
-
- qboapi = QboApi.new(access_token: "qyprd2uvCOdRq8xzoSSiiiiii", realm_id: "12314xxxxxx7")
|
|
75
|
-
- qboapi.get :customer, 1
|
|
49
|
+
- qbo_api = QboApi.new(access_token: "qyprd2uvCOdRq8xzoSSiiiiii", realm_id: "12314xxxxxx7")
|
|
50
|
+
- qbo_api.get :customer, 1
|
|
76
51
|
```
|
|
77
52
|
|
|
78
|
-
### TLS v1.2
|
|
79
|
-
Intuit will be [requiring](https://developer.intuit.com/hub/blog/2017/08/03/upgrading-your-apps-to-support-tls-1-2) API client connections to be negotiated over TLS1.2 by December 31st, 2017. Using the default HTTP client (Net::HTTP) with Faraday this is the case with QboApi, however, if you are using another HTTP client you may need to directly set the TLS version negotiation manually.
|
|
80
|
-
|
|
81
53
|
### DateTime serialization
|
|
82
54
|
Some QBO entities have attributes of type DateTime (e.g., Time Activities with StartTime and EndTime). All DateTimes passed to the QBO API must be serialized in ISO 8601 format.
|
|
83
55
|
If ActiveSupport is loaded, you can achieve proper serialization with the following configuration:
|
|
@@ -119,7 +91,6 @@ QboApi.minor_version = 8
|
|
|
119
91
|
# Works with .get, .create, .update, .query methods
|
|
120
92
|
```
|
|
121
93
|
|
|
122
|
-
|
|
123
94
|
### Create
|
|
124
95
|
```ruby
|
|
125
96
|
invoice = {
|
|
@@ -191,6 +162,40 @@ QboApi.minor_version = 8
|
|
|
191
162
|
p response.size # => 28
|
|
192
163
|
```
|
|
193
164
|
|
|
165
|
+
### Import/retrieve all
|
|
166
|
+
*Note: There is some overlap with the `all` and the `get` methods. The `get` method is limited to 1000 results where the `all` method will return all the results no matter the number.*
|
|
167
|
+
```ruby
|
|
168
|
+
# retrieves all active customers
|
|
169
|
+
qbo_api.all(:customers).each do |c|
|
|
170
|
+
p "#{c['Id']} #{c['DisplayName']}"
|
|
171
|
+
end
|
|
172
|
+
|
|
173
|
+
# retrieves all active or inactive employees
|
|
174
|
+
qbo_api.all(:employees, inactive: true).each do |e|
|
|
175
|
+
p "#{e['Id']} #{e['DisplayName']}"
|
|
176
|
+
end
|
|
177
|
+
|
|
178
|
+
# retrieves all vendors by groups of 5
|
|
179
|
+
qbo_api.all(:vendor, max: 5).each do |v|
|
|
180
|
+
p v['DisplayName']
|
|
181
|
+
end
|
|
182
|
+
|
|
183
|
+
# retrieves all customers by groups of 2 using a custom select query
|
|
184
|
+
where = "WHERE Id IN ('5', '6', '7', '8', '9', '10')"
|
|
185
|
+
qbo_api.all(:customer, max: 2, select: "SELECT * FROM Customer #{where}").each do |c|
|
|
186
|
+
p c['DisplayName']
|
|
187
|
+
end
|
|
188
|
+
```
|
|
189
|
+
|
|
190
|
+
#### Note: .all() returns a Ruby Enumerator
|
|
191
|
+
|
|
192
|
+
```
|
|
193
|
+
api.all(:clients).take(50).each { |c| p c["Id"] }
|
|
194
|
+
api.all(:clients).count
|
|
195
|
+
api.all(:clients).first
|
|
196
|
+
api.all(:clients).to_a
|
|
197
|
+
```
|
|
198
|
+
|
|
194
199
|
### Search with irregular characters
|
|
195
200
|
```ruby
|
|
196
201
|
# Use the .esc() method
|
|
@@ -264,7 +269,7 @@ Be aware that any errors will not raise a `QboApi::Error`, but will be returned
|
|
|
264
269
|
}
|
|
265
270
|
]
|
|
266
271
|
}
|
|
267
|
-
response =
|
|
272
|
+
response = qbo_api.batch(payload)
|
|
268
273
|
expect(response['BatchItemResponse'].size).to eq 2
|
|
269
274
|
expect(batch_response.detect{ |b| b["bId"] == "bid1" }["Vendor"]["DisplayName"]).to eq "Smith Family Store"
|
|
270
275
|
```
|
|
@@ -273,7 +278,7 @@ Be aware that any errors will not raise a `QboApi::Error`, but will be returned
|
|
|
273
278
|
|
|
274
279
|
```ruby
|
|
275
280
|
params = { start_date: '2015-01-01', end_date: '2015-07-31', customer: 1, summarize_column_by: 'Customers' }
|
|
276
|
-
response =
|
|
281
|
+
response = qbo_api.reports(name: 'ProfitAndLoss', params: params)
|
|
277
282
|
p response["Header"]["ReportName"]) #=> 'ProfitAndLoss'
|
|
278
283
|
```
|
|
279
284
|
|
|
@@ -310,31 +315,6 @@ See [docs](https://developer.intuit.com/docs/0100_quickbooks_online/0100_essenti
|
|
|
310
315
|
end
|
|
311
316
|
```
|
|
312
317
|
|
|
313
|
-
### Import/retrieve all
|
|
314
|
-
*Note: There is some overlap with the `all` and the `get` methods. The `get` method is limited to 1000 results where the `all` method will return all the results no matter the number.*
|
|
315
|
-
```ruby
|
|
316
|
-
# retrieves all active customers
|
|
317
|
-
qbo_api.all(:customers).each do |c|
|
|
318
|
-
p "#{c['Id']} #{c['DisplayName']}"
|
|
319
|
-
end
|
|
320
|
-
|
|
321
|
-
# retrieves all active or inactive employees
|
|
322
|
-
qbo_api.all(:employees, inactive: true).each do |e|
|
|
323
|
-
p "#{e['Id']} #{e['DisplayName']}"
|
|
324
|
-
end
|
|
325
|
-
|
|
326
|
-
# retrieves all vendors by groups of 5
|
|
327
|
-
qbo_api.all(:vendor, max: 5).each do |v|
|
|
328
|
-
p v['DisplayName']
|
|
329
|
-
end
|
|
330
|
-
|
|
331
|
-
# retrieves all customers by groups of 2 using a custom select query
|
|
332
|
-
where = "WHERE Id IN ('5', '6', '7', '8', '9', '10')"
|
|
333
|
-
qbo_api.all(:customer, max: 2, select: "SELECT * FROM Customer #{where}").each do |c|
|
|
334
|
-
p c['DisplayName']
|
|
335
|
-
end
|
|
336
|
-
```
|
|
337
|
-
|
|
338
318
|
### What kind of QuickBooks entity?
|
|
339
319
|
```ruby
|
|
340
320
|
p qbo_api.is_transaction_entity?(:invoice) # => true
|
|
@@ -343,9 +323,8 @@ See [docs](https://developer.intuit.com/docs/0100_quickbooks_online/0100_essenti
|
|
|
343
323
|
p qbo_api.is_transaction_entity?(:customer) # => false
|
|
344
324
|
p qbo_api.is_name_list_entity?(:vendors) # => true
|
|
345
325
|
```
|
|
346
|
-
## <a name='OAuth2-example'>
|
|
347
|
-
|
|
348
|
-
- <a href="http://minimul.com/access-the-quickbooks-online-api-with-oauth2.html" target="_blank">Check out this article on spinning up the OAuth2 example</a>.
|
|
326
|
+
## <a name='OAuth2-example'>Spin up an example</a>
|
|
327
|
+
- <a href="http://minimul.com/access-the-quickbooks-online-api-with-oauth2.html" target="_blank">Check out this article on spinning up the example</a>.
|
|
349
328
|
- `git clone git://github.com/minimul/qbo_api && cd qbo_api`
|
|
350
329
|
- `bundle`
|
|
351
330
|
- Create a `.env` file
|
|
@@ -360,7 +339,7 @@ See [docs](https://developer.intuit.com/docs/0100_quickbooks_online/0100_essenti
|
|
|
360
339
|
- Create a new Company ([from the manage sandboxes page](https://developer.intuit.com/v2/ui#/sandbox))
|
|
361
340
|
Don't use it for anything else besides testing this app.
|
|
362
341
|
-. Copy the 'Company ID' to your .env as QBO_API_COMPANY_ID
|
|
363
|
-
- Start up the example
|
|
342
|
+
- Start up the example app
|
|
364
343
|
- `ruby example/oauth2.rb`
|
|
365
344
|
- Go to `http://localhost:9393/oauth2`
|
|
366
345
|
- Use the `Connect to QuickBooks` button to connect to your QuickBooks sandbox, which you receive when signing up at [https://developer.intuit.com](https://developer.intuit.com).
|
|
@@ -370,35 +349,13 @@ See [docs](https://developer.intuit.com/docs/0100_quickbooks_online/0100_essenti
|
|
|
370
349
|
- Checkout [`example/oauth2.rb`](https://github.com/minimul/qbo_api/blob/master/example/oauth2.rb)
|
|
371
350
|
to see what is going on under the hood.
|
|
372
351
|
|
|
373
|
-
## OAuth1: Spin up an example
|
|
374
|
-
### OLD LEGACY - SEE OAUTH2 EXAMPLE ABOVE
|
|
375
|
-
- <a href="http://minimul.com/getting-started-with-the-modern-ruby-quickbooks-online-client-qbo_api-part-1.html" target="_blank">Check out this tutorial and screencast on spinning up an example</a>.
|
|
376
|
-
- `git clone git://github.com/minimul/qbo_api && cd qbo_api`
|
|
377
|
-
- `bundle`
|
|
378
|
-
- Create a `.env` file
|
|
379
|
-
- `cp .env.example_app.oauth1 .env`
|
|
380
|
-
- If needed create an account at [https://developer.intuit.com](https://developer.intuit.com)
|
|
381
|
-
- Click `Get started coding`
|
|
382
|
-
- Create an app with both the `Accounting` & `Payments` selected.
|
|
383
|
-
- Go to the `Development` tab and copy and paste the consumer key and secret into the `.env` file
|
|
384
|
-
as QBO_API_CONSUMER_KEY and QBO_API_CONSUMER_SECRET respectively.
|
|
385
|
-
- Start up the example app
|
|
386
|
-
- `ruby example/oauth.rb`
|
|
387
|
-
- Go to `http://localhost:9393`
|
|
388
|
-
- Use the `Connect to QuickBooks` button to connect to your QuickBooks sandbox, which you receive when signing up at [https://developer.intuit.com](https://developer.intuit.com).
|
|
389
|
-
- After successfully connecting to your sandbox run:
|
|
390
|
-
- `http://localhost:9393/customer/5`
|
|
391
|
-
- You should see "Dukes Basketball Camp" displayed
|
|
392
|
-
- Checkout [`example/oauth.rb`](https://github.com/minimul/qbo_api/blob/master/example/oauth.rb)
|
|
393
|
-
to see what is going on under the hood.
|
|
394
|
-
|
|
395
352
|
## Webhooks
|
|
396
353
|
- <a href="http://minimul.com/getting-started-with-quickbooks-online-webhooks.html" target="_blank">Check out this tutorial and screencast on handling a webhook request</a>. Also checkout [`example/app.rb`](https://github.com/minimul/qbo_api/blob/master/example/app.rb) for the request handling code.
|
|
397
354
|
|
|
398
355
|
See https://www.twilio.com/blog/2015/09/6-awesome-reasons-to-use-ngrok-when-testing-webhooks.html
|
|
399
356
|
for how to install ngrok and what it is.
|
|
400
357
|
|
|
401
|
-
- With
|
|
358
|
+
- With the example app running, run:
|
|
402
359
|
`ngrok http 9393 -subdomain=somereasonablyuniquenamehere`
|
|
403
360
|
|
|
404
361
|
- Go to the [`Development` tab](https://developer.intuit.com/v2/ui#/app/dashboard)
|
|
@@ -408,7 +365,7 @@ for how to install ngrok and what it is.
|
|
|
408
365
|
- After saving the webhook, click 'show token'.
|
|
409
366
|
Add the token to your .env as QBO_API_VERIFIER_TOKEN
|
|
410
367
|
|
|
411
|
-
- In another tab, create a customer via the
|
|
368
|
+
- In another tab, create a customer via the API:
|
|
412
369
|
`bundle exec ruby -rqbo_api -rdotenv -e 'Dotenv.load; p QboApi.new(access_token: ENV.fetch("QBO_API_OAUTH2_ACCESS_TOKEN"), realm_id: ENV.fetch("QBO_API_COMPANY_ID")).create(:customer, payload: { DisplayName: "TestCustomer" })'`
|
|
413
370
|
(You'll also need to have added the QBO_API_COMPANY_ID and QBO_API_OAUTH2_ACCESS_TOKEN to your .env)
|
|
414
371
|
|
|
@@ -421,6 +378,28 @@ for how to install ngrok and what it is.
|
|
|
421
378
|
"POST /webhooks HTTP/1.1" 200 - 0.0013
|
|
422
379
|
```
|
|
423
380
|
|
|
381
|
+
### Just For Hackers
|
|
382
|
+
|
|
383
|
+
- Using the build_connection method
|
|
384
|
+
```
|
|
385
|
+
connection = build_connection('https://oauth.platform.intuit.com', headers: { 'Accept' => 'application/json' }) do |conn|
|
|
386
|
+
conn.basic_auth(client_id, client_secret)
|
|
387
|
+
conn.request :url_encoded # application/x-www-form-urlencoded
|
|
388
|
+
conn.use FaradayMiddleware::ParseJson, parser_options: { symbolize_names: true }
|
|
389
|
+
conn.use Faraday::Response::RaiseError
|
|
390
|
+
end
|
|
391
|
+
|
|
392
|
+
raw_response = connection.post do |req|
|
|
393
|
+
req.body = { grant_type: :refresh_token, refresh_token: current_refresh_token }
|
|
394
|
+
req.url '/oauth2/v1/tokens/bearer'
|
|
395
|
+
end
|
|
396
|
+
```
|
|
397
|
+
- Once your .env file is completely filled out you can use the console to play around in your sandbox
|
|
398
|
+
```
|
|
399
|
+
bin/console test
|
|
400
|
+
>> @qbo_api.get :customer, 1
|
|
401
|
+
```
|
|
402
|
+
|
|
424
403
|
## Contributing
|
|
425
404
|
|
|
426
405
|
Bug reports and pull requests are welcome on GitHub at https://github.com/minimul/qbo_api.
|
|
@@ -438,11 +417,6 @@ Bug reports and pull requests are welcome on GitHub at https://github.com/minimu
|
|
|
438
417
|
- All specs that require interaction with the API must be recorded against your personal QuickBooks sandbox. More coming on how to create or modifying existing specs against your sandbox.
|
|
439
418
|
- <a href="http://minimul.com/the-modern-ruby-quickbooks-client-contributing.html" target="_blank">Check out this tutorial and screencast on contributing to qbo_api</a>.
|
|
440
419
|
|
|
441
|
-
#### Protip: Once your .env file is completely filled out you can use the console to play around in your sandbox
|
|
442
|
-
```
|
|
443
|
-
bin/console test
|
|
444
|
-
>> @qbo_api.get :customer, 1
|
|
445
|
-
```
|
|
446
420
|
|
|
447
421
|
## License
|
|
448
422
|
|
data/example/base.rb
CHANGED
data/example/oauth2.rb
CHANGED
|
@@ -24,16 +24,29 @@ class OAuth2App < Sinatra::Base
|
|
|
24
24
|
Rack::OAuth2::Client.new(
|
|
25
25
|
identifier: CLIENT_ID,
|
|
26
26
|
secret: CLIENT_SECRET,
|
|
27
|
-
redirect_uri:
|
|
27
|
+
redirect_uri: redirect_url,
|
|
28
28
|
authorization_endpoint: "https://appcenter.intuit.com/connect/oauth2",
|
|
29
29
|
token_endpoint: "https://oauth.platform.intuit.com/oauth2/v1/tokens/bearer"
|
|
30
30
|
)
|
|
31
31
|
end
|
|
32
|
+
|
|
33
|
+
def authorize_url(state:)
|
|
34
|
+
oauth2_client.authorization_uri(
|
|
35
|
+
client_id: CLIENT_ID,
|
|
36
|
+
scope: "com.intuit.quickbooks.accounting",
|
|
37
|
+
redirect_uri: redirect_url,
|
|
38
|
+
response_type: "code",
|
|
39
|
+
state: state
|
|
40
|
+
)
|
|
41
|
+
end
|
|
42
|
+
|
|
43
|
+
def redirect_url
|
|
44
|
+
"http://localhost:#{PORT}/oauth2-redirect"
|
|
45
|
+
end
|
|
32
46
|
end
|
|
33
47
|
|
|
34
48
|
get '/oauth2' do
|
|
35
49
|
session[:state] = SecureRandom.uuid
|
|
36
|
-
@client = oauth2_client
|
|
37
50
|
erb :oauth2
|
|
38
51
|
end
|
|
39
52
|
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
<svg xmlns="http://www.w3.org/2000/svg" style="isolation:isolate" viewBox="0 0 775.39 132"><defs><clipPath id="a"><path d="M0 0h775.39v132H0z"/></clipPath></defs><g clip-path="url(#a)"><path d="M775.395 124c0 4.4-3.6 8-8 8H8c-4.4 0-8-3.6-8-8V8c0-4.4 3.6-8 8-8h759.395c4.4 0 8 3.6 8 8v116z" fill="#328538"/><path d="M775.395 124c0 4.4-3.6 8-8 8H8c-4.4 0-8-3.6-8-8V8c0-4.4 3.6-8 8-8h759.395c4.4 0 8 3.6 8 8v116z" fill="none" vector-effect="non-scaling-stroke" stroke-width="4" stroke="#328538" stroke-miterlimit="10"/><path d="M178.168 56.127c-1.033-1.4-2.38-2.424-4.039-3.07-1.66-.645-3.284-.968-4.869-.968-2.028 0-3.872.368-5.532 1.106a13.005 13.005 0 0 0-4.287 3.042c-1.198 1.292-2.121 2.804-2.766 4.538-.646 1.733-.968 3.614-.968 5.642 0 2.14.313 4.093.941 5.864.627 1.771 1.521 3.291 2.683 4.563a12.012 12.012 0 0 0 4.176 2.96c1.622.703 3.448 1.052 5.477 1.052 2.103 0 3.964-.415 5.588-1.244 1.623-.831 2.932-1.928 3.928-3.292l5.587 3.926a17.878 17.878 0 0 1-6.362 5.063c-2.509 1.198-5.441 1.799-8.796 1.799-3.062 0-5.873-.508-8.437-1.523-2.564-1.014-4.767-2.433-6.611-4.258-1.844-1.826-3.282-4.002-4.314-6.53-1.034-2.524-1.55-5.318-1.55-8.38 0-3.134.544-5.965 1.632-8.492 1.088-2.527 2.582-4.674 4.482-6.445 1.898-1.77 4.14-3.135 6.721-4.094 2.581-.958 5.384-1.437 8.408-1.437 1.255 0 2.564.119 3.928.359 1.365.24 2.675.608 3.928 1.105a19.141 19.141 0 0 1 3.541 1.855 11.42 11.42 0 0 1 2.82 2.654l-5.309 4.205m13.056 16.597c0 1.032.156 2.065.471 3.097a8.468 8.468 0 0 0 1.41 2.767 7.381 7.381 0 0 0 2.378 1.991c.96.517 2.102.774 3.43.774 1.328 0 2.471-.257 3.43-.774a7.42 7.42 0 0 0 2.38-1.991 8.566 8.566 0 0 0 1.41-2.767 10.66 10.66 0 0 0 .47-3.097c0-1.033-.158-2.056-.47-3.071a8.637 8.637 0 0 0-1.41-2.738 7.1 7.1 0 0 0-2.38-1.963c-.959-.5-2.102-.748-3.43-.748-1.328 0-2.47.248-3.43.748a7.063 7.063 0 0 0-2.378 1.963 8.536 8.536 0 0 0-1.41 2.738 10.303 10.303 0 0 0-.471 3.071zm-6.749 0c0-2.103.377-4.011 1.134-5.726.755-1.714 1.779-3.181 3.07-4.398 1.29-1.217 2.821-2.157 4.592-2.821 1.77-.664 3.65-.996 5.642-.996 1.992 0 3.872.332 5.643.996 1.771.664 3.3 1.604 4.592 2.821 1.291 1.217 2.313 2.684 3.071 4.398.754 1.715 1.133 3.623 1.133 5.726 0 2.103-.379 4.02-1.133 5.753-.758 1.733-1.78 3.218-3.071 4.454-1.292 1.236-2.821 2.203-4.592 2.903-1.771.7-3.651 1.052-5.643 1.052s-3.872-.352-5.642-1.052c-1.771-.7-3.302-1.667-4.592-2.903-1.291-1.236-2.315-2.721-3.07-4.454-.757-1.733-1.134-3.65-1.134-5.753m33.91-13.167h6.307v4.26h.111c.589-1.328 1.612-2.498 3.069-3.513 1.457-1.015 3.181-1.521 5.173-1.521 1.734 0 3.218.303 4.454.912 1.234.609 2.249 1.412 3.042 2.408a9.715 9.715 0 0 1 1.742 3.429 14.43 14.43 0 0 1 .554 3.983v16.597h-6.638V71.396c0-.775-.056-1.586-.167-2.435a6.59 6.59 0 0 0-.719-2.294 4.775 4.775 0 0 0-1.521-1.688c-.647-.443-1.504-.664-2.572-.664-1.071 0-1.992.212-2.767.637a5.872 5.872 0 0 0-1.908 1.631 7.188 7.188 0 0 0-1.134 2.296 9.124 9.124 0 0 0-.387 2.628v14.605h-6.639V59.557m30.814 0h6.306v4.26h.111c.588-1.328 1.612-2.498 3.069-3.513 1.458-1.015 3.182-1.521 5.174-1.521 1.732 0 3.217.303 4.452.912 1.236.609 2.25 1.412 3.044 2.408a9.713 9.713 0 0 1 1.741 3.429c.369 1.292.553 2.619.553 3.983v16.597h-6.638V71.396c0-.775-.055-1.586-.166-2.435a6.569 6.569 0 0 0-.718-2.294 4.788 4.788 0 0 0-1.522-1.688c-.646-.443-1.504-.664-2.572-.664-1.07 0-1.992.212-2.766.637a5.851 5.851 0 0 0-1.908 1.631 7.169 7.169 0 0 0-1.135 2.296 9.124 9.124 0 0 0-.387 2.628v14.605h-6.638V59.557m49.51 10.622c0-.848-.12-1.66-.358-2.435a5.614 5.614 0 0 0-1.135-2.047c-.516-.588-1.171-1.06-1.964-1.411-.793-.349-1.724-.525-2.793-.525-1.992 0-3.679.6-5.063 1.799-1.383 1.198-2.148 2.737-2.295 4.619h13.608zm6.639 2.988v.885c0 .294-.019.589-.055.884h-20.192c.072.96.322 1.836.747 2.628a6.69 6.69 0 0 0 1.687 2.048 8.437 8.437 0 0 0 2.378 1.355 7.86 7.86 0 0 0 2.767.497c1.659 0 3.06-.304 4.204-.912a7.856 7.856 0 0 0 2.821-2.518l4.426 3.541c-2.619 3.541-6.418 5.311-11.396 5.311-2.066 0-3.964-.323-5.698-.969-1.734-.644-3.236-1.557-4.509-2.738-1.272-1.179-2.268-2.627-2.987-4.342-.72-1.716-1.078-3.661-1.078-5.837 0-2.139.358-4.084 1.078-5.836.719-1.752 1.706-3.245 2.96-4.481 1.254-1.235 2.738-2.194 4.452-2.878 1.716-.681 3.57-1.022 5.56-1.022 1.844 0 3.55.303 5.118.912a11.122 11.122 0 0 1 4.066 2.71c1.143 1.2 2.038 2.693 2.683 4.483.645 1.788.968 3.881.968 6.279m23.179-6.252c-.518-.738-1.291-1.355-2.324-1.852-1.032-.5-2.084-.748-3.152-.748-1.218 0-2.288.248-3.21.748a6.992 6.992 0 0 0-2.296 1.962 8.446 8.446 0 0 0-1.354 2.739 10.907 10.907 0 0 0-.443 3.07c0 1.033.156 2.057.471 3.07a8.538 8.538 0 0 0 1.409 2.739 7.183 7.183 0 0 0 2.352 1.964c.94.498 2.037.746 3.292.746a8.386 8.386 0 0 0 3.097-.608c1.032-.405 1.862-.996 2.49-1.77l4.149 4.204c-1.107 1.181-2.517 2.094-4.232 2.738-1.715.646-3.568.969-5.56.969-1.956 0-3.808-.314-5.56-.941-1.752-.626-3.283-1.549-4.592-2.766-1.309-1.218-2.341-2.691-3.097-4.426-.756-1.733-1.134-3.707-1.134-5.919 0-2.138.378-4.074 1.134-5.809.756-1.733 1.778-3.208 3.07-4.425a13.728 13.728 0 0 1 4.508-2.821c1.715-.664 3.55-.996 5.506-.996 1.954 0 3.844.369 5.67 1.106 1.826.738 3.272 1.752 4.342 3.043l-4.536 3.983m6.417-2.047v-5.311h4.647v-7.689h6.528v7.689h6.638v5.311h-6.638v12.336c0 1.181.212 2.157.636 2.932.424.774 1.373 1.161 2.849 1.161.443 0 .921-.045 1.439-.137a5.718 5.718 0 0 0 1.382-.415l.222 5.2c-.591.222-1.291.395-2.103.526-.811.129-1.585.194-2.323.194-1.77 0-3.209-.25-4.314-.748-1.107-.497-1.984-1.18-2.628-2.047-.646-.865-1.088-1.862-1.328-2.986a17.355 17.355 0 0 1-.36-3.624V64.868h-4.647m29.872 0v-5.311h4.648v-7.689h6.527v7.689h6.638v5.311h-6.638v12.336c0 1.181.212 2.157.637 2.932.423.774 1.373 1.161 2.849 1.161.443 0 .92-.045 1.438-.137a5.704 5.704 0 0 0 1.382-.415l.222 5.2c-.591.222-1.291.395-2.102.526-.812.129-1.586.194-2.324.194-1.77 0-3.208-.25-4.314-.748-1.107-.497-1.983-1.18-2.628-2.047-.646-.865-1.088-1.862-1.328-2.986a17.356 17.356 0 0 1-.359-3.624V64.868h-4.648m26.444 7.856c0 1.032.156 2.065.469 3.097a8.512 8.512 0 0 0 1.412 2.767 7.381 7.381 0 0 0 2.378 1.991c.958.517 2.102.774 3.43.774 1.328 0 2.471-.257 3.43-.774a7.392 7.392 0 0 0 2.378-1.991 8.531 8.531 0 0 0 1.412-2.767 10.66 10.66 0 0 0 .47-3.097c0-1.033-.158-2.056-.47-3.071a8.601 8.601 0 0 0-1.412-2.738 7.072 7.072 0 0 0-2.378-1.963c-.959-.5-2.102-.748-3.43-.748-1.328 0-2.472.248-3.43.748a7.063 7.063 0 0 0-2.378 1.963 8.58 8.58 0 0 0-1.412 2.738 10.365 10.365 0 0 0-.469 3.071zm-6.749 0c0-2.103.377-4.011 1.133-5.726.756-1.714 1.779-3.181 3.071-4.398 1.29-1.217 2.821-2.157 4.592-2.821 1.77-.664 3.65-.996 5.642-.996 1.992 0 3.872.332 5.643.996 1.771.664 3.3 1.604 4.592 2.821 1.291 1.217 2.313 2.684 3.071 4.398.754 1.715 1.133 3.623 1.133 5.726 0 2.103-.379 4.02-1.133 5.753-.758 1.733-1.78 3.218-3.071 4.454-1.292 1.236-2.821 2.203-4.592 2.903-1.771.7-3.651 1.052-5.643 1.052s-3.872-.352-5.642-1.052c-1.771-.7-3.302-1.667-4.592-2.903-1.292-1.236-2.315-2.721-3.071-4.454-.756-1.733-1.133-3.65-1.133-5.753" fill="#FFF"/><path d="M449.899 52.2c-1.882 0-3.643.351-5.283 1.051-1.641.701-3.053 1.658-4.233 2.876-1.18 1.217-2.111 2.674-2.794 4.371-.682 1.697-1.024 3.541-1.024 5.531 0 2.103.323 4.011.968 5.727.646 1.715 1.551 3.18 2.712 4.397 1.162 1.217 2.554 2.167 4.176 2.85 1.623.682 3.412 1.022 5.367 1.022 1.917 0 3.696-.34 5.339-1.022 1.64-.683 3.05-1.633 4.232-2.85 1.178-1.217 2.101-2.682 2.765-4.397.664-1.716.996-3.624.996-5.727 0-1.99-.313-3.834-.94-5.531-.628-1.697-1.521-3.154-2.683-4.371-1.162-1.218-2.554-2.175-4.177-2.876-1.623-.7-3.429-1.051-5.421-1.051zm23.51 33.912h-23.621c-3.136 0-5.984-.452-8.548-1.356-2.563-.904-4.757-2.213-6.583-3.928-1.825-1.715-3.236-3.818-4.232-6.307-.996-2.489-1.493-5.318-1.493-8.492 0-2.986.525-5.707 1.576-8.16 1.052-2.452 2.517-4.564 4.399-6.333 1.88-1.771 4.101-3.144 6.665-4.123 2.564-.976 5.339-1.464 8.327-1.464 2.986 0 5.753.488 8.298 1.464 2.544.979 4.748 2.352 6.611 4.123 1.861 1.769 3.309 3.881 4.341 6.333 1.034 2.453 1.551 5.174 1.551 8.16 0 1.771-.204 3.393-.609 4.868-.407 1.476-.932 2.813-1.578 4.011a15.475 15.475 0 0 1-2.212 3.155 16.224 16.224 0 0 1-2.573 2.294v.111h9.681v5.644m27.439 0h-6.307v-4.261h-.11c-.591 1.328-1.614 2.498-3.07 3.513-1.457 1.015-3.181 1.522-5.173 1.522-1.733 0-3.217-.305-4.453-.913-1.236-.609-2.25-1.41-3.042-2.408a9.677 9.677 0 0 1-1.744-3.429 14.461 14.461 0 0 1-.553-3.983V59.557h6.639v14.716c0 .773.056 1.586.166 2.434.111.849.351 1.613.719 2.296a4.767 4.767 0 0 0 1.521 1.686c.646.443 1.503.664 2.572.664 1.034 0 1.946-.212 2.74-.636.792-.424 1.438-.968 1.936-1.632a7.23 7.23 0 0 0 1.134-2.296 9.19 9.19 0 0 0 .386-2.626V59.557h6.639v26.555m6.693-26.555h6.639v26.555h-6.639V59.557zm-.941-9.017c0-1.069.397-2 1.189-2.795.794-.792 1.799-1.188 3.016-1.188 1.218 0 2.24.379 3.07 1.134.83.757 1.245 1.705 1.245 2.849 0 1.143-.415 2.093-1.245 2.849-.83.756-1.852 1.133-3.07 1.133-1.217 0-2.222-.395-3.016-1.188-.792-.793-1.189-1.724-1.189-2.794zm32.419 16.375c-.518-.738-1.291-1.355-2.324-1.852-1.032-.5-2.084-.748-3.154-.748-1.217 0-2.286.248-3.208.748a6.962 6.962 0 0 0-2.296 1.962 8.47 8.47 0 0 0-1.356 2.739 10.978 10.978 0 0 0-.442 3.07c0 1.033.157 2.057.47 3.07a8.583 8.583 0 0 0 1.411 2.739 7.183 7.183 0 0 0 2.352 1.964c.94.498 2.036.746 3.291.746a8.395 8.395 0 0 0 3.098-.608c1.032-.405 1.862-.996 2.49-1.77l4.149 4.204c-1.107 1.181-2.517 2.094-4.232 2.738-1.716.646-3.568.969-5.56.969-1.956 0-3.809-.314-5.56-.941-1.752-.626-3.283-1.549-4.592-2.766-1.309-1.218-2.343-2.691-3.097-4.426-.758-1.733-1.135-3.707-1.135-5.919 0-2.138.377-4.074 1.135-5.809.754-1.733 1.778-3.208 3.07-4.425a13.718 13.718 0 0 1 4.508-2.821c1.715-.664 3.55-.996 5.504-.996 1.955 0 3.846.369 5.671 1.106 1.825.738 3.272 1.752 4.343 3.043l-4.536 3.983m7.578-22.627h6.639v26.444h.165l10.07-11.175h8.518l-11.506 12.006 12.225 14.549h-8.795l-10.512-13.609h-.165v13.609h-6.639V44.288zm35.847 35.958h6.252c.885 0 1.843-.063 2.876-.193a9.396 9.396 0 0 0 2.849-.802 5.593 5.593 0 0 0 2.158-1.77c.572-.774.857-1.808.857-3.097 0-2.065-.701-3.504-2.101-4.316-1.403-.811-3.523-1.217-6.363-1.217h-6.528v11.395zm0-17.37h6.196c2.324 0 4.093-.46 5.311-1.383 1.217-.921 1.826-2.23 1.826-3.928 0-1.77-.628-3.022-1.881-3.761-1.255-.739-3.209-1.107-5.864-1.107h-5.588v10.179zm-6.969-15.932h15.268c1.474 0 2.932.175 4.37.525 1.439.351 2.719.923 3.844 1.715 1.126.793 2.038 1.817 2.739 3.071.7 1.253 1.052 2.765 1.052 4.536 0 2.213-.628 4.038-1.881 5.477-1.255 1.439-2.896 2.471-4.924 3.097v.111c2.47.332 4.5 1.292 6.085 2.877 1.585 1.587 2.379 3.707 2.379 6.363 0 2.139-.424 3.936-1.272 5.393-.85 1.456-1.964 2.627-3.348 3.512-1.383.886-2.968 1.522-4.756 1.91a25.792 25.792 0 0 1-5.45.581h-14.106V46.944m39.277 25.78c0 1.032.156 2.065.469 3.097a8.49 8.49 0 0 0 1.411 2.767 7.395 7.395 0 0 0 2.379 1.991c.958.517 2.102.774 3.43.774 1.327 0 2.47-.257 3.43-.774a7.413 7.413 0 0 0 2.378-1.991 8.51 8.51 0 0 0 1.411-2.767c.313-1.032.471-2.065.471-3.097 0-1.033-.158-2.056-.471-3.071a8.578 8.578 0 0 0-1.411-2.738 7.092 7.092 0 0 0-2.378-1.963c-.96-.5-2.103-.748-3.43-.748-1.328 0-2.472.248-3.43.748a7.076 7.076 0 0 0-2.379 1.963 8.558 8.558 0 0 0-1.411 2.738 10.365 10.365 0 0 0-.469 3.071zm-6.749 0c0-2.103.377-4.011 1.133-5.726.756-1.714 1.779-3.181 3.071-4.398 1.29-1.217 2.821-2.157 4.59-2.821 1.771-.664 3.652-.996 5.644-.996 1.991 0 3.872.332 5.643.996 1.769.664 3.3 1.604 4.591 2.821 1.29 1.217 2.314 2.684 3.07 4.398.756 1.715 1.135 3.623 1.135 5.726 0 2.103-.379 4.02-1.135 5.753-.756 1.733-1.78 3.218-3.07 4.454-1.291 1.236-2.822 2.203-4.591 2.903-1.771.7-3.652 1.052-5.643 1.052-1.992 0-3.873-.352-5.644-1.052-1.769-.7-3.3-1.667-4.59-2.903-1.292-1.236-2.315-2.721-3.071-4.454-.756-1.733-1.133-3.65-1.133-5.753m39.11 0c0 1.032.156 2.065.471 3.097a8.47 8.47 0 0 0 1.411 2.767 7.367 7.367 0 0 0 2.377 1.991c.96.517 2.103.774 3.431.774 1.328 0 2.47-.257 3.429-.774a7.41 7.41 0 0 0 2.38-1.991 8.588 8.588 0 0 0 1.411-2.767c.312-1.032.469-2.065.469-3.097 0-1.033-.157-2.056-.469-3.071a8.66 8.66 0 0 0-1.411-2.738 7.09 7.09 0 0 0-2.38-1.963c-.959-.5-2.101-.748-3.429-.748-1.328 0-2.471.248-3.431.748a7.05 7.05 0 0 0-2.377 1.963 8.538 8.538 0 0 0-1.411 2.738 10.303 10.303 0 0 0-.471 3.071zm-6.749 0c0-2.103.377-4.011 1.135-5.726.754-1.714 1.778-3.181 3.069-4.398 1.291-1.217 2.821-2.157 4.592-2.821 1.771-.664 3.651-.996 5.643-.996s3.872.332 5.642.996c1.771.664 3.3 1.604 4.592 2.821 1.291 1.217 2.314 2.684 3.071 4.398.755 1.715 1.133 3.623 1.133 5.726 0 2.103-.378 4.02-1.133 5.753-.757 1.733-1.78 3.218-3.071 4.454-1.292 1.236-2.821 2.203-4.592 2.903-1.77.7-3.65 1.052-5.642 1.052-1.992 0-3.872-.352-5.643-1.052-1.771-.7-3.301-1.667-4.592-2.903-1.291-1.236-2.315-2.721-3.069-4.454-.758-1.733-1.135-3.65-1.135-5.753m34.021-28.436h6.638v26.444h.166l10.068-11.175h8.52l-11.506 12.006 12.226 14.549H691.7l-10.511-13.609h-.166v13.609h-6.638V44.288z" fill="#F4F5F5"/><path d="M717.149 66.639c-.589-.775-1.402-1.448-2.433-2.02a6.867 6.867 0 0 0-3.376-.858c-1.069 0-2.047.222-2.932.664-.885.443-1.328 1.182-1.328 2.214 0 1.033.489 1.759 1.467 2.185.976.424 2.405.856 4.288 1.298.996.222 2 .518 3.014.886 1.014.369 1.936.857 2.767 1.467a7.23 7.23 0 0 1 2.019 2.268c.516.903.773 2.001.773 3.291 0 1.623-.303 2.997-.912 4.122a7.773 7.773 0 0 1-2.433 2.739c-1.015.7-2.196 1.208-3.542 1.52a18.318 18.318 0 0 1-4.177.471c-2.064 0-4.075-.379-6.029-1.134-1.956-.756-3.579-1.835-4.868-3.237l4.37-4.094c.738.96 1.695 1.752 2.876 2.379 1.18.628 2.49.94 3.928.94.479 0 .968-.055 1.466-.165.498-.111.96-.286 1.384-.526.424-.24.764-.561 1.024-.968.256-.406.386-.904.386-1.493 0-1.107-.508-1.9-1.521-2.379-1.016-.48-2.536-.96-4.564-1.438a21.777 21.777 0 0 1-2.904-.859 9.374 9.374 0 0 1-2.517-1.383 6.382 6.382 0 0 1-1.771-2.129c-.443-.848-.664-1.899-.664-3.154 0-1.474.304-2.746.912-3.817a7.867 7.867 0 0 1 2.408-2.628c.995-.682 2.12-1.188 3.373-1.52a15.082 15.082 0 0 1 3.874-.498c1.917 0 3.789.332 5.614.996 1.827.664 3.274 1.677 4.343 3.042l-4.315 3.818" fill="#F4F5F5"/><path d="M95.897 66.634c0-9.662-7.862-17.524-17.525-17.524h-1.604v6.157h1.604c6.269 0 11.368 5.1 11.368 11.367 0 6.27-5.099 11.37-11.368 11.37h-5.507v-37.37h-6.157V84.16h11.664c9.663 0 17.525-7.862 17.525-17.526zM62.793 49.11H51.13c-9.663 0-17.525 7.862-17.525 17.524 0 9.664 7.862 17.526 17.525 17.526h1.604v-6.156H51.13c-6.269 0-11.369-5.1-11.369-11.37 0-6.267 5.1-11.367 11.369-11.367h5.506v37.367h6.157V49.11zm45.991 17.557c0 24.301-19.7 44-44 44-24.301 0-44-19.699-44-44 0-24.3 19.699-44 44-44 24.3 0 44 19.7 44 44z" fill="#FFF"/></g></svg>
|
data/example/views/oauth2.erb
CHANGED
|
@@ -3,20 +3,10 @@
|
|
|
3
3
|
<head>
|
|
4
4
|
<meta charset="UTF-8">
|
|
5
5
|
<title>QBO Connect via OAuth2</title>
|
|
6
|
-
|
|
7
|
-
<script type="text/javascript" src="<%= QboApi::APP_CENTER_BASE %>/Content/IA/intuit.ipp.anywhere-1.3.1.js"></script>
|
|
8
|
-
<script>
|
|
9
|
-
intuit.ipp.anywhere.setup({
|
|
10
|
-
grantUrl: "<%= @client.authorization_uri(scope: 'com.intuit.quickbooks.accounting', state: session[:state]) %>",
|
|
11
|
-
datasources: {
|
|
12
|
-
quickbooks : true,
|
|
13
|
-
payments : true
|
|
14
|
-
}
|
|
15
|
-
});
|
|
16
|
-
</script>
|
|
17
6
|
</head>
|
|
18
|
-
<body>
|
|
19
|
-
|
|
20
|
-
|
|
7
|
+
<body style="padding:15px;">
|
|
8
|
+
<a href="<%= authorize_url(state: session[:state]) %>">
|
|
9
|
+
<img src="connect-to-qbo.svg" alt="Connect to QuickBooks Online Button" width="400">
|
|
10
|
+
</a>
|
|
21
11
|
</body>
|
|
22
12
|
</html>
|
data/lib/qbo_api/api_methods.rb
CHANGED
|
@@ -1,9 +1,8 @@
|
|
|
1
1
|
class QboApi
|
|
2
2
|
module ApiMethods
|
|
3
|
-
|
|
4
3
|
def all(entity, max: 1000, select: nil, inactive: false, params: nil, &block)
|
|
5
|
-
enumerator = create_all_enumerator(entity, max: max, select: select,
|
|
6
|
-
|
|
4
|
+
enumerator = create_all_enumerator(entity, max: max, select: select,
|
|
5
|
+
inactive: inactive, params: params)
|
|
7
6
|
if block_given?
|
|
8
7
|
enumerator.each(&block)
|
|
9
8
|
else
|
|
@@ -17,9 +16,6 @@ class QboApi
|
|
|
17
16
|
request(:get, entity: entity, path: path, params: params)
|
|
18
17
|
end
|
|
19
18
|
|
|
20
|
-
# @example
|
|
21
|
-
# get(:customer, 5)
|
|
22
|
-
# @see #get_by_query_filter
|
|
23
19
|
def get(entity, id_or_query_filter_args, params: nil)
|
|
24
20
|
if id_or_query_filter_args.is_a?(Array)
|
|
25
21
|
get_by_query_filter(entity, id_or_query_filter_args, params: params)
|
|
@@ -29,11 +25,6 @@ class QboApi
|
|
|
29
25
|
end
|
|
30
26
|
end
|
|
31
27
|
|
|
32
|
-
# @example
|
|
33
|
-
# get_by_query_filter(:customer, ["DisplayName", "Dukes Basketball Camp"])
|
|
34
|
-
# get_by_query_filter(:customer, ["DisplayName", "LIKE", "Dukes%"])
|
|
35
|
-
# get_by_query_filter(:vendor, ["DisplayName", "IN", "(true, false)"])
|
|
36
|
-
# get_by_query_filter(:customer, ["DisplayName", "Amy's Bird Sanctuary"])
|
|
37
28
|
def get_by_query_filter(entity, query_filter_args, params: nil)
|
|
38
29
|
query_str = get_query_str(entity, query_filter_args)
|
|
39
30
|
if resp = query(query_str, params: params)
|
|
@@ -143,6 +134,5 @@ class QboApi
|
|
|
143
134
|
resp = get(entity, id)
|
|
144
135
|
build_deactivate(entity, resp)
|
|
145
136
|
end
|
|
146
|
-
|
|
147
137
|
end
|
|
148
138
|
end
|
data/lib/qbo_api/attachment.rb
CHANGED
|
@@ -1,5 +1,11 @@
|
|
|
1
1
|
class QboApi
|
|
2
2
|
module Attachment
|
|
3
|
+
def read_attachment(id:)
|
|
4
|
+
raw_response = connection.get do |request|
|
|
5
|
+
request.url "#{realm_id}/attachable/#{id}"
|
|
6
|
+
end
|
|
7
|
+
response(raw_response, entity: :attachable)
|
|
8
|
+
end
|
|
3
9
|
|
|
4
10
|
def upload_attachment(payload:, attachment:)
|
|
5
11
|
content_type = payload['ContentType'] || payload[:ContentType]
|
|
@@ -7,19 +13,28 @@ class QboApi
|
|
|
7
13
|
raw_response = attachment_connection.post do |request|
|
|
8
14
|
request.url "#{realm_id}/upload"
|
|
9
15
|
request.body = {
|
|
10
|
-
|
|
11
|
-
|
|
12
|
-
|
|
13
|
-
|
|
16
|
+
'file_metadata_01':
|
|
17
|
+
Faraday::UploadIO.new(StringIO.new(payload.to_json), 'application/json', 'attachment.json'),
|
|
18
|
+
'file_content_01':
|
|
19
|
+
Faraday::UploadIO.new(attachment, content_type, file_name)
|
|
14
20
|
}
|
|
15
21
|
end
|
|
16
22
|
response(raw_response, entity: :attachable)
|
|
17
23
|
end
|
|
18
24
|
|
|
25
|
+
# The `attachable` must be the full payload returned in the read response
|
|
26
|
+
def delete_attachment(attachable:)
|
|
27
|
+
raw_response = connection.post do |request|
|
|
28
|
+
request.url "#{realm_id}/attachable?operation=delete"
|
|
29
|
+
request.body = attachable.to_json
|
|
30
|
+
end
|
|
31
|
+
|
|
32
|
+
response(raw_response, entity: :attachable)
|
|
33
|
+
end
|
|
34
|
+
|
|
19
35
|
def attachment_connection
|
|
20
36
|
@attachment_connection ||= authorized_multipart_connection(endpoint_url)
|
|
21
37
|
end
|
|
22
|
-
|
|
23
38
|
end
|
|
24
39
|
end
|
|
25
40
|
|
data/lib/qbo_api/connection.rb
CHANGED
|
@@ -4,16 +4,10 @@ require 'faraday/detailed_logger'
|
|
|
4
4
|
|
|
5
5
|
class QboApi
|
|
6
6
|
module Connection
|
|
7
|
-
AUTHORIZATION_MIDDLEWARES = []
|
|
8
|
-
|
|
9
|
-
def Connection.add_authorization_middleware(strategy_name)
|
|
10
|
-
Connection::AUTHORIZATION_MIDDLEWARES << strategy_name
|
|
11
|
-
end
|
|
12
|
-
|
|
13
7
|
def authorized_json_connection(url, headers: nil)
|
|
14
8
|
headers ||= {}
|
|
15
|
-
headers['Accept'] ||= 'application/json'
|
|
16
|
-
headers['Content-Type'] ||= 'application/json;charset=UTF-8'
|
|
9
|
+
headers['Accept'] ||= 'application/json'
|
|
10
|
+
headers['Content-Type'] ||= 'application/json;charset=UTF-8'
|
|
17
11
|
build_connection(url, headers: headers) do |conn|
|
|
18
12
|
add_authorization_middleware(conn)
|
|
19
13
|
add_exception_middleware(conn)
|
|
@@ -35,17 +29,6 @@ class QboApi
|
|
|
35
29
|
end
|
|
36
30
|
end
|
|
37
31
|
|
|
38
|
-
# @example
|
|
39
|
-
# connection = build_connection('https://oauth.platform.intuit.com', headers: { 'Accept' => 'application/json' }) do |conn|
|
|
40
|
-
# conn.basic_auth(client_id, client_secret)
|
|
41
|
-
# conn.request :url_encoded # application/x-www-form-urlencoded
|
|
42
|
-
# conn.use FaradayMiddleware::ParseJson, parser_options: { symbolize_names: true }
|
|
43
|
-
# conn.use Faraday::Response::RaiseError
|
|
44
|
-
# end
|
|
45
|
-
# raw_response = connection.post {|req|
|
|
46
|
-
# req.body = { grant_type: :refresh_token, refresh_token: current_refresh_token }
|
|
47
|
-
# req.url '/oauth2/v1/tokens/bearer'
|
|
48
|
-
# }
|
|
49
32
|
def build_connection(url, headers: nil)
|
|
50
33
|
Faraday.new(url: url) { |conn|
|
|
51
34
|
conn.response :detailed_logger, QboApi.logger, LOG_TAG if QboApi.log
|
|
@@ -119,22 +102,11 @@ class QboApi
|
|
|
119
102
|
end
|
|
120
103
|
|
|
121
104
|
def add_authorization_middleware(conn)
|
|
122
|
-
|
|
123
|
-
raise QboApi::Error.new error_body: 'Add a configured authorization_middleware'
|
|
124
|
-
end) do |strategy_name|
|
|
125
|
-
next unless public_send("use_#{strategy_name}_middleware?")
|
|
126
|
-
public_send("add_#{strategy_name}_authorization_middleware", conn)
|
|
127
|
-
true
|
|
128
|
-
end
|
|
105
|
+
conn.request :oauth2, access_token, token_type: 'bearer'
|
|
129
106
|
end
|
|
130
107
|
|
|
131
108
|
def entity_name(entity)
|
|
132
109
|
singular(entity)
|
|
133
110
|
end
|
|
134
|
-
|
|
135
|
-
require_relative 'connection/oauth1'
|
|
136
|
-
include OAuth1
|
|
137
|
-
require_relative 'connection/oauth2'
|
|
138
|
-
include OAuth2
|
|
139
111
|
end
|
|
140
112
|
end
|
data/lib/qbo_api/entity.rb
CHANGED
data/lib/qbo_api/error.rb
CHANGED
|
@@ -1,4 +1,3 @@
|
|
|
1
|
-
|
|
2
1
|
#200 OK The request succeeded. However, the response body may contain a <Fault> element, indicating an error.
|
|
3
2
|
#400 Bad request Generally, the request cannot be fulfilled due to bad syntax. In some cases, this response code is returned for a request with bad authorization data.
|
|
4
3
|
#401 Unauthorized Authentication or authorization has failed.
|
|
@@ -8,10 +7,12 @@
|
|
|
8
7
|
#500 Internal Server Error An error occurred on the server while processing the request. Resubmit request once; if it persists, contact developer support.
|
|
9
8
|
#502 Bad Gateway The server, while acting as a gateway or proxy, received an invalid response from an inbound server it accessed while attempting to fulfill the request.
|
|
10
9
|
#503 Service Unavailable The service is temporarily unavailable.
|
|
10
|
+
#504 Gateway Timeout
|
|
11
11
|
# Custom error class for rescuing from all QuickBooks Online errors
|
|
12
12
|
class QboApi
|
|
13
13
|
class Error < StandardError
|
|
14
14
|
attr_reader :fault
|
|
15
|
+
|
|
15
16
|
def initialize(errors = nil)
|
|
16
17
|
if errors
|
|
17
18
|
@fault = errors
|
|
@@ -46,4 +47,7 @@ class QboApi
|
|
|
46
47
|
|
|
47
48
|
# Raised when QuickBooks Online returns the HTTP status code 503
|
|
48
49
|
class ServiceUnavailable < Error; end
|
|
50
|
+
|
|
51
|
+
# Raised when QuickBooks Online returns the HTTP status code 504
|
|
52
|
+
class GatewayTimeout < Error; end
|
|
49
53
|
end
|
|
@@ -1,6 +1,5 @@
|
|
|
1
1
|
require 'faraday'
|
|
2
2
|
require 'nokogiri'
|
|
3
|
-
|
|
4
3
|
# @private
|
|
5
4
|
module FaradayMiddleware
|
|
6
5
|
# @private
|
|
@@ -25,6 +24,8 @@ module FaradayMiddleware
|
|
|
25
24
|
raise QboApi::BadGateway.new({ error_body: response.reason_phrase })
|
|
26
25
|
when 503
|
|
27
26
|
raise QboApi::ServiceUnavailable.new(error_message(response))
|
|
27
|
+
when 504
|
|
28
|
+
raise QboApi::GatewayTimeout.new(error_message(response))
|
|
28
29
|
end
|
|
29
30
|
end
|
|
30
31
|
end
|
|
@@ -40,7 +41,8 @@ module FaradayMiddleware
|
|
|
40
41
|
method: response.method,
|
|
41
42
|
url: response.url,
|
|
42
43
|
status: response.status,
|
|
43
|
-
error_body: error_body(response.body)
|
|
44
|
+
error_body: error_body(response.body),
|
|
45
|
+
intuit_tid: response[:response_headers]['intuit_tid']
|
|
44
46
|
}
|
|
45
47
|
end
|
|
46
48
|
|
|
@@ -78,6 +80,5 @@ module FaradayMiddleware
|
|
|
78
80
|
}
|
|
79
81
|
end
|
|
80
82
|
end
|
|
81
|
-
|
|
82
83
|
end
|
|
83
84
|
end
|
data/lib/qbo_api/supporting.rb
CHANGED
|
@@ -1,6 +1,5 @@
|
|
|
1
1
|
class QboApi
|
|
2
2
|
module Supporting
|
|
3
|
-
|
|
4
3
|
def cdc(entities:, changed_since:)
|
|
5
4
|
path = "#{realm_id}/cdc"
|
|
6
5
|
path = add_params_to_path(path: path, params: { entities: entities, changedSince: cdc_time(changed_since) })
|
|
@@ -17,6 +16,5 @@ class QboApi
|
|
|
17
16
|
path = add_params_to_path(path: path, params: params) if params
|
|
18
17
|
request(:get, path: path)
|
|
19
18
|
end
|
|
20
|
-
|
|
21
19
|
end
|
|
22
20
|
end
|
data/lib/qbo_api/util.rb
CHANGED
data/lib/qbo_api/version.rb
CHANGED
data/lib/qbo_api.rb
CHANGED
|
@@ -22,15 +22,15 @@ class QboApi
|
|
|
22
22
|
include Attachment
|
|
23
23
|
include ApiMethods
|
|
24
24
|
|
|
25
|
-
attr_accessor :realm_id
|
|
25
|
+
attr_accessor :access_token, :realm_id
|
|
26
26
|
attr_accessor :endpoint
|
|
27
27
|
|
|
28
28
|
V3_ENDPOINT_BASE_URL = 'https://sandbox-quickbooks.api.intuit.com/v3/company/'
|
|
29
29
|
PAYMENTS_API_BASE_URL = 'https://sandbox.api.intuit.com/quickbooks/v4/payments'
|
|
30
30
|
LOG_TAG = "[QuickBooks]"
|
|
31
31
|
|
|
32
|
-
# @param attributes [Hash<Symbol,String>]
|
|
33
32
|
def initialize(attributes = {})
|
|
33
|
+
raise ArgumentError, "missing keyword: access_token" unless attributes.key?(:access_token)
|
|
34
34
|
raise ArgumentError, "missing keyword: realm_id" unless attributes.key?(:realm_id)
|
|
35
35
|
attributes = default_attributes.merge!(attributes)
|
|
36
36
|
attributes.each do |attribute, value|
|
data/qbo_api.gemspec
CHANGED
|
@@ -18,14 +18,15 @@ Gem::Specification.new do |spec|
|
|
|
18
18
|
spec.executables = spec.files.grep(%r{^exe/}) { |f| File.basename(f) }
|
|
19
19
|
spec.require_paths = ["lib"]
|
|
20
20
|
|
|
21
|
-
spec.add_development_dependency "bundler"
|
|
22
|
-
spec.add_development_dependency "rake"
|
|
21
|
+
spec.add_development_dependency "bundler"
|
|
22
|
+
spec.add_development_dependency "rake"
|
|
23
23
|
spec.add_development_dependency "rspec"
|
|
24
24
|
spec.add_development_dependency 'webmock'
|
|
25
|
+
spec.add_development_dependency 'rexml'
|
|
25
26
|
spec.add_development_dependency 'simple_oauth'
|
|
26
27
|
spec.add_development_dependency 'dotenv'
|
|
27
28
|
spec.add_development_dependency 'vcr'
|
|
28
|
-
spec.add_development_dependency '
|
|
29
|
+
spec.add_development_dependency 'amazing_print'
|
|
29
30
|
spec.add_runtime_dependency 'faraday'
|
|
30
31
|
spec.add_runtime_dependency 'faraday_middleware'
|
|
31
32
|
spec.add_runtime_dependency 'faraday-detailed_logger'
|
metadata
CHANGED
|
@@ -1,43 +1,43 @@
|
|
|
1
1
|
--- !ruby/object:Gem::Specification
|
|
2
2
|
name: qbo_api
|
|
3
3
|
version: !ruby/object:Gem::Version
|
|
4
|
-
version:
|
|
4
|
+
version: 2.0.1
|
|
5
5
|
platform: ruby
|
|
6
6
|
authors:
|
|
7
7
|
- Christian Pelczarski
|
|
8
|
-
autorequire:
|
|
8
|
+
autorequire:
|
|
9
9
|
bindir: exe
|
|
10
10
|
cert_chain: []
|
|
11
|
-
date:
|
|
11
|
+
date: 2021-10-02 00:00:00.000000000 Z
|
|
12
12
|
dependencies:
|
|
13
13
|
- !ruby/object:Gem::Dependency
|
|
14
14
|
name: bundler
|
|
15
15
|
requirement: !ruby/object:Gem::Requirement
|
|
16
16
|
requirements:
|
|
17
|
-
- - "
|
|
17
|
+
- - ">="
|
|
18
18
|
- !ruby/object:Gem::Version
|
|
19
|
-
version: '
|
|
19
|
+
version: '0'
|
|
20
20
|
type: :development
|
|
21
21
|
prerelease: false
|
|
22
22
|
version_requirements: !ruby/object:Gem::Requirement
|
|
23
23
|
requirements:
|
|
24
|
-
- - "
|
|
24
|
+
- - ">="
|
|
25
25
|
- !ruby/object:Gem::Version
|
|
26
|
-
version: '
|
|
26
|
+
version: '0'
|
|
27
27
|
- !ruby/object:Gem::Dependency
|
|
28
28
|
name: rake
|
|
29
29
|
requirement: !ruby/object:Gem::Requirement
|
|
30
30
|
requirements:
|
|
31
|
-
- - "
|
|
31
|
+
- - ">="
|
|
32
32
|
- !ruby/object:Gem::Version
|
|
33
|
-
version: '
|
|
33
|
+
version: '0'
|
|
34
34
|
type: :development
|
|
35
35
|
prerelease: false
|
|
36
36
|
version_requirements: !ruby/object:Gem::Requirement
|
|
37
37
|
requirements:
|
|
38
|
-
- - "
|
|
38
|
+
- - ">="
|
|
39
39
|
- !ruby/object:Gem::Version
|
|
40
|
-
version: '
|
|
40
|
+
version: '0'
|
|
41
41
|
- !ruby/object:Gem::Dependency
|
|
42
42
|
name: rspec
|
|
43
43
|
requirement: !ruby/object:Gem::Requirement
|
|
@@ -66,6 +66,20 @@ dependencies:
|
|
|
66
66
|
- - ">="
|
|
67
67
|
- !ruby/object:Gem::Version
|
|
68
68
|
version: '0'
|
|
69
|
+
- !ruby/object:Gem::Dependency
|
|
70
|
+
name: rexml
|
|
71
|
+
requirement: !ruby/object:Gem::Requirement
|
|
72
|
+
requirements:
|
|
73
|
+
- - ">="
|
|
74
|
+
- !ruby/object:Gem::Version
|
|
75
|
+
version: '0'
|
|
76
|
+
type: :development
|
|
77
|
+
prerelease: false
|
|
78
|
+
version_requirements: !ruby/object:Gem::Requirement
|
|
79
|
+
requirements:
|
|
80
|
+
- - ">="
|
|
81
|
+
- !ruby/object:Gem::Version
|
|
82
|
+
version: '0'
|
|
69
83
|
- !ruby/object:Gem::Dependency
|
|
70
84
|
name: simple_oauth
|
|
71
85
|
requirement: !ruby/object:Gem::Requirement
|
|
@@ -109,7 +123,7 @@ dependencies:
|
|
|
109
123
|
- !ruby/object:Gem::Version
|
|
110
124
|
version: '0'
|
|
111
125
|
- !ruby/object:Gem::Dependency
|
|
112
|
-
name:
|
|
126
|
+
name: amazing_print
|
|
113
127
|
requirement: !ruby/object:Gem::Requirement
|
|
114
128
|
requirements:
|
|
115
129
|
- - ">="
|
|
@@ -178,14 +192,13 @@ dependencies:
|
|
|
178
192
|
- - ">="
|
|
179
193
|
- !ruby/object:Gem::Version
|
|
180
194
|
version: '0'
|
|
181
|
-
description:
|
|
195
|
+
description:
|
|
182
196
|
email:
|
|
183
197
|
- christian@minimul.com
|
|
184
198
|
executables: []
|
|
185
199
|
extensions: []
|
|
186
200
|
extra_rdoc_files: []
|
|
187
201
|
files:
|
|
188
|
-
- ".env.example_app.oauth1"
|
|
189
202
|
- ".env.example_app.oauth2"
|
|
190
203
|
- ".env.test"
|
|
191
204
|
- ".gitignore"
|
|
@@ -197,8 +210,8 @@ files:
|
|
|
197
210
|
- bin/console
|
|
198
211
|
- bin/setup
|
|
199
212
|
- example/base.rb
|
|
200
|
-
- example/oauth.rb
|
|
201
213
|
- example/oauth2.rb
|
|
214
|
+
- example/public/connect-to-qbo.svg
|
|
202
215
|
- example/views/customer.erb
|
|
203
216
|
- example/views/index.erb
|
|
204
217
|
- example/views/oauth2.erb
|
|
@@ -208,8 +221,6 @@ files:
|
|
|
208
221
|
- lib/qbo_api/attachment.rb
|
|
209
222
|
- lib/qbo_api/configuration.rb
|
|
210
223
|
- lib/qbo_api/connection.rb
|
|
211
|
-
- lib/qbo_api/connection/oauth1.rb
|
|
212
|
-
- lib/qbo_api/connection/oauth2.rb
|
|
213
224
|
- lib/qbo_api/entity.rb
|
|
214
225
|
- lib/qbo_api/error.rb
|
|
215
226
|
- lib/qbo_api/raise_http_exception.rb
|
|
@@ -221,7 +232,7 @@ homepage: https://github.com/minimul/qbo_api
|
|
|
221
232
|
licenses:
|
|
222
233
|
- MIT
|
|
223
234
|
metadata: {}
|
|
224
|
-
post_install_message:
|
|
235
|
+
post_install_message:
|
|
225
236
|
rdoc_options: []
|
|
226
237
|
require_paths:
|
|
227
238
|
- lib
|
|
@@ -236,8 +247,8 @@ required_rubygems_version: !ruby/object:Gem::Requirement
|
|
|
236
247
|
- !ruby/object:Gem::Version
|
|
237
248
|
version: '0'
|
|
238
249
|
requirements: []
|
|
239
|
-
rubygems_version: 3.0.
|
|
240
|
-
signing_key:
|
|
250
|
+
rubygems_version: 3.0.3
|
|
251
|
+
signing_key:
|
|
241
252
|
specification_version: 4
|
|
242
253
|
summary: Ruby JSON-only client for QuickBooks Online API v3. Built on top of the Faraday
|
|
243
254
|
gem.
|
data/.env.example_app.oauth1
DELETED
data/example/oauth.rb
DELETED
|
@@ -1,62 +0,0 @@
|
|
|
1
|
-
require 'bundler/inline'
|
|
2
|
-
|
|
3
|
-
require File.expand_path(File.join('..', 'base'), __FILE__)
|
|
4
|
-
|
|
5
|
-
install_gems = true
|
|
6
|
-
gemfile(install_gems) do
|
|
7
|
-
source 'https://rubygems.org'
|
|
8
|
-
|
|
9
|
-
instance_eval(&BASE_GEMS)
|
|
10
|
-
|
|
11
|
-
gem 'omniauth'
|
|
12
|
-
gem 'omniauth-quickbooks'
|
|
13
|
-
end
|
|
14
|
-
|
|
15
|
-
instance_eval(&BASE_SETUP)
|
|
16
|
-
|
|
17
|
-
class OAuthApp < Sinatra::Base
|
|
18
|
-
instance_eval(&BASE_APP_CONFIG)
|
|
19
|
-
|
|
20
|
-
CONSUMER_KEY = ENV['QBO_API_CONSUMER_KEY']
|
|
21
|
-
CONSUMER_SECRET = ENV['QBO_API_CONSUMER_SECRET']
|
|
22
|
-
|
|
23
|
-
use Rack::Session::Cookie, secret: '34233adasf/qewrq453agqr9(lasfa)'
|
|
24
|
-
use OmniAuth::Builder do
|
|
25
|
-
provider :quickbooks, CONSUMER_KEY, CONSUMER_SECRET
|
|
26
|
-
end
|
|
27
|
-
|
|
28
|
-
get '/' do
|
|
29
|
-
@app_center = QboApi::APP_CENTER_BASE
|
|
30
|
-
@auth_data = oauth_data
|
|
31
|
-
@port = PORT
|
|
32
|
-
erb :index
|
|
33
|
-
end
|
|
34
|
-
|
|
35
|
-
get '/customer/:id' do
|
|
36
|
-
if session[:token]
|
|
37
|
-
api = QboApi.new(oauth_data)
|
|
38
|
-
@resp = api.get :customer, params[:id]
|
|
39
|
-
end
|
|
40
|
-
erb :customer
|
|
41
|
-
end
|
|
42
|
-
|
|
43
|
-
get '/auth/quickbooks/callback' do
|
|
44
|
-
auth = env["omniauth.auth"][:credentials]
|
|
45
|
-
session[:token] = auth[:token]
|
|
46
|
-
session[:secret] = auth[:secret]
|
|
47
|
-
session[:realm_id] = params['realmId']
|
|
48
|
-
'<!DOCTYPE html><html lang="en"><head></head><body><script>window.opener.location.reload(); window.close();</script></body></html>'
|
|
49
|
-
end
|
|
50
|
-
|
|
51
|
-
def oauth_data
|
|
52
|
-
{
|
|
53
|
-
consumer_key: CONSUMER_KEY,
|
|
54
|
-
consumer_secret: CONSUMER_SECRET,
|
|
55
|
-
token: session[:token],
|
|
56
|
-
token_secret: session[:secret],
|
|
57
|
-
realm_id: session[:realm_id]
|
|
58
|
-
}
|
|
59
|
-
end
|
|
60
|
-
end
|
|
61
|
-
|
|
62
|
-
OAuthApp.run!
|
|
@@ -1,60 +0,0 @@
|
|
|
1
|
-
class QboApi
|
|
2
|
-
APP_CENTER_BASE = 'https://appcenter.intuit.com'
|
|
3
|
-
APP_CENTER_URL = APP_CENTER_BASE + '/Connect/Begin?oauth_token='
|
|
4
|
-
APP_CONNECTION_URL = APP_CENTER_BASE + '/api/v1/connection'
|
|
5
|
-
|
|
6
|
-
attr_accessor :token, :token_secret
|
|
7
|
-
attr_accessor :consumer_key, :consumer_secret
|
|
8
|
-
|
|
9
|
-
module Connection::OAuth1
|
|
10
|
-
|
|
11
|
-
def self.included(*)
|
|
12
|
-
QboApi::Connection.add_authorization_middleware :oauth1
|
|
13
|
-
super
|
|
14
|
-
end
|
|
15
|
-
|
|
16
|
-
def default_attributes
|
|
17
|
-
super.merge!(
|
|
18
|
-
token: nil, token_secret: nil,
|
|
19
|
-
consumer_key: defined?(CONSUMER_KEY) ? CONSUMER_KEY : nil,
|
|
20
|
-
consumer_secret: defined?(CONSUMER_SECRET) ? CONSUMER_SECRET : nil,
|
|
21
|
-
)
|
|
22
|
-
end
|
|
23
|
-
|
|
24
|
-
def add_oauth1_authorization_middleware(conn)
|
|
25
|
-
gem 'simple_oauth'
|
|
26
|
-
require 'simple_oauth'
|
|
27
|
-
conn.request :oauth, oauth_data
|
|
28
|
-
end
|
|
29
|
-
|
|
30
|
-
def use_oauth1_middleware?
|
|
31
|
-
token != nil
|
|
32
|
-
end
|
|
33
|
-
|
|
34
|
-
# https://developer.intuit.com/docs/0100_quickbooks_online/0100_essentials/0085_develop_quickbooks_apps/0004_authentication_and_authorization/oauth_management_api#/Reconnect
|
|
35
|
-
def disconnect
|
|
36
|
-
path = "#{APP_CONNECTION_URL}/disconnect"
|
|
37
|
-
request(:get, path: path)
|
|
38
|
-
end
|
|
39
|
-
|
|
40
|
-
# https://developer.intuit.com/docs/0100_quickbooks_online/0100_essentials/0085_develop_quickbooks_apps/0004_authentication_and_authorization/oauth_management_api#/Reconnect
|
|
41
|
-
def reconnect
|
|
42
|
-
path = "#{APP_CONNECTION_URL}/reconnect"
|
|
43
|
-
request(:get, path: path)
|
|
44
|
-
end
|
|
45
|
-
|
|
46
|
-
private
|
|
47
|
-
|
|
48
|
-
# Use with simple_oauth OAuth1 middleware
|
|
49
|
-
# @see #add_authorization_middleware
|
|
50
|
-
def oauth_data
|
|
51
|
-
{
|
|
52
|
-
consumer_key: @consumer_key,
|
|
53
|
-
consumer_secret: @consumer_secret,
|
|
54
|
-
token: @token,
|
|
55
|
-
token_secret: @token_secret
|
|
56
|
-
}
|
|
57
|
-
end
|
|
58
|
-
|
|
59
|
-
end
|
|
60
|
-
end
|
|
@@ -1,24 +0,0 @@
|
|
|
1
|
-
class QboApi
|
|
2
|
-
attr_accessor :access_token
|
|
3
|
-
|
|
4
|
-
module Connection::OAuth2
|
|
5
|
-
|
|
6
|
-
def self.included(*)
|
|
7
|
-
QboApi::Connection.add_authorization_middleware :oauth2
|
|
8
|
-
super
|
|
9
|
-
end
|
|
10
|
-
|
|
11
|
-
def default_attributes
|
|
12
|
-
super.merge!(
|
|
13
|
-
access_token: nil
|
|
14
|
-
)
|
|
15
|
-
end
|
|
16
|
-
def add_oauth2_authorization_middleware(conn)
|
|
17
|
-
conn.request :oauth2, access_token, token_type: 'bearer'
|
|
18
|
-
end
|
|
19
|
-
|
|
20
|
-
def use_oauth2_middleware?
|
|
21
|
-
access_token != nil
|
|
22
|
-
end
|
|
23
|
-
end
|
|
24
|
-
end
|