func (a *ApplicationController) Deploy(r *knot.WebContext) interface{} { r.Config.OutputType = knot.OutputJson path := filepath.Join(EC_DATA_PATH, "application", "log") log, _ := toolkit.NewLog(false, true, path, "log-%s", "20060102-1504") log.AddLog("Get payload", "INFO") payload := struct { ID string `json:"_id",bson:"_id"` Server string }{} err := r.GetPayload(&payload) if err != nil { log.AddLog(err.Error(), "ERROR") return helper.CreateResult(false, nil, err.Error()) } log.AddLog("Get application with ID: "+payload.ID, "INFO") app := new(colonycore.Application) err = colonycore.Get(app, payload.ID) if err != nil { log.AddLog(err.Error(), "ERROR") return helper.CreateResult(false, nil, err.Error()) } log.AddLog("Get server with ID: "+payload.Server, "INFO") server := new(colonycore.Server) err = colonycore.Get(server, payload.Server) if err != nil { log.AddLog(err.Error(), "ERROR") return helper.CreateResult(false, nil, err.Error()) } serverPathSeparator := a.GetServerPathSeparator(server) changeDeploymentStatus := func(status bool) { deployedTo := []string{} for _, each := range app.DeployedTo { if each != server.ID { deployedTo = append(deployedTo, server.ID) } } if status { app.DeployedTo = append(deployedTo, server.ID) } colonycore.Save(app) } log.AddLog(fmt.Sprintf("Connect to server %v", server), "INFO") sshSetting, sshClient, err := new(ServerController).SSHConnect(server) defer sshClient.Close() if server.OS == "windows" { sourcePath := filepath.Join(EC_APP_PATH, "src", app.ID) destinationPath := strings.Join([]string{server.AppPath, "src"}, serverPathSeparator) destinationZipPathOutput := strings.Join([]string{destinationPath, app.ID}, serverPathSeparator) var sourceZipPath string var unzipCmd string var destinationZipPath string if strings.Contains(server.CmdExtract, "7z") || strings.Contains(server.CmdExtract, "zip") { sourceZipPath = filepath.Join(EC_APP_PATH, "src", fmt.Sprintf("%s.zip", app.ID)) destinationZipPath = fmt.Sprintf("%s.zip", destinationZipPathOutput) deszip := fmt.Sprintf("%s%s%s", destinationPath, serverPathSeparator, app.ID) // cmd /C 7z e -o %s -y %s unzipCmd = fmt.Sprintf("cmd /C %s", server.CmdExtract) unzipCmd = strings.Replace(unzipCmd, `%1`, deszip, -1) unzipCmd = strings.Replace(unzipCmd, `%2`, destinationZipPath, -1) log.AddLog(unzipCmd, "INFO") err = toolkit.ZipCompress(sourcePath, sourceZipPath) if err != nil { log.AddLog(err.Error(), "ERROR") changeDeploymentStatus(false) return helper.CreateResult(false, nil, err.Error()) } } else { message := "currently only zip/7z command which is supported" log.AddLog(message, "ERROR") changeDeploymentStatus(false) return helper.CreateResult(false, nil, message) } rmCmdZip := fmt.Sprintf("rm -rf %s", destinationZipPath) log.AddLog(rmCmdZip, "INFO") _, err = sshSetting.GetOutputCommandSsh(rmCmdZip) if err != nil { log.AddLog(err.Error(), "ERROR") changeDeploymentStatus(false) return helper.CreateResult(false, nil, err.Error()) } err = sshSetting.SshCopyByPath(sourceZipPath, destinationPath) log.AddLog(fmt.Sprintf("scp from %s to %s", sourceZipPath, destinationPath), "INFO") rmCmdZipOutput := fmt.Sprintf("rm -rf %s", destinationZipPathOutput) log.AddLog(rmCmdZipOutput, "INFO") _, err = sshSetting.GetOutputCommandSsh(rmCmdZipOutput) if err != nil { log.AddLog(err.Error(), "ERROR") changeDeploymentStatus(false) return helper.CreateResult(false, nil, err.Error()) } mkdirDestCmd := fmt.Sprintf("%s %s%s%s", server.CmdMkDir, destinationPath, serverPathSeparator, app.ID) log.AddLog(mkdirDestCmd, "INFO") _, err = sshSetting.GetOutputCommandSsh(mkdirDestCmd) if err != nil { log.AddLog(err.Error(), "ERROR") changeDeploymentStatus(false) return helper.CreateResult(false, nil, err.Error()) } chmodDestCmd := fmt.Sprintf("chmod -R 755 %s%s%s", destinationPath, serverPathSeparator, app.ID) log.AddLog(chmodDestCmd, "INFO") _, err = sshSetting.GetOutputCommandSsh(chmodDestCmd) if err != nil { log.AddLog(err.Error(), "ERROR") changeDeploymentStatus(false) return helper.CreateResult(false, nil, err.Error()) } log.AddLog(unzipCmd, "INFO") _, err = sshSetting.GetOutputCommandSsh(unzipCmd) if err != nil { log.AddLog(err.Error(), "ERROR") changeDeploymentStatus(false) return helper.CreateResult(false, nil, err.Error()) } err = os.Remove(sourceZipPath) log.AddLog(fmt.Sprintf("remove %s", sourceZipPath), "INFO") if err != nil { log.AddLog(err.Error(), "ERROR") changeDeploymentStatus(false) return helper.CreateResult(false, nil, err.Error()) } findCommand := fmt.Sprintf(`find %s -name "*install.bat"`, destinationZipPathOutput) log.AddLog(findCommand, "INFO") installerPath, err := sshSetting.GetOutputCommandSsh(findCommand) installerPath = strings.TrimSpace(installerPath) if err != nil { log.AddLog(err.Error(), "ERROR") changeDeploymentStatus(false) return helper.CreateResult(false, nil, err.Error()) } if installerPath == "" { errString := "installer not found" log.AddLog(errString, "ERROR") changeDeploymentStatus(false) return helper.CreateResult(false, nil, errString) } chmodCommand := fmt.Sprintf("chmod 755 %s%sinstall.bat", destinationZipPathOutput, serverPathSeparator) log.AddLog(chmodCommand, "INFO") _, err = sshSetting.GetOutputCommandSsh(chmodCommand) if err != nil { log.AddLog(err.Error(), "ERROR") changeDeploymentStatus(false) return helper.CreateResult(false, nil, err.Error()) } installerBasePath, _ := func(path string) (string, string) { comps := strings.Split(path, serverPathSeparator) ibp := strings.Join(comps[:len(comps)-1], serverPathSeparator) ilf := comps[len(comps)-1] return ibp, ilf }(installerPath) fmt.Println(installerBasePath) cRunCommand := make(chan string, 1) go func() { runCommand := fmt.Sprintf("cmd /C %s%sinstall.bat", destinationZipPathOutput, serverPathSeparator) log.AddLog(runCommand, "INFO") res, err := sshSetting.RunCommandSsh(runCommand) fmt.Println(res) if err != nil { log.AddLog(err.Error(), "ERROR") cRunCommand <- err.Error() } else { cRunCommand <- "" } }() errorMessage := "" select { case receiveRunCommandOutput := <-cRunCommand: errorMessage = receiveRunCommandOutput case <-time.After(time.Second * 3): errorMessage = "" } if errorMessage != "" { log.AddLog(errorMessage, "ERROR") changeDeploymentStatus(false) return helper.CreateResult(false, nil, errorMessage) } if app.DeployedTo == nil { app.DeployedTo = []string{} } changeDeploymentStatus(true) return helper.CreateResult(true, nil, "") } sourcePath := filepath.Join(EC_APP_PATH, "src", app.ID) destinationPath := strings.Join([]string{server.AppPath, "src"}, serverPathSeparator) destinationZipPathOutput := strings.Join([]string{destinationPath, app.ID}, serverPathSeparator) var sourceZipPath string var unzipCmd string var destinationZipPath string if strings.Contains(server.CmdExtract, "tar") { sourceZipPath = filepath.Join(EC_APP_PATH, "src", fmt.Sprintf("%s.tar", app.ID)) destinationZipPath = fmt.Sprintf("%s.tar", destinationZipPathOutput) // tar -xvf %s -C %s unzipCmd = strings.Replace(server.CmdExtract, `%1`, destinationZipPath, -1) unzipCmd = strings.Replace(unzipCmd, `%2`, destinationZipPathOutput, -1) log.AddLog(unzipCmd, "INFO") err = toolkit.TarCompress(sourcePath, sourceZipPath) if err != nil { log.AddLog(err.Error(), "ERROR") changeDeploymentStatus(false) return helper.CreateResult(false, nil, err.Error()) } } else if strings.Contains(server.CmdExtract, "zip") { sourceZipPath = filepath.Join(EC_APP_PATH, "src", fmt.Sprintf("%s.zip", app.ID)) destinationZipPath = fmt.Sprintf("%s.zip", destinationZipPathOutput) // unzip %s -d %s unzipCmd = strings.Replace(server.CmdExtract, `%1`, destinationZipPath, -1) unzipCmd = strings.Replace(unzipCmd, `%2`, destinationZipPathOutput, -1) log.AddLog(unzipCmd, "INFO") err = toolkit.ZipCompress(sourcePath, sourceZipPath) if err != nil { log.AddLog(err.Error(), "ERROR") changeDeploymentStatus(false) return helper.CreateResult(false, nil, err.Error()) } } else { message := "currently only zip/tar command which is supported" log.AddLog(message, "ERROR") changeDeploymentStatus(false) return helper.CreateResult(false, nil, message) } rmCmdZip := fmt.Sprintf("rm -rf %s", destinationZipPath) log.AddLog(rmCmdZip, "INFO") _, err = sshSetting.GetOutputCommandSsh(rmCmdZip) if err != nil { log.AddLog(err.Error(), "ERROR") changeDeploymentStatus(false) return helper.CreateResult(false, nil, err.Error()) } err = sshSetting.SshCopyByPath(sourceZipPath, destinationPath) log.AddLog(fmt.Sprintf("scp from %s to %s", sourceZipPath, destinationPath), "INFO") rmCmdZipOutput := fmt.Sprintf("rm -rf %s", destinationZipPathOutput) log.AddLog(rmCmdZipOutput, "INFO") _, err = sshSetting.GetOutputCommandSsh(rmCmdZipOutput) if err != nil { log.AddLog(err.Error(), "ERROR") changeDeploymentStatus(false) return helper.CreateResult(false, nil, err.Error()) } mkdirDestCmd := fmt.Sprintf("%s %s%s%s", server.CmdMkDir, destinationPath, serverPathSeparator, app.ID) log.AddLog(mkdirDestCmd, "INFO") _, err = sshSetting.GetOutputCommandSsh(mkdirDestCmd) if err != nil { log.AddLog(err.Error(), "ERROR") changeDeploymentStatus(false) return helper.CreateResult(false, nil, err.Error()) } chmodDestCmd := fmt.Sprintf("chmod -R 777 %s%s%s", destinationPath, serverPathSeparator, app.ID) log.AddLog(chmodDestCmd, "INFO") _, err = sshSetting.GetOutputCommandSsh(chmodDestCmd) if err != nil { log.AddLog(err.Error(), "ERROR") changeDeploymentStatus(false) return helper.CreateResult(false, nil, err.Error()) } log.AddLog(unzipCmd, "INFO") _, err = sshSetting.GetOutputCommandSsh(unzipCmd) if err != nil { log.AddLog(err.Error(), "ERROR") changeDeploymentStatus(false) return helper.CreateResult(false, nil, err.Error()) } err = os.Remove(sourceZipPath) log.AddLog(fmt.Sprintf("remove %s", sourceZipPath), "INFO") if err != nil { log.AddLog(err.Error(), "ERROR") changeDeploymentStatus(false) return helper.CreateResult(false, nil, err.Error()) } findCommand := fmt.Sprintf(`find %s -name "*install.sh"`, destinationZipPathOutput) log.AddLog(findCommand, "INFO") installerPath, err := sshSetting.GetOutputCommandSsh(findCommand) installerPath = strings.TrimSpace(installerPath) if err != nil { log.AddLog(err.Error(), "ERROR") changeDeploymentStatus(false) return helper.CreateResult(false, nil, err.Error()) } if installerPath == "" { errString := "installer not found" log.AddLog(errString, "ERROR") changeDeploymentStatus(false) return helper.CreateResult(false, nil, errString) } chmodCommand := fmt.Sprintf("chmod 755 %s", installerPath) log.AddLog(chmodCommand, "INFO") _, err = sshSetting.GetOutputCommandSsh(chmodCommand) if err != nil { log.AddLog(err.Error(), "ERROR") changeDeploymentStatus(false) return helper.CreateResult(false, nil, err.Error()) } installerBasePath, installerFile := func(path string) (string, string) { comps := strings.Split(path, serverPathSeparator) ibp := strings.Join(comps[:len(comps)-1], serverPathSeparator) ilf := comps[len(comps)-1] return ibp, ilf }(installerPath) cRunCommand := make(chan string, 1) go func() { runCommand := fmt.Sprintf("cd %s && ./%s &", installerBasePath, installerFile) log.AddLog(runCommand, "INFO") _, err = sshSetting.RunCommandSsh(runCommand) if err != nil { log.AddLog(err.Error(), "ERROR") cRunCommand <- err.Error() } else { cRunCommand <- "" } }() errorMessage := "" select { case receiveRunCommandOutput := <-cRunCommand: errorMessage = receiveRunCommandOutput case <-time.After(time.Second * 3): errorMessage = "" } if errorMessage != "" { log.AddLog(errorMessage, "ERROR") changeDeploymentStatus(false) return helper.CreateResult(false, nil, errorMessage) } if app.DeployedTo == nil { app.DeployedTo = []string{} } changeDeploymentStatus(true) return helper.CreateResult(true, nil, "") }
func (p *Page) CopyFileToServer(server *Server, sourcePath string, destPath string, appID string, log *toolkit.LogEngine) error { var serverPathSeparator string if strings.Contains(destPath, "/") { serverPathSeparator = `/` } else { serverPathSeparator = "\\\\" } destZipPath := strings.Join([]string{destPath, appID}, serverPathSeparator) unzipCmd, sourceZipFile, destZipFile, err := p.DefineCommand(server, sourcePath, destZipPath, appID) log.AddLog(toolkit.Sprintf("Connect to server %v", server), "INFO") sshSetting, sshClient, err := p.connectSSH(server) defer sshClient.Close() log.AddLog(unzipCmd, "INFO") /*compress file on local colony manager*/ if strings.Contains(sourceZipFile, ".zip") { err = toolkit.ZipCompress(sourcePath, sourceZipFile) } else if strings.Contains(sourceZipFile, ".tar") { err = toolkit.TarCompress(sourcePath, sourceZipFile) } if err != nil { log.AddLog(err.Error(), "ERROR") return err } rmCmdZip := toolkit.Sprintf("rm -rf %s", destZipFile) log.AddLog(rmCmdZip, "INFO") _, err = sshSetting.GetOutputCommandSsh(rmCmdZip) /*delete zip file on server before copy file*/ if err != nil { log.AddLog(err.Error(), "ERROR") return err } log.AddLog(toolkit.Sprintf("scp from %s to %s", sourceZipFile, destPath), "INFO") err = sshSetting.SshCopyByPath(sourceZipFile, destPath) /*copy zip file from colony manager to server*/ if err != nil { log.AddLog(err.Error(), "ERROR") return err } rmCmdZipOutput := toolkit.Sprintf("rm -rf %s", destZipPath) log.AddLog(rmCmdZipOutput, "INFO") _, err = sshSetting.GetOutputCommandSsh(rmCmdZipOutput) /*delete folder before extract zip file on server*/ if err != nil { log.AddLog(err.Error(), "ERROR") return err } mkdirDestCmd := toolkit.Sprintf("%s %s%s%s", server.CmdMkDir, destZipPath, serverPathSeparator, appID) log.AddLog(mkdirDestCmd, "INFO") _, err = sshSetting.GetOutputCommandSsh(mkdirDestCmd) /*make new dest folder on server for folder extraction*/ if err != nil { log.AddLog(err.Error(), "ERROR") return err } chmodDestCmd := toolkit.Sprintf("chmod -R 755 %s%s%s", destZipPath, serverPathSeparator, appID) log.AddLog(chmodDestCmd, "INFO") _, err = sshSetting.GetOutputCommandSsh(chmodDestCmd) /*set chmod on new folder extraction*/ if err != nil { log.AddLog(err.Error(), "ERROR") return err } log.AddLog(unzipCmd, "INFO") _, err = sshSetting.GetOutputCommandSsh(unzipCmd) /*extract zip file to server*/ if err != nil { log.AddLog(err.Error(), "ERROR") return err } log.AddLog(toolkit.Sprintf("remove %s", sourceZipFile), "INFO") err = os.Remove(sourceZipFile) /*remove zip file from local colony manager*/ if err != nil { log.AddLog(err.Error(), "ERROR") return err } log.AddLog(rmCmdZip, "INFO") _, err = sshSetting.GetOutputCommandSsh(rmCmdZip) /*delete zip file on server after folder extraction*/ if err != nil { log.AddLog(err.Error(), "ERROR") return err } return nil }