sift 1.1.7.3 → 2.0.0.0
Sign up to get free protection for your applications and to get access to all the features.
- checksums.yaml +5 -13
- data/.travis.yml +5 -0
- data/HISTORY +6 -2
- data/README.rdoc +36 -11
- data/lib/sift.rb +33 -8
- data/lib/sift/client.rb +347 -107
- data/lib/sift/version.rb +2 -2
- data/sift.gemspec +2 -2
- data/spec/unit/client_203_spec.rb +192 -0
- data/spec/unit/client_label_spec.rb +55 -11
- data/spec/unit/client_spec.rb +141 -49
- metadata +26 -17
checksums.yaml
CHANGED
@@ -1,15 +1,7 @@
|
|
1
1
|
---
|
2
|
-
|
3
|
-
metadata.gz:
|
4
|
-
|
5
|
-
data.tar.gz: !binary |-
|
6
|
-
NjJmY2FmYWQxMWEyNjFlY2MwMDdmOGZlN2ZiMWE0ODFiMGI1N2MyYg==
|
2
|
+
SHA1:
|
3
|
+
metadata.gz: 5116181929ffbab6a17941eb341a852a7c4c75c6
|
4
|
+
data.tar.gz: 4699c62cdadc3fd2f9123b929925abcf45cfb19b
|
7
5
|
SHA512:
|
8
|
-
metadata.gz:
|
9
|
-
|
10
|
-
ZjhkNmZlMzA5MGRiNGU1OWM3NGI4MzFjMDZkODE5NzQ3NDkyZGQwYmVhNzIy
|
11
|
-
NzI3ZmIzZjkzMzMyMWEwMTBmMzMxYTIwMjA0YTExN2UxZThhNDE=
|
12
|
-
data.tar.gz: !binary |-
|
13
|
-
ZGQ0Zjk1YTRmM2YyYzBhMjkzYzcxNzZkOWIxNTIxNTY2MzcyZmUyY2U3ZDRi
|
14
|
-
YTk1OGExNzBlZDFjNjhlZjhlOTE4NDUzOWJjNjI0Y2MwOTFmYmEwMmY1MDI0
|
15
|
-
OWU1MDQ0YzBmN2EzMmE1ZmQyMDRmNTJkNTI5Y2IzNzAwNTlmN2M=
|
6
|
+
metadata.gz: 5d228bd45520217fe3e06a0e2673e4a176b497ff83fc5f73940a6e656006b7725521597fb263d64cc133020162400562380b30aee1f29c9a3bde91ce080e03a3
|
7
|
+
data.tar.gz: bce89304cbf0eb1c963e05c9ec76248ba5e06d9c0829df983735dfaf5828288faf8e73fd3c81a53876ee39081cf3695364a929775ffdb5665caa99fc4dc6f957
|
data/.travis.yml
CHANGED
data/HISTORY
CHANGED
@@ -1,5 +1,9 @@
|
|
1
|
-
===
|
2
|
-
*
|
1
|
+
=== 2.0.0.0 2016-07-19
|
2
|
+
* adds support for v204 of Sift Science's APIs
|
3
|
+
* adds Workflow Status API, User Decisions API, Order Decisions API
|
4
|
+
* v204 APIs are now called by default -- this is an incompatible change
|
5
|
+
(use :version => 203 to call the previous API version)
|
6
|
+
* uses Hash arg for optional params in Client methods -- incompatible change
|
3
7
|
|
4
8
|
=== 1.1.7.2 2015-04-13
|
5
9
|
* Fixed backwards compatibility issue
|
data/README.rdoc
CHANGED
@@ -1,5 +1,6 @@
|
|
1
1
|
= Sift Science Ruby bindings {<img src="https://travis-ci.org/SiftScience/sift-ruby.png?branch=master" alt="Build Status" />}[https://travis-ci.org/SiftScience/sift-ruby]
|
2
2
|
|
3
|
+
|
3
4
|
== Requirements
|
4
5
|
|
5
6
|
* Ruby 1.8.7 or above. (Ruby 1.8.6 might work if you load ActiveSupport.)
|
@@ -12,6 +13,7 @@ For development only:
|
|
12
13
|
* webmock, 1.16 or greater
|
13
14
|
* rake, any version
|
14
15
|
|
16
|
+
|
15
17
|
== Installation
|
16
18
|
|
17
19
|
If you want to build the gem from source:
|
@@ -22,16 +24,19 @@ Alternatively, you can install the gem from Rubyforge:
|
|
22
24
|
|
23
25
|
$ gem install sift
|
24
26
|
|
27
|
+
|
25
28
|
== Usage
|
29
|
+
|
26
30
|
require "sift"
|
27
31
|
|
28
32
|
Sift.api_key = '<your_api_key_here>'
|
33
|
+
Sift.account_id = '<your_account_id_here>'
|
29
34
|
client = Sift::Client.new()
|
30
35
|
|
31
36
|
# send a transaction event -- note this is blocking
|
32
37
|
event = "$transaction"
|
33
38
|
|
34
|
-
user_id = "23056"
|
39
|
+
user_id = "23056" # User ID's may only contain a-z, A-Z, 0-9, =, ., -, _, +, @, :, &, ^, %, !, $
|
35
40
|
|
36
41
|
properties = {
|
37
42
|
"$user_id" => user_id,
|
@@ -50,20 +55,39 @@ Alternatively, you can install the gem from Rubyforge:
|
|
50
55
|
}
|
51
56
|
|
52
57
|
response = client.track(event, properties)
|
53
|
-
|
54
|
-
response.ok? # returns true or false
|
55
|
-
|
56
|
-
response.http_status_code # HTTP response code, 200 is ok.
|
57
|
-
|
58
|
-
response.api_status # status field in the return body, Link to Error Codes
|
59
58
|
|
60
|
-
response.
|
59
|
+
response.ok? # returns true or false
|
60
|
+
response.body # API response body
|
61
|
+
response.http_status_code # HTTP response code, 200 is ok.
|
62
|
+
response.api_status # status field in the return body, Link to Error Codes
|
63
|
+
response.api_error_message # Error message associated with status Error Code
|
61
64
|
|
62
|
-
|
65
|
+
|
66
|
+
# Request a score for the user with user_id 23056
|
63
67
|
response = client.score(user_id)
|
64
|
-
|
68
|
+
|
69
|
+
|
65
70
|
# Label the user with user_id 23056 as Bad with all optional fields
|
66
|
-
response = client.label(user_id,{
|
71
|
+
response = client.label(user_id, {
|
72
|
+
"$is_bad" => true,
|
73
|
+
"$abuse_type" => "payment_abuse",
|
74
|
+
"$description" => "Chargeback issued",
|
75
|
+
"$source" => "Manual Review",
|
76
|
+
"$analyst" => "analyst.name@your_domain.com"
|
77
|
+
})
|
78
|
+
|
79
|
+
|
80
|
+
# Get the status of a workflow run
|
81
|
+
response = client.get_workflow_status('my_run_id')
|
82
|
+
|
83
|
+
|
84
|
+
# Get the latest decisions for a user
|
85
|
+
response = client.get_user_decisions('example_user_id')
|
86
|
+
|
87
|
+
|
88
|
+
# Get the latest decisions for an order
|
89
|
+
response = client.get_order_decisions('example_order_id')
|
90
|
+
|
67
91
|
|
68
92
|
== Building
|
69
93
|
|
@@ -78,6 +102,7 @@ Building and publishing the gem is captured by the following steps:
|
|
78
102
|
$ rake install
|
79
103
|
$ rake release
|
80
104
|
|
105
|
+
|
81
106
|
== Testing
|
82
107
|
|
83
108
|
To run the various tests use the rake command as follows:
|
data/lib/sift.rb
CHANGED
@@ -3,21 +3,46 @@ require "sift/client"
|
|
3
3
|
|
4
4
|
module Sift
|
5
5
|
|
6
|
-
# Returns the path for the
|
7
|
-
def self.
|
8
|
-
"/v#{
|
6
|
+
# Returns the path for the specified API version
|
7
|
+
def self.rest_api_path(version=API_VERSION)
|
8
|
+
"/v#{version}/events"
|
9
9
|
end
|
10
10
|
|
11
|
-
|
12
|
-
|
13
|
-
"/v#{
|
11
|
+
# Returns the Score API path for the specified user ID and API version
|
12
|
+
def self.score_api_path(user_id, version=API_VERSION)
|
13
|
+
"/v#{version}/score/#{URI.encode(user_id)}/"
|
14
14
|
end
|
15
|
-
|
16
|
-
#
|
15
|
+
|
16
|
+
# Returns the users API path for the specified user ID and API version
|
17
|
+
def self.users_label_api_path(user_id, version=API_VERSION)
|
18
|
+
"/v#{version}/users/#{URI.encode(user_id)}/labels"
|
19
|
+
end
|
20
|
+
|
21
|
+
# Returns the path for the Workflow Status API
|
22
|
+
def self.workflow_status_path(account_id, run_id)
|
23
|
+
"/v3/accounts/#{account_id}/workflows/runs/#{run_id}"
|
24
|
+
end
|
25
|
+
|
26
|
+
# Returns the path for User Decisions API
|
27
|
+
def self.user_decisions_api_path(account_id, user_id)
|
28
|
+
"/v3/accounts/#{account_id}/users/#{user_id}/decisions"
|
29
|
+
end
|
30
|
+
|
31
|
+
# Returns the path for Orders Decisions API
|
32
|
+
def self.order_decisions_api_path(account_id, order_id)
|
33
|
+
"/v3/accounts/#{account_id}/orders/#{order_id}/decisions"
|
34
|
+
end
|
35
|
+
|
36
|
+
# Module-scoped public API key
|
17
37
|
class << self
|
18
38
|
attr_accessor :api_key
|
19
39
|
end
|
20
40
|
|
41
|
+
# Module-scoped account ID
|
42
|
+
class << self
|
43
|
+
attr_accessor :account_id
|
44
|
+
end
|
45
|
+
|
21
46
|
# Sets the Output logger to use within the client. This can be left uninitializaed
|
22
47
|
# but is useful for debugging.
|
23
48
|
def self.logger=(logger)
|
data/lib/sift/client.rb
CHANGED
@@ -15,8 +15,9 @@ module Sift
|
|
15
15
|
|
16
16
|
# Constructor
|
17
17
|
#
|
18
|
-
#
|
19
|
-
#
|
18
|
+
# ==== Parameters:
|
19
|
+
#
|
20
|
+
# http_response::
|
20
21
|
# The HTTP body text returned from the API call. The body is expected to be
|
21
22
|
# a JSON object that can be decoded into status, message and request
|
22
23
|
# sections.
|
@@ -37,10 +38,11 @@ module Sift
|
|
37
38
|
# Helper method returns true if and only if the response from the API call was
|
38
39
|
# successful
|
39
40
|
#
|
40
|
-
#
|
41
|
-
#
|
41
|
+
# ==== Returns:
|
42
|
+
#
|
43
|
+
# true on success; false otherwise
|
44
|
+
#
|
42
45
|
def ok?
|
43
|
-
|
44
46
|
if @http_raw_response.kind_of? Net::HTTPNoContent
|
45
47
|
#if there is no content expected, use HTTP code
|
46
48
|
204 == @http_status_code
|
@@ -51,14 +53,14 @@ module Sift
|
|
51
53
|
end
|
52
54
|
|
53
55
|
|
54
|
-
#
|
55
|
-
# Getter method for
|
56
|
+
# DEPRECATED
|
57
|
+
# Getter method for deprecated 'json' member variable.
|
56
58
|
def json
|
57
59
|
@body
|
58
60
|
end
|
59
61
|
|
60
|
-
#
|
61
|
-
# Getter method for
|
62
|
+
# DEPRECATED
|
63
|
+
# Getter method for deprecated 'original_request' member variable.
|
62
64
|
def original_request
|
63
65
|
@request
|
64
66
|
end
|
@@ -67,29 +69,50 @@ module Sift
|
|
67
69
|
# This class wraps accesses through the API
|
68
70
|
#
|
69
71
|
class Client
|
70
|
-
API_ENDPOINT =
|
71
|
-
|
72
|
+
API_ENDPOINT = 'https://api.siftscience.com'
|
73
|
+
API3_ENDPOINT = 'https://api3.siftscience.com'
|
72
74
|
|
73
75
|
include HTTParty
|
74
76
|
base_uri API_ENDPOINT
|
75
77
|
|
78
|
+
|
76
79
|
# Constructor
|
77
80
|
#
|
78
|
-
#
|
79
|
-
# api_key
|
80
|
-
# The Sift Science API key associated with your customer account. This parameter
|
81
|
-
# cannot be nil or blank.
|
82
|
-
# path
|
83
|
-
# The path to the event API, e.g., "/v201/events"
|
81
|
+
# ==== Parameters:
|
84
82
|
#
|
85
|
-
|
86
|
-
|
87
|
-
|
88
|
-
|
89
|
-
|
90
|
-
|
91
|
-
|
92
|
-
|
83
|
+
# opts (optional)::
|
84
|
+
# A Hash of optional parameters for this Client --
|
85
|
+
#
|
86
|
+
# :api_key::
|
87
|
+
# The Sift Science API key associated with your account.
|
88
|
+
# Sift.api_key is used if this parameter is not set.
|
89
|
+
#
|
90
|
+
# :account_id::
|
91
|
+
# The ID of your Sift Science account. Sift.account_id is
|
92
|
+
# used if this parameter is not set.
|
93
|
+
#
|
94
|
+
# :timeout::
|
95
|
+
# The number of seconds to wait before failing a request. By
|
96
|
+
# default this is configured to 2 seconds.
|
97
|
+
#
|
98
|
+
# :version::
|
99
|
+
# The version of the Events API, Score API, and Labels API to call.
|
100
|
+
# By default, version 204.
|
101
|
+
#
|
102
|
+
# :path::
|
103
|
+
# The URL path to use for Events API path. By default, the
|
104
|
+
# official path of the specified-version of the Events API.
|
105
|
+
#
|
106
|
+
#
|
107
|
+
def initialize(opts = {})
|
108
|
+
@api_key = opts[:api_key] || Sift.api_key
|
109
|
+
@account_id = opts[:account_id] || Sift.account_id
|
110
|
+
@version = opts[:version] || API_VERSION
|
111
|
+
@timeout = opts[:timeout] || 2 # 2-second timeout by default
|
112
|
+
@path = opts[:path] || Sift.rest_api_path(@version)
|
113
|
+
|
114
|
+
raise("api_key must be a non-empty string") if !@api_key.is_a?(String) || @api_key.empty?
|
115
|
+
raise("path must be a non-empty string") if !@path.is_a?(String) || @path.empty?
|
93
116
|
end
|
94
117
|
|
95
118
|
def api_key
|
@@ -97,64 +120,95 @@ module Sift
|
|
97
120
|
end
|
98
121
|
|
99
122
|
def user_agent
|
100
|
-
"SiftScience/v#{
|
123
|
+
"SiftScience/v#{@version} sift-ruby/#{VERSION}"
|
101
124
|
end
|
102
125
|
|
103
|
-
|
104
|
-
#
|
126
|
+
|
127
|
+
# Sends an event to the Sift Science Events API.
|
105
128
|
#
|
106
|
-
#
|
107
|
-
# event
|
108
|
-
# The name of the event to send. This can be either a reserved event name, like
|
109
|
-
# $transaction or $label or a custom event name (that does not start with a $).
|
110
|
-
# This parameter must be specified.
|
129
|
+
# See https://siftscience.com/developers/docs/ruby/events-api .
|
111
130
|
#
|
112
|
-
#
|
113
|
-
#
|
114
|
-
#
|
131
|
+
# ==== Parameters:
|
132
|
+
#
|
133
|
+
# event::
|
134
|
+
# The name of the event to send. This can be either a reserved
|
135
|
+
# event name, like $transaction or $label or a custom event name
|
136
|
+
# (that does not start with a $). This parameter must be
|
137
|
+
# specified.
|
138
|
+
#
|
139
|
+
# properties::
|
140
|
+
# A hash of name-value pairs that specify the event-specific
|
141
|
+
# attributes to track. This parameter must be specified.
|
142
|
+
#
|
143
|
+
# opts (optional)::
|
144
|
+
# A Hash of optional parameters for the request --
|
145
|
+
#
|
146
|
+
# :return_score::
|
147
|
+
# If true, requests that the response include a score for this
|
148
|
+
# user, computed using the submitted event. See
|
149
|
+
# https://siftscience.com/developers/docs/ruby/score-api/synchronous-scores
|
150
|
+
#
|
151
|
+
# :abuse_types::
|
152
|
+
# List of abuse types, specifying for which abuse types a
|
153
|
+
# score should be returned (if scoring was requested). By
|
154
|
+
# default, a score is returned for every abuse type to which
|
155
|
+
# you are subscribed.
|
115
156
|
#
|
116
|
-
#
|
117
|
-
#
|
118
|
-
#
|
157
|
+
# :return_action::
|
158
|
+
# If true, requests that the response include any actions
|
159
|
+
# triggered as a result of the tracked event.
|
119
160
|
#
|
120
|
-
#
|
121
|
-
#
|
161
|
+
# :return_workflow_status::
|
162
|
+
# If true, requests that the response include the status of
|
163
|
+
# any workflow run as a result of the tracked event. See
|
164
|
+
# https://siftscience.com/developers/docs/ruby/workflows-api/workflow-decisions
|
122
165
|
#
|
123
|
-
#
|
124
|
-
#
|
125
|
-
# be calculated using the submitted event. This feature must be
|
126
|
-
# enabled for your account in order to use it. Please contact
|
127
|
-
# support@siftscience.com if you are interested in using this feature.
|
166
|
+
# :timeout::
|
167
|
+
# Overrides the timeout (in seconds) for this call.
|
128
168
|
#
|
129
|
-
#
|
130
|
-
#
|
169
|
+
# :api_key::
|
170
|
+
# Overrides the API key for this call.
|
131
171
|
#
|
132
|
-
#
|
133
|
-
#
|
134
|
-
# method returns nil; otherwise, a Response object is returned and captures
|
135
|
-
# the status message and status code. In general, you can ignore the returned
|
136
|
-
# result, though.
|
172
|
+
# :version::
|
173
|
+
# Overrides the version of the Events API to call.
|
137
174
|
#
|
138
|
-
|
139
|
-
|
140
|
-
|
175
|
+
# :path::
|
176
|
+
# Overrides the URI path for this API call.
|
177
|
+
#
|
178
|
+
# ==== Returns:
|
179
|
+
#
|
180
|
+
# In the case of a connection error (timeout, broken connection,
|
181
|
+
# etc.), this method returns nil; otherwise, a Response object is
|
182
|
+
# returned that captures the status message and status code.
|
183
|
+
#
|
184
|
+
def track(event, properties = {}, opts = {})
|
185
|
+
api_key = opts[:api_key] || @api_key
|
186
|
+
version = opts[:version] || @version
|
187
|
+
path = opts[:path] || (version && Sift.rest_api_path(version)) || @path
|
188
|
+
timeout = opts[:timeout] || @timeout
|
189
|
+
return_score = opts[:return_score]
|
190
|
+
return_action = opts[:return_action]
|
191
|
+
return_workflow_status = opts[:return_workflow_status]
|
192
|
+
abuse_types = opts[:abuse_types]
|
193
|
+
|
141
194
|
raise("event must be a non-empty string") if (!event.is_a? String) || event.empty?
|
142
195
|
raise("properties cannot be empty") if properties.empty?
|
143
|
-
raise("
|
144
|
-
path ||= @path
|
145
|
-
timeout ||= @timeout
|
196
|
+
raise("api_key cannot be empty") if api_key.empty?
|
146
197
|
|
147
|
-
|
148
|
-
|
149
|
-
|
150
|
-
|
198
|
+
query = {}
|
199
|
+
query["return_score"] = "true" if return_score
|
200
|
+
query["return_action"] = "true" if return_action
|
201
|
+
query["return_workflow_status"] = "true" if return_workflow_status
|
202
|
+
query["abuse_types"] = abuse_types.join(",") if abuse_types
|
151
203
|
|
152
204
|
options = {
|
153
205
|
:body => MultiJson.dump(delete_nils(properties).merge({"$type" => event,
|
154
206
|
"$api_key" => api_key})),
|
155
|
-
:headers => {"User-Agent" => user_agent}
|
207
|
+
:headers => {"User-Agent" => user_agent},
|
208
|
+
:query => query
|
156
209
|
}
|
157
210
|
options.merge!(:timeout => timeout) unless timeout.nil?
|
211
|
+
|
158
212
|
begin
|
159
213
|
response = self.class.post(path, options)
|
160
214
|
Response.new(response.body, response.code, response.response)
|
@@ -165,91 +219,277 @@ module Sift
|
|
165
219
|
end
|
166
220
|
end
|
167
221
|
|
168
|
-
|
169
|
-
#
|
222
|
+
|
223
|
+
# Retrieves a user's fraud score from the Sift Science API.
|
170
224
|
#
|
171
|
-
#
|
172
|
-
#
|
225
|
+
# See https://siftscience.com/developers/docs/ruby/score-api/score-api .
|
226
|
+
#
|
227
|
+
# ==== Parameters:
|
228
|
+
#
|
229
|
+
# user_id::
|
173
230
|
# A user's id. This id should be the same as the user_id used in
|
174
231
|
# event calls.
|
175
232
|
#
|
176
|
-
#
|
177
|
-
# A
|
178
|
-
#
|
233
|
+
# opts (optional)::
|
234
|
+
# A Hash of optional parameters for the request --
|
235
|
+
#
|
236
|
+
# :abuse_types::
|
237
|
+
# List of abuse types, specifying for which abuse types a
|
238
|
+
# score should be returned. By default, a score is returned
|
239
|
+
# for every abuse type to which you are subscribed.
|
240
|
+
#
|
241
|
+
# :api_key::
|
242
|
+
# Overrides the API key for this call.
|
243
|
+
#
|
244
|
+
# :timeout::
|
245
|
+
# Overrides the timeout (in seconds) for this call.
|
246
|
+
#
|
247
|
+
# :version::
|
248
|
+
# Overrides the version of the Events API to call.
|
249
|
+
#
|
250
|
+
# ==== Returns:
|
179
251
|
#
|
180
|
-
|
252
|
+
# A Response object containing a status code, status message, and,
|
253
|
+
# if successful, the user's score(s).
|
254
|
+
#
|
255
|
+
def score(user_id, opts = {})
|
256
|
+
abuse_types = opts[:abuse_types]
|
257
|
+
api_key = opts[:api_key] || @api_key
|
258
|
+
timeout = opts[:timeout] || @timeout
|
259
|
+
version = opts[:version] || @version
|
181
260
|
|
182
261
|
raise("user_id must be a non-empty string") if (!user_id.is_a? String) || user_id.to_s.empty?
|
183
262
|
raise("Bad api_key parameter") if api_key.empty?
|
184
|
-
timetout ||= @timeout
|
185
263
|
|
186
|
-
|
264
|
+
query = {}
|
265
|
+
query["api_key"] = api_key
|
266
|
+
query["abuse_types"] = abuse_types.join(",") if abuse_types
|
267
|
+
|
268
|
+
options = {
|
269
|
+
:headers => {"User-Agent" => user_agent},
|
270
|
+
:query => query
|
271
|
+
}
|
187
272
|
options.merge!(:timeout => timeout) unless timeout.nil?
|
188
273
|
|
189
|
-
response = self.class.get(
|
274
|
+
response = self.class.get(Sift.score_api_path(user_id, version), options)
|
190
275
|
Response.new(response.body, response.code, response.response)
|
191
|
-
|
192
276
|
end
|
193
277
|
|
194
|
-
|
278
|
+
|
279
|
+
# Labels a user.
|
280
|
+
#
|
281
|
+
# See https://siftscience.com/developers/docs/ruby/labels-api/label-user .
|
195
282
|
#
|
196
|
-
#
|
197
|
-
#
|
283
|
+
# ==== Parameters:
|
284
|
+
#
|
285
|
+
# user_id::
|
198
286
|
# A user's id. This id should be the same as the user_id used in
|
199
287
|
# event calls.
|
200
288
|
#
|
201
|
-
# properties
|
289
|
+
# properties::
|
202
290
|
# A hash of name-value pairs that specify the label attributes.
|
203
291
|
# This parameter must be specified.
|
204
292
|
#
|
205
|
-
#
|
206
|
-
#
|
207
|
-
#
|
293
|
+
# opts (optional)::
|
294
|
+
# A Hash of optional parameters for the request --
|
295
|
+
#
|
296
|
+
# :api_key::
|
297
|
+
# Overrides the API key for this call.
|
298
|
+
#
|
299
|
+
# :timeout::
|
300
|
+
# Overrides the timeout (in seconds) for this call.
|
301
|
+
#
|
302
|
+
# :version::
|
303
|
+
# Overrides the version of the Events API to call.
|
208
304
|
#
|
209
|
-
#
|
210
|
-
# A Response object is returned and captures the status message and
|
211
|
-
# status code. In general, you can ignore the returned result, though.
|
305
|
+
# ==== Returns:
|
212
306
|
#
|
213
|
-
|
307
|
+
# In the case of a connection error (timeout, broken connection,
|
308
|
+
# etc.), this method returns nil; otherwise, a Response object is
|
309
|
+
# returned that captures the status message and status code.
|
310
|
+
#
|
311
|
+
def label(user_id, properties = {}, opts = {})
|
312
|
+
api_key = opts[:api_key] || @api_key
|
313
|
+
timeout = opts[:timeout] || @timeout
|
314
|
+
version = opts[:version] || @version
|
315
|
+
path = Sift.users_label_api_path(user_id, version)
|
214
316
|
|
215
317
|
raise("user_id must be a non-empty string") if (!user_id.is_a? String) || user_id.to_s.empty?
|
216
318
|
|
217
|
-
|
218
|
-
|
219
|
-
# No return_action logic supported when using labels.
|
220
|
-
track("$label", delete_nils(properties), timeout, path, false, api_key, false)
|
319
|
+
track("$label", delete_nils(properties),
|
320
|
+
:path => path, :api_key => api_key, :timeout => timeout)
|
221
321
|
end
|
222
322
|
|
223
|
-
|
323
|
+
|
324
|
+
# Unlabels a user.
|
224
325
|
#
|
225
|
-
#
|
226
|
-
#
|
326
|
+
# See https://siftscience.com/developers/docs/ruby/labels-api/unlabel-user .
|
327
|
+
#
|
328
|
+
# ==== Parameters:
|
329
|
+
#
|
330
|
+
# user_id::
|
227
331
|
# A user's id. This id should be the same as the user_id used in
|
228
332
|
# event calls.
|
229
333
|
#
|
230
|
-
#
|
231
|
-
#
|
232
|
-
#
|
334
|
+
# opts (optional)::
|
335
|
+
# A Hash of optional parameters for this request --
|
336
|
+
#
|
337
|
+
# :abuse_type::
|
338
|
+
# The abuse type for which the user should be unlabeled. If
|
339
|
+
# omitted, the user is unlabeled for all abuse types.
|
340
|
+
#
|
341
|
+
# :api_key::
|
342
|
+
# Overrides the API key for this call.
|
343
|
+
#
|
344
|
+
# :timeout::
|
345
|
+
# Overrides the timeout (in seconds) for this call.
|
346
|
+
#
|
347
|
+
# :version::
|
348
|
+
# Overrides the version of the Events API to call.
|
349
|
+
#
|
350
|
+
# ==== Returns:
|
233
351
|
#
|
234
|
-
#
|
235
|
-
# A Response object is returned with only an http code of 204.
|
352
|
+
# A Response object is returned with only an http code of 204.
|
236
353
|
#
|
237
|
-
def unlabel(user_id,
|
354
|
+
def unlabel(user_id, opts = {})
|
355
|
+
abuse_type = opts[:abuse_type]
|
356
|
+
api_key = opts[:api_key] || @api_key
|
357
|
+
timeout = opts[:timeout] || @timeout
|
358
|
+
version = opts[:version] || @version
|
238
359
|
|
239
360
|
raise("user_id must be a non-empty string") if (!user_id.is_a? String) || user_id.to_s.empty?
|
240
|
-
timetout ||= @timeout
|
241
361
|
|
242
|
-
|
362
|
+
query = {}
|
363
|
+
query[:api_key] = api_key
|
364
|
+
query[:abuse_type] = abuse_type if abuse_type
|
365
|
+
|
366
|
+
options = {
|
367
|
+
:headers => {},
|
368
|
+
:query => query
|
369
|
+
}
|
243
370
|
options.merge!(:timeout => timeout) unless timeout.nil?
|
244
|
-
|
245
|
-
response = self.class.delete(
|
371
|
+
|
372
|
+
response = self.class.delete(Sift.users_label_api_path(user_id, version), options)
|
246
373
|
Response.new(response.body, response.code, response.response)
|
247
374
|
end
|
248
375
|
|
376
|
+
|
377
|
+
# Gets the status of a workflow run.
|
378
|
+
#
|
379
|
+
# See https://siftscience.com/developers/docs/ruby/workflows-api/workflow-status .
|
380
|
+
#
|
381
|
+
# ==== Parameters
|
382
|
+
#
|
383
|
+
# run_id::
|
384
|
+
# The ID of a workflow run.
|
385
|
+
#
|
386
|
+
# opts (optional)::
|
387
|
+
# A Hash of optional parameters for this request --
|
388
|
+
#
|
389
|
+
# :account_id::
|
390
|
+
# Overrides the API key for this call.
|
391
|
+
#
|
392
|
+
# :api_key::
|
393
|
+
# Overrides the API key for this call.
|
394
|
+
#
|
395
|
+
# :timeout::
|
396
|
+
# Overrides the timeout (in seconds) for this call.
|
397
|
+
#
|
398
|
+
def get_workflow_status(run_id, opts = {})
|
399
|
+
account_id = opts[:account_id] || @account_id
|
400
|
+
api_key = opts[:api_key] || @api_key
|
401
|
+
timeout = opts[:timeout] || @timeout
|
402
|
+
|
403
|
+
options = {
|
404
|
+
:headers => { "User-Agent" => user_agent },
|
405
|
+
:basic_auth => { :username => api_key, :password => "" }
|
406
|
+
}
|
407
|
+
options.merge!(:timeout => timeout) unless timeout.nil?
|
408
|
+
|
409
|
+
uri = API3_ENDPOINT + Sift.workflow_status_path(account_id, run_id)
|
410
|
+
response = self.class.get(uri, options)
|
411
|
+
Response.new(response.body, response.code, response.response)
|
412
|
+
end
|
413
|
+
|
414
|
+
|
415
|
+
# Gets the decision status of a user.
|
416
|
+
#
|
417
|
+
# See https://siftscience.com/developers/docs/ruby/decisions-api/decision-status .
|
418
|
+
#
|
419
|
+
# ==== Parameters
|
420
|
+
#
|
421
|
+
# user_id::
|
422
|
+
# The ID of user.
|
423
|
+
#
|
424
|
+
# opts (optional)::
|
425
|
+
# A Hash of optional parameters for this request --
|
426
|
+
#
|
427
|
+
# :account_id::
|
428
|
+
# Overrides the API key for this call.
|
429
|
+
#
|
430
|
+
# :api_key::
|
431
|
+
# Overrides the API key for this call.
|
432
|
+
#
|
433
|
+
# :timeout::
|
434
|
+
# Overrides the timeout (in seconds) for this call.
|
435
|
+
#
|
436
|
+
def get_user_decisions(user_id, opts = {})
|
437
|
+
account_id = opts[:account_id] || @account_id
|
438
|
+
api_key = opts[:api_key] || @api_key
|
439
|
+
timeout = opts[:timeout] || @timeout
|
440
|
+
|
441
|
+
options = {
|
442
|
+
:headers => { "User-Agent" => user_agent },
|
443
|
+
:basic_auth => { :username => api_key, :password => "" }
|
444
|
+
}
|
445
|
+
options.merge!(:timeout => timeout) unless timeout.nil?
|
446
|
+
|
447
|
+
uri = API3_ENDPOINT + Sift.user_decisions_api_path(account_id, user_id)
|
448
|
+
response = self.class.get(uri, options)
|
449
|
+
Response.new(response.body, response.code, response.response)
|
450
|
+
end
|
451
|
+
|
452
|
+
|
453
|
+
# Gets the decision status of an order.
|
454
|
+
#
|
455
|
+
# See https://siftscience.com/developers/docs/ruby/decisions-api/decision-status .
|
456
|
+
#
|
457
|
+
# ==== Parameters
|
458
|
+
#
|
459
|
+
# order_id::
|
460
|
+
# The ID of an order.
|
461
|
+
#
|
462
|
+
# opts (optional)::
|
463
|
+
# A Hash of optional parameters for this request --
|
464
|
+
#
|
465
|
+
# :account_id::
|
466
|
+
# Overrides the API key for this call.
|
467
|
+
#
|
468
|
+
# :api_key::
|
469
|
+
# Overrides the API key for this call.
|
470
|
+
#
|
471
|
+
# :timeout::
|
472
|
+
# Overrides the timeout (in seconds) for this call.
|
473
|
+
#
|
474
|
+
def get_order_decisions(order_id, opts = {})
|
475
|
+
account_id = opts[:account_id] || @account_id
|
476
|
+
api_key = opts[:api_key] || @api_key
|
477
|
+
timeout = opts[:timeout] || @timeout
|
478
|
+
|
479
|
+
options = {
|
480
|
+
:headers => { "User-Agent" => user_agent },
|
481
|
+
:basic_auth => { :username => api_key, :password => "" }
|
482
|
+
}
|
483
|
+
options.merge!(:timeout => timeout) unless timeout.nil?
|
484
|
+
|
485
|
+
uri = API3_ENDPOINT + Sift.order_decisions_api_path(account_id, order_id)
|
486
|
+
response = self.class.get(uri, options)
|
487
|
+
Response.new(response.body, response.code, response.response)
|
488
|
+
end
|
489
|
+
|
490
|
+
|
249
491
|
private
|
250
|
-
|
251
|
-
# uri = URI.parse(API_ENDPOINT)
|
252
|
-
# end
|
492
|
+
|
253
493
|
def delete_nils(properties)
|
254
494
|
properties.delete_if do |k, v|
|
255
495
|
case v
|