cropio-ruby 0.1.2 → 0.1.3

Sign up to get free protection for your applications and to get access to all the features.
checksums.yaml CHANGED
@@ -1,7 +1,7 @@
1
1
  ---
2
2
  SHA1:
3
- metadata.gz: df3ab04e2f1368de1fceb18ca7c84826829de720
4
- data.tar.gz: cf07ed8c51da46d6626b4ed856e731a1dffed48c
3
+ metadata.gz: afd6f4a57445477df70033561a85459d8f7b69e2
4
+ data.tar.gz: 799fcb92903ae02aaa589e2209f602434032b9e9
5
5
  SHA512:
6
- metadata.gz: f55888c856366020c264e828a517b6e53c29038bd6057c60a75a2907340fafea6b5c68c808421a3364826b9fdae942289805b614781667b861e0b9506df254c9
7
- data.tar.gz: 2727d87c87dd21f3f9fd8e9147544c65b6bd5bd634d0cf5aadb09905627b3b000eb39baa3e7d553be3b296bfeadd972cf3b62b1a21b32841ac7c297f13dd533d
6
+ metadata.gz: 73783fbd5238a14da0bc6b7f00b38ac169f921abe1bf7502337b33d49cbb35f201c330a2cf4eba3eb46d5c2685d6bc0bc6ef4289e1f9981ec08f578b0535baba
7
+ data.tar.gz: ead1b0a204f01ec45fe396a66402040f34a32f24fa46433f19381bca4b79d4ac7dcae8c8a37bf55ec24c536c4d3fcbf5ba458292216c2d7656d54d7c9865296d
data/README.md CHANGED
@@ -23,7 +23,9 @@ Or install it yourself as:
23
23
 
24
24
  Require it:
25
25
 
26
- $ require 'cropio'
26
+ ```ruby
27
+ require 'cropio'
28
+ ```
27
29
 
28
30
  To load Cropio resources to current namespace:
29
31
 
@@ -36,7 +38,7 @@ try to request some data from Cropio gem will get authentication token.
36
38
 
37
39
  ```ruby
38
40
  Cropio.credentials = {
39
- email: 'your account email,
41
+ email: 'your account email',
40
42
  password: 'your password'
41
43
  }
42
44
 
data/Rakefile CHANGED
@@ -1 +1 @@
1
- require "bundler/gem_tasks"
1
+ require 'bundler/gem_tasks'
data/cropio-ruby.gemspec CHANGED
@@ -4,25 +4,32 @@ $LOAD_PATH.unshift(lib) unless $LOAD_PATH.include?(lib)
4
4
  require 'cropio/version'
5
5
 
6
6
  Gem::Specification.new do |spec|
7
- spec.name = "cropio-ruby"
8
- spec.version = Cropio::VERSION
9
- spec.authors = ["Sergey Vernidub"]
10
- spec.email = ["info@cropio.com"]
7
+ spec.name = 'cropio-ruby'
8
+ spec.version = Cropio::VERSION
9
+ spec.authors = ['Sergey Vernidub']
10
+ spec.email = ['info@cropio.com']
11
11
 
12
- spec.summary = %q{Cropio API bindings for Ruby}
13
- spec.description = %q{Cropio-Ruby provides simple ActiveRecord-like wrappings for Cropio API}
14
- spec.homepage = "https://cropio.com"
12
+ spec.summary = 'Cropio API bindings for Ruby'
15
13
 
16
- spec.files = `git ls-files -z`.split("\x0").reject { |f| f.match(%r{^(test|spec|features)/}) }
17
- spec.bindir = "exe"
18
- spec.executables = spec.files.grep(%r{^exe/}) { |f| File.basename(f) }
19
- spec.require_paths = ["lib"]
14
+ spec.description = <<STR
15
+ Cropio-Ruby provides simple ActiveRecord-like wrappings for Cropio API
16
+ STR
17
+
18
+ spec.homepage = 'https://cropio.com'
19
+
20
+ spec.files = `git ls-files -z`.split("\x0").reject do |f|
21
+ f.match(%r{^(test|spec|features)/})
22
+ end
23
+
24
+ spec.bindir = 'exe'
25
+ spec.executables = spec.files.grep(%r{^exe/}) { |f| File.basename(f) }
26
+ spec.require_paths = ['lib']
20
27
 
21
28
  spec.add_dependency 'json'
22
29
  spec.add_dependency 'rest-client'
23
30
 
24
- spec.add_development_dependency "bundler", "~> 1.9"
25
- spec.add_development_dependency "rake", "~> 10.0"
26
- spec.add_development_dependency "pry"
27
- spec.add_development_dependency "byebug"
31
+ spec.add_development_dependency 'bundler', '~> 1.9'
32
+ spec.add_development_dependency 'rake', '~> 10.0'
33
+ spec.add_development_dependency 'pry'
34
+ spec.add_development_dependency 'byebug'
28
35
  end
data/lib/cropio.rb CHANGED
@@ -5,11 +5,19 @@ require 'cropio/connection'
5
5
  require 'cropio/resource'
6
6
  require 'cropio/resources'
7
7
 
8
+ # Cropio-Ruby provides simple ActiveRecord-like wrappings
9
+ # for Cropio API. Currently it supports Cropio APIv3.
10
+ #
11
+ # Main gem's module Cropio contains accessors for credentials and other stuff
8
12
  module Cropio
13
+ # Getter for credentials
9
14
  def self.credentials
10
15
  @credentials
11
16
  end
12
17
 
18
+ # Setter for credentials,
19
+ # accepts Hash or OpenStruct with email and password or api_token
20
+ # as param
13
21
  def self.credentials=(credentials)
14
22
  case credentials
15
23
  when Hash
@@ -1,30 +1,36 @@
1
1
  module Cropio
2
2
  module Connection
3
+ # Contains authentication options for connection.
3
4
  module Authenticable
5
+ # Public interface for authentication request
4
6
  def authenticate!
5
7
  auth_request
6
8
  end
7
9
 
8
10
  protected
9
11
 
12
+ # Define wrappers around specified methods to be sure
13
+ # they are authenticated.
10
14
  def authenticate_before(*methods)
11
15
  methods.each do |method_name|
12
16
  unauthentificated_method = method(method_name)
13
17
  singleton_class.send(:define_method, method_name) do |*args|
14
- authenticate! if !authenticated?
18
+ authenticate! unless authenticated?
15
19
  unauthentificated_method.call(*args)
16
20
  end
17
21
  end
18
22
  end
19
23
 
24
+ # Send authentication request.
20
25
  def auth_request
21
26
  process_result RestClient.post(url_for('sign_in'),
22
- auth_request_params.to_json,
23
- authentication_headers)
27
+ auth_request_params.to_json,
28
+ authentication_headers)
24
29
  rescue RestClient::Unauthorized => e
25
30
  process_result(e.http_body)
26
31
  end
27
32
 
33
+ # Process result returned by authentication request.
28
34
  def process_result(result)
29
35
  result = JSON.parse(result)
30
36
 
@@ -36,6 +42,7 @@ module Cropio
36
42
  end
37
43
  end
38
44
 
45
+ # Return params based on user credentials.
39
46
  def auth_request_params
40
47
  {
41
48
  user_login: {
@@ -44,18 +51,22 @@ module Cropio
44
51
  }
45
52
  }
46
53
  rescue NoMethodError => e
47
- if %i(email password).include?(e.name)
48
- fail "Cropio credentials is not specified: #{e.name}"
49
- else
50
- raise e
51
- end
54
+ process_auth_params_error(e) || raise(e)
52
55
  end
53
56
 
57
+ # Returns true if user has api token.
54
58
  def authenticated?
55
59
  !Cropio.credentials.api_token.nil?
56
60
  rescue NoMethodError => e
57
61
  e.name == :api_token ? false : raise(e)
58
62
  end
63
+
64
+ # Process NoMethodError and prints norification if
65
+ # exeption was produced by empty credentials.
66
+ def process_auth_params_error(e)
67
+ return unless %i(email password).include?(e.name)
68
+ fail "Cropio credentials is not specified: #{e.name}"
69
+ end
59
70
  end
60
71
  end
61
72
  end
@@ -1,23 +1,27 @@
1
1
  module Cropio
2
2
  module Connection
3
+ # Contains logic for requests configuration
4
+ # like appending headers to requests.
3
5
  module Configurable
4
-
6
+ # Cropio's server and API's entry point url
5
7
  BASE_URL = 'https://cropio.com/api/v3'
6
8
 
7
9
  protected
8
10
 
11
+ # Returns headers set for request.
9
12
  def headers
10
13
  authenticated? ? authenticated_headers : authentication_headers
11
14
  end
12
15
 
16
+ # Returns headers for authentication query.
13
17
  def authentication_headers
14
18
  { content_type: :json, accept: :json }
15
19
  end
16
20
 
21
+ # Returns headers for authenticated queries.
17
22
  def authenticated_headers
18
- authentication_headers.merge({
19
- 'X-User-Api-Token' => Cropio.credentials.api_token
20
- })
23
+ authentication_headers.merge(
24
+ 'X-User-Api-Token' => Cropio.credentials.api_token)
21
25
  end
22
26
  end
23
27
  end
@@ -1,20 +1,25 @@
1
- require'rest-client'
1
+ require 'rest-client'
2
2
 
3
3
  module Cropio
4
4
  module Connection
5
+ # Contains logic of proxing calls to HTTPS requests.
5
6
  module Proxiable
6
- def get(resource, query={})
7
- proxy(method: :get, url: url_for(resource), headers: {params: query})
7
+ # Accepts reources name and params to perform HTTPS GET request.
8
+ def get(resource, query = {})
9
+ proxy(method: :get, url: url_for(resource), headers: { params: query })
8
10
  end
9
11
 
12
+ # Accepts reources name and params to perform HTTPS POST request.
10
13
  def post(resource, data)
11
14
  proxy(method: :post, url: url_for(resource), data: data)
12
15
  end
13
16
 
17
+ # Accepts reources name and params to perform HTTPS PATCH request.
14
18
  def patch(resource, data)
15
19
  proxy(method: :patch, url: url_for(resource), data: data)
16
20
  end
17
21
 
22
+ # Accepts reources name and params to perform HTTPS DELETE request.
18
23
  def delete(resource)
19
24
  proxy(method: :delete, url: url_for(resource))
20
25
  end
@@ -41,12 +46,12 @@ module Cropio
41
46
 
42
47
  def proxy_post(options)
43
48
  RestClient.post(options[:url],
44
- {data: options[:data]}, options[:headers])
49
+ { data: options[:data] }, options[:headers])
45
50
  end
46
51
 
47
52
  def proxy_patch(options)
48
53
  RestClient.patch(options[:url],
49
- {data: options[:data]}, options[:headers])
54
+ { data: options[:data] }, options[:headers])
50
55
  end
51
56
 
52
57
  def proxy_delete(options)
@@ -1,5 +1,7 @@
1
1
  module Cropio
2
2
  module Connection
3
+ # Encapsulates communication with Cropio API.
4
+ # Proxies calls to API as HTTPS requests.
3
5
  class Proxy
4
6
  extend Authenticable
5
7
  extend Configurable
@@ -1,21 +1,24 @@
1
1
  module Cropio
2
+ # StringInflector contains operations for strings.
3
+ # We think it is bad idea to require active_support for this.
2
4
  class StringInflector
3
5
  class << self
4
6
  def underscore(string)
5
7
  string
6
8
  .gsub(/::/, '/')
7
- .gsub(/([A-Z]+)([A-Z][a-z])/,'\1_\2')
8
- .gsub(/([a-z\d])([A-Z])/,'\1_\2')
9
- .tr("-", "_")
9
+ .gsub(/([A-Z]+)([A-Z][a-z])/, '\1_\2')
10
+ .gsub(/([a-z\d])([A-Z])/, '\1_\2')
11
+ .tr('-', '_')
10
12
  .downcase
11
13
  end
12
14
 
13
- # simple implementation - for resources plural form only
15
+ # Returns pluralized form for word passed as param.
16
+ # It is simple implementation - for resources plural forms only.
14
17
  def pluralize(string)
15
18
  if string[-1] == 'y'
16
- "#{ string[0..(string.length - 2)] }ies"
19
+ "#{string[0..(string.length - 2)]}ies"
17
20
  else
18
- "#{ string }s"
21
+ "#{string}s"
19
22
  end
20
23
  end
21
24
  end
@@ -1,5 +1,6 @@
1
1
  module Cropio
2
2
  module Resource
3
+ # Defines accessors for resource attrubutes.
3
4
  module Attributes
4
5
  def self.included(base)
5
6
  base.send(:attr_accessor, :attributes)
@@ -36,7 +37,7 @@ module Cropio
36
37
  end
37
38
 
38
39
  def define_attribute_getter(attribute_name)
39
- eval "
40
+ instance_eval "
40
41
  def #{attribute_name}
41
42
  attributes['#{attribute_name}']
42
43
  end
@@ -44,7 +45,7 @@ module Cropio
44
45
  end
45
46
 
46
47
  def define_attribute_setter(attribute_name)
47
- eval "
48
+ instance_eval "
48
49
  def #{attribute_name}=(val)
49
50
  attributes['#{attribute_name}'] = val
50
51
  end
@@ -52,7 +53,7 @@ module Cropio
52
53
  end
53
54
 
54
55
  def define_attribute_question(attribute_name)
55
- eval "
56
+ instance_eval "
56
57
  def #{attribute_name}?
57
58
  !attributes['#{attribute_name}'].nil?
58
59
  end
@@ -61,8 +62,8 @@ module Cropio
61
62
 
62
63
  def method_missing(name, *attrs, &block)
63
64
  name = name.to_s
64
- attr_name = name.gsub('=', '')
65
- if attributes.has_key?(attr_name)
65
+ attr_name = name.delete('=')
66
+ if attributes.key?(attr_name)
66
67
  define_attributes_accessors
67
68
  name == attr_name ? send(name) : send(name, attrs.first)
68
69
  else
@@ -1,81 +1,94 @@
1
1
  module Cropio
2
2
  module Resource
3
+ # Represents ActiveRecord::Base-like model's class
4
+ # with Cropio data selection and mutation.
3
5
  class Base
4
6
  include Attributes
5
7
 
6
- Proxy = Cropio::Connection::Proxy
7
- Limit = 1000
8
+ PROXY = Cropio::Connection::Proxy
9
+ LIMIT = 1000
8
10
 
9
- def initialize(attributes={})
11
+ def initialize(attributes = {})
10
12
  self.attributes = attributes
11
13
  end
12
14
 
15
+ # Returns name of Resource
13
16
  def self.resource_name
14
17
  @resource_name ||= StringInflector.underscore(name.split('::').last)
15
18
  end
16
19
 
20
+ # Return pluralized version of Resource's name
17
21
  def self.resources_name
18
22
  @resources_name ||= StringInflector.pluralize(resource_name)
19
23
  end
20
24
 
25
+ # Get all resources.
21
26
  def self.all
22
27
  to_instances(get_all_chunks)
23
28
  end
24
29
 
30
+ # Count all resources.
25
31
  def self.count
26
32
  all.count
27
33
  end
28
34
 
29
- def self.select(options={})
30
- end
31
-
35
+ # Returns persistance of the resource.
36
+ # Resource is persisted if it is saved
37
+ # and not deleted, if this resource exists
38
+ # on Cropio servers.
32
39
  def persisted?
33
- if @persisted.nil?
34
- @persisted = false
35
- end
36
-
37
- @persisted
40
+ @persisted.nil? && (@persisted ||= false)
38
41
  end
39
42
 
43
+ # Saves current resource to Cropio.
40
44
  def save
41
- self.attributes = if persisted?
42
- Proxy.patch("#{resources_name}/#{id}", attributes)
43
- else
44
- @persisted = true
45
- Proxy.post(resources_name, attributes)
46
- end
45
+ self.attributes =
46
+ if persisted?
47
+ PROXY.patch("#{resources_name}/#{id}", attributes)
48
+ else
49
+ @persisted = true
50
+ PROXY.post(resources_name, attributes)
51
+ end
47
52
  end
48
53
 
54
+ # Remove this resource from Cropio.
49
55
  def destroy
50
56
  if persisted?
51
- Proxy.delete("#{resources_name}/#{id}")
57
+ PROXY.delete("#{resources_name}/#{id}")
52
58
  @persisted = false
53
59
  true
54
60
  else
55
- raise 'Cropio record is not persisted!'
61
+ fail 'Cropio record is not persisted!'
56
62
  end
57
63
  end
58
64
 
59
65
  private
66
+
67
+ # Returns pluralized name of own type.
60
68
  def resources_name
61
69
  self.class.resources_name
62
70
  end
63
71
 
64
- def self.get_all_chunks(options={})
72
+ # Download resources from Cropio by Chunks.
73
+ def self.get_all_chunks(options = {})
65
74
  response = nil
66
75
  buffer = []
67
- limit = options[:limit] || (2 ** 32 - 1)
68
- while is_data?(response) && limit > 0
69
- chunk_size = limit < Limit ? limit : Limit
70
- limit -= chunk_size
71
- offset = buffer.any? ? buffer.last['id'] + 1 : 0
72
- response = get_chunk(limit: chunk_size, from_id: offset)
76
+ limit = options[:limit] || (2**32 - 1)
77
+ while data?(response) && limit > 0
78
+ limit -= limit < LIMIT ? limit : LIMIT
79
+ response = get_chunk(limit: limit, from_id: offset(buffer))
73
80
  buffer += response['data']
74
81
  end
75
82
  buffer
76
83
  end
77
84
 
78
- def self.is_data?(response=nil)
85
+ # Gets offset for next chunk during download.
86
+ def self.offset(buffer)
87
+ buffer.any? ? buffer.last['id'] + 1 : 0
88
+ end
89
+
90
+ # Returns false if chunk is not empty.
91
+ def self.data?(response = nil)
79
92
  if response.nil?
80
93
  true
81
94
  else
@@ -83,17 +96,21 @@ module Cropio
83
96
  end
84
97
  end
85
98
 
99
+ # Download chunk from Cropio.
86
100
  def self.get_chunk(options)
87
- Proxy.get(resources_name, limit: options[:limit],
88
- from_id: options[:from_id])
101
+ PROXY.get(resources_name,
102
+ limit: options[:limit],
103
+ from_id: options[:from_id])
89
104
  end
90
105
 
106
+ # Converts each received attribute's hash to resources.
91
107
  def self.to_instances(attr_sets)
92
108
  attr_sets.map do |attr_set|
93
109
  to_instance(attr_set)
94
110
  end
95
111
  end
96
112
 
113
+ # Converts specified attribute's hash to resource.
97
114
  def self.to_instance(attr_set)
98
115
  new(attr_set).tap do |resource|
99
116
  resource.instance_eval do
@@ -28,6 +28,6 @@ require_relative './resources/seed'
28
28
  require_relative './resources/user'
29
29
 
30
30
  module Cropio
31
- module CropioResources
31
+ module Resources
32
32
  end
33
33
  end
@@ -1,3 +1,3 @@
1
1
  module Cropio
2
- VERSION = "0.1.2"
2
+ VERSION = '0.1.3'
3
3
  end
metadata CHANGED
@@ -1,14 +1,14 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: cropio-ruby
3
3
  version: !ruby/object:Gem::Version
4
- version: 0.1.2
4
+ version: 0.1.3
5
5
  platform: ruby
6
6
  authors:
7
7
  - Sergey Vernidub
8
8
  autorequire:
9
9
  bindir: exe
10
10
  cert_chain: []
11
- date: 2015-08-19 00:00:00.000000000 Z
11
+ date: 2015-08-22 00:00:00.000000000 Z
12
12
  dependencies:
13
13
  - !ruby/object:Gem::Dependency
14
14
  name: json
@@ -94,7 +94,8 @@ dependencies:
94
94
  - - ">="
95
95
  - !ruby/object:Gem::Version
96
96
  version: '0'
97
- description: Cropio-Ruby provides simple ActiveRecord-like wrappings for Cropio API
97
+ description: |
98
+ Cropio-Ruby provides simple ActiveRecord-like wrappings for Cropio API
98
99
  email:
99
100
  - info@cropio.com
100
101
  executables: []