Browse code

Merge pull request #10986 from crosbymichael/create-api-type

Create api types package for structured responses

Jessie Frazelle authored on 2015/03/03 05:22:02
Showing 7 changed files
... ...
@@ -26,7 +26,7 @@ import (
26 26
 
27 27
 	log "github.com/Sirupsen/logrus"
28 28
 	"github.com/docker/docker/api"
29
-	"github.com/docker/docker/api/stats"
29
+	"github.com/docker/docker/api/types"
30 30
 	"github.com/docker/docker/autogen/dockerversion"
31 31
 	"github.com/docker/docker/engine"
32 32
 	"github.com/docker/docker/graph"
... ...
@@ -2133,7 +2133,7 @@ func (cid *cidFile) Write(id string) error {
2133 2133
 	return nil
2134 2134
 }
2135 2135
 
2136
-func (cli *DockerCli) createContainer(config *runconfig.Config, hostConfig *runconfig.HostConfig, cidfile, name string) (engine.Env, error) {
2136
+func (cli *DockerCli) createContainer(config *runconfig.Config, hostConfig *runconfig.HostConfig, cidfile, name string) (*types.ContainerCreateResponse, error) {
2137 2137
 	containerValues := url.Values{}
2138 2138
 	if name != "" {
2139 2139
 		containerValues.Set("name", name)
... ...
@@ -2172,23 +2172,19 @@ func (cli *DockerCli) createContainer(config *runconfig.Config, hostConfig *runc
2172 2172
 		return nil, err
2173 2173
 	}
2174 2174
 
2175
-	var result engine.Env
2176
-	if err := result.Decode(stream); err != nil {
2175
+	var response types.ContainerCreateResponse
2176
+	if err := json.NewDecoder(stream).Decode(&response); err != nil {
2177 2177
 		return nil, err
2178 2178
 	}
2179
-
2180
-	for _, warning := range result.GetList("Warnings") {
2179
+	for _, warning := range response.Warnings {
2181 2180
 		fmt.Fprintf(cli.err, "WARNING: %s\n", warning)
2182 2181
 	}
2183
-
2184 2182
 	if containerIDFile != nil {
2185
-		if err = containerIDFile.Write(result.Get("Id")); err != nil {
2183
+		if err = containerIDFile.Write(response.ID); err != nil {
2186 2184
 			return nil, err
2187 2185
 		}
2188 2186
 	}
2189
-
2190
-	return result, nil
2191
-
2187
+	return &response, nil
2192 2188
 }
2193 2189
 
2194 2190
 func (cli *DockerCli) CmdCreate(args ...string) error {
... ...
@@ -2207,14 +2203,11 @@ func (cli *DockerCli) CmdCreate(args ...string) error {
2207 2207
 		cmd.Usage()
2208 2208
 		return nil
2209 2209
 	}
2210
-
2211
-	createResult, err := cli.createContainer(config, hostConfig, hostConfig.ContainerIDFile, *flName)
2210
+	response, err := cli.createContainer(config, hostConfig, hostConfig.ContainerIDFile, *flName)
2212 2211
 	if err != nil {
2213 2212
 		return err
2214 2213
 	}
2215
-
2216
-	fmt.Fprintf(cli.out, "%s\n", createResult.Get("Id"))
2217
-
2214
+	fmt.Fprintf(cli.out, "%s\n", response.ID)
2218 2215
 	return nil
2219 2216
 }
2220 2217
 
... ...
@@ -2272,38 +2265,32 @@ func (cli *DockerCli) CmdRun(args ...string) error {
2272 2272
 		sigProxy = false
2273 2273
 	}
2274 2274
 
2275
-	runResult, err := cli.createContainer(config, hostConfig, hostConfig.ContainerIDFile, *flName)
2275
+	createResponse, err := cli.createContainer(config, hostConfig, hostConfig.ContainerIDFile, *flName)
2276 2276
 	if err != nil {
2277 2277
 		return err
2278 2278
 	}
2279
-
2280 2279
 	if sigProxy {
2281
-		sigc := cli.forwardAllSignals(runResult.Get("Id"))
2280
+		sigc := cli.forwardAllSignals(createResponse.ID)
2282 2281
 		defer signal.StopCatch(sigc)
2283 2282
 	}
2284
-
2285 2283
 	var (
2286 2284
 		waitDisplayId chan struct{}
2287 2285
 		errCh         chan error
2288 2286
 	)
2289
-
2290 2287
 	if !config.AttachStdout && !config.AttachStderr {
2291 2288
 		// Make this asynchronous to allow the client to write to stdin before having to read the ID
2292 2289
 		waitDisplayId = make(chan struct{})
2293 2290
 		go func() {
2294 2291
 			defer close(waitDisplayId)
2295
-			fmt.Fprintf(cli.out, "%s\n", runResult.Get("Id"))
2292
+			fmt.Fprintf(cli.out, "%s\n", createResponse.ID)
2296 2293
 		}()
2297 2294
 	}
2298
-
2299 2295
 	if *flAutoRemove && (hostConfig.RestartPolicy.Name == "always" || hostConfig.RestartPolicy.Name == "on-failure") {
2300 2296
 		return ErrConflictRestartPolicyAndAutoRemove
2301 2297
 	}
2302
-
2303 2298
 	// We need to instantiate the chan because the select needs it. It can
2304 2299
 	// be closed but can't be uninitialized.
2305 2300
 	hijacked := make(chan io.Closer)
2306
-
2307 2301
 	// Block the return until the chan gets closed
2308 2302
 	defer func() {
2309 2303
 		log.Debugf("End of CmdRun(), Waiting for hijack to finish.")
... ...
@@ -2311,7 +2298,6 @@ func (cli *DockerCli) CmdRun(args ...string) error {
2311 2311
 			log.Errorf("Hijack did not finish (chan still open)")
2312 2312
 		}
2313 2313
 	}()
2314
-
2315 2314
 	if config.AttachStdin || config.AttachStdout || config.AttachStderr {
2316 2315
 		var (
2317 2316
 			out, stderr io.Writer
... ...
@@ -2319,7 +2305,6 @@ func (cli *DockerCli) CmdRun(args ...string) error {
2319 2319
 			v           = url.Values{}
2320 2320
 		)
2321 2321
 		v.Set("stream", "1")
2322
-
2323 2322
 		if config.AttachStdin {
2324 2323
 			v.Set("stdin", "1")
2325 2324
 			in = cli.in
... ...
@@ -2336,14 +2321,12 @@ func (cli *DockerCli) CmdRun(args ...string) error {
2336 2336
 				stderr = cli.err
2337 2337
 			}
2338 2338
 		}
2339
-
2340 2339
 		errCh = promise.Go(func() error {
2341
-			return cli.hijack("POST", "/containers/"+runResult.Get("Id")+"/attach?"+v.Encode(), config.Tty, in, out, stderr, hijacked, nil)
2340
+			return cli.hijack("POST", "/containers/"+createResponse.ID+"/attach?"+v.Encode(), config.Tty, in, out, stderr, hijacked, nil)
2342 2341
 		})
2343 2342
 	} else {
2344 2343
 		close(hijacked)
2345 2344
 	}
2346
-
2347 2345
 	// Acknowledge the hijack before starting
2348 2346
 	select {
2349 2347
 	case closer := <-hijacked:
... ...
@@ -2360,12 +2343,12 @@ func (cli *DockerCli) CmdRun(args ...string) error {
2360 2360
 	}
2361 2361
 
2362 2362
 	//start the container
2363
-	if _, _, err = readBody(cli.call("POST", "/containers/"+runResult.Get("Id")+"/start", nil, false)); err != nil {
2363
+	if _, _, err = readBody(cli.call("POST", "/containers/"+createResponse.ID+"/start", nil, false)); err != nil {
2364 2364
 		return err
2365 2365
 	}
2366 2366
 
2367 2367
 	if (config.AttachStdin || config.AttachStdout || config.AttachStderr) && config.Tty && cli.isTerminalOut {
2368
-		if err := cli.monitorTtySize(runResult.Get("Id"), false); err != nil {
2368
+		if err := cli.monitorTtySize(createResponse.ID, false); err != nil {
2369 2369
 			log.Errorf("Error monitoring TTY size: %s", err)
2370 2370
 		}
2371 2371
 	}
... ...
@@ -2390,26 +2373,26 @@ func (cli *DockerCli) CmdRun(args ...string) error {
2390 2390
 	if *flAutoRemove {
2391 2391
 		// Autoremove: wait for the container to finish, retrieve
2392 2392
 		// the exit code and remove the container
2393
-		if _, _, err := readBody(cli.call("POST", "/containers/"+runResult.Get("Id")+"/wait", nil, false)); err != nil {
2393
+		if _, _, err := readBody(cli.call("POST", "/containers/"+createResponse.ID+"/wait", nil, false)); err != nil {
2394 2394
 			return err
2395 2395
 		}
2396
-		if _, status, err = getExitCode(cli, runResult.Get("Id")); err != nil {
2396
+		if _, status, err = getExitCode(cli, createResponse.ID); err != nil {
2397 2397
 			return err
2398 2398
 		}
2399
-		if _, _, err := readBody(cli.call("DELETE", "/containers/"+runResult.Get("Id")+"?v=1", nil, false)); err != nil {
2399
+		if _, _, err := readBody(cli.call("DELETE", "/containers/"+createResponse.ID+"?v=1", nil, false)); err != nil {
2400 2400
 			return err
2401 2401
 		}
2402 2402
 	} else {
2403 2403
 		// No Autoremove: Simply retrieve the exit code
2404 2404
 		if !config.Tty {
2405 2405
 			// In non-TTY mode, we can't detach, so we must wait for container exit
2406
-			if status, err = waitForExit(cli, runResult.Get("Id")); err != nil {
2406
+			if status, err = waitForExit(cli, createResponse.ID); err != nil {
2407 2407
 				return err
2408 2408
 			}
2409 2409
 		} else {
2410 2410
 			// In TTY mode, there is a race: if the process dies too slowly, the state could
2411 2411
 			// be updated after the getExitCode call and result in the wrong exit code being reported
2412
-			if _, status, err = getExitCode(cli, runResult.Get("Id")); err != nil {
2412
+			if _, status, err = getExitCode(cli, createResponse.ID); err != nil {
2413 2413
 				return err
2414 2414
 			}
2415 2415
 		}
... ...
@@ -2653,7 +2636,7 @@ func (s *containerStats) Collect(cli *DockerCli) {
2653 2653
 	)
2654 2654
 	go func() {
2655 2655
 		for {
2656
-			var v *stats.Stats
2656
+			var v *types.Stats
2657 2657
 			if err := dec.Decode(&v); err != nil {
2658 2658
 				u <- err
2659 2659
 				return
... ...
@@ -2770,7 +2753,7 @@ func (cli *DockerCli) CmdStats(args ...string) error {
2770 2770
 	return nil
2771 2771
 }
2772 2772
 
2773
-func calculateCpuPercent(previousCpu, previousSystem uint64, v *stats.Stats) float64 {
2773
+func calculateCpuPercent(previousCpu, previousSystem uint64, v *types.Stats) float64 {
2774 2774
 	var (
2775 2775
 		cpuPercent = 0.0
2776 2776
 		// calculate the change for the cpu usage of the container in between readings
... ...
@@ -27,6 +27,7 @@ import (
27 27
 
28 28
 	log "github.com/Sirupsen/logrus"
29 29
 	"github.com/docker/docker/api"
30
+	"github.com/docker/docker/api/types"
30 31
 	"github.com/docker/docker/daemon/networkdriver/portallocator"
31 32
 	"github.com/docker/docker/engine"
32 33
 	"github.com/docker/docker/pkg/listenbuffer"
... ...
@@ -140,12 +141,22 @@ func httpError(w http.ResponseWriter, err error) {
140 140
 	}
141 141
 }
142 142
 
143
-func writeJSON(w http.ResponseWriter, code int, v engine.Env) error {
143
+// writeJSONEnv writes the engine.Env values to the http response stream as a
144
+// json encoded body.
145
+func writeJSONEnv(w http.ResponseWriter, code int, v engine.Env) error {
144 146
 	w.Header().Set("Content-Type", "application/json")
145 147
 	w.WriteHeader(code)
146 148
 	return v.Encode(w)
147 149
 }
148 150
 
151
+// writeJSON writes the value v to the http response stream as json with standard
152
+// json encoding.
153
+func writeJSON(w http.ResponseWriter, code int, v interface{}) error {
154
+	w.Header().Set("Content-Type", "application/json")
155
+	w.WriteHeader(code)
156
+	return json.NewEncoder(w).Encode(v)
157
+}
158
+
149 159
 func streamJSON(job *engine.Job, w http.ResponseWriter, flush bool) {
150 160
 	w.Header().Set("Content-Type", "application/json")
151 161
 	if flush {
... ...
@@ -183,7 +194,7 @@ func postAuth(eng *engine.Engine, version version.Version, w http.ResponseWriter
183 183
 	if status := engine.Tail(stdoutBuffer, 1); status != "" {
184 184
 		var env engine.Env
185 185
 		env.Set("Status", status)
186
-		return writeJSON(w, http.StatusOK, env)
186
+		return writeJSONEnv(w, http.StatusOK, env)
187 187
 	}
188 188
 	w.WriteHeader(http.StatusNoContent)
189 189
 	return nil
... ...
@@ -526,7 +537,7 @@ func postCommit(eng *engine.Engine, version version.Version, w http.ResponseWrit
526 526
 		return err
527 527
 	}
528 528
 	env.Set("Id", engine.Tail(stdoutBuffer, 1))
529
-	return writeJSON(w, http.StatusCreated, env)
529
+	return writeJSONEnv(w, http.StatusCreated, env)
530 530
 }
531 531
 
532 532
 // Creates an image from Pull or from Import
... ...
@@ -705,18 +716,16 @@ func postContainersCreate(eng *engine.Engine, version version.Version, w http.Re
705 705
 	if err := parseForm(r); err != nil {
706 706
 		return nil
707 707
 	}
708
+	if err := checkForJson(r); err != nil {
709
+		return err
710
+	}
708 711
 	var (
709
-		out          engine.Env
710 712
 		job          = eng.Job("create", r.Form.Get("name"))
711 713
 		outWarnings  []string
712 714
 		stdoutBuffer = bytes.NewBuffer(nil)
713 715
 		warnings     = bytes.NewBuffer(nil)
714 716
 	)
715 717
 
716
-	if err := checkForJson(r); err != nil {
717
-		return err
718
-	}
719
-
720 718
 	if err := job.DecodeEnv(r.Body); err != nil {
721 719
 		return err
722 720
 	}
... ...
@@ -732,10 +741,10 @@ func postContainersCreate(eng *engine.Engine, version version.Version, w http.Re
732 732
 	for scanner.Scan() {
733 733
 		outWarnings = append(outWarnings, scanner.Text())
734 734
 	}
735
-	out.Set("Id", engine.Tail(stdoutBuffer, 1))
736
-	out.SetList("Warnings", outWarnings)
737
-
738
-	return writeJSON(w, http.StatusCreated, out)
735
+	return writeJSON(w, http.StatusCreated, &types.ContainerCreateResponse{
736
+		ID:       engine.Tail(stdoutBuffer, 1),
737
+		Warnings: outWarnings,
738
+	})
739 739
 }
740 740
 
741 741
 func postContainersRestart(eng *engine.Engine, version version.Version, w http.ResponseWriter, r *http.Request, vars map[string]string) error {
... ...
@@ -878,7 +887,7 @@ func postContainersWait(eng *engine.Engine, version version.Version, w http.Resp
878 878
 	}
879 879
 
880 880
 	env.Set("StatusCode", engine.Tail(stdoutBuffer, 1))
881
-	return writeJSON(w, http.StatusOK, env)
881
+	return writeJSONEnv(w, http.StatusOK, env)
882 882
 }
883 883
 
884 884
 func postContainersResize(eng *engine.Engine, version version.Version, w http.ResponseWriter, r *http.Request, vars map[string]string) error {
... ...
@@ -1149,7 +1158,7 @@ func postContainerExecCreate(eng *engine.Engine, version version.Version, w http
1149 1149
 	// Return the ID
1150 1150
 	out.Set("Id", engine.Tail(stdoutBuffer, 1))
1151 1151
 
1152
-	return writeJSON(w, http.StatusCreated, out)
1152
+	return writeJSONEnv(w, http.StatusCreated, out)
1153 1153
 }
1154 1154
 
1155 1155
 // TODO(vishh): Refactor the code to avoid having to specify stream config as part of both create and start.
1156 1156
deleted file mode 100644
... ...
@@ -1,87 +0,0 @@
1
-// This package is used for API stability in the types and response to the
2
-// consumers of the API stats endpoint.
3
-package stats
4
-
5
-import "time"
6
-
7
-type ThrottlingData struct {
8
-	// Number of periods with throttling active
9
-	Periods uint64 `json:"periods"`
10
-	// Number of periods when the container hit its throttling limit.
11
-	ThrottledPeriods uint64 `json:"throttled_periods"`
12
-	// Aggregate time the container was throttled for in nanoseconds.
13
-	ThrottledTime uint64 `json:"throttled_time"`
14
-}
15
-
16
-// All CPU stats are aggregated since container inception.
17
-type CpuUsage struct {
18
-	// Total CPU time consumed.
19
-	// Units: nanoseconds.
20
-	TotalUsage uint64 `json:"total_usage"`
21
-	// Total CPU time consumed per core.
22
-	// Units: nanoseconds.
23
-	PercpuUsage []uint64 `json:"percpu_usage"`
24
-	// Time spent by tasks of the cgroup in kernel mode.
25
-	// Units: nanoseconds.
26
-	UsageInKernelmode uint64 `json:"usage_in_kernelmode"`
27
-	// Time spent by tasks of the cgroup in user mode.
28
-	// Units: nanoseconds.
29
-	UsageInUsermode uint64 `json:"usage_in_usermode"`
30
-}
31
-
32
-type CpuStats struct {
33
-	CpuUsage       CpuUsage       `json:"cpu_usage"`
34
-	SystemUsage    uint64         `json:"system_cpu_usage"`
35
-	ThrottlingData ThrottlingData `json:"throttling_data,omitempty"`
36
-}
37
-
38
-type MemoryStats struct {
39
-	// current res_counter usage for memory
40
-	Usage uint64 `json:"usage"`
41
-	// maximum usage ever recorded.
42
-	MaxUsage uint64 `json:"max_usage"`
43
-	// TODO(vishh): Export these as stronger types.
44
-	// all the stats exported via memory.stat.
45
-	Stats map[string]uint64 `json:"stats"`
46
-	// number of times memory usage hits limits.
47
-	Failcnt uint64 `json:"failcnt"`
48
-	Limit   uint64 `json:"limit"`
49
-}
50
-
51
-type BlkioStatEntry struct {
52
-	Major uint64 `json:"major"`
53
-	Minor uint64 `json:"minor"`
54
-	Op    string `json:"op"`
55
-	Value uint64 `json:"value"`
56
-}
57
-
58
-type BlkioStats struct {
59
-	// number of bytes tranferred to and from the block device
60
-	IoServiceBytesRecursive []BlkioStatEntry `json:"io_service_bytes_recursive"`
61
-	IoServicedRecursive     []BlkioStatEntry `json:"io_serviced_recursive"`
62
-	IoQueuedRecursive       []BlkioStatEntry `json:"io_queue_recursive"`
63
-	IoServiceTimeRecursive  []BlkioStatEntry `json:"io_service_time_recursive"`
64
-	IoWaitTimeRecursive     []BlkioStatEntry `json:"io_wait_time_recursive"`
65
-	IoMergedRecursive       []BlkioStatEntry `json:"io_merged_recursive"`
66
-	IoTimeRecursive         []BlkioStatEntry `json:"io_time_recursive"`
67
-	SectorsRecursive        []BlkioStatEntry `json:"sectors_recursive"`
68
-}
69
-
70
-type Network struct {
71
-	RxBytes   uint64 `json:"rx_bytes"`
72
-	RxPackets uint64 `json:"rx_packets"`
73
-	RxErrors  uint64 `json:"rx_errors"`
74
-	RxDropped uint64 `json:"rx_dropped"`
75
-	TxBytes   uint64 `json:"tx_bytes"`
76
-	TxPackets uint64 `json:"tx_packets"`
77
-	TxErrors  uint64 `json:"tx_errors"`
78
-	TxDropped uint64 `json:"tx_dropped"`
79
-}
80
-
81
-type Stats struct {
82
-	Read        time.Time   `json:"read"`
83
-	Network     Network     `json:"network,omitempty"`
84
-	CpuStats    CpuStats    `json:"cpu_stats,omitempty"`
85
-	MemoryStats MemoryStats `json:"memory_stats,omitempty"`
86
-	BlkioStats  BlkioStats  `json:"blkio_stats,omitempty"`
87
-}
88 1
new file mode 100644
... ...
@@ -0,0 +1,87 @@
0
+// This package is used for API stability in the types and response to the
1
+// consumers of the API stats endpoint.
2
+package types
3
+
4
+import "time"
5
+
6
+type ThrottlingData struct {
7
+	// Number of periods with throttling active
8
+	Periods uint64 `json:"periods"`
9
+	// Number of periods when the container hit its throttling limit.
10
+	ThrottledPeriods uint64 `json:"throttled_periods"`
11
+	// Aggregate time the container was throttled for in nanoseconds.
12
+	ThrottledTime uint64 `json:"throttled_time"`
13
+}
14
+
15
+// All CPU stats are aggregated since container inception.
16
+type CpuUsage struct {
17
+	// Total CPU time consumed.
18
+	// Units: nanoseconds.
19
+	TotalUsage uint64 `json:"total_usage"`
20
+	// Total CPU time consumed per core.
21
+	// Units: nanoseconds.
22
+	PercpuUsage []uint64 `json:"percpu_usage"`
23
+	// Time spent by tasks of the cgroup in kernel mode.
24
+	// Units: nanoseconds.
25
+	UsageInKernelmode uint64 `json:"usage_in_kernelmode"`
26
+	// Time spent by tasks of the cgroup in user mode.
27
+	// Units: nanoseconds.
28
+	UsageInUsermode uint64 `json:"usage_in_usermode"`
29
+}
30
+
31
+type CpuStats struct {
32
+	CpuUsage       CpuUsage       `json:"cpu_usage"`
33
+	SystemUsage    uint64         `json:"system_cpu_usage"`
34
+	ThrottlingData ThrottlingData `json:"throttling_data,omitempty"`
35
+}
36
+
37
+type MemoryStats struct {
38
+	// current res_counter usage for memory
39
+	Usage uint64 `json:"usage"`
40
+	// maximum usage ever recorded.
41
+	MaxUsage uint64 `json:"max_usage"`
42
+	// TODO(vishh): Export these as stronger types.
43
+	// all the stats exported via memory.stat.
44
+	Stats map[string]uint64 `json:"stats"`
45
+	// number of times memory usage hits limits.
46
+	Failcnt uint64 `json:"failcnt"`
47
+	Limit   uint64 `json:"limit"`
48
+}
49
+
50
+type BlkioStatEntry struct {
51
+	Major uint64 `json:"major"`
52
+	Minor uint64 `json:"minor"`
53
+	Op    string `json:"op"`
54
+	Value uint64 `json:"value"`
55
+}
56
+
57
+type BlkioStats struct {
58
+	// number of bytes tranferred to and from the block device
59
+	IoServiceBytesRecursive []BlkioStatEntry `json:"io_service_bytes_recursive"`
60
+	IoServicedRecursive     []BlkioStatEntry `json:"io_serviced_recursive"`
61
+	IoQueuedRecursive       []BlkioStatEntry `json:"io_queue_recursive"`
62
+	IoServiceTimeRecursive  []BlkioStatEntry `json:"io_service_time_recursive"`
63
+	IoWaitTimeRecursive     []BlkioStatEntry `json:"io_wait_time_recursive"`
64
+	IoMergedRecursive       []BlkioStatEntry `json:"io_merged_recursive"`
65
+	IoTimeRecursive         []BlkioStatEntry `json:"io_time_recursive"`
66
+	SectorsRecursive        []BlkioStatEntry `json:"sectors_recursive"`
67
+}
68
+
69
+type Network struct {
70
+	RxBytes   uint64 `json:"rx_bytes"`
71
+	RxPackets uint64 `json:"rx_packets"`
72
+	RxErrors  uint64 `json:"rx_errors"`
73
+	RxDropped uint64 `json:"rx_dropped"`
74
+	TxBytes   uint64 `json:"tx_bytes"`
75
+	TxPackets uint64 `json:"tx_packets"`
76
+	TxErrors  uint64 `json:"tx_errors"`
77
+	TxDropped uint64 `json:"tx_dropped"`
78
+}
79
+
80
+type Stats struct {
81
+	Read        time.Time   `json:"read"`
82
+	Network     Network     `json:"network,omitempty"`
83
+	CpuStats    CpuStats    `json:"cpu_stats,omitempty"`
84
+	MemoryStats MemoryStats `json:"memory_stats,omitempty"`
85
+	BlkioStats  BlkioStats  `json:"blkio_stats,omitempty"`
86
+}
0 87
new file mode 100644
... ...
@@ -0,0 +1,11 @@
0
+package types
1
+
2
+// ContainerCreateResponse contains the information returned to a client on the
3
+// creation of a new container.
4
+type ContainerCreateResponse struct {
5
+	// ID is the ID of the created container.
6
+	ID string `json:"Id"`
7
+
8
+	// Warnings are any warnings encountered during the creation of the container.
9
+	Warnings []string `json:"Warnings"`
10
+}
... ...
@@ -3,7 +3,7 @@ package daemon
3 3
 import (
4 4
 	"encoding/json"
5 5
 
6
-	"github.com/docker/docker/api/stats"
6
+	"github.com/docker/docker/api/types"
7 7
 	"github.com/docker/docker/daemon/execdriver"
8 8
 	"github.com/docker/docker/engine"
9 9
 	"github.com/docker/libcontainer"
... ...
@@ -33,10 +33,10 @@ func (daemon *Daemon) ContainerStats(job *engine.Job) engine.Status {
33 33
 
34 34
 // convertToAPITypes converts the libcontainer.ContainerStats to the api specific
35 35
 // structs.  This is done to preserve API compatibility and versioning.
36
-func convertToAPITypes(ls *libcontainer.ContainerStats) *stats.Stats {
37
-	s := &stats.Stats{}
36
+func convertToAPITypes(ls *libcontainer.ContainerStats) *types.Stats {
37
+	s := &types.Stats{}
38 38
 	if ls.NetworkStats != nil {
39
-		s.Network = stats.Network{
39
+		s.Network = types.Network{
40 40
 			RxBytes:   ls.NetworkStats.RxBytes,
41 41
 			RxPackets: ls.NetworkStats.RxPackets,
42 42
 			RxErrors:  ls.NetworkStats.RxErrors,
... ...
@@ -49,7 +49,7 @@ func convertToAPITypes(ls *libcontainer.ContainerStats) *stats.Stats {
49 49
 	}
50 50
 	cs := ls.CgroupStats
51 51
 	if cs != nil {
52
-		s.BlkioStats = stats.BlkioStats{
52
+		s.BlkioStats = types.BlkioStats{
53 53
 			IoServiceBytesRecursive: copyBlkioEntry(cs.BlkioStats.IoServiceBytesRecursive),
54 54
 			IoServicedRecursive:     copyBlkioEntry(cs.BlkioStats.IoServicedRecursive),
55 55
 			IoQueuedRecursive:       copyBlkioEntry(cs.BlkioStats.IoQueuedRecursive),
... ...
@@ -60,21 +60,21 @@ func convertToAPITypes(ls *libcontainer.ContainerStats) *stats.Stats {
60 60
 			SectorsRecursive:        copyBlkioEntry(cs.BlkioStats.SectorsRecursive),
61 61
 		}
62 62
 		cpu := cs.CpuStats
63
-		s.CpuStats = stats.CpuStats{
64
-			CpuUsage: stats.CpuUsage{
63
+		s.CpuStats = types.CpuStats{
64
+			CpuUsage: types.CpuUsage{
65 65
 				TotalUsage:        cpu.CpuUsage.TotalUsage,
66 66
 				PercpuUsage:       cpu.CpuUsage.PercpuUsage,
67 67
 				UsageInKernelmode: cpu.CpuUsage.UsageInKernelmode,
68 68
 				UsageInUsermode:   cpu.CpuUsage.UsageInUsermode,
69 69
 			},
70
-			ThrottlingData: stats.ThrottlingData{
70
+			ThrottlingData: types.ThrottlingData{
71 71
 				Periods:          cpu.ThrottlingData.Periods,
72 72
 				ThrottledPeriods: cpu.ThrottlingData.ThrottledPeriods,
73 73
 				ThrottledTime:    cpu.ThrottlingData.ThrottledTime,
74 74
 			},
75 75
 		}
76 76
 		mem := cs.MemoryStats
77
-		s.MemoryStats = stats.MemoryStats{
77
+		s.MemoryStats = types.MemoryStats{
78 78
 			Usage:    mem.Usage,
79 79
 			MaxUsage: mem.MaxUsage,
80 80
 			Stats:    mem.Stats,
... ...
@@ -84,10 +84,10 @@ func convertToAPITypes(ls *libcontainer.ContainerStats) *stats.Stats {
84 84
 	return s
85 85
 }
86 86
 
87
-func copyBlkioEntry(entries []cgroups.BlkioStatEntry) []stats.BlkioStatEntry {
88
-	out := make([]stats.BlkioStatEntry, len(entries))
87
+func copyBlkioEntry(entries []cgroups.BlkioStatEntry) []types.BlkioStatEntry {
88
+	out := make([]types.BlkioStatEntry, len(entries))
89 89
 	for i, re := range entries {
90
-		out[i] = stats.BlkioStatEntry{
90
+		out[i] = types.BlkioStatEntry{
91 91
 			Major: re.Major,
92 92
 			Minor: re.Minor,
93 93
 			Op:    re.Op,
... ...
@@ -9,7 +9,7 @@ import (
9 9
 	"testing"
10 10
 	"time"
11 11
 
12
-	"github.com/docker/docker/api/stats"
12
+	"github.com/docker/docker/api/types"
13 13
 	"github.com/docker/docker/vendor/src/code.google.com/p/go/src/pkg/archive/tar"
14 14
 )
15 15
 
... ...
@@ -311,7 +311,7 @@ func TestGetContainerStats(t *testing.T) {
311 311
 		}
312 312
 
313 313
 		dec := json.NewDecoder(bytes.NewBuffer(sr.body))
314
-		var s *stats.Stats
314
+		var s *types.Stats
315 315
 		// decode only one object from the stream
316 316
 		if err := dec.Decode(&s); err != nil {
317 317
 			t.Fatal(err)