github.com/mattyr/nomad@v0.3.3-0.20160919021406-3485a065154a/client/getter/getter.go (about) 1 package getter 2 3 import ( 4 "fmt" 5 "net/url" 6 "path/filepath" 7 "sync" 8 9 gg "github.com/hashicorp/go-getter" 10 "github.com/hashicorp/nomad/client/driver/env" 11 "github.com/hashicorp/nomad/nomad/structs" 12 ) 13 14 var ( 15 // getters is the map of getters suitable for Nomad. It is initialized once 16 // and the lock is used to guard access to it. 17 getters map[string]gg.Getter 18 lock sync.Mutex 19 20 // supported is the set of download schemes supported by Nomad 21 supported = []string{"http", "https", "s3"} 22 ) 23 24 // getClient returns a client that is suitable for Nomad downloading artifacts. 25 func getClient(src, dst string) *gg.Client { 26 lock.Lock() 27 defer lock.Unlock() 28 29 // Return the pre-initialized client 30 if getters == nil { 31 getters = make(map[string]gg.Getter, len(supported)) 32 for _, getter := range supported { 33 if impl, ok := gg.Getters[getter]; ok { 34 getters[getter] = impl 35 } 36 } 37 } 38 39 return &gg.Client{ 40 Src: src, 41 Dst: dst, 42 Mode: gg.ClientModeAny, 43 Getters: getters, 44 } 45 } 46 47 // getGetterUrl returns the go-getter URL to download the artifact. 48 func getGetterUrl(taskEnv *env.TaskEnvironment, artifact *structs.TaskArtifact) (string, error) { 49 taskEnv.Build() 50 u, err := url.Parse(taskEnv.ReplaceEnv(artifact.GetterSource)) 51 if err != nil { 52 return "", fmt.Errorf("failed to parse source URL %q: %v", artifact.GetterSource, err) 53 } 54 55 // Build the url 56 q := u.Query() 57 for k, v := range artifact.GetterOptions { 58 q.Add(k, taskEnv.ReplaceEnv(v)) 59 } 60 u.RawQuery = q.Encode() 61 return u.String(), nil 62 } 63 64 // GetArtifact downloads an artifact into the specified task directory. 65 func GetArtifact(taskEnv *env.TaskEnvironment, artifact *structs.TaskArtifact, taskDir string) error { 66 url, err := getGetterUrl(taskEnv, artifact) 67 if err != nil { 68 return err 69 } 70 71 // Download the artifact 72 dest := filepath.Join(taskDir, artifact.RelativeDest) 73 if err := getClient(url, dest).Get(); err != nil { 74 return fmt.Errorf("GET error: %v", err) 75 } 76 77 return nil 78 }