diff --git a/ansible/roles/deploy-containers/defaults/main.yml b/ansible/roles/deploy-containers/defaults/main.yml
index 9130164e9cbc7847df2e4b0a12992aa8b6ca6107..0838be95c4f343081266ac46d0231f6db317e9ff 100644
--- a/ansible/roles/deploy-containers/defaults/main.yml
+++ b/ansible/roles/deploy-containers/defaults/main.yml
@@ -1,4 +1,7 @@
 ---
+# Action to perform: One of: "deploy", "destroy".
+deploy_containers_action: "deploy"
+
 deploy_containers_defaults:
   comparisons:
     image: strict
diff --git a/ansible/roles/deploy-containers/tasks/deploy-container.yml b/ansible/roles/deploy-containers/tasks/deploy-container.yml
new file mode 100644
index 0000000000000000000000000000000000000000..0c5ccc087b3656eaceeddd93ae4cd7cef763f747
--- /dev/null
+++ b/ansible/roles/deploy-containers/tasks/deploy-container.yml
@@ -0,0 +1,38 @@
+---
+- name: "[{{ container_name }}] Ensure we have latest image"
+  docker_image:
+    name: "{{ container_config.image }}"
+    tag: "{{ container_config.tag | default(omit) }}"
+    source: pull
+
+- name: "[{{ container_name }}] Include tasks file for pre task(s)"
+  include_tasks: "{{ container_config.pre }}"
+  when: container_config.pre is defined
+
+- name: "[{{ container_name }}] Start container"
+  docker_container:
+    capabilities: "{{ container_config.capabilities | default(omit) }}"
+    command: "{{ container_config.command | default(omit) }}"
+    comparisons: "{{ container_config.comparisons | default(deploy_containers_defaults.comparisons) }}"
+    detach: "{{ container_config.detach | default(deploy_containers_defaults.detach) }}"
+    env: "{{ container_config.env | default(omit) }}"
+    name: "{{ container_name }}"
+    network_mode: "{{ container_config.network_mode | default(deploy_containers_defaults.network_mode) }}"
+    image: "{{ container_config.image }}:{{ container_config.tag | default('latest') }}"
+    init: "{{ container_config.init | default(deploy_containers_defaults.init) }}"
+    ipc_mode: "{{ container_config.ipc_mode | default(omit) }}"
+    pid_mode: "{{ container_config.pid_mode | default(omit) }}"
+    ports: "{{ container_config.ports | default(omit) }}"
+    privileged: "{{ container_config.privileged | default(omit) }}"
+    restart_policy: "{{ container_config.restart_policy | default(deploy_containers_defaults.restart_policy) }}"
+    shm_size: "{{ container_config.shm_size | default(omit) }}"
+    sysctls: "{{ container_config.sysctls | default(omit) }}"
+    timeout: "{{ deploy_containers_docker_api_timeout }}"
+    ulimits: "{{ container_config.ulimits | default(omit) }}"
+    user: "{{ container_config.user | default(omit) }}"
+    volumes: "{{ container_config.volumes | default(omit) }}"
+  become: true
+
+- name: "[{{ container_name }}] Include tasks file for post task(s)"
+  include_tasks: "{{ container_config.post }}"
+  when: container_config.post is defined
diff --git a/ansible/roles/deploy-containers/tasks/deploy.yml b/ansible/roles/deploy-containers/tasks/deploy.yml
index d146f21a19542d1197cf90682f4867befa265040..79796b4b67b6c658217dd9d11daa23d2094e1ffc 100644
--- a/ansible/roles/deploy-containers/tasks/deploy.yml
+++ b/ansible/roles/deploy-containers/tasks/deploy.yml
@@ -1,37 +1,17 @@
 ---
-- name: "[{{ container_name }}] Ensure we have latest image"
-  docker_image:
-    name: "{{ container_config.image }}"
-    tag: "{{ container_config.tag | default(omit) }}"
-    source: pull
+- name: Login to docker registry
+  docker_login:
+    registry_url: "{{ kolla_docker_registry or omit }}"
+    username: "{{ kolla_docker_registry_username }}"
+    password: "{{ kolla_docker_registry_password }}"
+    reauthorize: yes
+  when:
+    - deploy_containers_registry_attempt_login | bool
+  become: true
 
-- name: "[{{ container_name }}] Include tasks file for pre task(s)"
-  include_tasks: "{{ container_config.pre }}"
-  when: container_config.pre is defined
-
-- name: "[{{ container_name }}] Start container"
-  docker_container:
-    capabilities: "{{ container_config.capabilities | default(omit) }}"
-    command: "{{ container_config.command | default(omit) }}"
-    comparisons: "{{ container_config.comparisons | default(deploy_containers_defaults.comparisons) }}"
-    detach: "{{ container_config.detach | default(deploy_containers_defaults.detach) }}"
-    env: "{{ container_config.env | default(omit) }}"
-    name: "{{ container_name }}"
-    network_mode: "{{ container_config.network_mode | default(deploy_containers_defaults.network_mode) }}"
-    image: "{{ container_config.image }}:{{ container_config.tag | default('latest') }}"
-    init: "{{ container_config.init | default(deploy_containers_defaults.init) }}"
-    ipc_mode: "{{ container_config.ipc_mode | default(omit) }}"
-    pid_mode: "{{ container_config.pid_mode | default(omit) }}"
-    ports: "{{ container_config.ports | default(omit) }}"
-    privileged: "{{ container_config.privileged | default(omit) }}"
-    restart_policy: "{{ container_config.restart_policy | default(deploy_containers_defaults.restart_policy) }}"
-    shm_size: "{{ container_config.shm_size | default(omit) }}"
-    sysctls: "{{ container_config.sysctls | default(omit) }}"
-    timeout: "{{ deploy_containers_docker_api_timeout }}"
-    ulimits: "{{ container_config.ulimits | default(omit) }}"
-    user: "{{ container_config.user | default(omit) }}"
-    volumes: "{{ container_config.volumes | default(omit) }}"
-
-- name: "[{{ container_name }}] Include tasks file for post task(s)"
-  include_tasks: "{{ container_config.post }}"
-  when: container_config.post is defined
+- name: Deploy containers (loop)
+  include_tasks: deploy-container.yml
+  vars:
+    container_name: "{{ item.key }}"
+    container_config: "{{ item.value }}"
+  with_dict: "{{ seed_containers }}"
diff --git a/ansible/roles/deploy-containers/tasks/destroy-container.yml b/ansible/roles/deploy-containers/tasks/destroy-container.yml
new file mode 100644
index 0000000000000000000000000000000000000000..692ce2a630deea5de33ac0a59c9f83cf8f8c254b
--- /dev/null
+++ b/ansible/roles/deploy-containers/tasks/destroy-container.yml
@@ -0,0 +1,15 @@
+---
+
+- name: "[{{ container_name }}] Include tasks file for pre destroy task(s)"
+  include_tasks: "{{ container_config.pre_destroy }}"
+  when: container_config.pre_destroy is defined
+
+- name: "[{{ container_name }}] Delete container"
+  docker_container:
+    name: "{{ container_name }}"
+    state: absent
+  become: true
+
+- name: "[{{ container_name }}] Include tasks file for post destroy task(s)"
+  include_tasks: "{{ container_config.post_destroy }}"
+  when: container_config.post_destroy is defined
diff --git a/ansible/roles/deploy-containers/tasks/destroy.yml b/ansible/roles/deploy-containers/tasks/destroy.yml
new file mode 100644
index 0000000000000000000000000000000000000000..acf0d25bd306a0dc59ea77e3f90b8991dbf897c3
--- /dev/null
+++ b/ansible/roles/deploy-containers/tasks/destroy.yml
@@ -0,0 +1,6 @@
+- name: Destroy containers (loop)
+  include_tasks: destroy-container.yml
+  vars:
+    container_name: "{{ item.key }}"
+    container_config: "{{ item.value }}"
+  with_dict: "{{ seed_containers }}"
\ No newline at end of file
diff --git a/ansible/roles/deploy-containers/tasks/main.yml b/ansible/roles/deploy-containers/tasks/main.yml
index a16e6d8d75ec2ef6cafd57b6f7a5444c9249ff74..bcbde162999ed86e384870dfe6695464653f94a0 100644
--- a/ansible/roles/deploy-containers/tasks/main.yml
+++ b/ansible/roles/deploy-containers/tasks/main.yml
@@ -1,16 +1,2 @@
 ---
-- name: Login to docker registry
-  docker_login:
-    registry_url: "{{ kolla_docker_registry or omit }}"
-    username: "{{ kolla_docker_registry_username }}"
-    password: "{{ kolla_docker_registry_password }}"
-    reauthorize: yes
-  when:
-    - deploy_containers_registry_attempt_login | bool
-
-- name: Deploy containers (loop)
-  include_tasks: deploy.yml
-  vars:
-    container_name: "{{ item.key }}"
-    container_config: "{{ item.value }}"
-  with_dict: "{{ seed_containers }}"
+- include_tasks: "{{ deploy_containers_action }}.yml"
diff --git a/ansible/seed-deploy-containers.yml b/ansible/seed-deploy-containers.yml
index 23eb241c995e18a3de3e35ab403fe7a4d3ffd368..585487af8e8ceb3442fc7fb1b254818eac0533b8 100644
--- a/ansible/seed-deploy-containers.yml
+++ b/ansible/seed-deploy-containers.yml
@@ -3,5 +3,7 @@
   hosts: seed
   tags:
     - seed-deploy-containers
+  vars:
+    deploy_containers_action: "{{ kayobe_action }}"
   roles:
     - role: deploy-containers
diff --git a/doc/source/administration/seed.rst b/doc/source/administration/seed.rst
index ff8fab5105eb96b30745a8211315175cebcfff8c..673e1215254867868efb1debe0761a17953a1c2c 100644
--- a/doc/source/administration/seed.rst
+++ b/doc/source/administration/seed.rst
@@ -13,6 +13,29 @@ To deprovision the seed VM::
 
     (kayobe) $ kayobe seed vm deprovision
 
+Destroying all services on the seed
+===================================
+
+.. warning::
+
+   This step will destroy all containers, container images, and volumes that were deployed by
+   Kayobe and Kolla. To destroy volumes and images associated with
+   :ref:`custom containers <configuration-seed-custom-containers>`, you must configure the
+   ``post_destroy`` and ``pre_destroy`` hooks to do the clean up manually as Kayobe will not
+   automatically clean these up. It is generally only advised to run this command when
+   you have no important data on the system.
+
+To destroy the seed services::
+
+    (kayobe) $ kayobe seed service destroy --yes-i-really-really-mean-it
+
+This can optionally be used with a tag::
+
+    (kayobe) $ kayobe seed service destroy --yes-i-really-really-mean-it -kt none -t docker-registry
+
+Care must be taken to set both kayobe and kolla tags to avoid accidentally
+destroying other services.
+
 Updating Packages
 =================
 
diff --git a/doc/source/configuration/reference/seed-custom-containers.rst b/doc/source/configuration/reference/seed-custom-containers.rst
index 5b3e03cdd25cf3a8b18ca9d546899df1fb5ff054..b4f3035ac78bc04c934901da4d442da0452ca203 100644
--- a/doc/source/configuration/reference/seed-custom-containers.rst
+++ b/doc/source/configuration/reference/seed-custom-containers.rst
@@ -20,10 +20,27 @@ For example, to deploy a squid container image:
        image: "stackhpc/squid:3.5.20-1"
        pre: "{{ kayobe_env_config_path }}/containers/squid/pre.yml"
        post: "{{ kayobe_env_config_path }}/containers/squid/post.yml"
-
-Please notice the *optional* pre and post Ansible task files - those need to
-be created in ``kayobe-config`` path and will be run before and after
-particular container deployment.
+       pre_destroy: "{{ kayobe_env_config_path }}/containers/squid/pre_destroy.yml"
+       post_destroy: "{{ kayobe_env_config_path }}/containers/squid/post_destroy.yml"
+
+Please notice the *optional* pre, post, pre_destroy, and post_destroy Ansible task
+files - those need to be created in ``kayobe-config`` path. The table below describes
+when they will run:
+
+.. list-table:: Container hooks
+   :widths: 25 75
+   :header-rows: 1
+
+   * - Hook
+     - Trigger point
+   * - pre
+     - Before container deployment
+   * - post
+     - After container deployment
+   * - pre_destroy
+     - Before container is destroyed
+   * - post_destroy
+     - After container is destroyed
 
 Possible options for container deployment:
 
diff --git a/kayobe/cli/commands.py b/kayobe/cli/commands.py
index 7b059b9b5344819c434d4a94fa9f533c94a311ee..adeed542605a5dfec474c5b2518fedcf421151fd 100644
--- a/kayobe/cli/commands.py
+++ b/kayobe/cli/commands.py
@@ -730,7 +730,8 @@ class SeedServiceDeploy(KollaAnsibleMixin, KayobeAnsibleMixin, VaultMixin,
         self.app.LOG.debug("Deploying seed services")
         playbooks = _build_playbook_list(
             "seed-deploy-containers")
-        self.run_kayobe_playbooks(parsed_args, playbooks)
+        extra_vars = {"kayobe_action": "deploy"}
+        self.run_kayobe_playbooks(parsed_args, playbooks, extra_vars=extra_vars)
         self.generate_kolla_ansible_config(parsed_args, service_config=False,
                                            bifrost_config=True)
 
@@ -739,8 +740,44 @@ class SeedServiceDeploy(KollaAnsibleMixin, KayobeAnsibleMixin, VaultMixin,
             "seed-credentials",
             "seed-introspection-rules",
             "dell-switch-bmp")
-        self.run_kayobe_playbooks(parsed_args, playbooks)
+        self.run_kayobe_playbooks(parsed_args, playbooks, extra_vars=extra_vars)
+
+class SeedServiceDestroy(KollaAnsibleMixin, KayobeAnsibleMixin, VaultMixin,
+                        Command):
+    """Destroy the seed services.
+
+    * Destroys user defined containers
+    * Destroys kolla deployed containers
+    * Destroys docker registry
+    """
+
+    def take_action(self, parsed_args):
+        if not parsed_args.yes_i_really_really_mean_it:
+            self.app.LOG.error("This will permanently destroy all services "
+                               "and data. Specify "
+                               "--yes-i-really-really-mean-it to confirm that "
+                               "you understand this.")
+            sys.exit(1)
+        self.app.LOG.debug("Destroying seed services")
+        self.generate_kolla_ansible_config(parsed_args, service_config=False,
+                                           bifrost_config=False)
+        extra_args = ["--yes-i-really-really-mean-it"]
+        self.run_kolla_ansible_seed(parsed_args, "destroy", extra_args=extra_args)
 
+        extra_vars = {"kayobe_action": "destroy"}
+        playbooks = _build_playbook_list(
+            "seed-deploy-containers",
+            "docker-registry")
+        self.run_kayobe_playbooks(parsed_args, playbooks, extra_vars=extra_vars)
+
+    def get_parser(self, prog_name):
+        parser = super(SeedServiceDestroy, self).get_parser(prog_name)
+        group = parser.add_argument_group("Services")
+        group.add_argument("--yes-i-really-really-mean-it",
+                           action='store_true',
+                           help="confirm that you understand that this will "
+                                "permanently destroy all services and data.")
+        return parser
 
 class SeedServiceUpgrade(KollaAnsibleMixin, KayobeAnsibleMixin, VaultMixin,
                          Command):
@@ -762,7 +799,8 @@ class SeedServiceUpgrade(KollaAnsibleMixin, KayobeAnsibleMixin, VaultMixin,
         self.app.LOG.debug("Upgrading seed services")
         playbooks = _build_playbook_list(
             "seed-deploy-containers")
-        self.run_kayobe_playbooks(parsed_args, playbooks)
+        extra_vars = {"kayobe_action": "deploy"}
+        self.run_kayobe_playbooks(parsed_args, playbooks, extra_vars=extra_vars)
         self.generate_kolla_ansible_config(parsed_args, service_config=False,
                                            bifrost_config=True)
 
diff --git a/kayobe/tests/unit/cli/test_commands.py b/kayobe/tests/unit/cli/test_commands.py
index 83739c678bb202f3fc6abc7eb7268e1230e9568c..56c902e9bf216e53237499de597a8a606ad965ed 100644
--- a/kayobe/tests/unit/cli/test_commands.py
+++ b/kayobe/tests/unit/cli/test_commands.py
@@ -810,6 +810,7 @@ class TestCase(unittest.TestCase):
             mock.call(
                 mock.ANY,
                 [utils.get_data_files_path("ansible", "seed-deploy-containers.yml")],  # noqa
+                extra_vars={'kayobe_action': 'deploy'}
             ),
             mock.call(
                 mock.ANY,
@@ -834,6 +835,7 @@ class TestCase(unittest.TestCase):
                     utils.get_data_files_path(
                         "ansible", "dell-switch-bmp.yml"),
                 ],
+                extra_vars={'kayobe_action': 'deploy'}
             ),
         ]
         self.assertListEqual(expected_calls, mock_run.call_args_list)
@@ -862,6 +864,7 @@ class TestCase(unittest.TestCase):
             mock.call(
                 mock.ANY,
                 [utils.get_data_files_path("ansible", "seed-deploy-containers.yml")],  # noqa
+                extra_vars={'kayobe_action': 'deploy'}
             ),
             mock.call(
                 mock.ANY,
diff --git a/releasenotes/notes/adds-seed-service-destroy-1bdf79990d050e68.yaml b/releasenotes/notes/adds-seed-service-destroy-1bdf79990d050e68.yaml
new file mode 100644
index 0000000000000000000000000000000000000000..06b7526efd3d65e08eeaee385ec1551d8aeac8a0
--- /dev/null
+++ b/releasenotes/notes/adds-seed-service-destroy-1bdf79990d050e68.yaml
@@ -0,0 +1,6 @@
+---
+features:
+  - |
+    Adds the command ``kayobe seed service destroy``. This can be used to clean
+    up all services on the seed host. Caution is advised when using this command
+    as it will delete all of the data on the seed.
diff --git a/setup.cfg b/setup.cfg
index ce9dcb69ee085f02ea994037e4b9da53b654f1d6..df817dc0f28d8a88680ed462f3cc995a9f968c37 100644
--- a/setup.cfg
+++ b/setup.cfg
@@ -96,6 +96,7 @@ kayobe.cli=
     seed_hypervisor_host_package_update = kayobe.cli.commands:SeedHypervisorHostPackageUpdate
     seed_hypervisor_host_upgrade = kayobe.cli.commands:SeedHypervisorHostUpgrade
     seed_service_deploy = kayobe.cli.commands:SeedServiceDeploy
+    seed_service_destroy = kayobe.cli.commands:SeedServiceDestroy
     seed_service_upgrade = kayobe.cli.commands:SeedServiceUpgrade
     seed_vm_deprovision = kayobe.cli.commands:SeedVMDeprovision
     seed_vm_provision = kayobe.cli.commands:SeedVMProvision
@@ -221,6 +222,8 @@ kayobe.cli.seed_hypervisor_host_upgrade =
     hooks = kayobe.cli.commands:HookDispatcher
 kayobe.cli.seed_service_deploy =
     hooks = kayobe.cli.commands:HookDispatcher
+kayobe.cli.seed_service_destroy =
+    hooks = kayobe.cli.commands:HookDispatcher
 kayobe.cli.seed_service_upgrade =
     hooks = kayobe.cli.commands:HookDispatcher
 kayobe.cli.seed_vm_deprovision =