Skip to content

Commit

Permalink
add module parameter :use_ssh_agent to skip ssh-add before git over S…
Browse files Browse the repository at this point in the history
…SH commands, fixes #171
  • Loading branch information
xorpaul committed Mar 31, 2021
1 parent 12f3a90 commit ae3a3c4
Show file tree
Hide file tree
Showing 7 changed files with 105 additions and 7 deletions.
8 changes: 7 additions & 1 deletion config.go
Original file line number Diff line number Diff line change
Expand Up @@ -196,7 +196,7 @@ func readPuppetfile(pf string, sshKey string, source string, branch string, forc
reForgeModule := regexp.MustCompile("^\\s*(?:mod)\\s+['\"]?([^'\"]+[-/][^'\"]+)['\"](?:\\s*)[,]?(.*)")
reForgeAttribute := regexp.MustCompile("\\s*['\"]?([^\\s'\"]+)\\s*['\"]?(?:=>)?\\s*['\"]?([^'\"]+)?")
reGitModule := regexp.MustCompile("^\\s*(?:mod)\\s+['\"]?([^'\"/]+)['\"]\\s*,(.*)")
reGitAttribute := regexp.MustCompile("\\s*:(git|commit|tag|branch|ref|link|ignore[-_]unreachable|fallback|install_path|default_branch|local)\\s*=>\\s*['\"]?([^'\"]+)['\"]?")
reGitAttribute := regexp.MustCompile("\\s*:(git|commit|tag|branch|ref|link|ignore[-_]unreachable|fallback|install_path|default_branch|local|use_ssh_agent)\\s*=>\\s*['\"]?([^'\"]+)['\"]?")
reUniqueGitAttribute := regexp.MustCompile("\\s*:(?:commit|tag|branch|ref|link)\\s*=>")
reDanglingAttribute := regexp.MustCompile("^\\s*:[^ ]+\\s*=>")
moduleDir := "modules"
Expand Down Expand Up @@ -392,6 +392,12 @@ func readPuppetfile(pf string, sshKey string, source string, branch string, forc
if local {
gm.local = true
}
} else if gitModuleAttribute == "use_ssh_agent" {
useSSHAgent, err := strconv.ParseBool(a[2])
if err != nil {
Fatalf("Error: Can not convert value " + a[2] + " of parameter " + gitModuleAttribute + " to boolean. In " + pf + " for module " + gitModuleName + " line: " + line)
}
gm.useSSHAgent = useSSHAgent
}

}
Expand Down
1 change: 1 addition & 0 deletions g10k.go
Original file line number Diff line number Diff line change
Expand Up @@ -182,6 +182,7 @@ type GitModule struct {
installPath string
local bool
moduleDir string
useSSHAgent bool
}

// ForgeResult is returned by queryForgeAPI and contains if and which version of the Puppetlabs Forge module needs to be downloaded
Expand Down
25 changes: 24 additions & 1 deletion g10k_puppetfile_test.go
Original file line number Diff line number Diff line change
Expand Up @@ -98,7 +98,9 @@ func equalGitModule(a, b GitModule) bool {
a.ref != b.ref ||
a.link != b.link ||
a.ignoreUnreachable != b.ignoreUnreachable ||
a.installPath != b.installPath {
a.installPath != b.installPath ||
a.local != b.local ||
a.useSSHAgent != b.useSSHAgent {
return false
}
if len(a.fallback) != len(b.fallback) {
Expand Down Expand Up @@ -500,3 +502,24 @@ func TestReadPuppetfileGitDashNSlashNotation(t *testing.T) {
t.Errorf("Expected Puppetfile: %+v, but got Puppetfile: %+v", expected, got)
}
}

func TestReadPuppetfileSSHKeyAlreadyLoaded(t *testing.T) {
quiet = true
funcName := strings.Split(funcName(), ".")[len(strings.Split(funcName(), "."))-1]
got := readPuppetfile("tests/"+funcName, "", "test", "test", false, false)

fm := make(map[string]ForgeModule)
gm := make(map[string]GitModule)
gm["example_module"] = GitModule{git: "[email protected]/foo/example-module.git", branch: "foo", useSSHAgent: true}

expected := Puppetfile{source: "test", gitModules: gm, forgeModules: fm}
//fmt.Println(got)

if !equalPuppetfile(got, expected) {
fmt.Println("Expected:")
spew.Dump(expected)
fmt.Println("Got:")
spew.Dump(got)
t.Errorf("Expected Puppetfile: %+v, but got Puppetfile: %+v", expected, got)
}
}
54 changes: 54 additions & 0 deletions g10k_test.go
Original file line number Diff line number Diff line change
Expand Up @@ -9,6 +9,7 @@ import (
"os/exec"
"path/filepath"
"reflect"
"runtime"
"strconv"
"strings"
"syscall"
Expand Down Expand Up @@ -3208,3 +3209,56 @@ func TestBranchFilterRegex(t *testing.T) {

purgeDir("/tmp/branchfilter", funcName)
}

func TestResolvePuppetfileUseSSHAgent(t *testing.T) {
quiet = true
funcName := strings.Split(funcName(), ".")[len(strings.Split(funcName(), "."))-1]
configFile = "tests/TestConfigUseSSHAgent.yaml"
config = readConfigfile(configFile)
if os.Getenv("TEST_FOR_CRASH_"+funcName) == "1" {
purgeDir("/tmp/example/", funcName)
purgeDir("/tmp/g10k/", funcName)
debug = true
branchParam = "use_ssh_agent"
resolvePuppetEnvironment(false, "")
return
}

cmd := exec.Command(os.Args[0], "-test.run="+funcName+"$")
cmd.Env = append(os.Environ(), "TEST_FOR_CRASH_"+funcName+"=1")
out, err := cmd.CombinedOutput()

exitCode := 0
if msg, ok := err.(*exec.ExitError); ok { // there is error code
exitCode = msg.Sys().(syscall.WaitStatus).ExitStatus()
}

if 1 != exitCode {
t.Errorf("terminated with %v, but we expected exit status %v Output: %s", exitCode, 1, string(out))
}
//fmt.Println(string(out))

sshAddCmd := "ssh-add"
if runtime.GOOS == "darwin" {
sshAddCmd = "ssh-add -K"
}

expectedLines := []string{
"DEBUG git repo url [email protected]:foo/git_module_with_ssh_agent.git with loaded SSH keys from ssh-agent",
"DEBUG git repo url [email protected]:foobar/github_module_without_ssh_add.git with SSH key tests/TestConfigUseSSHAgent.yaml",
"DEBUG git repo url [email protected]:bar/git_module_with_ssh_add.git with SSH key tests/TestConfigUseSSHAgent.yaml",
"DEBUG executeCommand(): Executing git clone --mirror [email protected]:foo/git_module_with_ssh_agent.git /tmp/g10k/modules/[email protected]_git_module_with_ssh_agent.git",
"DEBUG executeCommand(): Executing git clone --mirror [email protected]:foobar/github_module_without_ssh_add.git /tmp/g10k/modules/[email protected]_github_module_without_ssh_add.git",
"DEBUG executeCommand(): Executing ssh-agent bash -c '" + sshAddCmd + " tests/TestConfigUseSSHAgent.yaml; git clone --mirror [email protected]:bar/git_module_with_ssh_add.git /tmp/g10k/modules/[email protected]_git_module_with_ssh_add.git'",
}

for _, expectedLine := range expectedLines {
if !strings.Contains(string(out), expectedLine) {
t.Errorf("Could not find expected line '" + expectedLine + "' in debug output")
}
}

moduleParam = ""
debug = false

}
11 changes: 6 additions & 5 deletions git.go
Original file line number Diff line number Diff line change
Expand Up @@ -58,7 +58,6 @@ func resolveGitRepositories(uniqueGitModules map[string]GitModule) {
wg.Add(len(uniqueGitModules))

for url, gm := range uniqueGitModules {
Debugf("git repo url " + url)
privateKey := gm.privateKey
go func(url string, gm GitModule, bar *uiprogress.Bar) {
// Try to receive from the concurrentGoroutines channel. When we have something,
Expand All @@ -69,8 +68,10 @@ func resolveGitRepositories(uniqueGitModules map[string]GitModule) {
defer bar.Incr()
defer wg.Done()

if len(gm.privateKey) > 0 {
Debugf("git repo url " + url + " with ssh key " + privateKey)
if gm.useSSHAgent {
Debugf("git repo url " + url + " with loaded SSH keys from ssh-agent")
} else if len(gm.privateKey) > 0 {
Debugf("git repo url " + url + " with SSH key " + privateKey)
} else {
Debugf("git repo url " + url + " without ssh key")
}
Expand All @@ -95,11 +96,12 @@ func resolveGitRepositories(uniqueGitModules map[string]GitModule) {
}

func doMirrorOrUpdate(gitModule GitModule, workDir string, retryCount int) bool {
//fmt.Printf("%+v\n", gitModule)
isControlRepo := strings.HasPrefix(workDir, config.EnvCacheDir)
isInModulesCacheDir := strings.HasPrefix(workDir, config.ModulesCacheDir)

needSSHKey := true
if len(gitModule.privateKey) == 0 || strings.Contains(gitModule.git, "github.com") {
if len(gitModule.privateKey) == 0 || strings.Contains(gitModule.git, "github.com") || gitModule.useSSHAgent == true {
if isControlRepo {
needSSHKey = true
} else {
Expand All @@ -109,7 +111,6 @@ func doMirrorOrUpdate(gitModule GitModule, workDir string, retryCount int) bool
er := ExecResult{}
gitCmd := "git clone --mirror " + gitModule.git + " " + workDir
if config.CloneGitModules && !isControlRepo && !isInModulesCacheDir {
//fmt.Printf("%+v\n", gitModule)
gitCmd = "git clone --single-branch --branch " + gitModule.tree + " " + gitModule.git + " " + workDir
}
if isDir(workDir) {
Expand Down
8 changes: 8 additions & 0 deletions tests/TestConfigUseSSHAgent.yaml
Original file line number Diff line number Diff line change
@@ -0,0 +1,8 @@
---
:cachedir: '/tmp/g10k'

sources:
example:
remote: 'https://github.com/xorpaul/g10k-environment.git'
basedir: '/tmp/example/'
private_key: 'tests/TestConfigUseSSHAgent.yaml' # just some existing file, we just want to check if the ssh-add command isn't used
5 changes: 5 additions & 0 deletions tests/TestReadPuppetfileSSHKeyAlreadyLoaded
Original file line number Diff line number Diff line change
@@ -0,0 +1,5 @@
mod 'example_module',
:git => '[email protected]/foo/example-module.git',
:branch => 'foo',
:use_ssh_agent => true

0 comments on commit ae3a3c4

Please sign in to comment.