wixanswers 0.0.3
Sign up to get free protection for your applications and to get access to all the features.
- checksums.yaml +7 -0
- data/CHANGELOG.md +13 -0
- data/LICENSE.md +7 -0
- data/README.md +53 -0
- data/lib/wixanswers.rb +23 -0
- data/lib/wixanswers/models/attachment.rb +20 -0
- data/lib/wixanswers/models/base.rb +39 -0
- data/lib/wixanswers/models/label.rb +16 -0
- data/lib/wixanswers/models/ticket/by_agent.rb +8 -0
- data/lib/wixanswers/models/ticket/chat.rb +8 -0
- data/lib/wixanswers/models/ticket/phone_callback.rb +7 -0
- data/lib/wixanswers/models/ticket/reply.rb +58 -0
- data/lib/wixanswers/models/ticket/ticket.rb +117 -0
- data/lib/wixanswers/models/ticket/widget.rb +7 -0
- data/lib/wixanswers/models/user/agent.rb +35 -0
- data/lib/wixanswers/models/user/company.rb +11 -0
- data/lib/wixanswers/models/user/group.rb +21 -0
- data/lib/wixanswers/models/user/location.rb +14 -0
- data/lib/wixanswers/models/user/team.rb +14 -0
- data/lib/wixanswers/models/user/user.rb +34 -0
- data/lib/wixanswers/models/user_info.rb +44 -0
- data/lib/wixanswers/rest/api.rb +6 -0
- data/lib/wixanswers/rest/enumerations.rb +95 -0
- data/lib/wixanswers/rest/exceptions.rb +28 -0
- data/lib/wixanswers/version.rb +38 -0
- data/wixanswers.gemspec +19 -0
- metadata +82 -0
checksums.yaml
ADDED
@@ -0,0 +1,7 @@
|
|
1
|
+
---
|
2
|
+
SHA256:
|
3
|
+
metadata.gz: ab2efe60f7a4edaf0679e4af2e77136613dc5db51c778154971faf9e1fddb782
|
4
|
+
data.tar.gz: 79384045fa6f34ec14a8e6c3ac83f5460f061e4ff7d772fb64840b441c26cb82
|
5
|
+
SHA512:
|
6
|
+
metadata.gz: b8033ceed55b50873ec0eb48c44e3d952fba71d24978009aa1893c5bdb118596e28b6daed89086423d7dd25981f19aef05e28ab763283991feb3daee31816652
|
7
|
+
data.tar.gz: 794022bc28a08b1630ff841af19b03ccbd21595b053d811ca16109f45c46bea6c2a93a7e35fd2f029952a16ead825389bbc7d01a26d38c37011e448c2d960ada
|
data/CHANGELOG.md
ADDED
@@ -0,0 +1,13 @@
|
|
1
|
+
0.0.3
|
2
|
+
------
|
3
|
+
* fixed wrong method name
|
4
|
+
|
5
|
+
0.0.1
|
6
|
+
------
|
7
|
+
|
8
|
+
* Created models for all Ticket and Reply objects
|
9
|
+
* Created models for all User objects
|
10
|
+
* Created models for Attachment, Label and UserInfo attributes
|
11
|
+
* Created basic Enumerations for WixAnswers
|
12
|
+
* Validate object structure using SCHEMA and raise exceptions on non-implemented objects
|
13
|
+
* load ticket and reply objects from a raw payload
|
data/LICENSE.md
ADDED
@@ -0,0 +1,7 @@
|
|
1
|
+
Copyright (c) 2020 Roee Sheelo
|
2
|
+
|
3
|
+
Permission is hereby granted, free of charge, to any person obtaining a copy of this software and associated documentation files (the "Software"), to deal in the Software without restriction, including without limitation the rights to use, copy, modify, merge, publish, distribute, sublicense, and/or sell copies of the Software, and to permit persons to whom the Software is furnished to do so, subject to the following conditions:
|
4
|
+
|
5
|
+
The above copyright notice and this permission notice shall be included in all copies or substantial portions of the Software.
|
6
|
+
|
7
|
+
THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
|
data/README.md
ADDED
@@ -0,0 +1,53 @@
|
|
1
|
+
# wixanswers
|
2
|
+
A Ruby Wrapper to the WIX Answers REST API
|
3
|
+
|
4
|
+
# Introduction
|
5
|
+
The WIX Answers REST API enables you to use code to interact
|
6
|
+
with the Wix Answers back-end. You can use the API to create
|
7
|
+
webhooks that interact with the Wix Answers front and back-ends,
|
8
|
+
or create a new front-end app that works with the Wix Answers
|
9
|
+
back-end. You can also use the API to get information about your
|
10
|
+
customers and their Wix Answers history
|
11
|
+
(Source: [Wix Answers Developers Overview](https://help.wixanswers.com/kb/en/article/wix-answers-api-overview)).
|
12
|
+
|
13
|
+
This library serves as a Ruby wrapper for the API, in order to
|
14
|
+
enable easy interfacing with WIX Answers REST API's raw payload.
|
15
|
+
|
16
|
+
# Features
|
17
|
+
* Schema-based Objects for Tickets, Users and other API objects
|
18
|
+
* Schema validation
|
19
|
+
* Enumerations and enumerations validation
|
20
|
+
|
21
|
+
|
22
|
+
# Usage Examples
|
23
|
+
|
24
|
+
**Instantiating a new Ticket directly**
|
25
|
+
```
|
26
|
+
ticket = WixAnswers:Models::Ticket.new(<ticket_payload>)
|
27
|
+
```
|
28
|
+
|
29
|
+
**Instantiating a new Ticket via the `#from_payload` method**
|
30
|
+
```
|
31
|
+
ticket = WixAnswers::Models::Ticket.from_payload(<ticket_payload>)
|
32
|
+
```
|
33
|
+
|
34
|
+
**Validating Enumeration**
|
35
|
+
```
|
36
|
+
WixAnswers::Enumerations::Channel.validate!(payload[:channel])
|
37
|
+
```
|
38
|
+
|
39
|
+
# Supported Ruby Versions
|
40
|
+
|
41
|
+
* \>= 2.3
|
42
|
+
|
43
|
+
|
44
|
+
# Installation
|
45
|
+
|
46
|
+
```
|
47
|
+
gem install wixanswers
|
48
|
+
```
|
49
|
+
|
50
|
+
Or via Gemfile:
|
51
|
+
```
|
52
|
+
gem 'wixanswers'
|
53
|
+
```
|
data/lib/wixanswers.rb
ADDED
@@ -0,0 +1,23 @@
|
|
1
|
+
require 'wixanswers/rest/api'
|
2
|
+
require 'wixanswers/rest/enumerations'
|
3
|
+
require 'wixanswers/rest/exceptions'
|
4
|
+
|
5
|
+
require 'wixanswers/models/base'
|
6
|
+
|
7
|
+
require 'wixanswers/models/user/user'
|
8
|
+
require 'wixanswers/models/user/agent'
|
9
|
+
require 'wixanswers/models/user/company'
|
10
|
+
require 'wixanswers/models/user/group'
|
11
|
+
require 'wixanswers/models/user/location'
|
12
|
+
require 'wixanswers/models/user/team'
|
13
|
+
|
14
|
+
require 'wixanswers/models/ticket/ticket'
|
15
|
+
require 'wixanswers/models/ticket/reply'
|
16
|
+
require 'wixanswers/models/ticket/by_agent'
|
17
|
+
require 'wixanswers/models/ticket/chat'
|
18
|
+
require 'wixanswers/models/ticket/phone_callback'
|
19
|
+
require 'wixanswers/models/ticket/widget'
|
20
|
+
|
21
|
+
require 'wixanswers/models/attachment'
|
22
|
+
require 'wixanswers/models/label'
|
23
|
+
require 'wixanswers/models/user_info'
|
@@ -0,0 +1,20 @@
|
|
1
|
+
require_relative './base'
|
2
|
+
|
3
|
+
# https://help.wixanswers.com/kb/en/article/api-object-structures#attachment-object
|
4
|
+
module WixAnswers
|
5
|
+
module Models
|
6
|
+
class Attachment < Base
|
7
|
+
SCHEMA ||= {
|
8
|
+
name: {type: "String", description: "The attachment name", required: true},
|
9
|
+
url: {type: "String", description: "URL of the attachment", required: true},
|
10
|
+
status: {type: "Integer", description: "The attachment status", required: true},
|
11
|
+
sizeBytes: {type: "Integer", description: "The size of the attachment, in bytes"},
|
12
|
+
contentType: {type: "String", description: "The content type of the attachment"}
|
13
|
+
}
|
14
|
+
|
15
|
+
def initialize(attrs={})
|
16
|
+
super(attrs)
|
17
|
+
end
|
18
|
+
end
|
19
|
+
end
|
20
|
+
end
|
@@ -0,0 +1,39 @@
|
|
1
|
+
|
2
|
+
module WixAnswers
|
3
|
+
module Models
|
4
|
+
class Base
|
5
|
+
attr_accessor :attrs
|
6
|
+
|
7
|
+
def initialize(attrs={})
|
8
|
+
self.attrs = attrs.deep_symbolize_keys!
|
9
|
+
|
10
|
+
self.validate!
|
11
|
+
end
|
12
|
+
|
13
|
+
def validate!
|
14
|
+
self.validate_schema!
|
15
|
+
|
16
|
+
return self
|
17
|
+
end
|
18
|
+
|
19
|
+
def validate_schema!
|
20
|
+
return unless defined?(self.class::SCHEMA)
|
21
|
+
|
22
|
+
# make sure all required params appear and that the supplied arguments match their types
|
23
|
+
self.class::SCHEMA.each_pair do |k,v|
|
24
|
+
attr = self.attrs[k]
|
25
|
+
|
26
|
+
raise WixAnswers::Exceptions::MissingAttribute.new(k) if v[:required] and attr.nil?
|
27
|
+
|
28
|
+
attr_type = v[:type] == "Boolean" ? ["FalseClass", "TrueClass"] : Array.wrap(v[:type])
|
29
|
+
|
30
|
+
raise WixAnswers::Exceptions::SchemaTypeError.new(v[:type], attr.class.name) if !attr.nil? and !attr_type.include?(attr.class.name)
|
31
|
+
end
|
32
|
+
end
|
33
|
+
|
34
|
+
def method_missing(k)
|
35
|
+
self.attrs[k.to_sym]
|
36
|
+
end
|
37
|
+
end
|
38
|
+
end
|
39
|
+
end
|
@@ -0,0 +1,16 @@
|
|
1
|
+
|
2
|
+
module WixAnswers
|
3
|
+
module Models
|
4
|
+
class Label < Base
|
5
|
+
SCHEMA ||= {
|
6
|
+
id: {type: "String", description: "Ticket ID", required: true},
|
7
|
+
name: {type: "String", required: true},
|
8
|
+
status: {type: "Integer", required: true}
|
9
|
+
}
|
10
|
+
|
11
|
+
def initialize(attrs={})
|
12
|
+
super(attrs)
|
13
|
+
end
|
14
|
+
end
|
15
|
+
end
|
16
|
+
end
|
@@ -0,0 +1,58 @@
|
|
1
|
+
|
2
|
+
# https://help.wixanswers.com/kb/en/article/api-object-structures#reply-object
|
3
|
+
module WixAnswers
|
4
|
+
module Models
|
5
|
+
class Reply < Base
|
6
|
+
SCHEMA ||= {
|
7
|
+
id: {type: "String", description: "Reply ID", required: true},
|
8
|
+
ticketId: {type: "String", description: "The ticket to which this reply is attached", required: true},
|
9
|
+
content: {type: "String", description: "Reply content HTML"},
|
10
|
+
type: {type: "Integer", description: "Reply Type", required: true},
|
11
|
+
attachments: {type: "Array", description: "List of reply attachments"},
|
12
|
+
ccRecipients: {type: "Array", description: "Current CC email addresses associated with the reply"},
|
13
|
+
slaState: {type: "Hash", description: "SLA policy associated with the reply"},
|
14
|
+
newTicketStatus: {type: "Integer", description: "New Ticket Status. Relevant when the ticket status is changed when the reply is attached."},
|
15
|
+
user: {type: "Hash", description: "The user or agent that wrote the reply", required: true},
|
16
|
+
userInfo: {type: "Hash", description: "Structure of user system information sent by the user's browser"},
|
17
|
+
channel: {type: "Integer", description: "How the reply was created", required: true},
|
18
|
+
webChannelData: {type: "Hash", description: "Additional data is channel is web"},
|
19
|
+
chatChannelData: {type: "Hash", description: "Additional data if channel is chat"},
|
20
|
+
widgetChannelData: {type: "Hash", description: "Additional data if channel is widget"},
|
21
|
+
emailChannelData: {type: "Hash", description: "Additional data if channel is email"},
|
22
|
+
facebookChannelData: {type: "Hash", description: "Additional data if channel is facebook"},
|
23
|
+
timelineItemType: {type: "Integer", description: "For a reply, this is always 9"},
|
24
|
+
deleted: {type: "Boolean", description: "Whether this reply was deleted"},
|
25
|
+
creationDate: {type: "Integer", description: "Time this record was created", required: true},
|
26
|
+
lastUpdateDate: {type: "Integer", description: "Last time this record was updated"},
|
27
|
+
importId: {type: "String", description: "Import batch process"},
|
28
|
+
parentTicket: {type: "Hash", required: true},
|
29
|
+
}
|
30
|
+
|
31
|
+
def initialize(attrs={})
|
32
|
+
super(attrs)
|
33
|
+
end
|
34
|
+
|
35
|
+
def validate!
|
36
|
+
Enumerations::ReplyType.validate!(self.attrs[:type])
|
37
|
+
super
|
38
|
+
end
|
39
|
+
|
40
|
+
def user
|
41
|
+
@_user ||= User.new(self.attrs[:user] || {})
|
42
|
+
end
|
43
|
+
|
44
|
+
def ticket
|
45
|
+
return @_ticket if defined?(@_ticket)
|
46
|
+
|
47
|
+
attrs = self.attrs[:parentTicket]
|
48
|
+
return if attrs.nil?
|
49
|
+
|
50
|
+
@_ticket = Ticket.from_payload(attrs)
|
51
|
+
end
|
52
|
+
|
53
|
+
def user_info
|
54
|
+
self.ticket.user_info unless self.ticket.nil?
|
55
|
+
end
|
56
|
+
end
|
57
|
+
end
|
58
|
+
end
|
@@ -0,0 +1,117 @@
|
|
1
|
+
|
2
|
+
# https://help.wixanswers.com/kb/en/article/api-object-structures#ticket-object
|
3
|
+
|
4
|
+
module WixAnswers
|
5
|
+
module Models
|
6
|
+
class Ticket < Base
|
7
|
+
SCHEMA ||= {
|
8
|
+
id: {type: "String", description: "Ticket ID", required: true},
|
9
|
+
locale: {type: "String", description: "Ticket language"},
|
10
|
+
subject: {type: "String", description: "Ticket subject", required: true},
|
11
|
+
content: {type: "String", description: "Ticket content"},
|
12
|
+
user: {type: "Hash", description: "User that created the ticket, or on behalf of whom the ticket was created", required: true},
|
13
|
+
company: {type: "Hash", description: "Company associated with the ticket"},
|
14
|
+
userInfo: {type: "Hash", description: "Structure of user system information sent by the user's browser"},
|
15
|
+
status: {type: "Integer", description: "Ticket Status", required: true},
|
16
|
+
priority: {type: "Integer", description: "Ticket priority", required: true},
|
17
|
+
repliesCount: {type: "Integer", description: "Number of ticket replies (user and agent replies, not including internal notes)"},
|
18
|
+
lastReply: {type: "Hash", description: "Last reply (user or agent, not internal note)"},
|
19
|
+
channel: {type: "Integer", description: "The channel by which the ticket was created"},
|
20
|
+
channelData: {type: "Hash", description: "Other data related to the channel, depending on the channel"},
|
21
|
+
labels: {type: "Array", description: "List of labels attached to the ticket"},
|
22
|
+
relatedArticleIds: {type: "Array", description: "List of articles that are marked as related to the ticket"},
|
23
|
+
ticketNumber: {type: "Integer", description: "Ticket reference number", required: true},
|
24
|
+
creationDate: {type: "Integer", description: "Time this record was created", required: true},
|
25
|
+
lastUpdateDate: {type: "Integer", description: "Last time this record was updated"},
|
26
|
+
assignedBy: {type: "Hash", description: "Agent who assigned the ticket"},
|
27
|
+
createdByAgent: {type: "Hash", description: "Agent who created the ticket"},
|
28
|
+
assignedUser: {type: "Hash", description: "Agent assigned to the ticket"},
|
29
|
+
assignedGroup: {type: "Hash", description: "Agent group assigned to the ticket"},
|
30
|
+
lastAgentReplyDate: {type: "Integer", description: "The time of the last agent reply"},
|
31
|
+
lastSolvedDate: {type: "Integer", description: "The time the ticket was last solved."},
|
32
|
+
lastOpenedDate: {type: "Integer", description: "The last time the ticket was opened"},
|
33
|
+
lastStatusChangeDate: {type: "Integer", description: "The last time the ticket status changed"},
|
34
|
+
handledByUserIds: {type: "Array", description: "List of user/agent IDs that have previously handled the ticket"},
|
35
|
+
handlingUsers: {type: "Array", description: "List of user/agent IDs that are currently handling the ticket"},
|
36
|
+
repliedByUserIds: {type: "Array", description: "List of user/agent IDs that have replied to the ticket"},
|
37
|
+
positiveRatedUserIds: {type: "Array", description: "List of users that rated the ticket positively"},
|
38
|
+
negativeRatedUserIds: {type: "Array", description: "List of users that rated the ticket negatively"},
|
39
|
+
customFields: {type: "Array", description: "List of ticket custom field values"},
|
40
|
+
hasAgentReply: {type: "Boolean", description: "Whether the ticket has a reply from an agent"},
|
41
|
+
spam: {type: "Boolean", description: "Whether the ticket was marked as spam"},
|
42
|
+
unauthenticated: {type: "Boolean", description: "Whether the user is unauthenticated (not registered in Wix Answers)"},
|
43
|
+
createdOnBehalf: {type: "Boolean", description: "Whether an agent created the ticket on behalf of the user"},
|
44
|
+
initialUserEmail: {type: "String", description: "Email address of user who created the ticket"},
|
45
|
+
allCcUsers: {type: "Array", description: "All (current or previous) CC users associated with the ticket"},
|
46
|
+
allCcUserIds: {type: "Array", description: "All (current or previous) CC users associated with the ticket"},
|
47
|
+
ccUserIds: {type: "Array", description: "CC users associated with the most recent reply"},
|
48
|
+
SLA: {type: "Hash", description: "SLA policy associated with the ticket"},
|
49
|
+
previousLocales: {type: "String", description: "List of previous locales"},
|
50
|
+
importId: {type: "String", description: "Import batch process"},
|
51
|
+
}
|
52
|
+
|
53
|
+
def initialize(attrs={})
|
54
|
+
super(attrs)
|
55
|
+
end
|
56
|
+
|
57
|
+
def attachments
|
58
|
+
@_attachments ||= (self.attrs[:attachments] || []).map {|attrs| Attachment.new(attrs)}
|
59
|
+
end
|
60
|
+
|
61
|
+
def user_info
|
62
|
+
@_user_info ||= UserInfo.new(self.attrs[:userInfo] || {})
|
63
|
+
end
|
64
|
+
|
65
|
+
def user
|
66
|
+
@_user ||= User.new(self.attrs[:user] || {})
|
67
|
+
end
|
68
|
+
|
69
|
+
def labels
|
70
|
+
@_labels ||= (self.attrs[:labels] || []).map {|attrs| Label.new(attrs)}
|
71
|
+
end
|
72
|
+
|
73
|
+
def last_reply
|
74
|
+
@_last_reply ||= Reply.new(self.attrs[:lastReply] || {})
|
75
|
+
end
|
76
|
+
|
77
|
+
def assigned_by
|
78
|
+
@_assigned_by ||= User.new(self.attrs[:assignedBy] || {})
|
79
|
+
end
|
80
|
+
|
81
|
+
def created_by_agent
|
82
|
+
@_created_by_agent ||= User.new(self.attrs[:createdByAgent] || {})
|
83
|
+
end
|
84
|
+
|
85
|
+
def assigned_user
|
86
|
+
@_assigned_user ||= Agent.new(self.attrs[:assignedUser] || {})
|
87
|
+
end
|
88
|
+
|
89
|
+
def assigned_group
|
90
|
+
@_assigned_group ||= Group.new(self.attrs[:assignedGroup] || {})
|
91
|
+
end
|
92
|
+
|
93
|
+
def all_cc_users
|
94
|
+
@_all_cc_users ||= (self.attrs[:allCcUsers] || []).map {|attrs| User.new(attrs)}
|
95
|
+
end
|
96
|
+
|
97
|
+
def self.from_payload(payload)
|
98
|
+
Enumerations::Channel.validate!(payload[:channel])
|
99
|
+
|
100
|
+
case payload[:channel]
|
101
|
+
when Enumerations::Channel::WEB
|
102
|
+
Models::Ticket.new(payload)
|
103
|
+
when Enumerations::Channel::BY_AGENT
|
104
|
+
Models::ByAgent.new(payload)
|
105
|
+
when Enumerations::Channel::EMAIL
|
106
|
+
Models::Reply.new(payload)
|
107
|
+
when Enumerations::Channel::PHONE_CALLBACK
|
108
|
+
Models::PhoneCallback.new(payload)
|
109
|
+
when Enumerations::Channel::WIDGET
|
110
|
+
Models::Widget.new(payload)
|
111
|
+
else
|
112
|
+
raise Exceptions::NotImplementedError.new('Channel', payload[:channel])
|
113
|
+
end
|
114
|
+
end
|
115
|
+
end
|
116
|
+
end
|
117
|
+
end
|
@@ -0,0 +1,35 @@
|
|
1
|
+
|
2
|
+
# https://help.wixanswers.com/kb/en/article/api-object-structures#agent-object
|
3
|
+
module WixAnswers
|
4
|
+
module Models
|
5
|
+
class Agent < User
|
6
|
+
SCHEMA ||= User::SCHEMA.merge({
|
7
|
+
roleId: {type: 'String', description: 'User role'},
|
8
|
+
statusStartDate: {type: 'Integer', description: 'Time status last changed'},
|
9
|
+
agentCreationDate: {type: 'Integer', description: 'Time this user was made an agent'},
|
10
|
+
agentLastUpdateDate: {type: 'Integer', description: 'Last time the record of this agent was updated'},
|
11
|
+
manager: {type: 'Hash', description: 'The agent\'s manager'},
|
12
|
+
isManager: {type: 'Boolean', description: 'Whether this agent is a manager of one or more other agents'},
|
13
|
+
locationId: {type: 'String', description: 'The agent\'s location'},
|
14
|
+
teamId: {type: 'String', description: 'The agent\'s team'},
|
15
|
+
jobTitle: {type: 'String', description: 'The agent\'s job title'},
|
16
|
+
locales: {type: 'Array', description: 'The languages with which the agent is familiar'},
|
17
|
+
active: {type: 'Boolean', description: 'Whether the agent is active or not'},
|
18
|
+
supportUtilizationRate: {type: 'Integer', description: 'The agent\'s availability percentage'},
|
19
|
+
groupIds: {type: 'Array', description: 'The groups of which this agent is a member'},
|
20
|
+
qualifiedChannels: {type: 'Array', description: 'List of Agent Channels methods that the agent uses to communicate with users'},
|
21
|
+
channel: {type: 'Integer', description: 'Agent Channel to which the agent is currently assigned'},
|
22
|
+
customStatusId: {type: 'String', description: 'A custom busy status'},
|
23
|
+
agentStatus: {type: 'Integer', description: 'Agent Status'},
|
24
|
+
lastChatAssignedDate: {type: 'Integer', description: 'Time agent last assigned to a chat'},
|
25
|
+
assignedQueues: {type: 'Array', description: 'List of queues to which the agent is assigned'},
|
26
|
+
statistics: {type: 'Hash'},
|
27
|
+
customFields: {type: 'Hash', description: 'List of agent custom field values'},
|
28
|
+
})
|
29
|
+
|
30
|
+
def manager
|
31
|
+
@_manager ||= Agent.new(self.attrs[:manager] || {})
|
32
|
+
end
|
33
|
+
end
|
34
|
+
end
|
35
|
+
end
|
@@ -0,0 +1,21 @@
|
|
1
|
+
|
2
|
+
# https://help.wixanswers.com/kb/en/article/api-object-structures#group-object
|
3
|
+
module WixAnswers
|
4
|
+
module Models
|
5
|
+
class Group < Base
|
6
|
+
SCHEMA ||= {
|
7
|
+
id: {type: 'String', description: 'The group ID', required: true},
|
8
|
+
name: {type: 'String', description: 'The group name, between 1 and 100 characters'},
|
9
|
+
settings: {type: 'Hash'},
|
10
|
+
creationDate: {type: 'Integer', description: 'Time this record was created', required: true},
|
11
|
+
latUpdateDate: {type: 'Integer', description: 'Last time this record was updated'},
|
12
|
+
membersCount: {type: 'Integer', description: 'Number of agents in the group'},
|
13
|
+
members: {type: 'Array', description: 'List of agents in the group'},
|
14
|
+
}
|
15
|
+
|
16
|
+
def members
|
17
|
+
@members ||= (self.attrs[:members] || []).map {|member| Agent.new(member)}
|
18
|
+
end
|
19
|
+
end
|
20
|
+
end
|
21
|
+
end
|
@@ -0,0 +1,14 @@
|
|
1
|
+
|
2
|
+
# https://help.wixanswers.com/kb/en/article/api-object-structures#location-object
|
3
|
+
module WixAnswers
|
4
|
+
module Models
|
5
|
+
class Location < Base
|
6
|
+
SCHEMA ||= {
|
7
|
+
id: {type: 'String', description: 'The location ID', required: true},
|
8
|
+
name: {type: 'String', description: 'The location name'},
|
9
|
+
creationDate: {type: 'Integer', description: 'Time this record was created', required: true},
|
10
|
+
latUpdateDate: {type: 'Integer', description: 'Last time this record was updated'},
|
11
|
+
}
|
12
|
+
end
|
13
|
+
end
|
14
|
+
end
|
@@ -0,0 +1,14 @@
|
|
1
|
+
|
2
|
+
# https://help.wixanswers.com/kb/en/article/api-object-structures#team-object
|
3
|
+
module WixAnswers
|
4
|
+
module Models
|
5
|
+
class Team < Base
|
6
|
+
SCHEMA ||= {
|
7
|
+
id: {type: 'String', description: 'The team ID', required: true},
|
8
|
+
name: {type: 'String', description: 'The team name'},
|
9
|
+
creationDate: {type: 'Integer', description: 'Time this record was created', required: true},
|
10
|
+
latUpdateDate: {type: 'Integer', description: 'Last time this record was updated'},
|
11
|
+
}
|
12
|
+
end
|
13
|
+
end
|
14
|
+
end
|
@@ -0,0 +1,34 @@
|
|
1
|
+
|
2
|
+
# https://help.wixanswers.com/kb/en/article/api-object-structures#user-object
|
3
|
+
module WixAnswers
|
4
|
+
module Models
|
5
|
+
class User < Base
|
6
|
+
SCHEMA ||= {
|
7
|
+
id: {type: "String", description: "User ID", required: true},
|
8
|
+
firstName: {type: "String", description: "User first name"},
|
9
|
+
lastName: {type: "String", description: "User last name"},
|
10
|
+
userType: {type: 'Integer', description: "User Type", required: true},
|
11
|
+
email: {type: "String", description: "User email address, up to 200 characters. Must be unique to this user object."},
|
12
|
+
emailStatus: {type: "String", description: "Email Status"},
|
13
|
+
lastUpdateDate: {type: "Integer", description: "Time this record was last updated"},
|
14
|
+
profileImage: {type: "String", description: "URL of user’s profile image"},
|
15
|
+
signature: {type: "String", description: "URL of signature"},
|
16
|
+
phoneNumbers: {type: "Array", description: "List of phone numbers"},
|
17
|
+
company: {type: "Hash", description: "Associated company"},
|
18
|
+
isPartner: {type: "Boolean", description: "Whether the user is a partner"},
|
19
|
+
companyIds: {type: "Array", description: "List of associated companies"},
|
20
|
+
externalId: {type: "String", description: "Relevant only for tenants supporting SSO - the external ID in the tenant’s SSO auth system"},
|
21
|
+
creationDate: {type: "Integer", description: "Time this record was created"},
|
22
|
+
customFields: {type: "Hash", description: "List of user custom field values"},
|
23
|
+
banned: {type: "Boolean", description: "Whether the user is banned"},
|
24
|
+
importId: {type: "Boolean", description: "Import batch process"},
|
25
|
+
}
|
26
|
+
|
27
|
+
def validate!
|
28
|
+
super
|
29
|
+
|
30
|
+
Enumerations::UserType.validate!(self.userType)
|
31
|
+
end
|
32
|
+
end
|
33
|
+
end
|
34
|
+
end
|
@@ -0,0 +1,44 @@
|
|
1
|
+
|
2
|
+
module WixAnswers
|
3
|
+
module Models
|
4
|
+
class UserInfo < Base
|
5
|
+
SCHEMA ||= {
|
6
|
+
ip: {type: "String"},
|
7
|
+
userAgent: {type: "String"},
|
8
|
+
operatingSystemFamily: {type: "String"},
|
9
|
+
operatingSystemName: {type: "String"},
|
10
|
+
operatingSystemVersion: {type: "String"},
|
11
|
+
browserFamily: {type: "String"},
|
12
|
+
browserName: {type: "String"},
|
13
|
+
browserVersion: {type: "String"},
|
14
|
+
netSpeed: {type: "String"},
|
15
|
+
domain: {type: "String"},
|
16
|
+
ispName: {type: "String"},
|
17
|
+
organization: {type: "String"},
|
18
|
+
city: {type: "String"},
|
19
|
+
regionName: {type: "String"},
|
20
|
+
postalCode: {type: "String"},
|
21
|
+
metroCode: {type: "String"},
|
22
|
+
areaCode: {type: "String"},
|
23
|
+
countryCode: {type: "String"},
|
24
|
+
countryName: {type: "String"},
|
25
|
+
continentCode: {type: "String"},
|
26
|
+
latitude: {type: "Integer"},
|
27
|
+
longitude: {type: "Integer"},
|
28
|
+
timezone: {type: "String"},
|
29
|
+
asNumber: {type: "String"},
|
30
|
+
ipUserType: {type: "String"},
|
31
|
+
processed: {type: "Boolean"},
|
32
|
+
}
|
33
|
+
|
34
|
+
def initialize(attrs={})
|
35
|
+
super(attrs)
|
36
|
+
end
|
37
|
+
|
38
|
+
def validate!
|
39
|
+
# does not require validation
|
40
|
+
self
|
41
|
+
end
|
42
|
+
end
|
43
|
+
end
|
44
|
+
end
|
@@ -0,0 +1,95 @@
|
|
1
|
+
|
2
|
+
|
3
|
+
module WixAnswers
|
4
|
+
module Enumerations
|
5
|
+
class Enumeration
|
6
|
+
def self.values
|
7
|
+
Set.new(constants.map {|const| const_get(const) })
|
8
|
+
end
|
9
|
+
|
10
|
+
def self.valid?(value)
|
11
|
+
values.include?(value)
|
12
|
+
end
|
13
|
+
|
14
|
+
def self.validate!(value)
|
15
|
+
raise Exceptions::UnsupportedType.new(self.name, value) unless self.valid?(value)
|
16
|
+
end
|
17
|
+
end
|
18
|
+
|
19
|
+
class WebhookType < Enumeration
|
20
|
+
TICKET_CREATED ||= 2
|
21
|
+
TICKET_STATUS_CHANGED ||= 8
|
22
|
+
end
|
23
|
+
|
24
|
+
class AttachmentStatus < Enumeration
|
25
|
+
FAILED ||= 1
|
26
|
+
INVALID_EXTENSION ||= 2
|
27
|
+
MAX_FILE_SIZE_EXCEEDED ||= 3
|
28
|
+
OK ||= 200
|
29
|
+
end
|
30
|
+
|
31
|
+
# https://help.wixanswers.com/kb/en/article/api-enumerations#user-type
|
32
|
+
class UserType < Enumeration
|
33
|
+
AUTHENTICATED ||= 1
|
34
|
+
UNAUTHENTICATED ||= 2
|
35
|
+
PENDING_AUTHENTICATION ||= 4
|
36
|
+
PENDING_DELETION ||= 5
|
37
|
+
DELETED ||= 99
|
38
|
+
end
|
39
|
+
|
40
|
+
# https://help.wixanswers.com/kb/en/article/api-enumerations#call-type
|
41
|
+
class CallType < Enumeration
|
42
|
+
INBOUND ||= 10
|
43
|
+
OUTBOUND ||= 20
|
44
|
+
CALLBACK ||= 30
|
45
|
+
end
|
46
|
+
|
47
|
+
# https://help.wixanswers.com/kb/en/article/api-enumerations#reply-type
|
48
|
+
class ReplyType < Enumeration
|
49
|
+
USER ||= 100
|
50
|
+
CC_USER ||= 101
|
51
|
+
AGENT ||= 110
|
52
|
+
INTERNAL ||= 120
|
53
|
+
end
|
54
|
+
|
55
|
+
# https://help.wixanswers.com/kb/en/article/api-enumerations#article-type
|
56
|
+
class ArticleType < Enumeration
|
57
|
+
ARTICLE ||= 100
|
58
|
+
FEATURE_REQUEST ||= 110
|
59
|
+
KNOWN_ISSUE ||= 120
|
60
|
+
VIDEO ||= 130
|
61
|
+
end
|
62
|
+
|
63
|
+
# https://help.wixanswers.com/kb/en/article/api-enumerations#ticket-priority
|
64
|
+
class TicketPriority < Enumeration
|
65
|
+
LOW ||= 10
|
66
|
+
NORMAL ||= 20
|
67
|
+
HIGH ||= 30
|
68
|
+
end
|
69
|
+
|
70
|
+
# https://help.wixanswers.com/kb/en/article/api-enumerations#channel
|
71
|
+
class Channel < Enumeration
|
72
|
+
WEB ||= 100
|
73
|
+
EMAIL ||= 110
|
74
|
+
PHONE_CALLBACK ||= 120
|
75
|
+
PHONE_OUTBOUND ||= 121
|
76
|
+
PHONE_INBOUND ||= 122
|
77
|
+
BY_AGENT ||= 130
|
78
|
+
FACEBOOK ||= 140
|
79
|
+
WHATSAPP ||= 150
|
80
|
+
CHAT ||= 160
|
81
|
+
WIDGET ||= 170
|
82
|
+
API ||= 180
|
83
|
+
SMS ||= 190
|
84
|
+
end
|
85
|
+
|
86
|
+
# https://help.wixanswers.com/kb/en/article/api-enumerations#satisfaction
|
87
|
+
class Satisfaction < Enumeration
|
88
|
+
NOT_AT_ALL ||= 10
|
89
|
+
NOT_VERY ||= 10
|
90
|
+
SOMEWHAT ||= 20
|
91
|
+
VERY ||= 30
|
92
|
+
EXTREMELY ||= 40
|
93
|
+
end
|
94
|
+
end
|
95
|
+
end
|
@@ -0,0 +1,28 @@
|
|
1
|
+
|
2
|
+
module WixAnswers
|
3
|
+
module Exceptions
|
4
|
+
class UnsupportedType < StandardError
|
5
|
+
def initialize(payload_type, value)
|
6
|
+
super("Unsupported Payload #{payload_type.split('::')[-1]}: #{value}")
|
7
|
+
end
|
8
|
+
end
|
9
|
+
|
10
|
+
class MissingAttribute < StandardError
|
11
|
+
def initialize(value)
|
12
|
+
super("Missing Attribute: #{value}")
|
13
|
+
end
|
14
|
+
end
|
15
|
+
|
16
|
+
class SchemaTypeError < TypeError
|
17
|
+
def initialize(expected, actual)
|
18
|
+
super("no implicit conversation of #{expected} to #{actual}")
|
19
|
+
end
|
20
|
+
end
|
21
|
+
|
22
|
+
class NotImplementedError < StandardError
|
23
|
+
def initialize(object_type, value)
|
24
|
+
super("Unimplemented #{object_type} Entity: #{value}")
|
25
|
+
end
|
26
|
+
end
|
27
|
+
end
|
28
|
+
end
|
@@ -0,0 +1,38 @@
|
|
1
|
+
module WixAnswers
|
2
|
+
module Version
|
3
|
+
module_function
|
4
|
+
|
5
|
+
def major
|
6
|
+
0
|
7
|
+
end
|
8
|
+
|
9
|
+
def minor
|
10
|
+
0
|
11
|
+
end
|
12
|
+
|
13
|
+
def patch
|
14
|
+
3
|
15
|
+
end
|
16
|
+
|
17
|
+
def pre
|
18
|
+
nil
|
19
|
+
end
|
20
|
+
|
21
|
+
def to_h
|
22
|
+
{
|
23
|
+
major: major,
|
24
|
+
minor: minor,
|
25
|
+
patch: patch,
|
26
|
+
pre: pre,
|
27
|
+
}
|
28
|
+
end
|
29
|
+
|
30
|
+
def to_a
|
31
|
+
[major, minor, patch, pre].compact
|
32
|
+
end
|
33
|
+
|
34
|
+
def to_s
|
35
|
+
to_a.join('.')
|
36
|
+
end
|
37
|
+
end
|
38
|
+
end
|
data/wixanswers.gemspec
ADDED
@@ -0,0 +1,19 @@
|
|
1
|
+
lib = File.expand_path('lib', __dir__)
|
2
|
+
$LOAD_PATH.unshift(lib) unless $LOAD_PATH.include?(lib)
|
3
|
+
|
4
|
+
require 'wixanswers/version'
|
5
|
+
|
6
|
+
Gem::Specification.new do |spec|
|
7
|
+
spec.add_development_dependency 'bundler', '~> 1.0'
|
8
|
+
spec.authors = ['Roee Sheelo']
|
9
|
+
spec.description = 'A Ruby interface to the WixAnswers API'
|
10
|
+
spec.email = %w[roee.sheelo@gmail.com]
|
11
|
+
spec.files = %w[CHANGELOG.md LICENSE.md README.md wixanswers.gemspec] + Dir['lib/**/*.rb']
|
12
|
+
spec.homepage = 'https://github.com/communit-team/wixanswers'
|
13
|
+
spec.licenses = %w[MIT]
|
14
|
+
spec.name = 'wixanswers'
|
15
|
+
spec.require_paths = %w[lib]
|
16
|
+
spec.required_ruby_version = '>= 2.3.1'
|
17
|
+
spec.summary = spec.description
|
18
|
+
spec.version = WixAnswers::Version
|
19
|
+
end
|
metadata
ADDED
@@ -0,0 +1,82 @@
|
|
1
|
+
--- !ruby/object:Gem::Specification
|
2
|
+
name: wixanswers
|
3
|
+
version: !ruby/object:Gem::Version
|
4
|
+
version: 0.0.3
|
5
|
+
platform: ruby
|
6
|
+
authors:
|
7
|
+
- Roee Sheelo
|
8
|
+
autorequire:
|
9
|
+
bindir: bin
|
10
|
+
cert_chain: []
|
11
|
+
date: 2020-11-17 00:00:00.000000000 Z
|
12
|
+
dependencies:
|
13
|
+
- !ruby/object:Gem::Dependency
|
14
|
+
name: bundler
|
15
|
+
requirement: !ruby/object:Gem::Requirement
|
16
|
+
requirements:
|
17
|
+
- - "~>"
|
18
|
+
- !ruby/object:Gem::Version
|
19
|
+
version: '1.0'
|
20
|
+
type: :development
|
21
|
+
prerelease: false
|
22
|
+
version_requirements: !ruby/object:Gem::Requirement
|
23
|
+
requirements:
|
24
|
+
- - "~>"
|
25
|
+
- !ruby/object:Gem::Version
|
26
|
+
version: '1.0'
|
27
|
+
description: A Ruby interface to the WixAnswers API
|
28
|
+
email:
|
29
|
+
- roee.sheelo@gmail.com
|
30
|
+
executables: []
|
31
|
+
extensions: []
|
32
|
+
extra_rdoc_files: []
|
33
|
+
files:
|
34
|
+
- CHANGELOG.md
|
35
|
+
- LICENSE.md
|
36
|
+
- README.md
|
37
|
+
- lib/wixanswers.rb
|
38
|
+
- lib/wixanswers/models/attachment.rb
|
39
|
+
- lib/wixanswers/models/base.rb
|
40
|
+
- lib/wixanswers/models/label.rb
|
41
|
+
- lib/wixanswers/models/ticket/by_agent.rb
|
42
|
+
- lib/wixanswers/models/ticket/chat.rb
|
43
|
+
- lib/wixanswers/models/ticket/phone_callback.rb
|
44
|
+
- lib/wixanswers/models/ticket/reply.rb
|
45
|
+
- lib/wixanswers/models/ticket/ticket.rb
|
46
|
+
- lib/wixanswers/models/ticket/widget.rb
|
47
|
+
- lib/wixanswers/models/user/agent.rb
|
48
|
+
- lib/wixanswers/models/user/company.rb
|
49
|
+
- lib/wixanswers/models/user/group.rb
|
50
|
+
- lib/wixanswers/models/user/location.rb
|
51
|
+
- lib/wixanswers/models/user/team.rb
|
52
|
+
- lib/wixanswers/models/user/user.rb
|
53
|
+
- lib/wixanswers/models/user_info.rb
|
54
|
+
- lib/wixanswers/rest/api.rb
|
55
|
+
- lib/wixanswers/rest/enumerations.rb
|
56
|
+
- lib/wixanswers/rest/exceptions.rb
|
57
|
+
- lib/wixanswers/version.rb
|
58
|
+
- wixanswers.gemspec
|
59
|
+
homepage: https://github.com/communit-team/wixanswers
|
60
|
+
licenses:
|
61
|
+
- MIT
|
62
|
+
metadata: {}
|
63
|
+
post_install_message:
|
64
|
+
rdoc_options: []
|
65
|
+
require_paths:
|
66
|
+
- lib
|
67
|
+
required_ruby_version: !ruby/object:Gem::Requirement
|
68
|
+
requirements:
|
69
|
+
- - ">="
|
70
|
+
- !ruby/object:Gem::Version
|
71
|
+
version: 2.3.1
|
72
|
+
required_rubygems_version: !ruby/object:Gem::Requirement
|
73
|
+
requirements:
|
74
|
+
- - ">="
|
75
|
+
- !ruby/object:Gem::Version
|
76
|
+
version: '0'
|
77
|
+
requirements: []
|
78
|
+
rubygems_version: 3.0.8
|
79
|
+
signing_key:
|
80
|
+
specification_version: 4
|
81
|
+
summary: A Ruby interface to the WixAnswers API
|
82
|
+
test_files: []
|