76

The git documentation doesn't make it at all clear what the difference is between a git submodule update and a git submodule sync is. I'm also not finding any help out on the web. Can someone help me out with what the difference is here?

   update
       Update the registered submodules to match what the superproject expects
       by cloning missing submodules and updating the working tree of the
       submodules. The "updating" can be done in several ways depending on
       command line options and the value of submodule.<name>.update
       configuration variable.

-

   sync
       Synchronizes submodules' remote URL configuration setting to the value
       specified in .gitmodules. It will only affect those submodules which
       already have a URL entry in .git/config (that is the case when they are
       initialized or freshly added). This is useful when submodule URLs
       change upstream and you need to update your local repositories
       accordingly.

For reference, I'm using the git client version 2.11.0

Benjamin Leinweber
  • 2,774
  • 1
  • 24
  • 41

2 Answers2

70

update is basically doing git pull in each submodule (except without a branch, since the main repo specifies a commit directly).

The tricky one is sync. Imagine you clone a project with submodules, then later the upstream project changes one of the submodules to point to a different URL.

Your local copy of the submodule will still point to the old URL, since git never allows remote repositories to force a change to local configuration. You need to run git submodule sync to apply the remote repo's configuration to your local submodule repos.

Note also that, if you are making changes to the submodules, you might want the URLs to mismatch even if the upstream never changed them ... but using multiple remote URLs is probably a better idea for that case.

Jarsen
  • 7,432
  • 6
  • 27
  • 26
o11c
  • 15,265
  • 4
  • 50
  • 75
  • 1
    I'm not sure I understand your URL mismatch comment. Can you elaborate on that? – Benjamin Leinweber Aug 14 '17 at 17:48
  • 4
    You might not have *permission* to push directly to the repo that's being used as a submodule. So you push to your fork, then make a PR to the main submodule repo. – o11c Aug 14 '17 at 18:46
  • A note for those searching on how to push: If you do have permission to push to the remote repository, you don't use a git submodule command, but can enter the submodule directory and use a normal git commands from there. – ryanwebjackson Dec 15 '22 at 16:11
64

git submodule update updates the contents of the submodules. It is effectively running a "git fetch" and "git checkout" in each of your submodules.

git submodule sync updates the metadata about a submodule to reflect changes in the submodule URL. It re-synchronizes the information in .git/config with the information in .gitmodules.

larsks
  • 277,717
  • 41
  • 399
  • 399
  • 2
    Hmm, this is interesting. Does `git submodule init` imply a `git submodule sync` as well? I've been using a remote repo with multiple submodules and doing `git submodule init; git submodule update` after a `git pull` and have never gotten out of sync. – Benjamin Leinweber Aug 14 '17 at 17:34
  • I don't know, but it seems like that would be a relatively easy test. – larsks Aug 14 '17 at 17:56
  • 3
    @BenjaminLeinweber Off topic, but maybe use `&&` instead of `;` to separate your commands. This way, the following command will not execute if the first one failed. – ahogen Jul 31 '19 at 17:01
  • 1
    @BenjaminLeinweber, You only need to do a ```git submodule update``` everytime you do a ```git pull``` on your main repository, unless you're setting up the git submodule for the first time on a newly cloned main repo. – Sam Apr 15 '20 at 05:07