bmizerany-sinatra 0.3.2

Sign up to get free protection for your applications and to get access to all the features.
Files changed (48) hide show
  1. data/ChangeLog +78 -0
  2. data/LICENSE +22 -0
  3. data/README.rdoc +523 -0
  4. data/Rakefile +162 -0
  5. data/images/404.png +0 -0
  6. data/images/500.png +0 -0
  7. data/lib/sinatra/test/methods.rb +76 -0
  8. data/lib/sinatra/test/rspec.rb +10 -0
  9. data/lib/sinatra/test/spec.rb +10 -0
  10. data/lib/sinatra/test/unit.rb +13 -0
  11. data/lib/sinatra.rb +1466 -0
  12. data/sinatra.gemspec +77 -0
  13. data/test/app_test.rb +299 -0
  14. data/test/application_test.rb +318 -0
  15. data/test/builder_test.rb +101 -0
  16. data/test/custom_error_test.rb +62 -0
  17. data/test/erb_test.rb +136 -0
  18. data/test/event_context_test.rb +15 -0
  19. data/test/events_test.rb +65 -0
  20. data/test/filter_test.rb +30 -0
  21. data/test/haml_test.rb +233 -0
  22. data/test/helper.rb +7 -0
  23. data/test/mapped_error_test.rb +72 -0
  24. data/test/pipeline_test.rb +66 -0
  25. data/test/public/foo.xml +1 -0
  26. data/test/sass_test.rb +57 -0
  27. data/test/sessions_test.rb +39 -0
  28. data/test/streaming_test.rb +118 -0
  29. data/test/sym_params_test.rb +19 -0
  30. data/test/template_test.rb +30 -0
  31. data/test/use_in_file_templates_test.rb +47 -0
  32. data/test/views/foo.builder +1 -0
  33. data/test/views/foo.erb +1 -0
  34. data/test/views/foo.haml +1 -0
  35. data/test/views/foo.sass +2 -0
  36. data/test/views/foo_layout.erb +2 -0
  37. data/test/views/foo_layout.haml +2 -0
  38. data/test/views/layout_test/foo.builder +1 -0
  39. data/test/views/layout_test/foo.erb +1 -0
  40. data/test/views/layout_test/foo.haml +1 -0
  41. data/test/views/layout_test/foo.sass +2 -0
  42. data/test/views/layout_test/layout.builder +3 -0
  43. data/test/views/layout_test/layout.erb +1 -0
  44. data/test/views/layout_test/layout.haml +1 -0
  45. data/test/views/layout_test/layout.sass +2 -0
  46. data/test/views/no_layout/no_layout.builder +1 -0
  47. data/test/views/no_layout/no_layout.haml +1 -0
  48. metadata +129 -0
data/ChangeLog ADDED
@@ -0,0 +1,78 @@
1
+ = 0.3.2
2
+
3
+ * BUG: Static and send_file read entire file into String before
4
+ sending. Updated to stream with 8K chunks instead.
5
+
6
+ * Rake tasks and assets for building basic documentation website.
7
+ See http://sinatra.rubyforge.org
8
+
9
+ * Various minor doc fixes.
10
+
11
+ = 0.3.1
12
+
13
+ * Unbreak optional path parameters [jeremyevans]
14
+
15
+ = 0.3.0
16
+
17
+ * Add sinatra.gemspec w/ support for github gem builds. Forks can now
18
+ enable the build gem option in github to get free username-sinatra.gem
19
+ builds: gem install username-sinatra.gem --source=http://gems.github.com/
20
+
21
+ * Require rack-0.4 gem; removes frozen rack dir.
22
+
23
+ * Basic RSpec support; require 'sinatra/test/rspec' instead of
24
+ 'sinatra/test/spec' to use. [avdi]
25
+
26
+ * before filters can modify request environment vars used for
27
+ routing (e.g., PATH_INFO, REQUEST_METHOD, etc.) for URL rewriting
28
+ type functionality.
29
+
30
+ * In-file templates now uses @@ instead of ## as template separator.
31
+
32
+ * Top-level environment test predicates: development?, test?, production?
33
+
34
+ * Top-level "set", "enable", and "disable" methods for tweaking
35
+ app options. [rtomayko]
36
+
37
+ * Top-level "use" method for building Rack middleware pipelines
38
+ leading to app. See README for usage. [rtomayko]
39
+
40
+ * New "reload" option - set false to disable reloading in development.
41
+
42
+ * New "host" option - host/ip to bind to [cschneid]
43
+
44
+ * New "app_file" option - override the file to reload in development
45
+ mode [cschneid]
46
+
47
+ * Development error/not_found page cleanup [sr, adamwiggins]
48
+
49
+ * Remove a bunch of core extensions (String#to_param, String#from_param,
50
+ Hash#from_params, Hash#to_params, Hash#symbolize_keys, Hash#pass)
51
+
52
+ * Various grammar and formatting fixes to README; additions on
53
+ community and contributing [cypher]
54
+
55
+ * Build RDoc using Hanna template: http://sinatrarb.rubyforge.org/api
56
+
57
+ * Specs, documentation and fixes for splat'n routes [vic]
58
+
59
+ * Fix whitespace errors across all source files. [rtomayko]
60
+
61
+ * Fix streaming issues with Mongrel (body not closed). [bmizerany]
62
+
63
+ * Fix various issues with environment not being set properly (configure
64
+ blocks not running, error pages not registering, etc.) [cypher]
65
+
66
+ * Fix to allow locals to be passed to ERB templates [cschneid]
67
+
68
+ * Fix locking issues causing random errors during reload in development.
69
+
70
+ * Fix for escaped paths not resolving static files [Matthew Walker]
71
+
72
+ = 0.2.1
73
+
74
+ * File upload fix and minor tweaks.
75
+
76
+ = 0.2.0
77
+
78
+ * Initial gem release of 0.2 coebase.
data/LICENSE ADDED
@@ -0,0 +1,22 @@
1
+ Copyright (c) 2007 Blake Mizerany
2
+
3
+ Permission is hereby granted, free of charge, to any person
4
+ obtaining a copy of this software and associated documentation
5
+ files (the "Software"), to deal in the Software without
6
+ restriction, including without limitation the rights to use,
7
+ copy, modify, merge, publish, distribute, sublicense, and/or sell
8
+ copies of the Software, and to permit persons to whom the
9
+ Software is furnished to do so, subject to the following
10
+ conditions:
11
+
12
+ The above copyright notice and this permission notice shall be
13
+ included in all copies or substantial portions of the Software.
14
+
15
+ THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
16
+ EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES
17
+ OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
18
+ NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT
19
+ HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY,
20
+ WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING
21
+ FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR
22
+ OTHER DEALINGS IN THE SOFTWARE.
data/README.rdoc ADDED
@@ -0,0 +1,523 @@
1
+ = Sinatra
2
+
3
+ Sinatra is a DSL for quickly creating web-applications in Ruby with minimal
4
+ effort.
5
+
6
+ == Sample App
7
+
8
+ # myapp.rb
9
+ require 'rubygems'
10
+ require 'sinatra'
11
+ get '/' do
12
+ 'Hello world!'
13
+ end
14
+
15
+ Run with <tt>ruby myapp.rb</tt> and view at <tt>http://localhost:4567</tt>
16
+
17
+ == HTTP Methods
18
+
19
+ get '/' do
20
+ .. show things ..
21
+ end
22
+
23
+ post '/' do
24
+ .. create something ..
25
+ end
26
+
27
+ put '/' do
28
+ .. update something ..
29
+ end
30
+
31
+ delete '/' do
32
+ .. annihilate something ..
33
+ end
34
+
35
+ head '/' do
36
+
37
+ end
38
+
39
+ NOTE: <tt>put</tt> and <tt>delete</tt> are also triggered when a
40
+ <tt>_method</tt> parameter is set to PUT or DELETE and the HTTP request method
41
+ is POST
42
+
43
+ == Routes
44
+
45
+ Routes are matched based on the order of declaration. The first route that
46
+ matches the request is invoked.
47
+
48
+ Simple:
49
+
50
+ get '/hi' do
51
+ ...
52
+ end
53
+
54
+ Named parameters:
55
+
56
+ get '/:name' do
57
+ # matches /sinatra and the like and sets params[:name]
58
+ end
59
+
60
+ Splat parameters:
61
+
62
+ get '/say/*/to/*' do
63
+ # matches /say/hello/to/world
64
+ params["splat"] # => ["hello", "world"]
65
+ end
66
+
67
+ get '/download/*.*' do
68
+ # matches /download/path/to/file.xml
69
+ params["splat"] # => ["path/to/file", "xml"]
70
+ end
71
+
72
+ User agent matching:
73
+
74
+ get '/foo', :agent => /Songbird (\d\.\d)[\d\/]*?/ do
75
+ "You're using Songbird version #{params[:agent][0]}"
76
+ end
77
+
78
+ get '/foo' do
79
+ # matches non-songbird browsers
80
+ end
81
+
82
+ == Static files
83
+
84
+ Put all of your static content in the ./public directory
85
+
86
+ root
87
+ \ public
88
+
89
+ If a file exists that maps to the REQUEST_PATH then it is served and the
90
+ request ends. Otherwise, Sinatra will look for an event that matches the
91
+ path.
92
+
93
+ == Views
94
+
95
+ Views are searched for in a "views" directory in the same location as
96
+ your main application.
97
+
98
+ === Haml Templates
99
+
100
+ get '/' do
101
+ haml :index
102
+ end
103
+
104
+ Renders <tt>./views/index.haml</tt>.
105
+
106
+ === Erb
107
+
108
+ get '/' do
109
+ erb :index
110
+ end
111
+
112
+ Renders <tt>./views/index.erb</tt>
113
+
114
+ === Builder
115
+
116
+ See Sinatra::Builder
117
+
118
+ === Sass
119
+
120
+ get '/stylesheet.css' do
121
+ content_type 'text/css', :charset => 'utf-8'
122
+ sass :stylesheet
123
+ end
124
+
125
+ Renders <tt>./views/stylesheet.sass</tt>.
126
+
127
+ === Inline Templates
128
+
129
+ get '/' do
130
+ haml '%div.title Hello World'
131
+ end
132
+
133
+ Renders the inlined template string.
134
+
135
+ === Accessing Variables
136
+
137
+ Templates are evaluated within the Sinatra::EventContext instance
138
+ used to evaluate event blocks. Instance variables set in event
139
+ blocks can be accessed direcly in views:
140
+
141
+ get '/:id' do
142
+ @foo = Foo.find(params[:id])
143
+ haml '%h1== @foo.name'
144
+ end
145
+
146
+ Or, specify an explicit Hash of local variables:
147
+
148
+ get '/:id' do
149
+ foo = Foo.find(params[:id])
150
+ haml '%h1== foo.name', :locals => { :foo => foo }
151
+ end
152
+
153
+ This is typically used when rendering templates as partials from within
154
+ other templates.
155
+
156
+ === In-file Templates
157
+
158
+ Templates may be defined at the end of the source file:
159
+
160
+ get '/' do
161
+ haml :index
162
+ end
163
+
164
+ use_in_file_templates!
165
+
166
+ __END__
167
+
168
+ @@ layout
169
+ X
170
+ = yield
171
+ X
172
+
173
+ @@ index
174
+ %div.title Hello world!!!!!
175
+
176
+ It's also possible to define named templates using the top-level template
177
+ method:
178
+
179
+ template :layout do
180
+ "X\n=yield\nX"
181
+ end
182
+
183
+ template :index do
184
+ '%div.title Hello World!'
185
+ end
186
+
187
+ get '/' do
188
+ haml :index
189
+ end
190
+
191
+ == Helpers
192
+
193
+ The top-level <tt>helpers</tt> method takes a block and extends all
194
+ EventContext instances with the methods defined:
195
+
196
+ helpers do
197
+ def bar(name)
198
+ "#{name}bar"
199
+ end
200
+ end
201
+
202
+ get '/:name' do
203
+ bar(params[:name])
204
+ end
205
+
206
+ == Filters
207
+
208
+ These are run in Sinatra::EventContext before every event.
209
+
210
+ before do
211
+ .. this code will run before each event ..
212
+ end
213
+
214
+ == Halt!
215
+
216
+ To immediately stop a request during a before filter or event use:
217
+
218
+ throw :halt
219
+
220
+ Set the body to the result of a helper method
221
+
222
+ throw :halt, :helper_method
223
+
224
+ Set the body to the result of a helper method after sending it parameters from
225
+ the local scope
226
+
227
+ throw :halt, [:helper_method, foo, bar]
228
+
229
+ Set the body to a simple string
230
+
231
+ throw :halt, 'this will be the body'
232
+
233
+ Set status then the body
234
+
235
+ throw :halt, [401, 'go away!']
236
+
237
+ Set the status then call a helper method with params from local scope
238
+
239
+ throw :halt, [401, [:helper_method, foo, bar]]
240
+
241
+ Run a proc inside the Sinatra::EventContext instance and set the body to the
242
+ result
243
+
244
+ throw :halt, lambda { puts 'In a proc!'; 'I just wrote to $stdout!' }
245
+
246
+ Create you own to_result
247
+
248
+ class MyResultObject
249
+ def to_result(event_context, *args)
250
+ event_context.body = 'This will be the body!
251
+ end
252
+ end
253
+
254
+ get '/' do
255
+ throw :halt, MyResultObject.new
256
+ end
257
+
258
+ Get the gist? If you want more fun with this then checkout <tt>to_result</tt>
259
+ on Array, Symbol, Fixnum, NilClass.
260
+
261
+ == Configuration and Reloading
262
+
263
+ Sinatra supports multiple environments and reloading. Reloading happens
264
+ before every request when running under the :development environment. Wrap
265
+ your configurations in <tt>configure</tt> (i.e. Database connections, Constants,
266
+ etc.) to protect them from reloading or to target specific environments.
267
+
268
+ All environments:
269
+
270
+ configure do
271
+ ...
272
+ end
273
+
274
+ Production:
275
+
276
+ configure :production do
277
+ ...
278
+ end
279
+
280
+ Two at a time:
281
+
282
+ configure :production, :test do
283
+ ...
284
+ end
285
+
286
+ This is also really nifty for error handling.
287
+
288
+ == Error handling
289
+
290
+ Error handlers run inside the current Sinatra::EventContext instance, which
291
+ means you get all the goodies it has to offer (i.e. haml, erb, throw :halt,
292
+ etc.)
293
+
294
+ === Not Found
295
+
296
+ When Sinatra::NotFound is raised, the not_found handler is invoked:
297
+
298
+ not_found do
299
+ 'This is nowhere to be found'
300
+ end
301
+
302
+ === Error
303
+
304
+ By default, the +error+ handler is invoked on Sinatra::ServerError or when
305
+ an unknown error occurs.
306
+
307
+ The exception can be obtained from the 'sinatra.error' variable in
308
+ request.env.
309
+
310
+ error do
311
+ 'Sorry there was a nasty error - ' + request.env['sinatra.error'].name
312
+ end
313
+
314
+ Custom errors:
315
+
316
+ error MyCustomError do
317
+ 'So what happened was...' + request.env['sinatra.error'].message
318
+ end
319
+
320
+ Then, if this happens:
321
+
322
+ get '/' do
323
+ raise MyCustomError, 'something bad'
324
+ end
325
+
326
+ You get this:
327
+
328
+ So what happened was... something bad
329
+
330
+ Sinatra installs special not_found and error handlers when running under
331
+ the development.
332
+
333
+ == Mime types
334
+
335
+ When using send_file or static files you may have mime types Sinatra doesn't
336
+ understand. Use +mime+ in those cases.
337
+
338
+ mime :foo, 'text/foo'
339
+
340
+ == Rack Middleware
341
+
342
+ Sinatra rides on Rack[http://rack.rubyforge.org/], a minimal standard
343
+ interface for Ruby web frameworks. One of Rack's most interesting capabilities
344
+ for application developers is support for "middleware" -- components that sit
345
+ between the server and your application monitoring and/or manipulating the
346
+ HTTP request/response to provide various types of common functionality.
347
+
348
+ Sinatra makes building Rack middleware pipelines a cinch via a top-level
349
+ +use+ method:
350
+
351
+ require 'sinatra'
352
+ require 'my_custom_middleware'
353
+
354
+ use Rack::Lint
355
+ use MyCustomMiddleware
356
+
357
+ get '/hello' do
358
+ 'Hello World'
359
+ end
360
+
361
+ The semantics of +use+ are identical to those defined for the
362
+ Rack::Builder[http://rack.rubyforge.org/doc/classes/Rack/Builder.html] DSL
363
+ (most frequently used from rackup files). For example, the +use+ method
364
+ accepts multiple/variable args as well as blocks:
365
+
366
+ use Rack::Auth::Basic do |username, password|
367
+ username == 'admin' && password == 'secret'
368
+ end
369
+
370
+ Rack is distributed with a variety of standard middleware for logging,
371
+ debugging, URL routing, authentication, and session handling. Sinatra uses
372
+ many of of these components automatically based on configuration so you
373
+ typically don't have to +use+ them explicitly.
374
+
375
+ == Testing
376
+
377
+ === Test/Unit
378
+
379
+ require 'rubygems'
380
+ require 'sinatra'
381
+ require 'sinatra/test/unit'
382
+ require 'my_sinatra_app'
383
+
384
+ class MyAppTest < Test::Unit::TestCase
385
+
386
+ def test_my_default
387
+ get_it '/'
388
+ assert_equal 'My Default Page!', @response.body
389
+ end
390
+
391
+ def test_with_agent
392
+ get_it '/', :agent => 'Songbird'
393
+ assert_equal 'You're in Songbird!', @response.body
394
+ end
395
+
396
+ ...
397
+
398
+ end
399
+
400
+ === Test/Spec
401
+
402
+ require 'rubygems'
403
+ require 'sinatra'
404
+ require 'sinatra/test/spec'
405
+ require 'my_sinatra_app'
406
+
407
+ describe 'My app' do
408
+
409
+ it "should show a default page" do
410
+ get_it '/'
411
+ should.be.ok
412
+ body.should.equal 'My Default Page!'
413
+ end
414
+
415
+ ...
416
+
417
+ end
418
+
419
+ === RSpec
420
+
421
+ require 'rubygems'
422
+ require 'spec'
423
+ require 'sinatra'
424
+ require 'sinatra/test/rspec'
425
+ require 'my_sinatra_app'
426
+
427
+ describe 'My app' do
428
+ it 'should show a default page' do
429
+ get_it '/'
430
+ @response.should be_ok
431
+ @response.body.should == 'My Default Page!'
432
+ end
433
+
434
+ ...
435
+
436
+ end
437
+
438
+ See Sinatra::Test::Methods for more information on +get_it+, +post_it+,
439
+ +put_it+, and friends.
440
+
441
+ == Command line
442
+
443
+ Sinatra applications can be run directly:
444
+
445
+ ruby myapp.rb [-h] [-x] [-p PORT] [-e ENVIRONMENT]
446
+
447
+ Options are:
448
+
449
+ -h # help
450
+ -p # set the port (default is 4567)
451
+ -e # set the environment (default is development)
452
+ -x # turn on the mutex lock (default is off)
453
+
454
+ == Contributing
455
+
456
+ === Tools
457
+
458
+ Besides Ruby itself, you only need a text editor, preferably one that supports
459
+ Ruby syntax hilighting. VIM and Emacs are a fine choice on any platform, but
460
+ feel free to use whatever you're familiar with.
461
+
462
+ Sinatra uses the Git source code management system. If you're unfamiliar with
463
+ Git, you can find more information and tutorials on http://git.or.cz/ as well
464
+ as http://git-scm.com/. Scott Chacon created a great series of introductory
465
+ screencasts about Git, which you can find here: http://www.gitcasts.com/
466
+
467
+ === First Time: Cloning The Sinatra Repo
468
+
469
+ cd where/you/keep/your/projects
470
+ git clone git://github.com/bmizerany/sinatra.git
471
+ cd sinatra
472
+ cd path/to/your_project
473
+ ln -s ../sinatra/
474
+
475
+ === Updating Your Existing Sinatra Clone
476
+
477
+ cd where/you/keep/sinatra
478
+ git pull
479
+
480
+ === Using Edge Sinatra in Your App
481
+
482
+ at the top of your sinatra_app.rb file:
483
+
484
+ $:.unshift File.dirname(__FILE__) + '/sinatra/lib'
485
+ require 'sinatra'
486
+
487
+ get '/about' do
488
+ "I'm running on Version " + Sinatra::VERSION
489
+ end
490
+
491
+ === Contributing a Patch
492
+
493
+ There are several ways to do this. Probably the easiest (and preferred) way is
494
+ to fork Sinatra on GitHub (http://github.com/bmizerany/sinatra), push your
495
+ changes to your Sinatra repo, and then send Blake Mizerany (bmizerany on
496
+ GitHub) a pull request.
497
+
498
+ You can also create a patch file and attach it to a feature request or bug fix
499
+ on the issue tracker (see below) or send it to the mailing list (see Community
500
+ section).
501
+
502
+ === Issue Tracking and Feature Requests
503
+
504
+ http://sinatra.lighthouseapp.com/
505
+
506
+ == Community
507
+
508
+ === Mailing List
509
+
510
+ http://groups.google.com/group/sinatrarb
511
+
512
+ If you have a problem or question, please make sure to include all the
513
+ relevant information in your mail, like the Sinatra version you're using, what
514
+ version of Ruby you have, and so on.
515
+
516
+ === IRC Channel
517
+
518
+ You can find us on the Freenode network in the channel #sinatra
519
+ (irc://chat.freenode.net/#sinatra)
520
+
521
+ There's usually someone online at any given time, but we cannot pay attention
522
+ to the channel all the time, so please stick around for a while after asking a
523
+ question.