knockapi 0.4.1 → 0.4.4

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
  SHA256:
3
- metadata.gz: e5539a9d4052b39167c0aa22d71eb9848ab0c6ad0c2812bf72e09cc446256868
4
- data.tar.gz: 7b08912b135c05a15d528527788a3f7aa8d7b67b7c14e0e5bcbac8f80fb5fe4e
3
+ metadata.gz: 9d0a730346c7c39ec862f160ac31fd80844b3f0907129a02ad320bf724e74888
4
+ data.tar.gz: bab747c80c86891e7e5d8135748deec4cd8c6bee1b20fbddf19546aefebe5646
5
5
  SHA512:
6
- metadata.gz: 2e2976916846b11c9a8ccb6cdacba9f12fecb0e113f8114cb1eed77a248b53156cdf025ffd823148567675489d988f655d80fec43cdb8a2174f6d6cce5a0db02
7
- data.tar.gz: 83b75fd115a9ce6905629cc20bbdf1550eb726e2e39ece0e4d4215a1203ee1b6af46877d1dd50cda0de1c1230a5f948a9e6e974cdd600ca62794a154ba9f1ab6
6
+ metadata.gz: a7e879b66a557daac3950155ec7429cbfe72b7f6d7f2491eb440f92cf1b1f620753a2dab325751bdb704933df7be8c598b9b47c67b191c7659dbd9470c888f2c
7
+ data.tar.gz: 689dba9548ddba6fe5e2e90fb339eb2dee6c23f9c8d51ce878d4d163da70453482a1fae0806c7fa56638e3dec9aa0cf38f3c5669c657b11768d7e1087a57dd47
@@ -0,0 +1,52 @@
1
+ # This workflow uses actions that are not certified by GitHub.
2
+ # They are provided by a third-party and are governed by
3
+ # separate terms of service, privacy policy, and support
4
+ # documentation.
5
+ # This workflow will download a prebuilt Ruby version, install dependencies and run tests with Rake
6
+ # For more information see: https://github.com/marketplace/actions/setup-ruby-jruby-and-truffleruby
7
+
8
+ name: Ruby
9
+
10
+ on:
11
+ push:
12
+ branches: [ "main" ]
13
+ pull_request:
14
+ branches: [ "main" ]
15
+
16
+ permissions:
17
+ contents: read
18
+
19
+ jobs:
20
+ test:
21
+
22
+ runs-on: ubuntu-latest
23
+ strategy:
24
+ matrix:
25
+ ruby-version: ['2.6', '2.7', '3.0']
26
+
27
+ steps:
28
+ - uses: actions/checkout@v3
29
+ - name: Set up Ruby
30
+ # To automatically get bug fixes and new Ruby versions for ruby/setup-ruby,
31
+ # change this to (see https://github.com/ruby/setup-ruby#versioning):
32
+ # uses: ruby/setup-ruby@v1
33
+ uses: ruby/setup-ruby@2b019609e2b0f1ea1a2bc8ca11cb82ab46ada124
34
+ with:
35
+ ruby-version: ${{ matrix.ruby-version }}
36
+ bundler-cache: true # runs 'bundle install' and caches installed gems automatically
37
+ - name: Run tests
38
+ run: bundle exec rspec spec
39
+
40
+ lint:
41
+
42
+ runs-on: ubuntu-latest
43
+ steps:
44
+ - name: Checkout code
45
+ uses: actions/checkout@v3
46
+ - name: Install Ruby and gems
47
+ uses: ruby/setup-ruby@8f312efe1262fb463d906e9bf040319394c18d3e # v1.92
48
+ with:
49
+ bundler-cache: true
50
+ # Add or replace any other lints here
51
+ - name: Lint Ruby files
52
+ run: bundle exec rubocop
data/.rubocop.yml ADDED
@@ -0,0 +1,8 @@
1
+ AllCops:
2
+ TargetRubyVersion: 2.5
3
+ Metrics/LineLength:
4
+ Max: 120
5
+ Metrics/MethodLength:
6
+ Max: 35
7
+ Metrics/ParameterLists:
8
+ Max: 6
data/Gemfile CHANGED
@@ -1,5 +1,9 @@
1
1
  # frozen_string_literal: true
2
2
 
3
- source "https://rubygems.org"
3
+ source 'https://rubygems.org'
4
4
 
5
5
  gemspec
6
+
7
+ group :test do
8
+ gem 'rspec', '~> 3.11'
9
+ end
data/Gemfile.lock CHANGED
@@ -1,12 +1,13 @@
1
1
  PATH
2
2
  remote: .
3
3
  specs:
4
- knockapi (0.4.1)
4
+ knockapi (0.4.4)
5
5
 
6
6
  GEM
7
7
  remote: https://rubygems.org/
8
8
  specs:
9
9
  ast (2.4.2)
10
+ diff-lcs (1.5.0)
10
11
  parallel (1.20.1)
11
12
  parser (3.0.2.0)
12
13
  ast (~> 2.4.1)
@@ -14,6 +15,19 @@ GEM
14
15
  rake (13.0.6)
15
16
  regexp_parser (2.1.1)
16
17
  rexml (3.2.5)
18
+ rspec (3.11.0)
19
+ rspec-core (~> 3.11.0)
20
+ rspec-expectations (~> 3.11.0)
21
+ rspec-mocks (~> 3.11.0)
22
+ rspec-core (3.11.0)
23
+ rspec-support (~> 3.11.0)
24
+ rspec-expectations (3.11.0)
25
+ diff-lcs (>= 1.2.0, < 2.0)
26
+ rspec-support (~> 3.11.0)
27
+ rspec-mocks (3.11.1)
28
+ diff-lcs (>= 1.2.0, < 2.0)
29
+ rspec-support (~> 3.11.0)
30
+ rspec-support (3.11.0)
17
31
  rubocop (1.18.4)
18
32
  parallel (~> 1.10)
19
33
  parser (>= 3.0.0.0)
@@ -42,6 +56,7 @@ DEPENDENCIES
42
56
  bundler (>= 2.0.1)
43
57
  knockapi!
44
58
  rake
59
+ rspec (~> 3.11)
45
60
  standard
46
61
 
47
62
  BUNDLED WITH
data/bin/console CHANGED
@@ -1,7 +1,8 @@
1
1
  #!/usr/bin/env ruby
2
+ # frozen_string_literal: true
2
3
 
3
- require "bundler/setup"
4
- require "knock"
4
+ require 'bundler/setup'
5
+ require 'knock'
5
6
 
6
- require "irb"
7
- IRB.start(__FILE__)
7
+ require 'irb'
8
+ IRB.start(__FILE__)
data/knockapi.gemspec CHANGED
@@ -1,30 +1,30 @@
1
1
  # frozen_string_literal: true
2
2
 
3
- lib = File.expand_path("lib", __dir__)
3
+ lib = File.expand_path('lib', __dir__)
4
4
  $LOAD_PATH.unshift(lib) unless $LOAD_PATH.include?(lib)
5
- require "knock/version"
5
+ require 'knock/version'
6
6
 
7
7
  Gem::Specification.new do |spec|
8
- spec.name = "knockapi"
8
+ spec.name = 'knockapi'
9
9
  spec.version = Knock::VERSION
10
- spec.authors = ["Knock Labs, Inc."]
11
- spec.email = ["support@knock.app"]
12
- spec.description = "API client for Knock"
13
- spec.summary = "API client for Knock"
14
- spec.homepage = "https://github.com/knocklabs/knock-ruby"
15
- spec.license = "MIT"
10
+ spec.authors = ['Knock Labs, Inc.']
11
+ spec.email = ['support@knock.app']
12
+ spec.description = 'API client for Knock'
13
+ spec.summary = 'API client for Knock'
14
+ spec.homepage = 'https://github.com/knocklabs/knock-ruby'
15
+ spec.license = 'MIT'
16
16
  spec.metadata = {
17
- "documentation_uri" => "https://docs.knock.app"
17
+ 'documentation_uri' => 'https://docs.knock.app'
18
18
  }
19
19
 
20
20
  spec.files = `git ls-files`.split($INPUT_RECORD_SEPARATOR)
21
21
  spec.executables = spec.files.grep(%r{^bin/}) { |f| File.basename(f) }
22
22
  spec.test_files = spec.files.grep(%r{^(test|spec|features)/})
23
- spec.require_paths = ["lib"]
23
+ spec.require_paths = ['lib']
24
24
 
25
- spec.add_development_dependency "bundler", ">= 2.0.1"
26
- spec.add_development_dependency "rake"
27
- spec.add_development_dependency "standard"
25
+ spec.add_development_dependency 'bundler', '>= 2.0.1'
26
+ spec.add_development_dependency 'rake'
27
+ spec.add_development_dependency 'standard'
28
28
 
29
- spec.required_ruby_version = ">= 2.5"
29
+ spec.required_ruby_version = '>= 2.5'
30
30
  end
data/lib/knock/base.rb CHANGED
@@ -1,11 +1,12 @@
1
+ # frozen_string_literal: true
2
+
1
3
  module Knock
2
4
  ## The Base class handles setting and reading the Knock API Key for authentication
3
5
  module Base
4
6
  attr_accessor :key
5
7
 
6
8
  class << self
7
- attr_writer :key
8
- attr_reader :key
9
+ attr_accessor :key
9
10
  end
10
11
  end
11
12
  end
@@ -1,5 +1,7 @@
1
- require "net/http"
2
- require "uri"
1
+ # frozen_string_literal: true
2
+
3
+ require 'net/http'
4
+ require 'uri'
3
5
 
4
6
  module Knock
5
7
  # Provides convienience methods for working with bulk operations
data/lib/knock/client.rb CHANGED
@@ -1,3 +1,5 @@
1
+ # frozen_string_literal: true
2
+
1
3
  module Knock
2
4
  # A Net::HTTP based API client for interacting with the Knock API
3
5
  module Client
@@ -18,7 +20,7 @@ module Knock
18
20
  http_status = response.code.to_i
19
21
  handle_error_response(response: response) if http_status >= 400
20
22
 
21
- JSON.parse(response.body)
23
+ JSON.parse(response.body) if response.body && (response.body != '')
22
24
  end
23
25
 
24
26
  def get_request(path:, auth: false, params: {}, access_token: nil)
@@ -27,19 +29,19 @@ module Knock
27
29
 
28
30
  request = Net::HTTP::Get.new(
29
31
  uri.to_s,
30
- "Content-Type" => "application/json"
32
+ 'Content-Type' => 'application/json'
31
33
  )
32
34
 
33
- request["Authorization"] = "Bearer #{access_token || Knock.key!}" if auth
34
- request["User-Agent"] = user_agent
35
+ request['Authorization'] = "Bearer #{access_token || Knock.key!}" if auth
36
+ request['User-Agent'] = user_agent
35
37
  request
36
38
  end
37
39
 
38
- def post_request(path:, auth: false, idempotency_key: nil, body: nil)
39
- request = Net::HTTP::Post.new(path, "Content-Type" => "application/json")
40
+ def post_request(path:, auth: false, _idempotency_key: nil, body: nil)
41
+ request = Net::HTTP::Post.new(path, 'Content-Type' => 'application/json')
40
42
  request.body = body.to_json if body
41
- request["Authorization"] = "Bearer #{Knock.key!}" if auth
42
- request["User-Agent"] = user_agent
43
+ request['Authorization'] = "Bearer #{Knock.key!}" if auth
44
+ request['User-Agent'] = user_agent
43
45
  request
44
46
  end
45
47
 
@@ -49,19 +51,19 @@ module Knock
49
51
 
50
52
  request = Net::HTTP::Delete.new(
51
53
  uri.to_s,
52
- "Content-Type" => "application/json"
54
+ 'Content-Type' => 'application/json'
53
55
  )
54
56
 
55
- request["Authorization"] = "Bearer #{Knock.key!}" if auth
56
- request["User-Agent"] = user_agent
57
+ request['Authorization'] = "Bearer #{Knock.key!}" if auth
58
+ request['User-Agent'] = user_agent
57
59
  request
58
60
  end
59
61
 
60
- def put_request(path:, auth: false, idempotency_key: nil, body: nil)
61
- request = Net::HTTP::Put.new(path, "Content-Type" => "application/json")
62
+ def put_request(path:, auth: false, _idempotency_key: nil, body: nil)
63
+ request = Net::HTTP::Put.new(path, 'Content-Type' => 'application/json')
62
64
  request.body = body.to_json if body
63
- request["Authorization"] = "Bearer #{Knock.key!}" if auth
64
- request["User-Agent"] = user_agent
65
+ request['Authorization'] = "Bearer #{Knock.key!}" if auth
66
+ request['User-Agent'] = user_agent
65
67
  request
66
68
  end
67
69
 
@@ -69,6 +71,8 @@ module Knock
69
71
  "Knock Ruby - v#{Knock::VERSION}"
70
72
  end
71
73
 
74
+ # rubocop:disable Metrics/AbcSize
75
+
72
76
  def handle_error_response(response:)
73
77
  http_status = response.code.to_i
74
78
  json = JSON.parse(response.body)
@@ -76,41 +80,43 @@ module Knock
76
80
  case http_status
77
81
  when 400
78
82
  raise InvalidRequestError.new(
79
- message: json["message"],
83
+ message: json['message'],
80
84
  http_status: http_status,
81
- request_id: response["x-request-id"]
85
+ request_id: response['x-request-id']
82
86
  )
83
87
  when 401
84
88
  raise AuthenticationError.new(
85
- message: json["message"],
89
+ message: json['message'],
86
90
  http_status: http_status,
87
- request_id: response["x-request-id"]
91
+ request_id: response['x-request-id']
88
92
  )
89
93
  when 404
90
94
  raise APIError.new(
91
- message: json["message"],
95
+ message: json['message'],
92
96
  http_status: http_status,
93
- request_id: response["x-request-id"]
97
+ request_id: response['x-request-id']
94
98
  )
95
99
  when 422
96
- message = json["message"]
97
- errors = extract_error(json["errors"]) if json["errors"]
100
+ message = json['message']
101
+ errors = extract_error(json['errors']) if json['errors']
98
102
  message += " (#{errors})" if errors
99
103
 
100
104
  raise InvalidRequestError.new(
101
105
  message: message,
102
106
  http_status: http_status,
103
- request_id: response["x-request-id"]
107
+ request_id: response['x-request-id']
104
108
  )
105
109
  end
106
110
  end
107
111
 
112
+ # rubocop:enable Metrics/AbcSize
113
+
108
114
  private
109
115
 
110
116
  def extract_error(errors)
111
117
  errors.map do |error|
112
- "#{error["field"]}: #{error["message"]} (#{error["type"]})"
113
- end.join("; ")
118
+ "#{error['field']}: #{error['message']} (#{error['type']})"
119
+ end.join('; ')
114
120
  end
115
121
  end
116
122
  end
data/lib/knock/errors.rb CHANGED
@@ -1,9 +1,12 @@
1
+ # frozen_string_literal: true
2
+
1
3
  module Knock
4
+ # Knock specific errors
2
5
  class KnockError < StandardError
3
- attr_reader :http_status
4
- attr_reader :request_id
6
+ attr_reader :http_status, :request_id
5
7
 
6
8
  def initialize(message: nil, error: nil, error_description: nil, http_status: nil, request_id: nil)
9
+ super
7
10
  @message = message
8
11
  @error = error
9
12
  @error_description = error_description
@@ -12,8 +15,8 @@ module Knock
12
15
  end
13
16
 
14
17
  def to_s
15
- status_string = @http_status.nil? ? "" : "Status #{@http_status}, "
16
- id_string = @request_id.nil? ? "" : " - request ID: #{@request_id}"
18
+ status_string = @http_status.nil? ? '' : "Status #{@http_status}, "
19
+ id_string = @request_id.nil? ? '' : " - request ID: #{@request_id}"
17
20
 
18
21
  if @error && @error_description
19
22
  error_string = "error: #{@error}, error_description: #{@error_description}"
@@ -0,0 +1,89 @@
1
+ # frozen_string_literal: true
2
+
3
+ require 'net/http'
4
+ require 'uri'
5
+
6
+ module Knock
7
+ # Methods for interacting with messages in Knock
8
+ module Messages
9
+ class << self
10
+ include Base
11
+ include Client
12
+
13
+ # Retrieves a paginated list of messages for the provided environment
14
+ #
15
+ # @param [Hash] options Options to pass to the messages endpoint query
16
+ #
17
+ # @return [Hash] Paginated list of Message records
18
+ def list(options: {})
19
+ request = get_request(
20
+ auth: true,
21
+ path: '/v1/messages',
22
+ params: options
23
+ )
24
+
25
+ execute_request(request: request)
26
+ end
27
+
28
+ # Retrieves a Message
29
+ #
30
+ # @param [String] id The message id
31
+ #
32
+ # @return [Hash] The Message
33
+ def get(id:)
34
+ request = get_request(
35
+ auth: true,
36
+ path: "/v1/messages/#{id}"
37
+ )
38
+
39
+ execute_request(request: request)
40
+ end
41
+
42
+ # Get a Message's content
43
+ #
44
+ # @param [String] id The message id
45
+ #
46
+ # @return [Hash] The Message content
47
+ def get_content(id:)
48
+ request = get_request(
49
+ auth: true,
50
+ path: "/v1/messages/#{id}/content"
51
+ )
52
+
53
+ execute_request(request: request)
54
+ end
55
+
56
+ # Get a Message's activities
57
+ #
58
+ # @param [String] id The message id
59
+ # @param [Hash] options Options to pass to the paginated activities endpoint query
60
+ #
61
+ # @return [Hash] Paginated Message's activities
62
+ def get_activities(id:, options: {})
63
+ request = get_request(
64
+ auth: true,
65
+ path: "/v1/messages/#{id}/activities",
66
+ params: options
67
+ )
68
+
69
+ execute_request(request: request)
70
+ end
71
+
72
+ # Get a Message's events
73
+ #
74
+ # @param [String] id The message id
75
+ # @param [Hash] options Options to pass to the paginated events endpoint query
76
+ #
77
+ # @return [Hash] Paginated Message's events
78
+ def get_events(id:, options: {})
79
+ request = get_request(
80
+ auth: true,
81
+ path: "/v1/messages/#{id}/events",
82
+ params: options
83
+ )
84
+
85
+ execute_request(request: request)
86
+ end
87
+ end
88
+ end
89
+ end
data/lib/knock/objects.rb CHANGED
@@ -1,13 +1,18 @@
1
- require "net/http"
2
- require "uri"
1
+ # frozen_string_literal: true
2
+
3
+ require 'net/http'
4
+ require 'uri'
3
5
 
4
6
  module Knock
5
- # Provides convienience methods for working with bulk operations
7
+ # Methods for interacting with objects in Knock
8
+ # rubocop:disable Metrics/ModuleLength
6
9
  module Objects
7
10
  class << self
8
11
  include Base
9
12
  include Client
10
13
 
14
+ DEFAULT_PREFERENCE_SET_ID = 'default'
15
+
11
16
  # Retrieves an Object in a collection
12
17
  #
13
18
  # @param [String] collection The collection the object is in
@@ -50,7 +55,7 @@ module Knock
50
55
  request = post_request(
51
56
  auth: true,
52
57
  path: "/v1/objects/#{collection}/bulk/set",
53
- body: {objects: objects}
58
+ body: { objects: objects }
54
59
  )
55
60
 
56
61
  execute_request(request: request)
@@ -81,7 +86,7 @@ module Knock
81
86
  request = post_request(
82
87
  auth: true,
83
88
  path: "/v1/objects/#{collection}/bulk/delete",
84
- body: {object_ids: object_ids}
89
+ body: { object_ids: object_ids }
85
90
  )
86
91
 
87
92
  execute_request(request: request)
@@ -111,15 +116,194 @@ module Knock
111
116
  # @param [Hash] channel_data channel data
112
117
  #
113
118
  # @return [Hash] channel data
114
- def set_channel_data(id:, channel_id:, channel_data:)
119
+ def set_channel_data(collection:, id:, channel_id:, channel_data:)
115
120
  request = put_request(
116
121
  auth: true,
117
122
  path: "/v1/objects/#{collection}/#{id}/channel_data/#{channel_id}",
118
- body: {data: channel_data}
123
+ body: { data: channel_data }
124
+ )
125
+
126
+ execute_request(request: request)
127
+ end
128
+
129
+ # Unsets object channel data for the given channel id
130
+ #
131
+ # @param [String] collection The collection the object is in
132
+ # @param [String] id The object id
133
+ # @param [String] channel_id target channel ID
134
+ #
135
+ # @return [Hash] channel data
136
+ def unset_channel_data(collection:, id:, channel_id:)
137
+ request = delete_request(
138
+ auth: true,
139
+ path: "/v1/objects/#{collection}/#{id}/channel_data/#{channel_id}"
140
+ )
141
+
142
+ execute_request(request: request)
143
+ end
144
+
145
+ # Get object's messages
146
+ #
147
+ # @param [String] collection The collection the object is in
148
+ # @param [String] id The object id
149
+ # @param [Hash] options Options to pass to the messages endpoint query
150
+ #
151
+ # @return [Hash] Paginated messages response
152
+ def get_messages(collection:, id:, options: {})
153
+ request = get_request(
154
+ auth: true,
155
+ path: "/v1/objects/#{collection}/#{id}/messages",
156
+ params: options
157
+ )
158
+
159
+ execute_request(request: request)
160
+ end
161
+
162
+ ##
163
+ # Preferences
164
+ ##
165
+
166
+ # Returns all preference sets for the object
167
+ #
168
+ # @param [String] collection The collection the object is in
169
+ # @param [String] id The object id
170
+ #
171
+ # @return [Array] The preference sets
172
+ def get_all_preferences(collection:, id:)
173
+ endpoint = "/v1/objects/#{collection}/#{id}/preferences"
174
+
175
+ request = get_request(
176
+ auth: true,
177
+ path: endpoint
178
+ )
179
+
180
+ execute_request(request: request)
181
+ end
182
+
183
+ # Gets a single preference set, defaults to the 'default' set
184
+ # for the object given.
185
+ #
186
+ # @param [String] collection The collection the object is in
187
+ # @param [String] id The object id
188
+ # @param [String] preference_set The preference set ID (defaults to `default`)
189
+ #
190
+ # @return [Hash] The preference set (if it exists)
191
+ def get_preferences(collection:, id:, preference_set: DEFAULT_PREFERENCE_SET_ID)
192
+ endpoint = "/v1/objects/#{collection}/#{id}/preferences/#{preference_set}"
193
+
194
+ request = get_request(
195
+ auth: true,
196
+ path: endpoint
197
+ )
198
+
199
+ execute_request(request: request)
200
+ end
201
+
202
+ # Sets multiple preferences at once for the preference set.
203
+ #
204
+ # @param [String] collection The collection the object is in
205
+ # @param [String] id The object id
206
+ # @param [String] preference_set The preference set ID (defaults to `default`)
207
+ # @param [Hash] channel_types The channel_types hash to set
208
+ # @param [Hash] workflows The workflows hash to set
209
+ # @param [Hash] categories The categories hash to set
210
+ #
211
+ # @return [Hash] The preference set
212
+
213
+ def set_preferences(
214
+ collection:,
215
+ id:,
216
+ channel_types: nil,
217
+ workflows: nil,
218
+ categories: nil,
219
+ preference_set: DEFAULT_PREFERENCE_SET_ID
220
+ )
221
+ endpoint = "/v1/objects/#{collection}/#{id}/preferences/#{preference_set}"
222
+
223
+ request = put_request(
224
+ auth: true,
225
+ path: endpoint,
226
+ body: {
227
+ channel_types: channel_types,
228
+ workflows: workflows,
229
+ categories: categories
230
+ }
231
+ )
232
+
233
+ execute_request(request: request)
234
+ end
235
+
236
+ # Sets preferences for the given channel type
237
+ #
238
+ # @param [String] collection The collection the object is in
239
+ # @param [String] id The object id
240
+ # @param [String] preference_set The preference set ID (defaults to `default`)
241
+ # @param [String] channel_type The channel type to set
242
+ # @param [Bool] setting Whether the channel type is enabled or not
243
+ #
244
+ # @return [Hash] The preference set
245
+ def set_channel_type_preferences(collection:,
246
+ id:,
247
+ channel_type:,
248
+ setting:,
249
+ preference_set: DEFAULT_PREFERENCE_SET_ID)
250
+ endpoint = "/v1/objects/#{collection}/#{id}/preferences/#{preference_set}/channel_types/#{channel_type}"
251
+
252
+ request = put_request(
253
+ auth: true,
254
+ path: endpoint,
255
+ body: { subscribed: setting }
256
+ )
257
+
258
+ execute_request(request: request)
259
+ end
260
+
261
+ # Sets preferences for the given workflow
262
+ #
263
+ # @param [String] collection The collection the object is in
264
+ # @param [String] id The object id
265
+ # @param [String] preference_set The preference set ID (defaults to `default`)
266
+ # @param [String] workflow The workflow to set preferences for
267
+ # @param [Bool | Hash] setting Either a boolean to indicate if the type is enabled
268
+ # or a hash containing channel types and settings
269
+ #
270
+ # @return [Hash] The preference set
271
+ def set_workflow_preferences(collection:, id:, workflow:, setting:, preference_set: DEFAULT_PREFERENCE_SET_ID)
272
+ params = setting.is_a?(Hash) ? setting : { subscribed: setting }
273
+ endpoint = "/v1/objects/#{collection}/#{id}/preferences/#{preference_set}/workflows/#{workflow}"
274
+
275
+ request = put_request(
276
+ auth: true,
277
+ path: endpoint,
278
+ body: params
279
+ )
280
+
281
+ execute_request(request: request)
282
+ end
283
+
284
+ # Sets preferences for the given category
285
+ #
286
+ # @param [String] collection The collection the object is in
287
+ # @param [String] id The object id
288
+ # @param [String] preference_set The preference set ID (defaults to `default`)
289
+ # @param [String] category The category to set preferences for
290
+ # @param [Bool | Hash] setting Either a boolean to indicate if the type is enabled
291
+ # or a hash containing channel types and settings
292
+ #
293
+ # @return [Hash] The preference set
294
+ def set_category_preferences(collection:, id:, category:, setting:, preference_set: DEFAULT_PREFERENCE_SET_ID)
295
+ params = setting.is_a?(Hash) ? setting : { subscribed: setting }
296
+ endpoint = "/v1/objects/#{collection}/#{id}/preferences/#{preference_set}/categories/#{category}"
297
+
298
+ request = put_request(
299
+ auth: true,
300
+ path: endpoint,
301
+ body: params
119
302
  )
120
303
 
121
304
  execute_request(request: request)
122
305
  end
123
306
  end
124
307
  end
308
+ # rubocop:enable Metrics/ModuleLength
125
309
  end
@@ -1,5 +1,7 @@
1
- require "net/http"
2
- require "uri"
1
+ # frozen_string_literal: true
2
+
3
+ require 'net/http'
4
+ require 'uri'
3
5
 
4
6
  module Knock
5
7
  # Provides convienience methods for working with preferences (deprecated)
@@ -36,7 +38,7 @@ module Knock
36
38
  # @param [String] preference_set The preference set ID (defaults to `default`)
37
39
  # @param [Hash] preferences The preferences hash to set
38
40
  #
39
- #  @return [Hash] The preference set
41
+ # @return [Hash] The preference set
40
42
  # @deprecated Please use {#Knock::Users.set_preferences} instead
41
43
  def update(
42
44
  user_id:,
@@ -0,0 +1,73 @@
1
+ # frozen_string_literal: true
2
+
3
+ require 'net/http'
4
+ require 'uri'
5
+
6
+ module Knock
7
+ # Methods for interacting with tenants in Knock
8
+ module Tenants
9
+ class << self
10
+ include Base
11
+ include Client
12
+
13
+ # Retrieves all Tenants in environment
14
+ #
15
+ # @param [Hash] options Options to pass to the tenants endpoint query
16
+ #
17
+ # @return [Hash] Paginated list of Tenant records
18
+ def list(options: {})
19
+ request = get_request(
20
+ auth: true,
21
+ path: '/v1/tenants',
22
+ params: options
23
+ )
24
+
25
+ execute_request(request: request)
26
+ end
27
+
28
+ # Retrieves a Tenant
29
+ #
30
+ # @param [String] id The Tenant id
31
+ #
32
+ # @return [Hash] The Tenant
33
+ def get(id:)
34
+ request = get_request(
35
+ auth: true,
36
+ path: "/v1/tenants/#{id}"
37
+ )
38
+
39
+ execute_request(request: request)
40
+ end
41
+
42
+ # Upserts a Tenant
43
+ #
44
+ # @param [String] id The Tenant id
45
+ # @param [Hash] tenant_data The data to set on the Tenant
46
+ #
47
+ # @return [Hash] The Tenant
48
+ def set(id:, tenant_data: {})
49
+ request = put_request(
50
+ auth: true,
51
+ path: "/v1/tenants/#{id}",
52
+ body: tenant_data
53
+ )
54
+
55
+ execute_request(request: request)
56
+ end
57
+
58
+ # Deletes a Tenant
59
+ #
60
+ # @param [String] id The Tenant id
61
+ #
62
+ # @return [nil] Nothing
63
+ def delete(id:)
64
+ request = delete_request(
65
+ auth: true,
66
+ path: "/v1/tenants/#{id}"
67
+ )
68
+
69
+ execute_request(request: request)
70
+ end
71
+ end
72
+ end
73
+ end
data/lib/knock/users.rb CHANGED
@@ -1,14 +1,17 @@
1
- require "net/http"
2
- require "uri"
1
+ # frozen_string_literal: true
2
+
3
+ require 'net/http'
4
+ require 'uri'
3
5
 
4
6
  module Knock
5
7
  # Provides convienience methods for working with users
8
+ # rubocop:disable Metrics/ModuleLength
6
9
  module Users
7
10
  class << self
8
11
  include Base
9
12
  include Client
10
13
 
11
- DEFAULT_PREFERENCE_SET_ID = "default"
14
+ DEFAULT_PREFERENCE_SET_ID = 'default'
12
15
 
13
16
  # Identifies the user
14
17
  #
@@ -34,8 +37,8 @@ module Knock
34
37
  def bulk_identify(users: [])
35
38
  request = post_request(
36
39
  auth: true,
37
- path: "/v1/users/bulk/identify",
38
- body: {users: users}
40
+ path: '/v1/users/bulk/identify',
41
+ body: { users: users }
39
42
  )
40
43
 
41
44
  execute_request(request: request)
@@ -77,8 +80,8 @@ module Knock
77
80
  def bulk_delete(user_ids: [])
78
81
  request = post_request(
79
82
  auth: true,
80
- path: "/v1/users/bulk/delete",
81
- body: {user_ids: user_ids}
83
+ path: '/v1/users/bulk/delete',
84
+ body: { user_ids: user_ids }
82
85
  )
83
86
 
84
87
  execute_request(request: request)
@@ -198,12 +201,10 @@ module Knock
198
201
  preferences: {},
199
202
  preference_set: DEFAULT_PREFERENCE_SET_ID
200
203
  )
201
- endpoint = "/v1/users/bulk/preferences"
204
+ endpoint = '/v1/users/bulk/preferences'
202
205
 
203
206
  # Put the preference set id if it doesn't already exist
204
- unless preferences.has_key("id")
205
- preferences["id"] = preference_set
206
- end
207
+ preferences['id'] = preference_set unless preferences.has_key('id')
207
208
 
208
209
  request = put_request(
209
210
  auth: true,
@@ -231,7 +232,7 @@ module Knock
231
232
  request = put_request(
232
233
  auth: true,
233
234
  path: endpoint,
234
- body: {subscribed: setting}
235
+ body: { subscribed: setting }
235
236
  )
236
237
 
237
238
  execute_request(request: request)
@@ -247,7 +248,7 @@ module Knock
247
248
  #
248
249
  # @return [Hash] The preference set
249
250
  def set_workflow_preferences(user_id:, workflow:, setting:, preference_set: DEFAULT_PREFERENCE_SET_ID)
250
- params = setting.is_a?(Hash) ? setting : {subscribed: setting}
251
+ params = setting.is_a?(Hash) ? setting : { subscribed: setting }
251
252
  endpoint = "/v1/users/#{user_id}/preferences/#{preference_set}/workflows/#{workflow}"
252
253
 
253
254
  request = put_request(
@@ -269,7 +270,7 @@ module Knock
269
270
  #
270
271
  # @return [Hash] The preference set
271
272
  def set_category_preferences(user_id:, category:, setting:, preference_set: DEFAULT_PREFERENCE_SET_ID)
272
- params = setting.is_a?(Hash) ? setting : {subscribed: setting}
273
+ params = setting.is_a?(Hash) ? setting : { subscribed: setting }
273
274
  endpoint = "/v1/users/#{user_id}/preferences/#{preference_set}/categories/#{category}"
274
275
 
275
276
  request = put_request(
@@ -311,11 +312,48 @@ module Knock
311
312
  request = put_request(
312
313
  auth: true,
313
314
  path: "/v1/users/#{id}/channel_data/#{channel_id}",
314
- body: {data: channel_data}
315
+ body: { data: channel_data }
316
+ )
317
+
318
+ execute_request(request: request)
319
+ end
320
+
321
+ # Unsets user's channel data for the given channel id
322
+ #
323
+ # @param [String] id the user ID
324
+ # @param [String] channel_id target channel ID
325
+ # @param [Hash] channel_data channel data
326
+ #
327
+ # @return [Hash] channel data
328
+ def unset_channel_data(id:, channel_id:)
329
+ request = delete_request(
330
+ auth: true,
331
+ path: "/v1/users/#{id}/channel_data/#{channel_id}"
332
+ )
333
+
334
+ execute_request(request: request)
335
+ end
336
+
337
+ ##
338
+ # Messages
339
+ ##
340
+
341
+ # Get user's messages
342
+ #
343
+ # @param [String] id the user ID
344
+ # @param [Hash] options Options to pass to the messages endpoint query
345
+ #
346
+ # @return [Hash] Paginated messages response
347
+ def get_messages(id:, options: {})
348
+ request = get_request(
349
+ auth: true,
350
+ path: "/v1/users/#{id}/messages",
351
+ params: options
315
352
  )
316
353
 
317
354
  execute_request(request: request)
318
355
  end
319
356
  end
320
357
  end
358
+ # rubocop:enable Metrics/ModuleLength
321
359
  end
data/lib/knock/version.rb CHANGED
@@ -1,5 +1,5 @@
1
1
  # frozen_string_literal: true
2
2
 
3
3
  module Knock
4
- VERSION = "0.4.1"
4
+ VERSION = '0.4.4'
5
5
  end
@@ -1,5 +1,7 @@
1
- require "net/http"
2
- require "uri"
1
+ # frozen_string_literal: true
2
+
3
+ require 'net/http'
4
+ require 'uri'
3
5
 
4
6
  module Knock
5
7
  # Methods for interacting with workflows in Knock
@@ -11,7 +13,7 @@ module Knock
11
13
  # Triggers the workflow with the given key
12
14
  #
13
15
  # @param [String] key The workflow key
14
- # @param [String, Hash] actor The actor identifier
16
+ # @param [String, Hash] actor The actor identifier (optional)
15
17
  # @param [Array<String, Hash>] recipients The recipient identifiers
16
18
  # @param [Hash] data The data to pass to the workflow
17
19
  # @param [String] cancellation_key An optional key to identify this workflow
data/lib/knock.rb CHANGED
@@ -1,10 +1,11 @@
1
1
  # frozen_string_literal: true
2
2
 
3
- require "knock/version"
4
- require "json"
3
+ require 'knock/version'
4
+ require 'json'
5
5
 
6
+ # Setup for Knock client
6
7
  module Knock
7
- API_HOSTNAME = ENV["KNOCK_API_HOSTNAME"] || "api.knock.app"
8
+ API_HOSTNAME = ENV['KNOCK_API_HOSTNAME'] || 'api.knock.app'
8
9
 
9
10
  def self.key=(value)
10
11
  Base.key = value
@@ -15,25 +16,27 @@ module Knock
15
16
  end
16
17
 
17
18
  def self.key!
18
- key || raise("Knock.key not set")
19
+ key || raise('Knock.key not set')
19
20
  end
20
21
 
21
- autoload :Base, "knock/base"
22
- autoload :Client, "knock/client"
22
+ autoload :Base, 'knock/base'
23
+ autoload :Client, 'knock/client'
23
24
 
24
25
  # Resources
25
- autoload :Preferences, "knock/preferences"
26
- autoload :Users, "knock/users"
27
- autoload :Workflows, "knock/workflows"
28
- autoload :BulkOperations, "knock/bulk_operations"
29
- autoload :Objects, "knock/objects"
26
+ autoload :Preferences, 'knock/preferences'
27
+ autoload :Users, 'knock/users'
28
+ autoload :Workflows, 'knock/workflows'
29
+ autoload :BulkOperations, 'knock/bulk_operations'
30
+ autoload :Objects, 'knock/objects'
31
+ autoload :Tenants, 'knock/tenants'
32
+ autoload :Messages, 'knock/messages'
30
33
 
31
34
  # Errors
32
- autoload :APIError, "knock/errors"
33
- autoload :AuthenticationError, "knock/errors"
34
- autoload :InvalidRequestError, "knock/errors"
35
+ autoload :APIError, 'knock/errors'
36
+ autoload :AuthenticationError, 'knock/errors'
37
+ autoload :InvalidRequestError, 'knock/errors'
35
38
 
36
- key = ENV["KNOCK_API_KEY"]
39
+ key = ENV['KNOCK_API_KEY']
37
40
  Knock.key = key unless key.nil?
38
41
 
39
42
  # Triggers the workflow with the given key
@@ -0,0 +1,66 @@
1
+ # frozen_string_literal: true
2
+
3
+ require_relative '../lib/knock'
4
+ # rubocop:disable Metrics/BlockLength
5
+ describe 'tenant tests' do
6
+ before do
7
+ allow_any_instance_of(Knock::Client)
8
+ .to receive(:execute_request)
9
+ .with({ request: 'request' })
10
+ .and_return('ok')
11
+ end
12
+ describe '#list' do
13
+ before do
14
+ allow_any_instance_of(Knock::Client)
15
+ .to receive(:get_request)
16
+ .with({ auth: true,
17
+ path: '/v1/tenants',
18
+ params: {} })
19
+ .and_return('request')
20
+ end
21
+ it 'sends the correct parameters to the tenants API' do
22
+ Knock::Tenants.list(options: {})
23
+ end
24
+ end
25
+
26
+ describe '#get' do
27
+ before do
28
+ allow_any_instance_of(Knock::Client)
29
+ .to receive(:get_request)
30
+ .with({ auth: true,
31
+ path: '/v1/tenants/tenant_id' })
32
+ .and_return('request')
33
+ end
34
+ it 'sends the correct parameters to the tenants API' do
35
+ Knock::Tenants.get(id: 'tenant_id')
36
+ end
37
+ end
38
+
39
+ describe '#delete' do
40
+ before do
41
+ allow_any_instance_of(Knock::Client)
42
+ .to receive(:delete_request)
43
+ .with({ auth: true,
44
+ path: '/v1/tenants/tenant_id' })
45
+ .and_return('request')
46
+ end
47
+ it 'sends the correct parameters to the tenants API' do
48
+ Knock::Tenants.delete(id: 'tenant_id')
49
+ end
50
+ end
51
+
52
+ describe '#set' do
53
+ before do
54
+ body = { name: 'My tenant', settings: { branding: { primary_color: '#FFFFFF' } } }
55
+ allow_any_instance_of(Knock::Client).to receive(:put_request)
56
+ .with({ auth: true,
57
+ body: body, path: '/v1/tenants/tenant_id' })
58
+ .and_return('request')
59
+ end
60
+ it 'sends the correct parameters to the tenants API' do
61
+ tenant_data = { name: 'My tenant', settings: { branding: { primary_color: '#FFFFFF' } } }
62
+ Knock::Tenants.set(id: 'tenant_id', tenant_data: tenant_data)
63
+ end
64
+ end
65
+ end
66
+ # rubocop:enable Metrics/BlockLength
metadata CHANGED
@@ -1,14 +1,14 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: knockapi
3
3
  version: !ruby/object:Gem::Version
4
- version: 0.4.1
4
+ version: 0.4.4
5
5
  platform: ruby
6
6
  authors:
7
7
  - Knock Labs, Inc.
8
8
  autorequire:
9
9
  bindir: bin
10
10
  cert_chain: []
11
- date: 2022-01-21 00:00:00.000000000 Z
11
+ date: 2022-07-18 00:00:00.000000000 Z
12
12
  dependencies:
13
13
  - !ruby/object:Gem::Dependency
14
14
  name: bundler
@@ -62,7 +62,9 @@ extensions: []
62
62
  extra_rdoc_files: []
63
63
  files:
64
64
  - ".github/workflows/publish.yml"
65
+ - ".github/workflows/ruby.yml"
65
66
  - ".gitignore"
67
+ - ".rubocop.yml"
66
68
  - ".ruby-version"
67
69
  - Gemfile
68
70
  - Gemfile.lock
@@ -76,11 +78,14 @@ files:
76
78
  - lib/knock/bulk_operations.rb
77
79
  - lib/knock/client.rb
78
80
  - lib/knock/errors.rb
81
+ - lib/knock/messages.rb
79
82
  - lib/knock/objects.rb
80
83
  - lib/knock/preferences.rb
84
+ - lib/knock/tenants.rb
81
85
  - lib/knock/users.rb
82
86
  - lib/knock/version.rb
83
87
  - lib/knock/workflows.rb
88
+ - spec/tenants_spec.rb
84
89
  homepage: https://github.com/knocklabs/knock-ruby
85
90
  licenses:
86
91
  - MIT
@@ -101,8 +106,9 @@ required_rubygems_version: !ruby/object:Gem::Requirement
101
106
  - !ruby/object:Gem::Version
102
107
  version: '0'
103
108
  requirements: []
104
- rubygems_version: 3.3.3
109
+ rubygems_version: 3.3.7
105
110
  signing_key:
106
111
  specification_version: 4
107
112
  summary: API client for Knock
108
- test_files: []
113
+ test_files:
114
+ - spec/tenants_spec.rb