class Puma::Configuration
The main configuration class of Puma
.
It can be initialized with a set of “user” options and “default” options. Defaults will be merged with `Configuration.puma_default_options`.
This class works together with 2 main other classes the `UserFileDefaultOptions` which stores configuration options in order so the precedence is that user set configuration wins over “file” based configuration wins over “default” configuration. These configurations are set via the `DSL` class. This class powers the Puma
config file syntax and does double duty as a configuration DSL
used by the `Puma::CLI` and Puma
rack handler.
It also handles loading plugins.
- Note:
-
`:port` and `:host` are not valid keys. By the time they make it to the configuration options they are expected to be incorporated into a `:binds` key. Under the hood the
DSL
maps `port` and `host` calls to `:binds`config = Configuration.new({}) do |user_config, file_config, default_config| user_config.port 3003 end config.load puts config.options[:port] # => 3003
It is expected that `load` is called on the configuration instance after setting config. This method expands any values in `config_file` and puts them into the correct configuration option hash.
Once all configuration is complete it is expected that `clamp` will be called on the instance. This will expand any procs stored under “default” values. This is done because an environment variable may have been modified while loading configuration files.
Attributes
Public Class Methods
# File lib/puma/configuration.rb, line 140 def initialize(user_options={}, default_options = {}, &block) default_options = self.puma_default_options.merge(default_options) @options = UserFileDefaultOptions.new(user_options, default_options) @plugins = PluginLoader.new @user_dsl = DSL.new(@options.user_options, self) @file_dsl = DSL.new(@options.file_options, self) @default_dsl = DSL.new(@options.default_options, self) if !@options[:prune_bundler] default_options[:preload_app] = (@options[:workers] > 1) && Puma.forkable? end if block configure(&block) end end
# File lib/puma/configuration.rb, line 306 def self.temp_path require 'tmpdir' t = (Time.now.to_f * 1000).to_i "#{Dir.tmpdir}/puma-status-#{t}-#{$$}" end
Private Class Methods
# File lib/puma/configuration.rb, line 358 def self.random_token require 'securerandom' unless defined?(SecureRandom) SecureRandom.hex(16) end
Public Instance Methods
Load the specified rackup file, pull options from the rackup file, and set @app.
# File lib/puma/configuration.rb, line 266 def app found = options[:app] || load_rackup if @options[:log_requests] require 'puma/commonlogger' logger = @options[:logger] found = CommonLogger.new(found, logger) end ConfigMiddleware.new(self, found) end
Indicate if there is a properly configured app
# File lib/puma/configuration.rb, line 255 def app_configured? @options[:app] || File.exist?(rackup) end
Call once all configuration (included from rackup files) is loaded to flesh out any defaults
# File lib/puma/configuration.rb, line 236 def clamp @options.finalize_values end
# File lib/puma/configuration.rb, line 221 def config_files files = @options.all_of(:config_files) return [] if files == ['-'] return files if files.any? first_default_file = %W(config/puma/#{environment_str}.rb config/puma.rb).find do |f| File.exist?(f) end [first_default_file] end
# File lib/puma/configuration.rb, line 160 def configure yield @user_dsl, @file_dsl, @default_dsl ensure @user_dsl._offer_plugins @file_dsl._offer_plugins @default_dsl._offer_plugins end
@version 5.0.0
# File lib/puma/configuration.rb, line 184 def default_max_threads Puma.mri? ? 5 : 16 end
Return which environment we're running in
# File lib/puma/configuration.rb, line 279 def environment @options[:environment] end
# File lib/puma/configuration.rb, line 283 def environment_str environment.respond_to?(:call) ? environment.call : environment end
# File lib/puma/configuration.rb, line 302 def final_options @options.final_options end
# File lib/puma/configuration.rb, line 174 def flatten dup.flatten! end
# File lib/puma/configuration.rb, line 178 def flatten! @options = @options.flatten self end
# File lib/puma/configuration.rb, line 168 def initialize_copy(other) @conf = nil @cli_options = nil @options = @options.dup end
# File lib/puma/configuration.rb, line 215 def load config_files.each { |config_file| @file_dsl._load_from(config_file) } @options end
# File lib/puma/configuration.rb, line 287 def load_plugin(name) @plugins.create name end
# File lib/puma/configuration.rb, line 188 def puma_default_options { :min_threads => Integer(ENV['PUMA_MIN_THREADS'] || ENV['MIN_THREADS'] || 0), :max_threads => Integer(ENV['PUMA_MAX_THREADS'] || ENV['MAX_THREADS'] || default_max_threads), :log_requests => false, :debug => false, :binds => ["tcp://#{DefaultTCPHost}:#{DefaultTCPPort}"], :workers => Integer(ENV['WEB_CONCURRENCY'] || 0), :silence_single_worker_warning => false, :mode => :http, :worker_timeout => DefaultWorkerTimeout, :worker_boot_timeout => DefaultWorkerTimeout, :worker_shutdown_timeout => DefaultWorkerShutdownTimeout, :remote_address => :socket, :tag => method(:infer_tag), :environment => -> { ENV['RACK_ENV'] || ENV['RAILS_ENV'] || "development" }, :rackup => DefaultRackup, :logger => STDOUT, :persistent_timeout => Const::PERSISTENT_TIMEOUT, :first_data_timeout => Const::FIRST_DATA_TIMEOUT, :raise_exception_on_sigterm => true, :max_fast_inline => Const::MAX_FAST_INLINE, :io_selector_backend => :auto, :mutate_stdout_and_stderr_to_sync_on_write => true, } end
# File lib/puma/configuration.rb, line 259 def rackup @options[:rackup] end
# File lib/puma/configuration.rb, line 291 def run_hooks(key, arg, events) @options.all_of(key).each do |b| begin b.call arg rescue => e events.log "WARNING hook #{key} failed with exception (#{e.class}) #{e.message}" events.debug e.backtrace.join("\n") end end end
Private Instance Methods
# File lib/puma/configuration.rb, line 315 def infer_tag File.basename(Dir.getwd) end
# File lib/puma/configuration.rb, line 342 def load_rackup raise "Missing rackup file '#{rackup}'" unless File.exist?(rackup) rack_app, rack_options = rack_builder.parse_file(rackup) @options.file_options.merge!(rack_options) config_ru_binds = [] rack_options.each do |k, v| config_ru_binds << v if k.to_s.start_with?("bind") end @options.file_options[:binds] = config_ru_binds unless config_ru_binds.empty? rack_app end
Load and use the normal Rack
builder if we can, otherwise fallback to our minimal version.
# File lib/puma/configuration.rb, line 321 def rack_builder # Load bundler now if we can so that we can pickup rack from # a Gemfile if ENV.key? 'PUMA_BUNDLER_PRUNED' begin require 'bundler/setup' rescue LoadError end end begin require 'rack' require 'rack/builder' rescue LoadError # ok, use builtin version return Puma::Rack::Builder else return ::Rack::Builder end end