On Thu, Apr 25, 2013 at 8:12 PM, PJ Eby <p...@telecommunity.com> wrote: > I was just fiddling with an experimental environment marker > implementation for setuptools, and ran across a bit of a quirk in the > spec. It says that the value of 'extra' is 'None', but that > comparisons can only be done on strings. > > This leads to two problems: first, the syntax doesn't have a way to > spell 'None', so you can't actually compare it to something. Second, > if you compare it to a string using the equality operators, IIUC > you'll get a TypeError under Python 3. > > Should it actually be defaulting 'extra' to an empty string? That > would actually make a lot more sense, and avoid the issue of > implementing non-string comparisons, None literals, etc. > > (Doing extras in this way actually has another problem, btw, which is > that it's insane to do a != comparison on an 'extra'. And there are > probably other insane operations on extras, because unlike everything > else, the extra would need to be dynamically evaluated. I think it > would probably be an improvement to remove extras from the environment > marker system altogether and just have a mapping of extras instead, > ala setuptools. But that can be treated as a separate issue from the > 'None' problem.)
I wondered when someone was going to bring that up. Markerlib, currently a part of distribute as _markerlib, works by compiling each unique conditional (environment marker) to a function using the AST module. One of the arguments to the function is "extra" and the rest are the ordinary environment marker names like os and python version. (Markerlib also takes advantage of the fact that in AST/eval land variable names can have dots in them without triggering attribute access which I think is kindof cool.) Once the marker is compiled it is really fast to evaluate a few times which we do for extras (number of extras declared + 1 times). The way they are evaluated / defined is designed to limit mischief like installing different requirements if two extras are requested at once instead of installing one extra, and then later installing the other. It wouldn't make sense to write "None" in the environment marker itself. We ask you not to mention "extra" at all in that case. Once it's a function I can pass None as a parameter to guarantee it won't match anything you wrote in your marker. Long story short IMO the concrete requirements fall out more or less effortlessly. I liked flattening the per-environment and per-extras conditional requirements into a single mechanism, and I had no choice pre-JSON-metadata. Hello Nick! It could also be more like requires : [ { condition : "foo == 'gurgle'", requirements : [ "bar", "baz" ] } , { requirements : [ "quux", "splort" ] } ] for a conditional and unconditional requirement. This syntax would also avoid putting data in keys which seems to be fashionable. _______________________________________________ Distutils-SIG maillist - Distutils-SIG@python.org http://mail.python.org/mailman/listinfo/distutils-sig