Kaynağa Gözat

run now try to pull if unknown image

Victor Vieux 12 yıl önce
ebeveyn
işleme
a48eb4dff8
2 değiştirilmiş dosya ile 78 ekleme ve 46 silme
  1. 64 24
      api.go
  2. 14 22
      commands.go

+ 64 - 24
api.go

@@ -130,7 +130,7 @@ func ListenAndServe(addr string, rtime *Runtime) error {
 
 		var allImages map[string]*Image
 		var err error
-		if All == "true" {
+		if All == "1" {
 			allImages, err = rtime.graph.Map()
 		} else {
 			allImages, err = rtime.graph.Heads()
@@ -152,7 +152,7 @@ func ListenAndServe(addr string, rtime *Runtime) error {
 					continue
 				}
 				delete(allImages, id)
-				if Quiet != "true" {
+				if Quiet != "1" {
 					out.Repository = name
 					out.Tag = tag
 					out.Id = TruncateId(id)
@@ -167,7 +167,7 @@ func ListenAndServe(addr string, rtime *Runtime) error {
 		if NameFilter == "" {
 			for id, image := range allImages {
 				var out ApiImages
-				if Quiet != "true" {
+				if Quiet != "1" {
 					out.Repository = "<none>"
 					out.Tag = "<none>"
 					out.Id = TruncateId(id)
@@ -355,7 +355,7 @@ func ListenAndServe(addr string, rtime *Runtime) error {
 		var outs []ApiContainers
 
 		for i, container := range rtime.List() {
-			if !container.State.Running && All != "true" && n == -1 {
+			if !container.State.Running && All != "1" && n == -1 {
 				continue
 			}
 			if i == n {
@@ -363,9 +363,9 @@ func ListenAndServe(addr string, rtime *Runtime) error {
 			}
 			var out ApiContainers
 			out.Id = container.ShortId()
-			if Quiet != "true" {
+			if Quiet != "1" {
 				command := fmt.Sprintf("%s %s", container.Path, strings.Join(container.Args, " "))
-				if NoTrunc != "true" {
+				if NoTrunc != "1" {
 					command = Trunc(command, 20)
 				}
 				out.Image = rtime.repositories.ImageName(container.Image)
@@ -420,7 +420,7 @@ func ListenAndServe(addr string, rtime *Runtime) error {
 		repo := r.Form.Get("repo")
 		tag := r.Form.Get("tag")
 		var force bool
-		if r.Form.Get("force") == "true" {
+		if r.Form.Get("force") == "1" {
 			force = true
 		}
 
@@ -451,14 +451,14 @@ func ListenAndServe(addr string, rtime *Runtime) error {
 
 		fmt.Fprintln(file, "HTTP/1.1 200 OK\r\nContent-Type: application/json\r\n\r\n")
 		if rtime.graph.LookupRemoteImage(name, rtime.authConfig) {
-			if err := rtime.graph.PullImage(file, name, rtime.authConfig); err != nil {
-				fmt.Fprintln(file, "Error: "+err.Error())
-			}
-			return
-		}
-		if err := rtime.graph.PullRepository(file, name, "", rtime.repositories, rtime.authConfig); err != nil {
-			fmt.Fprintln(file, "Error: "+err.Error())
-		}
+                        if err := rtime.graph.PullImage(file, name, rtime.authConfig); err != nil {
+                                fmt.Fprintln(file, "Error: "+err.Error())
+                        }
+                        return nil
+                }
+                if err := rtime.graph.PullRepository(file, name, "", rtime.repositories, rtime.authConfig); err != nil {
+                        fmt.Fprintln(file, "Error: "+err.Error())
+                }
 	})
 
 	r.Path("/containers").Methods("POST").HandlerFunc(func(w http.ResponseWriter, r *http.Request) {
@@ -488,14 +488,19 @@ func ListenAndServe(addr string, rtime *Runtime) error {
 			// If container not found, try to pull it
 			if rtime.graph.IsNotExist(err) {
 				fmt.Fprintf(file, "Image %s not found, trying to pull it from registry.\r\n", config.Image)
-				//if err = srv.CmdPull(stdin, stdout, config.Image); err != nil {
-				//	fmt.Fprintln(file, "Error: "+err.Error())
-				//	return
-				//}
-				//if container, err = srv.runtime.Create(config); err != nil {
-				//	fmt.Fprintln(file, "Error: "+err.Error())
-				//	return
-				//}
+				if rtime.graph.LookupRemoteImage(name, rtime.authConfig) {
+					if err := rtime.graph.PullImage(file, name, rtime.authConfig); err != nil {
+						fmt.Fprintln(file, "Error: "+err.Error())
+						return
+					}
+				} else  if err := rtime.graph.PullRepository(file, name, "", rtime.repositories, rtime.authConfig); err != nil {
+					fmt.Fprintln(file, "Error: "+err.Error())
+					return
+				}
+				if container, err = rtime.Create(&config); err != nil {
+					fmt.Fprintln(file, "Error: "+err.Error())
+					return
+				}
 			} else {
 				fmt.Fprintln(file, "Error: "+err.Error())
 				return
@@ -532,8 +537,43 @@ func ListenAndServe(addr string, rtime *Runtime) error {
 		}
 		Debugf("Waiting for attach to return\n")
 		<-attachErr
-		// Expecting I/O pipe error, discarding        
+		// Expecting I/O pipe error, discarding
+	})
+
+	r.Path("/containers/{name:.*}/attach").Methods("POST").HandlerFunc(func(w http.ResponseWriter, r *http.Request) {
+		log.Println(r.Method, r.RequestURI)
+		vars := mux.Vars(r)
+		name := vars["name"]
+		if container := rtime.Get(name); container != nil {
+			conn, _, err := w.(http.Hijacker).Hijack()
+			if err != nil {
+				http.Error(w, err.Error(), http.StatusInternalServerError)
+				return
+			}
+			defer conn.Close()
+			file, err := conn.(*net.TCPConn).File()
+			if err != nil {
+				http.Error(w, err.Error(), http.StatusInternalServerError)
+				return
+			}
+			defer file.Close()
 
+			fmt.Fprintln(file, "HTTP/1.1 200 OK\r\nContent-Type: application/json\r\n\r\n")
+			r, w := io.Pipe()
+			go func() {
+				defer w.Close()
+				defer Debugf("Closing buffered stdin pipe")
+				io.Copy(w, file)
+			}()
+			cStdin := r
+
+			<-container.Attach(cStdin, nil, file, file)
+			// Expecting I/O pipe error, discarding                     
+
+		} else {
+			http.Error(w, "No such container: "+name, http.StatusNotFound)
+			return
+		}
 	})
 
 	r.Path("/containers/{name:.*}/restart").Methods("POST").HandlerFunc(func(w http.ResponseWriter, r *http.Request) {

+ 14 - 22
commands.go

@@ -26,6 +26,7 @@ var (
 func ParseCommands(args []string) error {
 
 	cmds := map[string]func(args []string) error{
+		"attach":  CmdAttach,
 		"commit":  CmdCommit,
 		"diff":    CmdDiff,
 		"export":  CmdExport,
@@ -63,7 +64,7 @@ func ParseCommands(args []string) error {
 func cmdHelp(args []string) error {
 	help := "Usage: docker COMMAND [arg...]\n\nA self-sufficient runtime for linux containers.\n\nCommands:\n"
 	for _, cmd := range [][]string{
-		//		{"attach", "Attach to a running container"},
+		{"attach", "Attach to a running container"},
 		{"commit", "Create a new image from a container's changes"},
 		{"diff", "Inspect changes on a container's filesystem"},
 		{"export", "Stream the contents of a container as a tar archive"},
@@ -631,10 +632,10 @@ func CmdImages(args []string) error {
 		v.Set("filter", cmd.Arg(0))
 	}
 	if *quiet {
-		v.Set("quiet", "true")
+		v.Set("quiet", "1")
 	}
 	if *all {
-		v.Set("all", "true")
+		v.Set("all", "1")
 	}
 
 	body, err := call("GET", "/images?"+v.Encode())
@@ -682,13 +683,13 @@ func CmdPs(args []string) error {
 		*last = 1
 	}
 	if *quiet {
-		v.Set("quiet", "true")
+		v.Set("quiet", "1")
 	}
 	if *all {
-		v.Set("all", "true")
+		v.Set("all", "1")
 	}
 	if *noTrunc {
-		v.Set("notrunc", "true")
+		v.Set("notrunc", "1")
 	}
 	if *last != -1 {
 		v.Set("n", strconv.Itoa(*last))
@@ -822,9 +823,8 @@ func CmdLogs(args []string) error {
 	return nil
 }
 
-/*
-func (srv *Server) CmdAttach(stdin io.ReadCloser, stdout rcli.DockerConn, args ...string) error {
-	cmd := rcli.Subcmd(stdout, "attach", "CONTAINER", "Attach to a running container")
+func CmdAttach(args []string) error {
+	cmd := Subcmd("attach", "CONTAINER", "Attach to a running container")
 	if err := cmd.Parse(args); err != nil {
 		return nil
 	}
@@ -832,20 +832,13 @@ func (srv *Server) CmdAttach(stdin io.ReadCloser, stdout rcli.DockerConn, args .
 		cmd.Usage()
 		return nil
 	}
-	name := cmd.Arg(0)
-	container := srv.runtime.Get(name)
-	if container == nil {
-		return fmt.Errorf("No such container: %s", name)
-	}
 
-	if container.Config.Tty {
-		stdout.SetOptionRawTerminal()
+	if err := callStream("POST", "/containers/"+cmd.Arg(0)+"/attach", nil, true); err != nil {
+		return err
 	}
-	// Flush the options to make sure the client sets the raw mode
-	stdout.Flush()
-	return <-container.Attach(stdin, nil, stdout, stdout)
+	return nil
 }
-*/
+
 /*
 // Ports type - Used to parse multiple -p flags
 type ports []int
@@ -921,7 +914,7 @@ func CmdTag(args []string) error {
 	}
 
 	if *force {
-		v.Set("force", "true")
+		v.Set("force", "1")
 	}
 
 	if err := callStream("POST", "/images/"+cmd.Arg(0)+"/tag?"+v.Encode(), nil, false); err != nil {
@@ -931,7 +924,6 @@ func CmdTag(args []string) error {
 }
 
 func CmdRun(args []string) error {
-	fmt.Println("CmdRun")
 	config, cmd, err := ParseRun(args)
 	if err != nil {
 		return err