func WaitTaskDone(task_id, auth string, onTik func(), onError func(error) bool, onDone func(lib.TaskResult) bool) (task_res lib.TaskResult, err error) { send_buf := []byte(fmt.Sprintf(`{"task_id": "%s"}`, task_id)) for { err = lib.PostJson(fmt.Sprintf("%s/task", FlaxtonContainerRepo), send_buf, &task_res, auth) if err != nil { if onError != nil { if onError(err) { return } } } else { if task_res.Error || task_res.Done { if onDone != nil { if onDone(task_res) { return } } } } if onTik != nil { onTik() } time.Sleep(time.Second * 2) } }
func AddTask(auth, task_type, daemon string, data interface{}) (task_resp lib.TaskSendResponse, err error) { sdn_map := make(map[string]interface{}) sdn_map["task_type"] = task_type sdn_map["daemon"] = daemon sdn_map["data"] = data var send_buf []byte send_buf, err = json.Marshal(sdn_map) if err != nil { return } err = lib.PostJson(fmt.Sprintf("%s/task/add", FlaxtonContainerRepo), send_buf, &task_resp, auth) return }
func (fxd *FxDaemon) RunTasks() { var ( send_buf []byte marshal_error error request_error error current_tasks []lib.Task current_result lib.TaskResult ) for { if len(fxd.PendingTasks) > 0 { current_tasks = make([]lib.Task, 0) current_tasks = append(current_tasks, fxd.PendingTasks...) fxd.PendingTasks = make([]lib.Task, 0) // Clearing tasks fmt.Println("Task: Got new ", len(current_tasks), "tasks") // Starting execution for current tasks // TODO: maybe we will need concurrent execution in future for _, t := range current_tasks { fmt.Println("Task: ", t.TaskID, t.Type) switch t.Type { case lib.TaskImageTransfer: { current_result = lib.TaskResult{ TaskID: t.TaskID, StartTime: time.Now().UTC().Unix(), Error: false, Done: false, Message: "", } cont_call := make(map[string]string) err := t.ConvertData(&cont_call) if err != nil { current_result.Error = true current_result.Message = err.Error() } else { err = fxd.TransferImage(cont_call) if err != nil { current_result.Error = true current_result.Message = err.Error() } else { current_result.Done = true current_result.EndTime = time.Now().UTC().Unix() } } } case lib.TaskSetDaemonName: { name_map := make(map[string]string) err := t.ConvertData(&name_map) if err != nil { current_result.Error = true current_result.Message = err.Error() } else { fxd.Name = name_map["name"] fxd.Register() current_result.Done = true current_result.Message = fmt.Sprintf("Daemon Name Registered %s", fxd.Name) current_result.EndTime = time.Now().UTC().Unix() } } case lib.TaskAddChildServer: { child_map := make(map[string]ChildServer) err := t.ConvertData(&child_map) if err != nil { current_result.Error = true current_result.Message = err.Error() } else { var port int for k, ch := range child_map { port, _ = strconv.Atoi(k) if _, ok := fxd.BalancerPortChild[port]; !ok { fxd.BalancerPortChild[port] = make([]ChildServer, 0) } fxd.BalancerPortChild[port] = append(fxd.BalancerPortChild[port], ch) current_result.Done = true current_result.EndTime = time.Now().UTC().Unix() } } } case lib.TaskAddBalancingImage: { im_map := make(map[string]BalancerImageInfo) err := t.ConvertData(&im_map) if err != nil { current_result.Error = true current_result.Message = err.Error() } else { var port int for k, im := range im_map { port, _ = strconv.Atoi(k) if _, ok := fxd.BalancerPortImages[port]; !ok { fxd.BalancerPortImages[port] = make([]BalancerImageInfo, 0) } fxd.BalancerPortImages[port] = append(fxd.BalancerPortImages[port], im) go fxd.StartBalancerPort(port) current_result.Message = fmt.Sprintf("%s%d port balancing started for image %s\n", current_result.Message, port, im.ImageName) } current_result.Done = true current_result.EndTime = time.Now().UTC().Unix() } } case lib.TaskStartBalancerPort: { im_map := make(map[string]int) err := t.ConvertData(&im_map) if err != nil { current_result.Error = true current_result.Message = err.Error() } else { go fxd.StartBalancerPort(im_map["port"]) current_result.Message = fmt.Sprintf("%d port balancing started", im_map["port"]) current_result.Done = true current_result.EndTime = time.Now().UTC().Unix() } } case lib.TaskStopBalancerPort: { im_map := make(map[string]int) err := t.ConvertData(&im_map) if err != nil { current_result.Error = true current_result.Message = err.Error() } else { go fxd.StopBalancerPort(im_map["port"]) current_result.Message = fmt.Sprintf("%d port balancing stoped", im_map["port"]) current_result.Done = true current_result.EndTime = time.Now().UTC().Unix() } } case lib.TaskStartContainer: { im_map := make(map[string]docker.HostConfig) // ContainerID -> Container Host Config err := t.ConvertData(&im_map) if err != nil { current_result.Error = true current_result.Message = err.Error() } else { message := "" for cid, conf := range im_map { err = StartContainer(cid, &conf) if err != nil { message = fmt.Sprintf("%s|%s&", cid, err.Error(), message) } } if message != "" { current_result.Error = true current_result.Message = message } else { current_result.EndTime = time.Now().UTC().Unix() } } } case lib.TaskStopContainer: { im_map := make(map[string]uint) // ContainerID -> Stop Timeout err := t.ConvertData(&im_map) if err != nil { current_result.Error = true current_result.Message = err.Error() } else { message := "" for cid, t := range im_map { err = StopContainer(cid, t) if err != nil { message = fmt.Sprintf("%s|%s&", cid, err.Error(), message) } } if message != "" { current_result.Error = true current_result.Message = message } else { current_result.EndTime = time.Now().UTC().Unix() } } } case lib.TaskPauseContainer: { im_map := make([]string, 0) // ContainerID Array to pause err := t.ConvertData(&im_map) if err != nil { current_result.Error = true current_result.Message = err.Error() } else { message := "" for _, cid := range im_map { err = PauseContainer(cid) if err != nil { message = fmt.Sprintf("%s|%s&", cid, err.Error(), message) } } if message != "" { current_result.Error = true current_result.Message = message } else { current_result.EndTime = time.Now().UTC().Unix() } } } case lib.TaskCreateContainer: { im_map := make(map[string]docker.CreateContainerOptions) // ContainerName -> Creation Options err := t.ConvertData(&im_map) if err != nil { current_result.Error = true current_result.Message = err.Error() } else { message := "" for cname, opts := range im_map { err = CreateContainer(opts) if err != nil { message = fmt.Sprintf("%s|%s&", cname, err.Error(), message) } } if message != "" { current_result.Error = true current_result.Message = message } else { current_result.EndTime = time.Now().UTC().Unix() } } } default: { current_result.TaskID = "-1" } } if current_result.TaskID == "-1" { fmt.Println("Unknown Task Command", t.Type) } else { send_buf, marshal_error = json.Marshal(current_result) if marshal_error != nil { log.Fatal(marshal_error) } else { request_error = lib.PostJson(fmt.Sprintf("%s/task", FlaxtonContainerRepo), send_buf, nil, fmt.Sprintf("%s|%s", fxd.AuthKey, fxd.ID)) if request_error != nil { log.Fatal(request_error) } else { fmt.Println("Task: Done ", t.TaskID, current_result.EndTime) } } } } } time.Sleep(time.Second * 2) } }
func RunArguments(args []string) { // Loading Configurations if file exists console_config := ConsoleConfig{} if _, err := os.Stat(FlaxtonConfigFile); os.IsNotExist(err) { logrus.Warn("Config File Doesent exisists, it will be created after authorization") } else { console_config.LoadConfig() } switch args[1] { case "-d", "daemon": { daemon := fxdocker.NewDaemon(fxdocker.DockerEndpoint, false) if len(console_config.DaemonID) == 0 { fmt.Println("Generating ID for this server") console_config.DaemonID = lib.RandomString(25) fmt.Println(console_config.DaemonID) console_config.SaveConfig() } daemon.AuthKey = console_config.Authorization daemon.ID = console_config.DaemonID next_args := args[1:] for i, arg := range args[1:] { switch arg { case "-balancer": { local_port, _ := strconv.Atoi(next_args[i+1]) image_port, _ := strconv.Atoi(next_args[i+3]) daemon.BalancerPortImages[local_port] = make([]fxdocker.BalancerImageInfo, 0) daemon.BalancerPortImages[local_port] = append(daemon.BalancerPortImages[local_port], fxdocker.BalancerImageInfo{ ImageName: next_args[i+2], ImagePort: image_port, Port: local_port, }) } case "-child": { local_port, _ := strconv.Atoi(next_args[i+1]) child_port, _ := strconv.Atoi(next_args[i+3]) if len(daemon.BalancerPortChild[local_port]) == 0 { daemon.BalancerPortChild[local_port] = make([]fxdocker.ChildServer, 0) } daemon.BalancerPortChild[local_port] = append(daemon.BalancerPortChild[local_port], fxdocker.ChildServer{ IP: next_args[i+2], Port: child_port, }) } case "-offline": { daemon.Offline = true } case "stop-port": { daemon_name := next_args[i+1] port_str := next_args[i+2] port, err := strconv.Atoi(port_str) if err != nil { fmt.Println(err.Error()) os.Exit(1) } sdn_map := make(map[string]int) sdn_map["port"] = port task_res, task_err := fxdocker.AddTask(daemon.AuthKey, lib.TaskStopBalancerPort, daemon_name, sdn_map) if task_err != nil { fmt.Println(task_err) } else { fmt.Println("Task Sent !") fmt.Println(task_res.TaskId) fxdocker.WaitTaskDone(task_res.TaskId, daemon.AuthKey, func() { fmt.Print(".") }, func(err error) bool { fmt.Println(err.Error()) return false }, func(t lib.TaskResult) bool { fmt.Println(t.Message) return true }) } os.Exit(1) } case "map-image": { daemon_name := next_args[i+1] port_str := next_args[i+2] port, err := strconv.Atoi(port_str) if err != nil { fmt.Println(err.Error()) os.Exit(1) } image := next_args[i+3] image_port_str := next_args[i+4] image_port, err2 := strconv.Atoi(image_port_str) if err2 != nil { fmt.Println(err2.Error()) os.Exit(1) } sdn_map := make(map[string]fxdocker.BalancerImageInfo) sdn_map[port_str] = fxdocker.BalancerImageInfo{Port: port, ImageName: image, ImagePort: image_port} task_res, task_err := fxdocker.AddTask(daemon.AuthKey, lib.TaskAddBalancingImage, daemon_name, sdn_map) if task_err != nil { fmt.Println(task_err) } else { fmt.Println("Task Sent !") fxdocker.WaitTaskDone(task_res.TaskId, daemon.AuthKey, func() { fmt.Print(".") }, func(err error) bool { fmt.Println(err.Error()) return false }, func(t lib.TaskResult) bool { fmt.Println(t.Message) return true }) } os.Exit(1) } case "list": // Get list of all daemons for current user { var list_resp []fxdocker.FxDaemon request_error := lib.PostJson(fmt.Sprintf("%s/daemon/list", fxdocker.FlaxtonContainerRepo), []byte("{}"), &list_resp, console_config.Authorization) if request_error != nil { fmt.Println("Response Error: ", request_error.Error()) os.Exit(1) } fmt.Println("List of Daemons") for _, d := range list_resp { fmt.Println(d.ID, " ", d.Name) } os.Exit(1) } case "pause-container": { daemon_name := next_args[i+1] sdn_map := make([]string, 1) sdn_map[0] = next_args[i+2] _, task_err := fxdocker.AddTask(daemon.AuthKey, lib.TaskPauseContainer, daemon_name, sdn_map) if task_err != nil { fmt.Println(task_err) } else { fmt.Println("Task Sent !") } os.Exit(1) } case "set_name": { daemon_name := next_args[i+1] name := next_args[i+2] sdn_map := make(map[string]string) sdn_map["name"] = name _, task_err := fxdocker.AddTask(daemon.AuthKey, lib.TaskSetDaemonName, daemon_name, sdn_map) if task_err != nil { fmt.Println(task_err) } else { fmt.Println("Task Sent !") } os.Exit(1) } case "help", "-h", "-help": { fmt.Println("This command is for Starting Flaxton daemon load balancer and daemon API server") fmt.Println("Formant: flaxton daemon [COMMAND] <OPTIONS>") fmt.Println("COMMAND:") fmt.Println("set-name : Set name for daemon, to access with human friendly names") fmt.Println("list : List of daemon servers for current logged in user") fmt.Println("map-image : Map image to balancer port for specific daemon: <balancer_name,id> <balancing_port> <image_name> <image_port>") fmt.Println("stop-port : Stop balancing port for specific daemon: <balancer_name,id> <balancing port to stop>") fmt.Println("OPTIONS:") fmt.Println("-balancer : Options should be followed by this direction - local_port image_name image_port") fmt.Println("-child : Add chaild server with this combination: [balancing port] [ip address]") fmt.Println("-offline : If this parameter exists, then daemon will be working without flaxton.io server") os.Exit(1) } } } request_error := daemon.Register() if request_error != nil { fmt.Println("Unable to register daemon: ", request_error.Error()) os.Exit(1) } fmt.Println("Starting Flaxton Daemon ", daemon.ID) daemon.Run() } case "-t", "transfer": { if len(console_config.Authorization) == 0 { fmt.Printf("For this operation you need to login using your flaxton.io creditailes") fmt.Printf("flaxton login -u <username> -p <password>") fmt.Printf("Or If you don't have acount please register here https://flaxton.io/register") return } var ( image = "" run_command = "" daemon = "" count = "" cpu_share = "0" mem_set = "0" ) next_args := args[1:] for i, arg := range args[1:] { switch strings.ToLower(arg) { case "-img": // Container ID parameter { image = next_args[i+1] } case "-cmd": // Repo Name { run_command = next_args[i+1] } case "-cpu": // Repo Name { cpu_share = next_args[i+1] } case "-mem": // Repo Name { mem_set = next_args[i+1] } case "-daemon": // Destination Host { daemon = next_args[i+1] } case "-count": // Need to run or not { count = next_args[i+1] } case "help", "-h", "-help": { fmt.Println("This command is for transfering container to another Flaxton Daemon") fmt.Println("Formant: flaxton transfer <OPTIONS>") fmt.Println("OPTIONS:") fmt.Println("-img : Docker local image name, id or repository") fmt.Println("-cmd : If you want to start container after transfering, give this parameter as a run command") fmt.Println("-cpu : number for CPU shares based on Docker cpu-share parameter") fmt.Println("-mem : container RAM memory amount") fmt.Println("-count : How many containers you want to start after transfering, default: 1") fmt.Println("-daemon : Destionation Daemon Name or ID") os.Exit(1) } } } fxdocker.TransferImage(image, daemon, run_command, cpu_share, mem_set, count, console_config.Authorization) } case "-l", "login": { var ( username = "" password = "" ) next_args := args[1:] for i, arg := range args[1:] { switch strings.ToLower(arg) { case "-u": { username = next_args[i+1] } case "-p": { hasher := md5.New() hasher.Write([]byte(next_args[i+1])) password = hex.EncodeToString(hasher.Sum(nil)) } case "help", "-h", "-help": { fmt.Println("This command is for sign in to flaxton.io service for transfering and using containers on large clusters") fmt.Println("Formant: flaxton login <OPTIONS>") fmt.Println("OPTIONS:") fmt.Println("-u : Username for Flaxton") fmt.Println("-p : Password for Flaxton") os.Exit(1) } } } console_config.Authorization = fxdocker.FlaxtonConsoleLogin(username, password) console_config.Username = username console_config.SaveConfig() fmt.Println("Login Successful !") } } }