rack-app 1.4.0 → 2.0.0

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.
checksums.yaml CHANGED
@@ -1,7 +1,7 @@
1
1
  ---
2
2
  SHA1:
3
- metadata.gz: 632e1777a182db0bdfc19b0fdd9afcf41d8f6ba7
4
- data.tar.gz: d6b89d0e7444d94a0b0aff3423de437a7e7d3788
3
+ metadata.gz: 6883859ca0d72bc8fac97ac3b745a225bdbede0e
4
+ data.tar.gz: d53e14b3621d6290af628d6e11880629728eb206
5
5
  SHA512:
6
- metadata.gz: 8a53d244b2e6fcfbfd32d766b3ce83b06e5c840040775644172d210745aef9c3adf0c38c07ed79fa1ae68b5b275578b017ef14393a1bb5c4b9ff4278568d363c
7
- data.tar.gz: 32763b6832f209639396916a5ad5f7e7737586db7896d8dfd5f7ee3e2b144d00a0ae845744db8f20f3d8708b9d7b98aaa69f57b8fcc2bfb07dccd88c579b3361
6
+ metadata.gz: 80e9b3a47d3158c15837ca297e0a87f244859beae87ffbcedf59fc9a42987c19a63e7a2eab0c3c4b906bd5e66ed959b6461deb475dddca8e4772765211bfd587
7
+ data.tar.gz: da9cded93beb9b94645842ea4022f67b68633f0ee0c99355a53e217c6a79460ac375fbe43e3d73cbb63f5d082918b86594f5b64d9bdb30c8ec789096e0d336cb
data/VERSION CHANGED
@@ -1 +1 @@
1
- 1.4.0
1
+ 2.0.0
@@ -8,240 +8,19 @@ class Rack::App
8
8
  require 'rack/app/constants'
9
9
 
10
10
  require 'rack/app/utils'
11
- require 'rack/app/file'
12
-
13
11
  require 'rack/app/params'
14
12
  require 'rack/app/router'
15
13
  require 'rack/app/endpoint'
16
14
  require 'rack/app/serializer'
15
+ require 'rack/app/file_server'
17
16
  require 'rack/app/error_handler'
18
17
  require 'rack/app/endpoint/not_found'
19
18
  require 'rack/app/request_configurator'
20
19
 
21
- class << self
22
-
23
- def inherited(klass)
24
-
25
- klass.serializer(&serializer.logic)
26
- klass.headers.merge!(headers)
27
- klass.middlewares.push(*middlewares)
28
-
29
- on_inheritance.each do |block|
30
- block.call(self, klass)
31
- klass.on_inheritance(&block)
32
- end
33
-
34
- error.handlers.each do |ex_class, block|
35
- klass.error(ex_class, &block)
36
- end
37
-
38
- end
39
-
40
- def on_mounted(&block)
41
- @on_mounted ||= []
42
- @on_mounted << block unless block.nil?
43
- @on_mounted
44
- end
45
-
46
- alias while_being_mounted on_mounted
47
-
48
- def on_inheritance(&block)
49
- @on_inheritance ||= []
50
- @on_inheritance << block unless block.nil?
51
- @on_inheritance
52
- end
53
-
54
- def serializer(&definition_how_to_serialize)
55
- @serializer ||= Rack::App::Serializer.new
56
-
57
- unless definition_how_to_serialize.nil?
58
- @serializer.set_serialization_logic(definition_how_to_serialize)
59
- end
60
-
61
- return @serializer
62
- end
63
-
64
- def headers(new_headers=nil)
65
- @headers ||= {}
66
- @headers.merge!(new_headers) if new_headers.is_a?(Hash)
67
- @headers
68
- end
69
-
70
- def middlewares(&block)
71
- @middlewares ||= []
72
- @middlewares << block unless block.nil?
73
- @middlewares
74
- end
75
-
76
- alias middleware middlewares
77
-
78
- def error(*exception_classes, &block)
79
- @error_handler ||= Rack::App::ErrorHandler.new
80
- unless block.nil?
81
- @error_handler.register_handler(exception_classes, block)
82
- end
83
-
84
- return @error_handler
85
- end
86
-
87
- def namespace(request_path_namespace)
88
- return unless block_given?
89
- @namespaces ||= []
90
- @namespaces.push(request_path_namespace)
91
- yield
92
- @namespaces.pop
93
- nil
94
- end
95
-
96
- def router
97
- @router ||= Rack::App::Router.new
98
- end
99
-
100
- def call(request_env)
101
- Rack::App::RequestConfigurator.configure(request_env)
102
- endpoint = router.fetch_endpoint(
103
- request_env['REQUEST_METHOD'],
104
- request_env[Rack::App::Constants::NORMALIZED_REQUEST_PATH])
105
- endpoint.call(request_env)
106
- end
107
-
108
- def description(*description_texts)
109
- @last_description = description_texts.join("\n")
110
- end
111
-
112
- alias desc description
113
-
114
- def get(path = '/', &block)
115
- add_route('GET', path, &block)
116
- end
117
-
118
- def post(path = '/', &block)
119
- add_route('POST', path, &block)
120
- end
121
-
122
- def put(path = '/', &block)
123
- add_route('PUT', path, &block)
124
- end
125
-
126
- def head(path = '/', &block)
127
- add_route('HEAD', path, &block)
128
- end
129
-
130
- def delete(path = '/', &block)
131
- add_route('DELETE', path, &block)
132
- end
133
-
134
- def options(path = '/', &block)
135
- add_route('OPTIONS', path, &block)
136
- end
137
-
138
- def patch(path = '/', &block)
139
- add_route('PATCH', path, &block)
140
- end
141
-
142
- def alias_endpoint(new_request_path, original_request_path)
143
- router.endpoints.select { |ep| ep[:request_path] == original_request_path }.each do |endpoint|
144
- router.register_endpoint!(endpoint[:request_method], new_request_path, endpoint[:description], endpoint[:endpoint])
145
- end
146
- end
147
-
148
- def root(endpoint_path)
149
- %W[GET POST PUT DELETE OPTIONS PATCH HEAD].each do |request_method|
150
- endpoint = router.fetch_endpoint(request_method, endpoint_path)
151
- next if endpoint == Rack::App::Endpoint::NOT_FOUND
152
- router.register_endpoint!(request_method, '/', 'Root endpoint', endpoint)
153
- end
154
- end
155
-
156
- def add_route(request_method, request_path, &block)
157
-
158
- request_path = ::Rack::App::Utils.join(@namespaces, request_path)
159
-
160
- builder = Rack::Builder.new
161
- middlewares.each do |builder_block|
162
- builder_block.call(builder)
163
- end
164
-
165
- properties = {
166
- :user_defined_logic => block,
167
- :request_method => request_method,
168
- :request_path => request_path,
169
-
170
- :default_headers => headers,
171
- :error_handler => error,
172
- :description => @last_description,
173
- :serializer => serializer,
174
- :middleware => builder,
175
- :app_class => self
176
- }
177
-
178
-
179
- endpoint = Rack::App::Endpoint.new(properties)
180
- router.register_endpoint!(request_method, request_path, @last_description, endpoint)
181
-
182
- @last_description = nil
183
- return endpoint
184
-
185
- end
186
-
187
- def serve_files_from(file_path, options={})
188
- file_server = Rack::App::File::Server.new(Rack::App::Utils.expand_path(file_path))
189
- request_path = Rack::App::Utils.join(@namespaces, options[:to], '**', '*')
190
- router.register_endpoint!('GET', request_path, @last_description, file_server)
191
- @last_description = nil
192
- end
193
-
194
- def mount(api_class, mount_prop={})
195
-
196
- unless api_class.is_a?(Class) and api_class <= Rack::App
197
- raise(ArgumentError, 'Invalid class given for mount, must be a Rack::App')
198
- end
199
-
200
- api_class.on_mounted.each do |on_mount|
201
- on_mount.call(self, mount_prop)
202
- end
203
-
204
- merge_prop = {:namespaces => [@namespaces, mount_prop[:to]].flatten}
205
- router.merge_router!(api_class.router, merge_prop)
206
-
207
- return nil
208
- end
209
-
210
- end
211
-
212
- attr_writer :request, :response
213
-
214
- def params
215
- @__params__ ||= Rack::App::Params.new(request.env).to_hash
216
- end
217
-
218
- def request
219
- @request || raise("request object is not set for #{self.class}")
220
- end
221
-
222
- def response
223
- @response || raise("response object is not set for #{self.class}")
224
- end
225
-
226
- def payload
227
- @__payload__ ||= lambda {
228
- return nil unless @request.body.respond_to?(:gets)
229
-
230
- payload = ''
231
- while chunk = @request.body.gets
232
- payload << chunk
233
- end
234
- @request.body.rewind
235
-
236
- return payload
237
- }.call
238
- end
20
+ require 'rack/app/singleton_methods'
21
+ extend Rack::App::SingletonMethods
239
22
 
240
- def redirect_to(url)
241
- url = "#{url}?#{request.env['QUERY_STRING']}" unless request.env['QUERY_STRING'].empty?
242
- response.status = 301
243
- response.headers.merge!({'Location' => url})
244
- 'See Ya!'
245
- end
23
+ require 'rack/app/instance_methods'
24
+ include Rack::App::InstanceMethods
246
25
 
247
26
  end
@@ -1,4 +1,3 @@
1
1
  module Rack::App::Constants
2
2
  NORMALIZED_REQUEST_PATH = 'NORMALIZED_REQUEST_PATH'
3
-
4
3
  end
@@ -54,16 +54,9 @@ class Rack::App::Endpoint
54
54
  protected
55
55
 
56
56
  def set_response_body(response, result)
57
- if result.is_a?(::Rack::App::File::Streamer)
58
- response.length += result.length
59
- response.headers[LAST_MODIFIED_HEADER]= result.mtime
60
- response.body = result
57
+ return nil unless response.body.is_a?(Array)
61
58
 
62
- else
63
- response.write(String(@serializer.serialize(result)))
64
-
65
- end
66
- nil
59
+ response.write(String(@serializer.serialize(result)))
67
60
  end
68
61
 
69
62
  def set_default_headers(response)
@@ -1,9 +1,9 @@
1
- class Rack::App::File::Server
1
+ class Rack::App::FileServer
2
2
 
3
3
  def initialize(root_folder)
4
4
  require 'rack/file'
5
5
  @root_folder = root_folder
6
- @relative_file_paths = Dir.glob(File.join(@root_folder,'**','*')).map{|file_path| file_path.sub(@root_folder,'') }.sort_by{|str| str.length }.reverse
6
+ @relative_file_paths = Dir.glob(File.join(@root_folder, '**', '*')).map { |file_path| file_path.sub(@root_folder, '') }.sort_by { |str| str.length }.reverse
7
7
  @rack_file_server = ::Rack::File.new(@root_folder, {})
8
8
  end
9
9
 
@@ -13,13 +13,19 @@ class Rack::App::File::Server
13
13
  @relative_file_paths.each do |relative_file_path|
14
14
  if path_info =~ /#{Regexp.escape(relative_file_path)}$/
15
15
  env[::Rack::PATH_INFO]= relative_file_path
16
+ break
16
17
  end
17
18
  end
18
19
 
19
20
  @rack_file_server.call(env)
20
21
  end
21
22
 
22
- def register_path_params_matcher(*args)
23
+ def self.serve_file(env, file_path)
24
+ file_server = self.new(File.dirname(file_path))
25
+ env = env.dup
26
+ env[::Rack::REQUEST_METHOD]= 'GET'
27
+ env[::Rack::PATH_INFO]= file_path
28
+ file_server.call(env)
23
29
  end
24
30
 
25
31
  protected
@@ -0,0 +1,45 @@
1
+ module Rack::App::InstanceMethods
2
+
3
+ attr_writer :request, :response
4
+
5
+ def params
6
+ @__params__ ||= Rack::App::Params.new(request.env).to_hash
7
+ end
8
+
9
+ def request
10
+ @request || raise("request object is not set for #{self.class}")
11
+ end
12
+
13
+ def response
14
+ @response || raise("response object is not set for #{self.class}")
15
+ end
16
+
17
+ def payload
18
+ @__payload__ ||= lambda {
19
+ return nil unless @request.body.respond_to?(:gets)
20
+
21
+ payload = ''
22
+ while chunk = @request.body.gets
23
+ payload << chunk
24
+ end
25
+ @request.body.rewind
26
+
27
+ return payload
28
+ }.call
29
+ end
30
+
31
+ def redirect_to(url)
32
+ url = "#{url}?#{request.env['QUERY_STRING']}" unless request.env['QUERY_STRING'].empty?
33
+ response.status = 301
34
+ response.headers.merge!({'Location' => url})
35
+ 'See Ya!'
36
+ end
37
+
38
+ def serve_file(file_path)
39
+ raw_rack_resp = Rack::App::FileServer.serve_file(request.env, file_path)
40
+ response.headers.merge!(raw_rack_resp[1])
41
+ response.body = raw_rack_resp.last
42
+ return nil
43
+ end
44
+
45
+ end
@@ -89,7 +89,9 @@ class Rack::App::Router::Dynamic < Rack::App::Router::Base
89
89
  end
90
90
 
91
91
  current_cluster[:endpoint]= endpoint
92
- current_cluster[:endpoint].register_path_params_matcher(path_params)
92
+ if current_cluster[:endpoint].respond_to?(:register_path_params_matcher)
93
+ current_cluster[:endpoint].register_path_params_matcher(path_params)
94
+ end
93
95
 
94
96
  endpoint
95
97
  end
@@ -0,0 +1,17 @@
1
+ module Rack::App::SingletonMethods
2
+
3
+ require 'rack/app/singleton_methods/http_methods'
4
+ require 'rack/app/singleton_methods/inheritance'
5
+ require 'rack/app/singleton_methods/mounting'
6
+ require 'rack/app/singleton_methods/rack_interface'
7
+ require 'rack/app/singleton_methods/route_handling'
8
+ require 'rack/app/singleton_methods/utility'
9
+
10
+ include Rack::App::SingletonMethods::HttpMethods
11
+ include Rack::App::SingletonMethods::Inheritance
12
+ include Rack::App::SingletonMethods::Mounting
13
+ include Rack::App::SingletonMethods::RackInterface
14
+ include Rack::App::SingletonMethods::RouteHandling
15
+ include Rack::App::SingletonMethods::Utility
16
+
17
+ end
@@ -0,0 +1,44 @@
1
+ module Rack::App::SingletonMethods::HttpMethods
2
+
3
+ def get(path = '/', &block)
4
+ add_route('GET', path, &block)
5
+ end
6
+
7
+ def post(path = '/', &block)
8
+ add_route('POST', path, &block)
9
+ end
10
+
11
+ def put(path = '/', &block)
12
+ add_route('PUT', path, &block)
13
+ end
14
+
15
+ def head(path = '/', &block)
16
+ add_route('HEAD', path, &block)
17
+ end
18
+
19
+ def delete(path = '/', &block)
20
+ add_route('DELETE', path, &block)
21
+ end
22
+
23
+ def options(path = '/', &block)
24
+ add_route('OPTIONS', path, &block)
25
+ end
26
+
27
+ def patch(path = '/', &block)
28
+ add_route('PATCH', path, &block)
29
+ end
30
+
31
+ def alias_endpoint(new_request_path, original_request_path)
32
+ router.endpoints.select { |ep| ep[:request_path] == original_request_path }.each do |endpoint|
33
+ router.register_endpoint!(endpoint[:request_method], new_request_path, endpoint[:description], endpoint[:endpoint])
34
+ end
35
+ end
36
+
37
+ def serve_files_from(file_path, options={})
38
+ file_server = Rack::App::FileServer.new(Rack::App::Utils.expand_path(file_path))
39
+ request_path = Rack::App::Utils.join(@namespaces, options[:to], '**', '*')
40
+ router.register_endpoint!('GET', request_path, @last_description, file_server)
41
+ @last_description = nil
42
+ end
43
+
44
+ end
@@ -0,0 +1,26 @@
1
+ module Rack::App::SingletonMethods::Inheritance
2
+
3
+ def inherited(klass)
4
+
5
+ klass.serializer(&serializer.logic)
6
+ klass.headers.merge!(headers)
7
+ klass.middlewares.push(*middlewares)
8
+
9
+ on_inheritance.each do |block|
10
+ block.call(self, klass)
11
+ klass.on_inheritance(&block)
12
+ end
13
+
14
+ error.handlers.each do |ex_class, block|
15
+ klass.error(ex_class, &block)
16
+ end
17
+
18
+ end
19
+
20
+ def on_inheritance(&block)
21
+ @on_inheritance ||= []
22
+ @on_inheritance << block unless block.nil?
23
+ @on_inheritance
24
+ end
25
+
26
+ end
@@ -0,0 +1,27 @@
1
+ module Rack::App::SingletonMethods::Mounting
2
+
3
+ def on_mounted(&block)
4
+ @on_mounted ||= []
5
+ @on_mounted << block unless block.nil?
6
+ @on_mounted
7
+ end
8
+
9
+ alias while_being_mounted on_mounted
10
+
11
+ def mount(api_class, mount_prop={})
12
+
13
+ unless api_class.is_a?(Class) and api_class <= Rack::App
14
+ raise(ArgumentError, 'Invalid class given for mount, must be a Rack::App')
15
+ end
16
+
17
+ api_class.on_mounted.each do |on_mount|
18
+ on_mount.call(self, mount_prop)
19
+ end
20
+
21
+ merge_prop = {:namespaces => [@namespaces, mount_prop[:to]].flatten}
22
+ router.merge_router!(api_class.router, merge_prop)
23
+
24
+ return nil
25
+ end
26
+
27
+ end
@@ -0,0 +1,11 @@
1
+ module Rack::App::SingletonMethods::RackInterface
2
+
3
+ def call(request_env)
4
+ Rack::App::RequestConfigurator.configure(request_env)
5
+ endpoint = router.fetch_endpoint(
6
+ request_env['REQUEST_METHOD'],
7
+ request_env[Rack::App::Constants::NORMALIZED_REQUEST_PATH])
8
+ endpoint.call(request_env)
9
+ end
10
+
11
+ end
@@ -0,0 +1,61 @@
1
+ module Rack::App::SingletonMethods::RouteHandling
2
+
3
+ def root(endpoint_path)
4
+ %W[GET POST PUT DELETE OPTIONS PATCH HEAD].each do |request_method|
5
+ endpoint = router.fetch_endpoint(request_method, endpoint_path)
6
+ next if endpoint == Rack::App::Endpoint::NOT_FOUND
7
+ router.register_endpoint!(request_method, '/', 'Root endpoint', endpoint)
8
+ end
9
+ end
10
+
11
+ def description(*description_texts)
12
+ @last_description = description_texts.join("\n")
13
+ end
14
+
15
+ alias desc description
16
+
17
+ def add_route(request_method, request_path, &block)
18
+
19
+ request_path = ::Rack::App::Utils.join(@namespaces, request_path)
20
+
21
+ builder = Rack::Builder.new
22
+ middlewares.each do |builder_block|
23
+ builder_block.call(builder)
24
+ end
25
+
26
+ properties = {
27
+ :user_defined_logic => block,
28
+ :request_method => request_method,
29
+ :request_path => request_path,
30
+
31
+ :default_headers => headers,
32
+ :error_handler => error,
33
+ :description => @last_description,
34
+ :serializer => serializer,
35
+ :middleware => builder,
36
+ :app_class => self
37
+ }
38
+
39
+
40
+ endpoint = Rack::App::Endpoint.new(properties)
41
+ router.register_endpoint!(request_method, request_path, @last_description, endpoint)
42
+
43
+ @last_description = nil
44
+ return endpoint
45
+
46
+ end
47
+
48
+ def namespace(request_path_namespace)
49
+ return unless block_given?
50
+ @namespaces ||= []
51
+ @namespaces.push(request_path_namespace)
52
+ yield
53
+ @namespaces.pop
54
+ nil
55
+ end
56
+
57
+ def router
58
+ @router ||= Rack::App::Router.new
59
+ end
60
+
61
+ end
@@ -0,0 +1,36 @@
1
+ module Rack::App::SingletonMethods::Utility
2
+
3
+ def serializer(&definition_how_to_serialize)
4
+ @serializer ||= Rack::App::Serializer.new
5
+
6
+ unless definition_how_to_serialize.nil?
7
+ @serializer.set_serialization_logic(definition_how_to_serialize)
8
+ end
9
+
10
+ return @serializer
11
+ end
12
+
13
+ def headers(new_headers=nil)
14
+ @headers ||= {}
15
+ @headers.merge!(new_headers) if new_headers.is_a?(Hash)
16
+ @headers
17
+ end
18
+
19
+ def middlewares(&block)
20
+ @middlewares ||= []
21
+ @middlewares << block unless block.nil?
22
+ @middlewares
23
+ end
24
+
25
+ alias middleware middlewares
26
+
27
+ def error(*exception_classes, &block)
28
+ @error_handler ||= Rack::App::ErrorHandler.new
29
+ unless block.nil?
30
+ @error_handler.register_handler(exception_classes, block)
31
+ end
32
+
33
+ return @error_handler
34
+ end
35
+
36
+ end
metadata CHANGED
@@ -1,7 +1,7 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: rack-app
3
3
  version: !ruby/object:Gem::Version
4
- version: 1.4.0
4
+ version: 2.0.0
5
5
  platform: ruby
6
6
  authors:
7
7
  - Adam Luzsi
@@ -9,7 +9,7 @@ authors:
9
9
  autorequire:
10
10
  bindir: exe
11
11
  cert_chain: []
12
- date: 2016-03-01 00:00:00.000000000 Z
12
+ date: 2016-03-02 00:00:00.000000000 Z
13
13
  dependencies:
14
14
  - !ruby/object:Gem::Dependency
15
15
  name: bundler
@@ -93,10 +93,8 @@ files:
93
93
  - lib/rack/app/endpoint.rb
94
94
  - lib/rack/app/endpoint/not_found.rb
95
95
  - lib/rack/app/error_handler.rb
96
- - lib/rack/app/file.rb
97
- - lib/rack/app/file/server.rb
98
- - lib/rack/app/file/streamer.rb
99
- - lib/rack/app/file/version.rb
96
+ - lib/rack/app/file_server.rb
97
+ - lib/rack/app/instance_methods.rb
100
98
  - lib/rack/app/params.rb
101
99
  - lib/rack/app/request_configurator.rb
102
100
  - lib/rack/app/router.rb
@@ -104,6 +102,13 @@ files:
104
102
  - lib/rack/app/router/dynamic.rb
105
103
  - lib/rack/app/router/static.rb
106
104
  - lib/rack/app/serializer.rb
105
+ - lib/rack/app/singleton_methods.rb
106
+ - lib/rack/app/singleton_methods/http_methods.rb
107
+ - lib/rack/app/singleton_methods/inheritance.rb
108
+ - lib/rack/app/singleton_methods/mounting.rb
109
+ - lib/rack/app/singleton_methods/rack_interface.rb
110
+ - lib/rack/app/singleton_methods/route_handling.rb
111
+ - lib/rack/app/singleton_methods/utility.rb
107
112
  - lib/rack/app/test.rb
108
113
  - lib/rack/app/utils.rb
109
114
  - lib/rack/app/version.rb
@@ -1,5 +0,0 @@
1
- require 'rack/app'
2
- module Rack::App::File
3
- require 'rack/app/file/streamer'
4
- require 'rack/app/file/server'
5
- end
@@ -1,35 +0,0 @@
1
- class Rack::App::File::Streamer
2
-
3
- include Enumerable
4
-
5
- def each(&block)
6
- file { |f| f.each(&block) }
7
- end
8
-
9
- def render(object=nil)
10
- file { |f| f.read }
11
- end
12
-
13
- def mtime(object=nil)
14
- ::File.mtime(@file_path).httpdate
15
- end
16
-
17
- def length(object=nil)
18
- ::Rack::Utils.bytesize(render())
19
- end
20
-
21
- protected
22
-
23
- def initialize(file_path)
24
- @file_path = file_path
25
- @file = File.open(file_path)
26
- end
27
-
28
- def file(&block)
29
- @file.reopen(@file_path) if @file.closed?
30
- return block.call(@file)
31
- ensure
32
- @file.close
33
- end
34
-
35
- end
@@ -1,7 +0,0 @@
1
- module Rack
2
- end unless defined?(Rack)
3
- class Rack::App
4
- end unless defined?(Rack::App)
5
- module Rack::App::File
6
- VERSION = File.read(File.join(File.dirname(__FILE__),'..','..', '..', '..', 'VERSION')).strip
7
- end