Skip to content

Commit

Permalink
Improve env cleanup
Browse files Browse the repository at this point in the history
- Use docker-compose down command to cleanup
- Remove kill_continaers & remove_containers methods
- Remove skipper network hack
- Expose ports for containers which need external access
  • Loading branch information
sharbov committed Apr 3, 2018
1 parent 4a058cd commit dfe0b2a
Show file tree
Hide file tree
Showing 7 changed files with 110 additions and 129 deletions.
68 changes: 36 additions & 32 deletions README.md
Original file line number Diff line number Diff line change
Expand Up @@ -72,19 +72,23 @@ e.g `build-container-net: test_tests-network`
For example: `test_example.py`
```python
import os
import httplib
import logging
import requests

from six.moves import http_client

from docker_test_tools.utils import get_health_check
from docker_test_tools.base_test import BaseDockerTest
from docker_test_tools.wiremock import WiremockController

log = logging.getLogger(__name__)

CONSUL_URL = "http://localhost:8500"
WIREMOCK_URL = "http://localhost:9999"

# Define health check functions for the environment services
consul_health_check = get_health_check('consul.service', url='http://consul.service:8500')
mock_service_health_check = get_health_check('mocked.service', url='http://mocked.service:9999/__admin')
consul_health_check = get_health_check('consul.service', url=CONSUL_URL)
mock_service_health_check = get_health_check('mocked.service', url=WIREMOCK_URL + '/__admin')


class ExampleTest(BaseDockerTest):
Expand All @@ -95,73 +99,73 @@ class ExampleTest(BaseDockerTest):
mock_service_health_check]

# [OPTIONAL] User defined health checks timeout
CHECKS_TIMEOUT = 60
CHECKS_TIMEOUT = 10

def setUp(self):
"""Create a wiremock controller and add a cleanup for it."""
super(ExampleTest, self).setUp()

self.wiremock = WiremockController(url='http://mocked.service:9999')
self.wiremock = WiremockController(url=WIREMOCK_URL)
self.addCleanup(self.wiremock.reset_mapping)

def test_services_sanity(self):
"""Validate services are responsive once the test start."""
logging.info('Validating consul container is responsive')
self.assertEquals(requests.get('http://consul.service:8500').status_code, httplib.OK)
log.info('Validating consul container is responsive')
self.assertEquals(requests.get(CONSUL_URL).status_code, http_client.OK)

logging.info('Validating wiremock container is responsive')
self.assertEquals(requests.get('http://mocked.service:9999/__admin').status_code, httplib.OK)
log.info('Validating wiremock container is responsive')
self.assertEquals(requests.get(WIREMOCK_URL + '/__admin').status_code, http_client.OK)

def test_service_down(self):
"""Validate service down scenario."""
logging.info('Validating consul container is responsive')
self.assertEquals(requests.get('http://consul.service:8500').status_code, httplib.OK)
log.info('Validating consul container is responsive')
self.assertEquals(requests.get(CONSUL_URL).status_code, http_client.OK)

logging.info('Validating consul container is unresponsive while in `container_down` context')
log.info('Validating consul container is unresponsive while in `container_down` context')
with self.controller.container_down(name='consul.service', health_check=consul_health_check):
with self.assertRaises(requests.ConnectionError):
requests.get('http://consul.service:8500')
requests.get(CONSUL_URL)

logging.info('Validating consul container has recovered and is responsive')
self.assertEquals(requests.get('http://consul.service:8500').status_code, httplib.OK)
log.info('Validating consul container has recovered and is responsive')
self.assertEquals(requests.get(CONSUL_URL).status_code, http_client.OK)

def test_service_stopped(self):
"""Validate service stopped scenario."""
logging.info('Validating consul container is responsive')
self.assertEquals(requests.get('http://consul.service:8500').status_code, httplib.OK)
log.info('Validating consul container is responsive')
self.assertEquals(requests.get(CONSUL_URL).status_code, http_client.OK)

logging.info('Validating consul container is unresponsive while in `container_stopped` context')
log.info('Validating consul container is unresponsive while in `container_stopped` context')
with self.controller.container_stopped(name='consul.service', health_check=consul_health_check):
with self.assertRaises(requests.ConnectionError):
requests.get('http://consul.service:8500')
requests.get(CONSUL_URL)

logging.info('Validating consul container has recovered and is responsive')
self.assertEquals(requests.get('http://consul.service:8500').status_code, httplib.OK)
log.info('Validating consul container has recovered and is responsive')
self.assertEquals(requests.get(CONSUL_URL).status_code, http_client.OK)

def test_service_paused(self):
"""Validate service paused scenario."""
logging.info('Validating consul container is responsive')
self.assertEquals(requests.get('http://consul.service:8500', timeout=2).status_code, httplib.OK)
log.info('Validating consul container is responsive')
self.assertEquals(requests.get(CONSUL_URL, timeout=2).status_code, http_client.OK)

logging.info('Validating consul container is unresponsive while in `container_paused` context')
log.info('Validating consul container is unresponsive while in `container_paused` context')
with self.controller.container_paused(name='consul.service', health_check=consul_health_check):
with self.assertRaises(requests.Timeout):
requests.get('http://consul.service:8500', timeout=2)
requests.get(CONSUL_URL, timeout=2)

logging.info('Validating consul container has recovered and is responsive')
self.assertEquals(requests.get('http://consul.service:8500', timeout=2).status_code, httplib.OK)
log.info('Validating consul container has recovered and is responsive')
self.assertEquals(requests.get(CONSUL_URL, timeout=2).status_code, http_client.OK)

def test_mocked_service_configuration(self):
"""Validate wiremock service."""
logging.info('Validating mocked service fail to find `test` endpoint')
self.assertEquals(requests.post('http://mocked.service:9999/test').status_code, httplib.NOT_FOUND)
log.info('Validating mocked service fail to find `test` endpoint')
self.assertEquals(requests.post(WIREMOCK_URL + '/test').status_code, http_client.NOT_FOUND)

logging.info('Use WiremockController to stub the service `test` endpoint')
log.info('Use WiremockController to stub the service `test` endpoint')
stubs_dir_path = os.path.join(os.path.dirname(__file__), '..', 'resources', 'wiremock_stubs')
self.wiremock.set_mapping_from_dir(stubs_dir_path)

logging.info('Validating mocked service response on `test` endpoint')
self.assertEquals(requests.post('http://mocked.service:9999/test').status_code, httplib.OK)
log.info('Validating mocked service response on `test` endpoint')
self.assertEquals(requests.post(WIREMOCK_URL + '/test').status_code, http_client.OK)
```

## Integrating With `nose2`
Expand Down
32 changes: 10 additions & 22 deletions docker_test_tools/environment.py
Original file line number Diff line number Diff line change
Expand Up @@ -97,7 +97,7 @@ def setup(self):
try:
log.debug("Setting up the environment")
self.cleanup()
self.run_containers()
self.up()

for plugin in self.plugins:
try:
Expand Down Expand Up @@ -134,41 +134,29 @@ def cleanup(self):
log.warning("Container reuse enabled: Skipping environment cleanup")
return

self.kill_containers()
self.remove_containers()
self.down()

def run_containers(self):
def up(self):
"""Run environment containers."""
log.debug("Running environment containers, using docker compose: %s", self.compose_path)
log.debug("Setting environment up, using docker compose: %s", self.compose_path)
try:
subprocess.check_output(
['docker-compose', '-f', self.compose_path, '-p', self.project_name, 'up', '--build', '-d'],
stderr=subprocess.STDOUT, env=self.environment_variables
)
except subprocess.CalledProcessError as error:
raise RuntimeError("Failed running environment containers, reason: %s" % error.output)
raise RuntimeError("Failed setting up environment, reason: %s" % error.output)

def remove_containers(self):
"""Remove the environment containers."""
log.debug("Removing environment containers, using docker compose: %s", self.compose_path)
try:
subprocess.check_output(
['docker-compose', '-f', self.compose_path, '-p', self.project_name, 'rm', '-f'],
stderr=subprocess.STDOUT, env=self.environment_variables
)
except subprocess.CalledProcessError as error:
raise RuntimeError("Failed removing environment containers, reason: %s" % error.output)

def kill_containers(self):
"""Kill the environment containers."""
log.debug("Killing environment containers, using docker compose: %s", self.compose_path)
def down(self):
"""Run environment containers."""
log.debug("Taking environment down, using docker compose: %s", self.compose_path)
try:
subprocess.check_output(
['docker-compose', '-f', self.compose_path, '-p', self.project_name, 'kill'],
['docker-compose', '-f', self.compose_path, '-p', self.project_name, 'down'],
stderr=subprocess.STDOUT, env=self.environment_variables
)
except subprocess.CalledProcessError as error:
raise RuntimeError("Failed killing environment containers, reason: %s" % error.output)
raise RuntimeError("Failed taking environment down, reason: %s" % error.output)

def kill_container(self, name):
"""Kill the container.
Expand Down
3 changes: 1 addition & 2 deletions skipper.yaml
Original file line number Diff line number Diff line change
@@ -1,5 +1,4 @@
registry: rackattack-nas.dc1:5000
build-container-image: py27-build
build-container-net: example_tests-network
make:
makefile: Makefile.internal
makefile: Makefile.internal
52 changes: 28 additions & 24 deletions tests/integration/test_example.py
Original file line number Diff line number Diff line change
@@ -1,17 +1,21 @@
import os
from six.moves import http_client
import logging
import requests

from six.moves import http_client

from docker_test_tools.utils import get_health_check
from docker_test_tools.base_test import BaseDockerTest
from docker_test_tools.wiremock import WiremockController

log = logging.getLogger(__name__)

CONSUL_URL = "http://localhost:8500"
WIREMOCK_URL = "http://localhost:9999"

# Define health check functions for the environment services
consul_health_check = get_health_check('consul.service', url='http://consul.service:8500')
mock_service_health_check = get_health_check('mocked.service', url='http://mocked.service:9999/__admin')
consul_health_check = get_health_check('consul.service', url=CONSUL_URL)
mock_service_health_check = get_health_check('mocked.service', url=WIREMOCK_URL + '/__admin')


class ExampleTest(BaseDockerTest):
Expand All @@ -22,85 +26,85 @@ class ExampleTest(BaseDockerTest):
mock_service_health_check]

# [OPTIONAL] User defined health checks timeout
CHECKS_TIMEOUT = 60
CHECKS_TIMEOUT = 10

def setUp(self):
"""Create a wiremock controller and add a cleanup for it."""
super(ExampleTest, self).setUp()

self.wiremock = WiremockController(url='http://mocked.service:9999')
self.wiremock = WiremockController(url=WIREMOCK_URL)
self.addCleanup(self.wiremock.reset_mapping)

def test_services_sanity(self):
"""Validate services are responsive once the test start."""
log.info('Validating consul container is responsive')
self.assertEquals(requests.get('http://consul.service:8500').status_code, http_client.OK)
self.assertEquals(requests.get(CONSUL_URL).status_code, http_client.OK)

log.info('Validating wiremock container is responsive')
self.assertEquals(requests.get('http://mocked.service:9999/__admin').status_code, http_client.OK)
self.assertEquals(requests.get(WIREMOCK_URL + '/__admin').status_code, http_client.OK)

def test_service_down(self):
"""Validate service down scenario."""
log.info('Validating consul container is responsive')
self.assertEquals(requests.get('http://consul.service:8500').status_code, http_client.OK)
self.assertEquals(requests.get(CONSUL_URL).status_code, http_client.OK)

log.info('Validating consul container is unresponsive while in `container_down` context')
with self.controller.container_down(name='consul.service', health_check=consul_health_check):
with self.assertRaises(requests.ConnectionError):
requests.get('http://consul.service:8500')
requests.get(CONSUL_URL)

log.info('Validating consul container has recovered and is responsive')
self.assertEquals(requests.get('http://consul.service:8500').status_code, http_client.OK)
self.assertEquals(requests.get(CONSUL_URL).status_code, http_client.OK)

def test_service_stopped(self):
"""Validate service stopped scenario."""
log.info('Validating consul container is responsive')
self.assertEquals(requests.get('http://consul.service:8500').status_code, http_client.OK)
self.assertEquals(requests.get(CONSUL_URL).status_code, http_client.OK)

log.info('Validating consul container is unresponsive while in `container_stopped` context')
with self.controller.container_stopped(name='consul.service', health_check=consul_health_check):
with self.assertRaises(requests.ConnectionError):
requests.get('http://consul.service:8500')
requests.get(CONSUL_URL)

log.info('Validating consul container has recovered and is responsive')
self.assertEquals(requests.get('http://consul.service:8500').status_code, http_client.OK)
self.assertEquals(requests.get(CONSUL_URL).status_code, http_client.OK)

def test_service_paused(self):
"""Validate service paused scenario."""
log.info('Validating consul container is responsive')
self.assertEquals(requests.get('http://consul.service:8500', timeout=2).status_code, http_client.OK)
self.assertEquals(requests.get(CONSUL_URL, timeout=2).status_code, http_client.OK)

log.info('Validating consul container is unresponsive while in `container_paused` context')
with self.controller.container_paused(name='consul.service', health_check=consul_health_check):
with self.assertRaises(requests.Timeout):
requests.get('http://consul.service:8500', timeout=2)
requests.get(CONSUL_URL, timeout=2)

log.info('Validating consul container has recovered and is responsive')
self.assertEquals(requests.get('http://consul.service:8500', timeout=2).status_code, http_client.OK)
self.assertEquals(requests.get(CONSUL_URL, timeout=2).status_code, http_client.OK)

def test_mocked_service_configuration(self):
"""Validate wiremock service."""
log.info('Validating mocked service fail to find `test` endpoint')
self.assertEquals(requests.post('http://mocked.service:9999/test').status_code, http_client.NOT_FOUND)
self.assertEquals(requests.post(WIREMOCK_URL + '/test').status_code, http_client.NOT_FOUND)

log.info('Use WiremockController to stub the service `test` endpoint')
stubs_dir_path = os.path.join(os.path.dirname(__file__), '..', 'resources', 'wiremock_stubs')
self.wiremock.set_mapping_from_dir(stubs_dir_path)

log.info('Validating mocked service response on `test` endpoint')
self.assertEquals(requests.post('http://mocked.service:9999/test').status_code, http_client.OK)
self.assertEquals(requests.post(WIREMOCK_URL + '/test').status_code, http_client.OK)

def test_mocked_service_request_journal(self):
"""Validate wiremock request journal."""
log.info('Validating first request reaches the journal')
requests.post('http://mocked.service:9999/some-unique-request-33452')
requests.post(WIREMOCK_URL + '/some-unique-request-33452')
journal = self.wiremock.get_request_journal()
inner_url = journal[-1]['request']['url']
self.assertEquals(inner_url, "/some-unique-request-33452")

log.info('Validating filtering of specific requests from the journal')
requests.post('http://mocked.service:9999/test2')
requests.post('http://mocked.service:9999/test2')
requests.post(WIREMOCK_URL + '/test2')
requests.post(WIREMOCK_URL + '/test2')
filtered = self.wiremock.get_matching_requests('/test2')
self.assertEquals(len(filtered), 2)
self.assertEquals(filtered[0]['request']['url'], "/test2")
Expand All @@ -118,9 +122,9 @@ def test_mocked_service_request_journal(self):
self.assertIn(stub_file_path_example, stub_ids)

log.info('Validating filtering of specific requests from the journal by stub id')
requests.post('http://mocked.service:9999/test')
requests.post('http://mocked.service:9999/test')
requests.post('http://mocked.service:9999/some-unique-request-33452')
requests.post(WIREMOCK_URL + '/test')
requests.post(WIREMOCK_URL + '/test')
requests.post(WIREMOCK_URL + '/some-unique-request-33452')
journal = self.wiremock.get_request_journal()
self.assertEquals(len(journal), 3)
filtered = self.wiremock.get_matching_requests(stub_id=stub_ids[stub_file_path_example])
Expand Down
6 changes: 5 additions & 1 deletion tests/resources/docker-compose-v2.1.yml
Original file line number Diff line number Diff line change
Expand Up @@ -9,6 +9,8 @@ services:
consul.service:
image: consul
networks: [tests-network]
ports:
- 8500:8500

# [OPTIONAL] healthcheck definition requires docker version > 1.12.
healthcheck:
Expand All @@ -20,9 +22,11 @@ services:
image: stratoscale/wiremock:latest
networks: [tests-network]
command: "9999"
ports:
- 9999:9999

# [OPTIONAL] healthcheck definition requires docker version > 1.12.
healthcheck:
test: "curl -f http://localhost:9999/__admin || false"
interval: 1s
retries: 120
retries: 120
4 changes: 4 additions & 0 deletions tests/resources/docker-compose-v2.yml
Original file line number Diff line number Diff line change
Expand Up @@ -9,8 +9,12 @@ services:
consul.service:
image: consul
networks: [tests-network]
ports:
- 8500:8500

mocked.service:
image: stratoscale/wiremock:latest
networks: [tests-network]
command: "9999"
ports:
- 9999:9999

0 comments on commit dfe0b2a

Please sign in to comment.