lib/hanami/configuration.rb in hanami-1.3.5 vs lib/hanami/configuration.rb in hanami-2.0.0.alpha1

- old
+ new

@@ -1,215 +1,205 @@ -require 'concurrent' -require 'hanami/application' -require 'hanami/utils/class' -require 'hanami/utils/string' +# frozen_string_literal: true +require "uri" +require "concurrent/hash" +require "concurrent/array" +require "dry/inflector" + module Hanami - # @api private + # Hanami application configuration + # + # @since 2.0.0 + # + # rubocop:disable Metrics/ClassLength class Configuration - require "hanami/configuration/app" + require "hanami/configuration/cookies" + require "hanami/configuration/sessions" require "hanami/configuration/middleware" + require "hanami/configuration/security" - # @api private - def initialize(&blk) - @settings = Concurrent::Map.new - instance_eval(&blk) - end + # rubocop:disable Metrics/MethodLength + def initialize(env:) + @settings = Concurrent::Hash.new - # Mount a Hanami::Application or a Rack app - # - # @param app [#call] an application compatible with Rack SPEC - # @param options [Hash] a set of options - # @option :at [String] options the mount point - # @option :host [String] options the mount point - # - # @since 0.9.0 - # - # @example - # # config/environment.rb - # # ... - # Hanami.configure do - # mount Beta::Application, at: '/', host: 'beta.bookshelf.com' - # mount Admin::Application, at: '/api' - # mount Web::Application, at: '/' - # - # # ... - # end - def mount(app, options) - mounted[app] = App.new(app, options) + self.env = env + self.environments = DEFAULT_ENVIRONMENTS.clone + + self.base_url = DEFAULT_BASE_URL + + self.logger = DEFAULT_LOGGER.clone + self.routes = DEFAULT_ROUTES + self.cookies = DEFAULT_COOKIES + self.sessions = DEFAULT_SESSIONS + + self.default_request_format = DEFAULT_REQUEST_FORMAT + self.default_response_format = DEFAULT_RESPONSE_FORMAT + + self.middleware = Middleware.new + self.security = Security.new + + self.inflections = Dry::Inflector.new end + # rubocop:enable Metrics/MethodLength - # Configure database - # - # @param blk [Proc] the database configuration - # - # @see Hanami::Model.configure - # - # @example - # # config/environment.rb - # # ... - # Hanami.configure do - # model do - # adapter :sql, ENV['DATABASE_URL'] - # - # migrations 'db/migrations' - # schema 'db/schema.sql' - # end - # - # # ... - # end - def model(&blk) - if block_given? - settings.put_if_absent(:model, blk) - else - settings.fetch(:model) + def finalize + environment_for(env).each do |blk| + instance_eval(&blk) end + + self end - # Configure mailer - # - # @param blk [Proc] the mailer configuration - # - # @see Hanami::Mailer.configure - # - # @example - # # config/environment.rb - # # ... - # Hanami.configure do - # mailer do - # root 'lib/bookshelf/mailers' - # - # # See https://guides.hanamirb.org/mailers/delivery - # delivery :test - # end - # - # # ... - # end - def mailer(&blk) - mailer_settings.push(blk) if block_given? + def environment(name, &blk) + environment_for(name).push(blk) end - # @since next - # @api private - def mailer_settings - settings.fetch_or_store(:mailers, []) + def env=(value) + settings[:env] = value end - # @since 0.9.0 - # @api private - def mounted - settings.fetch_or_store(:mounted, {}) + def env + settings.fetch(:env) end - # @since 1.2.0 - # - # @example - # # config/environment.rb - # # ... - # Hanami.configure do - # middleware.use MyRackMiddleware - # end + def base_url=(value) + settings[:base_url] = URI.parse(value) + end + + def base_url + settings.fetch(:base_url) + end + + def logger=(options) + settings[:logger] = options + end + + def logger + settings.fetch(:logger) + end + + def routes=(value) + settings[:routes] = value + end + + def routes + settings.fetch(:routes) + end + + def cookies=(options) + settings[:cookies] = Cookies.new(options) + end + + def cookies + settings.fetch(:cookies) + end + + def sessions=(*args) + settings[:sessions] = Sessions.new(args) + end + + def sessions + settings.fetch(:sessions) + end + + def default_request_format=(value) + settings[:default_request_format] = value + end + + def default_request_format + settings.fetch(:default_request_format) + end + + def default_response_format=(value) + settings[:default_response_format] = value + end + + def default_response_format + settings.fetch(:default_response_format) + end + def middleware - settings.fetch_or_store(:middleware, Configuration::Middleware.new) + settings.fetch(:middleware) end - # Setup Early Hints feature - # - # @since 1.2.0 - # - # @example Enable for all the environments - # # config/environment.rb - # Hanami.configure do - # early_hints true - # end - # - # @example Enable only for production - # # config/environment.rb - # Hanami.configure do - # environment :production do - # early_hints true - # end - # end - def early_hints(value = nil) - if value.nil? - settings.fetch(:early_hints, false) - else - settings[:early_hints] = value - end + def security=(value) + settings[:security] = value end - # @since 0.9.0 - # @api private - def apps - mounted.each_pair do |klass, app| - yield(app) if klass <= Hanami::Application - end + def security + settings.fetch(:security) end - # Configure logger - # - # @since 1.0.0 - # - # @param options [Array] a set of options - # - # @see Hanami.logger - # @see Hanami::Logger - # - # @see https://guides.hanamirb.org/projects/logging - # - # @example Basic Usage - # # config/environment.rb - # # ... - # Hanami.configure do - # # ... - # environment :development do - # logger level: :debug - # end - # end - # - # @example Daily Rotation - # # config/environment.rb - # # ... - # Hanami.configure do - # # ... - # environment :development do - # logger 'daily', level: :debug - # end - # end - def logger(*options) - if options.empty? - settings.fetch(:logger, nil) + def inflections(&blk) + if blk.nil? + settings.fetch(:inflections) else - settings[:logger] = options + settings[:inflections] = Dry::Inflector.new(&blk) end end - # Configure settings for the current environment - # @since 1.0.0 - # - # @param name [Symbol] the name of the Hanami environment - # - # @see Hanami.env - # - # @example Configure Logging for Different Environments - # # config/environment.rb - # # ... - # Hanami.configure do - # # ... - # environment :development do - # logger level: :debug - # end - # - # environment :production do - # logger level: :info, formatter: :json - # end - # end - def environment(name) - yield if ENV['HANAMI_ENV'] == name.to_s + def router_settings + bu = base_url + + { + scheme: bu.scheme, + host: bu.host, + port: bu.port, + inflector: inflections + } end + def for_each_middleware(&blk) + stack = middleware.stack.dup + stack += sessions.middleware if sessions.enabled? + + stack.each(&blk) + end + + protected + + def environment_for(name) + settings[:environments][name] + end + + def environments=(values) + settings[:environments] = values + end + + def middleware=(value) + settings[:middleware] = value + end + + def inflections=(value) + settings[:inflections] = value + end + private - # @api private + DEFAULT_ENVIRONMENTS = Concurrent::Hash.new { |h, k| h[k] = Concurrent::Array.new } + private_constant :DEFAULT_ENVIRONMENTS + + DEFAULT_BASE_URL = "http://0.0.0.0:2300" + private_constant :DEFAULT_BASE_URL + + DEFAULT_LOGGER = { level: :debug }.freeze + private_constant :DEFAULT_LOGGER + + DEFAULT_ROUTES = File.join("config", "routes") + private_constant :DEFAULT_ROUTES + + DEFAULT_COOKIES = Cookies.null + private_constant :DEFAULT_COOKIES + + DEFAULT_SESSIONS = Sessions.null + private_constant :DEFAULT_SESSIONS + + DEFAULT_REQUEST_FORMAT = :html + private_constant :DEFAULT_REQUEST_FORMAT + + DEFAULT_RESPONSE_FORMAT = :html + private_constant :DEFAULT_RESPONSE_FORMAT + attr_reader :settings end + # rubocop:enable Metrics/ClassLength end