grape-resource-definition 0.0.2 → 0.1.0
Sign up to get free protection for your applications and to get access to all the features.
- checksums.yaml +4 -4
- data/.rspec +2 -2
- data/.ruby-gemset +1 -0
- data/.ruby-version +1 -0
- data/Gemfile +0 -1
- data/README.md +92 -2
- data/grape-resource-definition.gemspec +3 -3
- data/lib/grape_resource_definition.rb +3 -1
- data/lib/grape_resource_definition/no_resource_defined.rb +3 -0
- data/lib/grape_resource_definition/no_resource_definition.rb +3 -0
- data/lib/grape_resource_definition/resource_definition.rb +13 -13
- data/lib/grape_resource_definition/version.rb +1 -1
- data/spec/resource_definition_spec.rb +73 -12
- data/spec/spec_helper.rb +0 -5
- metadata +13 -9
checksums.yaml
CHANGED
@@ -1,7 +1,7 @@
|
|
1
1
|
---
|
2
2
|
SHA1:
|
3
|
-
metadata.gz:
|
4
|
-
data.tar.gz:
|
3
|
+
metadata.gz: 40de937f06ba2db30211deeacb679f153cd3b6b2
|
4
|
+
data.tar.gz: 13319ff6f39caf4476ea3594f7e6b8267f41d8b6
|
5
5
|
SHA512:
|
6
|
-
metadata.gz:
|
7
|
-
data.tar.gz:
|
6
|
+
metadata.gz: ff1e623402da185d3f42d78987482db0e06ee09c54c69c24821d7635d07b2add634fda3ef0357d33156c4f9fc387f18510b2f48829bfeb0d4d4c10d860671e88
|
7
|
+
data.tar.gz: f60d82e4493ce4ca34a8a2f86c57024b09026cf1f43b3ce3e94b41478408f2ea1d139059348cad0ded6069685e15e9a4fb86b969a4a4d7b7f16b02bbf9e217f4
|
data/.rspec
CHANGED
@@ -1,2 +1,2 @@
|
|
1
|
-
--
|
2
|
-
--format
|
1
|
+
--colour
|
2
|
+
--format documentation
|
data/.ruby-gemset
ADDED
@@ -0,0 +1 @@
|
|
1
|
+
grape-resource-definition
|
data/.ruby-version
ADDED
@@ -0,0 +1 @@
|
|
1
|
+
2.1.5
|
data/Gemfile
CHANGED
data/README.md
CHANGED
@@ -1,4 +1,94 @@
|
|
1
|
-
|
1
|
+
Grape::ResourceDefinition
|
2
2
|
=========================
|
3
3
|
|
4
|
-
|
4
|
+
(Still making the tests and the rest of the documentation)
|
5
|
+
|
6
|
+
Based on Praxis principle, that design and implementation should be separated, I've created this gem to add the possibility to define the params validation & coercion outside the route's class.
|
7
|
+
|
8
|
+
If you are using Grape to create a Blog API (of course), you should have something like this:
|
9
|
+
|
10
|
+
```ruby
|
11
|
+
class Posts < Grape::API
|
12
|
+
|
13
|
+
desc 'Get all blog posts',
|
14
|
+
http_codes: [
|
15
|
+
[200, 'Ok']
|
16
|
+
]
|
17
|
+
|
18
|
+
params do
|
19
|
+
optional :q, type: Hash
|
20
|
+
optional :order_by, type: String
|
21
|
+
optional :order_dir, type: String
|
22
|
+
end
|
23
|
+
|
24
|
+
get '/posts' do
|
25
|
+
# Logic to get those posts
|
26
|
+
end
|
27
|
+
|
28
|
+
end
|
29
|
+
```
|
30
|
+
|
31
|
+
If your Posts API have only this route, to get all posts, it's ok. But if you have all actions to CRUD your posts, and some more to handle your specific business logic, this will become a mess... for sure.
|
32
|
+
|
33
|
+
This was a problem for me. I like my code to be as readable as possible and, with all these documentation and params definition that we need to create ou API, this is not possible.
|
34
|
+
|
35
|
+
So.. with this gem you can define your resource definition outside your route and call it when you need it.
|
36
|
+
|
37
|
+
```ruby
|
38
|
+
module Resources
|
39
|
+
|
40
|
+
module Posts
|
41
|
+
|
42
|
+
include Grape::ResourceDefinition
|
43
|
+
|
44
|
+
resource_define :index do
|
45
|
+
|
46
|
+
desc 'Get all blog posts',
|
47
|
+
http_codes: [
|
48
|
+
[200, 'Ok']
|
49
|
+
]
|
50
|
+
|
51
|
+
params do
|
52
|
+
optional :q, type: Hash
|
53
|
+
optional :order_by, type: String
|
54
|
+
optional :order_dir, type: String
|
55
|
+
end
|
56
|
+
|
57
|
+
end
|
58
|
+
|
59
|
+
end
|
60
|
+
|
61
|
+
end
|
62
|
+
```
|
63
|
+
|
64
|
+
...and your route links to that resource:
|
65
|
+
|
66
|
+
```ruby
|
67
|
+
class Posts < Grape::API
|
68
|
+
|
69
|
+
resource_definition Resources::Posts
|
70
|
+
|
71
|
+
define :index
|
72
|
+
get '/posts' do
|
73
|
+
# Logic to get those posts
|
74
|
+
end
|
75
|
+
|
76
|
+
end
|
77
|
+
```
|
78
|
+
|
79
|
+
I've made this really simple, the rest it's up to you. I don't want to add constraints on that.
|
80
|
+
|
81
|
+
## Installation
|
82
|
+
|
83
|
+
Add this line to your application's Gemfile:
|
84
|
+
|
85
|
+
gem 'grape-resource-definition'
|
86
|
+
|
87
|
+
And then execute:
|
88
|
+
|
89
|
+
$ bundle
|
90
|
+
|
91
|
+
Or install it yourself as:
|
92
|
+
|
93
|
+
$ gem install grape-resource-definition
|
94
|
+
|
@@ -18,9 +18,9 @@ Gem::Specification.new do |gem|
|
|
18
18
|
gem.test_files = gem.files.grep(%r{^(test|spec|features)/})
|
19
19
|
gem.require_paths = ['lib']
|
20
20
|
|
21
|
-
gem.add_runtime_dependency 'grape', ['
|
21
|
+
gem.add_runtime_dependency 'grape', ['~> 0.10']
|
22
22
|
|
23
|
-
gem.add_development_dependency 'rspec', '~>
|
23
|
+
gem.add_development_dependency 'rspec', '~> 3.1'
|
24
24
|
gem.add_development_dependency 'rake', '~> 0'
|
25
25
|
gem.add_development_dependency 'pry', '~> 0'
|
26
|
-
end
|
26
|
+
end
|
@@ -5,20 +5,20 @@ module Grape
|
|
5
5
|
|
6
6
|
def definitions
|
7
7
|
model_name = Grape::ResourceDefinition.get_class_name(self)
|
8
|
-
Grape::ResourceDefinition.
|
8
|
+
Grape::ResourceDefinition.defined_resources[model_name]
|
9
9
|
end
|
10
10
|
|
11
|
-
def resource_define(name, ¶ms_block)
|
11
|
+
def resource_define(name, ¶ms_block)
|
12
12
|
definitions[name] = params_block
|
13
13
|
end
|
14
14
|
|
15
15
|
def define(name)
|
16
16
|
if definitions.nil?
|
17
|
-
raise "No
|
17
|
+
raise NoResourceDefinition, "No resource definition for #{self}"
|
18
18
|
end
|
19
|
-
|
19
|
+
|
20
20
|
if definitions[name].nil?
|
21
|
-
raise "
|
21
|
+
raise NoResourceDefined, "':#{name}' is not defined for #{self}"
|
22
22
|
end
|
23
23
|
|
24
24
|
self.instance_eval &definitions[name]
|
@@ -26,22 +26,22 @@ module Grape
|
|
26
26
|
|
27
27
|
end
|
28
28
|
|
29
|
-
def self.
|
30
|
-
@
|
29
|
+
def self.defined_resources
|
30
|
+
@defined_resources
|
31
31
|
end
|
32
|
-
|
32
|
+
|
33
33
|
def self.included(other)
|
34
34
|
model_name = get_class_name(other)
|
35
35
|
|
36
|
-
@
|
37
|
-
@
|
36
|
+
@defined_resources ||= {}
|
37
|
+
@defined_resources[model_name] = {}
|
38
38
|
|
39
39
|
other.include ClassMethods
|
40
40
|
other.extend ClassMethods
|
41
41
|
end
|
42
42
|
|
43
43
|
def self.get_class_name(klass)
|
44
|
-
klass.name.split("::")[-1].to_sym
|
44
|
+
klass.name.split("::")[-1].to_sym
|
45
45
|
end
|
46
46
|
|
47
47
|
end
|
@@ -55,6 +55,6 @@ module Grape
|
|
55
55
|
extend resource_definition_module
|
56
56
|
end
|
57
57
|
end
|
58
|
-
|
58
|
+
|
59
59
|
end
|
60
|
-
end
|
60
|
+
end
|
@@ -1,15 +1,21 @@
|
|
1
1
|
require 'pry'
|
2
2
|
require 'spec_helper'
|
3
3
|
|
4
|
-
describe Grape::ResourceDefinition do
|
4
|
+
describe Grape::ResourceDefinition do
|
5
5
|
|
6
6
|
module Resources
|
7
7
|
module Todos
|
8
|
-
|
9
8
|
include Grape::ResourceDefinition
|
10
9
|
|
11
|
-
resource_define :
|
12
|
-
desc 'Get
|
10
|
+
resource_define :index do
|
11
|
+
desc 'Get all todos',
|
12
|
+
http_codes: [
|
13
|
+
[200, 'Ok']
|
14
|
+
]
|
15
|
+
end
|
16
|
+
|
17
|
+
resource_define :show do
|
18
|
+
desc 'Get a todo by id',
|
13
19
|
http_codes: [
|
14
20
|
[200, 'Ok'],
|
15
21
|
[404, 'Not Found']
|
@@ -19,20 +25,75 @@ describe Grape::ResourceDefinition do
|
|
19
25
|
requires :id, type: Integer
|
20
26
|
end
|
21
27
|
end
|
22
|
-
|
23
28
|
end
|
24
29
|
end
|
25
30
|
|
26
|
-
|
27
|
-
|
28
|
-
|
29
|
-
|
30
|
-
|
31
|
-
|
32
|
-
|
31
|
+
context 'correct defined resource and link with resource_definition' do
|
32
|
+
|
33
|
+
subject do
|
34
|
+
class Todos < Grape::API
|
35
|
+
resource_definition Resources::Todos
|
36
|
+
|
37
|
+
define :show
|
38
|
+
get('/todos/:id') {}
|
33
39
|
end
|
34
40
|
|
41
|
+
Todos.new
|
42
|
+
end
|
43
|
+
|
44
|
+
let(:defined_resources) do
|
45
|
+
Grape::ResourceDefinition.defined_resources
|
35
46
|
end
|
47
|
+
|
48
|
+
it 'should have :Todos resource with :show definition' do
|
49
|
+
|
50
|
+
expect(defined_resources).to \
|
51
|
+
have_key(:Todos)
|
52
|
+
|
53
|
+
expect(defined_resources[:Todos]).to \
|
54
|
+
have_key(:index)
|
55
|
+
|
56
|
+
expect(defined_resources[:Todos]).to \
|
57
|
+
have_key(:show)
|
58
|
+
|
59
|
+
# expect(subject).to receive(:define).with(:show)
|
60
|
+
|
61
|
+
end
|
62
|
+
|
63
|
+
end
|
64
|
+
|
65
|
+
context 'correct defined resource but no link with resource_definition' do
|
66
|
+
|
67
|
+
it 'should raise NoMethodError for define :index' do
|
68
|
+
|
69
|
+
expect do
|
70
|
+
class Todos < Grape::API
|
71
|
+
define :index
|
72
|
+
get('/todos/:id') {}
|
73
|
+
end
|
74
|
+
end.to \
|
75
|
+
raise_error(NoMethodError, /undefined method `define'/)
|
76
|
+
|
77
|
+
end
|
78
|
+
|
79
|
+
end
|
80
|
+
|
81
|
+
context 'resource not defined but has link to resource_definition' do
|
82
|
+
|
83
|
+
it 'should raise NoResourceDefined error for define :update' do
|
84
|
+
|
85
|
+
expect do
|
86
|
+
class Todos < Grape::API
|
87
|
+
resource_definition Resources::Todos
|
88
|
+
|
89
|
+
define :update
|
90
|
+
put('/todos/:id') {}
|
91
|
+
end
|
92
|
+
end.to \
|
93
|
+
raise_error(NoResourceDefined, /':update' is not defined for Todos/)
|
94
|
+
|
95
|
+
end
|
96
|
+
|
36
97
|
end
|
37
98
|
|
38
99
|
end
|
data/spec/spec_helper.rb
CHANGED
metadata
CHANGED
@@ -1,43 +1,43 @@
|
|
1
1
|
--- !ruby/object:Gem::Specification
|
2
2
|
name: grape-resource-definition
|
3
3
|
version: !ruby/object:Gem::Version
|
4
|
-
version: 0.0
|
4
|
+
version: 0.1.0
|
5
5
|
platform: ruby
|
6
6
|
authors:
|
7
7
|
- Joaquim Adráz
|
8
8
|
autorequire:
|
9
9
|
bindir: bin
|
10
10
|
cert_chain: []
|
11
|
-
date:
|
11
|
+
date: 2015-01-29 00:00:00.000000000 Z
|
12
12
|
dependencies:
|
13
13
|
- !ruby/object:Gem::Dependency
|
14
14
|
name: grape
|
15
15
|
requirement: !ruby/object:Gem::Requirement
|
16
16
|
requirements:
|
17
|
-
- -
|
17
|
+
- - "~>"
|
18
18
|
- !ruby/object:Gem::Version
|
19
|
-
version: 0.
|
19
|
+
version: '0.10'
|
20
20
|
type: :runtime
|
21
21
|
prerelease: false
|
22
22
|
version_requirements: !ruby/object:Gem::Requirement
|
23
23
|
requirements:
|
24
|
-
- -
|
24
|
+
- - "~>"
|
25
25
|
- !ruby/object:Gem::Version
|
26
|
-
version: 0.
|
26
|
+
version: '0.10'
|
27
27
|
- !ruby/object:Gem::Dependency
|
28
28
|
name: rspec
|
29
29
|
requirement: !ruby/object:Gem::Requirement
|
30
30
|
requirements:
|
31
31
|
- - "~>"
|
32
32
|
- !ruby/object:Gem::Version
|
33
|
-
version: '
|
33
|
+
version: '3.1'
|
34
34
|
type: :development
|
35
35
|
prerelease: false
|
36
36
|
version_requirements: !ruby/object:Gem::Requirement
|
37
37
|
requirements:
|
38
38
|
- - "~>"
|
39
39
|
- !ruby/object:Gem::Version
|
40
|
-
version: '
|
40
|
+
version: '3.1'
|
41
41
|
- !ruby/object:Gem::Dependency
|
42
42
|
name: rake
|
43
43
|
requirement: !ruby/object:Gem::Requirement
|
@@ -75,6 +75,8 @@ extra_rdoc_files: []
|
|
75
75
|
files:
|
76
76
|
- ".gitignore"
|
77
77
|
- ".rspec"
|
78
|
+
- ".ruby-gemset"
|
79
|
+
- ".ruby-version"
|
78
80
|
- Gemfile
|
79
81
|
- LICENSE
|
80
82
|
- README.md
|
@@ -82,6 +84,8 @@ files:
|
|
82
84
|
- grape-resource-definition.gemspec
|
83
85
|
- lib/grape-resource-definition.rb
|
84
86
|
- lib/grape_resource_definition.rb
|
87
|
+
- lib/grape_resource_definition/no_resource_defined.rb
|
88
|
+
- lib/grape_resource_definition/no_resource_definition.rb
|
85
89
|
- lib/grape_resource_definition/resource_definition.rb
|
86
90
|
- lib/grape_resource_definition/version.rb
|
87
91
|
- spec/resource_definition_spec.rb
|
@@ -105,7 +109,7 @@ required_rubygems_version: !ruby/object:Gem::Requirement
|
|
105
109
|
version: '0'
|
106
110
|
requirements: []
|
107
111
|
rubyforge_project:
|
108
|
-
rubygems_version: 2.
|
112
|
+
rubygems_version: 2.4.5
|
109
113
|
signing_key:
|
110
114
|
specification_version: 4
|
111
115
|
summary: A simple way to define params validation and coercion outside API class
|