service_crud 0.0.1

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.
data/README.markdown ADDED
@@ -0,0 +1,106 @@
1
+ # Service Crud
2
+
3
+ The `service_crud` gem: A simple mixin for adding crud actions for a RESTful, ActiveResource style service (xml and json).
4
+
5
+ ## Requirements
6
+
7
+ This gem works with Rails 3.
8
+
9
+ ## Installation
10
+
11
+ $ cd /path/to/your/rails3/app
12
+ $ echo "gem service_crud" >> Gemfile
13
+ $ bundle install
14
+
15
+ ## Usage
16
+
17
+ Let's suppose we have a "Book" model, and we want to create XML and JSON RESTful services for it. Simple:
18
+
19
+ First, go to your routes.rb file and add the following route:
20
+
21
+ resources :books
22
+
23
+ Next, create the following controller in RAILS_ROOT/app/books_controller.rb:
24
+
25
+ class BooksController
26
+ include ServiceCrud
27
+ end
28
+
29
+ That's it. You can now GET, POST, PUT, and DELETE books through the standard RESTful urls.
30
+
31
+ ## Callbacks
32
+
33
+ Sometimes you need to do a little extra work on your data before/after you create/update/destroy. And sometimes that can't be pushed down to the ORM layer.
34
+ For example, suppose we want to set the `:updated_by` property on our model to the `current_user`. We could simply:
35
+
36
+ class BooksController
37
+ include ServiceCrud
38
+ before_update :set_updated_by
39
+
40
+ private
41
+ def set_updated_by(model)
42
+ model.update_by = current_user
43
+ end
44
+ end
45
+
46
+ ServiceCrud supports the following callbacks: `before_create`, `after_create`, `before_update`, `after_update`, `before_destroy`, and `after_destroy`.
47
+
48
+ ## Model Guessing
49
+
50
+ The `service_crud` library will look at the controller name and try to guess the model (e.g., "BooksController" -> "Book").
51
+
52
+ If your controller name doesn't match your model, call the `model` method:
53
+
54
+ class MyBooksController
55
+ include ServiceCrud
56
+ model Book
57
+ end
58
+
59
+ ## PUT/POST parameter guessing
60
+
61
+ Similarly, on POST or PUT, `service_crud` assumes that the top-level node of the XML or JSON is the lowercased, underscored, singularized symbol of your model name.
62
+
63
+ If that's not the case for your service, call the `model_attribute_root` class method:
64
+
65
+ class BooksController
66
+ include ServiceCrud
67
+ model_attribute_root :my_book
68
+ end
69
+
70
+ ## ORM
71
+
72
+ The `service_crud` library assumes an ActiveRecord ORM by default. It also, out of the box, supports the `couchrest_model` ORM for couchdb.
73
+ To use `couchrest_model`, simply:
74
+
75
+ class BooksController
76
+ include ServiceCrud
77
+ orm_methods! ServiceCrud::CouchRest::Model
78
+ end
79
+
80
+ The default ORM methods are:
81
+
82
+ module ServiceCrud
83
+ module DefaultOrm
84
+ def all; :all; end
85
+ def new; :new; end
86
+ def find; :find; end
87
+ def destroy; :destroy; end
88
+ def update_attributes; :update_attributes; end
89
+ def save; :save; end
90
+ end
91
+ end
92
+
93
+ If you're using an ORM other than ActiveRecord or CouchRest::Model, and some or all of your ORM's method names differ from ActiveRecord's,
94
+ then simply create a module that redefines one or more DefaultOrm methods. For example, suppose we create our own ORM, `MoonOrm`, and our method for finding
95
+ records is `lookup` instead of `find`. Then we'd simply:
96
+
97
+ module MoonOrmMethods
98
+ def find; :lookup; end
99
+ end
100
+
101
+ Then, in our controller:
102
+
103
+ class BooksController
104
+ include ServiceCrud
105
+ orm_methods! MoonOrmMethods
106
+ end
@@ -0,0 +1,7 @@
1
+ module ServiceCrud
2
+ module CouchRest
3
+ module Model
4
+ def find; :get; end
5
+ end
6
+ end
7
+ end
@@ -0,0 +1,10 @@
1
+ module ServiceCrud
2
+ class DefaultOrm
3
+ def all; :all; end
4
+ def new; :new; end
5
+ def find; :find; end
6
+ def destroy; :destroy; end
7
+ def update_attributes; :update_attributes; end
8
+ def save; :save; end
9
+ end
10
+ end
@@ -0,0 +1,153 @@
1
+ module ServiceCrud
2
+
3
+ def self.included(base)
4
+ base.extend ClassMethods
5
+ end
6
+
7
+ module ClassMethods
8
+ def model(klass=nil)
9
+ @model ||= klass
10
+ @model || self.to_s.gsub("Controller", "").singularize.constantize
11
+ end
12
+
13
+ def model_attribute_root(root=nil)
14
+ @model_attribute_root ||= root
15
+ @model_attribute_root || self.model.to_s.underscore.to_sym
16
+ end
17
+
18
+ def orm_methods!(orm_module)
19
+ self.orm_methods.extend orm_module
20
+ end
21
+
22
+ def orm_methods
23
+ @orm_methods ||= ServiceCrud::DefaultOrm.new
24
+ end
25
+
26
+ def before_create(method=nil, &block)
27
+ self.before_creates << method if method
28
+ self.before_creates << block if block
29
+ end
30
+
31
+ def before_update(method=nil, &block)
32
+ self.before_updates << method if method
33
+ self.before_updates << block if block
34
+ end
35
+
36
+ def before_destroy(method=nil, &block)
37
+ self.before_destroys << method if method
38
+ self.before_destroys << block if block
39
+ end
40
+
41
+ def after_create(method=nil, &block)
42
+ self.after_creates << method if method
43
+ self.after_creates << block if block
44
+ end
45
+
46
+ def after_update(method=nil, &block)
47
+ self.after_updates << method if method
48
+ self.after_updates << block if block
49
+ end
50
+
51
+ def after_destroy(method=nil, &block)
52
+ self.after_destroys << method if method
53
+ self.after_destroys << block if block
54
+ end
55
+
56
+ def before_creates; @before_creates ||= []; end
57
+ def before_updates; @before_updates ||= []; end
58
+ def before_destroys; @before_destroys ||= []; end
59
+ def after_creates; @after_creates ||= []; end
60
+ def after_updates; @after_updates ||= []; end
61
+ def after_destroys; @after_destroys ||= []; end
62
+
63
+ end
64
+
65
+ # GET /your_model.xml
66
+ # GET /your_model.json
67
+ def index
68
+ @models = self.class.model.send self.class.orm_methods.all
69
+
70
+ respond_to do |format|
71
+ format.xml { render :xml => @models }
72
+ format.json { render :json => @models }
73
+ end
74
+ end
75
+
76
+ # GET /your_model/1.xml
77
+ # GET /your_model/1.json
78
+ def show
79
+ @model = self.class.model.send self.class.orm_methods.find, params[:id]
80
+
81
+ respond_to do |format|
82
+ format.xml { render :xml => @model }
83
+ format.json { render :json => @model }
84
+ end
85
+ end
86
+
87
+ # POST /your_model.xml
88
+ # POST /your_model.json
89
+ def create
90
+ @model = self.class.model.send self.class.orm_methods.new, params[self.class.model_attribute_root]
91
+ run_service_crud_before_callbacks @model
92
+
93
+ respond_to do |format|
94
+ if @model.send self.class.orm_methods.save
95
+ run_service_crud_after_callbacks @model
96
+ location = "/#{controller_name}/#{@model.id}"
97
+ format.xml { render :xml => @model, :status => :created, :location => location }
98
+ format.json { render :json => @model, :status => :created, :location => location }
99
+ else
100
+ format.xml { render :xml => @model.errors, :status => :unprocessable_entity }
101
+ format.json { render :json => {:errors => @model.errors.to_a}.to_json, :status => :unprocessable_entity }
102
+ end
103
+ end
104
+ end
105
+
106
+ # PUT /your_model/1.xml
107
+ # PUT /your_model/1.json
108
+ def update
109
+ @model = self.class.model.send self.class.orm_methods.find, params[:id]
110
+ run_service_crud_before_callbacks @model
111
+
112
+ respond_to do |format|
113
+ if @model.send self.class.orm_methods.update_attributes, params[self.class.model_attribute_root]
114
+ run_service_crud_after_callbacks @model
115
+ format.xml { head :ok }
116
+ format.json { head :ok }
117
+ else
118
+ format.xml { render :xml => @model.errors, :status => :unprocessable_entity }
119
+ format.json { render :json => {:errors => @model.errors.to_a}.to_json, :status => :unprocessable_entity }
120
+ end
121
+ end
122
+ end
123
+
124
+ # DELETE /your_model/1.xml
125
+ # DELETE /your_model/1.json
126
+ def destroy
127
+ @model = self.class.model.send self.class.orm_methods.find, params[:id]
128
+ run_service_crud_before_callbacks @model
129
+ @model.send self.class.orm_methods.destroy
130
+ run_service_crud_after_callbacks @model
131
+
132
+ respond_to do |format|
133
+ format.xml { head :ok }
134
+ format.json { head :ok }
135
+ end
136
+ end
137
+
138
+ private
139
+ def run_service_crud_before_callbacks(model)
140
+ run_service_crud_callbacks self.class.send("before_#{action_name}s".to_sym), model
141
+ end
142
+
143
+ def run_service_crud_after_callbacks(model)
144
+ run_service_crud_callbacks self.class.send("after_#{action_name}s".to_sym), model
145
+ end
146
+
147
+ def run_service_crud_callbacks(service_crud_callbacks, model)
148
+ service_crud_callbacks.each do |method|
149
+ method.call(model) if method.respond_to?(:call) # if it's a proc
150
+ self.send method, model if method.kind_of?(Symbol)
151
+ end
152
+ end
153
+ end
@@ -0,0 +1,3 @@
1
+ require 'service_crud/default_orm'
2
+ require 'service_crud/couchrest_model'
3
+ require 'service_crud/service_crud'
metadata ADDED
@@ -0,0 +1,85 @@
1
+ --- !ruby/object:Gem::Specification
2
+ name: service_crud
3
+ version: !ruby/object:Gem::Version
4
+ hash: 29
5
+ prerelease: false
6
+ segments:
7
+ - 0
8
+ - 0
9
+ - 1
10
+ version: 0.0.1
11
+ platform: ruby
12
+ authors:
13
+ - Matt Parker
14
+ autorequire:
15
+ bindir: bin
16
+ cert_chain: []
17
+
18
+ date: 2010-11-07 00:00:00 -04:00
19
+ default_executable:
20
+ dependencies:
21
+ - !ruby/object:Gem::Dependency
22
+ name: rails
23
+ prerelease: false
24
+ requirement: &id001 !ruby/object:Gem::Requirement
25
+ none: false
26
+ requirements:
27
+ - - ">="
28
+ - !ruby/object:Gem::Version
29
+ hash: 7
30
+ segments:
31
+ - 3
32
+ - 0
33
+ version: "3.0"
34
+ type: :runtime
35
+ version_requirements: *id001
36
+ description: A simple mixin for providing crud actions for a RESTful, ActiveResource style service (xml and json).
37
+ email: moonmaster9000@gmail.com
38
+ executables: []
39
+
40
+ extensions: []
41
+
42
+ extra_rdoc_files:
43
+ - README.markdown
44
+ files:
45
+ - README.markdown
46
+ - lib/service_crud.rb
47
+ - lib/service_crud/couchrest_model.rb
48
+ - lib/service_crud/default_orm.rb
49
+ - lib/service_crud/service_crud.rb
50
+ has_rdoc: true
51
+ homepage: http://github.com/moonmaster9000/service_crud
52
+ licenses: []
53
+
54
+ post_install_message:
55
+ rdoc_options:
56
+ - --charset=UTF-8
57
+ require_paths:
58
+ - lib
59
+ required_ruby_version: !ruby/object:Gem::Requirement
60
+ none: false
61
+ requirements:
62
+ - - ">="
63
+ - !ruby/object:Gem::Version
64
+ hash: 3
65
+ segments:
66
+ - 0
67
+ version: "0"
68
+ required_rubygems_version: !ruby/object:Gem::Requirement
69
+ none: false
70
+ requirements:
71
+ - - ">="
72
+ - !ruby/object:Gem::Version
73
+ hash: 3
74
+ segments:
75
+ - 0
76
+ version: "0"
77
+ requirements: []
78
+
79
+ rubyforge_project:
80
+ rubygems_version: 1.3.7
81
+ signing_key:
82
+ specification_version: 3
83
+ summary: DRY service crud.
84
+ test_files: []
85
+