Re-enable test_stuck_job_cleanup

We have to add playbooks that weren't there before in
commitLayoutUpdate so that we can add jobs in a layout update.

Change-Id: Ieeef822bd084647e99f331a7e94314a53231ee80
Story: 2000773
Task: 3555
diff --git a/tests/base.py b/tests/base.py
index 2729233..cef3eba 100755
--- a/tests/base.py
+++ b/tests/base.py
@@ -1874,11 +1874,18 @@
 
     def commitLayoutUpdate(self, orig_name, source_name):
         source_path = os.path.join(self.test_root, 'upstream',
-                                   source_name, 'zuul.yaml')
-        with open(source_path, 'r') as nt:
-            before = self.addCommitToRepo(
-                orig_name, 'Pulling content from %s' % source_name,
-                {'zuul.yaml': nt.read()})
+                                   source_name)
+        to_copy = ['zuul.yaml']
+        for playbook in os.listdir(os.path.join(source_path, 'playbooks')):
+            to_copy.append('playbooks/{}'.format(playbook))
+        commit_data = {}
+        for source_file in to_copy:
+            source_file_path = os.path.join(source_path, source_file)
+            with open(source_file_path, 'r') as nt:
+                commit_data[source_file] = nt.read()
+        before = self.addCommitToRepo(
+            orig_name, 'Pulling content from %s' % source_name,
+            commit_data)
         return before
 
     def addEvent(self, connection, event):
diff --git a/tests/fixtures/config/single-tenant/git/layout-no-jobs/playbooks/gate-noop.yaml b/tests/fixtures/config/single-tenant/git/layout-no-jobs/playbooks/gate-noop.yaml
new file mode 100644
index 0000000..f679dce
--- /dev/null
+++ b/tests/fixtures/config/single-tenant/git/layout-no-jobs/playbooks/gate-noop.yaml
@@ -0,0 +1,2 @@
+- hosts: all
+  tasks: []
diff --git a/tests/fixtures/config/single-tenant/git/layout-no-jobs/zuul.yaml b/tests/fixtures/config/single-tenant/git/layout-no-jobs/zuul.yaml
new file mode 100644
index 0000000..5894440
--- /dev/null
+++ b/tests/fixtures/config/single-tenant/git/layout-no-jobs/zuul.yaml
@@ -0,0 +1,49 @@
+- pipeline:
+    name: check
+    manager: independent
+    source: gerrit
+    trigger:
+      gerrit:
+        - event: patchset-created
+    success:
+      gerrit:
+        verified: 1
+    failure:
+      gerrit:
+        verified: -1
+
+- pipeline:
+    name: gate
+    manager: dependent
+    success-message: Build succeeded (gate).
+    source:
+      gerrit
+    trigger:
+      gerrit:
+        - event: comment-added
+          approval:
+            - approved: 1
+    success:
+      gerrit:
+        verified: 2
+        submit: true
+    failure:
+      gerrit:
+        verified: -2
+    start:
+      gerrit:
+        verified: 0
+    precedence: high
+
+- job:
+    name: gate-noop
+
+- project:
+    name: org/project
+    merge-mode: cherry-pick
+    check:
+      jobs:
+        - gate-noop
+    gate:
+      jobs:
+        - gate-noop
diff --git a/tests/fixtures/layout-no-jobs.yaml b/tests/fixtures/layout-no-jobs.yaml
deleted file mode 100644
index e860ad5..0000000
--- a/tests/fixtures/layout-no-jobs.yaml
+++ /dev/null
@@ -1,43 +0,0 @@
-includes:
-  - python-file: custom_functions.py
-
-pipelines:
-  - name: check
-    manager: IndependentPipelineManager
-    trigger:
-      gerrit:
-        - event: patchset-created
-    success:
-      gerrit:
-        verified: 1
-    failure:
-      gerrit:
-        verified: -1
-
-  - name: gate
-    manager: DependentPipelineManager
-    failure-message: Build failed.  For information on how to proceed, see http://wiki.example.org/Test_Failures
-    trigger:
-      gerrit:
-        - event: comment-added
-          approval:
-            - approved: 1
-    success:
-      gerrit:
-        verified: 2
-        submit: true
-    failure:
-      gerrit:
-        verified: -2
-    start:
-      gerrit:
-        verified: 0
-    precedence: high
-
-projects:
-  - name: org/project
-    merge-mode: cherry-pick
-    check:
-      - gate-noop
-    gate:
-      - gate-noop
diff --git a/tests/unit/test_scheduler.py b/tests/unit/test_scheduler.py
index 260b97d..97bce7b 100755
--- a/tests/unit/test_scheduler.py
+++ b/tests/unit/test_scheduler.py
@@ -1950,28 +1950,25 @@
         self.assertReportedStat('test-timing', '3|ms')
         self.assertReportedStat('test-gauge', '12|g')
 
-    @skip("Disabled for early v3 development")
     def test_stuck_job_cleanup(self):
         "Test that pending jobs are cleaned up if removed from layout"
-        # This job won't be registered at startup because it is not in
-        # the standard layout, but we need it to already be registerd
-        # for when we reconfigure, as that is when Zuul will attempt
-        # to run the new job.
-        self.worker.registerFunction('build:gate-noop')
+
+        # We want to hold the project-merge job that the fake change enqueues
         self.gearman_server.hold_jobs_in_queue = True
         A = self.fake_gerrit.addFakeChange('org/project', 'master', 'A')
         A.addApproval('code-review', 2)
         self.fake_gerrit.addEvent(A.addApproval('approved', 1))
         self.waitUntilSettled()
+        # The assertion is that we have one job in the queue, project-merge
         self.assertEqual(len(self.gearman_server.getQueue()), 1)
 
-        self.updateConfigLayout(
-            'tests/fixtures/layout-no-jobs.yaml')
+        self.commitLayoutUpdate('common-config', 'layout-no-jobs')
         self.sched.reconfigure(self.config)
         self.waitUntilSettled()
 
         self.gearman_server.release('gate-noop')
         self.waitUntilSettled()
+        # asserting that project-merge is removed from queue
         self.assertEqual(len(self.gearman_server.getQueue()), 0)
         self.assertTrue(self.sched._areAllBuildsComplete())