{"action":"created","issue":{"url":"https://api.github.com/repos/warner/python-versioneer/issues/79","labels_url":"https://api.github.com/repos/warner/python-versioneer/issues/79/labels{/name}","comments_url":"https://api.github.com/repos/warner/python-versioneer/issues/79/comments","events_url":"https://api.github.com/repos/warner/python-versioneer/issues/79/events","html_url":"https://github.com/warner/python-versioneer/issues/79","id":85102284,"number":79,"title":"Git tags - support for multiple versions on same commit","user":{"login":"andrewmichaelsmith","id":686224,"avatar_url":"https://avatars.githubusercontent.com/u/686224?v=3","gravatar_id":"","url":"https://api.github.com/users/andrewmichaelsmith","html_url":"https://github.com/andrewmichaelsmith","followers_url":"https://api.github.com/users/andrewmichaelsmith/followers","following_url":"https://api.github.com/users/andrewmichaelsmith/following{/other_user}","gists_url":"https://api.github.com/users/andrewmichaelsmith/gists{/gist_id}","starred_url":"https://api.github.com/users/andrewmichaelsmith/starred{/owner}{/repo}","subscriptions_url":"https://api.github.com/users/andrewmichaelsmith/subscriptions","organizations_url":"https://api.github.com/users/andrewmichaelsmith/orgs","repos_url":"https://api.github.com/users/andrewmichaelsmith/repos","events_url":"https://api.github.com/users/andrewmichaelsmith/events{/privacy}","received_events_url":"https://api.github.com/users/andrewmichaelsmith/received_events","type":"User","site_admin":false},"labels":[],"state":"open","locked":false,"assignee":null,"milestone":null,"comments":1,"created_at":"2015-06-04T13:36:08Z","updated_at":"2015-06-08T08:55:17Z","closed_at":null,"body":"I think that the current mechanism for getting tags (improved in #77) doesn't pick the biggest version if you tag the same commit multiple times for the same application but for different versions.\r\n\r\nBasically when I bump a version number for my application without doing a commit (not that common but does happen if we update a package's dependencies) the older tag is getting picked up.\r\n\r\nProbably easiest to illustrate just using git and the current \"git describe\" command:\r\n \r\n```\r\n# git init .\r\nInitialised empty Git repository in /tmp/x/.git/\r\n# touch x && git add x && git commit -m \"test\"\r\n[master (root-commit) 217feb2] test\r\n 1 file changed, 0 insertions(+), 0 deletions(-)\r\n create mode 100644 x\r\n# git tag R_example_1.0.0\r\n# git tag R_example_1.0.1\r\n# git describe --tags --dirty --always --long --match \"R_example*\"\r\nR_example_1.0.0-0-g217feb2\r\n```\r\n\r\nHere 1.0.0 is getting taken over 1.0.1, clearly I'd like to have 1.0.1 taken over it.\r\n\r\nFrom [initial googling](http://stackoverflow.com/questions/4545370/how-to-list-all-tags-pointing-to-a-specific-commit-in-git) there seems to be a way to get the current tags for a commit. I suppose you could take these all in, [parse them](https://pythonhosted.org/setuptools/pkg_resources.html#parsing-utilities) and pick the biggest? But I guess this doesn't give you the nice things that describe does (like dirty and commits ahead)."},"comment":{"url":"https://api.github.com/repos/warner/python-versioneer/issues/comments/109916938","html_url":"https://github.com/warner/python-versioneer/issues/79#issuecomment-109916938","issue_url":"https://api.github.com/repos/warner/python-versioneer/issues/79","id":109916938,"user":{"login":"warner","id":27146,"avatar_url":"https://avatars.githubusercontent.com/u/27146?v=3","gravatar_id":"","url":"https://api.github.com/users/warner","html_url":"https://github.com/warner","followers_url":"https://api.github.com/users/warner/followers","following_url":"https://api.github.com/users/warner/following{/other_user}","gists_url":"https://api.github.com/users/warner/gists{/gist_id}","starred_url":"https://api.github.com/users/warner/starred{/owner}{/repo}","subscriptions_url":"https://api.github.com/users/warner/subscriptions","organizations_url":"https://api.github.com/users/warner/orgs","repos_url":"https://api.github.com/users/warner/repos","events_url":"https://api.github.com/users/warner/events{/privacy}","received_events_url":"https://api.github.com/users/warner/received_events","type":"User","site_admin":false},"created_at":"2015-06-08T08:55:17Z","updated_at":"2015-06-08T08:55:17Z","body":"Hm, one other (perhaps more common) way this might happen is if a release candidate gets promoted to the final release without additional changes, so you'd have \"v1.0rc1\" and \"v1.0\" tags on the same commit. (This is probably the ideal outcome in any process that involves \"release candidates\": making no changes between your last candidate and the final release). In that case, however, the more-final less-candidate-ish tag is shorter, so \"shortest tag wins\" still works.\r\n\r\nHow do you update the package dependencies without changing the source code at all? I guess the dependencies are being tracked externally somehow?\r\n\r\nI'm thinking we could include a list of all tags in the `get_versions()` dictionary output. The Versioneer code could have some built-in sorting function to decide which one makes it into the pre-rendered version string, but project-specific logic could look at the full tag set and do its own sort to decide which one to use. Yeah, like you said, not so easy to integrate with the other version information like \"distance\". I guess the consequence would be that revisions after a multiply-tagged commit would have non-ideal version strings, maybe `1.0.0+4.gHASH` where it should have been `1.0.1+4.gHASH`.\r\n\r\nThe built-in sort would ideally use the PEP440 version-sort logic (so it'd pick 1.0.1 over 1.0.0), but I don't want to have to import an external library to do the sort, so I'm not sure of the best way to bring that code into versioneer.py .\r\n\r\nMaybe it'd be good enough to:\r\n\r\n1. find all tags with the given prefix, strip the prefix\r\n2. find the length of the shortest tag, discard all tags longer than this\r\n3. sort the remaining (short) tags lexicographically, pick the \"largest\"\r\n\r\nThat'd choose 1.0.1 over 1.0.0, but also 1.2.13 over 1.10.2 . We could assume dotted-decimal and `sort(key=lambda tag: tuple([int(c) for c in tag.split(\".\")]))`, which I think is what Debian does, but it feels kinda dicey to make that assumption (I'd probably write it to only attempt that if all the tags matched a `[\\d\\.]` regex, and fall back to straight string-sort otherwise)."}}