From 2d50ec69965af3e5e15922094294fd451d468c46 Mon Sep 17 00:00:00 2001 From: Jhon Honce Date: Tue, 3 Nov 2020 13:15:16 -0700 Subject: Update CI tests to run python docker library against API * Update reference to docker-py to docker to reflect change in library name * Update tests to create storage sandbox * Enable all tests that endpoints support * Refactor containers/{id}/rename to return 404 not 500 * Refactor tests to use quay.io vs. docker.io Signed-off-by: Jhon Honce --- test/python/dockerpy/tests/__init__.py | 0 test/python/dockerpy/tests/common.py | 105 ------------- test/python/dockerpy/tests/constant.py | 13 -- test/python/dockerpy/tests/test_containers.py | 193 ------------------------ test/python/dockerpy/tests/test_images.py | 162 -------------------- test/python/dockerpy/tests/test_info_version.py | 44 ------ 6 files changed, 517 deletions(-) delete mode 100644 test/python/dockerpy/tests/__init__.py delete mode 100644 test/python/dockerpy/tests/common.py delete mode 100644 test/python/dockerpy/tests/constant.py delete mode 100644 test/python/dockerpy/tests/test_containers.py delete mode 100644 test/python/dockerpy/tests/test_images.py delete mode 100644 test/python/dockerpy/tests/test_info_version.py (limited to 'test/python/dockerpy/tests') diff --git a/test/python/dockerpy/tests/__init__.py b/test/python/dockerpy/tests/__init__.py deleted file mode 100644 index e69de29bb..000000000 diff --git a/test/python/dockerpy/tests/common.py b/test/python/dockerpy/tests/common.py deleted file mode 100644 index f83f4076f..000000000 --- a/test/python/dockerpy/tests/common.py +++ /dev/null @@ -1,105 +0,0 @@ -import os -import pathlib -import subprocess -import sys -import time - -from docker import APIClient - -from . import constant - -alpineDict = { - "name": "docker.io/library/alpine:latest", - "shortName": "alpine", - "tarballName": "alpine.tar" -} - - -def get_client(): - client = APIClient(base_url="http://localhost:8080", timeout=15) - return client - - -client = get_client() - - -def podman(): - binary = os.getenv("PODMAN_BINARY") - if binary is None: - binary = "../../../bin/podman" - return binary - - -def restore_image_from_cache(TestClass): - alpineImage = os.path.join(constant.ImageCacheDir, - alpineDict["tarballName"]) - if not os.path.exists(alpineImage): - os.makedirs(constant.ImageCacheDir, exist_ok=True) - client.pull(constant.ALPINE) - image = client.get_image(constant.ALPINE) - tarball = open(alpineImage, mode="wb") - for frame in image: - tarball.write(frame) - tarball.close() - else: - subprocess.run( - [podman(), "load", "-i", alpineImage], - shell=False, - stdin=subprocess.DEVNULL, - stdout=subprocess.DEVNULL, - stderr=subprocess.DEVNULL, - check=True, - ) - - -def flush_image_cache(TestCase): - for f in pathlib.Path(constant.ImageCacheDir).glob("*"): - f.unlink(f) - - -def run_top_container(): - c = client.create_container(image=constant.ALPINE, - command='/bin/sleep 5', - name=constant.TOP) - client.start(container=c.get("Id")) - return c.get("Id") - - -def enable_sock(TestClass): - TestClass.podman = subprocess.Popen( - [ - podman(), "system", "service", "tcp:localhost:8080", - "--log-level=debug", "--time=0" - ], - shell=False, - stdin=subprocess.DEVNULL, - stdout=subprocess.DEVNULL, - stderr=subprocess.DEVNULL, - ) - time.sleep(2) - - -def terminate_connection(TestClass): - TestClass.podman.terminate() - stdout, stderr = TestClass.podman.communicate(timeout=0.5) - if stdout: - print("\nService Stdout:\n" + stdout.decode('utf-8')) - if stderr: - print("\nService Stderr:\n" + stderr.decode('utf-8')) - - if TestClass.podman.returncode > 0: - sys.stderr.write("podman exited with error code {}\n".format( - TestClass.podman.returncode)) - sys.exit(2) - - -def remove_all_containers(): - containers = client.containers(quiet=True) - for c in containers: - client.remove_container(container=c.get("Id"), force=True) - - -def remove_all_images(): - allImages = client.images() - for image in allImages: - client.remove_image(image, force=True) diff --git a/test/python/dockerpy/tests/constant.py b/test/python/dockerpy/tests/constant.py deleted file mode 100644 index b44442d02..000000000 --- a/test/python/dockerpy/tests/constant.py +++ /dev/null @@ -1,13 +0,0 @@ -BB = "docker.io/library/busybox:latest" -NGINX = "docker.io/library/nginx:latest" -ALPINE = "docker.io/library/alpine:latest" -ALPINE_SHORTNAME = "alpine" -ALPINELISTTAG = "docker.io/library/alpine:3.10.2" -ALPINELISTDIGEST = "docker.io/library/alpine@sha256:72c42ed48c3a2db31b7dafe17d275b634664a708d901ec9fd57b1529280f01fb" -ALPINEAMD64DIGEST = "docker.io/library/alpine@sha256:acd3ca9941a85e8ed16515bfc5328e4e2f8c128caa72959a58a127b7801ee01f" -ALPINEAMD64ID = "961769676411f082461f9ef46626dd7a2d1e2b2a38e6a44364bcbecf51e66dd4" -ALPINEARM64DIGEST = "docker.io/library/alpine@sha256:db7f3dcef3d586f7dd123f107c93d7911515a5991c4b9e51fa2a43e46335a43e" -ALPINEARM64ID = "915beeae46751fc564998c79e73a1026542e945ca4f73dc841d09ccc6c2c0672" -infra = "k8s.gcr.io/pause:3.2" -TOP = "top" -ImageCacheDir = "/tmp/podman/imagecachedir" diff --git a/test/python/dockerpy/tests/test_containers.py b/test/python/dockerpy/tests/test_containers.py deleted file mode 100644 index 6b89688d4..000000000 --- a/test/python/dockerpy/tests/test_containers.py +++ /dev/null @@ -1,193 +0,0 @@ -import os -import time -import unittest - -import requests - -from . import common, constant - -client = common.get_client() - - -class TestContainers(unittest.TestCase): - topContainerId = "" - - def setUp(self): - super().setUp() - common.restore_image_from_cache(self) - TestContainers.topContainerId = common.run_top_container() - - def tearDown(self): - common.remove_all_containers() - common.remove_all_images() - return super().tearDown() - - @classmethod - def setUpClass(cls): - super().setUpClass() - common.enable_sock(cls) - - @classmethod - def tearDownClass(cls): - common.terminate_connection(cls) - common.flush_image_cache(cls) - return super().tearDownClass() - - def test_inspect_container(self): - # Inspect bogus container - with self.assertRaises(requests.HTTPError) as error: - client.inspect_container("dummy") - self.assertEqual(error.exception.response.status_code, 404) - # Inspect valid container by name - container = client.inspect_container(constant.TOP) - self.assertIn(TestContainers.topContainerId, container["Id"]) - # Inspect valid container by Id - container = client.inspect_container(TestContainers.topContainerId) - self.assertIn(constant.TOP, container["Name"]) - - def test_create_container(self): - # Run a container with detach mode - container = client.create_container(image="alpine", detach=True) - self.assertEqual(len(container), 2) - - def test_start_container(self): - # Start bogus container - with self.assertRaises(requests.HTTPError) as error: - client.start("dummy") - self.assertEqual(error.exception.response.status_code, 404) - - # Podman docs says it should give a 304 but returns with no response - # # Start a already started container should return 304 - # response = client.start(container=TestContainers.topContainerId) - # self.assertEqual(error.exception.response.status_code, 304) - - # Create a new container and validate the count - client.create_container(image=constant.ALPINE, name="container2") - containers = client.containers(quiet=True, all=True) - self.assertEqual(len(containers), 2) - - def test_stop_container(self): - # Stop bogus container - with self.assertRaises(requests.HTTPError) as error: - client.stop("dummy") - self.assertEqual(error.exception.response.status_code, 404) - - # Validate the container state - container = client.inspect_container(constant.TOP) - self.assertEqual(container["State"]["Status"], "running") - - # Stop a running container and validate the state - client.stop(TestContainers.topContainerId) - container = client.inspect_container(constant.TOP) - self.assertIn( - container["State"]["Status"], - "stopped exited", - ) - - def test_restart_container(self): - # Restart bogus container - with self.assertRaises(requests.HTTPError) as error: - client.restart("dummy") - self.assertEqual(error.exception.response.status_code, 404) - - # Validate the container state - client.stop(TestContainers.topContainerId) - container = client.inspect_container(constant.TOP) - self.assertEqual(container["State"]["Status"], "stopped") - - # restart a running container and validate the state - client.restart(TestContainers.topContainerId) - container = client.inspect_container(constant.TOP) - self.assertEqual(container["State"]["Status"], "running") - - def test_remove_container(self): - # Remove bogus container - with self.assertRaises(requests.HTTPError) as error: - client.remove_container("dummy") - self.assertEqual(error.exception.response.status_code, 404) - - # Remove container by ID with force - client.remove_container(TestContainers.topContainerId, force=True) - containers = client.containers() - self.assertEqual(len(containers), 0) - - def test_remove_container_without_force(self): - # Validate current container count - containers = client.containers() - self.assertTrue(len(containers), 1) - - # Remove running container should throw error - with self.assertRaises(requests.HTTPError) as error: - client.remove_container(TestContainers.topContainerId) - self.assertEqual(error.exception.response.status_code, 500) - - # Remove container by ID with force - client.stop(TestContainers.topContainerId) - client.remove_container(TestContainers.topContainerId) - containers = client.containers() - self.assertEqual(len(containers), 0) - - def test_pause_container(self): - # Pause bogus container - with self.assertRaises(requests.HTTPError) as error: - client.pause("dummy") - self.assertEqual(error.exception.response.status_code, 404) - - # Validate the container state - container = client.inspect_container(constant.TOP) - self.assertEqual(container["State"]["Status"], "running") - - # Pause a running container and validate the state - client.pause(container) - container = client.inspect_container(constant.TOP) - self.assertEqual(container["State"]["Status"], "paused") - - def test_pause_stoped_container(self): - # Stop the container - client.stop(TestContainers.topContainerId) - - # Pause exited container should trow error - with self.assertRaises(requests.HTTPError) as error: - client.pause(TestContainers.topContainerId) - self.assertEqual(error.exception.response.status_code, 500) - - def test_unpause_container(self): - # Unpause bogus container - with self.assertRaises(requests.HTTPError) as error: - client.unpause("dummy") - self.assertEqual(error.exception.response.status_code, 404) - - # Validate the container state - client.pause(TestContainers.topContainerId) - container = client.inspect_container(constant.TOP) - self.assertEqual(container["State"]["Status"], "paused") - - # Pause a running container and validate the state - client.unpause(TestContainers.topContainerId) - container = client.inspect_container(constant.TOP) - self.assertEqual(container["State"]["Status"], "running") - - def test_list_container(self): - - # Add container and validate the count - client.create_container(image="alpine", detach=True) - containers = client.containers(all=True) - self.assertEqual(len(containers), 2) - - # Not working for now......checking - # # List container with filter by id - # filters = {'id':TestContainers.topContainerId} - # filteredContainers = client.containers(all=True,filters = filters) - # self.assertEqual(len(filteredContainers) , 1) - - # # List container with filter by name - # filters = {'name':constant.TOP} - # filteredContainers = client.containers(all=True,filters = filters) - # self.assertEqual(len(filteredContainers) , 1) - - @unittest.skip("Not Supported yet") - def test_rename_container(self): - # rename bogus container - with self.assertRaises(requests.HTTPError) as error: - client.rename(container="dummy", name="newname") - self.assertEqual(error.exception.response.status_code, 404) diff --git a/test/python/dockerpy/tests/test_images.py b/test/python/dockerpy/tests/test_images.py deleted file mode 100644 index 602a86de2..000000000 --- a/test/python/dockerpy/tests/test_images.py +++ /dev/null @@ -1,162 +0,0 @@ -import os -import stat -import unittest -from os import remove -from stat import ST_SIZE - -import docker -import requests - -from . import common, constant - -client = common.get_client() - - -class TestImages(unittest.TestCase): - def setUp(self): - super().setUp() - common.restore_image_from_cache(self) - - def tearDown(self): - common.remove_all_images() - return super().tearDown() - - @classmethod - def setUpClass(cls): - super().setUpClass() - common.enable_sock(cls) - - @classmethod - def tearDownClass(cls): - common.terminate_connection(cls) - common.flush_image_cache(cls) - return super().tearDownClass() - -# Inspect Image - - def test_inspect_image(self): - # Check for error with wrong image name - with self.assertRaises(requests.HTTPError): - client.inspect_image("dummy") - alpine_image = client.inspect_image(constant.ALPINE) - self.assertIn(constant.ALPINE, alpine_image["RepoTags"]) - -# Tag Image - -# Validates if invalid image name is given a bad response is encountered. - - def test_tag_invalid_image(self): - with self.assertRaises(requests.HTTPError): - client.tag("dummy", "demo") - - # Validates if the image is tagged successfully. - def test_tag_valid_image(self): - client.tag(constant.ALPINE, "demo", constant.ALPINE_SHORTNAME) - alpine_image = client.inspect_image(constant.ALPINE) - for x in alpine_image["RepoTags"]: - if ("demo:alpine" in x): - self.assertTrue - self.assertFalse - - # Validates if name updates when the image is retagged. - @unittest.skip("doesn't work now") - def test_retag_valid_image(self): - client.tag(constant.ALPINE_SHORTNAME, "demo", "rename") - alpine_image = client.inspect_image(constant.ALPINE) - self.assertNotIn("demo:test", alpine_image["RepoTags"]) - -# List Image -# List All Images - - def test_list_images(self): - allImages = client.images() - self.assertEqual(len(allImages), 1) - # Add more images - client.pull(constant.BB) - allImages = client.images() - self.assertEqual(len(allImages), 2) - - # List images with filter - filters = {'reference': 'alpine'} - allImages = client.images(filters=filters) - self.assertEqual(len(allImages), 1) - -# Search Image - - def test_search_image(self): - response = client.search("alpine") - for i in response: - # Alpine found - if "docker.io/library/alpine" in i["Name"]: - self.assertTrue - self.assertFalse - -# Image Exist (No docker-py support yet) - -# Remove Image - - def test_remove_image(self): - # Check for error with wrong image name - with self.assertRaises(requests.HTTPError): - client.remove_image("dummy") - allImages = client.images() - self.assertEqual(len(allImages), 1) - alpine_image = client.inspect_image(constant.ALPINE) - client.remove_image(alpine_image) - allImages = client.images() - self.assertEqual(len(allImages), 0) - -# Image History - - def test_image_history(self): - # Check for error with wrong image name - with self.assertRaises(requests.HTTPError): - client.history("dummy") - - imageHistory = client.history(constant.ALPINE) - alpine_image = client.inspect_image(constant.ALPINE) - for h in imageHistory: - if h["Id"] in alpine_image["Id"]: - self.assertTrue - self.assertFalse - -# Prune Image (No docker-py support yet) - - def test_get_image_dummy(self): - # FIXME: seems to be an error in the library - self.skipTest("Documentation and library do not match") - # Check for error with wrong image name - with self.assertRaises(docker.errors.ImageNotFound): - client.get_image("dummy") - -# Export Image - - def test_export_image(self): - client.pull(constant.BB) - if not os.path.exists(constant.ImageCacheDir): - os.makedirs(constant.ImageCacheDir) - - image = client.get_image(constant.BB) - - file = os.path.join(constant.ImageCacheDir, "busybox.tar") - tarball = open(file, mode="wb") - for frame in image: - tarball.write(frame) - tarball.close() - sz = os.path.getsize(file) - self.assertGreater(sz, 0) - - -# Import|Load Image - - def test_import_image(self): - allImages = client.images() - self.assertEqual(len(allImages), 1) - file = os.path.join(constant.ImageCacheDir, "alpine.tar") - client.import_image_from_file(filename=file) - allImages = client.images() - self.assertEqual(len(allImages), 2) - -if __name__ == '__main__': - # Setup temporary space - unittest.main() diff --git a/test/python/dockerpy/tests/test_info_version.py b/test/python/dockerpy/tests/test_info_version.py deleted file mode 100644 index e3ee18ec7..000000000 --- a/test/python/dockerpy/tests/test_info_version.py +++ /dev/null @@ -1,44 +0,0 @@ -import unittest - -from . import common, constant - -client = common.get_client() - - -class TestInfo_Version(unittest.TestCase): - - podman = None - topContainerId = "" - - def setUp(self): - super().setUp() - common.restore_image_from_cache(self) - TestInfo_Version.topContainerId = common.run_top_container() - - def tearDown(self): - common.remove_all_containers() - common.remove_all_images() - return super().tearDown() - - @classmethod - def setUpClass(cls): - super().setUpClass() - common.enable_sock(cls) - - @classmethod - def tearDownClass(cls): - common.terminate_connection(cls) - return super().tearDownClass() - - def test_Info(self): - self.assertIsNotNone(client.info()) - - def test_info_container_details(self): - info = client.info() - self.assertEqual(info["Containers"], 1) - client.create_container(image=constant.ALPINE) - info = client.info() - self.assertEqual(info["Containers"], 2) - - def test_version(self): - self.assertIsNotNone(client.version()) -- cgit v1.2.3-54-g00ecf