restaurant 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/README.md +66 -60
- data/lib/restaurant.rb +1 -1
- data/lib/restaurant/authorization.rb +1 -73
- data/lib/restaurant/controller_helper.rb +1 -1
- data/lib/restaurant/restful_actions.rb +27 -7
- data/lib/restaurant/role_provider.rb +91 -0
- data/lib/restaurant/version.rb +1 -1
- metadata +6 -5
- data/lib/restaurant/model_class_finder.rb +0 -7
checksums.yaml
CHANGED
@@ -1,7 +1,7 @@
|
|
1
1
|
---
|
2
2
|
SHA1:
|
3
|
-
metadata.gz:
|
4
|
-
data.tar.gz:
|
3
|
+
metadata.gz: 5d5122a098f9caa7cc338db255ba09004f7ccf66
|
4
|
+
data.tar.gz: c3d345db89308e5c3290712e9107a0ce5e72fd4c
|
5
5
|
SHA512:
|
6
|
-
metadata.gz:
|
7
|
-
data.tar.gz:
|
6
|
+
metadata.gz: faeea0c7030f4a52afde512659ed888b5535ed1abe9ca06c913b8b643ffe39074cb857ec0035e9bf9f8b77e0d94c2d5d5c45da7ae01ed9304c6a0f03b217a95a
|
7
|
+
data.tar.gz: 7b66d037c43da749f4829d55a80ef64282544580fe07902b9ee4cbbe99d7fca79d144632055453dceae2b26f5376a7e242f00ac940cc7708875e8d4cf9154ae1
|
data/README.md
CHANGED
@@ -1,72 +1,52 @@
|
|
1
1
|
# Restaurant
|
2
|
-
Restaurant serves RESTful API on
|
2
|
+
Restaurant serves your data via auto-defined RESTful API on your rails application.
|
3
3
|
|
4
4
|
## Features
|
5
|
+
* Auto-defined controllers
|
6
|
+
* Auto-defined routes
|
7
|
+
* SQL-like URI query
|
8
|
+
* OAuth authentication
|
9
|
+
* Scope based authorization
|
10
|
+
* restrict actions
|
11
|
+
* restrict attributes
|
12
|
+
* restrict filtering
|
13
|
+
* restrict sorting
|
14
|
+
* RESTful APIs
|
15
|
+
* GET /:resources
|
16
|
+
* GET /:resources/:id
|
17
|
+
* POST /:resources
|
18
|
+
* PUT /:resources/:id
|
19
|
+
* DELETE /:resources/:id
|
5
20
|
|
6
|
-
|
7
|
-
|
8
|
-
All controllers and routings will be auto-defined based on your config/restaurant.yml definition.
|
9
|
-
No need to write any more app/controllers and config/routes.rb.
|
10
|
-
All you have to do is write your models and authorization yaml file.
|
11
|
-
|
12
|
-
```ruby
|
13
|
-
# app/controllers/application_controller.rb
|
14
|
-
class ApplicationController < ActionController::Base
|
15
|
-
include Restaurant::ControllerHelper
|
16
|
-
end
|
17
|
-
```
|
18
|
-
|
19
|
-
```ruby
|
20
|
-
# config/routes.rb
|
21
|
-
Rails.application.routes.draw do
|
22
|
-
Restaurant::Router.route(self)
|
23
|
-
end
|
24
|
-
```
|
21
|
+
## Auto-defined controllers and routes
|
22
|
+
Controllers and routes are auto-defined from your config/restaurant.yml.
|
25
23
|
|
26
24
|
```yaml
|
27
25
|
# config/restaurant.yml
|
28
|
-
public:
|
29
|
-
recipes:
|
30
|
-
actions:
|
31
|
-
-
|
32
|
-
|
33
|
-
|
34
|
-
|
35
|
-
|
26
|
+
public: # User with "public" scope token
|
27
|
+
recipes: #
|
28
|
+
actions: #
|
29
|
+
- show # can access to /recipes/:id
|
30
|
+
attributes: #
|
31
|
+
- title # can read recipe.title
|
32
|
+
admin: # User with "admin" scope token
|
33
|
+
recipes: #
|
34
|
+
actions: #
|
35
|
+
- index # can access to /recipes
|
36
|
+
- show # can access to /recipes/:id
|
37
|
+
where: #
|
38
|
+
- id # can filter recipes by id
|
39
|
+
- title # can filter recipes by title
|
40
|
+
order: #
|
41
|
+
- id # can sort recipes by id
|
42
|
+
- title # can sort recipes by title
|
43
|
+
attributes: #
|
44
|
+
- id # can read recipe.id
|
45
|
+
- title # can read recipe.title
|
36
46
|
```
|
37
47
|
|
38
|
-
|
39
|
-
You can
|
40
|
-
|
41
|
-
* User with "public" scope token
|
42
|
-
* can access /recipes/:id
|
43
|
-
* User with "admin" scope token
|
44
|
-
* can access /recipes/:id
|
45
|
-
* can access /recipes
|
46
|
-
* can filter recipes by id and title
|
47
|
-
* can sort recipes by id and title
|
48
|
-
|
49
|
-
```yaml
|
50
|
-
# config/restaurant.yml
|
51
|
-
public:
|
52
|
-
recipes:
|
53
|
-
actions:
|
54
|
-
- show
|
55
|
-
admin:
|
56
|
-
recipes:
|
57
|
-
actions:
|
58
|
-
- index
|
59
|
-
- show
|
60
|
-
where:
|
61
|
-
- id
|
62
|
-
- title
|
63
|
-
order:
|
64
|
-
- id
|
65
|
-
- title
|
66
|
-
```
|
67
|
-
|
68
|
-
### SQL-like URI query
|
69
|
-
Our restraunt serves SQL-like URI query system.
|
48
|
+
## SQL-like URI query
|
49
|
+
You can filter and sort resources by SQL-like URI query.
|
70
50
|
|
71
51
|
```ruby
|
72
52
|
context "with where params" do
|
@@ -84,3 +64,29 @@ context "with where params" do
|
|
84
64
|
end
|
85
65
|
end
|
86
66
|
```
|
67
|
+
|
68
|
+
## Install
|
69
|
+
```ruby
|
70
|
+
# Gemfile
|
71
|
+
gem "restaurant"
|
72
|
+
|
73
|
+
# app/controllers/application_controller.rb
|
74
|
+
class ApplicationController < ActionController::Base
|
75
|
+
include Restaurant::ControllerHelper
|
76
|
+
end
|
77
|
+
|
78
|
+
# config/routes.rb
|
79
|
+
Rails.application.routes.draw do
|
80
|
+
Restaurant::Router.route(self)
|
81
|
+
end
|
82
|
+
```
|
83
|
+
|
84
|
+
```
|
85
|
+
$ bundle install
|
86
|
+
$ bundle exec rails g doorkeeper:install
|
87
|
+
$ bundle exec rails g doorkeeper:migration
|
88
|
+
$ bundle exec rake db:migrate
|
89
|
+
```
|
90
|
+
|
91
|
+
## More
|
92
|
+
See [the example application](https://github.com/r7kamura/restaurant/tree/master/spec/dummy).
|
data/lib/restaurant.rb
CHANGED
@@ -3,10 +3,10 @@ require "restaurant/authorization"
|
|
3
3
|
require "restaurant/config"
|
4
4
|
require "restaurant/controller_helper"
|
5
5
|
require "restaurant/controller_provider"
|
6
|
-
require "restaurant/model_class_finder"
|
7
6
|
require "restaurant/params_query_responder"
|
8
7
|
require "restaurant/params_query_translator"
|
9
8
|
require "restaurant/restful_actions"
|
9
|
+
require "restaurant/role_provider"
|
10
10
|
require "restaurant/router"
|
11
11
|
require "restaurant/railtie"
|
12
12
|
|
@@ -8,78 +8,6 @@ module Restaurant::Authorization
|
|
8
8
|
private
|
9
9
|
|
10
10
|
def require_authorization
|
11
|
-
head 403 unless has_authorization?
|
12
|
-
end
|
13
|
-
|
14
|
-
def has_authorization?
|
15
|
-
has_action_authorization? && has_query_authorization?
|
16
|
-
end
|
17
|
-
|
18
|
-
def has_action_authorization?
|
19
|
-
controllers_set.any? do |controllers|
|
20
|
-
if controller = controllers[controller_name]
|
21
|
-
controller["actions"].include?(action_name)
|
22
|
-
end
|
23
|
-
end
|
24
|
-
end
|
25
|
-
|
26
|
-
def has_query_authorization?
|
27
|
-
if has_not_allowed_where? || has_not_allowed_order?
|
28
|
-
false
|
29
|
-
else
|
30
|
-
true
|
31
|
-
end
|
32
|
-
end
|
33
|
-
|
34
|
-
def controllers_set
|
35
|
-
@controllers_set ||= Restaurant::Config.roles.inject([]) do |result, (role, controllers)|
|
36
|
-
result << controllers if doorkeeper_token.scopes.include?(role.to_sym)
|
37
|
-
result
|
38
|
-
end
|
39
|
-
end
|
40
|
-
|
41
|
-
def has_where_query?
|
42
|
-
params[:where]
|
43
|
-
end
|
44
|
-
|
45
|
-
def has_order_query?
|
46
|
-
params[:order]
|
47
|
-
end
|
48
|
-
|
49
|
-
def current_abilities
|
50
|
-
@current_abilities ||= controllers_set.inject([]) do |abilities, controllers|
|
51
|
-
abilities << controllers[controller_name] if controllers[controller_name]
|
52
|
-
abilities
|
53
|
-
end
|
54
|
-
end
|
55
|
-
|
56
|
-
def current_order_abilities
|
57
|
-
current_abilities.inject([]) do |columns, ability|
|
58
|
-
columns + (ability["order"] || [])
|
59
|
-
end
|
60
|
-
end
|
61
|
-
|
62
|
-
def current_where_abilities
|
63
|
-
current_abilities.inject([]) do |columns, ability|
|
64
|
-
columns + (ability["where"] || [])
|
65
|
-
end
|
66
|
-
end
|
67
|
-
|
68
|
-
def has_not_allowed_where?
|
69
|
-
has_where_query? && (where_queries - current_where_abilities).any?
|
70
|
-
end
|
71
|
-
|
72
|
-
def has_not_allowed_order?
|
73
|
-
has_order_query? && (order_queries - current_order_abilities).any?
|
74
|
-
end
|
75
|
-
|
76
|
-
def where_queries
|
77
|
-
params[:where].keys
|
78
|
-
end
|
79
|
-
|
80
|
-
def order_queries
|
81
|
-
Array.wrap(params[:order]).map do |column|
|
82
|
-
column.sub(/^-/, "")
|
83
|
-
end
|
11
|
+
head 403 unless current_role.has_authorization?
|
84
12
|
end
|
85
13
|
end
|
@@ -4,10 +4,10 @@ module Restaurant::ControllerHelper
|
|
4
4
|
included do
|
5
5
|
use Rack::AcceptDefault
|
6
6
|
include Restaurant::ControllerProvider
|
7
|
-
include Restaurant::ModelClassFinder
|
8
7
|
include Restaurant::RestfulActions
|
9
8
|
include Restaurant::Authentication
|
10
9
|
include Restaurant::Authorization
|
10
|
+
include Restaurant::RoleProvider
|
11
11
|
self.responder = Restaurant::ParamsQueryResponder
|
12
12
|
end
|
13
13
|
end
|
@@ -1,15 +1,35 @@
|
|
1
1
|
module Restaurant::RestfulActions
|
2
|
-
|
2
|
+
def index
|
3
|
+
respond_with model.scoped, :only => current_role.allowed_attributes
|
4
|
+
end
|
3
5
|
|
4
|
-
|
5
|
-
|
6
|
+
def show
|
7
|
+
respond_with resource, :only => current_role.allowed_attributes
|
6
8
|
end
|
7
9
|
|
8
|
-
def
|
9
|
-
respond_with
|
10
|
+
def create
|
11
|
+
respond_with model.create(model_param), :only => current_role.allowed_attributes
|
10
12
|
end
|
11
13
|
|
12
|
-
def
|
13
|
-
respond_with
|
14
|
+
def update
|
15
|
+
respond_with resource.update_attributes(model_param)
|
16
|
+
end
|
17
|
+
|
18
|
+
def destroy
|
19
|
+
respond_with resource.delete
|
20
|
+
end
|
21
|
+
|
22
|
+
private
|
23
|
+
|
24
|
+
def model
|
25
|
+
self.class.name.sub(/Controller$/, "").singularize.constantize
|
26
|
+
end
|
27
|
+
|
28
|
+
def model_param
|
29
|
+
params[model.name.underscore]
|
30
|
+
end
|
31
|
+
|
32
|
+
def resource
|
33
|
+
model.find(params[:id])
|
14
34
|
end
|
15
35
|
end
|
@@ -0,0 +1,91 @@
|
|
1
|
+
module Restaurant::RoleProvider
|
2
|
+
def current_role
|
3
|
+
@current_role ||= Role.new(self)
|
4
|
+
end
|
5
|
+
|
6
|
+
class Role
|
7
|
+
delegate(
|
8
|
+
:action_name,
|
9
|
+
:controller_name,
|
10
|
+
:doorkeeper_token,
|
11
|
+
:params,
|
12
|
+
:to => :controller
|
13
|
+
)
|
14
|
+
|
15
|
+
attr_reader :controller
|
16
|
+
|
17
|
+
def initialize(controller)
|
18
|
+
@controller = controller
|
19
|
+
end
|
20
|
+
|
21
|
+
def has_authorization?
|
22
|
+
has_action_authorization? && has_query_authorization?
|
23
|
+
end
|
24
|
+
|
25
|
+
def abilities
|
26
|
+
@abilities ||= Restaurant::Config.roles.map do |role, controllers|
|
27
|
+
if doorkeeper_token.scopes.include?(role.to_sym)
|
28
|
+
controllers[controller_name]
|
29
|
+
end
|
30
|
+
end.compact
|
31
|
+
end
|
32
|
+
|
33
|
+
def allowed_attributes
|
34
|
+
abilities.map {|ability| ability["attributes"] }.compact.inject(:|)
|
35
|
+
end
|
36
|
+
|
37
|
+
private
|
38
|
+
|
39
|
+
def has_action_authorization?
|
40
|
+
abilities.any? do |ability|
|
41
|
+
ability["actions"].include?(action_name)
|
42
|
+
end
|
43
|
+
end
|
44
|
+
|
45
|
+
def has_query_authorization?
|
46
|
+
if has_not_allowed_where? || has_not_allowed_order?
|
47
|
+
false
|
48
|
+
else
|
49
|
+
true
|
50
|
+
end
|
51
|
+
end
|
52
|
+
|
53
|
+
def has_where_query?
|
54
|
+
params[:where]
|
55
|
+
end
|
56
|
+
|
57
|
+
def has_order_query?
|
58
|
+
params[:order]
|
59
|
+
end
|
60
|
+
|
61
|
+
def order_abilities
|
62
|
+
abilities.inject([]) do |columns, ability|
|
63
|
+
columns + (ability["order"] || [])
|
64
|
+
end
|
65
|
+
end
|
66
|
+
|
67
|
+
def where_abilities
|
68
|
+
abilities.inject([]) do |columns, ability|
|
69
|
+
columns + (ability["where"] || [])
|
70
|
+
end
|
71
|
+
end
|
72
|
+
|
73
|
+
def has_not_allowed_where?
|
74
|
+
has_where_query? && (where_queries - where_abilities).any?
|
75
|
+
end
|
76
|
+
|
77
|
+
def has_not_allowed_order?
|
78
|
+
has_order_query? && (order_queries - order_abilities).any?
|
79
|
+
end
|
80
|
+
|
81
|
+
def where_queries
|
82
|
+
params[:where].keys
|
83
|
+
end
|
84
|
+
|
85
|
+
def order_queries
|
86
|
+
Array.wrap(params[:order]).map do |column|
|
87
|
+
column.sub(/^-/, "")
|
88
|
+
end
|
89
|
+
end
|
90
|
+
end
|
91
|
+
end
|
data/lib/restaurant/version.rb
CHANGED
metadata
CHANGED
@@ -1,14 +1,14 @@
|
|
1
1
|
--- !ruby/object:Gem::Specification
|
2
2
|
name: restaurant
|
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
|
- Ryo Nakamura
|
8
8
|
autorequire:
|
9
9
|
bindir: bin
|
10
10
|
cert_chain: []
|
11
|
-
date: 2013-05-
|
11
|
+
date: 2013-05-14 00:00:00.000000000 Z
|
12
12
|
dependencies:
|
13
13
|
- !ruby/object:Gem::Dependency
|
14
14
|
name: rails
|
@@ -164,7 +164,8 @@ dependencies:
|
|
164
164
|
- - '>='
|
165
165
|
- !ruby/object:Gem::Version
|
166
166
|
version: '0'
|
167
|
-
description:
|
167
|
+
description: Restraunt serves your data via auto-defined RESTful API on your rails
|
168
|
+
application.
|
168
169
|
email:
|
169
170
|
- r7kamura@gmail.com
|
170
171
|
executables: []
|
@@ -176,11 +177,11 @@ files:
|
|
176
177
|
- lib/restaurant/config.rb
|
177
178
|
- lib/restaurant/controller_helper.rb
|
178
179
|
- lib/restaurant/controller_provider.rb
|
179
|
-
- lib/restaurant/model_class_finder.rb
|
180
180
|
- lib/restaurant/params_query_responder.rb
|
181
181
|
- lib/restaurant/params_query_translator.rb
|
182
182
|
- lib/restaurant/railtie.rb
|
183
183
|
- lib/restaurant/restful_actions.rb
|
184
|
+
- lib/restaurant/role_provider.rb
|
184
185
|
- lib/restaurant/router.rb
|
185
186
|
- lib/restaurant/version.rb
|
186
187
|
- lib/restaurant.rb
|
@@ -210,6 +211,6 @@ rubyforge_project:
|
|
210
211
|
rubygems_version: 2.0.0
|
211
212
|
signing_key:
|
212
213
|
specification_version: 4
|
213
|
-
summary:
|
214
|
+
summary: A rails plugin to auto-define RESTful API
|
214
215
|
test_files: []
|
215
216
|
has_rdoc:
|