[Git] How do I remove a submodule?


Answers

Via the page Git Submodule Tutorial:

To remove a submodule you need to:

  1. Delete the relevant section from the .gitmodules file.
  2. Stage the .gitmodules changes git add .gitmodules
  3. Delete the relevant section from .git/config.
  4. Run git rm --cached path_to_submodule (no trailing slash).
  5. Run rm -rf .git/modules/path_to_submodule
  6. Commit git commit -m "Removed submodule <name>"
  7. Delete the now untracked submodule files
    rm -rf path_to_submodule

See also: alternative steps below.

Question

How do I remove a Git submodule?

By the way, is there a reason I can't simply do

git submodule rm whatever

?




In addition to the recommendations, I also had to rm -Rf .git/modules/path/to/submodule to be able to add a new submodule with the same name (in my case I was replacing a fork with the original)




Here are the 4 steps that I found necessary or useful (important ones first):

git rm -f the_submodule
rm -rf .git/modules/the_submodule
git config -f .git/config --remove-section submodule.the_submodule
git commit -m "..."

In theory, git rm in step 1 should take care of it. Hopefully, the second part of OP question can be answered positively one day (that this can be done in one command).

But as of July 2017, step 2 is necessary to remove data in .git/modules/ for otherwise, you can't e.g. add the submodule back in the future.

You can probably get away with the above two steps for git 1.8.5+ as tinlyx's answer noted, as all git submodule commands seem to work.

Step 3 removes the section for the_submodule in the file .git/config. This should be done for completeness. (The entry may cause problems for older git versions, but I don't have one to test).

For this, most answers suggest using git submodule deinit. I find it more explicit and less confusing to use git config -f .git/config --remove-section. According to the git-submodule documentation, git deinit:

Unregister the given submodules ... If you really want to remove a submodule from the repository and commit that use git-rm[1] instead.

Last but not least, if you don't git commit, you will/may get an error when doing git submodule summary (as of git 2.7):

fatal: Not a git repository: 'the_submodule/.git'
* the_submodule 73f0d1d...0000000:

This is regardless of whether you do steps 2 or 3.




I found deinit works good for me:

git submodule deinit <submodule-name>    
git rm <submodule-name>

From git docs:

deinit

Unregister the given submodules, i.e. remove the whole submodule.$name section from .git/config together with their work tree.




To summarize, this is what you should do :

  1. Set path_to_submodule var (no trailing slash):

    path_to_submodule=path/to/submodule

  2. Delete the relevant line from the .gitmodules file:

    git config -f .gitmodules --remove-section submodule.$path_to_submodule

  3. Delete the relevant section from .git/config

    git config -f .git/config --remove-section submodule.$path_to_submodule

  4. Unstage and remove $path_to_submodule only from the index (to prevent losing information)

    git rm --cached $path_to_submodule

  5. Track changes made to .gitmodules

    git add .gitmodules

  6. Commit the superproject

    git commit -m "Remove submodule submodule_name"

  7. Delete the now untracked submodule files

    rm -rf $path_to_submodule

    rm -rf .git/modules/$path_to_submodule




I recently find out a git project which include many useful git related command: https://github.com/visionmedia/git-extras

Install it and type :

git-delete-submodule submodule

Then things are done. The submodule directory will be removed from your repo and still exist in your filesystem. You can then commit the change like: git commit -am "Remove the submodule".




After experimenting with all the different answers on this site, I ended up with this solution:

#!/bin/sh
path="$1"
if [ ! -f "$path/.git" ]; then
  echo "$path is no valid git submodule"
  exit 1
fi
git submodule deinit -f $path &&
git rm --cached $path &&
rm -rf .git/modules/$path &&
rm -rf $path &&
git reset HEAD .gitmodules &&
git config -f .gitmodules --remove-section submodule.$path

This restores the exact same state as before you added the submodule. You can right away add the submodule again, which was not possible with most of the answers here.

git submodule add $giturl test
aboveScript test

This leaves you with a clean checkout with no changes to commit.

This was tested with:

$ git --version
git version 1.9.3 (Apple Git-50)



To remove a submodule added using:

git submodule add blah@blah.com:repos/blah.git lib/blah

Run:

git rm lib/blah

That's it.

For old versions of git (circa ~1.8.5) use:

git submodule deinit lib/blah
git rm lib/blah
git config -f .gitmodules --remove-section submodule.lib/blah



The majority of answers to this question are outdated, incomplete, or unnecessarily complex.

A submodule cloned using git 1.7.8 or newer will leave at most four traces of itself in your local repo. The process for removing those four traces is given by the three commands below:

# Remove the submodule entry from .git/config
git submodule deinit -f path/to/submodule

# Remove the submodule directory from the superproject's .git/modules directory
rm -rf .git/modules/path/to/submodule

# Remove the entry in .gitmodules and remove the submodule directory located at path/to/submodule
git rm -f path/to/submodule



project dir:     ~/foo_project/
submodule:       ~/foo_project/lib/asubmodule
- - - - - - - - - - - - - - - - - - - - - - - - -
run:
  1.   cd ~/foo_project
  2.   git rm lib/asubmodule && 
          rm .git/modules/lib/asubmodule && 
            git submodule lib/asubmodule deinit --recursive --force





Links