materialist 0.0.2 → 0.0.3
Sign up to get free protection for your applications and to get access to all the features.
- checksums.yaml +4 -4
- data/.gitignore +1 -0
- data/Gemfile +0 -22
- data/README.md +55 -4
- data/lib/materialist/errors.rb +3 -0
- data/lib/materialist/materialized_record.rb +17 -10
- data/lib/materialist/materializer.rb +10 -1
- data/lib/materialist.rb +1 -1
- data/materialist.gemspec +10 -0
- data/spec/materialist/materialized_record_spec.rb +111 -0
- data/spec/materialist/materializer_spec.rb +40 -0
- data/spec/spec_helper.rb +0 -1
- metadata +129 -3
- data/Gemfile.lock +0 -165
checksums.yaml
CHANGED
@@ -1,7 +1,7 @@
|
|
1
1
|
---
|
2
2
|
SHA1:
|
3
|
-
metadata.gz:
|
4
|
-
data.tar.gz:
|
3
|
+
metadata.gz: 1816eac41c61b0649d368f678affea67e2e58b01
|
4
|
+
data.tar.gz: 326dee47ecc2f228212ffd474b153eb2bd5de7b9
|
5
5
|
SHA512:
|
6
|
-
metadata.gz:
|
7
|
-
data.tar.gz:
|
6
|
+
metadata.gz: 9443b581e97f752ef7d70922d38625e1019f825bb3bd9abcd0522143de8bea8cd947d0c7fa01b5abdf534611ccf24a3937c353e8e3b8e916edfe3efa976de16d
|
7
|
+
data.tar.gz: acd16b5c0a34c3b2be365223f67d92c5506c927f0fd47efc7be3db48118810eb0b764395d30f66ef7288da75741b7e71be88b4caf3274eba873e56e0e3a5057a
|
data/.gitignore
CHANGED
data/Gemfile
CHANGED
@@ -2,25 +2,3 @@ source 'https://rubygems.org'
|
|
2
2
|
|
3
3
|
# Specify your gem's dependencies in routemaster_client.gemspec
|
4
4
|
gemspec
|
5
|
-
|
6
|
-
gem 'activesupport'
|
7
|
-
gem 'sidekiq'
|
8
|
-
gem 'routemaster-drain', '~> 3.0'
|
9
|
-
|
10
|
-
# Just here to avoid a safety warning
|
11
|
-
gem 'psych', require: false
|
12
|
-
|
13
|
-
# Used in builds and tests
|
14
|
-
gem 'bundler', require: false
|
15
|
-
gem 'dotenv', require: false
|
16
|
-
gem 'simplecov', require: false
|
17
|
-
gem 'codecov', require: false
|
18
|
-
gem 'webmock', require: false
|
19
|
-
|
20
|
-
gem 'guard-rspec', require: false
|
21
|
-
gem 'pry', require: false
|
22
|
-
gem 'byebug', require: false
|
23
|
-
gem 'rspec', require: false
|
24
|
-
gem 'appraisal', require: false
|
25
|
-
gem 'dogstatsd', require: false
|
26
|
-
gem 'fork_break', require: false
|
data/README.md
CHANGED
@@ -8,7 +8,51 @@ materializing the remote resource (described by the event) in database.
|
|
8
8
|
This library is a set of utilities that provide both the wiring and the DSL to
|
9
9
|
painlessly do so.
|
10
10
|
|
11
|
-
###
|
11
|
+
### Install
|
12
|
+
|
13
|
+
In your `gemfile`
|
14
|
+
|
15
|
+
```ruby
|
16
|
+
gem 'materialist'
|
17
|
+
```
|
18
|
+
|
19
|
+
Then do
|
20
|
+
|
21
|
+
```bash
|
22
|
+
bundle
|
23
|
+
```
|
24
|
+
|
25
|
+
### Entity
|
26
|
+
|
27
|
+
Your materialised entity need to have a **unique** `source_url` column, alongside any other field you wish to materialise.
|
28
|
+
|
29
|
+
```ruby
|
30
|
+
class CreateZones < ActiveRecord::Migration[5.0]
|
31
|
+
def change
|
32
|
+
create_table :zones do |t|
|
33
|
+
t.integer :orderweb_id
|
34
|
+
t.string :code, null: false
|
35
|
+
t.string :name
|
36
|
+
t.string :timezone
|
37
|
+
t.string :country_name
|
38
|
+
t.string :country_iso_alpha2_code
|
39
|
+
t.string :source_url
|
40
|
+
|
41
|
+
t.timestamps
|
42
|
+
|
43
|
+
t.index :code, unique: true
|
44
|
+
t.index :source_url, unique: true
|
45
|
+
end
|
46
|
+
end
|
47
|
+
end
|
48
|
+
```
|
49
|
+
|
50
|
+
```ruby
|
51
|
+
class Zone < ApplicationRecord
|
52
|
+
end
|
53
|
+
```
|
54
|
+
|
55
|
+
### Routemaster Configuration
|
12
56
|
|
13
57
|
First you need an "event handler":
|
14
58
|
|
@@ -102,7 +146,7 @@ describes materializing from a relation of the resource. This can be nested to a
|
|
102
146
|
|
103
147
|
When inside the block of a `link` any other part of DSL can be used and will be evaluated in the context of the relation resource.
|
104
148
|
|
105
|
-
#### `after_upsert <method>`
|
149
|
+
#### `after_upsert <method>` -- also `after_destroy`
|
106
150
|
describes the name of the instance method to be invoked after a record was materialized.
|
107
151
|
|
108
152
|
```ruby
|
@@ -133,10 +177,17 @@ class Rider
|
|
133
177
|
end
|
134
178
|
```
|
135
179
|
|
136
|
-
|
180
|
+
#### DSL
|
181
|
+
|
182
|
+
- `source_link_reader <key>, via: <key> (default: none), allow_nil: true/false (default: false)`: Adds a method named `<key>` to the class giving access to the specified linked resource. If `allow_nil` is set to `false` (default) and error is raised if the resource is missing.
|
183
|
+
|
184
|
+
The above example will give you `.source`, `.city` and `.country` on any instances of `Rider`, allowing you to access remote resources.
|
137
185
|
|
138
186
|
e.g.
|
139
187
|
|
140
188
|
```ruby
|
141
|
-
Rider.last
|
189
|
+
rider = Rider.last
|
190
|
+
rider.source.name
|
191
|
+
rider.city.code
|
192
|
+
rider.country.created_at
|
142
193
|
```
|
@@ -1,4 +1,5 @@
|
|
1
1
|
require 'routemaster/api_client'
|
2
|
+
require_relative './errors'
|
2
3
|
|
3
4
|
module Materialist
|
4
5
|
module MaterializedRecord
|
@@ -8,12 +9,20 @@ module Materialist
|
|
8
9
|
end
|
9
10
|
|
10
11
|
module ClassMethods
|
11
|
-
def source_link_reader(*keys, via: nil)
|
12
|
+
def source_link_reader(*keys, via: nil, allow_nil: false)
|
12
13
|
keys.each do |key|
|
13
14
|
define_method(key) do
|
14
|
-
|
15
|
-
|
16
|
-
|
15
|
+
(via ? [via, key] : [key])
|
16
|
+
.inject(source_raw) do |res, path|
|
17
|
+
begin
|
18
|
+
(res && res.body._links.include?(path)) ?
|
19
|
+
res.send(path).show :
|
20
|
+
(allow_nil ? nil : raise(ResourceNotFound))
|
21
|
+
rescue Routemaster::Errors::ResourceNotFound
|
22
|
+
(allow_nil ? nil : raise(ResourceNotFound))
|
23
|
+
end
|
24
|
+
end
|
25
|
+
&.body
|
17
26
|
end
|
18
27
|
end
|
19
28
|
end
|
@@ -23,14 +32,12 @@ module Materialist
|
|
23
32
|
source_raw.body
|
24
33
|
end
|
25
34
|
|
26
|
-
|
27
|
-
api_client.get(source_url)
|
28
|
-
end
|
35
|
+
private
|
29
36
|
|
30
|
-
def
|
31
|
-
|
37
|
+
def source_raw
|
38
|
+
Routemaster::APIClient.new(
|
32
39
|
response_class: Routemaster::Responses::HateoasResponse
|
33
|
-
)
|
40
|
+
).get(source_url)
|
34
41
|
end
|
35
42
|
end
|
36
43
|
end
|
@@ -76,10 +76,19 @@ module Materialist
|
|
76
76
|
@options = klass.materialist_options
|
77
77
|
end
|
78
78
|
|
79
|
-
def upsert
|
79
|
+
def upsert(retry_on_race_condition: true)
|
80
80
|
upsert_record.tap do |entity|
|
81
81
|
instance.send(after_upsert, entity) if after_upsert
|
82
82
|
end
|
83
|
+
rescue ActiveRecord::RecordNotUnique, ActiveRecord::RecordInvalid
|
84
|
+
# when there is a race condition and uniqueness of :source_url
|
85
|
+
# is enforced by database index, this error is raised
|
86
|
+
# so we simply try upsert again
|
87
|
+
# if error is due to another type of uniqueness constraint
|
88
|
+
# second call will also fail and error would bubble up
|
89
|
+
retry_on_race_condition ?
|
90
|
+
upsert(retry_on_race_condition: false) :
|
91
|
+
raise
|
83
92
|
end
|
84
93
|
|
85
94
|
def destroy
|
data/lib/materialist.rb
CHANGED
data/materialist.gemspec
CHANGED
@@ -17,4 +17,14 @@ Gem::Specification.new do |spec|
|
|
17
17
|
spec.require_paths = %w(lib)
|
18
18
|
|
19
19
|
spec.add_runtime_dependency 'sidekiq'
|
20
|
+
spec.add_runtime_dependency 'activesupport'
|
21
|
+
spec.add_runtime_dependency 'routemaster-drain', '>= 3.0'
|
22
|
+
|
23
|
+
spec.add_development_dependency 'dotenv'
|
24
|
+
spec.add_development_dependency 'simplecov'
|
25
|
+
spec.add_development_dependency 'codecov'
|
26
|
+
spec.add_development_dependency 'webmock'
|
27
|
+
spec.add_development_dependency 'pry'
|
28
|
+
spec.add_development_dependency 'rspec'
|
29
|
+
spec.add_development_dependency 'appraisal'
|
20
30
|
end
|
@@ -10,8 +10,11 @@ RSpec.describe Materialist::MaterializedRecord do
|
|
10
10
|
include Materialist::MaterializedRecord
|
11
11
|
|
12
12
|
attr_accessor :source_url
|
13
|
+
|
13
14
|
source_link_reader :city
|
15
|
+
source_link_reader :device, allow_nil: true
|
14
16
|
source_link_reader :country, via: :city
|
17
|
+
source_link_reader :region, via: :city, allow_nil: true
|
15
18
|
end
|
16
19
|
end
|
17
20
|
|
@@ -48,17 +51,125 @@ RSpec.describe Materialist::MaterializedRecord do
|
|
48
51
|
expect(record.source.name).to eq 'jack'
|
49
52
|
expect(record.source.age).to eq 30
|
50
53
|
end
|
54
|
+
|
55
|
+
context "when remote source returns 404" do
|
56
|
+
before do
|
57
|
+
stub_request(:get, source_url).to_return(status: 404)
|
58
|
+
end
|
59
|
+
|
60
|
+
it "bubbles up routemaster error" do
|
61
|
+
expect{ record.source }.to raise_error(Routemaster::Errors::ResourceNotFound)
|
62
|
+
end
|
63
|
+
end
|
51
64
|
end
|
52
65
|
|
53
66
|
describe "simple link reader" do
|
54
67
|
it "returns the representation of the link source" do
|
55
68
|
expect(record.city.timezone).to eq 'Europe/Paris'
|
56
69
|
end
|
70
|
+
|
71
|
+
context "when linked resource returns 404" do
|
72
|
+
before do
|
73
|
+
stub_request(:get, city_url).to_return(status: 404)
|
74
|
+
end
|
75
|
+
|
76
|
+
it { expect{ record.city }.to raise_error Materialist::ResourceNotFound }
|
77
|
+
end
|
78
|
+
|
79
|
+
context "remote source is not linked to city" do
|
80
|
+
let(:source_body) {{ _links: { }, name: 'jack', age: 30 }}
|
81
|
+
|
82
|
+
it { expect{ record.city }.to raise_error Materialist::ResourceNotFound }
|
83
|
+
end
|
84
|
+
|
85
|
+
context "when nil is allowed" do
|
86
|
+
let(:device_url) { 'https://service.dev/devices/1' }
|
87
|
+
let(:source_body) {{ _links: { device: { href: device_url }}, name: 'jack', age: 30 }}
|
88
|
+
|
89
|
+
context "when linked resource returns 404" do
|
90
|
+
before do
|
91
|
+
stub_request(:get, device_url).to_return(status: 404)
|
92
|
+
end
|
93
|
+
|
94
|
+
it { expect(record.device).to be_nil }
|
95
|
+
end
|
96
|
+
|
97
|
+
context "remote source is not linked to device" do
|
98
|
+
let(:source_body) {{ _links: { }, name: 'jack', age: 30 }}
|
99
|
+
|
100
|
+
it { expect(record.device).to be_nil }
|
101
|
+
end
|
102
|
+
end
|
103
|
+
|
57
104
|
end
|
58
105
|
|
59
106
|
describe "simple link reader via another link" do
|
60
107
|
it "returns the representation of the link source" do
|
61
108
|
expect(record.country.tld).to eq 'fr'
|
62
109
|
end
|
110
|
+
|
111
|
+
context "when remote city returns 404" do
|
112
|
+
before do
|
113
|
+
stub_request(:get, city_url).to_return(status: 404)
|
114
|
+
end
|
115
|
+
|
116
|
+
it { expect{ record.country }.to raise_error Materialist::ResourceNotFound }
|
117
|
+
end
|
118
|
+
|
119
|
+
context "when remote country returns 404" do
|
120
|
+
before do
|
121
|
+
stub_request(:get, country_url).to_return(status: 404)
|
122
|
+
end
|
123
|
+
|
124
|
+
it { expect{ record.country }.to raise_error Materialist::ResourceNotFound }
|
125
|
+
end
|
126
|
+
|
127
|
+
context "remote source is not linked to city" do
|
128
|
+
let(:source_body) {{ _links: { }, name: 'jack', age: 30 }}
|
129
|
+
|
130
|
+
it { expect{ record.country }.to raise_error Materialist::ResourceNotFound }
|
131
|
+
end
|
132
|
+
|
133
|
+
context "remote city is not linked to country" do
|
134
|
+
let(:city_body) {{ _links: { }, timezone: 'Europe/Paris' }}
|
135
|
+
|
136
|
+
it { expect{ record.country }.to raise_error Materialist::ResourceNotFound }
|
137
|
+
end
|
138
|
+
|
139
|
+
context "when nil is allowed" do
|
140
|
+
|
141
|
+
context "when remote city returns 404" do
|
142
|
+
before do
|
143
|
+
stub_request(:get, city_url).to_return(status: 404)
|
144
|
+
end
|
145
|
+
|
146
|
+
it { expect(record.region).to be_nil }
|
147
|
+
end
|
148
|
+
|
149
|
+
context "remote city is not linked to region" do
|
150
|
+
let(:city_body) {{ _links: { }, timezone: 'Europe/Paris' }}
|
151
|
+
|
152
|
+
it { expect(record.region).to be_nil }
|
153
|
+
end
|
154
|
+
|
155
|
+
context "when region is defined" do
|
156
|
+
let(:region_url) { 'https://service.dev/regions/1' }
|
157
|
+
let(:city_body) {{ _links: { region: { href: region_url }}, timezone: 'Europe/Paris' }}
|
158
|
+
|
159
|
+
context "when remote region returns 404" do
|
160
|
+
before do
|
161
|
+
stub_request(:get, region_url).to_return(status: 404)
|
162
|
+
end
|
163
|
+
|
164
|
+
it { expect(record.region).to be_nil }
|
165
|
+
end
|
166
|
+
|
167
|
+
context "remote source is not linked to city" do
|
168
|
+
let(:city_body) {{ _links: {}, timezone: 'Europe/Paris' }}
|
169
|
+
|
170
|
+
it { expect(record.region).to be_nil }
|
171
|
+
end
|
172
|
+
end
|
173
|
+
end
|
63
174
|
end
|
64
175
|
end
|
@@ -49,7 +49,14 @@ RSpec.describe Materialist::Materializer do
|
|
49
49
|
end
|
50
50
|
|
51
51
|
class << self
|
52
|
+
attr_accessor :error_to_throw_once_in_find_or_initialize_by
|
53
|
+
|
52
54
|
def find_or_initialize_by(source_url:)
|
55
|
+
if(err = error_to_throw_once_in_find_or_initialize_by)
|
56
|
+
self.error_to_throw_once_in_find_or_initialize_by = nil
|
57
|
+
raise err
|
58
|
+
end
|
59
|
+
|
53
60
|
(all[source_url] || Foobar.new).tap do |record|
|
54
61
|
record.source_url = source_url
|
55
62
|
end
|
@@ -80,6 +87,11 @@ RSpec.describe Materialist::Materializer do
|
|
80
87
|
end
|
81
88
|
end
|
82
89
|
|
90
|
+
module ActiveRecord
|
91
|
+
class RecordNotUnique < StandardError; end
|
92
|
+
class RecordInvalid < StandardError; end
|
93
|
+
end
|
94
|
+
|
83
95
|
let(:country_url) { 'https://service.dev/countries/1' }
|
84
96
|
let(:country_body) {{ tld: 'fr' }}
|
85
97
|
let(:city_url) { 'https://service.dev/cities/1' }
|
@@ -134,6 +146,34 @@ RSpec.describe Materialist::Materializer do
|
|
134
146
|
end
|
135
147
|
end
|
136
148
|
|
149
|
+
context "when there is a race condition between a create and update" do
|
150
|
+
let(:error) { }
|
151
|
+
let!(:record) { Foobar.create!(source_url: source_url, name: 'mo') }
|
152
|
+
|
153
|
+
before { Foobar.error_to_throw_once_in_find_or_initialize_by = error }
|
154
|
+
|
155
|
+
[ ActiveRecord::RecordNotUnique, ActiveRecord::RecordInvalid ].each do |error_type|
|
156
|
+
context "when error of type #{error_type.name} is thrown" do
|
157
|
+
let(:error) { error_type }
|
158
|
+
|
159
|
+
it "still updates the record" do
|
160
|
+
expect{ perform }.to change { record.reload.name }
|
161
|
+
.from('mo').to('jack')
|
162
|
+
end
|
163
|
+
|
164
|
+
context "if error was thrown second time" do
|
165
|
+
before { allow(Foobar).to receive(:find_or_initialize_by).and_raise error }
|
166
|
+
|
167
|
+
it "bubbles up the error" do
|
168
|
+
expect{ perform }.to raise_error error
|
169
|
+
end
|
170
|
+
end
|
171
|
+
|
172
|
+
end
|
173
|
+
end
|
174
|
+
|
175
|
+
end
|
176
|
+
|
137
177
|
%i(create update noop).each do |action_name|
|
138
178
|
context "when action is :#{action_name}" do
|
139
179
|
let(:action) { action_name }
|
data/spec/spec_helper.rb
CHANGED
metadata
CHANGED
@@ -1,14 +1,14 @@
|
|
1
1
|
--- !ruby/object:Gem::Specification
|
2
2
|
name: materialist
|
3
3
|
version: !ruby/object:Gem::Version
|
4
|
-
version: 0.0.
|
4
|
+
version: 0.0.3
|
5
5
|
platform: ruby
|
6
6
|
authors:
|
7
7
|
- Mo Valipour
|
8
8
|
autorequire:
|
9
9
|
bindir: bin
|
10
10
|
cert_chain: []
|
11
|
-
date: 2017-09-
|
11
|
+
date: 2017-09-06 00:00:00.000000000 Z
|
12
12
|
dependencies:
|
13
13
|
- !ruby/object:Gem::Dependency
|
14
14
|
name: sidekiq
|
@@ -24,6 +24,132 @@ dependencies:
|
|
24
24
|
- - ">="
|
25
25
|
- !ruby/object:Gem::Version
|
26
26
|
version: '0'
|
27
|
+
- !ruby/object:Gem::Dependency
|
28
|
+
name: activesupport
|
29
|
+
requirement: !ruby/object:Gem::Requirement
|
30
|
+
requirements:
|
31
|
+
- - ">="
|
32
|
+
- !ruby/object:Gem::Version
|
33
|
+
version: '0'
|
34
|
+
type: :runtime
|
35
|
+
prerelease: false
|
36
|
+
version_requirements: !ruby/object:Gem::Requirement
|
37
|
+
requirements:
|
38
|
+
- - ">="
|
39
|
+
- !ruby/object:Gem::Version
|
40
|
+
version: '0'
|
41
|
+
- !ruby/object:Gem::Dependency
|
42
|
+
name: routemaster-drain
|
43
|
+
requirement: !ruby/object:Gem::Requirement
|
44
|
+
requirements:
|
45
|
+
- - ">="
|
46
|
+
- !ruby/object:Gem::Version
|
47
|
+
version: '3.0'
|
48
|
+
type: :runtime
|
49
|
+
prerelease: false
|
50
|
+
version_requirements: !ruby/object:Gem::Requirement
|
51
|
+
requirements:
|
52
|
+
- - ">="
|
53
|
+
- !ruby/object:Gem::Version
|
54
|
+
version: '3.0'
|
55
|
+
- !ruby/object:Gem::Dependency
|
56
|
+
name: dotenv
|
57
|
+
requirement: !ruby/object:Gem::Requirement
|
58
|
+
requirements:
|
59
|
+
- - ">="
|
60
|
+
- !ruby/object:Gem::Version
|
61
|
+
version: '0'
|
62
|
+
type: :development
|
63
|
+
prerelease: false
|
64
|
+
version_requirements: !ruby/object:Gem::Requirement
|
65
|
+
requirements:
|
66
|
+
- - ">="
|
67
|
+
- !ruby/object:Gem::Version
|
68
|
+
version: '0'
|
69
|
+
- !ruby/object:Gem::Dependency
|
70
|
+
name: simplecov
|
71
|
+
requirement: !ruby/object:Gem::Requirement
|
72
|
+
requirements:
|
73
|
+
- - ">="
|
74
|
+
- !ruby/object:Gem::Version
|
75
|
+
version: '0'
|
76
|
+
type: :development
|
77
|
+
prerelease: false
|
78
|
+
version_requirements: !ruby/object:Gem::Requirement
|
79
|
+
requirements:
|
80
|
+
- - ">="
|
81
|
+
- !ruby/object:Gem::Version
|
82
|
+
version: '0'
|
83
|
+
- !ruby/object:Gem::Dependency
|
84
|
+
name: codecov
|
85
|
+
requirement: !ruby/object:Gem::Requirement
|
86
|
+
requirements:
|
87
|
+
- - ">="
|
88
|
+
- !ruby/object:Gem::Version
|
89
|
+
version: '0'
|
90
|
+
type: :development
|
91
|
+
prerelease: false
|
92
|
+
version_requirements: !ruby/object:Gem::Requirement
|
93
|
+
requirements:
|
94
|
+
- - ">="
|
95
|
+
- !ruby/object:Gem::Version
|
96
|
+
version: '0'
|
97
|
+
- !ruby/object:Gem::Dependency
|
98
|
+
name: webmock
|
99
|
+
requirement: !ruby/object:Gem::Requirement
|
100
|
+
requirements:
|
101
|
+
- - ">="
|
102
|
+
- !ruby/object:Gem::Version
|
103
|
+
version: '0'
|
104
|
+
type: :development
|
105
|
+
prerelease: false
|
106
|
+
version_requirements: !ruby/object:Gem::Requirement
|
107
|
+
requirements:
|
108
|
+
- - ">="
|
109
|
+
- !ruby/object:Gem::Version
|
110
|
+
version: '0'
|
111
|
+
- !ruby/object:Gem::Dependency
|
112
|
+
name: pry
|
113
|
+
requirement: !ruby/object:Gem::Requirement
|
114
|
+
requirements:
|
115
|
+
- - ">="
|
116
|
+
- !ruby/object:Gem::Version
|
117
|
+
version: '0'
|
118
|
+
type: :development
|
119
|
+
prerelease: false
|
120
|
+
version_requirements: !ruby/object:Gem::Requirement
|
121
|
+
requirements:
|
122
|
+
- - ">="
|
123
|
+
- !ruby/object:Gem::Version
|
124
|
+
version: '0'
|
125
|
+
- !ruby/object:Gem::Dependency
|
126
|
+
name: rspec
|
127
|
+
requirement: !ruby/object:Gem::Requirement
|
128
|
+
requirements:
|
129
|
+
- - ">="
|
130
|
+
- !ruby/object:Gem::Version
|
131
|
+
version: '0'
|
132
|
+
type: :development
|
133
|
+
prerelease: false
|
134
|
+
version_requirements: !ruby/object:Gem::Requirement
|
135
|
+
requirements:
|
136
|
+
- - ">="
|
137
|
+
- !ruby/object:Gem::Version
|
138
|
+
version: '0'
|
139
|
+
- !ruby/object:Gem::Dependency
|
140
|
+
name: appraisal
|
141
|
+
requirement: !ruby/object:Gem::Requirement
|
142
|
+
requirements:
|
143
|
+
- - ">="
|
144
|
+
- !ruby/object:Gem::Version
|
145
|
+
version: '0'
|
146
|
+
type: :development
|
147
|
+
prerelease: false
|
148
|
+
version_requirements: !ruby/object:Gem::Requirement
|
149
|
+
requirements:
|
150
|
+
- - ">="
|
151
|
+
- !ruby/object:Gem::Version
|
152
|
+
version: '0'
|
27
153
|
description:
|
28
154
|
email:
|
29
155
|
- valipour@gmail.com
|
@@ -38,13 +164,13 @@ files:
|
|
38
164
|
- ".travis.yml"
|
39
165
|
- Appraisals
|
40
166
|
- Gemfile
|
41
|
-
- Gemfile.lock
|
42
167
|
- Guardfile
|
43
168
|
- LICENSE.txt
|
44
169
|
- README.md
|
45
170
|
- Rakefile
|
46
171
|
- appraise
|
47
172
|
- lib/materialist.rb
|
173
|
+
- lib/materialist/errors.rb
|
48
174
|
- lib/materialist/event_handler.rb
|
49
175
|
- lib/materialist/event_worker.rb
|
50
176
|
- lib/materialist/materialized_record.rb
|
data/Gemfile.lock
DELETED
@@ -1,165 +0,0 @@
|
|
1
|
-
PATH
|
2
|
-
remote: .
|
3
|
-
specs:
|
4
|
-
materialist (0.0.1)
|
5
|
-
sidekiq
|
6
|
-
|
7
|
-
GEM
|
8
|
-
remote: https://rubygems.org/
|
9
|
-
specs:
|
10
|
-
activesupport (5.1.3)
|
11
|
-
concurrent-ruby (~> 1.0, >= 1.0.2)
|
12
|
-
i18n (~> 0.7)
|
13
|
-
minitest (~> 5.1)
|
14
|
-
tzinfo (~> 1.1)
|
15
|
-
addressable (2.5.0)
|
16
|
-
public_suffix (~> 2.0, >= 2.0.2)
|
17
|
-
appraisal (2.2.0)
|
18
|
-
bundler
|
19
|
-
rake
|
20
|
-
thor (>= 0.14.0)
|
21
|
-
byebug (9.1.0)
|
22
|
-
codecov (0.1.10)
|
23
|
-
json
|
24
|
-
simplecov
|
25
|
-
url
|
26
|
-
coderay (1.1.1)
|
27
|
-
concurrent-ruby (1.0.5)
|
28
|
-
connection_pool (2.2.1)
|
29
|
-
crack (0.4.3)
|
30
|
-
safe_yaml (~> 1.0.0)
|
31
|
-
diff-lcs (1.3)
|
32
|
-
docile (1.1.5)
|
33
|
-
dogstatsd (2.0.0)
|
34
|
-
dotenv (2.2.1)
|
35
|
-
ethon (0.10.1)
|
36
|
-
ffi (>= 1.3.0)
|
37
|
-
faraday (0.13.1)
|
38
|
-
multipart-post (>= 1.2, < 3)
|
39
|
-
faraday_middleware (0.12.2)
|
40
|
-
faraday (>= 0.7.4, < 1.0)
|
41
|
-
ffi (1.9.18)
|
42
|
-
fork (1.0.1)
|
43
|
-
fork_break (0.1.4)
|
44
|
-
fork (= 1.0.1)
|
45
|
-
formatador (0.2.5)
|
46
|
-
guard (2.14.1)
|
47
|
-
formatador (>= 0.2.4)
|
48
|
-
listen (>= 2.7, < 4.0)
|
49
|
-
lumberjack (~> 1.0)
|
50
|
-
nenv (~> 0.1)
|
51
|
-
notiffany (~> 0.0)
|
52
|
-
pry (>= 0.9.12)
|
53
|
-
shellany (~> 0.0)
|
54
|
-
thor (>= 0.18.1)
|
55
|
-
guard-compat (1.2.1)
|
56
|
-
guard-rspec (4.7.3)
|
57
|
-
guard (~> 2.1)
|
58
|
-
guard-compat (~> 1.1)
|
59
|
-
rspec (>= 2.99.0, < 4.0)
|
60
|
-
hashdiff (0.3.2)
|
61
|
-
hashie (3.5.6)
|
62
|
-
i18n (0.8.6)
|
63
|
-
json (2.1.0)
|
64
|
-
listen (3.1.5)
|
65
|
-
rb-fsevent (~> 0.9, >= 0.9.4)
|
66
|
-
rb-inotify (~> 0.9, >= 0.9.7)
|
67
|
-
ruby_dep (~> 1.2)
|
68
|
-
lumberjack (1.0.12)
|
69
|
-
method_source (0.8.2)
|
70
|
-
minitest (5.10.3)
|
71
|
-
multipart-post (2.0.0)
|
72
|
-
nenv (0.3.0)
|
73
|
-
notiffany (0.1.1)
|
74
|
-
nenv (~> 0.1)
|
75
|
-
shellany (~> 0.0)
|
76
|
-
pry (0.10.4)
|
77
|
-
coderay (~> 1.1.0)
|
78
|
-
method_source (~> 0.8.1)
|
79
|
-
slop (~> 3.4)
|
80
|
-
psych (2.2.4)
|
81
|
-
public_suffix (2.0.5)
|
82
|
-
rack (2.0.3)
|
83
|
-
rack-protection (2.0.0)
|
84
|
-
rack
|
85
|
-
rake (12.0.0)
|
86
|
-
rb-fsevent (0.10.2)
|
87
|
-
rb-inotify (0.9.10)
|
88
|
-
ffi (>= 0.5.0, < 2)
|
89
|
-
redis (3.3.3)
|
90
|
-
redis-namespace (1.5.3)
|
91
|
-
redis (~> 3.0, >= 3.0.4)
|
92
|
-
routemaster-drain (3.0.1)
|
93
|
-
addressable
|
94
|
-
concurrent-ruby
|
95
|
-
faraday (>= 0.9.0)
|
96
|
-
faraday_middleware
|
97
|
-
hashie
|
98
|
-
rack (>= 1.4.5)
|
99
|
-
redis-namespace
|
100
|
-
typhoeus (~> 1.1)
|
101
|
-
wisper (~> 1.6.1)
|
102
|
-
rspec (3.6.0)
|
103
|
-
rspec-core (~> 3.6.0)
|
104
|
-
rspec-expectations (~> 3.6.0)
|
105
|
-
rspec-mocks (~> 3.6.0)
|
106
|
-
rspec-core (3.6.0)
|
107
|
-
rspec-support (~> 3.6.0)
|
108
|
-
rspec-expectations (3.6.0)
|
109
|
-
diff-lcs (>= 1.2.0, < 2.0)
|
110
|
-
rspec-support (~> 3.6.0)
|
111
|
-
rspec-mocks (3.6.0)
|
112
|
-
diff-lcs (>= 1.2.0, < 2.0)
|
113
|
-
rspec-support (~> 3.6.0)
|
114
|
-
rspec-support (3.6.0)
|
115
|
-
ruby_dep (1.5.0)
|
116
|
-
safe_yaml (1.0.4)
|
117
|
-
shellany (0.0.1)
|
118
|
-
sidekiq (5.0.4)
|
119
|
-
concurrent-ruby (~> 1.0)
|
120
|
-
connection_pool (~> 2.2, >= 2.2.0)
|
121
|
-
rack-protection (>= 1.5.0)
|
122
|
-
redis (~> 3.3, >= 3.3.3)
|
123
|
-
simplecov (0.15.0)
|
124
|
-
docile (~> 1.1.0)
|
125
|
-
json (>= 1.8, < 3)
|
126
|
-
simplecov-html (~> 0.10.0)
|
127
|
-
simplecov-html (0.10.2)
|
128
|
-
slop (3.6.0)
|
129
|
-
thor (0.20.0)
|
130
|
-
thread_safe (0.3.6)
|
131
|
-
typhoeus (1.3.0)
|
132
|
-
ethon (>= 0.9.0)
|
133
|
-
tzinfo (1.2.3)
|
134
|
-
thread_safe (~> 0.1)
|
135
|
-
url (0.3.2)
|
136
|
-
webmock (2.3.2)
|
137
|
-
addressable (>= 2.3.6)
|
138
|
-
crack (>= 0.3.2)
|
139
|
-
hashdiff
|
140
|
-
wisper (1.6.1)
|
141
|
-
|
142
|
-
PLATFORMS
|
143
|
-
ruby
|
144
|
-
|
145
|
-
DEPENDENCIES
|
146
|
-
activesupport
|
147
|
-
appraisal
|
148
|
-
bundler
|
149
|
-
byebug
|
150
|
-
codecov
|
151
|
-
dogstatsd
|
152
|
-
dotenv
|
153
|
-
fork_break
|
154
|
-
guard-rspec
|
155
|
-
materialist!
|
156
|
-
pry
|
157
|
-
psych
|
158
|
-
routemaster-drain (~> 3.0)
|
159
|
-
rspec
|
160
|
-
sidekiq
|
161
|
-
simplecov
|
162
|
-
webmock
|
163
|
-
|
164
|
-
BUNDLED WITH
|
165
|
-
1.15.4
|