Opened 9 years ago

Closed 9 years ago

#32840 closed defect (fixed)

python portgroup: strange results from python_get_version

Reported by: ryandesign (Ryan Schmidt) Owned by: macports-tickets@…
Priority: Normal Milestone:
Component: ports Version: 2.0.3
Keywords: Cc: jmroot (Joshua Root), drkp (Dan Ports)
Port: python

Description

The unified python portgroup has this code:

proc python_get_version {} {
    if {[string match py-* [option name]]} {
        return [string range [option subport] 2 3]
    } else {
        return [option python.default_version]
    }
}

This is strange and produces bizarre dependencies like this:

$ port deps py-urlwatch
Full Name: py-urlwatch @1.14_0
Library Dependencies: py-u-futures

In fact py-urlwatch declares a dependency on port:py${python.version}-futures. In the stub port, python.version is the 3rd and 4th characters of the port name (for "py-urlwatch", that's "-u"). In the non-stub ports, it takes the default version. This seems exactly backwards doesn't it? Shouldn't the condition be:

if {![string match py-* [option name]]} {

Or perhaps rather:

if {[string match py\[0-9\]\[0-9\]-* [option name]]} {

Change History (15)

comment:1 Changed 9 years ago by drkp (Dan Ports)

Cc: dports@… added

Well, the Python portgroup shouldn't do that, but at least part of the problem here is that py-urlwatch is depending on py${python.version}-futures even in the stub port. That probably ought to be in a if {$subport != $name} block. I don't think we want the stub port to depend on anything other than py${python.default_version}-urlwatch.

...and, in fact, this port is using depends_lib instead of depends_lib-append so it's overwriting the py24-urlwatch dependency, which is also broken. (Not to mention that py24-urlwatch doesn't exist, but that's #32839.)

comment:2 Changed 9 years ago by drkp (Dan Ports)

I think what we actually want is

    if {[string match py-* [option name]] &&
        [string match py\[0-9\]\[0-9\]-* [option subport]]} {
        return [string range [option subport] 2 3]
    } else {
        return [option python.default_version]
    }

which should do the right thing for py-foo stub ports, pyXX-foo subports, and apps (not name py-foo)

comment:3 Changed 9 years ago by jmroot (Joshua Root)

The code is correct. Yes, python.version is not well-defined in that case.

comment:4 in reply to:  3 Changed 9 years ago by ryandesign (Ryan Schmidt)

Replying to jmr@…:

The code is correct.

You mean the code Dan proposed above is correct, right? The code currently in the portgroup cannot be considered to be correct, in the case of stub ports.

comment:5 Changed 9 years ago by jmroot (Joshua Root)

No, I mean the current code is correct. You shouldn't be looking at python.version in a stub port.

comment:6 Changed 9 years ago by ryandesign (Ryan Schmidt)

Then we have an education problem; I think some portfile authors don't realize they need to restrict dependencies to the subports. I wrote a script to identify this and other common problems I've seen in python portgroup ports. These requirements should be mentioned in the python portgroup documentation in the guide.

comment:7 Changed 9 years ago by jmroot (Joshua Root)

Resolution: invalid
Status: newclosed

Sure, but it also only takes running 'port info' to see that something's wrong.

comment:8 Changed 9 years ago by ryandesign (Ryan Schmidt)

Not all issues that my script tests for are visible by looking at "port info", nor does "port info" tell you how to fix them.

comment:9 Changed 9 years ago by jmroot (Joshua Root)

Other issues that your script may happen to check for are not what this ticket is about.

comment:10 Changed 9 years ago by ryandesign (Ryan Schmidt)

Right, this ticket is about the bizarre way in which the python portgroup mangles the dependencies when portfile authors do not follow these (to them possibly unknown) requirements, a behavior for which Dan has already provided a fix above, and which I do not understand your reluctance to incorporate.

comment:11 Changed 9 years ago by jmroot (Joshua Root)

The portgroup doesn't mangle the dependency, the author uses a variable with no well-defined value when they write the dependency. Asking which version of python is in use when python is not used at all isn't even a sensible question. There is no sensible answer. Arbitrarily defining the answer to be something that looks less obviously wrong doesn't change that.

comment:12 Changed 9 years ago by ryandesign (Ryan Schmidt)

Then how about explaining to the portfile author what they've done wrong?

--- python-1.0.tcl	(revision 88867)
+++ python-1.0.tcl	(working copy)
@@ -65,6 +65,10 @@
 
 proc python_get_version {} {
     if {[string match py-* [option name]]} {
+        if {[option name] == [option subport]} {
+            ui_error "do not access python_get_version in a stub port"
+            return -code error "incorrect use of python_get_version"
+        }
         return [string range [option subport] 2 3]
     } else {
         return [option python.default_version]

comment:13 Changed 9 years ago by ryandesign (Ryan Schmidt)

Thank you for fixing this in r88869. I don't mean to be argumentative, I just think when we have the opportunity to educate port maintainers about mistakes they're making, that's better than letting them make the mistake and then have to file tickets about it later.

Unfortunately r88869 breaks all stub ports that do not declare "python.link_binaries no"; for example:

$ sudo port -s install py-numeric
--->  Computing dependencies for py-numeric
--->  Fetching py-numeric
--->  Verifying checksum(s) for py-numeric
--->  Extracting py-numeric
--->  Configuring py-numeric
--->  Building py-numeric
--->  Staging py-numeric into destroot
Error: Target org.macports.destroot returned: can't read "python.link_binaries": can't read "python.version": no such variable
Log for py-numeric is at: /opt/local/var/macports/logs/_Users_rschmidt_macports_dports_python_py-numeric/py-numeric/main.log
Error: Status 1 encountered during processing.
To report a bug, see <http://guide.macports.org/#project.tickets>

comment:14 in reply to:  description ; Changed 9 years ago by macports-trac@…

Resolution: invalid
Status: closedreopened

This is a new behavior, probably brought about by the change

# $Id: python-1.0.tcl 88880 2012-01-14 09:20:05Z jmr@… $

that invalidates some previously-sort-of-working portfiles.

It causes "port info all" to abort if not called as "port -p info all". It is reasonable to expect "port info all" to work at all times.

This problem affects the following ports in the same way ("Error: Unable to open port: can't read "python.version": no such variable"):

< py-bpython < py-docx < py-htmldocs < py-nose < py-transaction < py-urlwatch

There is also an anomaly with the way py-apsw is treated: its python-version variants show up in the results for "port info" but not for "port list".

Would it be possible to roll back the change to the group file until affected ports and the python-1.0 group file have been brought into harmony? This would seem to be a faster route to fixing the breakage than waiting on maintenance of six or seven portfiles.

comment:15 in reply to:  14 Changed 9 years ago by drkp (Dan Ports)

Resolution: fixed
Status: reopenedclosed

Replying to macports-trac@…:

Would it be possible to roll back the change to the group file until affected ports and the python-1.0 group file have been brought into harmony? This would seem to be a faster route to fixing the breakage than waiting on maintenance of six or seven portfiles.

Might as well just fix the ports...

  • py-bpython fixed in r88898
  • py-htmldocs fixed in r88899
  • py-nose fixed in r88900
  • py-transaction fixed in r88901
  • py-urlwatch fixed in r88902
  • py-docx looks like it was already fixed in r88895
Note: See TracTickets for help on using tickets.