sinatra 1.3.0.d → 1.3.0.e

Sign up to get free protection for your applications and to get access to all the features.

Potentially problematic release.


This version of sinatra might be problematic. Click here for more details.

Files changed (53) hide show
  1. data/.gitignore +6 -0
  2. data/.yardopts +4 -0
  3. data/CHANGES +80 -3
  4. data/Gemfile +18 -12
  5. data/README.de.rdoc +189 -381
  6. data/README.es.rdoc +193 -316
  7. data/README.fr.rdoc +327 -475
  8. data/README.jp.rdoc +7 -1
  9. data/README.rdoc +132 -101
  10. data/README.ru.rdoc +3 -3
  11. data/README.zh.rdoc +2 -2
  12. data/Rakefile +19 -27
  13. data/lib/sinatra/base.rb +186 -262
  14. data/lib/sinatra/version.rb +3 -0
  15. data/sinatra.gemspec +12 -128
  16. data/test/base_test.rb +1 -1
  17. data/test/builder_test.rb +1 -1
  18. data/test/coffee_test.rb +1 -1
  19. data/test/creole_test.rb +1 -1
  20. data/test/delegator_test.rb +9 -7
  21. data/test/encoding_test.rb +1 -1
  22. data/test/erb_test.rb +1 -1
  23. data/test/extensions_test.rb +1 -1
  24. data/test/filter_test.rb +7 -4
  25. data/test/haml_test.rb +1 -1
  26. data/test/helper.rb +16 -1
  27. data/test/helpers_test.rb +12 -1
  28. data/test/less_test.rb +1 -1
  29. data/test/liquid_test.rb +1 -1
  30. data/test/mapped_error_test.rb +44 -1
  31. data/test/markaby_test.rb +1 -1
  32. data/test/markdown_test.rb +1 -1
  33. data/test/middleware_test.rb +1 -1
  34. data/test/nokogiri_test.rb +1 -1
  35. data/test/radius_test.rb +1 -1
  36. data/test/rdoc_test.rb +2 -2
  37. data/test/readme_test.rb +136 -0
  38. data/test/request_test.rb +1 -1
  39. data/test/response_test.rb +13 -3
  40. data/test/result_test.rb +3 -3
  41. data/test/route_added_hook_test.rb +1 -1
  42. data/test/routing_test.rb +9 -2
  43. data/test/sass_test.rb +1 -1
  44. data/test/scss_test.rb +1 -1
  45. data/test/server_test.rb +1 -1
  46. data/test/settings_test.rb +55 -22
  47. data/test/sinatra_test.rb +1 -1
  48. data/test/slim_test.rb +1 -1
  49. data/test/static_test.rb +22 -1
  50. data/test/templates_test.rb +1 -1
  51. data/test/textile_test.rb +1 -1
  52. metadata +47 -59
  53. data/lib/sinatra/rack.rb +0 -44
@@ -0,0 +1,6 @@
1
+ # please add general patterns to your global ignore list
2
+ # see https://github.com/github/gitignore#readme
3
+
4
+ /pkg
5
+ /doc/api
6
+ /Gemfile.lock
@@ -0,0 +1,4 @@
1
+ --readme README.rdoc
2
+ --title 'Sinatra API Documentation'
3
+ --charset utf-8
4
+ 'lib/**/*.rb' - '*.rdoc'
data/CHANGES CHANGED
@@ -10,22 +10,99 @@
10
10
  explicitly to prevent that behavior. (Magnus Holm, Ryan Tomayko, Konstantin
11
11
  Haase)
12
12
 
13
+ * Patterns now match against the escaped URLs rather than the unescaped
14
+ version. This makes Sinatra confirm with RFC 2396 section 2.2 and RFC 2616
15
+ section 3.2.3 (escaped reserved characters should not be treated like the
16
+ unescaped version), meaning that "/:name" will also match `/foo%2Fbar`, but
17
+ not `/foo/bar`. To avoid incompatibility, pattern matching has been adjusted.
18
+ Moreover, since we do no longer need to keep an unescaped version of
19
+ path_info around, we handle all changes to `env['PATH_INFO']` correctly.
20
+ (Konstantin Haase)
21
+
22
+ * `settings.app_file` now defaults to the file subclassing `Sinatra::Base` in
23
+ modular applications. (Konstantin Haase)
24
+
13
25
  * Set up `Rack::Logger` or `Rack::NullLogger` depending on whether logging
14
26
  was enabled or not. Also, expose that logger with the `logger` helper
15
27
  method. (Konstantin Haase)
16
28
 
17
29
  * The sessions setting now may be an options hash. (Konstantin Haase)
18
30
 
19
- * Important: 1.8.6 support has been dropped. It is still usable if you use the
20
- backports gem, but no longer officially supported. (Konstantin Haase)
31
+ * Important: 1.8.6 support has been dropped. This version also depends on at
32
+ least Rack 1.3.0. This means that it is incompatible to Rails prior to 3.1.0.
33
+ Please use 1.2.x if you require an earlier version for Ruby or Rack, which we
34
+ will continue to supply with bug fixes. (Konstantin Haase)
21
35
 
22
36
  * It is now possible to use a different target class for the top level DSL (aka
23
37
  classic style) than `Sinatra::Application` by setting `Delegator.target`.
24
38
  This was mainly introduced to ease testing. (Konstantin Haase)
25
39
 
40
+ * Error handlers defined for an error class will now also handle subclasses of
41
+ that class, unless more specific error handlers exist. (Konstantin Haase)
42
+
43
+ * Error handling respects Exception#code, again. (Konstantin Haase)
44
+
45
+ * Changing a setting will merge hashes: `set(:x, :a => 1); set(:x :b => 2)`
46
+ will result in `{:a => 1, :b => 2}`. Use `set(:x, {:a => 1}, true)` to avoid
47
+ this behavior. (Konstantin Haase)
48
+
26
49
  * Added `request.accept?` and `request.preferred_type` to ease dealing with
27
50
  `Accept` headers. (Konstantin Haase)
28
51
 
52
+ * Uses SecureRandom to generate default session secret. (Konstantin Haase)
53
+
54
+ * `Sinatra.run!` now prints to stderr rather than stdout. (Andrew Armenia)
55
+
56
+ * Automatic `app_file` detection now works in directories containing brackets
57
+ (Konstantin Haase)
58
+
59
+ * Improved documentation. (Emanuele Vicentini, Peter Higgins, Takanori
60
+ Ishikawa, Konstantin Haase)
61
+
62
+ * Also specify charset in Content-Type header for JSON. (Konstantin Haase)
63
+
64
+ * Rack handler names will not be converted to lower case internally, this
65
+ allows you to run Sinatra with custom Rack handlers, like Kirk or Mongrel2.
66
+ Example: `ruby app.rb -s Mongrel2` (Konstantin Haase)
67
+
68
+ * Middleware setup is now distributed across multiple methods, allowing Sinatra
69
+ extensions to easily hook into the setup process. (Konstantin Haase)
70
+
71
+ * Internal refactoring and minor performance improvements. (Konstantin Haase)
72
+
73
+ = 1.2.7 (backports release) / Not Yet Released
74
+
75
+ Custom changes:
76
+
77
+ * Fix Ruby 1.8.6 issue with Accept header parsing. (Konstantin Haase)
78
+
79
+ Backported from 1.3.0:
80
+
81
+ * `Sinatra.run!` now prints to stderr rather than stdout. (Andrew Armenia)
82
+
83
+ * Automatic `app_file` detection now works in directories containing brackets
84
+ (Konstantin Haase)
85
+
86
+ * Improved documentation. (Emanuele Vicentini, Peter Higgins, Takanori
87
+ Ishikawa, Konstantin Haase)
88
+
89
+ * Also specify charset in Content-Type header for JSON. (Konstantin Haase)
90
+
91
+ * Rack handler names will not be converted to lower case internally, this
92
+ allows you to run Sinatra with custom Rack handlers, like Kirk or Mongrel2.
93
+ Example: `ruby app.rb -s Mongrel2` (Konstantin Haase)
94
+
95
+ * Fix uninitialized instance variable warning. (David Kellum)
96
+
97
+ = 1.2.6 / 2011-05-01
98
+
99
+ * Fix broken delegation, backport delegation tests from Sinatra 1.3.
100
+ (Konstantin Haase)
101
+
102
+ = 1.2.5 / 2011-04-30
103
+
104
+ * Restore compatibility with Ruby 1.8.6. (Konstantin Haase)
105
+
29
106
  = 1.2.4 / 2011-04-30
30
107
 
31
108
  * Sinatra::Application (classic style) does not use a session secret in
@@ -149,7 +226,7 @@
149
226
  * Sinatra now ships with a Gemfile for development dependencies, since it eases
150
227
  supporting different platforms, like JRuby. (Konstantin Haase)
151
228
 
152
- = 1.1.4 / 2011-04-13
229
+ = 1.1.4 (backports release) / 2011-04-13
153
230
 
154
231
  * Compatible with Tilt 1.3. (Konstantin Haase)
155
232
 
data/Gemfile CHANGED
@@ -7,40 +7,46 @@
7
7
  # If you have issues with a gem: `bundle install --without-coffee-script`.
8
8
 
9
9
  RUBY_ENGINE = 'ruby' unless defined? RUBY_ENGINE
10
- TILT_REPO = "git://github.com/rtomayko/tilt.git"
11
-
12
10
  source :rubygems unless ENV['QUICK']
13
- gemspec
14
11
 
15
12
  gem 'rake'
16
13
  gem 'rack-test', '>= 0.5.6'
17
14
 
18
15
  # Allows stuff like `tilt=1.2.2 bundle install` or `tilt=master ...`.
19
16
  # Used by the CI.
20
- tilt = (ENV['tilt'] || 'stable').dup
21
- tilt.sub! 'tilt-', ''
22
- if tilt != 'stable'
23
- tilt = {:git => TILT_REPO, :branch => tilt} unless tilt =~ /(\d+\.)+\d+/
24
- gem 'tilt', tilt
17
+ github = "git://github.com/%s.git"
18
+ repos = { 'tilt' => github % "rtomayko/tilt", 'rack' => github % "rack/rack" }
19
+ %w[tilt rack].each do |lib|
20
+ dep = (ENV[lib] || 'stable').sub "#{lib}-", ''
21
+ dep = nil if dep == 'stable'
22
+ dep = {:git => repos[lib], :branch => dep} if dep and dep !~ /(\d+\.)+\d+/
23
+ gem lib, dep
25
24
  end
26
25
 
27
26
  gem 'haml', '>= 3.0', :group => 'haml'
28
27
  gem 'sass', :group => 'sass'
29
28
  gem 'builder', :group => 'builder'
30
29
  gem 'erubis', :group => 'erubis'
31
- gem 'less', :group => 'less'
30
+ gem 'less', '~> 1.0', :group => 'less'
32
31
  gem 'liquid', :group => 'liquid'
33
- gem 'nokogiri', :group => 'nokogiri'
34
32
  gem 'slim', :group => 'slim'
35
- gem 'RedCloth', :group => 'redcloth'
33
+ gem 'RedCloth', :group => 'redcloth' if RUBY_VERSION < "1.9.3" and not RUBY_ENGINE.start_with? 'ma'
36
34
  gem 'coffee-script', '>= 2.0', :group => 'coffee-script'
37
35
  gem 'rdoc', :group => 'rdoc'
38
36
  gem 'kramdown', :group => 'kramdown'
39
37
  gem 'maruku', :group => 'maruku'
40
38
  gem 'creole', :group => 'creole'
41
39
 
42
- platforms :ruby do
40
+ gem 'nokogiri', :group => 'nokogiri' if RUBY_ENGINE != 'maglev'
41
+ #nokogiri_options = {:group => 'nokogiri'}
42
+ #nokogiri_options[:git] = "https://github.com/MagLev/nokogiri.git" if RUBY_ENGINE == 'maglev'
43
+ #gem 'nokogiri', nokogiri_options if RUBY_ENGINE != 'maglev'
44
+
45
+ unless RUBY_ENGINE == 'jruby' && JRUBY_VERSION < "1.6.1"
46
+ # C extensions
43
47
  gem 'rdiscount', :group => 'rdiscount'
48
+ gem 'redcarpet', :group => 'redcarpet'
49
+
44
50
  ## bluecloth is broken
45
51
  #gem 'bluecloth', :group => 'bluecloth'
46
52
  end
@@ -44,7 +44,7 @@ definiert. Jeder dieser Routen wird ein Ruby-Block zugeordnet:
44
44
  end
45
45
 
46
46
  options '/' do
47
- .. lege etwas fest ..
47
+ .. zeige, was wir können ..
48
48
  end
49
49
 
50
50
  Die Routen werden in der Reihenfolge durchlaufen, in der sie definiert wurden.
@@ -78,6 +78,12 @@ Routen-Muster können auch mit Splat- oder Wildcard-Parametern über das
78
78
  params[:splat] # => ["pfad/zu/datei", "xml"]
79
79
  end
80
80
 
81
+ Oder mit Block-Parametern:
82
+
83
+ get '/download/*.*' do |pfad, endung|
84
+ [pfad, endung] # => ["Pfad/zu/Datei", "xml"]
85
+ end
86
+
81
87
  Routen mit regulären Ausdrücken sind auch möglich:
82
88
 
83
89
  get %r{/hallo/([\w]+)} do
@@ -221,420 +227,213 @@ werden:
221
227
 
222
228
  set :views, File.dirname(__FILE__) + '/templates'
223
229
 
224
- Eine wichtige Sache, die man sich hierbei merken sollte, ist, dass man immer
225
- mit Symbols auf Templates verweisen sollte, auch wenn sich ein Template in
226
- einem Unterordner befindet (in diesen Fall <tt>:'subdir/template'</tt>).
227
- Rendering-Methoden rendern jeden String direkt.
228
-
229
- === Haml-Templates
230
-
231
- Das +haml+-Gem wird benötigt, um Haml-Templates rendern zu können:
232
-
233
- # haml muss eingebunden werden
234
- require 'haml'
235
-
236
- get '/' do
237
- haml :index
238
- end
239
-
240
- Dieser Code rendert <tt>./views/index.haml</tt>.
241
-
242
- {Haml-Optionen}[http://haml-lang.com/docs/yardoc/file.HAML_REFERENCE.html#options]
243
- können global durch die Sinatra-Konfiguration gesetzt werden,
244
- siehe {Optionen und Konfiguration}[http://www.sinatrarb.com/configuration.html],
245
- und individuell überschrieben werden.
246
-
247
- set :haml, :format => :html5 # Standard-Haml-Format ist :xhtml
248
-
249
- get '/' do
250
- haml :index, :format => :html4 # überschrieben
251
- end
252
-
253
- === Erb-Templates
254
-
255
- # erb muss eingebunden werden
256
- require 'erb'
257
-
258
- get '/' do
259
- erb :index
260
- end
261
-
262
- Dieser Code rendert <tt>./views/index.erb</tt>.
263
-
264
- === Erubis
265
-
266
- Das +erubis+-Gem wird benötigt, um Erubis-Templates rendern zu können:
267
-
268
- # erbubis muss eingebunden werden
269
- require 'erubis'
270
-
271
- get '/' do
272
- erubis :index
273
- end
274
-
275
- Dieser Code rendert <tt>./views/index.erubis</tt>.
276
-
277
- Es ist auch möglich, Erb durch Erubis zu ersetzen:
278
-
279
- require 'erubis'
280
- Tilt.register :erb, Tilt[:erubis]
281
-
282
- get '/' do
283
- erb :index
284
- end
285
-
286
- Dieser Code rendert ebenfalls <tt>./views/index.erb</tt>.
287
-
288
- === Builder-Templates
230
+ Es ist zu beachten, dass immer mit Symbolen auf Templates verwiesen werden
231
+ muss, auch dann, wenn sie sich in einem Unterordner befinden:
289
232
 
290
- Das +builder+-Gem wird benötigt, um Builder-Templates rendern zu können:
233
+ haml :'unterverzeichnis/template'
291
234
 
292
- # builder muss eingebunden werden
293
- require 'builder'
294
-
295
- get '/' do
296
- builder :index
297
- end
298
-
299
- Dieser Code rendert <tt>./views/index.builder</tt>.
300
-
301
- === Nokogiri-Templates
302
-
303
- Das +nokogiri+-Gem wird benötigt, um Nokogiri-Templates rendern zu können:
304
-
305
- # nokogiri muss eingebunden werden
306
- require 'nokogiri'
307
-
308
- get '/' do
309
- nokogiri :index
310
- end
311
-
312
- Dieser Code rendert <tt>./views/index.nokogiri</tt>.
313
-
314
- === Sass-Templates
315
-
316
- Das +haml+- oder +sass+-Gem wird benötigt, um Sass-Templates rendern zu können:
317
-
318
- # sass muss eingebunden werden
319
- require 'sass'
320
-
321
- get '/stylesheet.css' do
322
- sass :stylesheet
323
- end
324
-
325
- Dieser Code rendert <tt>./views/stylesheet.sass</tt>.
326
-
327
- {Sass-Optionen}[http://sass-lang.com/docs/yardoc/file.SASS_REFERENCE.html#options]
328
- können global durch die Sinatra-Konfiguration gesetzt werden, siehe
329
- {Optionen und Konfiguration}[http://www.sinatrarb.com/configuration.html],
330
- und individuell überschrieben werden.
331
-
332
- set :sass, :style => :compact # Standard Sass-Style ist :nested
333
-
334
- get '/stylesheet.css' do
335
- sass :stylesheet, :style => :expanded # überschrieben
336
- end
337
-
338
- === SCSS-Templates
339
-
340
- Das +haml+- oder +sass+-Gem wird benötigt, um SCSS-Templates rendern zu können:
341
-
342
- # sass muss eingebunden werden
343
- require 'sass'
344
-
345
- get '/stylesheet.css' do
346
- scss :stylesheet
347
- end
348
-
349
- Dieser Code rendert <tt>./views/stylesheet.scss</tt>.
350
-
351
- {SCSS-Optionen}[http://sass-lang.com/docs/yardoc/file.SASS_REFERENCE.html#options]
352
- können global durch die Sinatra-Konfiguration gesetzt werden, siehe
353
- {Optionen und Konfiguration}[http://www.sinatrarb.com/configuration.html], und
354
- individuell überschrieben werden.
355
-
356
- set :scss, :style => :compact # Standard-SCSS-Style ist :nested
357
-
358
- get '/stylesheet.css' do
359
- scss :stylesheet, :style => :expanded # überschrieben
360
- end
361
-
362
- === Less-Templates
363
-
364
- Das +less+-Gem wird benötigt, um Less-Templates rendern zu können:
365
-
366
- # less muss eingebunden werden
367
- require 'less'
368
-
369
- get '/stylesheet.css' do
370
- less :stylesheet
371
- end
372
-
373
- Dieser Code rendert <tt>./views/stylesheet.less</tt>.
374
-
375
- === Liquid-Templates
376
-
377
- Das +liquid+-Gem wird benötigt, um Liquid-Templates rendern zu können:
378
-
379
- # liquid muss eingebunden werden
380
- require 'liquid'
381
-
382
- get '/' do
383
- liquid :index
384
- end
385
-
386
- Dieser Code rendert <tt>./views/index.liquid</tt>.
387
-
388
- Da aus Liquid-Templates heraus keine Methoden (abgesehen von +yield+)
389
- aufgerufen werden können, ist es möglich, +locals+ zu übergeben:
390
-
391
- liquid :index, :locals => { :key => 'value' }
392
-
393
- === Markdown-Templates
394
-
395
- Das +rdiscount+-Gem wird benötigt, um Markdown-Templates rendern zu können:
396
-
397
- # rdiscount muss eingebunden werden
398
- require "rdiscount"
399
-
400
- get '/' do
401
- markdown :index
402
- end
403
-
404
- Dieser Code rendert <tt>./views/index.markdown</tt> (+md+ und +mkd+ sind
405
- ebenfalls zulässige Dateiendungen).
406
-
407
- Da es weder möglich ist, Methoden aufzurufen, noch +locals+ zu übergeben, ist
408
- es am sinnvollsten, Markdown in Kombination mit einer anderen Template-Engine
409
- zu nutzen:
410
-
411
- erb :overview, :locals => { :text => markdown(:introduction) }
412
-
413
- Es ist auch möglich, die +markdown+-Methode aus anderen Templates heraus
414
- aufzurufen:
415
-
416
- %h1 Hallo von Haml!
417
- %p= markdown(:greetings)
418
-
419
- Da man Ruby aus Markdown heraus nicht aufrufen kann, ist es nicht möglich,
420
- Layouts zu verwenden, die in Markdown geschrieben sind. Es ist aber möglich,
421
- einen anderen Renderer für das Template zu verwenden als für das Layout, indem
422
- man die <tt>:layout_engine</tt>-Option angibt:
423
-
424
- get '/' do
425
- markdown :index, :layout_engine => :erb
426
- end
427
-
428
- Das wird <tt>./views/index.md</tt> mit <tt>./views/layout.erb</tt> als Layout
429
- rendern.
430
-
431
- Denk daran, dass solche Einstellungen auch global gesetzt werden können:
432
-
433
- set :markdown, :layout_engine => :haml, :layout => :post
434
-
435
- get '/' do
436
- markdown :index
437
- end
438
-
439
- Das wird <tt>./views/index.md</tt> (und jedes andere Markdown-Template) mit
440
- <tt>./views/post.haml</tt> als Layout rendern.
441
-
442
- Ebenso ist es möglich, Markdown mit BlueCloth anstelle von RDiscount zu parsen:
443
-
444
- require 'bluecloth'
445
-
446
- Tilt.register 'markdown', BlueClothTemplate
447
- Tilt.register 'mkd', BlueClothTemplate
448
- Tilt.register 'md', BlueClothTemplate
449
-
450
- get '/' do
451
- markdown :index
452
- end
453
-
454
- Das sollte <tt>./views/index.md</tt> mit BlueCloth rendern.
455
-
456
- === Textile-Templates
457
-
458
- Das +redcloth+-Gem wird benötigt, um Textile-Templates rendern zu können:
235
+ Rendering-Methoden rendern jeden String direkt.
459
236
 
460
- # redcloth muss eingebunden werden
461
- require "redcloth"
237
+ === Verfügbare Templatesprachen
462
238
 
463
- get '/' do
464
- textile :index
465
- end
239
+ Einige Sprachen haben mehrere Implementierungen. Um festzulegen, welche
240
+ verwendet wird (und dann auch Thread-sicher ist), verwendet man am besten zu
241
+ Beginn ein 'require':
466
242
 
467
- Dieser Code rendert <tt>./views/index.textile</tt>.
243
+ require 'rdiscount' # oder require 'bluecloth'
244
+ get('/') { markdown :index }
468
245
 
469
- Da es weder möglich ist, Methoden aufzurufen, noch +locals+ zu übergeben, ist
470
- es sinnvoll, Textile in Kombination mit einer anderen Template-Engine zu
471
- nutzen:
246
+ === Haml Templates
472
247
 
473
- erb :overview, :locals => { :text => textile(:introduction) }
248
+ Abhängigkeit:: {haml}[http://haml-lang.com/]
249
+ Dateierweiterungs:: <tt>.haml</tt>
250
+ Beispiel:: <tt>haml :index, :format => :html5</tt>
474
251
 
475
- Es ist auch möglich, die +textile+-Methode aus anderen Templates heraus
476
- aufzurufen:
252
+ === Erb Templates
477
253
 
478
- %h1 Hallo von Haml!
479
- %p= textile(:greetings)
254
+ Abhängigkeit:: {erubis}[http://www.kuwata-lab.com/erubis/] oder
255
+ erb (included in Ruby)
256
+ Dateierweiterungs:: <tt>.erb</tt>, <tt>.rhtml</tt> oder <tt>.erubis</tt>
257
+ (nur Erubis)
258
+ Beispiel:: <tt>erb :index</tt>
480
259
 
481
- Da man Ruby aus Textile heraus nicht aufrufen kann, ist es nicht möglich,
482
- Layouts zu verwenden, die in Textile geschrieben sind. Es ist aber möglich,
483
- einen anderen Renderer für das Template zu verwenden als für das Layout, indem
484
- man die <tt>:layout_engine</tt>-Option angibt:
260
+ === Builder Templates
485
261
 
486
- get '/' do
487
- textile :index, :layout_engine => :erb
488
- end
262
+ Abhängigkeit:: {builder}[http://builder.rubyforge.org/]
263
+ Dateierweiterungs:: <tt>.builder</tt>
264
+ Beispiel:: <tt>builder { |xml| xml.em "Hallo" }</tt>
489
265
 
490
- Das wird <tt>./views/index.textile</tt> mit <tt>./views/layout.erb</tt> als
491
- Layout rendern.
266
+ Nimmt ebenso einen Block für Inline-Templates entgegen (siehe Beispiel).
492
267
 
493
- Denk daran, dass solche Einstellungen auch global gesetzt werden können:
268
+ === Nokogiri Templates
494
269
 
495
- set :textile, :layout_engine => :haml, :layout => :post
270
+ Abhängigkeit:: {nokogiri}[http://nokogiri.org/]
271
+ Dateierweiterungs:: <tt>.nokogiri</tt>
272
+ Beispiel:: <tt>nokogiri { |xml| xml.em "Hallo" }</tt>
496
273
 
497
- get '/' do
498
- textile :index
499
- end
274
+ Nimmt ebenso einen Block für Inline-Templates entgegen (siehe Beispiel).
500
275
 
501
- Das wird <tt>./views/index.textile</tt> (und jedes andere Markdown-Template)
502
- mit <tt>./views/post.haml</tt> als Layout rendern.
276
+ === Sass Templates
503
277
 
504
- === RDoc-Templates
278
+ Abhängigkeit:: {sass}[http://sass-lang.com/]
279
+ Dateierweiterungs:: <tt>.sass</tt>
280
+ Beispiel:: <tt>sass :stylesheet, :style => :expanded</tt>
505
281
 
506
- Das +rdoc+-Gem wird benötigt, um RDoc-Templates rendern zu können:
282
+ === SCSS Templates
507
283
 
508
- # rdoc/markup/to_html muss eingebunden werden
509
- require "rdoc/markup/to_html"
284
+ Abhängigkeit:: {sass}[http://sass-lang.com/]
285
+ Dateierweiterungs:: <tt>.scss</tt>
286
+ Beispiel:: <tt>scss :stylesheet, :style => :expanded</tt>
510
287
 
511
- get '/' do
512
- rdoc :index
513
- end
288
+ === Less Templates
514
289
 
515
- Dieser Code rendert <tt>./views/index.rdoc</tt>.
290
+ Abhängigkeit:: {less}[http://www.lesscss.org/]
291
+ Dateierweiterungs:: <tt>.less</tt>
292
+ Beispiel:: <tt>less :stylesheet</tt>
516
293
 
517
- Da es weder möglich ist, Methoden aufzurufen, noch +locals+ zu übergeben, ist
518
- es sinnvoll, RDoc in Kombination mit einer anderen Template-Engine zu nutzen:
294
+ === Liquid Templates
519
295
 
520
- erb :overview, :locals => { :text => rdoc(:introduction) }
296
+ Abhängigkeit:: {liquid}[http://www.liquidmarkup.org/]
297
+ Dateierweiterungs:: <tt>.liquid</tt>
298
+ Beispiel:: <tt>liquid :index, :locals => { :key => 'Wert' }</tt>
521
299
 
522
- Es ist auch möglich, die +rdoc+-Methode aus anderen Templates heraus
523
- aufzurufen:
300
+ Da man aus dem Liquid-Template heraus keine Ruby-Methoden aufrufen kann
301
+ (ausgenommen +yield+), wird man üblicherweise locals verwenden wollen, mit
302
+ denen man Variablen weitergibt.
524
303
 
525
- %h1 Hallo von Haml!
526
- %p= rdoc(:greetings)
304
+ === Markdown Templates
527
305
 
528
- Da man Ruby aus RDoc heraus nicht aufrufen kann, ist es nicht möglich, Layouts
529
- zu verwenden, die in RDoc geschrieben sind. Es ist aber möglich, einen anderen
530
- Renderer für das Template zu verwenden als für das Layout, indem man die
531
- <tt>:layout_engine</tt> option angibt:
306
+ Abhängigkeit:: {rdiscount}[https://github.com/rtomayko/rdiscount],
307
+ {redcarpet}[https://github.com/tanoku/redcarpet],
308
+ {bluecloth}[http://deveiate.org/projects/BlueCloth],
309
+ {kramdown}[http://kramdown.rubyforge.org/] *oder*
310
+ {maruku}[http://maruku.rubyforge.org/]
311
+ Dateierweiterungs:: <tt>.markdown</tt>, <tt>.mkd</tt> und <tt>.md</tt>
312
+ Beispiel:: <tt>markdown :index, :layout_engine => :erb</tt>
532
313
 
533
- get '/' do
534
- rdoc :index, :layout_engine => :erb
535
- end
314
+ Da man aus den Markdown-Templates heraus keine Ruby-Methoden aufrufen und auch
315
+ keine locals verwenden kann, wird man Markdown üblicherweise in Kombination mit
316
+ anderen Renderern verwenden wollen:
536
317
 
537
- Das wird <tt>./views/index.rdoc</tt> mit <tt>./views/layout.erb</tt> als Layout
538
- rendern.
318
+ erb :overview, :locals => { :text => markdown(:einfuehrung) }
539
319
 
540
- Denk daran, dass solche Einstellungen auch global gesetzt werden können:
320
+ Beachte, dass man die +markdown+-Methode auch aus anderen Templates heraus
321
+ aufrufen kann:
541
322
 
542
- set :rdoc, :layout_engine => :haml, :layout => :post
323
+ %h1 Gruß von Haml!
324
+ %p= markdown(:Grüsse)
543
325
 
544
- get '/' do
545
- rdoc :index
546
- end
326
+ Da man Ruby nicht von Markdown heraus aufrufen kann, können auch Layouts nicht
327
+ in Markdown geschrieben werden. Es ist aber möglich, einen Renderer für die
328
+ Templates zu verwenden und einen anderen für das Layout, indem die
329
+ <tt>:layout_engine</tt>-Option verwendet wird.
547
330
 
548
- Das wird <tt>./views/index.rdoc</tt> (und jedes andere Markdown-Template) mit
549
- <tt>./views/post.haml</tt> als Layout rendern.
331
+ === Textile Templates
550
332
 
551
- === Radius-Templates
333
+ Abhängigkeit:: {RedCloth}[http://redcloth.org/]
334
+ Dateierweiterungs:: <tt>.textile</tt>
335
+ Beispiel:: <tt>textile :index, :layout_engine => :erb</tt>
552
336
 
553
- Das +radius+-Gem wird benötigt, um Radius-Templates rendern zu können:
337
+ Da man aus dem Textile-Template heraus keine Ruby-Methoden aufrufen und auch
338
+ keine locals verwenden kann, wird man Textile üblicherweise in Kombination mit
339
+ anderen Renderern verwenden wollen:
554
340
 
555
- # radius muss eingebunden werden
556
- require 'radius'
341
+ erb :overview, :locals => { :text => textile(:einfuehrung) }
557
342
 
558
- get '/' do
559
- radius :index
560
- end
343
+ Beachte, dass man die +textile+-Methode auch aus anderen Templates heraus
344
+ aufrufen kann:
561
345
 
562
- Dieser Code rendert <tt>./views/index.radius</tt>.
346
+ %h1 Gruß von Haml!
347
+ %p= textile(:Grüsse)
563
348
 
564
- Da aus Radius-Templates heraus keine Methoden (abgesehen von +yield+)
565
- aufgerufen werden können, es es möglich, +locals+ zu übergeben:
349
+ Da man Ruby nicht von Textile heraus aufrufen kann, können auch Layouts nicht
350
+ in Textile geschrieben werden. Es ist aber möglich, einen Renderer für die
351
+ Templates zu verwenden und einen anderen für das Layout, indem die
352
+ <tt>:layout_engine</tt>-Option verwendet wird.
566
353
 
567
- radius :index, :locals => { :key => 'value' }
354
+ === RDoc Templates
568
355
 
569
- === Markaby-Templates
356
+ Abhängigkeit:: {rdoc}[http://rdoc.rubyforge.org/]
357
+ Dateierweiterungs:: <tt>.rdoc</tt>
358
+ Beispiel:: <tt>textile :README, :layout_engine => :erb</tt>
570
359
 
571
- Das +markaby+-Gem wird benötigt, um Markaby-Templates rendern zu können:
360
+ Da man aus dem RDoc-Template heraus keine Ruby-Methoden aufrufen und auch
361
+ keine locals verwenden kann, wird man RDoc üblicherweise in Kombination mit
362
+ anderen Renderern verwenden wollen:
572
363
 
573
- # markaby muss eingebunden werden
574
- require 'markaby'
364
+ erb :overview, :locals => { :text => rdoc(:einfuehrung) }
575
365
 
576
- get '/' do
577
- markaby :index
578
- end
366
+ Beachte, dass man die +rdoc+-Methode auch aus anderen Templates heraus
367
+ aufrufen kann:
579
368
 
580
- Dieser Code rendert <tt>./views/index.mab</tt>.
369
+ %h1 Gruß von Haml!
370
+ %p= rdoc(:Grüße)
581
371
 
582
- === Slim-Templates
372
+ Da man Ruby nicht von RDoc heraus aufrufen kann, können auch Layouts nicht
373
+ in RDoc geschrieben werden. Es ist aber möglich, einen Renderer für die
374
+ Templates zu verwenden und einen anderen für das Layout, indem die
375
+ <tt>:layout_engine</tt>-Option verwendet wird.
583
376
 
584
- Das +slim+-Gem wird benötigt, um Slim-Templates rendern zu können:
377
+ === Radius Templates
585
378
 
586
- # slim muss eingebunden werden
587
- require 'slim'
379
+ Abhängigkeit:: {radius}[http://radius.rubyforge.org/]
380
+ Dateierweiterungs:: <tt>.radius</tt>
381
+ Beispiel:: <tt>radius :index, :locals => { :key => 'Wert' }</tt>
588
382
 
589
- get '/' do
590
- slim :index
591
- end
383
+ Da man aus dem Radius-Template heraus keine Ruby-Methoden aufrufen kann, wird
384
+ man üblicherweise locals verwenden wollen, mit denen man Variablen weitergibt.
592
385
 
593
- Dieser Code rendert <tt>./views/index.slim</tt>.
386
+ === Markaby Templates
594
387
 
595
- === Creole-Templates
388
+ Abhängigkeit:: {markaby}[http://markaby.github.com/]
389
+ Dateierweiterungs:: <tt>.mab</tt>
390
+ Beispiel:: <tt>markaby { h1 "Willkommen!" }</tt>
596
391
 
597
- Das +creole+-Gem wird benötigt, um Creole-Templates rendern zu können:
392
+ Nimmt ebenso einen Block für Inline-Templates entgegen (siehe Beispiel).
598
393
 
599
- # creole muss eingebunden werden
600
- require 'creole'
394
+ === Slim Templates
601
395
 
602
- get '/' do
603
- creole :index
604
- end
396
+ Abhängigkeit:: {slim}[http://slim-lang.com/]
397
+ Dateierweiterungs:: <tt>.slim</tt>
398
+ Beispiel:: <tt>slim :index</tt>
605
399
 
606
- Dieser Code rendert <tt>./views/index.creole</tt>.
400
+ === Creole Templates
607
401
 
608
- === CoffeeScript-Templates
402
+ Abhängigkeit:: {creole}[https://github.com/minad/creole]
403
+ Dateierweiterungs:: <tt>.creole</tt>
404
+ Beispiel:: <tt>creole :wiki, :layout_engine => :erb</tt>
609
405
 
610
- Das <tt>coffee-script</tt>-Gem und mindestens eine der folgenden Optionen
611
- werden benötigt, um JavaScript auf dem Server ausführen zu können:
406
+ Da man aus dem Creole-Template heraus keine Ruby-Methoden aufrufen und auch
407
+ keine locals verwenden kann, wird man Creole üblicherweise in Kombination mit
408
+ anderen Renderern verwenden wollen:
612
409
 
613
- * +node+ (von Node.js) befindet sich im Pfad
614
- * du bist unter OS X
615
- * +therubyracer+ gem/library
410
+ erb :overview, :locals => { :text => creole(:einfuehrung) }
616
411
 
617
- Siehe auch http://github.com/josh/ruby-coffee-script für eine vollständige
618
- Liste aller Optionen.
412
+ Beachte, dass man die +creole+-Methode auch aus anderen Templates heraus
413
+ aufrufen kann:
619
414
 
620
- Nun können CoffeeScript-Templates in der Applikation gerendert werden:
415
+ %h1 Gruß von Haml!
416
+ %p= creole(:Grüße)
621
417
 
622
- # coffee-script muss eingebunden werden
623
- require 'coffee-script'
418
+ Da man Ruby nicht von Creole heraus aufrufen kann, können auch Layouts nicht
419
+ in Creole geschrieben werden. Es ist aber möglich, einen Renderer für die
420
+ Templates zu verwenden und einen anderen für das Layout, indem die
421
+ <tt>:layout_engine</tt>-Option verwendet wird.
624
422
 
625
- get '/application.js' do
626
- coffee :application
627
- end
423
+ === CoffeeScript Templates
628
424
 
629
- Dieser Code rendert <tt>./views/application.coffee</tt>.
425
+ Abhängigkeit:: {coffee-script}[https://github.com/josh/ruby-coffee-script]
426
+ und eine {Möglichkeit JavaScript auszuführen}[https://github.com/sstephenson/execjs/blob/master/README.md#readme]
427
+ Dateierweiterungs:: <tt>.coffee</tt>
428
+ Beispiel:: <tt>coffee :index</tt>
630
429
 
631
- === Inline-Templates
430
+ === Eingebettete Templates
632
431
 
633
432
  get '/' do
634
433
  haml '%div.title Hallo Welt'
635
434
  end
636
435
 
637
- Rendert den Inline-Template-String.
436
+ Rendert den eingebetteten Template-String.
638
437
 
639
438
  === Auf Variablen in Templates zugreifen
640
439
 
@@ -650,7 +449,7 @@ Oder durch einen expliziten Hash von lokalen Variablen:
650
449
 
651
450
  get '/:id' do
652
451
  foo = Foo.find(params[:id])
653
- haml '%h1= foo.name', :locals => { :foo => foo }
452
+ haml '%h1= bar.name', :locals => { :bar => foo }
654
453
  end
655
454
 
656
455
  Dies wird typischerweise bei Verwendung von Subtemplates (partials) in anderen
@@ -702,7 +501,7 @@ verwendet. Durch <tt>:layout => false</tt> kann das Ausführen verhindert
702
501
  werden:
703
502
 
704
503
  get '/' do
705
- haml :index, :layout => !request.xhr?
504
+ haml :index, :layout => request.xhr?
706
505
  end
707
506
 
708
507
  === Dateiendungen zuordnen
@@ -968,8 +767,10 @@ Wenn <tt>send_file</tt> oder statische Dateien verwendet werden, kann es
968
767
  vorkommen, dass Sinatra den Mime-Typ nicht kennt. Registriert wird dieser mit
969
768
  +mime_type+ per Dateiendung:
970
769
 
971
- mime_type :foo, 'text/foo'
972
-
770
+ configure do
771
+ mime_type :foo, 'text/foo'
772
+ end
773
+
973
774
  Es kann aber auch der +content_type+-Helfer verwendet werden:
974
775
 
975
776
  get '/' do
@@ -1478,10 +1279,17 @@ URL-Routing, Authentifizierung und Session-Verarbeitung. Sinatra verwendet
1478
1279
  viele von diesen Komponenten automatisch, abhängig von der Konfiguration. So
1479
1280
  muss +use+ häufig nicht explizit verwendet werden.
1480
1281
 
1282
+ Hilfreiche Middleware gibt es z.B. hier:
1283
+ {rack}[https://github.com/rack/rack/tree/master/lib/rack],
1284
+ {rack-contrib}[https://github.com/rack/rack-contrib#readme],
1285
+ mit {CodeRack}[http://coderack.org/] oder im
1286
+ {Rack wiki}[https://github.com/rack/rack/wiki/List-of-Middleware].
1287
+
1481
1288
  == Testen
1482
1289
 
1483
1290
  Sinatra-Tests können mit jedem auf Rack aufbauendem Test-Framework geschrieben
1484
- werden. {Rack::Test}[http://gitrdoc.com/brynary/rack-test] wird empfohlen:
1291
+ werden. {Rack::Test}[http://rdoc.info/github/brynary/rack-test/master/frames]
1292
+ wird empfohlen:
1485
1293
 
1486
1294
  require 'my_sinatra_app'
1487
1295
  require 'test/unit'
@@ -1510,9 +1318,6 @@ werden. {Rack::Test}[http://gitrdoc.com/brynary/rack-test] wird empfohlen:
1510
1318
  end
1511
1319
  end
1512
1320
 
1513
- Anmerkung: Das eingebaute Sinatra::Test-Modul und die
1514
- Sinatra::TestHarness-Klasse werden seit Version 0.9.2 nicht mehr unterstützt.
1515
-
1516
1321
  == Sinatra::Base - Middleware, Bibliotheken und modulare Anwendungen
1517
1322
 
1518
1323
  Das Definieren einer Top-Level-Anwendung funktioniert gut für
@@ -1521,9 +1326,9 @@ Middleware, Rails Metal, einfache Bibliotheken mit Server-Komponenten oder auch
1521
1326
  Sinatra-Erweiterungen geschrieben werden sollen.
1522
1327
 
1523
1328
  Die Top-Level-DSL belastet den Objekt-Namespace und setzt einen
1524
- Mikro-Anwendungsstil voraus (eine einzelne Anwendungsdatei, ./public und
1525
- ./views Ordner, Logging, Exception-Detail-Seite, usw.). Genau hier kommt
1526
- Sinatra::Base ins Spiel:
1329
+ Mikro-Anwendungsstil voraus (eine einzelne Anwendungsdatei, <tt>./public</tt>
1330
+ und <tt>./views</tt> Ordner, Logging, Exception-Detail-Seite, usw.). Genau
1331
+ hier kommt <tt>Sinatra::Base</tt> ins Spiel:
1527
1332
 
1528
1333
  require 'sinatra/base'
1529
1334
 
@@ -1543,15 +1348,15 @@ Server-Komponente einer Bibliothek:
1543
1348
 
1544
1349
  MyApp.run! :host => 'localhost', :port => 9090
1545
1350
 
1546
- Die Methoden der Sinatra::Base-Subklasse sind genau dieselben wie die der
1547
- Top-Level-DSL. Die meisten Top-Level-Anwendungen können mit nur zwei
1548
- Veränderungen zu Sinatra::Base-Komponenten konvertiert werden:
1351
+ Die Methoden der <tt>Sinatra::Base</tt>-Subklasse sind genau dieselben wie die
1352
+ der Top-Level-DSL. Die meisten Top-Level-Anwendungen können mit nur zwei
1353
+ Veränderungen zu <tt>Sinatra::Base</tt> konvertiert werden:
1549
1354
 
1550
1355
  * Die Datei sollte <tt>require 'sinatra/base'</tt> anstelle von
1551
1356
  <tt>require 'sinatra/base'</tt> aufrufen, ansonsten werden alle von
1552
1357
  Sinatras DSL-Methoden in den Top-Level-Namespace importiert.
1553
1358
  * Alle Routen, Error-Handler, Filter und Optionen der Applikation müssen in
1554
- einer Subklasse von Sinatra::Base definiert werden.
1359
+ einer Subklasse von <tt>Sinatra::Base</tt> definiert werden.
1555
1360
 
1556
1361
  <tt>Sinatra::Base</tt> ist ein unbeschriebenes Blatt. Die meisten Optionen sind
1557
1362
  per Standard deaktiviert. Das betrifft auch den eingebauten Server. Siehe
@@ -1581,7 +1386,7 @@ Unterschiede beachtet werden:
1581
1386
 
1582
1387
  Szenario Classic Modular
1583
1388
 
1584
- app_file file loading sinatra nil
1389
+ app_file sinatra ladende Datei Sinatra::Base subklassierende Datei
1585
1390
  run $0 == app_file false
1586
1391
  logging true false
1587
1392
  method_override true false
@@ -1610,7 +1415,7 @@ Oder über eine <tt>config.ru</tt>-Datei, die es erlaubt, einen beliebigen
1610
1415
  Rack-Handler zu verwenden:
1611
1416
 
1612
1417
  # config.ru
1613
- require 'mein_app'
1418
+ require './mein_app'
1614
1419
  run MeineApp
1615
1420
 
1616
1421
  Starte:
@@ -1630,7 +1435,7 @@ Schreibe eine Anwendungsdatei:
1630
1435
 
1631
1436
  sowie eine dazugehörige <tt>config.ru</tt>-Datei:
1632
1437
 
1633
- require 'app'
1438
+ require './app'
1634
1439
  run Sinatra::Application
1635
1440
 
1636
1441
  === Wann sollte eine config.ru-Datei verwendet werden?
@@ -1663,7 +1468,7 @@ andere Sinatra-Anwendung handeln, es kann jede andere Rack-Anwendung sein
1663
1468
  get('/login') { haml :login }
1664
1469
 
1665
1470
  post('/login') do
1666
- if params[:name] = 'admin' and params[:password] = 'admin'
1471
+ if params[:name] == 'admin' && params[:password] == 'admin'
1667
1472
  session['user_name'] = params[:name]
1668
1473
  else
1669
1474
  redirect '/login'
@@ -1688,7 +1493,7 @@ andere Sinatra-Anwendung handeln, es kann jede andere Rack-Anwendung sein
1688
1493
 
1689
1494
  Manche Situationen erfordern die Erstellung neuer Applikationen zur Laufzeit,
1690
1495
  ohne dass sie einer Konstanten zugeordnet werden. Dies lässt sich mit
1691
- `Sinatra.new` erreichen:
1496
+ <tt>Sinatra.new</tt> erreichen:
1692
1497
 
1693
1498
  require 'sinatra/base'
1694
1499
  my_app = Sinatra.new { get('/') { "hallo" } }
@@ -1731,12 +1536,13 @@ Verfügung stehen.
1731
1536
 
1732
1537
  === Anwendungs- oder Klassen-Scope
1733
1538
 
1734
- Jede Sinatra-Anwendung entspricht einer Sinatra::Base-Subklasse. Falls die Top-
1735
- Level-DSL verwendet wird (<tt>require 'sinatra'</tt>), handelt es sich um
1736
- Sinatra::Application, andernfalls ist es jene Subklasse, die explizit angelegt
1737
- wurde. Auf Klassenebene stehen Methoden wie +get+ oder +before+ zur Verfügung,
1738
- es gibt aber keinen Zugriff auf das +request+-Object oder die +session+, da nur
1739
- eine einzige Klasse für alle eingehenden Anfragen genutzt wird.
1539
+ Jede Sinatra-Anwendung entspricht einer <tt>Sinatra::Base</tt>-Subklasse. Falls
1540
+ die Top- Level-DSL verwendet wird (<tt>require 'sinatra'</tt>), handelt es sich
1541
+ um <tt>Sinatra::Application</tt>, andernfalls ist es jene Subklasse, die
1542
+ explizit angelegt wurde. Auf Klassenebene stehen Methoden wie +get+ oder
1543
+ +before+ zur Verfügung, es gibt aber keinen Zugriff auf das +request+-Object
1544
+ oder die +session+, da nur eine einzige Klasse für alle eingehenden Anfragen
1545
+ genutzt wird.
1740
1546
 
1741
1547
  Optionen, die via +set+ gesetzt werden, sind Methoden auf Klassenebene:
1742
1548
 
@@ -1848,24 +1654,25 @@ Die folgenden Versionen werden offiziell unterstützt:
1848
1654
  unterstützt.
1849
1655
 
1850
1656
  [ JRuby ]
1851
- JRuby wird offiziell unterstützt (JRuby >= 1.6.0). Probleme mit Template-
1657
+ JRuby wird offiziell unterstützt (JRuby >= 1.6.1). Probleme mit Template-
1852
1658
  Bibliotheken Dritter sind nicht bekannt. Falls JRuby zum Einsatz kommt,
1853
1659
  sollte aber darauf geachtet werden, dass ein JRuby-Rack-Handler zum Einsatz
1854
1660
  kommt – der Thin-Web-Server wird bisher nicht unterstütz. JRubys
1855
1661
  Unterstützung für C-Erweiterungen sind zur Zeit noch experimenteller Natur,
1856
- betrifft im Moment aber nur RDiscount.
1662
+ betrifft im Moment aber nur RDiscount und Redcarpet.
1857
1663
 
1858
- <b>Ruby 1.8.6 wird nicht weiter unterstützt.</b>
1664
+ <b>Ruby 1.8.6 wird nicht weiter unterstützt.</b> Falls Sinatra trotzdem unter
1665
+ 1.8.6 eingesetzt wird, muss Sinatra 1.2 verwendet werden, dass noch bis zum
1666
+ Release von Sinatra 1.4.0 mit kleinen Bugfixes versorgt werden wird.
1859
1667
 
1860
1668
  Weiterhin werden wir auf kommende Ruby-Versionen ein Auge haben.
1861
1669
 
1862
- Die nachfolgend aufgeführten Ruby-Implementationen werden offiziell nicht von
1670
+ Die nachfolgend aufgeführten Ruby-Implementierungen werden offiziell nicht von
1863
1671
  Sinatra unterstützt, funktionieren aber normalerweise:
1864
1672
 
1865
1673
  * Ältere Versionen von JRuby und Rubinius
1866
1674
  * MacRuby, Maglev, IronRuby
1867
1675
  * Ruby 1.9.0 und 1.9.1
1868
- * Ruby 1.8.6 mit {backports}[https://github.com/marcandre/backports/#readme]
1869
1676
 
1870
1677
  Nicht offiziell unterstützt bedeutet, dass wenn Sachen nicht funktionieren,
1871
1678
  wir davon ausgehen, dass es nicht an Sinatra sondern an der jeweiligen
@@ -1964,14 +1771,15 @@ SemVer und SemVerTag.
1964
1771
 
1965
1772
  * {Projekt-Website}[http://sinatra.github.com/] - Ergänzende Dokumentation,
1966
1773
  News und Links zu anderen Ressourcen.
1967
- * {Hilfe beisteuern}[http://sinatra.github.com/contributing.html] - Einen
1774
+ * {Mitmachen}[http://sinatra.github.com/contributing.html] - Einen
1968
1775
  Fehler gefunden? Brauchst du Hilfe? Hast du einen Patch?
1969
1776
  * {Issue-Tracker}[http://github.com/sinatra/sinatra/issues]
1970
1777
  * {Twitter}[http://twitter.com/sinatra]
1971
1778
  * {Mailing-Liste}[http://groups.google.com/group/sinatrarb]
1972
1779
  * {IRC: #sinatra}[irc://chat.freenode.net/#sinatra] auf http://freenode.net
1973
-
1780
+ * {Sinatra Book}[http://sinatra-book.gittr.com] Kochbuch Tutorial
1781
+ * {Sinatra Book Contrib}[http://sinatra-book-contrib.com/] Sinatra-Rezepte aus
1782
+ der Community
1974
1783
  * API Dokumentation für die {aktuelle Version}[http://rubydoc.info/gems/sinatra]
1975
1784
  oder für {HEAD}[http://rubydoc.info/github/sinatra/sinatra] auf
1976
1785
  http://rubydoc.info
1977
-