-
Notifications
You must be signed in to change notification settings - Fork 147
/
Copy pathbase.rb
133 lines (113 loc) · 3.96 KB
/
base.rb
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
require 'httparty'
require 'ostruct'
require 'forwardable'
module Pipedrive
# Globally set request headers
HEADERS = {
"User-Agent" => "Ruby.Pipedrive.Api",
"Accept" => "application/json",
"Content-Type" => "application/x-www-form-urlencoded"
}
# Base class for setting HTTParty configurations globally
class Base < OpenStruct
include HTTParty
base_uri 'https://api.pipedrive.com/v1'
headers HEADERS
format :json
extend Forwardable
def_delegators 'self.class', :delete, :get, :post, :put, :resource_path, :bad_response
attr_reader :data
# Create a new Pipedrive::Base object.
#
# Only used internally
#
# @param [Hash] attributes
# @return [Pipedrive::Base]
def initialize(attrs = {})
if attrs['data']
struct_attrs = attrs['data']
if attrs['additional_data']
struct_attrs.merge!(attrs['additional_data'])
end
else
struct_attrs = attrs
end
super(struct_attrs)
end
# Updates the object.
#
# @param [Hash] opts
# @return [Boolean]
def update(opts = {}, custom_header = {})
res = put "#{resource_path}/#{id}", body: opts, headers: Base.default_options[:headers].merge(custom_header)
opts = JSON.parse(opts) unless opts.is_a?(Hash)
if res.success?
res['data'] = Hash[res['data'].map {|k, v| [k.to_sym, v] }]
@table.merge!(res['data'])
else
Base.bad_response(res, opts)
end
end
class << self
# Sets the authentication credentials in a class variable.
#
# @param [String] email cl.ly email
# @param [String] password cl.ly password
# @return [Hash] authentication credentials
def authenticate(token)
default_params :api_token => token
end
# Examines a bad response and raises an appropriate exception
#
# @param [HTTParty::Response] response
def bad_response(response, params={})
puts params.inspect
if response.class == HTTParty::Response
raise HTTParty::ResponseError, response
end
raise StandardError, 'Unknown error'
end
def new_list( attrs )
attrs['data'].is_a?(Array) ? attrs['data'].map {|data| self.new( 'data' => data ) } : []
end
def all(response = nil, options = { query: {} }, get_absolutely_all = true)
res = response || get(resource_path, options)
if res.ok?
data = res['data'].nil? ? [] : res['data'].map{|obj| new(obj)}
if get_absolutely_all && res['additional_data'] && res['additional_data']['pagination'] && res['additional_data']['pagination']['more_items_in_collection']
options[:query] = options[:query].merge({:start => res['additional_data']['pagination']['next_start']})
data += self.all(nil,options,true)
end
data
else
bad_response(res, options)
end
end
def create(opts = {}, custom_header = {})
res = post resource_path, body: opts, headers: default_options[:headers].merge(custom_header)
opts = JSON.parse(opts) unless opts.is_a?(Hash)
if res.success?
res['data'] = opts.merge res['data']
new(res)
else
bad_response(res,opts)
end
end
def find(id)
res = get "#{resource_path}/#{id}"
res.ok? ? new(res) : bad_response(res,id)
end
def find_by_name(name, opts={})
res = get "#{resource_path}/find", :query => { :term => name }.merge(opts)
res.ok? ? new_list(res) : bad_response(res,{:name => name}.merge(opts))
end
def resource_path
# The resource path should match the camelCased class name with the
# first letter downcased. Pipedrive API is sensitive to capitalisation
klass = name.split('::').last
klass[0] = klass[0].chr.downcase
klass.end_with?('y') ? "/#{klass.chop}ies" : "/#{klass}s"
end
end
end
end