You signed in with another tab or window. Reload to refresh your session.You signed out in another tab or window. Reload to refresh your session.You switched accounts on another tab or window. Reload to refresh your session.Dismiss alert
{{ message }}
Repository navigation
uv.lock is out of sync after running a release #1125
How can I keep my uv.lock file in sync with my other files like pyproject.toml?
I reviewed #1097 but my situation is different in two important ways:
I'm not building using psr; I have my own custom logic for that which is handled after the release is cut.
We use the GitHub Action and my uv uses private indexes so I would need to find a way to pass numerous secrets / specially formatted env vars into the runtime using the prior approach.
Suggestion
When I update my uv.lock, the change looks something like this:
[[package]]
name = "example"
-version = "0.7.0"+version = "0.10.0"
There's no need for any other complex locking behavior (hash pinning, etc.).
It seems like we could be able to specify this version update with a version_toml configuration or similar. However the problem is that we need to match on the [[package]] where name = "example" and then update the corresponding version field. I considered version_variables for this, which shows the potential to work but feels a bit hacky.
I reviewed #1097 but my situation is different in two important ways:
I'm not building using psr; I have my own custom logic for that which is handled after the release is cut.
We use the GitHub Action and my uv uses private indexes so I would need to find a way to pass numerous secrets / specially formatted env vars into the runtime using the prior approach.
The GitHub Action is only a convenience wrapper. It is not designed to fit all use cases. If it is the case where the GitHub Action is not convenient then just install PSR as a Python package into your CI environment and call it directly from the shell. If you decide to use the build command then we provide build_command_env as a specification of the env variable names you want preserved into the build command shell environment.
Since you are not wanting to use the PSR build command, I would just run your uv lock as a separate step. In this case you would probably need to run the following:
# PSR stamps version into files (nothing else)# don't build the changelog (especially in update mode)
semantic-release -v version --skip-build --no-commit --no-tag --no-changelog
# run UV lock as pyproject.toml is updated with the next version
uv lock
# stage the lock file to ensure it is included in the PSR commit
git add uv.lock
# you may need to reset your working directory here# if anything weird happens as PSR stamps for the 2nd time# git checkout .# run PSR fully to create release
semantic-release -v version --skip-build
It seems like we could be able to specify this version update with a version_toml configuration or similar. However the problem is that we need to match on the [[package]] where name = "example" and then update the corresponding version field. I considered version_variables for this, which shows the potential to work but feels a bit hacky.
We don't have an advanced toml parser to consider multiple keys to point to the correct value. Maybe we could if we had a clear way of defining it in the configuration but I don't know how that would work best.
version_variables is only a complex Regular Expression replace and likely will have undesirable effects on your uv.lock file as there are multiple version = specifications which will all be replaced regardless of which package it is related to.
Neither of these current implementations will work for your use case. The best recommendation I have is the double PSR call above.
Makes sense. I will move off the GitHub action for now. Thanks for the quick reply @codejedi365
As far as a more complex solution I may be willing to contribute something if we can agree on a design that makes sense. My first thought was some sort of per line predicate for the toml config? We could make it optional and invoked with a second : perhaps? Not sure exactly what it would look like and if you'd even be open to that. Or if people may already have a second : in those lines which would make it require a different approach
Regarding the regex my thought was to handle multiple lines to cover that issue about hitting other versions. I do still believe it'd be fragile and not sure if multiline would work; I only briefly looked at the implementation
@JonZeolla, wow that's great! Glad it all worked out well, thanks for replying!
I will think on the solutions for a while. Thanks for putting some thought to it. I did have plans to bring back some functionality for custom regex but I agree most are fragile for a lock file. If we move to a plugin model at some point in the distant future, I could foresee a plugin that specially handled a complex toml file or just uv.lock in general. Just at this time I cant see adding it to the baseline especially when uv is below 1.0.0.
With the two executions of PSR, each one could be the action as the cli parameters are all available via yaml with: values. I was probably a bit too harsh about its flexibility for your problem set and didn't require the switch. The downside I was thinking of is that uv is not installed in the container so adding the uv lock command in the build command requires install, all for the fact you weren't using a build command. But none of that really mattered in your case. You just needed it to stop at the stamp action before completing the release.
With that said, eventually #692 will be completed and we will move to a composite action which would eliminate the container build time (and restricted Python version) on GitHub Actions we impose right now. You would still have to do the two executions and uv lock in between but at least it would run faster. Future plan is to also add some caching of parsed commits so that the second execution is much faster when you have large commit histories.
@codejedi365 It looks like this flow broke in 8906d8e; if I do a --no-commit run first, then a --commit run, it won't commit the prior changes (as defined by the version_variables and version_toml) unless I intentionally stage them myself. Is that the new expected flow?
My guess is that it's this and this. Since we stage the changes before running the --commit, the new_content is the same as self.content (in the working tree), so it returns None.
Then, that doesn't add the file path to pathshere, which means it is not added to files_with_new_version_written here:
Yes and no. Yes, it was intentional to better detect if we actually made changes to files before staging them. Separately, I did not think about the consequence to your workflow that was expecting to apply versions again to specific files. So no, it was not intentional to cause this workflow to require a separate git add step. I opened #1211 to document this issue since it doesn't actually have anything to do with the uv.lock file.
Activity
codejedi365 commentedon Dec 16, 2024
The GitHub Action is only a convenience wrapper. It is not designed to fit all use cases. If it is the case where the GitHub Action is not convenient then just install PSR as a Python package into your CI environment and call it directly from the shell. If you decide to use the build command then we provide
build_command_envas a specification of the env variable names you want preserved into the build command shell environment.Since you are not wanting to use the PSR build command, I would just run your
uv lockas a separate step. In this case you would probably need to run the following:We don't have an advanced toml parser to consider multiple keys to point to the correct value. Maybe we could if we had a clear way of defining it in the configuration but I don't know how that would work best.
version_variablesis only a complex Regular Expression replace and likely will have undesirable effects on youruv.lockfile as there are multipleversion =specifications which will all be replaced regardless of which package it is related to.Neither of these current implementations will work for your use case. The best recommendation I have is the double PSR call above.
JonZeolla commentedon Dec 16, 2024
Makes sense. I will move off the GitHub action for now. Thanks for the quick reply @codejedi365
As far as a more complex solution I may be willing to contribute something if we can agree on a design that makes sense. My first thought was some sort of per line predicate for the toml config? We could make it optional and invoked with a second : perhaps? Not sure exactly what it would look like and if you'd even be open to that. Or if people may already have a second : in those lines which would make it require a different approach
JonZeolla commentedon Dec 16, 2024
Regarding the regex my thought was to handle multiple lines to cover that issue about hitting other versions. I do still believe it'd be fragile and not sure if multiline would work; I only briefly looked at the implementation
JonZeolla commentedon Dec 16, 2024
@codejedi365 thanks; I confirmed this all works e2e. Closing this for now; you're welcome to reopen if you want to pursue the enhancement
codejedi365 commentedon Dec 17, 2024
@JonZeolla, wow that's great! Glad it all worked out well, thanks for replying!
I will think on the solutions for a while. Thanks for putting some thought to it. I did have plans to bring back some functionality for custom regex but I agree most are fragile for a lock file. If we move to a plugin model at some point in the distant future, I could foresee a plugin that specially handled a complex toml file or just
uv.lockin general. Just at this time I cant see adding it to the baseline especially when uv is below 1.0.0.codejedi365 commentedon Dec 17, 2024
With the two executions of PSR, each one could be the action as the cli parameters are all available via yaml
with:values. I was probably a bit too harsh about its flexibility for your problem set and didn't require the switch. The downside I was thinking of is that uv is not installed in the container so adding the uv lock command in the build command requires install, all for the fact you weren't using a build command. But none of that really mattered in your case. You just needed it to stop at the stamp action before completing the release.With that said, eventually #692 will be completed and we will move to a composite action which would eliminate the container build time (and restricted Python version) on GitHub Actions we impose right now. You would still have to do the two executions and
uv lockin between but at least it would run faster. Future plan is to also add some caching of parsed commits so that the second execution is much faster when you have large commit histories.JonZeolla commentedon Mar 11, 2025
@codejedi365 It looks like this flow broke in 8906d8e; if I do a
--no-commitrun first, then a--commitrun, it won't commit the prior changes (as defined by theversion_variablesandversion_toml) unless I intentionally stage them myself. Is that the new expected flow?JonZeolla commentedon Mar 11, 2025
My guess is that it's this and this. Since we stage the changes before running the
--commit, thenew_contentis the same asself.content(in the working tree), so it returnsNone.Then, that doesn't add the file path to
pathshere, which means it is not added tofiles_with_new_version_writtenhere:python-semantic-release/src/semantic_release/cli/commands/version.py
Lines 617 to 623 in 5093f30
And then finally, it isn't staged and commit here:
python-semantic-release/src/semantic_release/cli/commands/version.py
Lines 654 to 668 in 5093f30
codejedi365 commentedon Mar 12, 2025
Yes and no. Yes, it was intentional to better detect if we actually made changes to files before staging them. Separately, I did not think about the consequence to your workflow that was expecting to apply versions again to specific files. So no, it was not intentional to cause this workflow to require a separate
git addstep. I opened #1211 to document this issue since it doesn't actually have anything to do with theuv.lockfile.