mirror of https://github.com/docker/compose.git
Don't recreate pre-existing volumes.
During the initialize_volumes phase, if a volume using the non-namespaced name already exists, don't create the namespaced equivalent. Signed-off-by: Joffrey F <joffrey@docker.com>
This commit is contained in:
parent
ad8faad296
commit
05935b5e54
|
@ -235,6 +235,12 @@ class Project(object):
|
||||||
def initialize_volumes(self):
|
def initialize_volumes(self):
|
||||||
try:
|
try:
|
||||||
for volume in self.volumes:
|
for volume in self.volumes:
|
||||||
|
if volume.is_user_created:
|
||||||
|
log.info(
|
||||||
|
'Found user-created volume "{0}". No new namespaced '
|
||||||
|
'volume will be created.'.format(volume.name)
|
||||||
|
)
|
||||||
|
continue
|
||||||
volume.create()
|
volume.create()
|
||||||
except NotFound:
|
except NotFound:
|
||||||
raise ConfigurationError(
|
raise ConfigurationError(
|
||||||
|
|
|
@ -1,6 +1,8 @@
|
||||||
from __future__ import absolute_import
|
from __future__ import absolute_import
|
||||||
from __future__ import unicode_literals
|
from __future__ import unicode_literals
|
||||||
|
|
||||||
|
from docker.errors import NotFound
|
||||||
|
|
||||||
|
|
||||||
class Volume(object):
|
class Volume(object):
|
||||||
def __init__(self, client, project, name, driver=None, driver_opts=None):
|
def __init__(self, client, project, name, driver=None, driver_opts=None):
|
||||||
|
@ -21,6 +23,15 @@ class Volume(object):
|
||||||
def inspect(self):
|
def inspect(self):
|
||||||
return self.client.inspect_volume(self.full_name)
|
return self.client.inspect_volume(self.full_name)
|
||||||
|
|
||||||
|
@property
|
||||||
|
def is_user_created(self):
|
||||||
|
try:
|
||||||
|
self.client.inspect_volume(self.name)
|
||||||
|
except NotFound:
|
||||||
|
return False
|
||||||
|
|
||||||
|
return True
|
||||||
|
|
||||||
@property
|
@property
|
||||||
def full_name(self):
|
def full_name(self):
|
||||||
return '{0}_{1}'.format(self.project, self.name)
|
return '{0}_{1}'.format(self.project, self.name)
|
||||||
|
|
|
@ -4,6 +4,7 @@ from __future__ import unicode_literals
|
||||||
import random
|
import random
|
||||||
|
|
||||||
import py
|
import py
|
||||||
|
from docker.errors import NotFound
|
||||||
|
|
||||||
from .testcases import DockerClientTestCase
|
from .testcases import DockerClientTestCase
|
||||||
from compose.config import config
|
from compose.config import config
|
||||||
|
@ -624,7 +625,7 @@ class ProjectTest(DockerClientTestCase):
|
||||||
self.assertEqual(volume_data['Name'], full_vol_name)
|
self.assertEqual(volume_data['Name'], full_vol_name)
|
||||||
self.assertEqual(volume_data['Driver'], 'local')
|
self.assertEqual(volume_data['Driver'], 'local')
|
||||||
|
|
||||||
def test_project_up_invalid_volume_driver(self):
|
def test_initialize_volumes_invalid_volume_driver(self):
|
||||||
vol_name = '{0:x}'.format(random.getrandbits(32))
|
vol_name = '{0:x}'.format(random.getrandbits(32))
|
||||||
|
|
||||||
config_data = config.Config(
|
config_data = config.Config(
|
||||||
|
@ -642,7 +643,7 @@ class ProjectTest(DockerClientTestCase):
|
||||||
with self.assertRaises(config.ConfigurationError):
|
with self.assertRaises(config.ConfigurationError):
|
||||||
project.initialize_volumes()
|
project.initialize_volumes()
|
||||||
|
|
||||||
def test_project_up_updated_driver(self):
|
def test_initialize_volumes_updated_driver(self):
|
||||||
vol_name = '{0:x}'.format(random.getrandbits(32))
|
vol_name = '{0:x}'.format(random.getrandbits(32))
|
||||||
full_vol_name = 'composetest_{0}'.format(vol_name)
|
full_vol_name = 'composetest_{0}'.format(vol_name)
|
||||||
|
|
||||||
|
@ -675,3 +676,24 @@ class ProjectTest(DockerClientTestCase):
|
||||||
assert 'Configuration for volume {0} specifies driver smb'.format(
|
assert 'Configuration for volume {0} specifies driver smb'.format(
|
||||||
vol_name
|
vol_name
|
||||||
) in str(e.exception)
|
) in str(e.exception)
|
||||||
|
|
||||||
|
def test_initialize_volumes_user_created_volumes(self):
|
||||||
|
# Use composetest_ prefix so it gets garbage-collected in tearDown()
|
||||||
|
vol_name = 'composetest_{0:x}'.format(random.getrandbits(32))
|
||||||
|
full_vol_name = 'composetest_{0}'.format(vol_name)
|
||||||
|
self.client.create_volume(vol_name)
|
||||||
|
config_data = config.Config(
|
||||||
|
version=2, services=[{
|
||||||
|
'name': 'web',
|
||||||
|
'image': 'busybox:latest',
|
||||||
|
'command': 'top'
|
||||||
|
}], volumes={vol_name: {'driver': 'local'}}
|
||||||
|
)
|
||||||
|
project = Project.from_config(
|
||||||
|
name='composetest',
|
||||||
|
config_data=config_data, client=self.client
|
||||||
|
)
|
||||||
|
project.initialize_volumes()
|
||||||
|
|
||||||
|
with self.assertRaises(NotFound):
|
||||||
|
self.client.inspect_volume(full_vol_name)
|
||||||
|
|
|
@ -54,3 +54,13 @@ class VolumeTest(DockerClientTestCase):
|
||||||
vol.remove()
|
vol.remove()
|
||||||
volumes = self.client.volumes()['Volumes']
|
volumes = self.client.volumes()['Volumes']
|
||||||
assert len([v for v in volumes if v['Name'] == vol.full_name]) == 0
|
assert len([v for v in volumes if v['Name'] == vol.full_name]) == 0
|
||||||
|
|
||||||
|
def test_is_user_created(self):
|
||||||
|
vol = Volume(self.client, 'composetest', 'uservolume01')
|
||||||
|
try:
|
||||||
|
self.client.create_volume('uservolume01')
|
||||||
|
assert vol.is_user_created is True
|
||||||
|
finally:
|
||||||
|
self.client.remove_volume('uservolume01')
|
||||||
|
vol2 = Volume(self.client, 'composetest', 'volume01')
|
||||||
|
assert vol2.is_user_created is False
|
||||||
|
|
Loading…
Reference in New Issue