sinatra 0.9.6 → 1.0.a
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.
- data/CHANGES +83 -29
- data/README.jp.rdoc +552 -0
- data/README.rdoc +31 -9
- data/Rakefile +73 -91
- data/lib/sinatra.rb +0 -1
- data/lib/sinatra/base.rb +248 -269
- data/lib/sinatra/main.rb +3 -11
- data/lib/sinatra/tilt.rb +509 -0
- data/sinatra.gemspec +15 -49
- data/test/erubis_test.rb +82 -0
- data/test/extensions_test.rb +1 -1
- data/test/filter_test.rb +125 -3
- data/test/helpers_test.rb +59 -2
- data/test/mapped_error_test.rb +31 -0
- data/test/middleware_test.rb +1 -1
- data/test/request_test.rb +15 -0
- data/test/routing_test.rb +76 -0
- data/test/{options_test.rb → settings_test.rb} +46 -50
- data/test/static_test.rb +13 -0
- data/test/templates_test.rb +43 -10
- data/test/views/error.erubis +3 -0
- data/test/views/hello.erubis +1 -0
- data/test/views/layout2.erubis +2 -0
- metadata +61 -88
- data/compat/app_test.rb +0 -282
- data/compat/application_test.rb +0 -262
- data/compat/builder_test.rb +0 -101
- data/compat/compat_test.rb +0 -12
- data/compat/custom_error_test.rb +0 -62
- data/compat/erb_test.rb +0 -136
- data/compat/events_test.rb +0 -78
- data/compat/filter_test.rb +0 -30
- data/compat/haml_test.rb +0 -237
- data/compat/helper.rb +0 -34
- data/compat/mapped_error_test.rb +0 -72
- data/compat/pipeline_test.rb +0 -45
- data/compat/public/foo.xml +0 -1
- data/compat/sass_test.rb +0 -67
- data/compat/sessions_test.rb +0 -42
- data/compat/streaming_test.rb +0 -133
- data/compat/sym_params_test.rb +0 -18
- data/compat/template_test.rb +0 -30
- data/compat/use_in_file_templates_test.rb +0 -47
- data/compat/views/foo.builder +0 -1
- data/compat/views/foo.erb +0 -1
- data/compat/views/foo.haml +0 -1
- data/compat/views/foo.sass +0 -2
- data/compat/views/foo_layout.erb +0 -2
- data/compat/views/foo_layout.haml +0 -2
- data/compat/views/layout_test/foo.builder +0 -1
- data/compat/views/layout_test/foo.erb +0 -1
- data/compat/views/layout_test/foo.haml +0 -1
- data/compat/views/layout_test/foo.sass +0 -2
- data/compat/views/layout_test/layout.builder +0 -3
- data/compat/views/layout_test/layout.erb +0 -1
- data/compat/views/layout_test/layout.haml +0 -1
- data/compat/views/layout_test/layout.sass +0 -2
- data/compat/views/no_layout/no_layout.builder +0 -1
- data/compat/views/no_layout/no_layout.haml +0 -1
- data/lib/sinatra/compat.rb +0 -258
- data/lib/sinatra/test.rb +0 -129
- data/lib/sinatra/test/bacon.rb +0 -19
- data/lib/sinatra/test/rspec.rb +0 -13
- data/lib/sinatra/test/spec.rb +0 -11
- data/lib/sinatra/test/unit.rb +0 -13
- data/test/render_backtrace_test.rb +0 -145
- data/test/test_test.rb +0 -155
data/compat/application_test.rb
DELETED
@@ -1,262 +0,0 @@
|
|
1
|
-
require File.dirname(__FILE__) + '/helper'
|
2
|
-
|
3
|
-
require 'uri'
|
4
|
-
|
5
|
-
class TesterWithEach
|
6
|
-
def each
|
7
|
-
yield 'foo'
|
8
|
-
yield 'bar'
|
9
|
-
yield 'baz'
|
10
|
-
end
|
11
|
-
end
|
12
|
-
|
13
|
-
context "An app returns" do
|
14
|
-
|
15
|
-
setup do
|
16
|
-
Sinatra.application = nil
|
17
|
-
end
|
18
|
-
|
19
|
-
specify "404 if no events found" do
|
20
|
-
request = Rack::MockRequest.new(@app)
|
21
|
-
get_it '/'
|
22
|
-
should.be.not_found
|
23
|
-
body.should.equal '<h1>Not Found</h1>'
|
24
|
-
end
|
25
|
-
|
26
|
-
specify "200 if success" do
|
27
|
-
get '/' do
|
28
|
-
'Hello World'
|
29
|
-
end
|
30
|
-
get_it '/'
|
31
|
-
should.be.ok
|
32
|
-
body.should.equal 'Hello World'
|
33
|
-
end
|
34
|
-
|
35
|
-
specify "an objects result from each if it has it" do
|
36
|
-
|
37
|
-
get '/' do
|
38
|
-
TesterWithEach.new
|
39
|
-
end
|
40
|
-
|
41
|
-
get_it '/'
|
42
|
-
should.be.ok
|
43
|
-
body.should.equal 'foobarbaz'
|
44
|
-
|
45
|
-
end
|
46
|
-
|
47
|
-
specify "404 if NotFound is raised" do
|
48
|
-
|
49
|
-
get '/' do
|
50
|
-
raise Sinatra::NotFound
|
51
|
-
end
|
52
|
-
|
53
|
-
get_it '/'
|
54
|
-
should.be.not_found
|
55
|
-
|
56
|
-
end
|
57
|
-
|
58
|
-
end
|
59
|
-
|
60
|
-
context "Application#configure blocks" do
|
61
|
-
|
62
|
-
setup do
|
63
|
-
Sinatra.application = nil
|
64
|
-
end
|
65
|
-
|
66
|
-
specify "run when no environment specified" do
|
67
|
-
ref = false
|
68
|
-
configure { ref = true }
|
69
|
-
ref.should.equal true
|
70
|
-
end
|
71
|
-
|
72
|
-
specify "run when matching environment specified" do
|
73
|
-
ref = false
|
74
|
-
configure(:test) { ref = true }
|
75
|
-
ref.should.equal true
|
76
|
-
end
|
77
|
-
|
78
|
-
specify "do not run when no matching environment specified" do
|
79
|
-
configure(:foo) { flunk "block should not have been executed" }
|
80
|
-
configure(:development, :production, :foo) { flunk "block should not have been executed" }
|
81
|
-
end
|
82
|
-
|
83
|
-
specify "accept multiple environments" do
|
84
|
-
ref = false
|
85
|
-
configure(:foo, :test, :bar) { ref = true }
|
86
|
-
ref.should.equal true
|
87
|
-
end
|
88
|
-
|
89
|
-
end
|
90
|
-
|
91
|
-
context "Events in an app" do
|
92
|
-
|
93
|
-
setup do
|
94
|
-
Sinatra.application = nil
|
95
|
-
end
|
96
|
-
|
97
|
-
specify "evaluate in a clean context" do
|
98
|
-
helpers do
|
99
|
-
def foo
|
100
|
-
'foo'
|
101
|
-
end
|
102
|
-
end
|
103
|
-
|
104
|
-
get '/foo' do
|
105
|
-
foo
|
106
|
-
end
|
107
|
-
|
108
|
-
get_it '/foo'
|
109
|
-
should.be.ok
|
110
|
-
body.should.equal 'foo'
|
111
|
-
end
|
112
|
-
|
113
|
-
specify "get access to request, response, and params" do
|
114
|
-
get '/:foo' do
|
115
|
-
params["foo"] + params["bar"]
|
116
|
-
end
|
117
|
-
|
118
|
-
get_it '/foo?bar=baz'
|
119
|
-
should.be.ok
|
120
|
-
body.should.equal 'foobaz'
|
121
|
-
end
|
122
|
-
|
123
|
-
specify "can filters by agent" do
|
124
|
-
|
125
|
-
get '/', :agent => /Windows/ do
|
126
|
-
request.env['HTTP_USER_AGENT']
|
127
|
-
end
|
128
|
-
|
129
|
-
get_it '/', :env => { :agent => 'Windows' }
|
130
|
-
should.be.ok
|
131
|
-
body.should.equal 'Windows'
|
132
|
-
|
133
|
-
get_it '/', :env => { :agent => 'Mac' }
|
134
|
-
should.not.be.ok
|
135
|
-
|
136
|
-
end
|
137
|
-
|
138
|
-
specify "can use regex to get parts of user-agent" do
|
139
|
-
|
140
|
-
get '/', :agent => /Windows (NT)/ do
|
141
|
-
params[:agent].first
|
142
|
-
end
|
143
|
-
|
144
|
-
get_it '/', :env => { :agent => 'Windows NT' }
|
145
|
-
|
146
|
-
body.should.equal 'NT'
|
147
|
-
|
148
|
-
end
|
149
|
-
|
150
|
-
specify "can deal with spaces in paths" do
|
151
|
-
|
152
|
-
path = '/path with spaces'
|
153
|
-
|
154
|
-
get path do
|
155
|
-
"Look ma, a path with spaces!"
|
156
|
-
end
|
157
|
-
|
158
|
-
get_it URI.encode(path)
|
159
|
-
|
160
|
-
body.should.equal "Look ma, a path with spaces!"
|
161
|
-
end
|
162
|
-
|
163
|
-
specify "route based on host" do
|
164
|
-
|
165
|
-
get '/' do
|
166
|
-
'asdf'
|
167
|
-
end
|
168
|
-
|
169
|
-
get_it '/'
|
170
|
-
assert ok?
|
171
|
-
assert_equal('asdf', body)
|
172
|
-
|
173
|
-
get '/foo', :host => 'foo.sinatrarb.com' do
|
174
|
-
'in foo!'
|
175
|
-
end
|
176
|
-
|
177
|
-
get '/foo', :host => 'bar.sinatrarb.com' do
|
178
|
-
'in bar!'
|
179
|
-
end
|
180
|
-
|
181
|
-
get_it '/foo', {}, 'HTTP_HOST' => 'foo.sinatrarb.com'
|
182
|
-
assert ok?
|
183
|
-
assert_equal 'in foo!', body
|
184
|
-
|
185
|
-
get_it '/foo', {}, 'HTTP_HOST' => 'bar.sinatrarb.com'
|
186
|
-
assert ok?
|
187
|
-
assert_equal 'in bar!', body
|
188
|
-
|
189
|
-
get_it '/foo'
|
190
|
-
assert not_found?
|
191
|
-
|
192
|
-
end
|
193
|
-
|
194
|
-
end
|
195
|
-
|
196
|
-
|
197
|
-
context "Options in an app" do
|
198
|
-
|
199
|
-
setup do
|
200
|
-
Sinatra.application = nil
|
201
|
-
@app = Sinatra::application
|
202
|
-
end
|
203
|
-
|
204
|
-
specify "can be set singly on app" do
|
205
|
-
@app.set :foo, 1234
|
206
|
-
@app.options.foo.should.equal 1234
|
207
|
-
end
|
208
|
-
|
209
|
-
specify "can be set singly from top-level" do
|
210
|
-
set_option :foo, 1234
|
211
|
-
@app.options.foo.should.equal 1234
|
212
|
-
end
|
213
|
-
|
214
|
-
specify "can be set multiply on app" do
|
215
|
-
@app.options.foo.should.be.nil
|
216
|
-
@app.set :foo => 1234,
|
217
|
-
:bar => 'hello, world'
|
218
|
-
@app.options.foo.should.equal 1234
|
219
|
-
@app.options.bar.should.equal 'hello, world'
|
220
|
-
end
|
221
|
-
|
222
|
-
specify "can be set multiply from top-level" do
|
223
|
-
@app.options.foo.should.be.nil
|
224
|
-
set_options :foo => 1234,
|
225
|
-
:bar => 'hello, world'
|
226
|
-
@app.options.foo.should.equal 1234
|
227
|
-
@app.options.bar.should.equal 'hello, world'
|
228
|
-
end
|
229
|
-
|
230
|
-
specify "can be enabled on app" do
|
231
|
-
@app.options.foo.should.be.nil
|
232
|
-
@app.enable :sessions, :foo, :bar
|
233
|
-
@app.options.sessions.should.equal true
|
234
|
-
@app.options.foo.should.equal true
|
235
|
-
@app.options.bar.should.equal true
|
236
|
-
end
|
237
|
-
|
238
|
-
specify "can be enabled from top-level" do
|
239
|
-
@app.options.foo.should.be.nil
|
240
|
-
enable :sessions, :foo, :bar
|
241
|
-
@app.options.sessions.should.equal true
|
242
|
-
@app.options.foo.should.equal true
|
243
|
-
@app.options.bar.should.equal true
|
244
|
-
end
|
245
|
-
|
246
|
-
specify "can be disabled on app" do
|
247
|
-
@app.options.foo.should.be.nil
|
248
|
-
@app.disable :sessions, :foo, :bar
|
249
|
-
@app.options.sessions.should.equal false
|
250
|
-
@app.options.foo.should.equal false
|
251
|
-
@app.options.bar.should.equal false
|
252
|
-
end
|
253
|
-
|
254
|
-
specify "can be enabled from top-level" do
|
255
|
-
@app.options.foo.should.be.nil
|
256
|
-
disable :sessions, :foo, :bar
|
257
|
-
@app.options.sessions.should.equal false
|
258
|
-
@app.options.foo.should.equal false
|
259
|
-
@app.options.bar.should.equal false
|
260
|
-
end
|
261
|
-
|
262
|
-
end
|
data/compat/builder_test.rb
DELETED
@@ -1,101 +0,0 @@
|
|
1
|
-
require File.dirname(__FILE__) + '/helper'
|
2
|
-
|
3
|
-
context "Builder" do
|
4
|
-
|
5
|
-
setup do
|
6
|
-
Sinatra.application = nil
|
7
|
-
end
|
8
|
-
|
9
|
-
context "without layouts" do
|
10
|
-
|
11
|
-
setup do
|
12
|
-
Sinatra.application = nil
|
13
|
-
end
|
14
|
-
|
15
|
-
specify "should render" do
|
16
|
-
|
17
|
-
get '/no_layout' do
|
18
|
-
builder 'xml.instruct!'
|
19
|
-
end
|
20
|
-
|
21
|
-
get_it '/no_layout'
|
22
|
-
should.be.ok
|
23
|
-
body.should == %(<?xml version="1.0" encoding="UTF-8"?>\n)
|
24
|
-
|
25
|
-
end
|
26
|
-
|
27
|
-
specify "should render inline block" do
|
28
|
-
|
29
|
-
get '/no_layout_and_inlined' do
|
30
|
-
@name = "Frank & Mary"
|
31
|
-
builder do |xml|
|
32
|
-
xml.couple @name
|
33
|
-
end
|
34
|
-
end
|
35
|
-
|
36
|
-
get_it '/no_layout_and_inlined'
|
37
|
-
should.be.ok
|
38
|
-
body.should == %(<couple>Frank & Mary</couple>\n)
|
39
|
-
|
40
|
-
end
|
41
|
-
|
42
|
-
end
|
43
|
-
|
44
|
-
|
45
|
-
|
46
|
-
context "Templates (in general)" do
|
47
|
-
|
48
|
-
setup do
|
49
|
-
Sinatra.application = nil
|
50
|
-
end
|
51
|
-
|
52
|
-
specify "are read from files if Symbols" do
|
53
|
-
|
54
|
-
get '/from_file' do
|
55
|
-
@name = 'Blue'
|
56
|
-
builder :foo, :views_directory => File.dirname(__FILE__) + "/views"
|
57
|
-
end
|
58
|
-
|
59
|
-
get_it '/from_file'
|
60
|
-
should.be.ok
|
61
|
-
body.should.equal %(<exclaim>You rock Blue!</exclaim>\n)
|
62
|
-
|
63
|
-
end
|
64
|
-
|
65
|
-
specify "use layout.ext by default if available" do
|
66
|
-
|
67
|
-
get '/' do
|
68
|
-
builder :foo, :views_directory => File.dirname(__FILE__) + "/views/layout_test"
|
69
|
-
end
|
70
|
-
|
71
|
-
get_it '/'
|
72
|
-
should.be.ok
|
73
|
-
body.should.equal "<layout>\n<this>is foo!</this>\n</layout>\n"
|
74
|
-
|
75
|
-
end
|
76
|
-
|
77
|
-
specify "renders without layout" do
|
78
|
-
|
79
|
-
get '/' do
|
80
|
-
builder :no_layout, :views_directory => File.dirname(__FILE__) + "/views/no_layout"
|
81
|
-
end
|
82
|
-
|
83
|
-
get_it '/'
|
84
|
-
should.be.ok
|
85
|
-
body.should.equal "<foo>No Layout!</foo>\n"
|
86
|
-
|
87
|
-
end
|
88
|
-
|
89
|
-
specify "raises error if template not found" do
|
90
|
-
|
91
|
-
get '/' do
|
92
|
-
builder :not_found
|
93
|
-
end
|
94
|
-
|
95
|
-
lambda { get_it '/' }.should.raise(Errno::ENOENT)
|
96
|
-
|
97
|
-
end
|
98
|
-
|
99
|
-
end
|
100
|
-
|
101
|
-
end
|
data/compat/compat_test.rb
DELETED
@@ -1,12 +0,0 @@
|
|
1
|
-
require File.dirname(__FILE__) + '/helper'
|
2
|
-
|
3
|
-
context "Compat" do
|
4
|
-
setup do
|
5
|
-
Sinatra.application = nil
|
6
|
-
@app = Sinatra.application
|
7
|
-
end
|
8
|
-
|
9
|
-
specify "makes EventContext available" do
|
10
|
-
assert_same Sinatra::Application, Sinatra::EventContext
|
11
|
-
end
|
12
|
-
end
|
data/compat/custom_error_test.rb
DELETED
@@ -1,62 +0,0 @@
|
|
1
|
-
require File.dirname(__FILE__) + '/helper'
|
2
|
-
|
3
|
-
context "Custom Errors" do
|
4
|
-
|
5
|
-
setup do
|
6
|
-
Sinatra.application = nil
|
7
|
-
end
|
8
|
-
|
9
|
-
specify "override the default 404" do
|
10
|
-
|
11
|
-
get_it '/'
|
12
|
-
should.be.not_found
|
13
|
-
body.should.equal '<h1>Not Found</h1>'
|
14
|
-
|
15
|
-
error Sinatra::NotFound do
|
16
|
-
'Custom 404'
|
17
|
-
end
|
18
|
-
|
19
|
-
get_it '/'
|
20
|
-
should.be.not_found
|
21
|
-
body.should.equal 'Custom 404'
|
22
|
-
|
23
|
-
end
|
24
|
-
|
25
|
-
specify "override the default 500" do
|
26
|
-
Sinatra.application.options.raise_errors = false
|
27
|
-
|
28
|
-
get '/' do
|
29
|
-
raise 'asdf'
|
30
|
-
end
|
31
|
-
|
32
|
-
get_it '/'
|
33
|
-
status.should.equal 500
|
34
|
-
body.should.equal '<h1>Internal Server Error</h1>'
|
35
|
-
|
36
|
-
|
37
|
-
error do
|
38
|
-
'Custom 500 for ' + request.env['sinatra.error'].message
|
39
|
-
end
|
40
|
-
|
41
|
-
get_it '/'
|
42
|
-
|
43
|
-
get_it '/'
|
44
|
-
status.should.equal 500
|
45
|
-
body.should.equal 'Custom 500 for asdf'
|
46
|
-
|
47
|
-
Sinatra.application.options.raise_errors = true
|
48
|
-
end
|
49
|
-
|
50
|
-
class UnmappedError < RuntimeError; end
|
51
|
-
|
52
|
-
specify "should bring unmapped error back to the top" do
|
53
|
-
get '/' do
|
54
|
-
raise UnmappedError, 'test'
|
55
|
-
end
|
56
|
-
|
57
|
-
assert_raises(UnmappedError) do
|
58
|
-
get_it '/'
|
59
|
-
end
|
60
|
-
end
|
61
|
-
|
62
|
-
end
|
data/compat/erb_test.rb
DELETED
@@ -1,136 +0,0 @@
|
|
1
|
-
require File.dirname(__FILE__) + '/helper'
|
2
|
-
|
3
|
-
context "Erb" do
|
4
|
-
|
5
|
-
setup do
|
6
|
-
Sinatra.application = nil
|
7
|
-
end
|
8
|
-
|
9
|
-
context "without layouts" do
|
10
|
-
|
11
|
-
setup do
|
12
|
-
Sinatra.application = nil
|
13
|
-
end
|
14
|
-
|
15
|
-
specify "should render" do
|
16
|
-
|
17
|
-
get '/no_layout' do
|
18
|
-
erb '<%= 1 + 1 %>'
|
19
|
-
end
|
20
|
-
|
21
|
-
get_it '/no_layout'
|
22
|
-
should.be.ok
|
23
|
-
body.should == '2'
|
24
|
-
|
25
|
-
end
|
26
|
-
|
27
|
-
specify "should take an options hash with :locals set with a string" do
|
28
|
-
get '/locals' do
|
29
|
-
erb '<%= foo %>', :locals => {:foo => "Bar"}
|
30
|
-
end
|
31
|
-
|
32
|
-
get_it '/locals'
|
33
|
-
should.be.ok
|
34
|
-
body.should == 'Bar'
|
35
|
-
end
|
36
|
-
|
37
|
-
specify "should take an options hash with :locals set with a complex object" do
|
38
|
-
get '/locals-complex' do
|
39
|
-
erb '<%= foo[0] %>', :locals => {:foo => ["foo", "bar", "baz"]}
|
40
|
-
end
|
41
|
-
|
42
|
-
get_it '/locals-complex'
|
43
|
-
should.be.ok
|
44
|
-
body.should == 'foo'
|
45
|
-
end
|
46
|
-
end
|
47
|
-
|
48
|
-
context "with layouts" do
|
49
|
-
|
50
|
-
setup do
|
51
|
-
Sinatra.application = nil
|
52
|
-
end
|
53
|
-
|
54
|
-
specify "can be inline" do
|
55
|
-
|
56
|
-
layout do
|
57
|
-
%Q{This is <%= yield %>!}
|
58
|
-
end
|
59
|
-
|
60
|
-
get '/lay' do
|
61
|
-
erb 'Blake'
|
62
|
-
end
|
63
|
-
|
64
|
-
get_it '/lay'
|
65
|
-
should.be.ok
|
66
|
-
body.should.equal 'This is Blake!'
|
67
|
-
|
68
|
-
end
|
69
|
-
|
70
|
-
specify "can use named layouts" do
|
71
|
-
|
72
|
-
layout :pretty do
|
73
|
-
%Q{<h1><%= yield %></h1>}
|
74
|
-
end
|
75
|
-
|
76
|
-
get '/pretty' do
|
77
|
-
erb 'Foo', :layout => :pretty
|
78
|
-
end
|
79
|
-
|
80
|
-
get '/not_pretty' do
|
81
|
-
erb 'Bar'
|
82
|
-
end
|
83
|
-
|
84
|
-
get_it '/pretty'
|
85
|
-
body.should.equal '<h1>Foo</h1>'
|
86
|
-
|
87
|
-
get_it '/not_pretty'
|
88
|
-
body.should.equal 'Bar'
|
89
|
-
|
90
|
-
end
|
91
|
-
|
92
|
-
specify "can be read from a file if they're not inlined" do
|
93
|
-
|
94
|
-
get '/foo' do
|
95
|
-
@title = 'Welcome to the Hello Program'
|
96
|
-
erb 'Blake', :layout => :foo_layout,
|
97
|
-
:views_directory => File.dirname(__FILE__) + "/views"
|
98
|
-
end
|
99
|
-
|
100
|
-
get_it '/foo'
|
101
|
-
body.should.equal "Welcome to the Hello Program\nHi Blake\n"
|
102
|
-
|
103
|
-
end
|
104
|
-
|
105
|
-
end
|
106
|
-
|
107
|
-
context "Templates (in general)" do
|
108
|
-
|
109
|
-
specify "are read from files if Symbols" do
|
110
|
-
|
111
|
-
get '/from_file' do
|
112
|
-
@name = 'Alena'
|
113
|
-
erb :foo, :views_directory => File.dirname(__FILE__) + "/views"
|
114
|
-
end
|
115
|
-
|
116
|
-
get_it '/from_file'
|
117
|
-
|
118
|
-
body.should.equal 'You rock Alena!'
|
119
|
-
|
120
|
-
end
|
121
|
-
|
122
|
-
specify "use layout.ext by default if available" do
|
123
|
-
|
124
|
-
get '/layout_from_file' do
|
125
|
-
erb :foo, :views_directory => File.dirname(__FILE__) + "/views/layout_test"
|
126
|
-
end
|
127
|
-
|
128
|
-
get_it '/layout_from_file'
|
129
|
-
should.be.ok
|
130
|
-
body.should.equal "x This is foo! x \n"
|
131
|
-
|
132
|
-
end
|
133
|
-
|
134
|
-
end
|
135
|
-
|
136
|
-
end
|