acfs 1.3.3 → 1.6.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 +372 -0
- data/LICENSE +22 -0
- data/README.md +321 -0
- data/acfs.gemspec +38 -0
- data/lib/acfs.rb +51 -0
- data/lib/acfs/adapter/base.rb +26 -0
- data/lib/acfs/adapter/typhoeus.rb +82 -0
- data/lib/acfs/collection.rb +28 -0
- data/lib/acfs/collections/paginatable.rb +76 -0
- data/lib/acfs/configuration.rb +120 -0
- data/lib/acfs/errors.rb +147 -0
- data/lib/acfs/global.rb +101 -0
- data/lib/acfs/location.rb +76 -0
- data/lib/acfs/middleware/base.rb +24 -0
- data/lib/acfs/middleware/json.rb +31 -0
- data/lib/acfs/middleware/logger.rb +23 -0
- data/lib/acfs/middleware/msgpack.rb +32 -0
- data/lib/acfs/middleware/print.rb +23 -0
- data/lib/acfs/middleware/serializer.rb +41 -0
- data/lib/acfs/operation.rb +96 -0
- data/lib/acfs/request.rb +32 -0
- data/lib/acfs/request/callbacks.rb +54 -0
- data/lib/acfs/resource.rb +39 -0
- data/lib/acfs/resource/attributes.rb +270 -0
- data/lib/acfs/resource/attributes/base.rb +29 -0
- data/lib/acfs/resource/attributes/boolean.rb +39 -0
- data/lib/acfs/resource/attributes/date_time.rb +32 -0
- data/lib/acfs/resource/attributes/dict.rb +39 -0
- data/lib/acfs/resource/attributes/float.rb +33 -0
- data/lib/acfs/resource/attributes/integer.rb +29 -0
- data/lib/acfs/resource/attributes/list.rb +36 -0
- data/lib/acfs/resource/attributes/string.rb +26 -0
- data/lib/acfs/resource/attributes/uuid.rb +48 -0
- data/lib/acfs/resource/dirty.rb +37 -0
- data/lib/acfs/resource/initialization.rb +31 -0
- data/lib/acfs/resource/loadable.rb +35 -0
- data/lib/acfs/resource/locatable.rb +135 -0
- data/lib/acfs/resource/operational.rb +26 -0
- data/lib/acfs/resource/persistence.rb +258 -0
- data/lib/acfs/resource/query_methods.rb +266 -0
- data/lib/acfs/resource/service.rb +44 -0
- data/lib/acfs/resource/validation.rb +49 -0
- data/lib/acfs/response.rb +30 -0
- data/lib/acfs/response/formats.rb +27 -0
- data/lib/acfs/response/status.rb +33 -0
- data/lib/acfs/rspec.rb +13 -0
- data/lib/acfs/runner.rb +102 -0
- data/lib/acfs/service.rb +94 -0
- data/lib/acfs/service/middleware.rb +58 -0
- data/lib/acfs/service/middleware/stack.rb +65 -0
- data/lib/acfs/singleton_resource.rb +85 -0
- data/lib/acfs/stub.rb +199 -0
- data/lib/acfs/util.rb +22 -0
- data/lib/acfs/version.rb +16 -0
- data/lib/acfs/yard.rb +6 -0
- data/spec/acfs/adapter/typhoeus_spec.rb +55 -0
- data/spec/acfs/collection_spec.rb +157 -0
- data/spec/acfs/configuration_spec.rb +53 -0
- data/spec/acfs/global_spec.rb +140 -0
- data/spec/acfs/location_spec.rb +25 -0
- data/spec/acfs/middleware/json_spec.rb +79 -0
- data/spec/acfs/middleware/msgpack_spec.rb +62 -0
- data/spec/acfs/operation_spec.rb +12 -0
- data/spec/acfs/request/callbacks_spec.rb +48 -0
- data/spec/acfs/request_spec.rb +79 -0
- data/spec/acfs/resource/attributes/boolean_spec.rb +58 -0
- data/spec/acfs/resource/attributes/date_time_spec.rb +51 -0
- data/spec/acfs/resource/attributes/dict_spec.rb +77 -0
- data/spec/acfs/resource/attributes/float_spec.rb +61 -0
- data/spec/acfs/resource/attributes/integer_spec.rb +36 -0
- data/spec/acfs/resource/attributes/list_spec.rb +60 -0
- data/spec/acfs/resource/attributes/uuid_spec.rb +42 -0
- data/spec/acfs/resource/attributes_spec.rb +179 -0
- data/spec/acfs/resource/dirty_spec.rb +49 -0
- data/spec/acfs/resource/initialization_spec.rb +36 -0
- data/spec/acfs/resource/loadable_spec.rb +22 -0
- data/spec/acfs/resource/locatable_spec.rb +118 -0
- data/spec/acfs/resource/persistance_spec.rb +322 -0
- data/spec/acfs/resource/query_methods_spec.rb +548 -0
- data/spec/acfs/resource/validation_spec.rb +129 -0
- data/spec/acfs/response/formats_spec.rb +52 -0
- data/spec/acfs/response/status_spec.rb +71 -0
- data/spec/acfs/runner_spec.rb +95 -0
- data/spec/acfs/service/middleware_spec.rb +35 -0
- data/spec/acfs/service_spec.rb +48 -0
- data/spec/acfs/singleton_resource_spec.rb +17 -0
- data/spec/acfs/stub_spec.rb +345 -0
- data/spec/acfs_spec.rb +205 -0
- data/spec/fixtures/config.yml +14 -0
- data/spec/spec_helper.rb +42 -0
- data/spec/support/hash.rb +11 -0
- data/spec/support/response.rb +12 -0
- data/spec/support/service.rb +92 -0
- data/spec/support/shared/find_callbacks.rb +50 -0
- metadata +159 -26
@@ -0,0 +1,36 @@
|
|
1
|
+
# frozen_string_literal: true
|
2
|
+
|
3
|
+
require 'spec_helper'
|
4
|
+
|
5
|
+
describe Acfs::Resource::Attributes::Integer do
|
6
|
+
let(:type) { Acfs::Resource::Attributes::Integer.new }
|
7
|
+
|
8
|
+
describe '#cast' do
|
9
|
+
subject { -> { type.cast value } }
|
10
|
+
|
11
|
+
context 'with nil' do
|
12
|
+
let(:value) { nil }
|
13
|
+
it { expect(subject.call).to eq nil }
|
14
|
+
end
|
15
|
+
|
16
|
+
context 'with empty string' do
|
17
|
+
let(:value) { '' }
|
18
|
+
it { expect(subject.call).to eq 0 }
|
19
|
+
end
|
20
|
+
|
21
|
+
context 'with blank string' do
|
22
|
+
let(:value) { " \t" }
|
23
|
+
it { expect(subject.call).to eq 0 }
|
24
|
+
end
|
25
|
+
|
26
|
+
context 'with string' do
|
27
|
+
let(:value) { '123' }
|
28
|
+
it { expect(subject.call).to eq 123 }
|
29
|
+
end
|
30
|
+
|
31
|
+
context 'with invalid string' do
|
32
|
+
let(:value) { '123a' }
|
33
|
+
it { is_expected.to raise_error ArgumentError }
|
34
|
+
end
|
35
|
+
end
|
36
|
+
end
|
@@ -0,0 +1,60 @@
|
|
1
|
+
# frozen_string_literal: true
|
2
|
+
|
3
|
+
require 'spec_helper'
|
4
|
+
|
5
|
+
describe Acfs::Resource::Attributes::List do
|
6
|
+
let(:type) { Acfs::Resource::Attributes::List.new }
|
7
|
+
|
8
|
+
describe '#cast' do
|
9
|
+
subject { -> { type.cast value } }
|
10
|
+
|
11
|
+
context 'with nil' do
|
12
|
+
let(:value) { nil }
|
13
|
+
it { expect(subject.call).to eq nil }
|
14
|
+
end
|
15
|
+
|
16
|
+
context 'with blank string (I)' do
|
17
|
+
let(:value) { '' }
|
18
|
+
it { expect(subject.call).to eq [] }
|
19
|
+
end
|
20
|
+
|
21
|
+
context 'with blank string (II)' do
|
22
|
+
let(:value) { " \t" }
|
23
|
+
it { expect(subject.call).to eq [] }
|
24
|
+
end
|
25
|
+
|
26
|
+
context 'with array' do
|
27
|
+
let(:value) { %w[abc cde efg] }
|
28
|
+
it { expect(subject.call).to eq value }
|
29
|
+
end
|
30
|
+
|
31
|
+
context 'with convertable object (I)' do
|
32
|
+
let(:value) do
|
33
|
+
Class.new do
|
34
|
+
def to_ary
|
35
|
+
[1, 2, 3]
|
36
|
+
end
|
37
|
+
end.new
|
38
|
+
end
|
39
|
+
|
40
|
+
it { expect(subject.call).to eq [1, 2, 3] }
|
41
|
+
end
|
42
|
+
|
43
|
+
context 'with convertable object (II)' do
|
44
|
+
let(:value) do
|
45
|
+
Class.new do
|
46
|
+
def to_a
|
47
|
+
[1, 2, 3]
|
48
|
+
end
|
49
|
+
end.new
|
50
|
+
end
|
51
|
+
|
52
|
+
it { expect(subject.call).to eq [1, 2, 3] }
|
53
|
+
end
|
54
|
+
|
55
|
+
context 'with non castable object' do
|
56
|
+
let(:value) { Object.new }
|
57
|
+
it { expect(subject.call).to eq [value] }
|
58
|
+
end
|
59
|
+
end
|
60
|
+
end
|
@@ -0,0 +1,42 @@
|
|
1
|
+
# frozen_string_literal: true
|
2
|
+
|
3
|
+
require 'spec_helper'
|
4
|
+
|
5
|
+
describe Acfs::Resource::Attributes::UUID do
|
6
|
+
let(:type) { Acfs::Resource::Attributes::UUID.new }
|
7
|
+
|
8
|
+
describe '#cast' do
|
9
|
+
subject { -> { type.cast(value) } }
|
10
|
+
|
11
|
+
context 'with nil' do
|
12
|
+
let(:value) { nil }
|
13
|
+
it { expect(subject.call).to eq nil }
|
14
|
+
end
|
15
|
+
|
16
|
+
context 'with empty string' do
|
17
|
+
let(:value) { '' }
|
18
|
+
it { expect(subject.call).to eq nil }
|
19
|
+
end
|
20
|
+
|
21
|
+
context 'with blank string' do
|
22
|
+
let(:value) { " \t" }
|
23
|
+
it { expect(subject.call).to eq nil }
|
24
|
+
end
|
25
|
+
|
26
|
+
context 'with string UUID' do
|
27
|
+
let(:value) { '450b7a40-94ad-11e3-baa8-0800200c9a66' }
|
28
|
+
it { expect(subject.call).to be_a String }
|
29
|
+
it { expect(subject.call).to eq value }
|
30
|
+
end
|
31
|
+
|
32
|
+
context 'with invalid string' do
|
33
|
+
let(:value) { 'invalid string' }
|
34
|
+
it { is_expected.to raise_error TypeError, /invalid UUID/i }
|
35
|
+
end
|
36
|
+
|
37
|
+
context 'with invalid UUID' do
|
38
|
+
let(:value) { 'xxxxxxxx-yyyy-11e3-baa8-0800200c9a66' }
|
39
|
+
it { is_expected.to raise_error TypeError, /invalid UUID/i }
|
40
|
+
end
|
41
|
+
end
|
42
|
+
end
|
@@ -0,0 +1,179 @@
|
|
1
|
+
# frozen_string_literal: true
|
2
|
+
|
3
|
+
require 'spec_helper'
|
4
|
+
|
5
|
+
describe Acfs::Resource::Attributes do
|
6
|
+
let(:model) { Class.new Acfs::Resource }
|
7
|
+
let(:submodel) { Class.new model }
|
8
|
+
|
9
|
+
describe '#initialize' do
|
10
|
+
before { model.attribute :name, :string, default: 'John' }
|
11
|
+
|
12
|
+
it 'should have attribute list' do
|
13
|
+
expect(model.new.attributes).to include(:name)
|
14
|
+
end
|
15
|
+
|
16
|
+
it 'should set default attributes' do
|
17
|
+
expect(model.new.name).to be == 'John'
|
18
|
+
end
|
19
|
+
|
20
|
+
context 'with dynamic default value' do
|
21
|
+
before do
|
22
|
+
model.attribute :name, :string, default: 'John'
|
23
|
+
model.attribute :mail, :string, default: -> { "#{name}@srv.tld" }
|
24
|
+
end
|
25
|
+
|
26
|
+
it 'should set dynamic default attributes' do
|
27
|
+
expect(model.new.mail).to be == 'John@srv.tld'
|
28
|
+
end
|
29
|
+
end
|
30
|
+
end
|
31
|
+
|
32
|
+
describe '#attributes' do
|
33
|
+
before do
|
34
|
+
model.attribute :name, :string, default: 'John'
|
35
|
+
model.attribute :age, :integer, default: 25
|
36
|
+
end
|
37
|
+
|
38
|
+
it 'should return hash of all attributes' do
|
39
|
+
expect(model.new.attributes).to eq(name: 'John', age: 25)
|
40
|
+
end
|
41
|
+
end
|
42
|
+
|
43
|
+
describe '#write_attributes' do
|
44
|
+
before do
|
45
|
+
model.attribute :name, :string, default: 'John'
|
46
|
+
model.attribute :age, :integer, default: 25
|
47
|
+
model.send :define_method, :name= do |name|
|
48
|
+
write_attribute :name, "The Great #{name}"
|
49
|
+
end
|
50
|
+
end
|
51
|
+
let(:params) { {name: 'James'} }
|
52
|
+
let(:opts) { {} }
|
53
|
+
let(:m) { model.new }
|
54
|
+
let(:action) { -> { m.write_attributes(params, **opts) } }
|
55
|
+
subject { action }
|
56
|
+
|
57
|
+
it 'should update attributes' do
|
58
|
+
should change(m, :attributes)
|
59
|
+
.from(name: 'The Great John', age: 25)
|
60
|
+
.to(name: 'The Great James', age: 25)
|
61
|
+
end
|
62
|
+
|
63
|
+
context 'without non-hash params' do
|
64
|
+
let(:params) { 'James' }
|
65
|
+
|
66
|
+
it { should_not change(m, :attributes) }
|
67
|
+
its(:call) { should eq false }
|
68
|
+
end
|
69
|
+
|
70
|
+
context 'with unknown attributes' do
|
71
|
+
let(:params) { {name: 'James', born_at: 'today'} }
|
72
|
+
|
73
|
+
it { should_not raise_error }
|
74
|
+
|
75
|
+
it 'should update known attributes and store unknown' do
|
76
|
+
should change(m, :attributes)
|
77
|
+
.from(name: 'The Great John', age: 25)
|
78
|
+
.to(name: 'The Great James', age: 25, born_at: 'today')
|
79
|
+
end
|
80
|
+
|
81
|
+
context 'with unknown: :raise option' do
|
82
|
+
let(:opts) { {unknown: :raise} }
|
83
|
+
|
84
|
+
it { should raise_error(ArgumentError, /unknown attribute/i) }
|
85
|
+
|
86
|
+
it do
|
87
|
+
expect do
|
88
|
+
subject.call
|
89
|
+
rescue StandardError
|
90
|
+
true
|
91
|
+
end.to_not change(m, :attributes)
|
92
|
+
end
|
93
|
+
end
|
94
|
+
end
|
95
|
+
end
|
96
|
+
|
97
|
+
describe '#_getter_' do
|
98
|
+
before { model.attribute :name, :string, default: 'John' }
|
99
|
+
|
100
|
+
it 'should return value' do
|
101
|
+
mo = model.new
|
102
|
+
mo.name = 'Paul'
|
103
|
+
|
104
|
+
expect(mo.name).to be == 'Paul'
|
105
|
+
end
|
106
|
+
|
107
|
+
it 'should return default value' do
|
108
|
+
expect(model.new.name).to be == 'John'
|
109
|
+
end
|
110
|
+
end
|
111
|
+
|
112
|
+
describe '#_setter_' do
|
113
|
+
before do
|
114
|
+
model.attribute :name, :string, default: 'John'
|
115
|
+
model.attribute :age, :integer, default: '25'
|
116
|
+
end
|
117
|
+
|
118
|
+
it 'should set value' do
|
119
|
+
o = model.new
|
120
|
+
o.name = 'Paul'
|
121
|
+
|
122
|
+
expect(o.name).to be == 'Paul'
|
123
|
+
end
|
124
|
+
|
125
|
+
it 'should update attributes hash' do
|
126
|
+
o = model.new
|
127
|
+
o.name = 'Johannes'
|
128
|
+
|
129
|
+
expect(o.attributes['name']).to be == 'Johannes'
|
130
|
+
end
|
131
|
+
|
132
|
+
it 'should cast values' do
|
133
|
+
o = model.new
|
134
|
+
o.age = '28'
|
135
|
+
|
136
|
+
expect(o.age).to be == 28
|
137
|
+
end
|
138
|
+
end
|
139
|
+
|
140
|
+
describe 'class' do
|
141
|
+
describe '#attributes' do
|
142
|
+
it 'should add an attribute to model attribute list' do
|
143
|
+
model.send :attribute, :name, :string
|
144
|
+
|
145
|
+
expect(model.attributes.symbolize_keys).to eq name: nil
|
146
|
+
end
|
147
|
+
|
148
|
+
it 'should accept a default value' do
|
149
|
+
model.send :attribute, :name, :string, default: 'John'
|
150
|
+
|
151
|
+
expect(model.attributes.symbolize_keys).to eq name: 'John'
|
152
|
+
end
|
153
|
+
|
154
|
+
it 'should accept a symbolic type' do
|
155
|
+
model.send :attribute, :age, :integer, default: '12'
|
156
|
+
|
157
|
+
expect(model.attributes.symbolize_keys).to eq age: 12
|
158
|
+
end
|
159
|
+
|
160
|
+
it 'should accept a class type' do
|
161
|
+
model.send :attribute, :age, Acfs::Resource::Attributes::Integer,
|
162
|
+
default: '12'
|
163
|
+
|
164
|
+
expect(model.attributes.symbolize_keys).to eq age: 12
|
165
|
+
end
|
166
|
+
|
167
|
+
context 'on inherited resources' do
|
168
|
+
before do
|
169
|
+
model.attribute :age, :integer, default: 5
|
170
|
+
submodel.attribute :born_at, :date_time
|
171
|
+
end
|
172
|
+
|
173
|
+
it 'includes superclass attributes' do
|
174
|
+
expect(submodel.attributes.keys).to match_array %w[age born_at]
|
175
|
+
end
|
176
|
+
end
|
177
|
+
end
|
178
|
+
end
|
179
|
+
end
|
@@ -0,0 +1,49 @@
|
|
1
|
+
# frozen_string_literal: true
|
2
|
+
|
3
|
+
require 'spec_helper'
|
4
|
+
|
5
|
+
describe Acfs::Resource::Dirty do
|
6
|
+
let(:model) { MyUser.new }
|
7
|
+
before do
|
8
|
+
stub_request(:get, 'http://users.example.org/users/1')
|
9
|
+
.to_return response id: 1, name: 'Anon', age: 12
|
10
|
+
stub_request(:post, 'http://users.example.org/users')
|
11
|
+
.to_return response id: 5, name: 'dhh', age: 12
|
12
|
+
end
|
13
|
+
|
14
|
+
it 'includes ActiveModel::Dirty' do
|
15
|
+
model.is_a? ActiveModel::Dirty
|
16
|
+
end
|
17
|
+
|
18
|
+
describe '#changed?' do
|
19
|
+
context 'after attribute change' do
|
20
|
+
let(:user) { MyUser.new name: 'dhh' }
|
21
|
+
|
22
|
+
it { expect(user).to be_changed }
|
23
|
+
|
24
|
+
context 'and saving' do
|
25
|
+
before { user.save }
|
26
|
+
it { expect(user).to_not be_changed }
|
27
|
+
end
|
28
|
+
end
|
29
|
+
|
30
|
+
context 'after model load' do
|
31
|
+
let(:user) { MyUser.find 1 }
|
32
|
+
before { user && Acfs.run }
|
33
|
+
|
34
|
+
it { expect(user).to_not be_changed }
|
35
|
+
end
|
36
|
+
|
37
|
+
context 'after model new without attrs' do
|
38
|
+
let(:user) { MyUser.new }
|
39
|
+
|
40
|
+
it { expect(user).to_not be_changed }
|
41
|
+
end
|
42
|
+
|
43
|
+
context 'after model new with attrs' do
|
44
|
+
let(:user) { MyUser.new name: 'Uschi' }
|
45
|
+
|
46
|
+
it { expect(user).to be_changed }
|
47
|
+
end
|
48
|
+
end
|
49
|
+
end
|
@@ -0,0 +1,36 @@
|
|
1
|
+
# frozen_string_literal: true
|
2
|
+
|
3
|
+
require 'spec_helper'
|
4
|
+
|
5
|
+
describe 'Acfs::Resource::Initialization' do
|
6
|
+
let(:model) do
|
7
|
+
Class.new(Acfs::Resource).tap do |c|
|
8
|
+
c.class_eval do
|
9
|
+
attr_accessor :name
|
10
|
+
attr_reader :age
|
11
|
+
|
12
|
+
private
|
13
|
+
|
14
|
+
attr_writer :age
|
15
|
+
end
|
16
|
+
end
|
17
|
+
end
|
18
|
+
|
19
|
+
describe '#initialize' do
|
20
|
+
it 'should allow to set attributes with initializer' do
|
21
|
+
m = model.new name: 'John'
|
22
|
+
expect(m.name).to eq 'John'
|
23
|
+
end
|
24
|
+
|
25
|
+
it 'should raise error when attributes with private setters are given' do
|
26
|
+
expect { model.new age: 25 }.to raise_error(NoMethodError)
|
27
|
+
end
|
28
|
+
end
|
29
|
+
|
30
|
+
describe '#persisted?' do
|
31
|
+
subject { model.new.persisted? }
|
32
|
+
it 'should be false' do
|
33
|
+
should be false
|
34
|
+
end
|
35
|
+
end
|
36
|
+
end
|
@@ -0,0 +1,22 @@
|
|
1
|
+
# frozen_string_literal: true
|
2
|
+
|
3
|
+
require 'spec_helper'
|
4
|
+
|
5
|
+
describe Acfs::Resource::Loadable do
|
6
|
+
let(:model) { MyUser.find 1 }
|
7
|
+
before do
|
8
|
+
stub_request(:get, 'http://users.example.org/users/1')
|
9
|
+
.to_return response id: 1, name: 'Anon', age: 12
|
10
|
+
end
|
11
|
+
|
12
|
+
describe '#loaded?' do
|
13
|
+
context 'before Acfs#run' do
|
14
|
+
it { expect(model).to_not be_loaded }
|
15
|
+
end
|
16
|
+
|
17
|
+
context 'afer Acfs#run' do
|
18
|
+
before { model && Acfs.run }
|
19
|
+
it { expect(model).to be_loaded }
|
20
|
+
end
|
21
|
+
end
|
22
|
+
end
|
@@ -0,0 +1,118 @@
|
|
1
|
+
# frozen_string_literal: true
|
2
|
+
|
3
|
+
require 'spec_helper'
|
4
|
+
|
5
|
+
describe Acfs::Resource::Locatable do
|
6
|
+
let(:model) { MyUser }
|
7
|
+
before do
|
8
|
+
stub_request(:get, 'http://users.example.org/users/1')
|
9
|
+
.to_return response id: 1, name: 'Anon', age: 12
|
10
|
+
stub_request(:get, 'http://users.example.org/users/1/profile')
|
11
|
+
.to_return response user_id: 2, twitter_handle: '@anon'
|
12
|
+
end
|
13
|
+
|
14
|
+
describe '.url' do
|
15
|
+
it 'should return URL' do
|
16
|
+
expect(model.url).to be == 'http://users.example.org/users'
|
17
|
+
end
|
18
|
+
|
19
|
+
it 'should return URL with id path part if specified' do
|
20
|
+
expect(model.url(5)).to be == 'http://users.example.org/users/5'
|
21
|
+
end
|
22
|
+
|
23
|
+
context 'with attribute in path' do
|
24
|
+
let(:model) { Profile }
|
25
|
+
|
26
|
+
it 'should replace placeholder' do
|
27
|
+
expect(model.url(user_id: 1))
|
28
|
+
.to eq 'http://users.example.org/users/1/profile'
|
29
|
+
end
|
30
|
+
|
31
|
+
context 'without attributes' do
|
32
|
+
it 'should raise an error if attribute is missing' do
|
33
|
+
expect { model.url }.to raise_error ArgumentError
|
34
|
+
end
|
35
|
+
end
|
36
|
+
end
|
37
|
+
|
38
|
+
describe 'custom paths' do
|
39
|
+
let(:model) { Session }
|
40
|
+
let(:location) { Session.location action: action }
|
41
|
+
subject { location }
|
42
|
+
|
43
|
+
context ':list location' do
|
44
|
+
let(:action) { :list }
|
45
|
+
|
46
|
+
its(:raw_uri) do
|
47
|
+
should eq 'http://users.example.org/users/:user_id/sessions'
|
48
|
+
end
|
49
|
+
end
|
50
|
+
|
51
|
+
context ':create location' do
|
52
|
+
let(:action) { :create }
|
53
|
+
its(:raw_uri) { should eq 'http://users.example.org/sessions' }
|
54
|
+
end
|
55
|
+
|
56
|
+
context ':read location' do
|
57
|
+
let(:action) { :read }
|
58
|
+
its(:raw_uri) { should eq 'http://users.example.org/sessions/:id' }
|
59
|
+
end
|
60
|
+
|
61
|
+
context ':update location' do
|
62
|
+
let(:action) { :update }
|
63
|
+
its(:raw_uri) do
|
64
|
+
expect { subject }.to raise_error ArgumentError, /update.*disabled/
|
65
|
+
end
|
66
|
+
end
|
67
|
+
|
68
|
+
context ':delete location' do
|
69
|
+
let(:action) { :delete }
|
70
|
+
its(:raw_uri) do
|
71
|
+
should eq 'http://users.example.org/users/:user_id/sessions/del/:id'
|
72
|
+
end
|
73
|
+
end
|
74
|
+
end
|
75
|
+
end
|
76
|
+
|
77
|
+
describe '#url' do
|
78
|
+
context 'new resource' do
|
79
|
+
let(:m) { model.new }
|
80
|
+
|
81
|
+
it 'should return nil' do
|
82
|
+
expect(m.url).to be_nil
|
83
|
+
end
|
84
|
+
|
85
|
+
context 'new resource with id' do
|
86
|
+
let(:m) { model.new id: 475 }
|
87
|
+
|
88
|
+
it 'should return resource URL' do
|
89
|
+
expect(m.url).to eq 'http://users.example.org/users/475'
|
90
|
+
end
|
91
|
+
end
|
92
|
+
|
93
|
+
context 'with attribute in path' do
|
94
|
+
it 'should return nil' do
|
95
|
+
expect(m.url).to be_nil
|
96
|
+
end
|
97
|
+
end
|
98
|
+
end
|
99
|
+
|
100
|
+
context 'loaded resource' do
|
101
|
+
let(:m) { model.find 1 }
|
102
|
+
before { m && Acfs.run }
|
103
|
+
|
104
|
+
it "should return resource's URL" do
|
105
|
+
expect(m.url).to eq 'http://users.example.org/users/1'
|
106
|
+
end
|
107
|
+
|
108
|
+
context 'with attribute in path' do
|
109
|
+
let(:model) { Profile }
|
110
|
+
let(:m) { model.find user_id: 1 }
|
111
|
+
|
112
|
+
it "should return resource's URL" do
|
113
|
+
expect(m.url).to eq 'http://users.example.org/users/2/profile'
|
114
|
+
end
|
115
|
+
end
|
116
|
+
end
|
117
|
+
end
|
118
|
+
end
|