acfs 1.3.2 → 1.3.3

Sign up to get free protection for your applications and to get access to all the features.
Files changed (96) hide show
  1. checksums.yaml +4 -4
  2. metadata +8 -141
  3. data/CHANGELOG.md +0 -325
  4. data/LICENSE +0 -22
  5. data/README.md +0 -334
  6. data/acfs.gemspec +0 -37
  7. data/lib/acfs.rb +0 -49
  8. data/lib/acfs/adapter/base.rb +0 -26
  9. data/lib/acfs/adapter/typhoeus.rb +0 -60
  10. data/lib/acfs/collection.rb +0 -27
  11. data/lib/acfs/collections/paginatable.rb +0 -75
  12. data/lib/acfs/configuration.rb +0 -113
  13. data/lib/acfs/errors.rb +0 -106
  14. data/lib/acfs/global.rb +0 -99
  15. data/lib/acfs/location.rb +0 -78
  16. data/lib/acfs/middleware/base.rb +0 -20
  17. data/lib/acfs/middleware/json.rb +0 -27
  18. data/lib/acfs/middleware/logger.rb +0 -23
  19. data/lib/acfs/middleware/msgpack.rb +0 -30
  20. data/lib/acfs/middleware/print.rb +0 -21
  21. data/lib/acfs/middleware/serializer.rb +0 -39
  22. data/lib/acfs/operation.rb +0 -81
  23. data/lib/acfs/request.rb +0 -36
  24. data/lib/acfs/request/callbacks.rb +0 -50
  25. data/lib/acfs/resource.rb +0 -37
  26. data/lib/acfs/resource/attributes.rb +0 -268
  27. data/lib/acfs/resource/attributes/base.rb +0 -28
  28. data/lib/acfs/resource/attributes/boolean.rb +0 -37
  29. data/lib/acfs/resource/attributes/date_time.rb +0 -31
  30. data/lib/acfs/resource/attributes/dict.rb +0 -37
  31. data/lib/acfs/resource/attributes/float.rb +0 -31
  32. data/lib/acfs/resource/attributes/integer.rb +0 -27
  33. data/lib/acfs/resource/attributes/list.rb +0 -34
  34. data/lib/acfs/resource/attributes/string.rb +0 -24
  35. data/lib/acfs/resource/attributes/uuid.rb +0 -47
  36. data/lib/acfs/resource/dirty.rb +0 -35
  37. data/lib/acfs/resource/initialization.rb +0 -29
  38. data/lib/acfs/resource/loadable.rb +0 -33
  39. data/lib/acfs/resource/locatable.rb +0 -128
  40. data/lib/acfs/resource/operational.rb +0 -22
  41. data/lib/acfs/resource/persistence.rb +0 -257
  42. data/lib/acfs/resource/query_methods.rb +0 -264
  43. data/lib/acfs/resource/service.rb +0 -42
  44. data/lib/acfs/resource/validation.rb +0 -37
  45. data/lib/acfs/response.rb +0 -28
  46. data/lib/acfs/response/formats.rb +0 -25
  47. data/lib/acfs/response/status.rb +0 -31
  48. data/lib/acfs/rspec.rb +0 -11
  49. data/lib/acfs/runner.rb +0 -97
  50. data/lib/acfs/service.rb +0 -91
  51. data/lib/acfs/service/middleware.rb +0 -56
  52. data/lib/acfs/service/middleware/stack.rb +0 -63
  53. data/lib/acfs/singleton_resource.rb +0 -83
  54. data/lib/acfs/stub.rb +0 -172
  55. data/lib/acfs/util.rb +0 -20
  56. data/lib/acfs/version.rb +0 -14
  57. data/lib/acfs/yard.rb +0 -5
  58. data/spec/acfs/adapter/typhoeus_spec.rb +0 -28
  59. data/spec/acfs/collection_spec.rb +0 -155
  60. data/spec/acfs/configuration_spec.rb +0 -51
  61. data/spec/acfs/global_spec.rb +0 -137
  62. data/spec/acfs/location_spec.rb +0 -23
  63. data/spec/acfs/middleware/json_spec.rb +0 -63
  64. data/spec/acfs/middleware/msgpack_spec.rb +0 -60
  65. data/spec/acfs/operation_spec.rb +0 -10
  66. data/spec/acfs/request/callbacks_spec.rb +0 -46
  67. data/spec/acfs/request_spec.rb +0 -77
  68. data/spec/acfs/resource/attributes/boolean_spec.rb +0 -56
  69. data/spec/acfs/resource/attributes/date_time_spec.rb +0 -49
  70. data/spec/acfs/resource/attributes/dict_spec.rb +0 -75
  71. data/spec/acfs/resource/attributes/float_spec.rb +0 -59
  72. data/spec/acfs/resource/attributes/integer_spec.rb +0 -34
  73. data/spec/acfs/resource/attributes/list_spec.rb +0 -58
  74. data/spec/acfs/resource/attributes/uuid_spec.rb +0 -40
  75. data/spec/acfs/resource/attributes_spec.rb +0 -179
  76. data/spec/acfs/resource/dirty_spec.rb +0 -47
  77. data/spec/acfs/resource/initialization_spec.rb +0 -30
  78. data/spec/acfs/resource/loadable_spec.rb +0 -20
  79. data/spec/acfs/resource/locatable_spec.rb +0 -116
  80. data/spec/acfs/resource/persistance_spec.rb +0 -316
  81. data/spec/acfs/resource/query_methods_spec.rb +0 -541
  82. data/spec/acfs/resource/validation_spec.rb +0 -127
  83. data/spec/acfs/response/formats_spec.rb +0 -50
  84. data/spec/acfs/response/status_spec.rb +0 -69
  85. data/spec/acfs/runner_spec.rb +0 -97
  86. data/spec/acfs/service/middleware_spec.rb +0 -33
  87. data/spec/acfs/service_spec.rb +0 -46
  88. data/spec/acfs/singleton_resource_spec.rb +0 -15
  89. data/spec/acfs/stub_spec.rb +0 -343
  90. data/spec/acfs_spec.rb +0 -203
  91. data/spec/fixtures/config.yml +0 -14
  92. data/spec/spec_helper.rb +0 -41
  93. data/spec/support/hash.rb +0 -9
  94. data/spec/support/response.rb +0 -10
  95. data/spec/support/service.rb +0 -91
  96. data/spec/support/shared/find_callbacks.rb +0 -48
data/LICENSE DELETED
@@ -1,22 +0,0 @@
1
- Copyright (c) 2013 Jan Graichen
2
-
3
- MIT License
4
-
5
- Permission is hereby granted, free of charge, to any person obtaining
6
- a copy of this software and associated documentation files (the
7
- "Software"), to deal in the Software without restriction, including
8
- without limitation the rights to use, copy, modify, merge, publish,
9
- distribute, sublicense, and/or sell copies of the Software, and to
10
- permit persons to whom the Software is furnished to do so, subject to
11
- the following conditions:
12
-
13
- The above copyright notice and this permission notice shall be
14
- included in all copies or substantial portions of the Software.
15
-
16
- THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
17
- EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
18
- MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
19
- NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE
20
- LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION
21
- OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION
22
- WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
data/README.md DELETED
@@ -1,334 +0,0 @@
1
- # Acfs - *API client for services*
2
-
3
- [![Gem Version](https://badge.fury.io/rb/acfs.svg)](http://badge.fury.io/rb/acfs)
4
- [![Build Status](http://img.shields.io/travis/jgraichen/acfs/master.svg)](https://travis-ci.org/jgraichen/acfs)
5
- [![Coverage Status](http://img.shields.io/coveralls/jgraichen/acfs/master.svg)](https://coveralls.io/r/jgraichen/acfs)
6
- [![RubyDoc Documentation](http://img.shields.io/badge/rubydoc-here-blue.svg)](http://rubydoc.info/github/jgraichen/acfs/master/frames)
7
-
8
- Acfs is a library to develop API client libraries for single services within a larger service oriented application.
9
-
10
- Acfs covers model and service abstraction, convenient query and filter methods, full middleware stack for pre-processing requests and responses on a per service level and automatic request queuing and parallel processing. See Usage for more.
11
-
12
- ## Installation
13
-
14
- Add this line to your application's Gemfile:
15
-
16
- gem 'acfs', '~> 1.3'
17
-
18
- And then execute:
19
-
20
- > bundle
21
-
22
- Or install it yourself as:
23
-
24
- > gem install acfs
25
-
26
- ## Usage
27
-
28
- First you need to define your service(s):
29
-
30
- ```ruby
31
- class UserService < Acfs::Service
32
- self.base_url = 'http://users.myapp.org'
33
-
34
- # You can configure middlewares you want to use for the service here.
35
- # Each service has it own middleware stack.
36
- #
37
- use Acfs::Middleware::JsonDecoder
38
- use Acfs::Middleware::MessagePackDecoder
39
- end
40
- ```
41
-
42
- This specifies where the `UserService` is located. You can now create some models representing resources served by the `UserService`.
43
-
44
- ```ruby
45
- class User < Acfs::Resource
46
- service UserService # Associate `User` model with `UserService`.
47
-
48
- # Define model attributes and types
49
- # Types are needed to parse and generate request and response payload.
50
-
51
- attribute :id, :uuid # Types can be classes or symbols.
52
- # Symbols will be used to load a class from `Acfs::Model::Attributes` namespace.
53
- # Eg. `:uuid` will load class `Acfs::Model::Attributes::Uuid`.
54
-
55
- attribute :name, :string, default: 'Anonymous'
56
- attribute :age, ::Acfs::Model::Attributes::Integer # Or use :integer
57
-
58
- end
59
- ```
60
-
61
- The service and model classes can be shipped as a gem or git submodule to be included by the frontend application(s).
62
-
63
- You can use the model there:
64
-
65
- ```ruby
66
- @user = User.find 14
67
-
68
- @user.loaded? #=> false
69
-
70
- Acfs.run # This will run all queued request as parallel as possible.
71
- # For @user the following URL will be requested:
72
- # `http://users.myapp.org/users/14`
73
-
74
- @model.name # => "..."
75
-
76
- @users = User.all
77
- @users.loaded? #=> false
78
-
79
- Acfs.run # Will request `http://users.myapp.org/users`
80
-
81
- @users #=> [<User>, ...]
82
- ```
83
-
84
- If you need multiple resources or dependent resources first define a "plan" how they can be loaded:
85
-
86
- ```ruby
87
- @user = User.find(5) do |user|
88
- # Block will be executed right after user with id 5 is loaded
89
-
90
- # You can load additional resources also from other services
91
- # Eg. fetch comments from `CommentSerivce`. The line below will
92
- # load comments from `http://comments.myapp.org/comments?user=5`
93
- @comments = Comment.where user: user.id
94
-
95
- # You can load multiple resources in parallel if you have multiple
96
- # ids.
97
- @friends = User.find 1, 4, 10 do |friends|
98
- # This block will be executed when all friends are loaded.
99
- # [ ... ]
100
- end
101
- end
102
-
103
- Acfs.run # This call will fire all request as parallel as possible.
104
- # The sequence above would look similar to:
105
- #
106
- # Start Fin
107
- # |===================| `Acfs.run`
108
- # |====| /users/5
109
- # | |==============| /comments?user=5
110
- # | |======| /users/1
111
- # | |=======| /users/4
112
- # | |======| /users/10
113
-
114
- # Now we can access all resources:
115
-
116
- @user.name # => "John
117
- @comments.size # => 25
118
- @friends[0].name # => "Miraculix"
119
- ```
120
-
121
- Use `.find_by` to get first element only. `.find_by` will call the `index`-Action and return the first resource. Optionally passed params will be sent as `GET` parameters and can be used for filtering in the service's controller.
122
- ```ruby
123
- @user = User.find_by age: 24
124
-
125
- Acfs.run # Will request `http://users.myapp.org/users?age=24`
126
-
127
- @user # Contains the first user object returned by the index action
128
- ```
129
- If no object can be found, `.find_by` will return `nil`. The optional callback will then be called with `nil` as parameter. Use `.find_by!` to raise an `Acfs::ResourceNotFound` exception if no object can be found. `.find_by!` will only invoke the optional callback if an object was successfully loaded.
130
-
131
- Acfs has basic update support using `PUT` requests:
132
-
133
- ```ruby
134
- @user = User.find 5
135
- @user.name = "Bob"
136
-
137
- @user.changed? # => true
138
- @user.persisted? # => false
139
-
140
- @user.save # Or .save!
141
- # Will PUT new resource to service synchronously.
142
-
143
- @user.changed? # => false
144
- @user.persisted? # => true
145
- ```
146
-
147
- ## Singleton resources
148
-
149
- Singletons can be used in Acfs by creating a new resource which inherits from `SingletonResource`:
150
-
151
- ```ruby
152
- class Single < Acfs::SingletonResource
153
- service UserService # Associate `Single` model with `UserService`.
154
-
155
- # Define model attributes and types as with regular resources
156
-
157
- attribute :name, :string, default: 'Anonymous'
158
- attribute :age, :integer
159
-
160
- end
161
- ```
162
-
163
- The following code explains the routing for singleton resource requests:
164
-
165
- ```ruby
166
- my_single = Single.new
167
- mysingle.save # sends POST request to /single
168
-
169
- my_single = Single.find
170
- Acfs.run # sends GET request to /single
171
-
172
- my_single.age = 28
173
- my_single.save # sends PUT request to /single
174
-
175
- my_single.delete # sends DELETE request to /single
176
- ```
177
-
178
- You also can pass parameters to the find call, these will sent as GET params to the index action:
179
-
180
- ```ruby
181
- my_single = Single.find name: 'Max'
182
- Acfs.run # sends GET request with param to /single?name=Max
183
- ```
184
-
185
- ## Resource Inheritance
186
-
187
- Acfs provides a resource inheritance similar to ActiveRecord Single Table Inheritance. If a
188
- `type` attribute exists and is a valid subclass of your resource they will be converted
189
- to you subclassed resources:
190
-
191
- ```ruby
192
- class Computer < Acfs::Resource
193
- ...
194
- end
195
-
196
- class Pc < Computer end
197
- class Mac < Computer end
198
- ```
199
-
200
- With the following response on `GET /computers` the collection will contain the appropriate
201
- subclass resources:
202
-
203
- ```json
204
- [
205
- { "id": 5, "type": "Computer"},
206
- { "id": 6, "type": "Mac"},
207
- { "id": 8, "type": "Pc"}
208
- ]
209
- ```
210
-
211
- ```ruby
212
- @computers = Computer.all
213
-
214
- Acfs.run
215
-
216
- @computer[0].class # => Computer
217
- @computer[1].class # => Mac
218
- @computer[2].class # => Pc
219
- ```
220
-
221
- ## Stubbing
222
-
223
- You can stub resources in applications using an Acfs service client:
224
-
225
- ```ruby
226
- # spec_helper.rb
227
-
228
- # This will enable stabs before each spec and clear internal state
229
- # after each spec.
230
- require 'acfs/rspec'
231
- ```
232
-
233
- ```ruby
234
- before do
235
- @stub = Acfs::Stub.resource MyUser, :read, with: { id: 1 }, return: { id: 1, name: 'John Smith', age: 32 }
236
- Acfs::Stub.resource MyUser, :read, with: { id: 2 }, raise: :not_found
237
- Acfs::Stub.resource Session, :create, with: { ident: 'john@exmaple.org', password: 's3cr3t' }, return: { id: 'longhash', user: 1 }
238
- Acfs::Stub.resource MyUser, :update, with: lambda { |op| op.data.include? :my_var }, raise: 400
239
- end
240
-
241
- it 'should find user number one' do
242
- user = MyUser.find 1
243
- Acfs.run
244
-
245
- expect(user.id).to be == 1
246
- expect(user.name).to be == 'John Smith'
247
- expect(user.age).to be == 32
248
-
249
- expect(@stub).to be_called
250
- expect(@stub).to_not be_called 5.times
251
- end
252
-
253
- it 'should not find user number two' do
254
- MyUser.find 3
255
-
256
- expect { Acfs.run }.to raise_error(Acfs::ResourceNotFound)
257
- end
258
-
259
- it 'should allow stub resource creation' do
260
- session = Session.create! ident: 'john@exmaple.org', password: 's3cr3t'
261
-
262
- expect(session.id).to be == 'longhash'
263
- expect(session.user).to be == 1
264
- end
265
- ```
266
-
267
- By default Acfs raises an error when a non stubbed resource should be requested. You can switch of the behavior:
268
-
269
- ```ruby
270
- before do
271
- Acfs::Stub.allow_requests = true
272
- end
273
-
274
- it 'should find user number one' do
275
- user = MyUser.find 1
276
- Acfs.run # Would have raised Acfs::RealRequestNotAllowedError
277
- # Will run real request to user service instead.
278
- end
279
- ```
280
-
281
- ## Instrumentation
282
-
283
- Acfs supports [instrumentation via active support][1].
284
-
285
- Acfs expose to following events
286
-
287
- * `acfs.operation.complete(operation, response)`: Acfs operation completed
288
- * `acfs.runner.sync_run(operation)`: Run operation right now skipping queue.
289
- * `acfs.runner.enqueue(operation)`: Enqueue operation to be run later.
290
- * `acfs.before_run`: directly before `acfs.run`
291
- * `acfs.run`: Run all queued operations.
292
-
293
- Read [official guide][2] to see to to subscribe.
294
-
295
- [1]: http://guides.rubyonrails.org/active_support_instrumentation.html
296
- [2]: http://guides.rubyonrails.org/active_support_instrumentation.html#subscribing-to-an-event
297
-
298
- ## Roadmap
299
-
300
- * Update
301
- * Better new? detection eg. storing ETag from request resources.
302
- * Use PATCH for with only changed attributes and `If-Unmodifed-Since`
303
- and `If-Match` header fields if resource was surly loaded from service
304
- and not created with an id (e.g `User.new id: 5, name: "john"`).
305
- * Conflict detection (ETag / If-Unmodified-Since)
306
- * High level features
307
- * Support for custom mime types on client and server side. (`application/vnd.myservice.user.v2+msgpack`)
308
- * Server side components
309
- * Reusing model definitions for generating responses?
310
- * Rails responders providing REST operations with integrated ETag,
311
- Modified Headers, conflict detection, ...
312
- * Documentation
313
-
314
- ## Contributing
315
-
316
- 1. Fork it
317
- 2. Create your feature branch (`git checkout -b my-new-feature`)
318
- 4. Add specs for your feature
319
- 5. Implement your feature
320
- 6. Commit your changes (`git commit -am 'Add some feature'`)
321
- 7. Push to the branch (`git push origin my-new-feature`)
322
- 8. Create new Pull Request
323
-
324
- ## Contributors
325
-
326
- * [Nicolas Fricke](https://github.com/nicolas-fricke)
327
- * [Tino Junge](https://github.com/tino-junge)
328
- * [Malte Swart](https://github.com/mswart)
329
-
330
- ## License
331
-
332
- MIT License
333
-
334
- Copyright (c) 2013 Jan Graichen. MIT license, see LICENSE for more details.
@@ -1,37 +0,0 @@
1
- # coding: utf-8
2
- lib = File.expand_path('../lib', __FILE__)
3
- $LOAD_PATH.unshift(lib) unless $LOAD_PATH.include?(lib)
4
- require 'acfs/version'
5
-
6
- Gem::Specification.new do |spec|
7
- spec.name = 'acfs'
8
- spec.version = Acfs::VERSION
9
- spec.authors = ['Jan Graichen']
10
- spec.email = %w(jg@altimos.de)
11
- spec.description = 'API Client For Services'
12
- spec.summary = 'An abstract API base client for service oriented application.'
13
- spec.homepage = 'https://github.com/jgraichen/acfs'
14
- spec.license = 'MIT'
15
-
16
- spec.files = Dir['**/*'].grep(%r{^((bin|lib|test|spec|features)/|.*\.gemspec|.*LICENSE.*|.*README.*|.*CHANGELOG.*)})
17
- spec.executables = spec.files.grep(%r{^bin/}) {|f| File.basename(f) }
18
- spec.test_files = spec.files.grep(%r{^(test|spec|features)/})
19
- spec.require_paths = %w(lib)
20
-
21
- spec.add_runtime_dependency 'activesupport', '>= 4.2'
22
- spec.add_runtime_dependency 'activemodel', '>= 4.2'
23
- spec.add_runtime_dependency 'actionpack', '>= 4.2'
24
- spec.add_runtime_dependency 'multi_json'
25
-
26
- # Bundle update w/o version resolves to 0.3.3 ...
27
- spec.add_runtime_dependency 'typhoeus', '~> 1.0'
28
-
29
- spec.add_runtime_dependency 'rack'
30
-
31
- spec.add_development_dependency 'bundler'
32
-
33
- if ENV['TRAVIS_BUILD_NUMBER'] && !ENV['TRAVIS_TAG']
34
- # Append travis build number for auto-releases
35
- spec.version = "#{spec.version}.1.b#{ENV['TRAVIS_BUILD_NUMBER']}"
36
- end
37
- end
@@ -1,49 +0,0 @@
1
- require 'active_support'
2
- require 'active_support/core_ext/hash'
3
- require 'active_support/core_ext/class'
4
- require 'active_support/core_ext/string'
5
- require 'active_support/core_ext/module'
6
- require 'active_support/notifications'
7
-
8
- module Acfs
9
- extend ActiveSupport::Autoload
10
- require 'acfs/version'
11
- require 'acfs/errors'
12
- require 'acfs/global'
13
- require 'acfs/util'
14
-
15
- require 'acfs/collection'
16
- require 'acfs/configuration'
17
- require 'acfs/location'
18
- require 'acfs/operation'
19
- require 'acfs/request'
20
- require 'acfs/resource'
21
- require 'acfs/response'
22
- require 'acfs/runner'
23
- require 'acfs/service'
24
- require 'acfs/singleton_resource'
25
-
26
- extend Global
27
-
28
- autoload :Stub
29
-
30
- module Middleware
31
- extend ActiveSupport::Autoload
32
- require 'acfs/middleware/base'
33
- require 'acfs/middleware/serializer'
34
-
35
- autoload :Print
36
- autoload :Logger
37
- autoload :JSON
38
- autoload :JsonDecoder, 'acfs/middleware/json'
39
- autoload :JsonEncoder, 'acfs/middleware/json'
40
- autoload :MessagePack, 'acfs/middleware/msgpack'
41
- autoload :MessagePackDecoder, 'acfs/middleware/msgpack'
42
- autoload :MessagePackEncoder, 'acfs/middleware/msgpack'
43
- end
44
-
45
- module Adapter
46
- require 'acfs/adapter/base'
47
- require 'acfs/adapter/typhoeus'
48
- end
49
- end
@@ -1,26 +0,0 @@
1
- module Acfs::Adapter
2
- # Base adapter handling operation queuing
3
- # and processing.
4
- #
5
- class Base
6
- # Start processing queued requests.
7
- #
8
- def start
9
- end
10
-
11
- # Abort running and queued requests.
12
- #
13
- def abort
14
- end
15
-
16
- # Run request right now skipping queue.
17
- #
18
- def run(_)
19
- end
20
-
21
- # Enqueue request to be run later.
22
- #
23
- def queue(_)
24
- end
25
- end
26
- end