Allow user to specify custom network aliases

Signed-off-by: Joffrey F <joffrey@docker.com>
This commit is contained in:
Joffrey F 2016-02-12 16:10:36 -08:00 committed by Daniel Nephin
parent d78ea85301
commit 2f7a77e954
6 changed files with 42 additions and 14 deletions

View File

@ -30,6 +30,7 @@ from .types import ServiceLink
from .types import VolumeFromSpec
from .types import VolumeSpec
from .validation import match_named_volumes
from .validation import match_network_aliases
from .validation import validate_against_fields_schema
from .validation import validate_against_service_schema
from .validation import validate_depends_on
@ -535,6 +536,8 @@ def validate_service(service_config, service_names, version):
validate_network_mode(service_config, service_names)
validate_depends_on(service_config, service_names)
match_network_aliases(service_config.config)
if not service_dict.get('image') and has_uppercase(service_name):
raise ConfigurationError(
"Service '{name}' contains uppercase characters which are not valid "

View File

@ -107,9 +107,16 @@
"network_mode": {"type": "string"},
"networks": {
"type": "array",
"items": {"type": "string"},
"uniqueItems": true
"$ref": "#/definitions/list_of_strings"
},
"network_aliases": {
"type": "object",
"patternProperties": {
"^[a-zA-Z0-9._-]+$": {
"$ref": "#/definitions/list_of_strings"
}
},
"additionalProperties": false
},
"pid": {"type": ["string", "null"]},

View File

@ -91,6 +91,19 @@ def match_named_volumes(service_dict, project_volumes):
)
def match_network_aliases(service_dict):
networks = service_dict.get('networks', [])
aliased_networks = service_dict.get('network_aliases', {}).keys()
for n in aliased_networks:
if n not in networks:
raise ConfigurationError(
'Network "{0}" is referenced in network_aliases, but is not'
'declared in the networks list for service "{1}"'.format(
n, service_dict.get('name')
)
)
def validate_top_level_service_objects(filename, service_dicts):
"""Perform some high level validation of the service name and value.

View File

@ -15,7 +15,7 @@ log = logging.getLogger(__name__)
class Network(object):
def __init__(self, client, project, name, driver=None, driver_opts=None,
ipam=None, external_name=None):
ipam=None, external_name=None, aliases=None):
self.client = client
self.project = project
self.name = name
@ -23,6 +23,7 @@ class Network(object):
self.driver_opts = driver_opts
self.ipam = create_ipam_config_from_dict(ipam)
self.external_name = external_name
self.aliases = aliases or []
def ensure(self):
if self.external_name:
@ -166,14 +167,18 @@ def get_network_names_for_service(service_dict):
def get_networks(service_dict, network_definitions):
networks = []
networks = {}
aliases = service_dict.get('network_aliases', {})
for name in get_network_names_for_service(service_dict):
log.debug(name)
network = network_definitions.get(name)
if network:
networks.append(network.full_name)
log.debug(aliases)
networks[network.full_name] = aliases.get(name, [])
else:
raise ConfigurationError(
'Service "{}" uses an undefined network "{}"'
.format(service_dict['name'], name))
log.debug(networks)
return networks

View File

@ -69,11 +69,11 @@ class Project(object):
if use_networking:
service_networks = get_networks(service_dict, networks)
else:
service_networks = []
service_networks = {}
service_dict.pop('networks', None)
links = project.get_links(service_dict)
network_mode = project.get_network_mode(service_dict, service_networks)
network_mode = project.get_network_mode(service_dict, service_networks.keys())
volumes_from = get_volumes_from(project, service_dict)
if config_data.version != V1:

View File

@ -123,7 +123,7 @@ class Service(object):
self.links = links or []
self.volumes_from = volumes_from or []
self.network_mode = network_mode or NetworkMode(None)
self.networks = networks or []
self.networks = networks or {}
self.options = options
def containers(self, stopped=False, one_off=False, filters={}):
@ -431,14 +431,14 @@ class Service(object):
def connect_container_to_networks(self, container):
connected_networks = container.get('NetworkSettings.Networks')
for network in self.networks:
for network, aliases in self.networks.items():
if network in connected_networks:
self.client.disconnect_container_from_network(
container.id, network)
self.client.connect_container_to_network(
container.id, network,
aliases=self._get_aliases(container),
aliases=list(self._get_aliases(container).union(aliases)),
links=self._get_links(False),
)
@ -472,7 +472,7 @@ class Service(object):
'image_id': self.image()['Id'],
'links': self.get_link_names(),
'net': self.network_mode.id,
'networks': self.networks,
'networks': self.networks.keys(),
'volumes_from': [
(v.source.name, v.mode)
for v in self.volumes_from if isinstance(v.source, Service)
@ -513,9 +513,9 @@ class Service(object):
def _get_aliases(self, container):
if container.labels.get(LABEL_ONE_OFF) == "True":
return []
return set()
return [self.name, container.short_id]
return set([self.name, container.short_id])
def _get_links(self, link_to_self):
links = {}