<div dir="ltr"><br><div class="gmail_extra"><br><br><div class="gmail_quote">On Tue, Nov 26, 2013 at 9:53 AM, Glenn Linderman <span dir="ltr"><<a href="mailto:v+python@g.nevcal.com" target="_blank">v+python@g.nevcal.com</a>></span> wrote:<br>

<blockquote class="gmail_quote" style="margin:0 0 0 .8ex;border-left:1px #ccc solid;padding-left:1ex">
  
    
  
  <div bgcolor="#FFFFFF" text="#330033">
    <div>Eli did give his use case... a front
      end for a program that has a parameter "--sync", and a front end
      preprocessor of some sort was trying to use "--sync-foo" as an
      argument, and wanted "--sync" to be left in the parameters to send
      on to the back end program.<br>
      <br>
      Design of the front-end might better be aware of back end
      parameters and not conflict, but the documentation could be
      improved, likely.<br>
      <br>
      It might also be possible to add a setting to disable the prefix
      matching feature, for code that prefers it not be done. Whether
      that is better done as a global setting, or a per-parameter
      setting I haven't thought through. But both the constructor and
      the parameter definitions already accept a variable number of
      named parameters, so I would think it would be possible to add
      another, and retain backward compatibility via an appropriate
      default.<div class="im"><br></div></div></div></blockquote><div><br></div><div>FWIW I'm not advocating a breaking behavior change here - I fully realize the ship has sailed. I'm interested in mitigation actions, though. Making the documentation explain this explicitly + adding an option to disable prefix matching (in 3.5 since we're past the 3.4 features point) will go a long way for alleviating this gotcha.<br>

<br>Eli<br></div><div><br> </div><blockquote class="gmail_quote" style="margin:0 0 0 .8ex;border-left:1px #ccc solid;padding-left:1ex"><div bgcolor="#FFFFFF" text="#330033"><div><div class="im">
      <br>
      On 11/26/2013 9:38 AM, Guido van Rossum wrote:<br>
    </div></div><div class="im">
    <blockquote type="cite">
      <div dir="ltr">
        <div>
          <div>I think matching on the shortest unique prefix is common
            for command line parsers in general, not just argparse. I
            believe optparse did this too, and even the venerable getopt
            does! I think all this originated in the original
            (non-Python) GNU standard for long option parsing. All that
            probably explains why the docs hardly touch upon it.<br>
            <br>
          </div>
          As to why parse_known_args also does this, I can see the
          reasoning behind this behavior: to the end user, "--sync" is a
          valid option, so it would be surprising if it didn't get
          recognized under certain conditions.<br>
          <br>
        </div>
        I suppose you were badly bitten by this recently? Can you tell
        us more about what happened?<br>
      </div>
      <div class="gmail_extra"><br>
        <br>
        <div class="gmail_quote">On Tue, Nov 26, 2013 at 9:30 AM, Eli
          Bendersky <span dir="ltr"><<a href="mailto:eliben@gmail.com" target="_blank">eliben@gmail.com</a>></span>
          wrote:<br>
          <blockquote class="gmail_quote" style="margin:0 0 0 .8ex;border-left:1px #ccc solid;padding-left:1ex">
            <div dir="ltr">
              <div>
                <div>
                  <div>
                    <div>Hello,<br>
                      <br>
                    </div>
                    argparse does prefix matching as long as there are
                    no conflicts. For example:<br>
                    <br>
                    <div style="margin-left:40px">argparser =
                      argparse.ArgumentParser()<br>
                      argparser.add_argument('--sync-foo',
                      action='store_true')<br>
                      args = argparser.parse_args()<br>
                    </div>
                    <br>
                  </div>
                  If I pass "--sync" to this script, it recognizes it as
                  "--sync-foo". This behavior is quite surprising
                  although I can see the motivation for it. At the very
                  least it should be much more explicitly documented
                  (AFAICS it's barely mentioned in the docs). <br>
                  <br>
                  If there's another argument registered, say
                  "--sync-bar" the above will fail due to a conflict.<br>
                  <br>
                  Now comes the nasty part. When using
                  "parse_known_args" instead of "parse_args", the above
                  happens too - --sync is recognized for --sync-foo and
                  captured by the parser. But this is wrong! The whole
                  idea of parse_known_args is to parse the known args,
                  leaving unknowns alone. This prefix matching harms
                  more than it helps here because maybe the program
                  we're actually acting as a front-end for (and hence
                  using parse_known_args) knows about --sync and wants
                  to get it.<br>
                  <br>
                </div>
                Unless I'm missing something, this is a bug. But I'm
                also not sure whether we can do anything about it at
                this point, as existing code *may* be relying on it. The
                right thing to do would be to disable this prefix
                matching when parse_known_args is called.<br>
                <br>
              </div>
              Again, at the very least this should be documented (for
              parse_known_args not less than a warning box, IMHO).<span><font color="#888888"><br>
                  <br>
                  Eli</font></span><br>
            </div>
          </blockquote>
        </div>
      </div>
    </blockquote>
    <br>
  </div></div>

<br>_______________________________________________<br>
Python-Dev mailing list<br>
<a href="mailto:Python-Dev@python.org">Python-Dev@python.org</a><br>
<a href="https://mail.python.org/mailman/listinfo/python-dev" target="_blank">https://mail.python.org/mailman/listinfo/python-dev</a><br>
Unsubscribe: <a href="https://mail.python.org/mailman/options/python-dev/eliben%40gmail.com" target="_blank">https://mail.python.org/mailman/options/python-dev/eliben%40gmail.com</a><br>
<br></blockquote></div><br></div></div>