My build script generates a version number from git tag, hash, and branch. This works splendidly, except when using cargo install --git.
My command is: cargo install --git https://example.com/repo.git --branch xyz
First I thought that cargo creates a shallow clone, but that's not it. However, the clone does not have any tags and what is even more puzzling is that the branch name is master. So, cargo install fetched the correct branch but renamed it to master and did not fetch any tags either.
Is there any way to tell cargo to retrieve all tags and not to rename the branch to master?
P.S.: I've read the cargo docs and did some research, but to no avail.
e.g. when doing a git clone -b xyz https://example.com/repo.git all the info is there, so what is cargo doing?
I have no idea what you are actually looking for, but you might be confused by the way cargo separates the git database and individual checkouts.
In short, the entire database is downloaded so cargo already has all of the tags and branches.
Each checkout is simply a local filesystem clone. And the original database's refs are not updated to indicate where the checkouts came from (i.e. the ./refs/heads and ./refs/tags directories are empty because they are not used nor needed for any purpose). It isn't supposed to simulate how a human operates git.
A couple of resources for you to investigate further:
FWIW, there are known issues with shallow clones (they are not supported by libgit2 or gitoxide). You can configure cargo to use the git cli though, if you need to: Configuration - The Cargo Book
Maybe I was not clear enough. A cargo install --git https://example.com/repo.git --branch xyz creates a somewhat messed-up git directory in .cargo/git/checkouts/. e.g. repo-7f25bc5356a562d5. (I call it messed-up because part of the info is missing (tags) and incorrect (branch).)
The binary is then compiled from within this directory. However, in this directory there are no tags from the https://example.com/repo.git repository, nor is the branch name correct.
This is why my build.rs cannot determine a tag nor the correct branch.
So how is cargo retrieving the repo from https://example.com/repo.git when invoked via cargo install --git https://example.com/repo.git --branch xyz.
In the repo-7f25bc5356a562d5 dir, the following happens:
$ git describe --abbrev=0 --tags
fatal: No names found, cannot describe anything.
$ git rev-parse --abbrev-ref HEAD
master
However, it should show the following (which is also shown when I run these commands in the directory cloned with git clone -b xyz https://example.com/repo.git)
If that code does not support your specific workflow, you might have better luck using the git cli. I also provided a link for info about how to configure it.
Thanks for the links, but they don't really help. I can't go through cargo's source code to find out why the tags and the branch info are missing (I would have to research the internals of git2 and go through more than just the one file in cargo that calls git2).
Unfortunately git-cli doesn't help either. I tried it. The directory into which the source code from https://example.com/repo.git is retrieved, still does not show any tags, and the branch name is always master. (even though I use --branch xyz)
Are you sure you understand what the issue is I am describing?
Now, if you go to ~/.cargo/git/checkouts/uts2ts-43f1439a65277dfc/f471df3:
$ cd ~/.cargo/git/checkouts/uts2ts-43f1439a65277dfc/f471df3
$ git describe --abbrev=0 --tags
fatal: No names found, cannot describe anything.
$ git rev-parse --abbrev-ref HEAD
master
As you can see there are no tags and instead of xyz the branch is shown as master.
Here are my questions:
is this a bug in cargo?
if not, how can I get branch xyz and tag v0.4.1
If this is not possible, then it is also impossible to use a build.rs script that generates correct information about the git repo, when using cargo install --git ....
In such a case I might open a feature request in the cargo repo.
No. Because I do not have a build script that requires it is built within a git repo.
And even if I did, I doubt I would expect cargo to fulfill that requirement. I would expect such a build script to completely break when installing the package from crates.io or another package registry. Cargo's support for git is not intended to be a replacement for git. (It's more of a compromise for when you don't want to publish.)
I would recommend using git commands in your CI if your build script depends on specific git details. Do the specific clone you intend, and build with cargo install --path ./path/to/package
Hmm, it works perfectly fine, when I run a cargo build in a manually cloned git repo. Which is basically the same as your suggestion to use --path. So I should be able to expect that my build script and process isn't rendered null and void, just because I am using --git (especially since cargo is using git and does not download a tarball where git info is missing).
My point is that there is IMO no good reason why tags are not fetched, nor why the branch is renamed by cargo. Or at least I don't see it, which is why I opened this topic. And I hoped I missed a hidden flag --just-work-already or --retain-tags-and-branch
I'm using install --git for projects that have a somewhat non-existent release policy, where the last release is like a year old, but a myriad of commits (with fixes and features) happened since then.
You are correct, I could use workarounds, but wouldn't it be great, if cargo just retained tags and branch info?