contentful-scheduler 0.3.0 → 0.4.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- checksums.yaml +4 -4
- data/CHANGELOG.md +8 -1
- data/README.md +95 -3
- data/lib/contentful/scheduler/auth.rb +64 -0
- data/lib/contentful/scheduler/controller.rb +11 -0
- data/lib/contentful/scheduler/tasks/publish.rb +1 -1
- data/lib/contentful/scheduler/version.rb +1 -1
- data/spec/contentful/scheduler/auth_spec.rb +67 -0
- data/spec/contentful/scheduler/controller_spec.rb +18 -0
- data/spec/contentful/scheduler/queue_spec.rb +5 -45
- data/spec/contentful/scheduler/tasks/publish_spec.rb +4 -4
- data/spec/spec_helper.rb +58 -0
- metadata +5 -2
checksums.yaml
CHANGED
|
@@ -1,7 +1,7 @@
|
|
|
1
1
|
---
|
|
2
2
|
SHA1:
|
|
3
|
-
metadata.gz:
|
|
4
|
-
data.tar.gz:
|
|
3
|
+
metadata.gz: f3171ffa6b6fee5eb141d60da86e954868dbfd5e
|
|
4
|
+
data.tar.gz: 2afa33f5a560b6f330b337b10a9cd4edb2082fd1
|
|
5
5
|
SHA512:
|
|
6
|
-
metadata.gz:
|
|
7
|
-
data.tar.gz:
|
|
6
|
+
metadata.gz: 91dd5e9622d174eefaccb065e09a27d40d683b978567f795ebba156679bb624aa7eb0500ae93245186eea6756519c6178861c14b8d0d1b52fa13879db62ad818
|
|
7
|
+
data.tar.gz: ba0f65329a151445be938e9301e5710c895e0a61569afc20a83c5d2ece65864230c49bdd21de8a195a093068895db3c4af587ed59c47c3853597db625db83791
|
data/CHANGELOG.md
CHANGED
|
@@ -2,6 +2,13 @@
|
|
|
2
2
|
|
|
3
3
|
## Unreleased
|
|
4
4
|
|
|
5
|
+
## 0.4.0
|
|
6
|
+
### Fixed
|
|
7
|
+
* Fixed User Agent Header to comply with specification.
|
|
8
|
+
|
|
9
|
+
### Added
|
|
10
|
+
* Added authentication mechanisms. [#9](https://github.com/contentful/contentful-scheduler.rb/issues/9)
|
|
11
|
+
|
|
5
12
|
## 0.3.0
|
|
6
13
|
### Added
|
|
7
14
|
* Added possibility to republish already published content. [#5](https://github.com/contentful/contentful-scheduler.rb/issues/5)
|
|
@@ -9,7 +16,7 @@
|
|
|
9
16
|
## 0.2.1
|
|
10
17
|
|
|
11
18
|
### Fixed
|
|
12
|
-
*
|
|
19
|
+
* Fixed time parsing.
|
|
13
20
|
|
|
14
21
|
## 0.2.0
|
|
15
22
|
|
data/README.md
CHANGED
|
@@ -13,8 +13,7 @@ entries for scheduled publishing.
|
|
|
13
13
|
`contentful-scheduler` provides a web endpoint to receive webhook calls from Contentful.
|
|
14
14
|
|
|
15
15
|
Every time the endpoint recieves a call it looks for the value of the field defined in the configuration.
|
|
16
|
-
If the value is a time in the future
|
|
17
|
-
the entry for publishing at the specified time.
|
|
16
|
+
If the value is a time in the future it will schedule the entry for publishing at the specified time.
|
|
18
17
|
|
|
19
18
|
A background worker based on the popular `resque` gem will then proceed to actually make the publish call
|
|
20
19
|
against the Content Management API at the due time. For this the Entries you wish to publish require a
|
|
@@ -92,7 +91,10 @@ config = {
|
|
|
92
91
|
spaces: {
|
|
93
92
|
'YOUR_SPACE_ID' => {
|
|
94
93
|
publish_field: 'publishDate', # It specifies the field ID for your Publish Date in your Content Type
|
|
95
|
-
management_token: 'YOUR_TOKEN'
|
|
94
|
+
management_token: 'YOUR_TOKEN',
|
|
95
|
+
auth: { # This is optional
|
|
96
|
+
# ... content in this section will be explained in a separate section ...
|
|
97
|
+
}
|
|
96
98
|
}
|
|
97
99
|
},
|
|
98
100
|
}
|
|
@@ -153,6 +155,96 @@ Under the space settings menu choose webhook and add a new webhook pointing to `
|
|
|
153
155
|
|
|
154
156
|
Keep in mind that if you modify the defaults, the URL should be changed to the values specified in the configuration.
|
|
155
157
|
|
|
158
|
+
## Authentication
|
|
159
|
+
|
|
160
|
+
You may want to provide an additional layer of security to your scheduler server, therefore an additional option to add space based authentication is provided.
|
|
161
|
+
|
|
162
|
+
There are two available authentication methods. Static string matching and lambda validations, which will be explained in the next section.
|
|
163
|
+
|
|
164
|
+
Any of both mechanisms require you to add additional headers to your webhook set up, which can be done through the [Contentful Web App](https://app.contentful.com),
|
|
165
|
+
or through the [CMA](https://www.contentful.com/developers/docs/references/content-management-api/#/reference/webhooks/webhook/create-update-a-webhook/console/ruby).
|
|
166
|
+
|
|
167
|
+
### Authentication via static token matching
|
|
168
|
+
|
|
169
|
+
The simplest authentication mechanism, is to provide a static set of valid strings that are considered valid when found in a determined header.
|
|
170
|
+
|
|
171
|
+
For example:
|
|
172
|
+
|
|
173
|
+
```ruby
|
|
174
|
+
config = {
|
|
175
|
+
# ... the rest of the config ...
|
|
176
|
+
spaces: {
|
|
177
|
+
'my_space' => {
|
|
178
|
+
# ... the rest of the space specific configuration ...
|
|
179
|
+
auth: {
|
|
180
|
+
key: 'X-Webhook-Server-Auth-Header',
|
|
181
|
+
valid_tokens: ['some_valid_static_token']
|
|
182
|
+
}
|
|
183
|
+
}
|
|
184
|
+
}
|
|
185
|
+
}
|
|
186
|
+
```
|
|
187
|
+
|
|
188
|
+
The above example, whenever your webhook sends the `X-Webhook-Server-Auth-Header` with a value of `some_valid_static_token`,
|
|
189
|
+
it will accept the request and queue your webhook for processing.
|
|
190
|
+
|
|
191
|
+
You can provide multiple or a single token. If a single token is provided, it's not necessary to include it in an array.
|
|
192
|
+
|
|
193
|
+
### Authentication via lambda
|
|
194
|
+
|
|
195
|
+
A more complicated solution, but far more secure, is the ability to execute a lambda as the validator function.
|
|
196
|
+
This allows you define a function for authentication. This function can call an external authentication service,
|
|
197
|
+
make checks against a database or do internal processing.
|
|
198
|
+
|
|
199
|
+
The function must return a truthy/falsey value in order for the authentication to be successful/unsuccessful.
|
|
200
|
+
|
|
201
|
+
For example, we validate that the token provided is either `foo` or `bar`:
|
|
202
|
+
|
|
203
|
+
```ruby
|
|
204
|
+
config = {
|
|
205
|
+
# ... the rest of the config ...
|
|
206
|
+
spaces: {
|
|
207
|
+
'my_space' => {
|
|
208
|
+
# ... the rest of the space specific configuration ...
|
|
209
|
+
auth: {
|
|
210
|
+
key: 'X-Webhook-Server-Auth-Header',
|
|
211
|
+
validation: -> (value) { /^(foo|bar)$/ =~ value }
|
|
212
|
+
}
|
|
213
|
+
}
|
|
214
|
+
}
|
|
215
|
+
}
|
|
216
|
+
```
|
|
217
|
+
|
|
218
|
+
Or a more complicated example, checking if the header is a valid OAuth token, and then making a request to our OAuth database.
|
|
219
|
+
For this example we'll consider you have a table called `tokens` and are using [DataMapper](https://datamapper.org) as a ORM,
|
|
220
|
+
and have a `valid?` method checking if the token is not expired.
|
|
221
|
+
|
|
222
|
+
```ruby
|
|
223
|
+
config = {
|
|
224
|
+
# ... the rest of the config ...
|
|
225
|
+
spaces: {
|
|
226
|
+
'my_space' => {
|
|
227
|
+
# ... the rest of the space specific configuration ...
|
|
228
|
+
auth: {
|
|
229
|
+
key: 'X-Webhook-Server-Auth-Header',
|
|
230
|
+
validation: proc do |value|
|
|
231
|
+
return false unless /^Bearer \w+/ =~ value
|
|
232
|
+
|
|
233
|
+
token = Token.first(token: value.gsub('Bearer ', ''))
|
|
234
|
+
|
|
235
|
+
return false if token.nil?
|
|
236
|
+
|
|
237
|
+
token.valid?
|
|
238
|
+
end
|
|
239
|
+
}
|
|
240
|
+
}
|
|
241
|
+
}
|
|
242
|
+
}
|
|
243
|
+
```
|
|
244
|
+
|
|
245
|
+
If you have multiple spaces and all share the same auth strategy, you can extract the authentication method to a variable,
|
|
246
|
+
and assign it to all the applicable spaces in order to reduce the code duplication.
|
|
247
|
+
|
|
156
248
|
## Running in Heroku
|
|
157
249
|
|
|
158
250
|
Heroku offers various Redis plugins, select the one of your liking, add the credentials into your configuration, and proceed to
|
|
@@ -0,0 +1,64 @@
|
|
|
1
|
+
module Contentful
|
|
2
|
+
module Scheduler
|
|
3
|
+
class Auth
|
|
4
|
+
attr_reader :webhook
|
|
5
|
+
|
|
6
|
+
def initialize(webhook)
|
|
7
|
+
@webhook = webhook
|
|
8
|
+
end
|
|
9
|
+
|
|
10
|
+
def auth
|
|
11
|
+
return true if auth_config.nil?
|
|
12
|
+
|
|
13
|
+
return verify_key_value_config if key_value_config?
|
|
14
|
+
return verify_lambda_config if lambda_config?
|
|
15
|
+
|
|
16
|
+
false
|
|
17
|
+
end
|
|
18
|
+
|
|
19
|
+
private
|
|
20
|
+
|
|
21
|
+
def key_value_config?
|
|
22
|
+
auth_config.key?(:key) && auth_config.key?(:valid_tokens)
|
|
23
|
+
end
|
|
24
|
+
|
|
25
|
+
def verify_key_value_config
|
|
26
|
+
value = webhook.raw_headers[auth_config[:key]]
|
|
27
|
+
|
|
28
|
+
return false if value.nil?
|
|
29
|
+
|
|
30
|
+
valid_tokens = auth_config[:valid_tokens]
|
|
31
|
+
|
|
32
|
+
return valid_tokens.include?(value) if valid_tokens.is_a?(::Array)
|
|
33
|
+
valid_tokens == value
|
|
34
|
+
end
|
|
35
|
+
|
|
36
|
+
def lambda_config?
|
|
37
|
+
auth_config.key?(:key) && auth_config.key?(:validation)
|
|
38
|
+
end
|
|
39
|
+
|
|
40
|
+
def verify_lambda_config
|
|
41
|
+
value = webhook.raw_headers[auth_config[:key]]
|
|
42
|
+
|
|
43
|
+
return false if value.nil?
|
|
44
|
+
|
|
45
|
+
validation = auth_config[:validation]
|
|
46
|
+
|
|
47
|
+
return false unless validation.is_a?(::Proc)
|
|
48
|
+
|
|
49
|
+
validation[value]
|
|
50
|
+
end
|
|
51
|
+
|
|
52
|
+
def auth_config
|
|
53
|
+
::Contentful::Scheduler.config
|
|
54
|
+
.fetch(:spaces, {})
|
|
55
|
+
.fetch(space_id, {})
|
|
56
|
+
.fetch(:auth, nil)
|
|
57
|
+
end
|
|
58
|
+
|
|
59
|
+
def space_id
|
|
60
|
+
webhook.space_id
|
|
61
|
+
end
|
|
62
|
+
end
|
|
63
|
+
end
|
|
64
|
+
end
|
|
@@ -1,4 +1,5 @@
|
|
|
1
1
|
require 'contentful/webhook/listener'
|
|
2
|
+
require_relative 'auth'
|
|
2
3
|
require_relative 'queue'
|
|
3
4
|
|
|
4
5
|
module Contentful
|
|
@@ -7,6 +8,11 @@ module Contentful
|
|
|
7
8
|
def create
|
|
8
9
|
return unless webhook.entry?
|
|
9
10
|
|
|
11
|
+
if !Auth.new(webhook).auth
|
|
12
|
+
logger.warn "Skipping - Authentication failed for Space: #{webhook.space_id} - Entry: #{webhook.id}"
|
|
13
|
+
return
|
|
14
|
+
end
|
|
15
|
+
|
|
10
16
|
logger.info "Queueing - Space: #{webhook.space_id} - Entry: #{webhook.id}"
|
|
11
17
|
|
|
12
18
|
Queue.instance(logger).update_or_create(webhook)
|
|
@@ -18,6 +24,11 @@ module Contentful
|
|
|
18
24
|
def delete
|
|
19
25
|
return unless webhook.entry?
|
|
20
26
|
|
|
27
|
+
if !Auth.new(webhook).auth
|
|
28
|
+
logger.warn "Skipping - Authentication failed for Space: #{webhook.space_id} - Entry: #{webhook.id}"
|
|
29
|
+
return
|
|
30
|
+
end
|
|
31
|
+
|
|
21
32
|
logger.info "Unqueueing - Space: #{webhook.space_id} - Entry: #{webhook.id}"
|
|
22
33
|
|
|
23
34
|
Queue.instance(logger).remove(webhook)
|
|
@@ -10,7 +10,7 @@ module Contentful
|
|
|
10
10
|
client = ::Contentful::Management::Client.new(
|
|
11
11
|
token,
|
|
12
12
|
raise_errors: true,
|
|
13
|
-
application_name: 'contentful
|
|
13
|
+
application_name: 'contentful.scheduler',
|
|
14
14
|
application_version: Contentful::Scheduler::VERSION
|
|
15
15
|
)
|
|
16
16
|
client.entries.find(space_id, entry_id).publish
|
|
@@ -0,0 +1,67 @@
|
|
|
1
|
+
require 'spec_helper'
|
|
2
|
+
|
|
3
|
+
describe Contentful::Scheduler::Auth do
|
|
4
|
+
before :each do
|
|
5
|
+
Contentful::Scheduler.config = base_config
|
|
6
|
+
end
|
|
7
|
+
|
|
8
|
+
describe 'auth' do
|
|
9
|
+
context 'when no auth is provided' do
|
|
10
|
+
it 'always returns true' do
|
|
11
|
+
webhook = WebhookDouble.new('id', 'no_auth')
|
|
12
|
+
expect(described_class.new(webhook).auth).to be_truthy
|
|
13
|
+
end
|
|
14
|
+
end
|
|
15
|
+
|
|
16
|
+
context 'when providing token array auth' do
|
|
17
|
+
it 'false when key not found' do
|
|
18
|
+
webhook = WebhookDouble.new('id', 'valid_token_array')
|
|
19
|
+
expect(described_class.new(webhook).auth).to be_falsey
|
|
20
|
+
end
|
|
21
|
+
|
|
22
|
+
it 'false when key found but value not matched' do
|
|
23
|
+
webhook = WebhookDouble.new('id', 'valid_token_array', {}, {}, {'auth' => 'not_valid'})
|
|
24
|
+
expect(described_class.new(webhook).auth).to be_falsey
|
|
25
|
+
end
|
|
26
|
+
|
|
27
|
+
it 'true when key found and value matched' do
|
|
28
|
+
webhook = WebhookDouble.new('id', 'valid_token_array', {}, {}, {'auth' => 'test_1'})
|
|
29
|
+
expect(described_class.new(webhook).auth).to be_truthy
|
|
30
|
+
end
|
|
31
|
+
end
|
|
32
|
+
|
|
33
|
+
context 'when providing token string auth' do
|
|
34
|
+
it 'false when key not found' do
|
|
35
|
+
webhook = WebhookDouble.new('id', 'valid_token_string')
|
|
36
|
+
expect(described_class.new(webhook).auth).to be_falsey
|
|
37
|
+
end
|
|
38
|
+
|
|
39
|
+
it 'false when key found but value not matched' do
|
|
40
|
+
webhook = WebhookDouble.new('id', 'valid_token_string', {}, {}, {'auth' => 'not_valid'})
|
|
41
|
+
expect(described_class.new(webhook).auth).to be_falsey
|
|
42
|
+
end
|
|
43
|
+
|
|
44
|
+
it 'true when key found and value matched' do
|
|
45
|
+
webhook = WebhookDouble.new('id', 'valid_token_string', {}, {}, {'auth' => 'test_2'})
|
|
46
|
+
expect(described_class.new(webhook).auth).to be_truthy
|
|
47
|
+
end
|
|
48
|
+
end
|
|
49
|
+
|
|
50
|
+
context 'when providing lambda auth' do
|
|
51
|
+
it 'false when key not found' do
|
|
52
|
+
webhook = WebhookDouble.new('id', 'lambda_auth')
|
|
53
|
+
expect(described_class.new(webhook).auth).to be_falsey
|
|
54
|
+
end
|
|
55
|
+
|
|
56
|
+
it 'false when key found but value not matched' do
|
|
57
|
+
webhook = WebhookDouble.new('id', 'lambda_auth', {}, {}, {'auth' => 'not_valid'})
|
|
58
|
+
expect(described_class.new(webhook).auth).to be_falsey
|
|
59
|
+
end
|
|
60
|
+
|
|
61
|
+
it 'true when key found and value matched' do
|
|
62
|
+
webhook = WebhookDouble.new('id', 'lambda_auth', {}, {}, {'auth' => 'test'})
|
|
63
|
+
expect(described_class.new(webhook).auth).to be_truthy
|
|
64
|
+
end
|
|
65
|
+
end
|
|
66
|
+
end
|
|
67
|
+
end
|
|
@@ -9,6 +9,10 @@ describe Contentful::Scheduler::Controller do
|
|
|
9
9
|
let(:queue) { ::Contentful::Scheduler::Queue.instance }
|
|
10
10
|
subject { described_class.new server, logger, timeout }
|
|
11
11
|
|
|
12
|
+
before :each do
|
|
13
|
+
Contentful::Scheduler.config = base_config
|
|
14
|
+
end
|
|
15
|
+
|
|
12
16
|
describe 'events' do
|
|
13
17
|
[:create, :save, :auto_save, :unarchive].each do |event|
|
|
14
18
|
it "creates or updates webhook metadata in publish queue on #{event}" do
|
|
@@ -42,5 +46,19 @@ describe Contentful::Scheduler::Controller do
|
|
|
42
46
|
end
|
|
43
47
|
end
|
|
44
48
|
end
|
|
49
|
+
|
|
50
|
+
describe 'auth' do
|
|
51
|
+
context 'on auth failure' do
|
|
52
|
+
let(:body) { {sys: { id: 'invalid_auth', space: { sys: { id: 'valid_token_string' } } }, fields: {} } }
|
|
53
|
+
|
|
54
|
+
it 'will stop the queueing process' do
|
|
55
|
+
expect(queue).not_to receive(:update_or_create)
|
|
56
|
+
|
|
57
|
+
headers['X-Contentful-Topic'] = "ContentfulManagement.Entry.save"
|
|
58
|
+
request = RequestDummy.new(headers, body)
|
|
59
|
+
subject.respond(request, MockResponse.new).join
|
|
60
|
+
end
|
|
61
|
+
end
|
|
62
|
+
end
|
|
45
63
|
end
|
|
46
64
|
end
|
|
@@ -1,67 +1,27 @@
|
|
|
1
1
|
require 'spec_helper'
|
|
2
2
|
|
|
3
|
-
class WebhookDouble
|
|
4
|
-
attr_reader :id, :space_id, :sys, :fields
|
|
5
|
-
def initialize(id, space_id, sys = {}, fields = {})
|
|
6
|
-
@id = id
|
|
7
|
-
@space_id = space_id
|
|
8
|
-
@sys = sys
|
|
9
|
-
@fields = fields
|
|
10
|
-
end
|
|
11
|
-
end
|
|
12
|
-
|
|
13
3
|
describe Contentful::Scheduler::Queue do
|
|
14
|
-
let(:config) {
|
|
15
|
-
{
|
|
16
|
-
logger: ::Contentful::Scheduler::DEFAULT_LOGGER,
|
|
17
|
-
endpoint: ::Contentful::Scheduler::DEFAULT_ENDPOINT,
|
|
18
|
-
port: ::Contentful::Scheduler::DEFAULT_PORT,
|
|
19
|
-
redis: {
|
|
20
|
-
host: 'localhost',
|
|
21
|
-
port: 12341,
|
|
22
|
-
password: 'foobar'
|
|
23
|
-
},
|
|
24
|
-
spaces: {
|
|
25
|
-
'foo' => {
|
|
26
|
-
publish_field: 'my_field',
|
|
27
|
-
management_token: 'foo'
|
|
28
|
-
}
|
|
29
|
-
}
|
|
30
|
-
}
|
|
31
|
-
}
|
|
32
|
-
|
|
4
|
+
let(:config) { base_config }
|
|
33
5
|
subject { described_class.instance }
|
|
34
6
|
|
|
35
7
|
before :each do
|
|
36
8
|
allow(Resque).to receive(:redis=)
|
|
37
9
|
described_class.class_variable_set(:@@instance, nil)
|
|
38
|
-
|
|
10
|
+
|
|
11
|
+
::Contentful::Scheduler.class_variable_set(:@@config, base_config)
|
|
39
12
|
end
|
|
40
13
|
|
|
41
14
|
describe 'singleton' do
|
|
42
15
|
it 'creates an instance if not initialized' do
|
|
43
|
-
|
|
44
|
-
expect(queue).to be_a described_class
|
|
16
|
+
expect(subject).to be_a described_class
|
|
45
17
|
end
|
|
46
18
|
|
|
47
19
|
it 'reuses same instance' do
|
|
48
|
-
|
|
49
|
-
|
|
50
|
-
expect(queue).to eq described_class.instance
|
|
51
|
-
end
|
|
52
|
-
end
|
|
53
|
-
|
|
54
|
-
describe 'attributes' do
|
|
55
|
-
it '.config' do
|
|
56
|
-
expect(subject.config).to eq config
|
|
20
|
+
expect(subject).to eq described_class.instance
|
|
57
21
|
end
|
|
58
22
|
end
|
|
59
23
|
|
|
60
24
|
describe 'instance methods' do
|
|
61
|
-
it '#spaces' do
|
|
62
|
-
expect(subject.spaces).to eq config[:spaces]
|
|
63
|
-
end
|
|
64
|
-
|
|
65
25
|
it '#webhook_publish_field?' do
|
|
66
26
|
expect(subject.webhook_publish_field?(
|
|
67
27
|
WebhookDouble.new('bar', 'foo', {}, {'my_field' => 'something'})
|
|
@@ -21,22 +21,22 @@ describe Contentful::Scheduler::Tasks::Publish do
|
|
|
21
21
|
let(:mock_entry) { MockEntry.new }
|
|
22
22
|
|
|
23
23
|
before :each do
|
|
24
|
-
::Contentful::Scheduler.
|
|
24
|
+
::Contentful::Scheduler.config = base_config
|
|
25
25
|
end
|
|
26
26
|
|
|
27
27
|
describe 'class methods' do
|
|
28
28
|
it '::perform' do
|
|
29
29
|
expect(::Contentful::Management::Client).to receive(:new).with(
|
|
30
|
-
'
|
|
30
|
+
'foo',
|
|
31
31
|
raise_errors: true,
|
|
32
|
-
application_name: 'contentful
|
|
32
|
+
application_name: 'contentful.scheduler',
|
|
33
33
|
application_version: Contentful::Scheduler::VERSION
|
|
34
34
|
) { mock_client }
|
|
35
35
|
expect(mock_client).to receive(:entries) { mock_entries }
|
|
36
36
|
expect(mock_entries).to receive(:find).with('foo', 'bar') { mock_entry }
|
|
37
37
|
expect(mock_entry).to receive(:publish)
|
|
38
38
|
|
|
39
|
-
described_class.perform('foo', 'bar', ::Contentful::Scheduler.config[:management_token])
|
|
39
|
+
described_class.perform('foo', 'bar', ::Contentful::Scheduler.config[:spaces]['foo'][:management_token])
|
|
40
40
|
end
|
|
41
41
|
end
|
|
42
42
|
end
|
data/spec/spec_helper.rb
CHANGED
|
@@ -40,6 +40,17 @@ class RequestDummy
|
|
|
40
40
|
end
|
|
41
41
|
end
|
|
42
42
|
|
|
43
|
+
class WebhookDouble
|
|
44
|
+
attr_reader :id, :space_id, :sys, :fields, :raw_headers
|
|
45
|
+
def initialize(id, space_id, sys = {}, fields = {}, headers = {})
|
|
46
|
+
@id = id
|
|
47
|
+
@space_id = space_id
|
|
48
|
+
@sys = sys
|
|
49
|
+
@fields = fields
|
|
50
|
+
@raw_headers = headers
|
|
51
|
+
end
|
|
52
|
+
end
|
|
53
|
+
|
|
43
54
|
class Contentful::Webhook::Listener::Controllers::Wait
|
|
44
55
|
@@sleeping = false
|
|
45
56
|
|
|
@@ -54,6 +65,53 @@ class Contentful::Webhook::Listener::Controllers::Wait
|
|
|
54
65
|
end
|
|
55
66
|
end
|
|
56
67
|
|
|
68
|
+
def base_config
|
|
69
|
+
{
|
|
70
|
+
logger: ::Contentful::Scheduler::DEFAULT_LOGGER,
|
|
71
|
+
endpoint: ::Contentful::Scheduler::DEFAULT_ENDPOINT,
|
|
72
|
+
port: ::Contentful::Scheduler::DEFAULT_PORT,
|
|
73
|
+
redis: {
|
|
74
|
+
host: 'localhost',
|
|
75
|
+
port: 12341,
|
|
76
|
+
password: 'foobar'
|
|
77
|
+
},
|
|
78
|
+
spaces: {
|
|
79
|
+
'foo' => {
|
|
80
|
+
publish_field: 'my_field',
|
|
81
|
+
management_token: 'foo'
|
|
82
|
+
},
|
|
83
|
+
'no_auth' => {
|
|
84
|
+
publish_field: 'my_field',
|
|
85
|
+
management_token: 'foo'
|
|
86
|
+
},
|
|
87
|
+
'valid_token_array' => {
|
|
88
|
+
publish_field: 'my_field',
|
|
89
|
+
management_token: 'foo',
|
|
90
|
+
auth: {
|
|
91
|
+
key: 'auth',
|
|
92
|
+
valid_tokens: ['test_1']
|
|
93
|
+
}
|
|
94
|
+
},
|
|
95
|
+
'valid_token_string' => {
|
|
96
|
+
publish_field: 'my_field',
|
|
97
|
+
management_token: 'foo',
|
|
98
|
+
auth: {
|
|
99
|
+
key: 'auth',
|
|
100
|
+
valid_tokens: 'test_2'
|
|
101
|
+
}
|
|
102
|
+
},
|
|
103
|
+
'lambda_auth' => {
|
|
104
|
+
publish_field: 'my_field',
|
|
105
|
+
management_token: 'foo',
|
|
106
|
+
auth: {
|
|
107
|
+
key: 'auth',
|
|
108
|
+
validation: -> (value) { value.size == 4 }
|
|
109
|
+
}
|
|
110
|
+
}
|
|
111
|
+
}
|
|
112
|
+
}
|
|
113
|
+
end
|
|
114
|
+
|
|
57
115
|
RSpec.configure do |config|
|
|
58
116
|
config.filter_run :focus => true
|
|
59
117
|
config.run_all_when_everything_filtered = true
|
metadata
CHANGED
|
@@ -1,14 +1,14 @@
|
|
|
1
1
|
--- !ruby/object:Gem::Specification
|
|
2
2
|
name: contentful-scheduler
|
|
3
3
|
version: !ruby/object:Gem::Version
|
|
4
|
-
version: 0.
|
|
4
|
+
version: 0.4.0
|
|
5
5
|
platform: ruby
|
|
6
6
|
authors:
|
|
7
7
|
- Contentful GmbH (David Litvak Bruno0
|
|
8
8
|
autorequire:
|
|
9
9
|
bindir: bin
|
|
10
10
|
cert_chain: []
|
|
11
|
-
date: 2018-02-
|
|
11
|
+
date: 2018-02-26 00:00:00.000000000 Z
|
|
12
12
|
dependencies:
|
|
13
13
|
- !ruby/object:Gem::Dependency
|
|
14
14
|
name: contentful-webhook-listener
|
|
@@ -201,11 +201,13 @@ files:
|
|
|
201
201
|
- example/Rakefile
|
|
202
202
|
- example/config.ru
|
|
203
203
|
- lib/contentful/scheduler.rb
|
|
204
|
+
- lib/contentful/scheduler/auth.rb
|
|
204
205
|
- lib/contentful/scheduler/controller.rb
|
|
205
206
|
- lib/contentful/scheduler/queue.rb
|
|
206
207
|
- lib/contentful/scheduler/tasks.rb
|
|
207
208
|
- lib/contentful/scheduler/tasks/publish.rb
|
|
208
209
|
- lib/contentful/scheduler/version.rb
|
|
210
|
+
- spec/contentful/scheduler/auth_spec.rb
|
|
209
211
|
- spec/contentful/scheduler/controller_spec.rb
|
|
210
212
|
- spec/contentful/scheduler/queue_spec.rb
|
|
211
213
|
- spec/contentful/scheduler/tasks/publish_spec.rb
|
|
@@ -236,6 +238,7 @@ signing_key:
|
|
|
236
238
|
specification_version: 4
|
|
237
239
|
summary: Customizable Scheduler for Contentful Entries.
|
|
238
240
|
test_files:
|
|
241
|
+
- spec/contentful/scheduler/auth_spec.rb
|
|
239
242
|
- spec/contentful/scheduler/controller_spec.rb
|
|
240
243
|
- spec/contentful/scheduler/queue_spec.rb
|
|
241
244
|
- spec/contentful/scheduler/tasks/publish_spec.rb
|