github.com/rsampaio/docker@v0.7.2-0.20150827203920-fdc73cc3fc31/integration-cli/docker_cli_start_volume_driver_unix_test.go (about) 1 // +build !windows 2 3 package main 4 5 import ( 6 "encoding/json" 7 "fmt" 8 "io/ioutil" 9 "net/http" 10 "net/http/httptest" 11 "os" 12 "path/filepath" 13 "strings" 14 15 "github.com/go-check/check" 16 ) 17 18 func init() { 19 check.Suite(&DockerExternalVolumeSuite{ 20 ds: &DockerSuite{}, 21 }) 22 } 23 24 type eventCounter struct { 25 activations int 26 creations int 27 removals int 28 mounts int 29 unmounts int 30 paths int 31 } 32 33 type DockerExternalVolumeSuite struct { 34 server *httptest.Server 35 ds *DockerSuite 36 d *Daemon 37 ec *eventCounter 38 } 39 40 func (s *DockerExternalVolumeSuite) SetUpTest(c *check.C) { 41 s.d = NewDaemon(c) 42 s.ec = &eventCounter{} 43 } 44 45 func (s *DockerExternalVolumeSuite) TearDownTest(c *check.C) { 46 s.d.Stop() 47 s.ds.TearDownTest(c) 48 } 49 50 func (s *DockerExternalVolumeSuite) SetUpSuite(c *check.C) { 51 mux := http.NewServeMux() 52 s.server = httptest.NewServer(mux) 53 54 type pluginRequest struct { 55 name string 56 } 57 58 mux.HandleFunc("/Plugin.Activate", func(w http.ResponseWriter, r *http.Request) { 59 s.ec.activations++ 60 61 w.Header().Set("Content-Type", "application/vnd.docker.plugins.v1+json") 62 fmt.Fprintln(w, `{"Implements": ["VolumeDriver"]}`) 63 }) 64 65 mux.HandleFunc("/VolumeDriver.Create", func(w http.ResponseWriter, r *http.Request) { 66 s.ec.creations++ 67 68 w.Header().Set("Content-Type", "application/vnd.docker.plugins.v1+json") 69 fmt.Fprintln(w, `{}`) 70 }) 71 72 mux.HandleFunc("/VolumeDriver.Remove", func(w http.ResponseWriter, r *http.Request) { 73 s.ec.removals++ 74 75 w.Header().Set("Content-Type", "application/vnd.docker.plugins.v1+json") 76 fmt.Fprintln(w, `{}`) 77 }) 78 79 mux.HandleFunc("/VolumeDriver.Path", func(w http.ResponseWriter, r *http.Request) { 80 s.ec.paths++ 81 82 var pr pluginRequest 83 if err := json.NewDecoder(r.Body).Decode(&pr); err != nil { 84 http.Error(w, err.Error(), 500) 85 } 86 87 p := hostVolumePath(pr.name) 88 89 w.Header().Set("Content-Type", "application/vnd.docker.plugins.v1+json") 90 fmt.Fprintln(w, fmt.Sprintf("{\"Mountpoint\": \"%s\"}", p)) 91 }) 92 93 mux.HandleFunc("/VolumeDriver.Mount", func(w http.ResponseWriter, r *http.Request) { 94 s.ec.mounts++ 95 96 var pr pluginRequest 97 if err := json.NewDecoder(r.Body).Decode(&pr); err != nil { 98 http.Error(w, err.Error(), 500) 99 } 100 101 p := hostVolumePath(pr.name) 102 if err := os.MkdirAll(p, 0755); err != nil { 103 http.Error(w, err.Error(), 500) 104 } 105 106 if err := ioutil.WriteFile(filepath.Join(p, "test"), []byte(s.server.URL), 0644); err != nil { 107 http.Error(w, err.Error(), 500) 108 } 109 110 w.Header().Set("Content-Type", "application/vnd.docker.plugins.v1+json") 111 fmt.Fprintln(w, fmt.Sprintf("{\"Mountpoint\": \"%s\"}", p)) 112 }) 113 114 mux.HandleFunc("/VolumeDriver.Unmount", func(w http.ResponseWriter, r *http.Request) { 115 s.ec.unmounts++ 116 117 var pr pluginRequest 118 if err := json.NewDecoder(r.Body).Decode(&pr); err != nil { 119 http.Error(w, err.Error(), 500) 120 } 121 122 w.Header().Set("Content-Type", "application/vnd.docker.plugins.v1+json") 123 fmt.Fprintln(w, `{}`) 124 }) 125 126 if err := os.MkdirAll("/etc/docker/plugins", 0755); err != nil { 127 c.Fatal(err) 128 } 129 130 if err := ioutil.WriteFile("/etc/docker/plugins/test-external-volume-driver.spec", []byte(s.server.URL), 0644); err != nil { 131 c.Fatal(err) 132 } 133 } 134 135 func (s *DockerExternalVolumeSuite) TearDownSuite(c *check.C) { 136 s.server.Close() 137 138 if err := os.RemoveAll("/etc/docker/plugins"); err != nil { 139 c.Fatal(err) 140 } 141 } 142 143 func (s *DockerExternalVolumeSuite) TestStartExternalNamedVolumeDriver(c *check.C) { 144 if err := s.d.StartWithBusybox(); err != nil { 145 c.Fatal(err) 146 } 147 148 out, err := s.d.Cmd("run", "--rm", "--name", "test-data", "-v", "external-volume-test:/tmp/external-volume-test", "--volume-driver", "test-external-volume-driver", "busybox:latest", "cat", "/tmp/external-volume-test/test") 149 if err != nil { 150 c.Fatal(out, err) 151 } 152 153 if !strings.Contains(out, s.server.URL) { 154 c.Fatalf("External volume mount failed. Output: %s\n", out) 155 } 156 157 p := hostVolumePath("external-volume-test") 158 _, err = os.Lstat(p) 159 if err == nil { 160 c.Fatalf("Expected error checking volume path in host: %s\n", p) 161 } 162 163 if !os.IsNotExist(err) { 164 c.Fatalf("Expected volume path in host to not exist: %s, %v\n", p, err) 165 } 166 167 c.Assert(s.ec.activations, check.Equals, 1) 168 c.Assert(s.ec.creations, check.Equals, 1) 169 c.Assert(s.ec.removals, check.Equals, 1) 170 c.Assert(s.ec.mounts, check.Equals, 1) 171 c.Assert(s.ec.unmounts, check.Equals, 1) 172 } 173 174 func (s *DockerExternalVolumeSuite) TestStartExternalVolumeUnnamedDriver(c *check.C) { 175 if err := s.d.StartWithBusybox(); err != nil { 176 c.Fatal(err) 177 } 178 179 out, err := s.d.Cmd("run", "--rm", "--name", "test-data", "-v", "/tmp/external-volume-test", "--volume-driver", "test-external-volume-driver", "busybox:latest", "cat", "/tmp/external-volume-test/test") 180 if err != nil { 181 c.Fatal(err) 182 } 183 184 if !strings.Contains(out, s.server.URL) { 185 c.Fatalf("External volume mount failed. Output: %s\n", out) 186 } 187 188 c.Assert(s.ec.activations, check.Equals, 1) 189 c.Assert(s.ec.creations, check.Equals, 1) 190 c.Assert(s.ec.removals, check.Equals, 1) 191 c.Assert(s.ec.mounts, check.Equals, 1) 192 c.Assert(s.ec.unmounts, check.Equals, 1) 193 } 194 195 func (s DockerExternalVolumeSuite) TestStartExternalVolumeDriverVolumesFrom(c *check.C) { 196 if err := s.d.StartWithBusybox(); err != nil { 197 c.Fatal(err) 198 } 199 200 out, err := s.d.Cmd("run", "-d", "--name", "vol-test1", "-v", "/foo", "--volume-driver", "test-external-volume-driver", "busybox:latest") 201 c.Assert(err, check.IsNil, check.Commentf(out)) 202 203 out, err = s.d.Cmd("run", "--rm", "--volumes-from", "vol-test1", "--name", "vol-test2", "busybox", "ls", "/tmp") 204 c.Assert(err, check.IsNil, check.Commentf(out)) 205 206 out, err = s.d.Cmd("rm", "-fv", "vol-test1") 207 c.Assert(err, check.IsNil, check.Commentf(out)) 208 209 c.Assert(s.ec.activations, check.Equals, 1) 210 c.Assert(s.ec.creations, check.Equals, 1) 211 c.Assert(s.ec.removals, check.Equals, 1) 212 c.Assert(s.ec.mounts, check.Equals, 2) 213 c.Assert(s.ec.unmounts, check.Equals, 2) 214 } 215 216 func (s DockerExternalVolumeSuite) TestStartExternalVolumeDriverDeleteContainer(c *check.C) { 217 if err := s.d.StartWithBusybox(); err != nil { 218 c.Fatal(err) 219 } 220 221 if out, err := s.d.Cmd("run", "-d", "--name", "vol-test1", "-v", "/foo", "--volume-driver", "test-external-volume-driver", "busybox:latest"); err != nil { 222 c.Fatal(out, err) 223 } 224 225 if out, err := s.d.Cmd("rm", "-fv", "vol-test1"); err != nil { 226 c.Fatal(out, err) 227 } 228 229 c.Assert(s.ec.activations, check.Equals, 1) 230 c.Assert(s.ec.creations, check.Equals, 1) 231 c.Assert(s.ec.removals, check.Equals, 1) 232 c.Assert(s.ec.mounts, check.Equals, 1) 233 c.Assert(s.ec.unmounts, check.Equals, 1) 234 } 235 236 func hostVolumePath(name string) string { 237 return fmt.Sprintf("/var/lib/docker/volumes/%s", name) 238 } 239 240 func (s *DockerExternalVolumeSuite) TestStartExternalNamedVolumeDriverCheckBindLocalVolume(c *check.C) { 241 if err := s.d.StartWithBusybox(); err != nil { 242 c.Fatal(err) 243 } 244 245 expected := s.server.URL 246 247 dockerfile := fmt.Sprintf(`FROM busybox:latest 248 RUN mkdir /nobindthenlocalvol 249 RUN echo %s > /nobindthenlocalvol/test 250 VOLUME ["/nobindthenlocalvol"]`, expected) 251 252 img := "test-checkbindlocalvolume" 253 254 args := []string{"--host", s.d.sock()} 255 buildOut, err := buildImageArgs(args, img, dockerfile, true) 256 fmt.Println(buildOut) 257 258 out, err := s.d.Cmd("run", "--rm", "--name", "test-data-nobind", "-v", "external-volume-test:/tmp/external-volume-test", "--volume-driver", "test-external-volume-driver", img, "cat", "/nobindthenlocalvol/test") 259 if err != nil { 260 fmt.Println(out) 261 c.Fatal(err) 262 } 263 264 if !strings.Contains(out, expected) { 265 c.Fatalf("External volume mount failed. Output: %s\n", out) 266 } 267 268 c.Assert(s.ec.activations, check.Equals, 1) 269 c.Assert(s.ec.creations, check.Equals, 1) 270 c.Assert(s.ec.removals, check.Equals, 1) 271 c.Assert(s.ec.mounts, check.Equals, 1) 272 c.Assert(s.ec.unmounts, check.Equals, 1) 273 }