@@ -618,6 +618,9 @@ def parse_options(self, arg_str, opt_str, *long_opts, **kw):
618618 posix = kw .get ('posix' , os .name == 'posix' )
619619 strict = kw .get ('strict' , True )
620620
621+ preserve_non_opts = kw .get ("preserve_non_opts" , False )
622+ remainder_arg_str = arg_str
623+
621624 # Check if we have more than one argument to warrant extra processing:
622625 odict = {} # Dictionary with options
623626 args = arg_str .split ()
@@ -629,10 +632,18 @@ def parse_options(self, arg_str, opt_str, *long_opts, **kw):
629632 try :
630633 opts ,args = getopt (argv , opt_str , long_opts )
631634 except GetoptError as e :
632- raise UsageError ('%s ( allowed: "%s" %s)' % (e .msg ,opt_str ,
633- " " .join (long_opts ))) from e
634- for o ,a in opts :
635- if o .startswith ('--' ):
635+ raise UsageError (
636+ '%s ( allowed: "%s" %s)' % (e .msg , opt_str , " " .join (long_opts ))
637+ ) from e
638+ for o , a in opts :
639+ if mode is "string" and preserve_non_opts :
640+ # remove option-parts from the original args-string and preserve remaining-part.
641+ # This relies on the arg_split(...) and getopt(...)'s impl spec, that the parsed options are
642+ # returned in the original order.
643+ remainder_arg_str = remainder_arg_str .replace (o , "" , 1 ).replace (
644+ a , "" , 1
645+ )
646+ if o .startswith ("--" ):
636647 o = o [2 :]
637648 else :
638649 o = o [1 :]
@@ -649,7 +660,10 @@ def parse_options(self, arg_str, opt_str, *long_opts, **kw):
649660 # Prepare opts,args for return
650661 opts = Struct (odict )
651662 if mode == 'string' :
652- args = ' ' .join (args )
663+ if preserve_non_opts :
664+ args = remainder_arg_str .lstrip ()
665+ else :
666+ args = " " .join (args )
653667
654668 return opts ,args
655669
0 commit comments