hanami-router 0.6.2 → 0.7.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: 2a2586983782aac1daa6b998207f6b1711ce0b30
4
- data.tar.gz: 56be6fbaa73b846cd3d531da9747edbbf938cb6f
3
+ metadata.gz: 393f316c6e21157b2ac3d3d7a9544c9311e55c41
4
+ data.tar.gz: 887ed0b0c22b13bf105a621b2cfb9f8ce7542ea7
5
5
  SHA512:
6
- metadata.gz: d4b100f203d78a140e62830b309f1bf6edca12cd825dfbfde86e6b89645baf7ed61898d06ec38bcf55b15eccb0fc38d3bc63ae9ffa151e6bb9a4dc3232d95650
7
- data.tar.gz: 807b558c107acf679aef63e26b7b17bf4d7d726e6ae198beb954e9d380ba1ebc3578ea95ce9c589111591ca81f8a4ffcd3050301a4c0c0bcbcc506604d1a8a06
6
+ metadata.gz: 4fc20e2fe87c4fd3f2a7c088d26836dca184f7dfa4918930793442f7fabecd99de3eaec56c16d2e0fe85cca6f5b90b21607efaa297b27868dad5a0701e0de649
7
+ data.tar.gz: 722378463a90b9ea3ebcd5151a630a776655ce37d1025389b5dda41f4bd76e7345506a44188ad10c6ec8d2af8f35a741419665afc0704ce782d8596db3d0d5ac
data/CHANGELOG.md CHANGED
@@ -1,6 +1,21 @@
1
1
  # Hanami::Router
2
2
  Rack compatible HTTP router for Ruby
3
3
 
4
+ ## v0.7.0 - 2016-07-22
5
+ ### Added
6
+ - [Sean Collins] Introduced `Hanami::Router#root`. Example: `root to: 'home#index'`, equivalent to `get '/', to: 'home#index', as: :root`.
7
+ - [Nicola Racco] Allow to mount Rack applications at a specific host. Example: `mount Blog, host: 'blog'`, which will be hit for `GET http://blog.example.com`
8
+ - [Luca Guidi] Support `multi_json` gem as backend for JSON body parser. If `multi_json` is present in the gem bundle, it will be used, otherwise it will fallback to Ruby's `JSON`.
9
+ - [Luca Guidi] Introduced `Hanami::Routing::RecognizedRoute#path` in order to allow a better introspection
10
+
11
+ ### Fixed
12
+ - [Andrew De Ponte] Make routes inspection to work when non-Hanami apps are mounted
13
+ - [Andrew De Ponte] Ensure to set the right `SCRIPT_NAME` in Rack env for mounted Hanami apps
14
+ - [Luca Guidi] Fix `NoMethodError` when `Hanami::Router#recognize` is invoked with a Rack env or a route name or a path that can't be recognized
15
+
16
+ ### Changed
17
+ – [Luca Guidi] Drop support for Ruby 2.0 and 2.1. Official support for JRuby 9.0.5.0+
18
+
4
19
  ## v0.6.2 - 2016-02-05
5
20
  ### Fixed
6
21
  - [Anton Davydov] Fix double leading slash for Capybara's `current_path`
data/README.md CHANGED
@@ -68,7 +68,8 @@ For the standalone usage, it supports neat features:
68
68
 
69
69
  ```ruby
70
70
  Hanami::Router.new do
71
- get '/', to: ->(env) { [200, {}, ['Hi!']] }
71
+ root to: ->(env) { [200, {}, ['Hello']] }
72
+ get '/lambda', to: ->(env) { [200, {}, ['World']] }
72
73
  get '/dashboard', to: Dashboard::Index
73
74
  get '/rack-app', to: RackApp.new
74
75
  get '/flowers', to: 'flowers#index'
@@ -167,6 +168,15 @@ router.trace '/hanami', to: endpoint
167
168
 
168
169
 
169
170
 
171
+ ### Root:
172
+
173
+ ```ruby
174
+ router = Hanami::Router.new
175
+ router.root to: ->(env) { [200, {}, ['Hello from Hanami!']] }
176
+ ```
177
+
178
+
179
+
170
180
  ### Redirect:
171
181
 
172
182
  ```ruby
@@ -608,6 +618,10 @@ If the json can't be parsed an exception is raised:
608
618
  Hanami::Routing::Parsing::BodyParsingError
609
619
  ```
610
620
 
621
+ ##### `multi_json`
622
+
623
+ If you want to use a different JSON backend, include `multi_json` in your `Gemfile`.
624
+
611
625
  #### Custom Parsers
612
626
 
613
627
  ```ruby
@@ -17,13 +17,14 @@ Gem::Specification.new do |spec|
17
17
  spec.executables = []
18
18
  spec.test_files = spec.files.grep(%r{^(test)/})
19
19
  spec.require_paths = ['lib']
20
- spec.required_ruby_version = '>= 2.0.0'
20
+ spec.required_ruby_version = '>= 2.2.0'
21
21
 
22
+ spec.add_dependency 'rack', '~> 1.6'
22
23
  spec.add_dependency 'http_router', '~> 0.11'
23
- spec.add_dependency 'hanami-utils', '~> 0.7'
24
+ spec.add_dependency 'hanami-utils', '~> 0.8'
24
25
 
25
26
  spec.add_development_dependency 'bundler', '~> 1.5'
26
27
  spec.add_development_dependency 'minitest', '~> 5'
27
- spec.add_development_dependency 'rake', '~> 10'
28
+ spec.add_development_dependency 'rake', '~> 11'
28
29
  spec.add_development_dependency 'rack-test', '~> 0.6'
29
30
  end
data/lib/hanami/router.rb CHANGED
@@ -91,6 +91,14 @@ module Hanami
91
91
  end
92
92
  end
93
93
 
94
+ # Defines root path
95
+ #
96
+ # @since 0.7.0
97
+ # @api private
98
+ #
99
+ # @see Hanami::Router#root
100
+ ROOT_PATH = '/'.freeze
101
+
94
102
  # Returns the given block as it is.
95
103
  #
96
104
  # When Hanami::Router is used as a standalone gem and the routes are defined
@@ -491,6 +499,36 @@ module Hanami
491
499
  @router.trace(path, options, &blk)
492
500
  end
493
501
 
502
+ # Defines a root route (a GET route for '/')
503
+ #
504
+ # @param options [Hash] the options to customize the route
505
+ # @option options [String,Proc,Class,Object#call] :to the endpoint
506
+ #
507
+ # @param blk [Proc] the anonymous proc to be used as endpoint for the route
508
+ #
509
+ # @return [Hanami::Routing::Route] this may vary according to the :route
510
+ # option passed to the constructor
511
+ #
512
+ # @since 0.7.0
513
+ #
514
+ # @example Fixed matching string
515
+ # require 'hanami/router'
516
+ #
517
+ # router = Hanami::Router.new
518
+ # router.root to: ->(env) { [200, {}, ['Hello from Hanami!']] }
519
+ #
520
+ # @example Included names as `root` (for path and url helpers)
521
+ # require 'hanami/router'
522
+ #
523
+ # router = Hanami::Router.new(scheme: 'https', host: 'hanamirb.org')
524
+ # router.root to: ->(env) { [200, {}, ['Hello from Hanami!']] }
525
+ #
526
+ # router.path(:root) # => "/"
527
+ # router.url(:root) # => "https://hanamirb.org/"
528
+ def root(options = {}, &blk)
529
+ @router.get(ROOT_PATH, options.merge(as: :root), &blk)
530
+ end
531
+
494
532
  # Defines a route that accepts a OPTIONS request for the given path.
495
533
  #
496
534
  # @param path [String] the relative URL to be matched
@@ -1,6 +1,6 @@
1
1
  module Hanami
2
2
  class Router
3
3
  # @since 0.1.0
4
- VERSION = '0.6.2'.freeze
4
+ VERSION = '0.7.0'.freeze
5
5
  end
6
6
  end
@@ -14,6 +14,10 @@ module Hanami
14
14
  # @api private
15
15
  NAMING_PATTERN = '%{controller}::%{action}'.freeze
16
16
 
17
+ # @since 0.7.0
18
+ # @api private
19
+ DEFAULT_RESPONSE = [404, {'X-Cascade' => 'pass'}, 'Not Found'].freeze
20
+
17
21
  # Default separator for controller and action.
18
22
  # A different separator can be passed to #initialize with the `:separator` option.
19
23
  #
@@ -48,7 +52,7 @@ module Hanami
48
52
  # will be ignored.
49
53
  # See the examples below.
50
54
  #
51
- # @option options [String] :action_separator the sepatator between controller and
55
+ # @option options [String] :action_separator the separator between controller and
52
56
  # action name. (defaults to `ACTION_SEPARATOR`)
53
57
  #
54
58
  # @return [Hanami::Routing::EndpointResolver] self
@@ -178,7 +182,7 @@ module Hanami
178
182
  protected
179
183
  def default
180
184
  @endpoint_class.new(
181
- ->(env) { [404, {'X-Cascade' => 'pass'}, 'Not Found'] }
185
+ ->(env) { DEFAULT_RESPONSE }
182
186
  )
183
187
  end
184
188
 
@@ -1,3 +1,4 @@
1
+ require 'uri'
1
2
  require 'http_router'
2
3
  require 'hanami/utils/io'
3
4
  require 'hanami/routing/endpoint_resolver'
@@ -37,6 +38,24 @@ module Hanami
37
38
  # @api private
38
39
  SCRIPT_NAME = 'SCRIPT_NAME'.freeze
39
40
 
41
+ # Path info - rack environment variable
42
+ #
43
+ # @since 0.7.0
44
+ # @api private
45
+ PATH_INFO = 'PATH_INFO'.freeze
46
+
47
+ # Default PATH_INFO for Rack requests
48
+ #
49
+ # @since 0.7.0
50
+ # @api private
51
+ DEFAULT_PATH_INFO = '/'.freeze
52
+
53
+ # URL separator
54
+ #
55
+ # @since 0.7.0
56
+ # @api private
57
+ URL_SEPARATOR = '/'.freeze
58
+
40
59
  # @since 0.5.0
41
60
  # @api private
42
61
  attr_reader :namespace
@@ -48,6 +67,8 @@ module Hanami
48
67
  # @since 0.1.0
49
68
  # @api private
50
69
  def initialize(options = {}, &blk)
70
+ @compiled = false
71
+ @uri_parser = URI::Parser.new
51
72
  super(options, &nil)
52
73
 
53
74
  @namespace = options[:namespace] if options[:namespace]
@@ -122,7 +143,7 @@ module Hanami
122
143
  # @since 0.1.1
123
144
  # @api private
124
145
  def mount(app, options)
125
- add("#{ options.fetch(:at) }*").to(
146
+ add("#{ options.fetch(:at) }*", host: options[:host]).to(
126
147
  @resolver.resolve(to: app)
127
148
  )
128
149
  end
@@ -158,10 +179,15 @@ module Hanami
158
179
  end
159
180
 
160
181
  # @api private
161
- # @since 0.5.0
162
- def rewrite_path_info(env, request)
163
- super
164
- env[SCRIPT_NAME] = @prefix.join(env[SCRIPT_NAME])
182
+ def rewrite_partial_path_info(env, request)
183
+ if request.path.empty?
184
+ env[SCRIPT_NAME] += env[PATH_INFO]
185
+ env[PATH_INFO] = DEFAULT_PATH_INFO
186
+ else
187
+ path_info_before = env[PATH_INFO].dup
188
+ env[PATH_INFO] = "/#{@uri_parser.escape(request.path.join(URL_SEPARATOR))}"
189
+ env[SCRIPT_NAME] += path_info_before[0, path_info_before.bytesize - env[PATH_INFO].bytesize]
190
+ end
165
191
  end
166
192
 
167
193
  private
@@ -1,4 +1,4 @@
1
- require 'json'
1
+ require 'hanami/utils/json'
2
2
 
3
3
  module Hanami
4
4
  module Routing
@@ -18,8 +18,8 @@ module Hanami
18
18
  #
19
19
  # @since 0.2.0
20
20
  def parse(body)
21
- JSON.parse(body)
22
- rescue JSON::ParserError => e
21
+ Hanami::Utils::Json.load(body)
22
+ rescue Hanami::Utils::Json::ParserError => e
23
23
  raise BodyParsingError.new(e.message)
24
24
  end
25
25
  end
@@ -12,6 +12,10 @@ module Hanami
12
12
  # @api private
13
13
  REQUEST_METHOD = 'REQUEST_METHOD'.freeze
14
14
 
15
+ # @since 0.7.0
16
+ # @api private
17
+ PATH_INFO = 'PATH_INFO'.freeze
18
+
15
19
  # @since 0.5.0
16
20
  # @api private
17
21
  NAMESPACE = '%s::'.freeze
@@ -39,7 +43,9 @@ module Hanami
39
43
  # @since 0.5.0
40
44
  # @api private
41
45
  def initialize(response, env, router)
42
- @env = env
46
+ @env = env
47
+ @endpoint = nil
48
+ @params = {}
43
49
 
44
50
  unless response.nil?
45
51
  @endpoint = response.route.dest
@@ -81,6 +87,16 @@ module Hanami
81
87
  @env[REQUEST_METHOD]
82
88
  end
83
89
 
90
+ # Relative URL (path)
91
+ #
92
+ # @return [String]
93
+ #
94
+ # @since 0.7.0
95
+ # @api public
96
+ def path
97
+ @env[PATH_INFO]
98
+ end
99
+
84
100
  # Action name
85
101
  #
86
102
  # @return [String]
@@ -99,6 +115,7 @@ module Hanami
99
115
  #
100
116
  # puts router.recognize('/books/23').action # => "books#show"
101
117
  def action
118
+ return unless routable?
102
119
  namespace = NAMESPACE % @namespace
103
120
 
104
121
  if destination.match(namespace)
@@ -129,7 +146,7 @@ module Hanami
129
146
  # puts router.recognize('/').routable? # => true
130
147
  # puts router.recognize('/foo').routable? # => false
131
148
  def routable?
132
- !!@endpoint
149
+ !@endpoint.nil?
133
150
  end
134
151
 
135
152
  private
@@ -142,10 +159,12 @@ module Hanami
142
159
  @destination ||= begin
143
160
  case k = @endpoint.__getobj__
144
161
  when Class
145
- k
162
+ k.name
163
+ when Proc
164
+ @endpoint.inspect
146
165
  else
147
- k.class
148
- end.name
166
+ k.class.name
167
+ end
149
168
  end
150
169
  end
151
170
  end
@@ -16,6 +16,13 @@ module Hanami
16
16
  # router = Hanami::Router.new
17
17
  # router.get('/', to: endpoint) # => #<Hanami::Routing::Route:0x007f83083ba028 ...>
18
18
  class Route < HttpRouter::Route
19
+ # @since 0.7.0
20
+ # @api private
21
+ def initialize(*)
22
+ super
23
+ @name = nil
24
+ end
25
+
19
26
  # Asks the given resolver to return an endpoint that will be associated
20
27
  # with the other options.
21
28
  #
@@ -45,12 +52,12 @@ module Hanami
45
52
  end
46
53
 
47
54
  # Introspect the given route to understand if there is a wrapped
48
- # Hanami::Router
55
+ # router that has an inspector
49
56
  #
50
57
  # @since 0.2.0
51
58
  # @api private
52
59
  def nested_router
53
- dest.routes if dest.respond_to?(:routes)
60
+ dest.routes if dest.respond_to?(:routes) && dest.routes.respond_to?(:inspector)
54
61
  end
55
62
 
56
63
  private
metadata CHANGED
@@ -1,7 +1,7 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: hanami-router
3
3
  version: !ruby/object:Gem::Version
4
- version: 0.6.2
4
+ version: 0.7.0
5
5
  platform: ruby
6
6
  authors:
7
7
  - Luca Guidi
@@ -10,8 +10,22 @@ authors:
10
10
  autorequire:
11
11
  bindir: bin
12
12
  cert_chain: []
13
- date: 2016-02-05 00:00:00.000000000 Z
13
+ date: 2016-07-22 00:00:00.000000000 Z
14
14
  dependencies:
15
+ - !ruby/object:Gem::Dependency
16
+ name: rack
17
+ requirement: !ruby/object:Gem::Requirement
18
+ requirements:
19
+ - - "~>"
20
+ - !ruby/object:Gem::Version
21
+ version: '1.6'
22
+ type: :runtime
23
+ prerelease: false
24
+ version_requirements: !ruby/object:Gem::Requirement
25
+ requirements:
26
+ - - "~>"
27
+ - !ruby/object:Gem::Version
28
+ version: '1.6'
15
29
  - !ruby/object:Gem::Dependency
16
30
  name: http_router
17
31
  requirement: !ruby/object:Gem::Requirement
@@ -32,14 +46,14 @@ dependencies:
32
46
  requirements:
33
47
  - - "~>"
34
48
  - !ruby/object:Gem::Version
35
- version: '0.7'
49
+ version: '0.8'
36
50
  type: :runtime
37
51
  prerelease: false
38
52
  version_requirements: !ruby/object:Gem::Requirement
39
53
  requirements:
40
54
  - - "~>"
41
55
  - !ruby/object:Gem::Version
42
- version: '0.7'
56
+ version: '0.8'
43
57
  - !ruby/object:Gem::Dependency
44
58
  name: bundler
45
59
  requirement: !ruby/object:Gem::Requirement
@@ -74,14 +88,14 @@ dependencies:
74
88
  requirements:
75
89
  - - "~>"
76
90
  - !ruby/object:Gem::Version
77
- version: '10'
91
+ version: '11'
78
92
  type: :development
79
93
  prerelease: false
80
94
  version_requirements: !ruby/object:Gem::Requirement
81
95
  requirements:
82
96
  - - "~>"
83
97
  - !ruby/object:Gem::Version
84
- version: '10'
98
+ version: '11'
85
99
  - !ruby/object:Gem::Dependency
86
100
  name: rack-test
87
101
  requirement: !ruby/object:Gem::Requirement
@@ -142,7 +156,7 @@ required_ruby_version: !ruby/object:Gem::Requirement
142
156
  requirements:
143
157
  - - ">="
144
158
  - !ruby/object:Gem::Version
145
- version: 2.0.0
159
+ version: 2.2.0
146
160
  required_rubygems_version: !ruby/object:Gem::Requirement
147
161
  requirements:
148
162
  - - ">="
@@ -150,9 +164,8 @@ required_rubygems_version: !ruby/object:Gem::Requirement
150
164
  version: '0'
151
165
  requirements: []
152
166
  rubyforge_project:
153
- rubygems_version: 2.5.1
167
+ rubygems_version: 2.6.4
154
168
  signing_key:
155
169
  specification_version: 4
156
170
  summary: Rack compatible HTTP router for Ruby and Hanami
157
171
  test_files: []
158
- has_rdoc: