Class: Wurk::Web::Authorization

Inherits:
Object
  • Object
show all
Defined in:
lib/wurk/web/config.rb

Overview

Rack middleware inserted into the engine. Resolves PATH_INFO + REQUEST_METHOD from env and delegates to Wurk::Web.config. The engine's mount path is stripped via SCRIPT_NAME so the callback sees engine-relative paths.

Constant Summary collapse

FORBIDDEN_BODY =
'Forbidden'
READ_ONLY_BODY =
'Read-only mode'
FORBIDDEN_HEADERS =
{ 'Content-Type' => 'text/plain' }.freeze
SAFE_METHODS =

Methods allowed while read-only. Anything else is a mutation and 403s.

%w[GET HEAD OPTIONS].freeze

Instance Method Summary collapse

Constructor Details

#initialize(app) ⇒ Authorization

Returns a new instance of Authorization.



403
404
405
# File 'lib/wurk/web/config.rb', line 403

def initialize(app)
  @app = app
end

Instance Method Details

#call(env) ⇒ Object



407
408
409
410
411
412
413
414
415
416
417
418
419
420
421
422
423
424
425
426
427
428
# File 'lib/wurk/web/config.rb', line 407

def call(env)
  method = env['REQUEST_METHOD']
  path = env['PATH_INFO'].to_s
  config = Wurk::Web.config
  return forbidden(FORBIDDEN_BODY) unless config.authorized?(env, method, path)

  # The machine API's own read-only refusal is an RFC-9457 problem
  # document with a slug a client can branch on; this one is the string
  # "Read-only mode" in text/plain. Same verdict either way, so hand the
  # decision down rather than answering here — stamping the env is what
  # makes mount mode 1 (and nothing else) inherit `WURK_WEB_READ_ONLY`.
  # The host's `authorized?` block above still applies: it gates the
  # mount, and a machine client reaching this path chose that mount.
  if ::Wurk::API.engine_serves?(path)
    env[::Wurk::API::READ_ONLY_ENV] = true if config.read_only?
    return @app.call(env)
  end

  return forbidden(READ_ONLY_BODY) if config.read_only? && !SAFE_METHODS.include?(method)

  @app.call(env)
end