// Running determines if the given process is running. func running(args ...string) (found bool) { found = false cmd := exec.Command("docker", "ps") stdout, err := cmd.StdoutPipe() if err != nil { logger.Log(fmt.Sprintln(err)) } _, err = cmd.StderrPipe() if err != nil { logger.Log(fmt.Sprintln(err)) } err = cmd.Start() if err != nil { logger.Log(fmt.Sprintln(err)) } buf := new(bytes.Buffer) buf.ReadFrom(stdout) s := buf.String() cmd.Wait() for _, id := range pids() { if !found { found = strings.Contains(s, id) } } return }
func Install(args ...string) { go func() { os.Chdir(root) opts := []string{"clone", args[0]} logger.Log("Cloning " + args[0] + "\n") cmd := exec.Command("git", opts...) cmd.Stdout = os.Stdout cmd.Stderr = os.Stderr err := cmd.Run() if err == nil { parts := strings.Split(args[0], "/") path := parts[len(parts)-1:][0] path = strings.Replace(path, ".git", "", -1) wd, _ := os.Getwd() logger.Log("Building Images here: " + wd + "/" + path + "\n") os.Chdir(wd + "/" + path) Build(path) cfg = nil BundleInstall("now") postInstall() } else { logger.Log(err.Error()) } }() }
// handleCommand will take in the argument for the process and run it func ParseCommand(args []string) { SetProcess(args[0]) SetConfig(config.Process(args[0])) opts := commandOpts(args) if message, ok := cfg.Valid(); ok { name := args[1] daemonCmd, daemonOk := DaemonizedCommands()[name] infoCmd, infoOk := InfoCommands()[name] interactiveCmd, interactiveOk := InteractiveCommands()[name] switch { case daemonOk: daemonCmd.run(opts...) case infoOk: infoCmd.run(opts...) case interactiveOk: interactiveCmd.run(opts...) default: logger.Log(fmt.Sprintf("Running Command: (%v) doesn't exists\n", args[1])) } } else { logger.Log(message) } }
func InstallSystemd(args ...string) { t := template.New("Systemd Conf") t, err := t.Parse(systemdConf) if err != nil { logger.Log(err.Error()) } wd, _ := os.Getwd() path := strings.Split(wd, "/") name := path[len(path)-1:][0] shoe := exe() logger.Log(shoe + "\n") fileName := fmt.Sprintf("/usr/lib/systemd/system/%s.service", name) file, err := os.OpenFile(fileName, os.O_RDWR|os.O_CREATE, 0666) if err != nil { return } defer file.Close() conf := SystemdConf{ Exe: shoe, App: name, Pwd: wd} t.Execute(file, conf) }
// runInstances wraps the given function and execute // the number of instances requested by the config file // for the command given. func runInstances(message string, fn runner) { logger.Log(fmt.Sprintf("%s %v\n", message, process)) for i := 0; i < cfg.Instances; i++ { logger.Log(fmt.Sprintf("...Instance %d of %d %s\n", i, cfg.Instances, process)) id, _ := pid(i) fn(i, id) } }
func Up() { http.HandleFunc("/clone", before(cloneHandler)) http.HandleFunc("/commands/", before(commandHandler)) http.HandleFunc("/apps/json/", before(makeHandler(appHandler))) http.HandleFunc("/list/json", before(listHandler)) http.HandleFunc("/css/application.css", before(cssHandler)) http.HandleFunc("/js/application.js", before(jsHandler)) http.HandleFunc("/", before(indexHandler)) logger.Log(fmt.Sprintf("Server up on port 9369\n")) logger.Log(fmt.Sprintf("Root: %s\n", command.Root())) http.ListenAndServe(":9369", nil) }
// Status will list out the statuses for the given process func Status(args ...string) { runInstances("Status", func(i int, id string) error { on := running() logger.Log(fmt.Sprintf("Container ID: %s\n", id)) logger.Log(fmt.Sprintf(" Running: %s\n", strconv.FormatBool(on))) if on { net := networkSettings(i) logger.Log(fmt.Sprintf(" IP: %s\n", net.Ip)) logger.Log(fmt.Sprintf(" Public Port: %s\n", net.Public.tcp)) logger.Log(fmt.Sprintf("Private Port: %s\n", net.Private.tcp)) } return nil }) }
func exe() string { out, err := exec.Command("which shoehorn").Output() if err != nil { logger.Log(err.Error()) out = []byte("/usr/bin/shoehorn") } return string(out) }
func Update(args ...string) { go func() { logger.Log("Updaing...") cmd := exec.Command("git", "pull") cmd.Stdout = os.Stdout cmd.Stderr = os.Stderr err := cmd.Run() if err == nil { Build(root) cfg = nil BundleInstall("now") postUpdate() } else { logger.Log(err.Error()) } }() }
// Build will create the container if nessary func Build(args ...string) { wd, _ := os.Getwd() logger.Log(fmt.Sprintf("In %s to build.", wd)) if cfg != nil { logger.Log(fmt.Sprintf("Building...%s\n", cfg.App)) cmd := exec.Command("docker", "build", "-t", cfg.Container, cfg.BuildFile) cmd.Stdout = os.Stdout cmd.Stderr = os.Stderr cmd.Stdin = os.Stdin cmd.Run() } else { config.LoadConfigs() for _, process := range config.List() { SetProcess(process) SetConfig(config.Process(process)) Build(args...) } } }
func commandHandler(w http.ResponseWriter, r *http.Request) { logger.Log(fmt.Sprintln("Command Handler")) base := r.URL.Path[len("/commands/"):] opts := strings.Split(base, "/") logger.Log(fmt.Sprintf("Commands: %v", opts)) site := opts[0] process := opts[1] cmd := opts[2] path := fmt.Sprintf("%s/%s", command.Root(), site) os.Chdir(path) command.MkDirs() config.LoadConfigs() old := os.Stdout re, wr, _ := os.Pipe() os.Stdout = wr command.ParseCommand([]string{process, cmd}) outC := make(chan string) go func() { var buf bytes.Buffer io.Copy(&buf, re) outC <- buf.String() }() wr.Close() os.Stdout = old out := <-outC clean := strings.Replace(out, "\n", "</br>", -1) o := map[string]string{"status": "ok", "output": clean} b, err := json.Marshal(o) if err != nil { http.Error(w, err.Error(), http.StatusInternalServerError) } renderTemplateString(w, string(b)) }
// Pids pulls all docker ids for each of the instances func pids(args ...string) (pids []string) { for i := 0; i < cfg.Instances; i++ { id, err := pid(i) if err != nil { logger.Log(fmt.Sprintln(err)) } else { pids = append(pids, id) } } return pids }
func PrintConfig(name string) { settings := Process(name) logger.Log(fmt.Sprintln("Process [" + name + "]")) printSetting("App Name", settings.App) printSetting("Start Command", settings.StartCmd) printSetting("Number of Instances", strconv.Itoa(settings.Instances)) printSetting("Private Port", strconv.Itoa(settings.Port)) printSetting("RAM in GB", strconv.Itoa(settings.GB)) printSetting("RAM in MB", strconv.Itoa(settings.MB)) printSetting("RAM in Bytes", strconv.Itoa(settings.Bytes)) printSetting("Domain", strings.Join(settings.Domain, " ")) printSetting("Kill Process?", strconv.FormatBool(settings.Kill)) printSetting("Container Name", settings.Container) printSetting("Volumn(s)", strings.Join(settings.Volumn, " ")) printSetting("Working Directory", settings.WorkingDir) printSetting("Build File", settings.BuildFile) }
func InstallUpstart(args ...string) { t := template.New("Upstart Conf") t, err := t.Parse(upstartConf) if err != nil { logger.Log(err.Error() + "\n") } wd, _ := os.Getwd() path := strings.Split(wd, "/") name := path[len(path)-1:][0] fileName := fmt.Sprintf("/etc/init/%s.conf", name) file, err := os.OpenFile(fileName, os.O_RDWR|os.O_CREATE, 0666) conf := UpstartConf{App: name, Exe: exe(), Pwd: wd} t.Execute(file, conf) }
// PrintCommands will list out all of the commands to the end user. func PrintCommands() { logger.Log(fmt.Sprintln("** Daemonized Commands **")) for cmd, desc := range DaemonizedCommands() { logger.Log(fmt.Sprintf("%15s: %s\n", cmd, desc.description)) } logger.Log(fmt.Sprintln("** Information Commands **")) for cmd, desc := range InfoCommands() { logger.Log(fmt.Sprintf("%15s: %s\n", cmd, desc.description)) } logger.Log(fmt.Sprintln("** Interactive Commands **")) for cmd, desc := range InteractiveCommands() { logger.Log(fmt.Sprintf("%15s: %s\n", cmd, desc.description)) } }
// outOpts will colorize the opts as well as print the docker command // that is about to execute. func outOpts(opts []string) { lime := ansi.ColorCode("green:black") reset := ansi.ColorCode("reset") msg := "\n\n" + lime + "docker %s" + reset + "\n\n" logger.Log(fmt.Sprintf(msg, strings.Join(opts, " "))) }
func before(fn func(http.ResponseWriter, *http.Request)) http.HandlerFunc { return func(w http.ResponseWriter, r *http.Request) { logger.Log(fmt.Sprintln(r.URL.Path)) fn(w, r) } }
// PrintParams will print all of the settings that will be passed. // into docker It assumes the first instance . func PrintParams(args ...string) { logger.Log(fmt.Sprintln(settingsToParams(0, false))) }
func printSetting(name string, value string) { if value != "" { logger.Log(fmt.Sprintf("%20v %v\n", name+":", value)) } }
// PrintProcesses prints out the listing of all the sections in the config file func PrintProcesses() { logger.Log(fmt.Sprintln("** List of Apps **")) logger.Log(fmt.Sprintln(List())) }
// Restart will call stop then start for this process func Restart(args ...string) { logger.Log(fmt.Sprintf("Restarting %v\n", process)) Stop(args...) Start(args...) }