Skip to content

git-lfs-migrate import doesn't work when .git/objects is a symlink #6030

@andrewbraxton

Description

@andrewbraxton

Describe the bug
Running git lfs migrate import errors when .git/objects is a symlink.

To Reproduce
Steps to reproduce the behavior:

# create a sandbox repo
mkdir -p sandbox/repo
cd sandbox/repo
git init --initial-branch=main

# make a commit
echo abc >> foo
git add .
git commit -m 'initial'

# copy objects folder to sandbox/ and symlink to it inside .git/
cp -r .git/objects ..
rm -rf .git/objects
ln -s ../../objects .git/objects

# try to migrate, observe error
git lfs migrate import --everything
Error in `git rev-list --reverse --topo-order --do-walk --stdin --`: exit status 128 fatal: not a git repository (or any parent up to mount point /)
Stopping at filesystem boundary (GIT_DISCOVERY_ACROSS_FILESYSTEM not set).

System environment
Fedora 40

Additional context
The reason that this error occurs is clear: git-rev-list is executed from inside the objects/ directory, but this doesn't work if objects/ is not in .git/:

if len(opt.WorkingDir) > 0 {
cmd.Dir = opt.WorkingDir
}

However, even if you remove this conditional such that rev-list is executed inside the cwd and thus succeeds, git lfs migrate import still doesn't work. No history is rewritten; it appears to be a no-op. You can observe this by doing the following, after hacking out the conditional logic to fix the rev-list error:

rm -rf .git/objects
cp -r ../objects .git/
git lfs migrate import --everything

git reset --hard HEAD@{1}
rm -rf .git/objects
ln -s ../../objects .git/
git lfs migrate import --everything

The outputs will look something like

Sorting commits: ..., done.
Rewriting commits: 100% (1/1), done.
  main  da0d9adcb169cc66ebd8f2d82d3c39a80495295d -> da62d0d420c23399dfaadc9ff63687c9926fb59f
Updating refs: ..., done.
Checkout: ..., done.

Sorting commits: ..., done.
Rewriting commits: 100% (1/1), done.
Updating refs: ..., done.
Checkout: ..., done.

The first case (no symlink), the history is rewritten. The second case (with symlink), nothing happens.

If you're wondering what the reason could be for having .git/objects/ symlinked, it's because that's how Google's git-repo tool sets up the working directories for an AOSP checkout. LFS users working on AOSP projects don't have much choice in this matter.

Metadata

Metadata

Assignees

No one assigned

    Labels

    Type

    No type

    Projects

    No projects

    Milestone

    No milestone

    Relationships

    None yet

    Development

    No branches or pull requests

    Issue actions