summaryrefslogtreecommitdiff
path: root/docker/api
diff options
context:
space:
mode:
Diffstat (limited to 'docker/api')
-rw-r--r--docker/api/build.py50
-rw-r--r--docker/api/client.py27
-rw-r--r--docker/api/container.py137
-rw-r--r--docker/api/exec_api.py12
-rw-r--r--docker/api/image.py50
-rw-r--r--docker/api/network.py6
-rw-r--r--docker/api/volume.py4
7 files changed, 79 insertions, 207 deletions
diff --git a/docker/api/build.py b/docker/api/build.py
index 220c93f..56f1fcf 100644
--- a/docker/api/build.py
+++ b/docker/api/build.py
@@ -1,7 +1,6 @@
import json
import logging
import os
-import re
from .. import auth
from .. import constants
@@ -14,7 +13,7 @@ log = logging.getLogger(__name__)
class BuildApiMixin(object):
def build(self, path=None, tag=None, quiet=False, fileobj=None,
- nocache=False, rm=False, stream=False, timeout=None,
+ nocache=False, rm=False, timeout=None,
custom_context=False, encoding=None, pull=False,
forcerm=False, dockerfile=None, container_limits=None,
decode=False, buildargs=None, gzip=False, shmsize=None,
@@ -67,9 +66,6 @@ class BuildApiMixin(object):
rm (bool): Remove intermediate containers. The ``docker build``
command now defaults to ``--rm=true``, but we have kept the old
default of `False` to preserve backward compatibility
- stream (bool): *Deprecated for API version > 1.8 (always True)*.
- Return a blocking generator you can iterate over to retrieve
- build output as it happens
timeout (int): HTTP timeout
custom_context (bool): Optional if using ``fileobj``
encoding (str): The encoding for a stream. Set to ``gzip`` for
@@ -154,17 +150,6 @@ class BuildApiMixin(object):
)
encoding = 'gzip' if gzip else encoding
- if utils.compare_version('1.8', self._version) >= 0:
- stream = True
-
- if dockerfile and utils.compare_version('1.17', self._version) < 0:
- raise errors.InvalidVersion(
- 'dockerfile was only introduced in API version 1.17'
- )
-
- if utils.compare_version('1.19', self._version) < 0:
- pull = 1 if pull else 0
-
u = self._url('/build')
params = {
't': tag,
@@ -179,12 +164,7 @@ class BuildApiMixin(object):
params.update(container_limits)
if buildargs:
- if utils.version_gte(self._version, '1.21'):
- params.update({'buildargs': json.dumps(buildargs)})
- else:
- raise errors.InvalidVersion(
- 'buildargs was only introduced in API version 1.21'
- )
+ params.update({'buildargs': json.dumps(buildargs)})
if shmsize:
if utils.version_gte(self._version, '1.22'):
@@ -256,30 +236,21 @@ class BuildApiMixin(object):
if encoding:
headers['Content-Encoding'] = encoding
- if utils.compare_version('1.9', self._version) >= 0:
- self._set_auth_headers(headers)
+ self._set_auth_headers(headers)
response = self._post(
u,
data=context,
params=params,
headers=headers,
- stream=stream,
+ stream=True,
timeout=timeout,
)
if context is not None and not custom_context:
context.close()
- if stream:
- return self._stream_helper(response, decode=decode)
- else:
- output = self._result(response)
- srch = r'Successfully built ([0-9a-f]+)'
- match = re.search(srch, output)
- if not match:
- return None, output
- return match.group(1), output
+ return self._stream_helper(response, decode=decode)
def _set_auth_headers(self, headers):
log.debug('Looking for auth config')
@@ -316,13 +287,8 @@ class BuildApiMixin(object):
)
)
- if utils.compare_version('1.19', self._version) >= 0:
- headers['X-Registry-Config'] = auth.encode_header(
- auth_data
- )
- else:
- headers['X-Registry-Config'] = auth.encode_header({
- 'configs': auth_data
- })
+ headers['X-Registry-Config'] = auth.encode_header(
+ auth_data
+ )
else:
log.debug('No auth config found')
diff --git a/docker/api/client.py b/docker/api/client.py
index 07bcfae..e69d143 100644
--- a/docker/api/client.py
+++ b/docker/api/client.py
@@ -1,6 +1,5 @@
import json
import struct
-import warnings
from functools import partial
import requests
@@ -27,7 +26,7 @@ from ..constants import (
MINIMUM_DOCKER_API_VERSION
)
from ..errors import (
- DockerException, TLSParameterError,
+ DockerException, InvalidVersion, TLSParameterError,
create_api_error_from_http_exception
)
from ..tls import TLSConfig
@@ -160,11 +159,9 @@ class APIClient(
)
)
if utils.version_lt(self._version, MINIMUM_DOCKER_API_VERSION):
- warnings.warn(
- 'The minimum API version supported is {}, but you are using '
- 'version {}. It is recommended you either upgrade Docker '
- 'Engine or use an older version of Docker SDK for '
- 'Python.'.format(MINIMUM_DOCKER_API_VERSION, self._version)
+ raise InvalidVersion(
+ 'API versions below {} are no longer supported by this '
+ 'library.'.format(MINIMUM_DOCKER_API_VERSION)
)
def _retrieve_server_version(self):
@@ -353,17 +350,8 @@ class APIClient(
break
yield data
- def _stream_raw_result_old(self, response):
- ''' Stream raw output for API versions below 1.6 '''
- self._raise_for_status(response)
- for line in response.iter_lines(chunk_size=1,
- decode_unicode=True):
- # filter out keep-alive new lines
- if line:
- yield line
-
def _stream_raw_result(self, response):
- ''' Stream result for TTY-enabled container above API 1.6 '''
+ ''' Stream result for TTY-enabled container '''
self._raise_for_status(response)
for out in response.iter_content(chunk_size=1, decode_unicode=True):
yield out
@@ -419,11 +407,6 @@ class APIClient(
return self._get_result_tty(stream, res, self._check_is_tty(container))
def _get_result_tty(self, stream, res, is_tty):
- # Stream multi-plexing was only introduced in API v1.6. Anything
- # before that needs old-style streaming.
- if utils.compare_version('1.6', self._version) < 0:
- return self._stream_raw_result_old(res)
-
# We should also use raw streaming (without keep-alives)
# if we're dealing with a tty-enabled container.
if is_tty:
diff --git a/docker/api/container.py b/docker/api/container.py
index 419ae44..152a08b 100644
--- a/docker/api/container.py
+++ b/docker/api/container.py
@@ -204,15 +204,13 @@ class ContainerApiMixin(object):
return res
def create_container(self, image, command=None, hostname=None, user=None,
- detach=False, stdin_open=False, tty=False,
- mem_limit=None, ports=None, environment=None,
- dns=None, volumes=None, volumes_from=None,
+ detach=False, stdin_open=False, tty=False, ports=None,
+ environment=None, volumes=None,
network_disabled=False, name=None, entrypoint=None,
- cpu_shares=None, working_dir=None, domainname=None,
- memswap_limit=None, cpuset=None, host_config=None,
- mac_address=None, labels=None, volume_driver=None,
- stop_signal=None, networking_config=None,
- healthcheck=None, stop_timeout=None, runtime=None):
+ working_dir=None, domainname=None, host_config=None,
+ mac_address=None, labels=None, stop_signal=None,
+ networking_config=None, healthcheck=None,
+ stop_timeout=None, runtime=None):
"""
Creates a container. Parameters are similar to those for the ``docker
run`` command except it doesn't support the attach options (``-a``).
@@ -354,27 +352,17 @@ class ContainerApiMixin(object):
return container ID
stdin_open (bool): Keep STDIN open even if not attached
tty (bool): Allocate a pseudo-TTY
- mem_limit (float or str): Memory limit. Accepts float values (which
- represent the memory limit of the created container in bytes)
- or a string with a units identification char (``100000b``,
- ``1000k``, ``128m``, ``1g``). If a string is specified without
- a units character, bytes are assumed as an intended unit.
ports (list of ints): A list of port numbers
environment (dict or list): A dictionary or a list of strings in
the following format ``["PASSWORD=xxx"]`` or
``{"PASSWORD": "xxx"}``.
- dns (:py:class:`list`): DNS name servers. Deprecated since API
- version 1.10. Use ``host_config`` instead.
volumes (str or list): List of paths inside the container to use
as volumes.
- volumes_from (:py:class:`list`): List of container names or Ids to
- get volumes from.
network_disabled (bool): Disable networking
name (str): A name for the container
entrypoint (str or list): An entrypoint
working_dir (str): Path to the working directory
domainname (str): The domain name to use for the container
- memswap_limit (int):
host_config (dict): A dictionary created with
:py:meth:`create_host_config`.
mac_address (str): The Mac Address to assign the container
@@ -382,7 +370,6 @@ class ContainerApiMixin(object):
``{"label1": "value1", "label2": "value2"}``) or a list of
names of labels to set with empty values (e.g.
``["label1", "label2"]``)
- volume_driver (str): The name of a volume driver/plugin.
stop_signal (str): The stop signal to use to stop the container
(e.g. ``SIGINT``).
stop_timeout (int): Timeout to stop the container, in seconds.
@@ -405,17 +392,12 @@ class ContainerApiMixin(object):
if isinstance(volumes, six.string_types):
volumes = [volumes, ]
- if host_config and utils.compare_version('1.15', self._version) < 0:
- raise errors.InvalidVersion(
- 'host_config is not supported in API < 1.15'
- )
-
config = self.create_container_config(
- image, command, hostname, user, detach, stdin_open, tty, mem_limit,
- ports, dns, environment, volumes, volumes_from,
- network_disabled, entrypoint, cpu_shares, working_dir, domainname,
- memswap_limit, cpuset, host_config, mac_address, labels,
- volume_driver, stop_signal, networking_config, healthcheck,
+ image, command, hostname, user, detach, stdin_open, tty,
+ ports, environment, volumes,
+ network_disabled, entrypoint, working_dir, domainname,
+ host_config, mac_address, labels,
+ stop_signal, networking_config, healthcheck,
stop_timeout, runtime
)
return self.create_container_from_config(config, name)
@@ -681,7 +663,6 @@ class ContainerApiMixin(object):
return self._stream_raw_result(res)
@utils.check_resource('container')
- @utils.minimum_version('1.20')
def get_archive(self, container, path):
"""
Retrieve a file or folder from a container in the form of a tar
@@ -786,59 +767,46 @@ class ContainerApiMixin(object):
:py:class:`docker.errors.APIError`
If the server returns an error.
"""
- if utils.compare_version('1.11', self._version) >= 0:
- if follow is None:
- follow = stream
- params = {'stderr': stderr and 1 or 0,
- 'stdout': stdout and 1 or 0,
- 'timestamps': timestamps and 1 or 0,
- 'follow': follow and 1 or 0,
- }
- if utils.compare_version('1.13', self._version) >= 0:
- if tail != 'all' and (not isinstance(tail, int) or tail < 0):
- tail = 'all'
- params['tail'] = tail
-
- if since is not None:
- if utils.version_lt(self._version, '1.19'):
- raise errors.InvalidVersion(
- 'since is not supported for API version < 1.19'
- )
- if isinstance(since, datetime):
- params['since'] = utils.datetime_to_timestamp(since)
- elif (isinstance(since, int) and since > 0):
- params['since'] = since
- else:
- raise errors.InvalidArgument(
- 'since value should be datetime or positive int, '
- 'not {}'.format(type(since))
- )
-
- if until is not None:
- if utils.version_lt(self._version, '1.35'):
- raise errors.InvalidVersion(
- 'until is not supported for API version < 1.35'
- )
- if isinstance(until, datetime):
- params['until'] = utils.datetime_to_timestamp(until)
- elif (isinstance(until, int) and until > 0):
- params['until'] = until
- else:
- raise errors.InvalidArgument(
- 'until value should be datetime or positive int, '
- 'not {}'.format(type(until))
- )
-
- url = self._url("/containers/{0}/logs", container)
- res = self._get(url, params=params, stream=stream)
- return self._get_result(container, stream, res)
- return self.attach(
- container,
- stdout=stdout,
- stderr=stderr,
- stream=stream,
- logs=True
- )
+ if follow is None:
+ follow = stream
+ params = {'stderr': stderr and 1 or 0,
+ 'stdout': stdout and 1 or 0,
+ 'timestamps': timestamps and 1 or 0,
+ 'follow': follow and 1 or 0,
+ }
+ if tail != 'all' and (not isinstance(tail, int) or tail < 0):
+ tail = 'all'
+ params['tail'] = tail
+
+ if since is not None:
+ if isinstance(since, datetime):
+ params['since'] = utils.datetime_to_timestamp(since)
+ elif (isinstance(since, int) and since > 0):
+ params['since'] = since
+ else:
+ raise errors.InvalidArgument(
+ 'since value should be datetime or positive int, '
+ 'not {}'.format(type(since))
+ )
+
+ if until is not None:
+ if utils.version_lt(self._version, '1.35'):
+ raise errors.InvalidVersion(
+ 'until is not supported for API version < 1.35'
+ )
+ if isinstance(until, datetime):
+ params['until'] = utils.datetime_to_timestamp(until)
+ elif (isinstance(until, int) and until > 0):
+ params['until'] = until
+ else:
+ raise errors.InvalidArgument(
+ 'until value should be datetime or positive int, '
+ 'not {}'.format(type(until))
+ )
+
+ url = self._url("/containers/{0}/logs", container)
+ res = self._get(url, params=params, stream=stream)
+ return self._get_result(container, stream, res)
@utils.check_resource('container')
def pause(self, container):
@@ -906,7 +874,6 @@ class ContainerApiMixin(object):
return h_ports
@utils.check_resource('container')
- @utils.minimum_version('1.20')
def put_archive(self, container, path, data):
"""
Insert a file or folder in an existing container using a tar archive as
@@ -976,7 +943,6 @@ class ContainerApiMixin(object):
)
self._raise_for_status(res)
- @utils.minimum_version('1.17')
@utils.check_resource('container')
def rename(self, container, name):
"""
@@ -1073,7 +1039,6 @@ class ContainerApiMixin(object):
res = self._post(url)
self._raise_for_status(res)
- @utils.minimum_version('1.17')
@utils.check_resource('container')
def stats(self, container, decode=None, stream=True):
"""
diff --git a/docker/api/exec_api.py b/docker/api/exec_api.py
index d607461..986d87f 100644
--- a/docker/api/exec_api.py
+++ b/docker/api/exec_api.py
@@ -5,7 +5,6 @@ from .. import utils
class ExecApiMixin(object):
- @utils.minimum_version('1.15')
@utils.check_resource('container')
def exec_create(self, container, cmd, stdout=True, stderr=True,
stdin=False, tty=False, privileged=False, user='',
@@ -41,14 +40,6 @@ class ExecApiMixin(object):
If the server returns an error.
"""
- if privileged and utils.version_lt(self._version, '1.19'):
- raise errors.InvalidVersion(
- 'Privileged exec is not supported in API < 1.19'
- )
- if user and utils.version_lt(self._version, '1.19'):
- raise errors.InvalidVersion(
- 'User-specific exec is not supported in API < 1.19'
- )
if environment is not None and utils.version_lt(self._version, '1.25'):
raise errors.InvalidVersion(
'Setting environment for exec is not supported in API < 1.25'
@@ -88,7 +79,6 @@ class ExecApiMixin(object):
res = self._post_json(url, data=data)
return self._result(res, True)
- @utils.minimum_version('1.16')
def exec_inspect(self, exec_id):
"""
Return low-level information about an exec command.
@@ -108,7 +98,6 @@ class ExecApiMixin(object):
res = self._get(self._url("/exec/{0}/json", exec_id))
return self._result(res, True)
- @utils.minimum_version('1.15')
def exec_resize(self, exec_id, height=None, width=None):
"""
Resize the tty session used by the specified exec command.
@@ -127,7 +116,6 @@ class ExecApiMixin(object):
res = self._post(url, params=params)
self._raise_for_status(res)
- @utils.minimum_version('1.15')
@utils.check_resource('exec_id')
def exec_start(self, exec_id, detach=False, tty=False, stream=False,
socket=False):
diff --git a/docker/api/image.py b/docker/api/image.py
index f37d2dd..fa832a3 100644
--- a/docker/api/image.py
+++ b/docker/api/image.py
@@ -54,8 +54,7 @@ class ImageApiMixin(object):
res = self._get(self._url("/images/{0}/history", image))
return self._result(res, True)
- def images(self, name=None, quiet=False, all=False, viz=False,
- filters=None):
+ def images(self, name=None, quiet=False, all=False, filters=None):
"""
List images. Similar to the ``docker images`` command.
@@ -76,10 +75,6 @@ class ImageApiMixin(object):
:py:class:`docker.errors.APIError`
If the server returns an error.
"""
- if viz:
- if utils.compare_version('1.7', self._version) >= 0:
- raise Exception('Viz output is not supported in API >= 1.7!')
- return self._result(self._get(self._url("images/viz")))
params = {
'filter': name,
'only_ids': 1 if quiet else 0,
@@ -226,19 +221,6 @@ class ImageApiMixin(object):
)
@utils.check_resource('image')
- def insert(self, image, url, path):
- if utils.compare_version('1.12', self._version) >= 0:
- raise errors.DeprecatedMethod(
- 'insert is not available for API version >=1.12'
- )
- api_url = self._url("/images/{0}/insert", image)
- params = {
- 'url': url,
- 'path': path
- }
- return self._result(self._post(api_url, params=params))
-
- @utils.check_resource('image')
def inspect_image(self, image):
"""
Get detailed information about an image. Similar to the ``docker
@@ -369,14 +351,13 @@ class ImageApiMixin(object):
}
headers = {}
- if utils.version_gte(self._version, '1.5'):
- if auth_config is None:
- header = auth.get_config_header(self, registry)
- if header:
- headers['X-Registry-Auth'] = header
- else:
- log.debug('Sending supplied auth config')
- headers['X-Registry-Auth'] = auth.encode_header(auth_config)
+ if auth_config is None:
+ header = auth.get_config_header(self, registry)
+ if header:
+ headers['X-Registry-Auth'] = header
+ else:
+ log.debug('Sending supplied auth config')
+ headers['X-Registry-Auth'] = auth.encode_header(auth_config)
if platform is not None:
if utils.version_lt(self._version, '1.32'):
@@ -440,14 +421,13 @@ class ImageApiMixin(object):
}
headers = {}
- if utils.compare_version('1.5', self._version) >= 0:
- if auth_config is None:
- header = auth.get_config_header(self, registry)
- if header:
- headers['X-Registry-Auth'] = header
- else:
- log.debug('Sending supplied auth config')
- headers['X-Registry-Auth'] = auth.encode_header(auth_config)
+ if auth_config is None:
+ header = auth.get_config_header(self, registry)
+ if header:
+ headers['X-Registry-Auth'] = header
+ else:
+ log.debug('Sending supplied auth config')
+ headers['X-Registry-Auth'] = auth.encode_header(auth_config)
response = self._post_json(
u, None, headers=headers, stream=stream, params=params
diff --git a/docker/api/network.py b/docker/api/network.py
index 7977808..57ed8d3 100644
--- a/docker/api/network.py
+++ b/docker/api/network.py
@@ -5,7 +5,6 @@ from .. import utils
class NetworkApiMixin(object):
- @minimum_version('1.21')
def networks(self, names=None, ids=None, filters=None):
"""
List networks. Similar to the ``docker networks ls`` command.
@@ -38,7 +37,6 @@ class NetworkApiMixin(object):
res = self._get(url, params=params)
return self._result(res, json=True)
- @minimum_version('1.21')
def create_network(self, name, driver=None, options=None, ipam=None,
check_duplicate=None, internal=False, labels=None,
enable_ipv6=False, attachable=None, scope=None,
@@ -175,7 +173,6 @@ class NetworkApiMixin(object):
url = self._url('/networks/prune')
return self._result(self._post(url, params=params), True)
- @minimum_version('1.21')
@check_resource('net_id')
def remove_network(self, net_id):
"""
@@ -188,7 +185,6 @@ class NetworkApiMixin(object):
res = self._delete(url)
self._raise_for_status(res)
- @minimum_version('1.21')
@check_resource('net_id')
def inspect_network(self, net_id, verbose=None, scope=None):
"""
@@ -216,7 +212,6 @@ class NetworkApiMixin(object):
return self._result(res, json=True)
@check_resource('container')
- @minimum_version('1.21')
def connect_container_to_network(self, container, net_id,
ipv4_address=None, ipv6_address=None,
aliases=None, links=None,
@@ -253,7 +248,6 @@ class NetworkApiMixin(object):
self._raise_for_status(res)
@check_resource('container')
- @minimum_version('1.21')
def disconnect_container_from_network(self, container, net_id,
force=False):
"""
diff --git a/docker/api/volume.py b/docker/api/volume.py
index ce911c8..900a608 100644
--- a/docker/api/volume.py
+++ b/docker/api/volume.py
@@ -3,7 +3,6 @@ from .. import utils
class VolumeApiMixin(object):
- @utils.minimum_version('1.21')
def volumes(self, filters=None):
"""
List volumes currently registered by the docker daemon. Similar to the
@@ -37,7 +36,6 @@ class VolumeApiMixin(object):
url = self._url('/volumes')
return self._result(self._get(url, params=params), True)
- @utils.minimum_version('1.21')
def create_volume(self, name=None, driver=None, driver_opts=None,
labels=None):
"""
@@ -90,7 +88,6 @@ class VolumeApiMixin(object):
return self._result(self._post_json(url, data=data), True)
- @utils.minimum_version('1.21')
def inspect_volume(self, name):
"""
Retrieve volume info by name.
@@ -138,7 +135,6 @@ class VolumeApiMixin(object):
url = self._url('/volumes/prune')
return self._result(self._post(url, params=params), True)
- @utils.minimum_version('1.21')
def remove_volume(self, name, force=False):
"""
Remove a volume. Similar to the ``docker volume rm`` command.