Merge lp:~benji/testrepository/add-worker-id-tagging into lp:~testrepository/testrepository/trunk

Proposed by Benji York on 2012-04-18
Status: Merged
Merged at revision: 148
Proposed branch: lp:~benji/testrepository/add-worker-id-tagging
Merge into: lp:~testrepository/testrepository/trunk
Diff against target: 72 lines (+25/-2)
2 files modified
testrepository/commands/load.py (+9/-2)
testrepository/tests/commands/test_load.py (+16/-0)
To merge this branch: bzr merge lp:~benji/testrepository/add-worker-id-tagging
Reviewer Review Type Date Requested Status
Jonathan Lange 2012-04-18 Approve on 2012-04-20
Review via email: mp+102574@code.launchpad.net

Commit Message

tag each test with the ID of the worker that executed the test

Description of the Change

This branch adds worker-ID tagging by taking advantage of the new testtools functionality.

When each test is run it is tagged with a "worker-#" string where "#" is a number identifying the worker process, starting with 1.

To post a comment you must log in.
Jonathan Lange (jml) wrote :

 * I can't seem to get this to actually generate output that includes the tags.

 * I get this failing test:

======================================================================
ERROR: testrepository.tests.commands.test_load.TestCommandLoad.test_load__wrap_result_inserts_worker_id_tag
----------------------------------------------------------------------
Traceback (most recent call last):
  File "testrepository/tests/commands/test_load.py", line 201, in test_load__wrap_result_inserts_worker_id_tag
    result.addSuccess(self)
  File "/home/jml/src/testtools/testtools/testresult/real.py", line 696, in addSuccess
    return self.decorated.addSuccess(test, details=details)
TypeError: addSuccess() got an unexpected keyword argument 'details'

Fix is probably to change:
    return Tagger(result, tags_to_add, tags_to_remove)

To:
    return Tagger(ExtendedToOriginalDecorator(result), tags_to_add, tags_to_remove)

Jonathan Lange (jml) wrote :

When I use subunit trunk, I get the tags in output. Yay. Still get failure though.

Benji York (benji) wrote :

On Wed, Apr 18, 2012 at 8:27 PM, Jonathan Lange <email address hidden> wrote:
> When I use subunit trunk, I get the tags in output. Yay. Still get failure though.

I had to use some trunks of testrepository dependencies. I will
identify which are important and report back here. I assume the failure
you get is the same as in your first comment.
--
Benji York

Gary Poster (gary) wrote :

I am seeing test tags leakage.

I ran the LP tests with these changes (and Jono's suggestion). It seemed to work. Looking deeper into the testr subunit result (in the .testrepository directory) after I set up worker tags, I saw something that concerned me. This should not include the "zope:layer" tag.

test: lib/lp/registry/stories/gpg-coc/xx-ubuntu-codeofconduct-signer.txt
time: 2012-04-19 01:15:58.192592Z
tags: worker-0 zope:layer
successful: lib/lp/registry/stories/gpg-coc/xx-ubuntu-codeofconduct-signer.txt [ multipart
]

The processing in testr/subunit/testtools is in fact adding it. Here's an excerpt from a raw run of the same test, run in the lptests container with ./bin/test --subunit -t stories/gpg. The test is at the end, but you can see a layer "test" earlier with the tag.

test: lp.testing.layers.PageTestLayer:setUp
tags: zope:layer
time: 2012-04-19 01:49:13.039859Z
successful: lp.testing.layers.PageTestLayer:setUp
tags: zope:layer:lp.testing.layers.PageTestLayer
test: lib/lp/registry/stories/gpg-coc/xx-gpg-coc.txt
successful: lib/lp/registry/stories/gpg-coc/xx-gpg-coc.txt
test: lib/lp/registry/stories/gpg-coc/xx-ubuntu-codeofconduct-signer.txt
successful: lib/lp/registry/stories/gpg-coc/xx-ubuntu-codeofconduct-signer.txt

No "zope:layer" tag is in there. It looks like something is keeping test tag state across tests.

I believe that the problem is not in this branch, but this branch exposes the feature, so it would be nice if the problem were resolved before the changes were merged.

Jonathan Lange (jml) wrote :

Yes, same failure in my second comment as in my first.

If I understand the "tag leaking" problem, it's that the PageTestLayer:setUp ought to have the zope:layer tag (and you guys are ok with that), but that the following tests ought not, (and yet, they do!). I'll have a poke around.

Just to be crystal clear, I don't think this problem is at all related to bug 664171. Do you?

Jonathan Lange (jml) wrote :

Tag leakage reported as bug 985613.

Gary Poster (gary) wrote :

@jml No, I don't think this problem is at all related to bug 664171.

Thank you!

151. By Benji York on 2012-04-19

merge from trunk

152. By Benji York on 2012-04-19

fix test failure when using trunk of testtools

Benji York (benji) wrote :

I've fixed the test failure. This branch should now work using released versions of all testr dependencies plus the trunk of testtools.

Jonathan Lange (jml) wrote :

 * LoggingResult is deprecated and uses an old API. Contrary to the advice I gave you on IRC, it is entirely appropriate to wrap that with ExtendedToOriginalDecorator. Using addUnexpectedSuccess is fine though.

 * I added some tests to automate my integration testing (http://paste.ubuntu.com/938182/) to my local branch. test_worker_tags_in_subunit_output fails with my packaged subunit (0.0.7-1build1) and with lp:subunit r152 (0.0.7 release) but succeeds when I use subunit trunk. I'd kind of like to know why, but not enough to figure it out myself or block this landing.

review: Approve

Preview Diff

[H/L] Next/Prev Comment, [J/K] Next/Prev File, [N/P] Next/Prev Hunk
1=== modified file 'testrepository/commands/load.py'
2--- testrepository/commands/load.py 2012-04-18 15:31:35 +0000
3+++ testrepository/commands/load.py 2012-04-19 15:07:19 +0000
4@@ -17,12 +17,19 @@
5 import optparse
6
7 import subunit
8-from testtools import ConcurrentTestSuite, MultiTestResult
9+from testtools import ConcurrentTestSuite, MultiTestResult, Tagger
10
11 from testrepository.commands import Command
12 from testrepository.repository import RepositoryNotFound
13
14
15+def _wrap_result(result, thread_number):
16+ worker_id = 'worker-%s' % thread_number
17+ tags_to_add = set([worker_id])
18+ tags_to_remove = set()
19+ return Tagger(result, tags_to_add, tags_to_remove)
20+
21+
22 class load(Command):
23 """Load a subunit stream into a repository.
24
25@@ -66,7 +73,7 @@
26 streams = list(suite)[0]
27 for stream in streams():
28 yield subunit.ProtocolTestCase(stream)
29- case = ConcurrentTestSuite(cases, make_tests)
30+ case = ConcurrentTestSuite(cases, make_tests, _wrap_result)
31 inserter = repo.get_inserter(partial=self.ui.options.partial)
32 try:
33 previous_run = repo.get_latest_run()
34
35=== modified file 'testrepository/tests/commands/test_load.py'
36--- testrepository/tests/commands/test_load.py 2011-11-03 18:25:11 +0000
37+++ testrepository/tests/commands/test_load.py 2012-04-19 15:07:19 +0000
38@@ -21,11 +21,13 @@
39 import testtools
40 from testtools.content import text_content
41 from testtools.matchers import MatchesException
42+from testtools.tests.helpers import LoggingResult
43
44 from testrepository.commands import load
45 from testrepository.ui.model import UI
46 from testrepository.tests import ResourcedTestCase, Wildcard
47 from testrepository.tests.test_repository import RecordingRepositoryFactory
48+from testrepository.tests.repository.test_file import HomeDirTempDir
49 from testrepository.repository import memory, RepositoryNotFound
50
51
52@@ -189,6 +191,20 @@
53 [('summary', True, 1, None, 2.0, None, [('id', 0, None)])],
54 ui.outputs[1:])
55
56+ def test_load__wrap_result_inserts_worker_id_tag(self):
57+ # The load command uses a result wrapper that tags each test with the
58+ # ID of the worker that executed the test.
59+ log = []
60+ result = load._wrap_result(LoggingResult(log), 99)
61+ result.startTestRun()
62+ result.startTest(self)
63+ result.addUnexpectedSuccess(self)
64+ result.stopTest(self)
65+ result.stopTestRun()
66+ # Even though no tag data was provided above, the test has been tagged
67+ # with the worker ID.
68+ self.assertIn(('tags', set(['worker-99']), set([])), log)
69+
70 def test_load_second_run(self):
71 # If there's a previous run in the database, then show information
72 # about the high level differences in the test run: how many more

Subscribers

People subscribed via source and target branches