Add support for TLS config command-line options

Signed-off-by: Joffrey F <joffrey@docker.com>
This commit is contained in:
Joffrey F 2016-03-15 14:19:25 -07:00
parent 4f5123bda9
commit 1ac33ea7e5
3 changed files with 58 additions and 5 deletions

View File

@ -12,6 +12,7 @@ from .. import config
from ..const import API_VERSIONS
from ..project import Project
from .docker_client import docker_client
from .docker_client import TLSArgs
from .utils import get_version_info
log = logging.getLogger(__name__)
@ -23,6 +24,8 @@ def project_from_options(project_dir, options):
get_config_path_from_options(options),
project_name=options.get('--project-name'),
verbose=options.get('--verbose'),
host=options.get('--host'),
tls_args=TLSArgs.from_options(options),
)
@ -37,8 +40,8 @@ def get_config_path_from_options(options):
return None
def get_client(verbose=False, version=None):
client = docker_client(version=version)
def get_client(verbose=False, version=None, tls_args=None, host=None):
client = docker_client(version=version, tls_args=tls_args, host=host)
if verbose:
version_info = six.iteritems(client.version())
log.info(get_version_info('full'))
@ -49,7 +52,8 @@ def get_client(verbose=False, version=None):
return client
def get_project(project_dir, config_path=None, project_name=None, verbose=False):
def get_project(project_dir, config_path=None, project_name=None, verbose=False,
host=None, tls_args=None):
config_details = config.find(project_dir, config_path)
project_name = get_project_name(config_details.working_dir, project_name)
config_data = config.load(config_details)
@ -57,7 +61,10 @@ def get_project(project_dir, config_path=None, project_name=None, verbose=False)
api_version = os.environ.get(
'COMPOSE_API_VERSION',
API_VERSIONS[config_data.version])
client = get_client(verbose=verbose, version=api_version)
client = get_client(
verbose=verbose, version=api_version, tls_args=tls_args,
host=host
)
return Project.from_config(project_name, config_data, client)

View File

@ -3,9 +3,11 @@ from __future__ import unicode_literals
import logging
import os
from collections import namedtuple
from docker import Client
from docker.errors import TLSParameterError
from docker.tls import TLSConfig
from docker.utils import kwargs_from_env
from ..const import HTTP_TIMEOUT
@ -14,7 +16,24 @@ from .errors import UserError
log = logging.getLogger(__name__)
def docker_client(version=None):
class TLSArgs(namedtuple('_TLSArgs', 'tls cert key ca_cert verify')):
@classmethod
def from_options(cls, options):
return cls(
tls=options.get('--tls', False),
ca_cert=options.get('--tlscacert'),
cert=options.get('--tlscert'),
key=options.get('--tlskey'),
verify=options.get('--tlsverify')
)
# def has_config(self):
# return (
# self.tls or self.ca_cert or self.cert or self.key or self.verify
# )
def docker_client(version=None, tls_args=None, host=None):
"""
Returns a docker-py client configured using environment variables
according to the same logic as the official Docker client.
@ -31,6 +50,26 @@ def docker_client(version=None):
"and DOCKER_CERT_PATH are set correctly.\n"
"You might need to run `eval \"$(docker-machine env default)\"`")
if host:
kwargs['base_url'] = host
if tls_args and any(tls_args):
if tls_args.tls is True:
kwargs['tls'] = True
else:
client_cert = None
if tls_args.cert or tls_args.key:
client_cert = (tls_args.cert, tls_args.key)
try:
kwargs['tls'] = TLSConfig(
client_cert=client_cert, verify=tls_args.verify,
ca_cert=tls_args.ca_cert
)
except TLSParameterError as e:
raise UserError(
"TLS configuration is invalid. Please double-check the "
"TLS command-line arguments. ({0})".format(e)
)
if version:
kwargs['version'] = version

View File

@ -149,6 +149,13 @@ class TopLevelCommand(object):
-p, --project-name NAME Specify an alternate project name (default: directory name)
--verbose Show more output
-v, --version Print version and exit
-H, --host HOST Daemon socket to connect to
--tls Use TLS; implied by --tlsverify
--tlsacert Trust certs signed only by this CA
--tlscert Path to TLS certificate file
--tlskey Path to TLS key file
--tlsverify Use TLS and verify the remote
Commands:
build Build or rebuild services