rage-rb 1.4.0 → 1.5.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 +4 -4
- data/CHANGELOG.md +16 -0
- data/README.md +1 -1
- data/lib/rage/cli.rb +1 -3
- data/lib/rage/controller/api.rb +22 -0
- data/lib/rage/router/backend.rb +10 -4
- data/lib/rage/router/dsl.rb +40 -0
- data/lib/rage/router/util.rb +15 -0
- data/lib/rage/templates/config.ru +0 -1
- data/lib/rage/version.rb +1 -1
- data/lib/rage-rb.rb +21 -23
- metadata +2 -2
checksums.yaml
CHANGED
@@ -1,7 +1,7 @@
|
|
1
1
|
---
|
2
2
|
SHA256:
|
3
|
-
metadata.gz:
|
4
|
-
data.tar.gz:
|
3
|
+
metadata.gz: 24a5bc4310d226a4072c06ac0a3cb015eb52163e7c37fc85aced61f5705b6ef5
|
4
|
+
data.tar.gz: 8bedd5b522c64c945a44fa4cb97e19f48d5b3a3aa46bb5687183c4cf3eac75f3
|
5
5
|
SHA512:
|
6
|
-
metadata.gz:
|
7
|
-
data.tar.gz:
|
6
|
+
metadata.gz: 10feb1fe42789d8470ecf9d7754be26b58db2f160f24c7e82aac8a831a5c4b828d297e01c2535b8e914d167de2bcf40a843b1964c5d1f3102ef4429016fefabd
|
7
|
+
data.tar.gz: 87c3ee06201e71f691b7158f911c0cfbf7763d2021801d298885c890772082a934d91fdb5df8c0f6bf65110acd480fd839ef19d6e9adc39d1c78d165a0e2701f
|
data/CHANGELOG.md
CHANGED
@@ -1,5 +1,21 @@
|
|
1
1
|
## [Unreleased]
|
2
2
|
|
3
|
+
## [1.5.0] - 2024-05-08
|
4
|
+
|
5
|
+
### Added
|
6
|
+
|
7
|
+
- Allow to have both Rails and Rage controllers in one application (#83).
|
8
|
+
- Add `authenticate_or_request_with_http_token` (#85).
|
9
|
+
- Add the `member` and `controller` route helpers (#86).
|
10
|
+
|
11
|
+
### Changed
|
12
|
+
|
13
|
+
- Deprecate `Rage.load_middlewares` (#83).
|
14
|
+
|
15
|
+
### Fixed
|
16
|
+
|
17
|
+
- Correctly init console in Rails mode (credit to [efibootmgr](https://github.com/efibootmgr)) (#84).
|
18
|
+
|
3
19
|
## [1.4.0] - 2024-05-01
|
4
20
|
|
5
21
|
### Added
|
data/README.md
CHANGED
@@ -155,8 +155,8 @@ Status | Changes
|
|
155
155
|
:white_check_mark: | ~~Add request logging.~~
|
156
156
|
:white_check_mark: | ~~Automatic code reloading in development with Zeitwerk.~~
|
157
157
|
:white_check_mark: | ~~Support conditional get with `etag` and `last_modified`.~~
|
158
|
+
:white_check_mark: | ~~Expose the `cookies` and `session` objects.~~
|
158
159
|
⏳ | Expose the `send_data` and `send_file` methods.
|
159
|
-
⏳ | Expose the `cookies` and `session` objects.
|
160
160
|
⏳ | Implement Iodine-based equivalent of Action Cable.
|
161
161
|
|
162
162
|
## Development
|
data/lib/rage/cli.rb
CHANGED
@@ -116,10 +116,8 @@ module Rage
|
|
116
116
|
def environment
|
117
117
|
require File.expand_path("config/application.rb", Dir.pwd)
|
118
118
|
|
119
|
-
# in Rails mode we delegate code loading to Rails, and thus need
|
120
|
-
# to manually load application code for CLI utilities to work
|
121
119
|
if Rage.config.internal.rails_mode
|
122
|
-
require "
|
120
|
+
require File.expand_path("config/environment.rb", Dir.pwd)
|
123
121
|
end
|
124
122
|
end
|
125
123
|
|
data/lib/rage/controller/api.rb
CHANGED
@@ -428,6 +428,28 @@ class RageController::API
|
|
428
428
|
yield token
|
429
429
|
end
|
430
430
|
|
431
|
+
# Authenticate using an HTTP Bearer token, or otherwise render an HTTP header requesting the client to send a
|
432
|
+
# Bearer token. For the authentication to be considered successful, the block should return a non-nil value.
|
433
|
+
#
|
434
|
+
# @yield [token] token value extracted from the `Authorization` header
|
435
|
+
# @example
|
436
|
+
# before_action :authenticate
|
437
|
+
#
|
438
|
+
# def authenticate
|
439
|
+
# authenticate_or_request_with_http_token do |token|
|
440
|
+
# ApiToken.find_by(token: token)
|
441
|
+
# end
|
442
|
+
# end
|
443
|
+
def authenticate_or_request_with_http_token
|
444
|
+
authenticate_with_http_token { |token| yield(token) } || request_http_token_authentication
|
445
|
+
end
|
446
|
+
|
447
|
+
# Render an HTTP header requesting the client to send a Bearer token for authentication.
|
448
|
+
def request_http_token_authentication
|
449
|
+
headers["Www-Authenticate"] = "Token"
|
450
|
+
render plain: "HTTP Token: Access denied.", status: 401
|
451
|
+
end
|
452
|
+
|
431
453
|
if !defined?(::ActionController::Parameters)
|
432
454
|
# Get the request data. The keys inside the hash are symbols, so `params.keys` returns an array of `Symbol`.<br>
|
433
455
|
# You can also load Strong Params to have Rage automatically wrap `params` in an instance of `ActionController::Parameters`.<br>
|
data/lib/rage/router/backend.rb
CHANGED
@@ -68,12 +68,18 @@ class Rage::Router::Backend
|
|
68
68
|
raise "Invalid route handler format, expected to match the 'controller#action' pattern" unless handler =~ STRING_HANDLER_REGEXP
|
69
69
|
|
70
70
|
controller, action = Rage::Router::Util.path_to_class($1), $2
|
71
|
-
run_action_method_name = controller.__register_action(action.to_sym)
|
72
71
|
|
73
|
-
|
74
|
-
|
72
|
+
if controller.ancestors.include?(RageController::API)
|
73
|
+
run_action_method_name = controller.__register_action(action.to_sym)
|
75
74
|
|
76
|
-
|
75
|
+
meta[:controller] = $1
|
76
|
+
meta[:action] = $2
|
77
|
+
|
78
|
+
handler = eval("->(env, params) { #{controller}.new(env, params).#{run_action_method_name} }")
|
79
|
+
else
|
80
|
+
# this is a Rails controller; notify `Rage::Router::Util::Cascade` to forward the request to Rails
|
81
|
+
handler = ->(_, _) { [404, { "X-Cascade" => "pass" }, []] }
|
82
|
+
end
|
77
83
|
else
|
78
84
|
raise "Non-string route handler should respond to `call`" unless handler.respond_to?(:call)
|
79
85
|
# while regular handlers are expected to be called with the `env` and `params` objects,
|
data/lib/rage/router/dsl.rb
CHANGED
@@ -209,6 +209,7 @@ class Rage::Router::DSL
|
|
209
209
|
# @param [Hash] opts scope options.
|
210
210
|
# @option opts [String] :module module option
|
211
211
|
# @option opts [String] :path path option
|
212
|
+
# @option opts [String] :controller controller option
|
212
213
|
# @example Route `/photos` to `Api::PhotosController`
|
213
214
|
# scope module: "api" do
|
214
215
|
# get "photos", to: "photos#index"
|
@@ -217,6 +218,11 @@ class Rage::Router::DSL
|
|
217
218
|
# scope path: "admin" do
|
218
219
|
# get "photos", to: "photos#index"
|
219
220
|
# end
|
221
|
+
# @example Route `/like` to `photos#like` and `/dislike` to `photos#dislike`
|
222
|
+
# scope controller: "photos" do
|
223
|
+
# post "like"
|
224
|
+
# post "dislike"
|
225
|
+
# end
|
220
226
|
# @example Nested calls
|
221
227
|
# scope module: "admin" do
|
222
228
|
# get "photos", to: "photos#index"
|
@@ -252,6 +258,19 @@ class Rage::Router::DSL
|
|
252
258
|
@defaults.pop
|
253
259
|
end
|
254
260
|
|
261
|
+
# Scopes routes to a specific controller.
|
262
|
+
#
|
263
|
+
# @example
|
264
|
+
# controller "photos" do
|
265
|
+
# post "like"
|
266
|
+
# post "dislike"
|
267
|
+
# end
|
268
|
+
def controller(controller, &block)
|
269
|
+
@controllers << controller
|
270
|
+
instance_eval &block
|
271
|
+
@controllers.pop
|
272
|
+
end
|
273
|
+
|
255
274
|
# Add a route to the collection.
|
256
275
|
#
|
257
276
|
# @example Add a `photos/search` path instead of `photos/:photo_id/search`
|
@@ -267,6 +286,27 @@ class Rage::Router::DSL
|
|
267
286
|
@path_prefixes = orig_path_prefixes
|
268
287
|
end
|
269
288
|
|
289
|
+
# Add a member route.
|
290
|
+
#
|
291
|
+
# @example Add a `photos/:id/preview` path instead of `photos/:photo_id/preview`
|
292
|
+
# resources :photos do
|
293
|
+
# member do
|
294
|
+
# get "preview"
|
295
|
+
# end
|
296
|
+
# end
|
297
|
+
def member(&block)
|
298
|
+
orig_path_prefixes = @path_prefixes
|
299
|
+
|
300
|
+
if (param_prefix = @path_prefixes.last)&.start_with?(":") && @controllers.any?
|
301
|
+
member_prefix = param_prefix.delete_prefix(":#{to_singular(@controllers.last)}_")
|
302
|
+
@path_prefixes = [*@path_prefixes[0...-1], ":#{member_prefix}"]
|
303
|
+
end
|
304
|
+
|
305
|
+
instance_eval &block
|
306
|
+
|
307
|
+
@path_prefixes = orig_path_prefixes
|
308
|
+
end
|
309
|
+
|
270
310
|
# Automatically create REST routes for a resource.
|
271
311
|
#
|
272
312
|
# @example Create five REST routes, all mapping to the `Photos` controller:
|
data/lib/rage/router/util.rb
CHANGED
@@ -30,4 +30,19 @@ class Rage::Router::Util
|
|
30
30
|
end
|
31
31
|
end
|
32
32
|
end
|
33
|
+
|
34
|
+
# @private
|
35
|
+
class Cascade
|
36
|
+
def initialize(rage_app, rails_app)
|
37
|
+
@rage_app = rage_app
|
38
|
+
@rails_app = rails_app
|
39
|
+
end
|
40
|
+
|
41
|
+
def call(env)
|
42
|
+
result = @rage_app.call(env)
|
43
|
+
return result if result[0] == :__http_defer__ || result[1]["X-Cascade".freeze] != "pass".freeze
|
44
|
+
|
45
|
+
@rails_app.call(env)
|
46
|
+
end
|
47
|
+
end
|
33
48
|
end
|
data/lib/rage/version.rb
CHANGED
data/lib/rage-rb.rb
CHANGED
@@ -7,7 +7,25 @@ require "pathname"
|
|
7
7
|
|
8
8
|
module Rage
|
9
9
|
def self.application
|
10
|
-
Application.new(__router)
|
10
|
+
app = Application.new(__router)
|
11
|
+
|
12
|
+
config.middleware.middlewares.reverse.inject(app) do |next_in_chain, (middleware, args, block)|
|
13
|
+
# in Rails compatibility mode we first check if the middleware is a part of the Rails middleware stack;
|
14
|
+
# if it is - it is expected to be built using `ActionDispatch::MiddlewareStack::Middleware#build`
|
15
|
+
if Rage.config.internal.rails_mode
|
16
|
+
rails_middleware = Rails.application.config.middleware.middlewares.find { |m| m.name == middleware.name }
|
17
|
+
end
|
18
|
+
|
19
|
+
if rails_middleware
|
20
|
+
rails_middleware.build(next_in_chain)
|
21
|
+
else
|
22
|
+
middleware.new(next_in_chain, *args, &block)
|
23
|
+
end
|
24
|
+
end
|
25
|
+
end
|
26
|
+
|
27
|
+
def self.multi_application
|
28
|
+
Rage::Router::Util::Cascade.new(application, Rails.application)
|
11
29
|
end
|
12
30
|
|
13
31
|
def self.routes
|
@@ -43,28 +61,8 @@ module Rage
|
|
43
61
|
@logger ||= config.logger
|
44
62
|
end
|
45
63
|
|
46
|
-
def self.load_middlewares(
|
47
|
-
|
48
|
-
# in Rails compatibility mode we first check if the middleware is a part of the Rails middleware stack;
|
49
|
-
# if it is - it is expected to be built using `ActionDispatch::MiddlewareStack::Middleware#build`, but Rack
|
50
|
-
# expects the middleware to respond to `#new`, so we wrap the middleware into a helper module
|
51
|
-
if Rage.config.internal.rails_mode
|
52
|
-
rails_middleware = Rails.application.config.middleware.middlewares.find { |m| m.name == middleware.name }
|
53
|
-
if rails_middleware
|
54
|
-
wrapper = Module.new do
|
55
|
-
extend self
|
56
|
-
attr_accessor :middleware
|
57
|
-
def new(app, *, &)
|
58
|
-
middleware.build(app)
|
59
|
-
end
|
60
|
-
end
|
61
|
-
wrapper.middleware = rails_middleware
|
62
|
-
middleware = wrapper
|
63
|
-
end
|
64
|
-
end
|
65
|
-
|
66
|
-
rack_builder.use(middleware, *args, &block)
|
67
|
-
end
|
64
|
+
def self.load_middlewares(_)
|
65
|
+
puts "`Rage.load_middlewares` is deprecated and has been merged into `Rage.application`. Please remove this call."
|
68
66
|
end
|
69
67
|
|
70
68
|
def self.code_loader
|
metadata
CHANGED
@@ -1,14 +1,14 @@
|
|
1
1
|
--- !ruby/object:Gem::Specification
|
2
2
|
name: rage-rb
|
3
3
|
version: !ruby/object:Gem::Version
|
4
|
-
version: 1.
|
4
|
+
version: 1.5.0
|
5
5
|
platform: ruby
|
6
6
|
authors:
|
7
7
|
- Roman Samoilov
|
8
8
|
autorequire:
|
9
9
|
bindir: exe
|
10
10
|
cert_chain: []
|
11
|
-
date: 2024-05-
|
11
|
+
date: 2024-05-08 00:00:00.000000000 Z
|
12
12
|
dependencies:
|
13
13
|
- !ruby/object:Gem::Dependency
|
14
14
|
name: thor
|