public
Rubygem
Description: JSON Web App Framework
Homepage: http://halcyon.rubyforge.org/
Clone URL: git://github.com/mtodd/halcyon.git
Click here to lend your support to: halcyon and make a donation at www.pledgie.com !
Added a simple way to respond without raising exceptions explicitly. [#44 
state:resolved]
mtodd (author)
Thu Jun 26 08:15:34 -0700 2008
commit  b8fbb9e40eb1aef1d230b36f3d4d070a2bec5ab0
tree    2adf4b5341fee9980a132d7869c8ddb7826b6dd0
parent  6bb78c3224ebe7d62e7fb230c27bfa448bb5e9d4
...
79
80
81
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
82
83
84
...
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
...
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
...
195
196
197
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
198
199
200
0
@@ -79,6 +79,72 @@ module Halcyon
0
       self.env['REQUEST_METHOD'].downcase.to_sym
0
     end
0
     
0
+ # Returns the name of the controller in path form.
0
+ #
0
+ def self.controller_name
0
+ @controller_name ||= self.name.to_const_path
0
+ end
0
+
0
+ # Returns the name of the controller in path form.
0
+ #
0
+ def controller_name
0
+ self.class.controller_name
0
+ end
0
+
0
+ # Generates a URL based on the given name and passed
0
+ # options. Used with named routes and resources:
0
+ #
0
+ # url(:users) # => "/users"
0
+ # url(:admin_permissons) # => "/admin/permissions"
0
+ # url(:user, @user) # => "/users/1"
0
+ #
0
+ # Based on the identical method of Merb's controller.
0
+ #
0
+ def url(name, rparams={})
0
+ Halcyon::Application::Router.generate(name, rparams,
0
+ { :controller => controller_name,
0
+ :action => method
0
+ }
0
+ )
0
+ end
0
+
0
+ #--
0
+ # Responders
0
+ #++
0
+
0
+ # Responds with the correct status and body specified.
0
+ #
0
+ # * +state+ a snake-case symbol of the status (ie, <tt>:not_found</tt>,
0
+ # <tt>:unprocessable_entity</tt>, or <tt>:forbidden</tt>)
0
+ # * +body+ the response body (if the default is insufficient)
0
+ #
0
+ # Examples:
0
+ #
0
+ # class Foos < Application
0
+ # def show
0
+ # if (foo = Foo[params[:id]])
0
+ # ok(foo)
0
+ # else
0
+ # status :not_found
0
+ # end
0
+ # end
0
+ # end
0
+ #
0
+ # The above example is the same as <tt>raise NotFound.new</tt>.
0
+ #
0
+ # If the state specified is not found, it will
0
+ # <tt>raise ServiceUnavailable.new</tt> (a <tt>503</tt> error). The error
0
+ # is then logged along with the backtrace.
0
+ #
0
+ def status(state, body = nil)
0
+ raise Halcyon::Exceptions.const_get(state.to_s.camel_case.to_sym).new(body)
0
+ rescue NameError => e
0
+ self.logger.error "Invalid status #{state.inspect} specified."
0
+ self.logger.error "Backtrace:\n" << e.backtrace.join("\n\t")
0
+ raise Halcyon::Exceptions::ServiceUnavailable.new
0
+ end
0
+ alias_method :error, :status
0
+
0
     # Formats message into the standard success response hash, with a status of
0
     # 200 (the standard success response).
0
     # +body+ the body of the response
0
@@ -129,35 +195,6 @@ module Halcyon
0
     end
0
     alias_method :missing, :not_found
0
     
0
- # Returns the name of the controller in path form.
0
- #
0
- def self.controller_name
0
- @controller_name ||= self.name.to_const_path
0
- end
0
-
0
- # Returns the name of the controller in path form.
0
- #
0
- def controller_name
0
- self.class.controller_name
0
- end
0
-
0
- # Generates a URL based on the given name and passed
0
- # options. Used with named routes and resources:
0
- #
0
- # url(:users) # => "/users"
0
- # url(:admin_permissons) # => "/admin/permissions"
0
- # url(:user, @user) # => "/users/1"
0
- #
0
- # Based on the identical method of Merb's controller.
0
- #
0
- def url(name, rparams={})
0
- Halcyon::Application::Router.generate(name, rparams,
0
- { :controller => controller_name,
0
- :action => method
0
- }
0
- )
0
- end
0
-
0
     #--
0
     # Filters
0
     #++
...
95
96
97
98
 
 
99
100
101
...
95
96
97
 
98
99
100
101
102
0
@@ -95,7 +95,8 @@ module Halcyon
0
       status, body = http_status
0
       class_eval <<-"end;"
0
         class #{body.gsub(/( |\-)/,'')} < Halcyon::Exceptions::Base
0
- def initialize(body='#{body}')
0
+ def initialize(body=nil)
0
+ body = '#{body}' if body.nil?
0
             super(#{status}, body)
0
           end
0
         end
...
23
24
25
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
26
27
28
...
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
0
@@ -23,6 +23,21 @@ describe "Halcyon::Controller" do
0
     controller.ok('OK', headers).should == {:status => 200, :body => 'OK', :headers => headers}
0
   end
0
   
0
+ it "should provide extensive responders" do
0
+ controller = Specs.new(Rack::MockRequest.env_for('/'))
0
+
0
+ should.raise(Halcyon::Exceptions::UnprocessableEntity) { controller.status(:unprocessable_entity) }
0
+ response = Rack::MockRequest.new(@app).get("/specs/unprocessable_entity_test")
0
+ response.body.should =~ %r{Unprocessable Entity}
0
+
0
+ should.raise(Halcyon::Exceptions::UnprocessableEntity) { controller.status(:unprocessable_entity) }
0
+ end
0
+
0
+ it "should indicate service is unavailable if an status specified is not found" do
0
+ controller = Specs.new(Rack::MockRequest.env_for('/'))
0
+ should.raise(Halcyon::Exceptions::ServiceUnavailable) { controller.status(:this_state_does_not_exist) }
0
+ end
0
+
0
   it "should provide a quick way to find out what method the request was performed using" do
0
     %w(GET POST PUT DELETE).each do |m|
0
       controller = Specs.new(Rack::MockRequest.env_for('/', :method => m))
...
43
44
45
 
 
 
 
46
47
48
...
43
44
45
46
47
48
49
50
51
52
0
@@ -43,6 +43,10 @@ class Specs < Application
0
     ok('fubr')
0
   end
0
   
0
+ def unprocessable_entity_test
0
+ error :unprocessable_entity
0
+ end
0
+
0
   def cause_exception
0
     raise Exception.new("Oops!")
0
   end

Comments

    No one has commented yet.