api_logic 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/Gemfile ADDED
@@ -0,0 +1,4 @@
1
+ source "http://rubygems.org"
2
+
3
+ # Specify your gem's dependencies in api_controller.gemspec
4
+ gemspec
data/README.mdown ADDED
@@ -0,0 +1,81 @@
1
+ # API Logic
2
+
3
+ A lightweight mixin for making API controllers
4
+
5
+ # Usage
6
+
7
+ Extend a controller with `ApiLogic` and call `exposes_model`
8
+ to generate the default REST actions.
9
+
10
+ class MyApiController < ApplicationController
11
+ extend ApiLogic
12
+ exposes_model Widget
13
+ respond_to :json, :xml
14
+ end
15
+
16
+ or if the controller's name looks like #{resource}ApiController then
17
+ exposes_model will automatically be called with the resource:
18
+
19
+ class CalendarApiController < ApplicationController
20
+ extend ApiLogic
21
+ respond_to :json, :xml
22
+ end
23
+
24
+ # Customization
25
+
26
+ ### Responder
27
+
28
+ ApiLogic calls `respond_with` for each REST action, so you can change
29
+ how it renders by replacing the Responder:
30
+
31
+ class CalendarApiController < ApplicationController
32
+ extend ApiLogic
33
+ responder = MyResponder
34
+ respond_to :json, :xml
35
+ end
36
+
37
+ ### Templates
38
+
39
+ The recommended way of customizing how a model is rendered to JSON or XML
40
+ is to supply a RABL template for the action.
41
+
42
+ ### Overriding methods
43
+
44
+ You can always override one of ApiLogic's actions by defining your own, but
45
+ ApiLogic gives a few finer-grained ways of controlling its default behavior.
46
+
47
+ You can override the method `find_models` to change how the index action
48
+ fetches models. By default `find_models` looks like this:
49
+
50
+ def find_models
51
+ model_class.all
52
+ end
53
+
54
+ You can override the method `find_model` to change how the show, update, and
55
+ destroy actions look up a model for the given URL. By default `find_model` looks
56
+ like this:
57
+
58
+ def find_model
59
+ @model = model_class.find(params[:id])
60
+ instance_variable_set "@#{model_singular}", @model
61
+ end
62
+
63
+ `create_attributes` and `update_attributes` return the attributes supplied
64
+ to `model_class.create` and `@model.update_attributes` in the create and
65
+ update actions. Their default implementations are:
66
+
67
+ def create_attributes
68
+ model_params
69
+ end
70
+
71
+ def update_attributes
72
+ model_params
73
+ end
74
+
75
+ And, finally, you can change how a model's attributes are pulled out of params
76
+ by overriding `model_params`. Its default implementation looks like this:
77
+
78
+ def model_params
79
+ params[model_singular]
80
+ end
81
+
data/Rakefile ADDED
@@ -0,0 +1 @@
1
+ require 'bundler/gem_tasks'
@@ -0,0 +1,33 @@
1
+ require 'action_controller/metal/responder'
2
+
3
+ module ApiLogic
4
+ class Responder < ActionController::Responder
5
+
6
+
7
+ def respond
8
+
9
+ # An API controller might want to tailor its response
10
+ # with a RABL template. If a template exists, render that.
11
+ #
12
+ # Also, if the resource is nil or if it doesn't respond to
13
+ # :to_#{format}, fall back to the default render functionality.
14
+ #
15
+ template_path = File.join(controller.controller_path, controller.action_name)
16
+ if resource.nil? || !resourceful? || controller.template_exists?(template_path)
17
+ render
18
+ else
19
+
20
+ # api_behavior takes as a parameter the error it will throw if
21
+ # the resource does not respond to :to_#{format}. (Since we've
22
+ # already checked :resourceful?, this error should never be thrown,
23
+ # but just in case, we'll supply NotImplementedError.)
24
+ api_behavior(NotImplementedError)
25
+ end
26
+ end
27
+
28
+
29
+ end
30
+ end
31
+
32
+ # Refer to the source of ActionController::Responder:
33
+ # https://github.com/rails/rails/blob/v3.0.3/actionpack/lib/action_controller/metal/responder.rb#L155
@@ -0,0 +1,3 @@
1
+ module ApiController
2
+ VERSION = "0.0.1"
3
+ end
data/lib/api_logic.rb ADDED
@@ -0,0 +1,129 @@
1
+ require "api_logic/version"
2
+ require "api_logic/responder"
3
+
4
+ module ApiLogic
5
+ extend ActiveSupport::Concern
6
+
7
+
8
+
9
+ included do
10
+ guess_model
11
+
12
+ def self.inherited(subclass)
13
+ super
14
+ subclass.guess_model
15
+ end
16
+ end
17
+
18
+
19
+
20
+ module ClassMethods
21
+
22
+ resonder = ::ApiLogic::Responder
23
+
24
+ attr_reader :model_class
25
+ alias :model :model_class
26
+ attr_reader :model_collection
27
+ attr_reader :model_singular
28
+
29
+
30
+ def guess_model
31
+ # puts "[api_logic] guessing model for #{self.name}"
32
+ if self.name =~ /(?:.*::)(.*?)ApiController/
33
+ model_name = $1.singularize
34
+ begin
35
+ exposes_model $1.singularize.constantize
36
+ rescue NameError
37
+ # puts " there is no model \"#{model_name}\""
38
+ end
39
+ else
40
+ # puts " the controller does not match the pattern /(?:.*::)(.*?)ApiController/"
41
+ end
42
+ end
43
+
44
+
45
+ def exposes_model(model_class)
46
+ # puts "[api_logic] exposing model #{model_class} on #{self.name}"
47
+
48
+ @model_class = model_class
49
+ @model_collection = model_class.name.tableize
50
+ @model_singular = @model_collection.singularize
51
+
52
+ before_filter :find_model, :only => [:show, :update, :destroy]
53
+
54
+ public
55
+
56
+ define_method :index do
57
+ collection = find_models
58
+ instance_variable_set "@#{model_collection}", collection
59
+ respond_with collection
60
+ end
61
+
62
+ define_method :show do
63
+ respond_with @model
64
+ end
65
+
66
+ define_method :create do
67
+ @model = create_model
68
+ instance_variable_set "@#{model_singular}", @model
69
+ respond_with @model
70
+ end
71
+
72
+ define_method :update do
73
+ @model.update_attributes(update_attributes)
74
+ respond_with @model
75
+ end
76
+
77
+ define_method :destroy do
78
+ @model.destroy
79
+ respond_with @model
80
+ end
81
+
82
+ end
83
+
84
+ end
85
+
86
+
87
+
88
+ def find_models
89
+ model_class.all
90
+ end
91
+
92
+ def find_model
93
+ @model = model_class.find(params[:id])
94
+ instance_variable_set "@#{model_singular}", @model
95
+ end
96
+
97
+ def create_model
98
+ model_class.create(create_attributes)
99
+ end
100
+
101
+
102
+ def create_attributes
103
+ model_params
104
+ end
105
+
106
+ def update_attributes
107
+ model_params
108
+ end
109
+
110
+ def model_params
111
+ params[model_singular]
112
+ end
113
+
114
+
115
+ def model_class
116
+ self.class.model
117
+ end
118
+
119
+ def model_collection
120
+ self.class.model_collection
121
+ end
122
+
123
+ def model_singular
124
+ self.class.model_singular
125
+ end
126
+
127
+
128
+
129
+ end
metadata ADDED
@@ -0,0 +1,83 @@
1
+ --- !ruby/object:Gem::Specification
2
+ name: api_logic
3
+ version: !ruby/object:Gem::Version
4
+ prerelease:
5
+ version: 0.0.1
6
+ platform: ruby
7
+ authors:
8
+ - Robert Lail
9
+ autorequire:
10
+ bindir: bin
11
+ cert_chain: []
12
+
13
+ date: 2011-08-18 00:00:00 -05:00
14
+ default_executable:
15
+ dependencies:
16
+ - !ruby/object:Gem::Dependency
17
+ name: activesupport
18
+ prerelease: false
19
+ requirement: &id001 !ruby/object:Gem::Requirement
20
+ none: false
21
+ requirements:
22
+ - - ">="
23
+ - !ruby/object:Gem::Version
24
+ version: "0"
25
+ type: :runtime
26
+ version_requirements: *id001
27
+ - !ruby/object:Gem::Dependency
28
+ name: actionpack
29
+ prerelease: false
30
+ requirement: &id002 !ruby/object:Gem::Requirement
31
+ none: false
32
+ requirements:
33
+ - - ">="
34
+ - !ruby/object:Gem::Version
35
+ version: "0"
36
+ type: :runtime
37
+ version_requirements: *id002
38
+ description: Mixes in to ActionController and generates default RESTful actions automatically in a highly customizable way.
39
+ email:
40
+ - robert.lail@cph.org
41
+ executables: []
42
+
43
+ extensions: []
44
+
45
+ extra_rdoc_files: []
46
+
47
+ files:
48
+ - lib/api_logic/responder.rb
49
+ - lib/api_logic/version.rb
50
+ - lib/api_logic.rb
51
+ - Gemfile
52
+ - Rakefile
53
+ - README.mdown
54
+ has_rdoc: true
55
+ homepage: https://github.com/boblail/api_logic
56
+ licenses: []
57
+
58
+ post_install_message:
59
+ rdoc_options: []
60
+
61
+ require_paths:
62
+ - lib
63
+ required_ruby_version: !ruby/object:Gem::Requirement
64
+ none: false
65
+ requirements:
66
+ - - ">="
67
+ - !ruby/object:Gem::Version
68
+ version: "0"
69
+ required_rubygems_version: !ruby/object:Gem::Requirement
70
+ none: false
71
+ requirements:
72
+ - - ">="
73
+ - !ruby/object:Gem::Version
74
+ version: "0"
75
+ requirements: []
76
+
77
+ rubyforge_project: api_logic
78
+ rubygems_version: 1.6.2
79
+ signing_key:
80
+ specification_version: 3
81
+ summary: A lightweight mixin for making API controllers
82
+ test_files: []
83
+