versacommerce_api 1.0.19 → 2.0
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 +5 -5
- data/.ruby-version +1 -1
- data/CHANGELOG +13 -0
- data/lib/versacommerce_api/cli.rb +7 -1
- data/lib/versacommerce_api/session.rb +42 -28
- data/lib/versacommerce_api/version.rb +1 -2
- data/lib/versacommerce_api.rb +0 -5
- data/versacommerce_api.gemspec +1 -1
- metadata +9 -16
- data/Gemfile.lock +0 -72
- data/lib/active_resource/base_ext.rb +0 -23
- data/lib/active_resource/connection_ext.rb +0 -32
- data/lib/active_resource/detailed_log_subscriber.rb +0 -20
- data/lib/active_resource/disable_prefix_check.rb +0 -9
- data/lib/active_resource/json_errors.rb +0 -22
checksums.yaml
CHANGED
@@ -1,7 +1,7 @@
|
|
1
1
|
---
|
2
|
-
|
3
|
-
metadata.gz:
|
4
|
-
data.tar.gz:
|
2
|
+
SHA256:
|
3
|
+
metadata.gz: fac7f3cca1b489267363775311b530256230f700f55aadb89e7c5ea82dd75c5c
|
4
|
+
data.tar.gz: fa80ac50004e4165876c117ebc0c2ea9772cd072bd3aef00e040d77664abf0bd
|
5
5
|
SHA512:
|
6
|
-
metadata.gz:
|
7
|
-
data.tar.gz:
|
6
|
+
metadata.gz: 89d670b9a2cf8521f79305252b54d05c8940e6fdae592225bc6a21cc7f09148b220d81c8be7af8eb6e4685277bc8311de1b493ee64f847e0eb7b89a722a4c6f8
|
7
|
+
data.tar.gz: 7cdb66a30203503d98430da02052fa4572784a65622388ba249b8286419dd69a6d429fce01cba0fddc5f604793e127c1369cdd124e1c32935772052b915a365d
|
data/.ruby-version
CHANGED
@@ -1 +1 @@
|
|
1
|
-
|
1
|
+
3.0.2
|
data/CHANGELOG
CHANGED
@@ -1,3 +1,16 @@
|
|
1
|
+
2.0 - Remove active_resource overrides
|
2
|
+
- Ask user for secret and then get required token and password in VersasCommerce CLI
|
3
|
+
1.0.20 - Allow to switch the API protocol
|
4
|
+
1.0.19 - Remove debug statement
|
5
|
+
1.0.18 - Add Event resource
|
6
|
+
- Add Product#tax_for_country
|
7
|
+
- Add missing api prefix to item resource
|
8
|
+
1.0.17 - Use HTTPS (Part #3)
|
9
|
+
- Add ProductListing resource
|
10
|
+
1.0.16 - Request token via HTTPS - (use HTTPS Part #2)
|
11
|
+
1.0.15 - Use HTTPS (Part #1)
|
12
|
+
1.0.14 - Allow updating the current Shop
|
13
|
+
1.0.13 - Add Metafields
|
1
14
|
1.0.12 - Associate customers with billing_address and shipping_address
|
2
15
|
1.0.11 - Associate items with shipments
|
3
16
|
- Associate shipments with orders
|
@@ -29,7 +29,8 @@ module VersacommerceAPI
|
|
29
29
|
config['domain'] = "#{config['domain']}.versacommerce.de" unless config['domain'].match(/[.:]/)
|
30
30
|
puts "\nopen https://#{config['domain']}/admin/settings/apps in your browser to get API credentials\n"
|
31
31
|
config['api_key'] = ask("API key :")
|
32
|
-
config['
|
32
|
+
config['secret'] = ask("Secret:")
|
33
|
+
config['password'] = get_password(config['domain'], config['api_key'], config['secret'])
|
33
34
|
create_file(file, config.to_yaml)
|
34
35
|
end
|
35
36
|
if available_connections.one?
|
@@ -161,5 +162,10 @@ module VersacommerceAPI
|
|
161
162
|
def config_file_not_found_error(filename)
|
162
163
|
raise ConfigFileError, "Could not find config file at #{filename}"
|
163
164
|
end
|
165
|
+
|
166
|
+
def get_password(domain, api_key, secret)
|
167
|
+
VersacommerceAPI::Session.setup(domain: domain, api_key: api_key, secret: secret)
|
168
|
+
VersacommerceAPI::Session.get_password
|
169
|
+
end
|
164
170
|
end
|
165
171
|
end
|
@@ -1,89 +1,103 @@
|
|
1
1
|
# -*- encoding : utf-8 -*-
|
2
|
+
require 'uri'
|
3
|
+
require 'net/http'
|
2
4
|
module VersacommerceAPI
|
3
|
-
|
5
|
+
|
4
6
|
class Session
|
5
7
|
cattr_accessor :api_key
|
6
8
|
cattr_accessor :secret
|
7
9
|
cattr_accessor :protocol
|
10
|
+
cattr_accessor :domain
|
8
11
|
self.protocol = 'https'
|
9
|
-
|
12
|
+
|
10
13
|
attr_accessor :url, :token, :name
|
11
|
-
|
12
|
-
|
14
|
+
|
15
|
+
|
13
16
|
def initialize(url, token = nil, params = nil)
|
14
17
|
self.url, self.token = url, token
|
15
|
-
|
18
|
+
|
16
19
|
if params && params[:signature]
|
17
20
|
unless self.class.validate_signature(params) && params[:timestamp].to_i > 24.hours.ago.utc.to_i
|
18
21
|
raise "Invalid Signature: Possible malicious login"
|
19
22
|
end
|
20
23
|
end
|
21
|
-
|
24
|
+
|
22
25
|
self.class.prepare_url(self.url)
|
23
26
|
end
|
24
|
-
|
25
|
-
|
27
|
+
|
28
|
+
|
26
29
|
def self.setup(params)
|
27
30
|
params.each { |k,value| send("#{k}=", value) }
|
28
31
|
end
|
29
|
-
|
30
|
-
|
32
|
+
|
33
|
+
|
31
34
|
def self.request_token(domain)
|
32
35
|
return nil if domain.blank? || api_key.blank?
|
33
36
|
begin
|
34
|
-
|
35
|
-
|
37
|
+
uri = URI("https://#{domain}/api/auth.xml?api_key=#{api_key}")
|
38
|
+
res = Net::HTTP.get_response(uri)
|
39
|
+
Hash.from_xml(res.body)["token"] if res&.body
|
36
40
|
rescue
|
37
41
|
nil
|
38
42
|
end
|
39
43
|
end
|
40
|
-
|
41
|
-
|
44
|
+
|
45
|
+
def self.get_password
|
46
|
+
return nil if domain.blank? || api_key.blank? || secret.blank?
|
47
|
+
|
48
|
+
token = request_token(domain)
|
49
|
+
return if token.blank?
|
50
|
+
|
51
|
+
Digest::MD5.hexdigest(secret + token)
|
52
|
+
end
|
53
|
+
|
54
|
+
|
55
|
+
|
42
56
|
def shop
|
43
57
|
Shop.current
|
44
58
|
end
|
45
|
-
|
46
|
-
|
59
|
+
|
60
|
+
|
47
61
|
def create_permission_url
|
48
62
|
return nil if url.blank? || api_key.blank?
|
49
|
-
"
|
63
|
+
"#{protocol}://#{url}/api/auth?api_key=#{api_key}"
|
50
64
|
end
|
51
|
-
|
52
|
-
|
65
|
+
|
66
|
+
|
53
67
|
# Used by ActiveResource::Base to make all non-authentication API calls
|
54
68
|
def site
|
55
69
|
"#{protocol}://#{api_key}:#{computed_password}@#{url}/api/"
|
56
70
|
end
|
57
|
-
|
58
|
-
|
71
|
+
|
72
|
+
|
59
73
|
def valid?
|
60
74
|
url.present? && token.present?
|
61
75
|
end
|
62
|
-
|
76
|
+
|
63
77
|
private
|
64
|
-
|
78
|
+
|
65
79
|
# The secret is computed by taking the shared_secret which we got when
|
66
80
|
# registring this third party application and concating the request_to it,
|
67
81
|
# and then calculating a MD5 hexdigest.
|
68
|
-
|
82
|
+
|
69
83
|
# secret = shared_key
|
70
84
|
# token was provided by registration
|
71
85
|
def computed_password
|
72
86
|
Digest::MD5.hexdigest(secret + token.to_s)
|
73
87
|
end
|
74
|
-
|
88
|
+
|
75
89
|
def self.prepare_url(url)
|
76
90
|
return nil if url.blank?
|
77
91
|
url.gsub!(/https?:\/\//, '') # remove http:// or https://
|
78
92
|
url.concat(".versacommerce.de") unless url.include?('.') # extend url to versacommerce.de if no host is given
|
79
93
|
end
|
80
|
-
|
94
|
+
|
81
95
|
def self.validate_signature(params)
|
82
96
|
return false unless signature = params[:signature]
|
83
|
-
|
97
|
+
|
84
98
|
sorted_params = params.except(:signature, :action, :controller).collect{|k,v|"#{k}=#{v}"}.sort.join
|
85
99
|
Digest::MD5.hexdigest(secret + sorted_params) == signature
|
86
100
|
end
|
87
101
|
end
|
88
|
-
|
102
|
+
|
89
103
|
end
|
data/lib/versacommerce_api.rb
CHANGED
@@ -6,11 +6,6 @@ require 'active_support/core_ext/class/attribute_accessors'
|
|
6
6
|
require 'digest/md5'
|
7
7
|
require 'base64'
|
8
8
|
require 'yaml'
|
9
|
-
require 'active_resource/connection_ext'
|
10
|
-
require 'active_resource/detailed_log_subscriber'
|
11
|
-
require 'active_resource/json_errors'
|
12
|
-
require 'active_resource/disable_prefix_check'
|
13
|
-
require 'active_resource/base_ext'
|
14
9
|
|
15
10
|
module VersacommerceAPI
|
16
11
|
# Your code goes here...
|
data/versacommerce_api.gemspec
CHANGED
@@ -19,7 +19,7 @@ Gem::Specification.new do |spec|
|
|
19
19
|
spec.test_files = spec.files.grep(%r{^(test|spec|features)/})
|
20
20
|
spec.require_paths = ["lib"]
|
21
21
|
|
22
|
-
spec.add_development_dependency "bundler", "~>
|
22
|
+
spec.add_development_dependency "bundler", "~> 2.3"
|
23
23
|
spec.add_development_dependency "rake"
|
24
24
|
spec.add_development_dependency "rspec"
|
25
25
|
spec.add_development_dependency "pry"
|
metadata
CHANGED
@@ -1,14 +1,14 @@
|
|
1
1
|
--- !ruby/object:Gem::Specification
|
2
2
|
name: versacommerce_api
|
3
3
|
version: !ruby/object:Gem::Version
|
4
|
-
version:
|
4
|
+
version: '2.0'
|
5
5
|
platform: ruby
|
6
6
|
authors:
|
7
7
|
- VersaCommerce
|
8
|
-
autorequire:
|
8
|
+
autorequire:
|
9
9
|
bindir: bin
|
10
10
|
cert_chain: []
|
11
|
-
date:
|
11
|
+
date: 2022-05-04 00:00:00.000000000 Z
|
12
12
|
dependencies:
|
13
13
|
- !ruby/object:Gem::Dependency
|
14
14
|
name: bundler
|
@@ -16,14 +16,14 @@ dependencies:
|
|
16
16
|
requirements:
|
17
17
|
- - "~>"
|
18
18
|
- !ruby/object:Gem::Version
|
19
|
-
version: '
|
19
|
+
version: '2.3'
|
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: '2.3'
|
27
27
|
- !ruby/object:Gem::Dependency
|
28
28
|
name: rake
|
29
29
|
requirement: !ruby/object:Gem::Requirement
|
@@ -140,7 +140,7 @@ description: The VersaCommerce API gem allows Ruby developers to programmaticall
|
|
140
140
|
access the admin section of VersaCommerce shops. The API is implemented as JSON
|
141
141
|
or XML over HTTP using all four verbs (GET/POST/PUT/DELETE). Each resource, like
|
142
142
|
Order, Product, or Collection, has its own URL and is manipulated in isolation.
|
143
|
-
email:
|
143
|
+
email:
|
144
144
|
executables:
|
145
145
|
- versacommerce
|
146
146
|
extensions: []
|
@@ -151,17 +151,11 @@ files:
|
|
151
151
|
- CHANGELOG
|
152
152
|
- CONTRIBUTORS
|
153
153
|
- Gemfile
|
154
|
-
- Gemfile.lock
|
155
154
|
- LICENSE.txt
|
156
155
|
- README.md
|
157
156
|
- RELEASING
|
158
157
|
- Rakefile
|
159
158
|
- bin/versacommerce
|
160
|
-
- lib/active_resource/base_ext.rb
|
161
|
-
- lib/active_resource/connection_ext.rb
|
162
|
-
- lib/active_resource/detailed_log_subscriber.rb
|
163
|
-
- lib/active_resource/disable_prefix_check.rb
|
164
|
-
- lib/active_resource/json_errors.rb
|
165
159
|
- lib/versacommerce_api.rb
|
166
160
|
- lib/versacommerce_api/associatable.rb
|
167
161
|
- lib/versacommerce_api/cli.rb
|
@@ -202,7 +196,7 @@ homepage: http://www.versacommerce.de
|
|
202
196
|
licenses:
|
203
197
|
- MIT
|
204
198
|
metadata: {}
|
205
|
-
post_install_message:
|
199
|
+
post_install_message:
|
206
200
|
rdoc_options: []
|
207
201
|
require_paths:
|
208
202
|
- lib
|
@@ -217,9 +211,8 @@ required_rubygems_version: !ruby/object:Gem::Requirement
|
|
217
211
|
- !ruby/object:Gem::Version
|
218
212
|
version: '0'
|
219
213
|
requirements: []
|
220
|
-
|
221
|
-
|
222
|
-
signing_key:
|
214
|
+
rubygems_version: 3.2.22
|
215
|
+
signing_key:
|
223
216
|
specification_version: 4
|
224
217
|
summary: The VersaCommerce API gem is a lightweight gem for accessing the VersaCommerce
|
225
218
|
admin REST web services
|
data/Gemfile.lock
DELETED
@@ -1,72 +0,0 @@
|
|
1
|
-
PATH
|
2
|
-
remote: .
|
3
|
-
specs:
|
4
|
-
versacommerce_api (1.0.12)
|
5
|
-
activeresource (>= 3.2.14)
|
6
|
-
thor (>= 0.14.4)
|
7
|
-
|
8
|
-
GEM
|
9
|
-
remote: https://rubygems.org/
|
10
|
-
specs:
|
11
|
-
activemodel (4.2.7)
|
12
|
-
activesupport (= 4.2.7)
|
13
|
-
builder (~> 3.1)
|
14
|
-
activeresource (4.1.0)
|
15
|
-
activemodel (~> 4.0)
|
16
|
-
activesupport (~> 4.0)
|
17
|
-
rails-observers (~> 0.1.2)
|
18
|
-
activesupport (4.2.7)
|
19
|
-
i18n (~> 0.7)
|
20
|
-
json (~> 1.7, >= 1.7.7)
|
21
|
-
minitest (~> 5.1)
|
22
|
-
thread_safe (~> 0.3, >= 0.3.4)
|
23
|
-
tzinfo (~> 1.1)
|
24
|
-
builder (3.2.2)
|
25
|
-
coderay (1.0.9)
|
26
|
-
diff-lcs (1.2.4)
|
27
|
-
fakeweb (1.3.0)
|
28
|
-
i18n (0.7.0)
|
29
|
-
json (1.8.3)
|
30
|
-
metaclass (0.0.1)
|
31
|
-
method_source (0.8.2)
|
32
|
-
minitest (5.9.0)
|
33
|
-
mocha (0.14.0)
|
34
|
-
metaclass (~> 0.0.1)
|
35
|
-
pry (0.9.12.2)
|
36
|
-
coderay (~> 1.0.5)
|
37
|
-
method_source (~> 0.8)
|
38
|
-
slop (~> 3.4)
|
39
|
-
pry-nav (0.2.3)
|
40
|
-
pry (~> 0.9.10)
|
41
|
-
rails-observers (0.1.2)
|
42
|
-
activemodel (~> 4.0)
|
43
|
-
rake (10.1.0)
|
44
|
-
rspec (2.14.1)
|
45
|
-
rspec-core (~> 2.14.0)
|
46
|
-
rspec-expectations (~> 2.14.0)
|
47
|
-
rspec-mocks (~> 2.14.0)
|
48
|
-
rspec-core (2.14.5)
|
49
|
-
rspec-expectations (2.14.3)
|
50
|
-
diff-lcs (>= 1.1.3, < 2.0)
|
51
|
-
rspec-mocks (2.14.3)
|
52
|
-
slop (3.4.6)
|
53
|
-
thor (0.19.1)
|
54
|
-
thread_safe (0.3.5)
|
55
|
-
tzinfo (1.2.2)
|
56
|
-
thread_safe (~> 0.1)
|
57
|
-
|
58
|
-
PLATFORMS
|
59
|
-
ruby
|
60
|
-
|
61
|
-
DEPENDENCIES
|
62
|
-
bundler (~> 1.3)
|
63
|
-
fakeweb
|
64
|
-
mocha (>= 0.9.8)
|
65
|
-
pry
|
66
|
-
pry-nav
|
67
|
-
rake
|
68
|
-
rspec
|
69
|
-
versacommerce_api!
|
70
|
-
|
71
|
-
BUNDLED WITH
|
72
|
-
1.12.1
|
@@ -1,23 +0,0 @@
|
|
1
|
-
# -*- encoding : utf-8 -*-
|
2
|
-
module ActiveResource
|
3
|
-
class Base
|
4
|
-
# BACKPORTED FROM ACTIVERESOURCE MASTER BRANCH
|
5
|
-
def self.headers
|
6
|
-
@headers ||= {}
|
7
|
-
|
8
|
-
if superclass != Object && superclass.headers
|
9
|
-
@headers = superclass.headers.merge(@headers)
|
10
|
-
else
|
11
|
-
@headers
|
12
|
-
end
|
13
|
-
end
|
14
|
-
# https://github.com/rails/activeresource/commit/dfef85ce8f653f75673631b2950fcdb0781c313c
|
15
|
-
def self.delete(id, options = {})
|
16
|
-
connection.delete(element_path(id, options), headers)
|
17
|
-
end
|
18
|
-
def self.build(attributes = {})
|
19
|
-
attrs = self.format.decode(connection.get("#{new_element_path}", headers).body).merge(attributes)
|
20
|
-
self.new(attrs)
|
21
|
-
end
|
22
|
-
end
|
23
|
-
end
|
@@ -1,32 +0,0 @@
|
|
1
|
-
# -*- encoding : utf-8 -*-
|
2
|
-
require 'active_support/core_ext/module/aliasing'
|
3
|
-
|
4
|
-
module ActiveResource
|
5
|
-
class Connection
|
6
|
-
|
7
|
-
attr_reader :response
|
8
|
-
|
9
|
-
def handle_response_with_response_capture(response)
|
10
|
-
@response = handle_response_without_response_capture(response)
|
11
|
-
end
|
12
|
-
|
13
|
-
def request_with_detailed_log_subscriber(method, path, *arguments)
|
14
|
-
result = request_without_detailed_log_subscriber(method, path, *arguments)
|
15
|
-
detailed_log_subscriber(result, arguments)
|
16
|
-
result
|
17
|
-
rescue => e
|
18
|
-
detailed_log_subscriber(e.response, arguments) if e.respond_to?(:response)
|
19
|
-
raise
|
20
|
-
end
|
21
|
-
|
22
|
-
def detailed_log_subscriber(response, arguments)
|
23
|
-
ActiveSupport::Notifications.instrument("request.active_resource_detailed") do |payload|
|
24
|
-
payload[:response] = response
|
25
|
-
payload[:data] = arguments
|
26
|
-
end
|
27
|
-
end
|
28
|
-
|
29
|
-
alias_method_chain :handle_response, :response_capture
|
30
|
-
alias_method_chain :request, :detailed_log_subscriber
|
31
|
-
end
|
32
|
-
end
|
@@ -1,20 +0,0 @@
|
|
1
|
-
# -*- encoding : utf-8 -*-
|
2
|
-
module ActiveResource
|
3
|
-
class DetailedLogSubscriber < ActiveSupport::LogSubscriber
|
4
|
-
def request(event)
|
5
|
-
data = event.payload[:data]
|
6
|
-
headers = data.extract_options!
|
7
|
-
request_body = data.first
|
8
|
-
|
9
|
-
info "Request:\n#{request_body}" if request_body
|
10
|
-
info "Headers: #{headers.inspect}"
|
11
|
-
info "Response:\n#{event.payload[:response].body}"
|
12
|
-
end
|
13
|
-
|
14
|
-
def logger
|
15
|
-
ActiveResource::Base.logger
|
16
|
-
end
|
17
|
-
end
|
18
|
-
end
|
19
|
-
|
20
|
-
ActiveResource::DetailedLogSubscriber.attach_to :active_resource_detailed
|
@@ -1,22 +0,0 @@
|
|
1
|
-
# -*- encoding : utf-8 -*-
|
2
|
-
require 'active_resource/base'
|
3
|
-
|
4
|
-
module ActiveResource
|
5
|
-
class Errors < ActiveModel::Errors
|
6
|
-
def from_hash(messages, save_cache = false)
|
7
|
-
clear unless save_cache
|
8
|
-
|
9
|
-
messages.each do |key,errors|
|
10
|
-
errors.each do |error|
|
11
|
-
add(key, error)
|
12
|
-
end
|
13
|
-
end
|
14
|
-
end
|
15
|
-
|
16
|
-
# Grabs errors from a json response.
|
17
|
-
def from_json(json, save_cache = false)
|
18
|
-
hash = ActiveSupport::JSON.decode(json)['errors'] || {} rescue {}
|
19
|
-
from_hash hash, save_cache
|
20
|
-
end
|
21
|
-
end
|
22
|
-
end
|