riq 1.0.1 → 1.0.2

Sign up to get free protection for your applications and to get access to all the features.
@@ -0,0 +1,158 @@
1
+ require_relative 'riq_obj'
2
+ using RIQExtensions
3
+
4
+ module RIQ
5
+ # Contacts represent people in an Organization’s address book.
6
+ class Contact < RIQObject
7
+ attr_accessor :properties
8
+
9
+ # (see RIQObject#node)
10
+ def node
11
+ self.class.node(@id)
12
+ end
13
+
14
+ # (see RIQObject.node)
15
+ def self.node(id = nil)
16
+ "contacts/#{id}"
17
+ end
18
+
19
+ # (see RIQObject#data)
20
+ def data
21
+ {
22
+ id: @id,
23
+ properties: @properties
24
+ # modified_date: @modified_date
25
+ }
26
+ end
27
+
28
+ # @!macro [new] prop
29
+ # @return [Array] all of the values for $0
30
+ def name
31
+ get_prop(:name)
32
+ end
33
+
34
+ # @macro prop
35
+ def phone
36
+ get_prop(:phone)
37
+ end
38
+
39
+ # @macro prop
40
+ def email
41
+ get_prop(:email)
42
+ end
43
+
44
+ # @macro prop
45
+ def address
46
+ get_prop(:address)
47
+ end
48
+
49
+ # Adds property with correct scaffolding
50
+ # @param prop [Symbol] Type Property to add, such as :name or :email
51
+ # @param val [String, Array] Value(s) to add
52
+ # @return [Array] Values for that property after the add
53
+ def add(prop, val)
54
+ # validate(prop)
55
+ prop = prop.to_sym
56
+ @properties[prop] = [] unless @properties.include? prop
57
+
58
+ if val.is_a? Array
59
+ val.each do |i|
60
+ add(prop, i)
61
+ end
62
+ return
63
+ end
64
+
65
+ raise RIQError, 'Values must be strings' unless val.is_a? String
66
+
67
+ # don't add duplicate
68
+ if @properties[prop].select{|p| p[:value] == val}.empty?
69
+ @properties[prop] << {value: val, metadata: {}}
70
+ end
71
+ send(prop)
72
+ end
73
+
74
+ # Removes property from hash
75
+ # @param prop [Symbol] Type Property to remove, such as :name or :email
76
+ # @param val [String, Array] Value(s) to remove
77
+ # @return [Array] Values for that property after the remove
78
+ def remove(prop, val)
79
+ # validate(prop)
80
+ prop = prop.to_sym
81
+
82
+ if val.is_a? Array
83
+ val.each do |i|
84
+ remove(prop, i)
85
+ end
86
+ end
87
+
88
+ if @properties.include? prop
89
+ @properties[prop] = @properties[prop].reject{|p| p[:value] == val}
90
+ end
91
+ send(prop)
92
+ end
93
+
94
+ # Edits an existing object based on matching email(s) or saves a new object
95
+ # @see RIQObject#save
96
+ def upsert
97
+ save({_upsert: 'email'})
98
+ end
99
+
100
+ # @param prop [Symbol] The property to fetch. One of [:name, :phone, :email, :address]
101
+ # @param val [String] The value to get info on, such as 'name@domain.com'
102
+ # @return [Hash] metadata and other info about a given property
103
+ def info(prop, val)
104
+ # validate(prop)
105
+
106
+ @properties[prop].select{|p| p[:value] == val}.first
107
+ end
108
+
109
+ private
110
+
111
+ def init(obj = nil)
112
+ unless obj.nil?
113
+ @id = obj[:id]
114
+ @modified_date = obj[:modified_date].cut_milis if obj[:modified_date]
115
+ @properties = {}
116
+ obj[:properties].each do |k,v|
117
+ raise RIQError, "Properties must be arrays, #{k} wasn't" if !v.is_a?(Array)
118
+
119
+ v.each do |i|
120
+ unless i.is_a?(Hash)
121
+ add(k, i)
122
+ else
123
+ @properties[k] = [] unless @properties.include?(k)
124
+ @properties[k] << i
125
+ end
126
+ end
127
+ end
128
+ else
129
+ @id = nil
130
+ @properties = {}
131
+ end
132
+ self
133
+ end
134
+
135
+ # unused because we actually put all sorts of stuff in there
136
+ def validate(prop)
137
+ raise RIQError, %q(Invalid property. Use [:name | :phone | :email | :address] instead) unless [:name, :phone, :email, :address].include? prop
138
+ end
139
+
140
+ def get_prop(prop)
141
+ if @properties.include? prop
142
+ @properties[prop].map{|p| p[:value]}
143
+ else
144
+ []
145
+ end
146
+ end
147
+ end
148
+
149
+ class << self
150
+ # Convenience method to create new Contacts
151
+ # @param id [String, nil] create a blank Contact object or
152
+ # fetch an existing one by id.
153
+ # @return [Contact]
154
+ def contact(id = nil)
155
+ Contact.new(id)
156
+ end
157
+ end
158
+ end
@@ -0,0 +1,56 @@
1
+ module RIQ
2
+ # Base exception class for our errors.
3
+ class RIQError < StandardError
4
+ end
5
+
6
+ # Hasn't been implemented yet. Doesn't get used often.
7
+ class NotImplementedError < RIQError
8
+ end
9
+
10
+ # Raised when an ObjectId fetch doesn't return anything.
11
+ class NotFoundError < RIQError
12
+ end
13
+
14
+ # Main error that includes info about the request and what went wrong.
15
+ class HTTPError < RIQError
16
+ attr_accessor :code
17
+ attr_accessor :message
18
+ attr_accessor :response
19
+
20
+ def initialize(resp)
21
+ # build response message
22
+ message = "\n[#{resp.code}] #{resp.message} : "
23
+ unless resp.parsed_response.nil?
24
+ begin
25
+ m = resp.parsed_response.fetch('errorMessage', 'no message')
26
+ rescue
27
+ # parse returned HTML
28
+ reg = resp.parsed_response.match(/<pre>(.*)<\/pre>/)
29
+ unless reg.nil?
30
+ m = reg[1].strip
31
+ else
32
+ m = 'no message'
33
+ end
34
+ end
35
+ message += "<#{m}>"
36
+ end
37
+
38
+ # pull out request info
39
+ req = resp.request
40
+ unless req.nil?
41
+ message += "\n Request: #{req.http_method} #{req.last_uri.to_s}"
42
+ unless req.raw_body.nil?
43
+ message += "\n #{req.raw_body}"
44
+ end
45
+ end
46
+
47
+ @message = message
48
+ @response = resp
49
+ end
50
+
51
+ # used to print the error nicely
52
+ def to_s
53
+ @message || super
54
+ end
55
+ end
56
+ end
@@ -0,0 +1,73 @@
1
+ require_relative 'riq_obj'
2
+ using RIQExtensions
3
+
4
+ module RIQ
5
+ # Events represent interactions involving a Contact associated with a List Item.
6
+ class Event < RIQObject
7
+ attr_accessor :subject
8
+ attr_accessor :body
9
+ # attr_reader :participant_ids
10
+
11
+ # (see RIQObject#node)
12
+ def node
13
+ self.class.node
14
+ end
15
+
16
+ # (see RIQObject#node)
17
+ def self.node
18
+ "events"
19
+ end
20
+
21
+ # (see RIQObject#data)
22
+ def data
23
+ {
24
+ subject: @subject,
25
+ body: @body,
26
+ participant_ids: @participant_ids
27
+ }
28
+ end
29
+
30
+ # @param type [Symbol] One of :email or :phone
31
+ # @param value [String] An email or phone number for the contact
32
+ def add_participant(type, value)
33
+ raise RIQError, 'Type must be :email or :phone' unless [:email, :phone].include?(type)
34
+ @participant_ids << {type: type, value: value}
35
+ end
36
+
37
+ # @return [Array] Immutable copy of participant_ids
38
+ def participant_ids
39
+ @participant_ids.dup
40
+ end
41
+
42
+ # @return [Hash] Success message, if successful.
43
+ def save
44
+ # there are no options to pass for event save
45
+ @client.put(node, payload, options: nil)
46
+ {status: 204, message: 'No Content'}
47
+ end
48
+
49
+ private
50
+ def init(obj = nil)
51
+ unless obj.nil?
52
+ @subject = obj[:subject]
53
+ @body = obj[:body]
54
+ @participant_ids = []
55
+ obj[:participant_ids].each{|o| add_participant(o[:type], o[:value])}
56
+ else
57
+ @subject = nil
58
+ @body = nil
59
+ @participant_ids = []
60
+ end
61
+ self
62
+ end
63
+ end
64
+
65
+ class << self
66
+ # Convenience method to create new Events
67
+ # @param obj [Hash] Info to parse into event
68
+ # @return [Event]
69
+ def event(obj = nil)
70
+ Event.new(obj)
71
+ end
72
+ end
73
+ end
@@ -0,0 +1,89 @@
1
+ require_relative 'riq_obj'
2
+
3
+ module RIQ
4
+ # A List is an object that can be created and customized by a User to represent
5
+ # Accounts (companies) or Contacts (people) in a process (such as a sales pipeline).
6
+ class List < RIQObject
7
+ # can't create a list through API, so these don't need to write
8
+ attr_reader :title
9
+ attr_reader :type
10
+ attr_reader :list_items
11
+ # for consistency
12
+ alias_method :name, :title
13
+
14
+ # (see RIQObject#initialize)
15
+ def initialize(id = nil)
16
+ super
17
+ @list_items = ListItemManager.new(@id)
18
+ end
19
+
20
+ # (see RIQObject#node)
21
+ def node
22
+ self.class.node(@id)
23
+ end
24
+
25
+ # (see RIQObject.node)
26
+ def self.node(id = nil)
27
+ "lists/#{id}"
28
+ end
29
+
30
+ # (see RIQObject#data)
31
+ def data
32
+ {
33
+ id: @id,
34
+ title: @title,
35
+ type: @type,
36
+ fields: @fields
37
+ }
38
+ end
39
+
40
+ # Overwriting parent because lists can't be saved through the API
41
+ def save
42
+ raise NotImplementedError, "Lists can't be edited through the API"
43
+ end
44
+
45
+ # Gets field if it exists
46
+ # @param id [String, Integer] field ID
47
+ # @return [Hash, nil] info on the field specified
48
+ def fields(id = nil)
49
+ unless id.nil?
50
+ @fields.select{|f| f['id'] == id.to_s}.first
51
+ else
52
+ @fields
53
+ end
54
+ end
55
+
56
+ # Convenience method for fetching or creating a listitem from the given list
57
+ # @param oid [String, nil] ObjectId
58
+ def list_item(oid = nil)
59
+ RIQ::ListItem.new(oid, lid: @id)
60
+ end
61
+
62
+ private
63
+
64
+ def init(obj = nil)
65
+ unless obj.nil?
66
+ @id = obj[:id]
67
+ @title = obj[:title]
68
+ @type = obj[:listType]
69
+ @fields = obj[:fields]
70
+ else
71
+ @id = nil
72
+ @title = nil
73
+ @type = nil
74
+ @fields = nil
75
+ end
76
+ self
77
+ end
78
+ end
79
+
80
+ class << self
81
+ # Convenience method to create new Lists
82
+ # @param id [String, nil] create a blank List object or
83
+ # fetch an existing one by id.
84
+ # @return [List]
85
+ def list(id = nil)
86
+ List.new(id)
87
+ end
88
+ end
89
+ end
@@ -0,0 +1,119 @@
1
+ require_relative 'riq_obj'
2
+ using RIQExtensions
3
+
4
+ module RIQ
5
+ # A List Item is a row in a List.
6
+ class ListItem < RIQObject
7
+ attr_accessor :name
8
+ attr_accessor :field_values
9
+ attr_accessor :account_id
10
+ attr_accessor :contact_ids
11
+ attr_accessor :list_id
12
+
13
+ attr_reader :modified_date
14
+ attr_reader :created_date
15
+
16
+ def initialize(id = nil, lid: nil)
17
+ if id.is_a? Hash
18
+ super(id)
19
+ elsif id.nil? && lid.nil?
20
+ super(nil)
21
+ elsif id.nil? && !lid.nil?
22
+ super(nil)
23
+ @list_id = lid
24
+ elsif id.nil? || lid.nil?
25
+ raise RIQError, 'ObjectID and List ID are required'
26
+ else
27
+ super("#{lid}/listitems/#{id}")
28
+ end
29
+ end
30
+
31
+ # (see RIQObject#node)
32
+ def node
33
+ self.class.node(@list_id, @id)
34
+ end
35
+
36
+ # @note this is the only object for which you have to include two params
37
+ # @param lid [String] ListId that the lit item belongs to
38
+ # @param oid [String] ObjectId for the object
39
+ def self.node(lid = nil, oid = nil)
40
+ # weird workaround for fetching node on init
41
+ if lid.nil? && !oid.nil?
42
+ "lists/#{oid}"
43
+ else
44
+ "lists/#{lid || @list_id}/listitems/#{oid}"
45
+ end
46
+ end
47
+
48
+ # (see RIQObject#data)
49
+ def data
50
+ {
51
+ name: @name,
52
+ account_id: @account_id,
53
+ contact_ids: @contact_ids.flatten,
54
+ id: @id,
55
+ list_id: @list_id,
56
+ field_values: @field_values,
57
+ modified_date: @modified_date
58
+ }
59
+ end
60
+
61
+ # (see RIQObject#payload)
62
+ def payload
63
+ pld = {}
64
+ data.each do |k, v|
65
+ if k == :field_values
66
+ pld['fieldValues'] = @field_values.to_raw
67
+ elsif k['_']
68
+ pld[k.to_cam] = v
69
+ else
70
+ pld[k] = v
71
+ end
72
+ end
73
+ pld.to_json
74
+ end
75
+
76
+ # @overload field_value(key)
77
+ # @param key [String, Integer]
78
+ # @return [Array] Value of key
79
+ # @overload field_value(key, value)
80
+ # Sets key to value
81
+ # @param key [String, Integer] Key to set
82
+ # @param value [#to_s] Sets key to value
83
+ def field_value(key, value = nil)
84
+ # TODO: double check that this works with arrays of stuff
85
+ # or, have a format function that casts ints to string on save
86
+ if value.nil?
87
+ @field_values.fetch(key.to_sym, nil)
88
+ else
89
+ @field_values[key.to_sym] = value.to_s
90
+ {key.to_sym => value.to_s}
91
+ end
92
+ end
93
+
94
+ private
95
+
96
+ def init(obj = nil)
97
+ unless obj.nil?
98
+ @id = obj[:id]
99
+ @list_id = obj[:list_id]
100
+ @name = obj[:name]
101
+ @field_values = obj[:field_values] ? obj[:field_values].from_raw : {}
102
+ @account_id = obj[:account_id]
103
+ @contact_ids = obj[:contact_ids] || []
104
+ @modified_date = obj[:modified_date].cut_milis if obj[:modified_date]
105
+ @created_date = obj[:creaeted_date].cut_milis if obj[:creaeted_date]
106
+ else
107
+ @id = nil
108
+ @list_id = nil
109
+ @name = nil
110
+ @field_values = {}
111
+ @account_id = nil
112
+ @contact_ids = []
113
+ @modified_date = nil
114
+ @created_date = nil
115
+ end
116
+ self
117
+ end
118
+ end
119
+ end