Skip to content

Better support for overriding options programmatically #805

Description

@ameir

Hello,

I am currently setting options from a file, similar to what is described in #413.

An issue I am having is that the options loaded in this way bypass validation, so bogus parameters can be inserted, and (more importantly for my case), type validation is not attempted. For example, if a Thor option is changed from a string to an array, if the config file sets that option as a string, it will remain as a string in the options hash. If code is dependent on this option being an array, things begin to fall apart.

If there's a way to instead merge a hash with the hash from

def parse(args) # rubocop:disable Metrics/MethodLength
@pile = args.dup
@is_treated_as_value = false
@parsing_options = true
while peek
if parsing_options?
match, is_switch = current_is_switch?
shifted = shift
if is_switch
case shifted
when SHORT_SQ_RE
unshift($1.split("").map { |f| "-#{f}" })
next
when EQ_RE
unshift($2, :is_value => true)
switch = $1
when SHORT_NUM
unshift($2)
switch = $1
when LONG_RE, SHORT_RE
switch = $1
end
switch = normalize_switch(switch)
option = switch_option(switch)
result = parse_peek(switch, option)
assign_result!(option, result)
elsif @stop_on_unknown
@parsing_options = false
@extra << shifted
@stopped_parsing_after_extra_index ||= @extra.size
@extra << shift while peek
break
elsif match
@extra << shifted
@extra << shift while peek && peek !~ /^-/
else
@extra << shifted
end
else
@extra << shift
end
end
check_requirement! unless @disable_required_check
assigns = Thor::CoreExt::HashWithIndifferentAccess.new(@assigns)
assigns.freeze
assigns
end
, that would probably work (i.e. override that method and merge one hash over the other). One issue with this (and the original method) is that defaults are resolved without us knowing if option values are default or user-provided. If there's a way to provide the initial hash before defaults are resolved, that would be ideal.

Thank you!

Activity

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Metadata

Metadata

Assignees

No one assigned

    Labels

    No labels
    No labels

    Type

    No type

    Projects

    No projects

      Milestone

      No milestone

      Relationships

      None yet

      Development

      No branches or pull requests

      Issue actions