Skip to content

Commit

Permalink
Merge pull request #195 from adracus/fix.relative-submodules
Browse files Browse the repository at this point in the history
Fix relative submodule resolution
  • Loading branch information
mcuadros committed Oct 30, 2020
2 parents 15aedd2 + 81d429b commit e9c56de
Show file tree
Hide file tree
Showing 3 changed files with 42 additions and 27 deletions.
24 changes: 23 additions & 1 deletion submodule.go
Expand Up @@ -5,6 +5,8 @@ import (
"context"
"errors"
"fmt"
"net/url"
"path"

"github.com/go-git/go-billy/v5"
"github.com/go-git/go-git/v5/config"
Expand Down Expand Up @@ -131,9 +133,29 @@ func (s *Submodule) Repository() (*Repository, error) {
return nil, err
}

moduleURL, err := url.Parse(s.c.URL)
if err != nil {
return nil, err
}

if !path.IsAbs(moduleURL.Path) {
remotes, err := s.w.r.Remotes()
if err != nil {
return nil, err
}

rootURL, err := url.Parse(remotes[0].c.URLs[0])
if err != nil {
return nil, err
}

rootURL.Path = path.Join(rootURL.Path, moduleURL.Path)
*moduleURL = *rootURL
}

_, err = r.CreateRemote(&config.RemoteConfig{
Name: DefaultRemoteName,
URLs: []string{s.c.URL},
URLs: []string{moduleURL.String()},
})

return r, err
Expand Down
22 changes: 0 additions & 22 deletions worktree.go
Expand Up @@ -720,31 +720,9 @@ func (w *Worktree) readGitmodulesFile() (*config.Modules, error) {
return m, err
}

w.resolveRelativeSubmodulePaths(m)

return m, nil
}


// resolveRelativeSubmodulePaths is to replace any relative submodule URL (../foobar.git) in .gitmodules
// to the accessible repository URL
func (w *Worktree) resolveRelativeSubmodulePaths(m *config.Modules) {
origin, err := w.r.Remotes()
// remote is not associated with this worktree. we don't need to process any futher more
if err != nil {
return
}

parentURL := filepath.Dir(origin[0].c.URLs[0])

for i := range m.Submodules {
if strings.HasPrefix(m.Submodules[i].URL, "../") {
child := strings.Replace(m.Submodules[i].URL, "../", "", 1)
m.Submodules[i].URL = fmt.Sprintf("%s/%s", parentURL, child)
}
}
}

// Clean the worktree by removing untracked files.
// An empty dir could be removed - this is what `git clean -f -d .` does.
func (w *Worktree) Clean(opts *CleanOptions) error {
Expand Down
23 changes: 19 additions & 4 deletions worktree_test.go
Expand Up @@ -520,7 +520,6 @@ func (s *WorktreeSuite) TestCheckoutSubmoduleInitialized(c *C) {
c.Assert(status.IsClean(), Equals, true)
}


func (s *WorktreeSuite) TestCheckoutRelativePathSubmoduleInitialized(c *C) {
url := "https://github.com/git-fixtures/submodule.git"
r := s.NewRepository(fixtures.ByURL(url).One())
Expand All @@ -547,13 +546,29 @@ func (s *WorktreeSuite) TestCheckoutRelativePathSubmoduleInitialized(c *C) {
// test submodule path
modules, err := w.readGitmodulesFile()

c.Assert(modules.Submodules["basic"].URL, Equals, "git@github.com:git-fixtures/basic.git")
c.Assert(modules.Submodules["itself"].URL, Equals, "git@github.com:git-fixtures/submodule.git")
c.Assert(modules.Submodules["basic"].URL, Equals, "../basic.git")
c.Assert(modules.Submodules["itself"].URL, Equals, "../submodule.git")

basicSubmodule, err := w.Submodule("basic")
c.Assert(err, IsNil)
basicRepo, err := basicSubmodule.Repository()
c.Assert(err, IsNil)
basicRemotes, err := basicRepo.Remotes()
c.Assert(err, IsNil)
c.Assert(basicRemotes[0].Config().URLs[0], Equals, "https://github.com/git-fixtures/basic.git")

itselfSubmodule, err := w.Submodule("itself")
c.Assert(err, IsNil)
itselfRepo, err := itselfSubmodule.Repository()
c.Assert(err, IsNil)
itselfRemotes, err := itselfRepo.Remotes()
c.Assert(err, IsNil)
c.Assert(itselfRemotes[0].Config().URLs[0], Equals, "https://github.com/git-fixtures/submodule.git")

sub, err := w.Submodules()
c.Assert(err, IsNil)

err = sub.Update(&SubmoduleUpdateOptions{Init: true, RecurseSubmodules:DefaultSubmoduleRecursionDepth})
err = sub.Update(&SubmoduleUpdateOptions{Init: true, RecurseSubmodules: DefaultSubmoduleRecursionDepth})
c.Assert(err, IsNil)

status, err := w.Status()
Expand Down

0 comments on commit e9c56de

Please sign in to comment.