Skip to content

setuptools-scm compatibility #641

New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Closed
jaustinpage opened this issue Dec 16, 2022 · 8 comments
Closed

setuptools-scm compatibility #641

jaustinpage opened this issue Dec 16, 2022 · 8 comments
Labels

Comments

@jaustinpage
Copy link

jaustinpage commented Dec 16, 2022

Description

I have had a lot of success in the past with using setuptools-scm. One nice feature is that it can be used in a way where you have a single source of truth as to what version you are on (via a tag). However, some features that setuptools-scm does not help with are having a good way to walk users through commit message writing, and having logic for how to bump from version to version based on those commit messages. When trying to run projects for large user bases and varied programming experience, the extra help goes a long way to easing pain for developers.

Possible Solution

In a perfect world, I would be able to use both tools. One possibility might work like this:
If commitizen is unable to find a current version number using its config mechanisms, and it detects that setuptools-scm is in use (maybe by checking the pyproject.toml['build-system']['requires'] for setuptools-scm?), then it falls back to using setuptools-scm's get_version() for the current version number. I would also be happy with an explicit flag or config line to specify to run in "setuptools-scm compatibility mode".

It would also be required that bump not try to save the version number to the config file when it is in this compatibility mode, but instead recompute after tagging with an additional call to setuptools-scm get_version() function to update the current version stored in the config.

I would also be happy with a way to extend the behavior of bump, perhaps something like #292 or some sort of other hooks for plugins might be useful for allowing people to extend this kind of functionality.

Additional context

potential issues:

It would be pretty easy for someone to try to write versions from both commitizen and setuptools_scm to the same files. both tools try to do this automatically in many cases, so the potential for conflict is definitely there.

Additional context

Thanks so much for taking the time to read this, and, after the discussion, i am happy to work on some pr's. I also recognize that the ethos of commitizen and setuptools_scm is a bit different from each other, but, I hope that maybe both together makes for an even better development environment.

@jaustinpage jaustinpage added the type: feature A new enhacement proposal label Dec 16, 2022
@jaustinpage
Copy link
Author

I think the "discussion" label might be good for this one...

@Lee-W
Copy link
Member

Lee-W commented Dec 29, 2022

Hi @jaustinpage sorry for late reply. I'm not that familiar with setuptools-scm. So my understanding of this feature is to use setuptools-scm to maintain the project version and use other commitzien. Is my understanding correct?

@jaustinpage
Copy link
Author

@Lee-W : your understanding is fundamentally correct.

In this mode:

Setuptools-scm would be the source of truth for what the "current version" is.

Commitizen bump would create tags for versions that follow the major.minor.patch format. It would ask steuptools-scm to determine the current version, and then use the existing logic to compute what the next version should be. Then it would tag the commit it is on with this new version. This will automatically cause setuptools-scm to be updated.

Setuptools-scm has built in mechanisms for automatically managing dev or pre-release versions.

@noirbizarre
Copy link
Member

noirbizarre commented Dec 31, 2022

I share my findings given I have dug this use case a bit.

TLDR: *-scm (setuptools-scm, pdm-scm which I use,,,) cannot be commitizen source of thrust but they are complementary, commitizen is working on sources and scm while setuptools(-scm) is working on packaging and runtime metadata) and consume scm data produced by commitizen (aka. the last tag)

While commitizen works on sources and scm itself (git more specifically), *-scm works on packaging and runtime using scm as source of thrust.
Using *-scm as commitizen source of thrust introduce a chicken and egg problem.

* -scm don't have any versionning logic, it don't know the current/previous version the only things it provides are:

  • get the current scm tag while packaging and inject it into the Core Metadata Version for tagged release (so runtime version extraction using packaging provide the tag)
  • get the current commit has and inject it as Core Metadata version if the commit does not have a tag
  • optionnaly write a the version string in the sources to be backward compatible (aka. have the version available as my_package.__version__

On the other side, commitizen need to get the previous version which *-scm can't provide and commitizen is the one tagging the last commit during bump. It also update the changelog in the bump commit.

While it is not possible to use *-scm as source of thrust, it is possible to use both commitizen and *-scm together to benefit from both:

  • use commitizen version field from config as source of thrust
  • bump using commitizen => changelog is updated and git tag is created
  • package hte tagged commit using your packager (setuptools with setuptools-scm in you case) => Core Metadata Version is taken from the current tag just set by commitizen) => Runtime version from metadata is available using either importlib.matadata or pkg_resources.

For static version at runtime (like in a my_pkh._version.py file), use:

[tool.setuptools_scm]
write_to = "my_pkg/_version.py"

and the file my_pkg/_version.py will be generated on packaging.

For intermediate (aka. not tagged) builds, *-scm set the version to the commit hash without relying on commitizen.

@jaustinpage
Copy link
Author

@noirbizarre : Why do you assert that setuptools-scm cannot be the source of truth for what the current version is? It provides a hook: https://github.com/pypa/setuptools_scm/#programmatic-usage for programmatically determining the current version. Is this not suitable as a direct replacement for checking the commitizen version field from config?

The only trick that would be required is forcing commitizen config to re-evaluate the version field using https://github.com/pypa/setuptools_scm/#programmatic-usage after performing a bump.

noirbizarre added a commit to noirbizarre/commitizen that referenced this issue Jan 1, 2023
@noirbizarre
Copy link
Member

noirbizarre commented Jan 1, 2023

I am sorry, it wasn't that clear: it is not impossible but in the current state, without #646 it seems very complex to implement while keeping the backward compatibility and not raising the complexity and introducing an hard dependency on setuptools-scm.

You are right, get_version is actually getting the last tagged version, so I think it is actually possible to have multiple approach based on #646 to handle this:

  • implement an external setuptools-scm version provider which is actually relying on setuptools-scm internally
  • implement an scm or git provider directly in Feature: version providers #646 without any extra dependencies (aka. relying on git describe as both setuptools-scm and commitizen are)

In the first one you benefit from all setuptools-scm specifities at the cost of extra dependencies and lots of error handling: because both tools don't have the some cases coverage (not strictly semver, calver support, mercurial support...) and can have contradictory settings.

I prefer the second approach because this does not introduce any extra dependencies and it is not coupled to setuptools-scm.

Given #646 is not yet accepted or reviewed, I cannot guarantee anything, but I added an scm provider to handle this case. Would it cover your use case @jaustinpage ? If not, with #646 it is totally possible to implement it in another VersionProvider.

noirbizarre added a commit to noirbizarre/commitizen that referenced this issue Jan 1, 2023
@jaustinpage
Copy link
Author

jaustinpage commented Jan 2, 2023

@noirbizarre : thank you so much for showing me #646, the VersionProvider ABC looks very promising.

I think either approach you mentioned can work well, and I'm happy to help with implementation.

noirbizarre added a commit to noirbizarre/commitizen that referenced this issue Jan 2, 2023
noirbizarre added a commit to noirbizarre/commitizen that referenced this issue Jan 2, 2023
Reads version from the repository last tag matching `tag_format`

Fixes commitizen-tools#641
@noirbizarre
Copy link
Member

I think the #646 is ready for a first review and you can test it. With commitizen installed from this branch, you should be able to define your commitizen config like this

[tool.commitizen]
# No version required
version_provider = "scm"

[tool.setuptools_scm]
# Your setuptools SCM config

noirbizarre added a commit to noirbizarre/commitizen that referenced this issue Jan 5, 2023
Reads version from the repository last tag matching `tag_format`

Fixes commitizen-tools#641
noirbizarre added a commit to noirbizarre/commitizen that referenced this issue Jan 10, 2023
Reads version from the repository last tag matching `tag_format`

Fixes commitizen-tools#641
noirbizarre added a commit to noirbizarre/commitizen that referenced this issue Jan 10, 2023
Reads version from the repository last tag matching `tag_format`

Fixes commitizen-tools#641
noirbizarre added a commit to noirbizarre/commitizen that referenced this issue Jan 10, 2023
Reads version from the repository last tag matching `tag_format`

Fixes commitizen-tools#641
noirbizarre added a commit to noirbizarre/commitizen that referenced this issue Jan 26, 2023
Reads version from the repository last tag matching `tag_format`

Fixes commitizen-tools#641
noirbizarre added a commit to noirbizarre/commitizen that referenced this issue Jan 26, 2023
Reads version from the repository last tag matching `tag_format`

Fixes commitizen-tools#641
noirbizarre added a commit to noirbizarre/commitizen that referenced this issue Jan 26, 2023
Reads version from the repository last tag matching `tag_format`

Fixes commitizen-tools#641
noirbizarre added a commit to noirbizarre/commitizen that referenced this issue Jan 26, 2023
Reads version from the repository last tag matching `tag_format`

Fixes commitizen-tools#641
noirbizarre added a commit to noirbizarre/commitizen that referenced this issue Jan 27, 2023
Reads version from the repository last tag matching `tag_format`

Fixes commitizen-tools#641
noirbizarre added a commit to noirbizarre/commitizen that referenced this issue Feb 11, 2023
Reads version from the repository last tag matching `tag_format`

Fixes commitizen-tools#641
Lee-W pushed a commit that referenced this issue Feb 12, 2023
Reads version from the repository last tag matching `tag_format`

Fixes #641
Lee-W pushed a commit that referenced this issue Mar 2, 2023
Reads version from the repository last tag matching `tag_format`

Fixes #641
@woile woile closed this as completed in 3a1af6a Apr 23, 2023
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
Projects
None yet
Development

No branches or pull requests

3 participants