func doInstall(c *cli.Context) { home := os.Getenv("HOME") packageName := c.Args().First() packageFile := "" if _, err := os.Stat(packageName); err == nil { fmt.Println("Install from a local package") pwd, err := os.Getwd() if err != nil { fmt.Println(err) os.Exit(1) } packageFile = filepath.Join(home, "/.dpm/cache/", packageName) err = cp(filepath.Join(pwd, packageName), packageFile) if err != nil { fmt.Println(err) os.Exit(1) } err = generateIndex(filepath.Join(home, "/.dpm/cache/"), filepath.Join(home, "/.dpm/index/")) if err != nil { fmt.Println(err) os.Exit(1) } } else { fmt.Println("Install from a remote repository") _, err = repo.Get(packageName, "") if err != nil { fmt.Println(err) os.Exit(1) } } if packageFile != "" { p, err := build.LoadPackage(packageFile) if err != nil { fmt.Println(err) os.Exit(1) } p.Extract(filepath.Join(home, "/.dpm/workspace", p.Sha256())) } }
func install(c *cli.Context) { home := os.Getenv("HOME") packageName := c.Args().First() entry, err := repo.Get(packageName, "") if err != nil { fmt.Println("Cannot find package in the index") os.Exit(1) } packageFile := filepath.Join(home, ".dpm", "cache", entry.Filename) _, err = os.Stat(packageFile) if err != nil { // not existed doInstall(c) } p, err := build.LoadPackage(packageFile) if err != nil { fmt.Println(err) os.Exit(1) } // extract the package // it will extract all dependencies in process _, err = os.Stat(filepath.Join(home, ".dpm", "workspace", entry.Hash)) if err != nil { err = p.Extract(filepath.Join(home, ".dpm", "workspace", entry.Hash)) if err != nil { fmt.Println(err) os.Exit(1) } } hashes, err := p.Order() if err != nil { fmt.Println(err) os.Exit(1) } fmt.Println("Dependencies resolved...") var em provision.ExportedMachine for _, hash := range hashes { packageSpec, err := build.ReadSpec(hash) if err != nil { fmt.Println(err) os.Exit(1) } fmt.Printf("Installing %s:%s (%s)...\n", packageSpec.Name, packageSpec.Version, hash[0:8]) provisionFile := filepath.Join(home, ".dpm", "workspace", hash, packageSpec.Provision) provSpec, err := provision.LoadFromFile(provisionFile) if err != nil { fmt.Println(err) os.Exit(1) } times := 0 loop: err = provSpec.Provision() if err != nil { fmt.Println(err) times++ if times < 10 { goto loop } os.Exit(1) } err = provSpec.ExportEnvsToFile(filepath.Join(home, ".dpm", "workspace", hash, ".env")) if err != nil { fmt.Println(err) os.Exit(1) } em = provSpec.ExportedMachine() compose, err := composition.NewProject(em, hash, packageSpec) if err != nil { fmt.Println(err) os.Exit(1) } err = compose.Up() if err != nil { fmt.Println(err) os.Exit(1) } } flag := "" mode := "engine" if em.Mode == provision.Swarm { flag = "--swarm " mode = "cluster" } fmt.Printf("\nExported machine is %s.\n", em.Name) fmt.Printf("Run \"docker-machine env %s%s\" to see how to connect to your Docker %s.\n", flag, em.Name, mode) }
func BuildPackage(dir string) (*Package, error) { home := os.Getenv("HOME") buf := new(bytes.Buffer) tarfile := new(archivex.TarFile) tarfile.Writer = tar.NewWriter(buf) specContent, err := ioutil.ReadFile(filepath.Join(dir, "SPEC.yml")) root := Root{} err = yaml.Unmarshal(specContent, &root) if err != nil { return nil, err } spec := root.Spec tarfile.AddFileWithName(filepath.Join(dir, "SPEC.yml"), "SPEC.yml") tarfile.AddFileWithName(filepath.Join(dir, spec.Provision), spec.Provision) tarfile.AddFileWithName(filepath.Join(dir, spec.Composition), spec.Composition) for _, d := range spec.Dirs { tarfile.AddAll(filepath.Join(dir, d), true) } hashes := []string{} graph := make(DepGraph) // resolve dependencies on build // to gaurantee that the package will have // the same behaviour everytime we deploy it for name, attributes := range spec.Dependencies { attrs, err := parse(attributes) if err != nil { return nil, err } entry, err := repo.Get(name, attrs["version"]) if err != nil { return nil, err } p, err := LoadPackage(filepath.Join(home, ".dpm", "cache", entry.Filename)) if err != nil { return nil, err } err = p.ExtractIfNotExist() if err != nil { return nil, err } hashes = append(hashes, entry.Hash) deps, err := p.Deps() if err != nil { return nil, err } graph = merge(graph, deps) } // add entry of this package before save to DEPS graph["this"] = hashes depsContent, err := yaml.Marshal(graph) if err != nil { return nil, err } tarfile.Add("DEPS", depsContent) order, cyclic := toposort(graph) if len(cyclic) != 0 { return nil, fmt.Errorf("Dependency cyclic detected") } for _, h := range order { if h == "this" { continue } tarfile.AddAll(filepath.Join(home, ".dpm", "workspace", h), true) } tarfile.Close() return &Package{buf.Bytes()}, nil }