{"record":{"id":"2f3473aa84ed672e","repo":"ruby-concurrency/concurrent-ruby","slug":"initial-capacity-must-be-a-positive-integer","errorCode":null,"errorMessage":":initial_capacity must be a positive Integer","messagePattern":":initial_capacity must be a positive Integer","errorType":"exception","errorClass":"ArgumentError","httpStatus":null,"severity":"error","filePath":"lib/concurrent-ruby/concurrent/map.rb","lineNumber":343,"sourceCode":"    private\n\n    def raise_fetch_no_key\n      raise KeyError, 'key not found'\n    end\n\n    def initialize_copy(other)\n      super\n      populate_from(other)\n    end\n\n    def populate_from(hash)\n      hash.each_pair { |k, v| self[k] = v }\n      self\n    end\n\n    def validate_options_hash!(options)\n      if (initial_capacity = options[:initial_capacity]) && (!initial_capacity.kind_of?(Integer) || initial_capacity < 0)\n        raise ArgumentError, \":initial_capacity must be a positive Integer\"\n      end\n      if (load_factor = options[:load_factor]) && (!load_factor.kind_of?(Numeric) || load_factor <= 0 || load_factor > 1)\n        raise ArgumentError, \":load_factor must be a number between 0 and 1\"\n      end\n    end\n  end\nend\n","sourceCodeStart":325,"sourceCodeEnd":351,"githubUrl":"https://github.com/ruby-concurrency/concurrent-ruby/blob/0b88d5ff75f69b3740c8f0868e76f833cb2fd45d/lib/concurrent-ruby/concurrent/map.rb#L325-L351","documentation":"Concurrent::Map.new accepts tuning options modeled on Java's ConcurrentHashMap. validate_options_hash! (map.rb:344-346) rejects :initial_capacity unless it is an Integer >= 0; a negative number, Float, String, or other non-Integer raises ArgumentError at construction time, before any entry is stored.","triggerScenarios":"Concurrent::Map.new(initial_capacity: -1); initial_capacity: 10.0 (Float, not Integer); initial_capacity: '100' read from YAML/ENV/JSON without casting to Integer.","commonSituations":"Porting Java ConcurrentHashMap tuning parameters verbatim; loading options from stringly-typed config; passing nil or a computed value that evaluates to a negative number.","solutions":["Pass a non-negative Integer: Concurrent::Map.new(initial_capacity: 64).","Cast untrusted config at the boundary: initial_capacity: cfg.fetch('initial_capacity', 0).to_i.","Clamp computed values: [capacity, 0].max so the constructor never sees a negative number."],"exampleFix":"# before\nmap = Concurrent::Map.new(initial_capacity: cfg['initial_capacity']) # '64' or -1 raises ArgumentError\n\n# after\nmap = Concurrent::Map.new(initial_capacity: [cfg.fetch('initial_capacity', 0).to_i, 0].max)","handlingStrategy":"validation","validationCode":"def map_capacity(raw)\n  cap = raw.is_a?(Integer) ? raw : raw.to_i\n  raise ArgumentError, ':initial_capacity must be an Integer >= 0' unless cap >= 0\n  cap\nend\nConcurrent::Map.new(initial_capacity: map_capacity(cfg['initial_capacity']))","typeGuard":null,"tryCatchPattern":null,"preventionTips":["Coerce config-sourced numbers to Integer at the config boundary.","Do not port Java float capacities verbatim; this API is Integer-only.","Unit-test Map construction with your real production config values."],"tags":["ruby","concurrent-map","argumenterror","constructor-validation","configuration"],"backgroundTag":"invalid-constructor-option","analyzedSha":"0b88d5ff75f69b3740c8f0868e76f833cb2fd45d","analyzedAt":"2026-08-21T20:12:56.291Z","schemaVersion":2},"datasetVersion":"2026-08-21T23:17:16.201Z"}