Merge lp:~thumper/launchpad/branch-index-slowness into lp:launchpad

Proposed by Tim Penhey
Status: Merged
Approved by: Tim Penhey
Approved revision: no longer in the source branch.
Merged at revision: 11000
Proposed branch: lp:~thumper/launchpad/branch-index-slowness
Merge into: lp:launchpad
Diff against target: 436 lines (+166/-26)
14 files modified
lib/lp/code/browser/branch.py (+105/-14)
lib/lp/code/browser/tests/test_branch.py (+33/-1)
lib/lp/code/configure.zcml (+1/-0)
lib/lp/code/interfaces/branch.py (+3/-0)
lib/lp/code/model/branch.py (+11/-0)
lib/lp/code/templates/branch-import-details.pt (+1/-1)
lib/lp/code/templates/branch-management.pt (+1/-1)
lib/lp/code/templates/branch-metadata.pt (+1/-1)
lib/lp/code/templates/branch-pending-merges.pt (+1/-1)
lib/lp/code/templates/branch-portlet-subscribers.pt (+1/-1)
lib/lp/code/templates/branch-recipes.pt (+1/-1)
lib/lp/code/templates/branch-related-bugs-specs.pt (+1/-1)
lib/lp/code/templates/branch-revisions.pt (+2/-2)
lib/lp/testing/factory.py (+4/-2)
To merge this branch: bzr merge lp:~thumper/launchpad/branch-index-slowness
Reviewer Review Type Date Requested Status
Paul Hummer (community) code Approve
Review via email: mp+27318@code.launchpad.net

Commit message

Fix time-outs on the branch index page for branches with lots of linked bugs.

Description of the change

This branch provides a DecoratedBranch object to cache database queries. An extra method is added to the branch class to get linked bugs and all their bug tasks.

As a part of this branch, only bugs in an incomplete state are shown on series branches.

To post a comment you must log in.
Revision history for this message
Paul Hummer (rockstar) wrote :

<rockstar> thumper, line 150 of your diff, why not use isinstance?
<thumper> rockstar: because I didn't think of it :)
<rockstar> thumper, okay. Can you remedy that?
<thumper> yep
<rockstar> thumper, do you have some data to go with this branch that might be good to go to the list?
<thumper> rockstar: what are you asking exactly
<rockstar> thumper, I think query count numbers along with the changes in this branch would be good to post to the list.
<thumper> rockstar: I'll be writing something up, yes

review: Approve (code)

Preview Diff

[H/L] Next/Prev Comment, [J/K] Next/Prev File, [N/P] Next/Prev Hunk
=== modified file 'lib/lp/code/browser/branch.py'
--- lib/lp/code/browser/branch.py 2010-05-30 04:06:48 +0000
+++ lib/lp/code/browser/branch.py 2010-06-11 05:08:31 +0000
@@ -25,13 +25,16 @@
25 'BranchURL',25 'BranchURL',
26 'BranchView',26 'BranchView',
27 'BranchSubscriptionsView',27 'BranchSubscriptionsView',
28 'DecoratedBranch',
28 'DecoratedBug',29 'DecoratedBug',
29 'RegisterBranchMergeProposalView',30 'RegisterBranchMergeProposalView',
30 'TryImportAgainView',31 'TryImportAgainView',
31 ]32 ]
3233
33import cgi34import cgi
35from collections import defaultdict
34from datetime import datetime, timedelta36from datetime import datetime, timedelta
37from operator import attrgetter
3538
36import pytz39import pytz
37import simplejson40import simplejson
@@ -78,6 +81,7 @@
78from canonical.widgets.lazrjs import vocabulary_to_choice_edit_items81from canonical.widgets.lazrjs import vocabulary_to_choice_edit_items
7982
80from lp.bugs.interfaces.bug import IBug83from lp.bugs.interfaces.bug import IBug
84from lp.bugs.interfaces.bugtask import UNRESOLVED_BUGTASK_STATUSES
81from lp.code.browser.branchref import BranchRef85from lp.code.browser.branchref import BranchRef
82from lp.code.browser.branchmergeproposal import (86from lp.code.browser.branchmergeproposal import (
83 latest_proposals_for_each_branch)87 latest_proposals_for_each_branch)
@@ -90,7 +94,7 @@
90 CodeImportAlreadyRequested, CodeImportAlreadyRunning,94 CodeImportAlreadyRequested, CodeImportAlreadyRunning,
91 CodeImportNotInReviewedState, InvalidBranchMergeProposal)95 CodeImportNotInReviewedState, InvalidBranchMergeProposal)
92from lp.code.interfaces.branch import (96from lp.code.interfaces.branch import (
93 BranchCreationForbidden, BranchExists, IBranch,97 BranchCreationForbidden, BranchExists, BzrIdentityMixin, IBranch,
94 user_has_special_branch_access)98 user_has_special_branch_access)
95from lp.code.interfaces.branchmergeproposal import IBranchMergeProposal99from lp.code.interfaces.branchmergeproposal import IBranchMergeProposal
96from lp.code.interfaces.branchtarget import IBranchTarget100from lp.code.interfaces.branchtarget import IBranchTarget
@@ -327,17 +331,103 @@
327331
328class DecoratedBug:332class DecoratedBug:
329 """Provide some additional attributes to a normal bug."""333 """Provide some additional attributes to a normal bug."""
330 delegates(IBug)334 delegates(IBug, 'bug')
331335
332 def __init__(self, context, branch):336 def __init__(self, bug, branch, tasks=None):
333 self.context = context337 self.bug = bug
334 self.branch = branch338 self.branch = branch
339 self.tasks = tasks
340 if self.tasks is None:
341 self.tasks = self.bug.bugtasks
342
343 @property
344 def bugtasks(self):
345 return self.tasks
346
347 @property
348 def default_bugtask(self):
349 return self.tasks[0]
350
351 def getBugTask(self, target):
352 # Copied from Bug.getBugTarget to avoid importing.
353 for bugtask in self.bugtasks:
354 if bugtask.target == target:
355 return bugtask
356 return None
335357
336 @property358 @property
337 def bugtask(self):359 def bugtask(self):
338 """Return the bugtask for the branch project, or the default bugtask.360 """Return the bugtask for the branch project, or the default bugtask.
339 """361 """
340 return self.branch.target.getBugTask(self.context)362 return self.branch.target.getBugTask(self)
363
364
365class DecoratedBranch(BzrIdentityMixin):
366 """Wrap a number of the branch accessors to cache results.
367
368 This avoids repeated db queries.
369 """
370 delegates(IBranch, 'branch')
371
372 def __init__(self, branch):
373 self.branch = branch
374
375 @cachedproperty
376 def linked_bugs(self):
377 bugs = defaultdict(list)
378 for bug, task in self.branch.getLinkedBugsAndTasks():
379 bugs[bug].append(task)
380 return [DecoratedBug(bug, self.branch, tasks)
381 for bug, tasks in bugs.iteritems()]
382
383 @property
384 def displayname(self):
385 return self.bzr_identity
386
387 @cachedproperty
388 def bzr_identity(self):
389 return super(DecoratedBranch, self).bzr_identity
390
391 @cachedproperty
392 def is_series_branch(self):
393 # True if linked to a product series or suite source package.
394 return (
395 len(self.associated_product_series) > 0 or
396 len(self.suite_source_packages) > 0)
397
398 def associatedProductSeries(self):
399 """Override the IBranch.associatedProductSeries."""
400 return self.associated_product_series
401
402 def associatedSuiteSourcePackages(self):
403 """Override the IBranch.associatedSuiteSourcePackages."""
404 return self.suite_source_packages
405
406 @cachedproperty
407 def associated_product_series(self):
408 return list(self.branch.associatedProductSeries())
409
410 @cachedproperty
411 def suite_source_packages(self):
412 return list(self.branch.associatedSuiteSourcePackages())
413
414 @cachedproperty
415 def upgrade_pending(self):
416 return self.branch.upgrade_pending
417
418 @cachedproperty
419 def subscriptions(self):
420 return list(self.branch.subscriptions)
421
422 def hasSubscription(self, user):
423 for sub in self.subscriptions:
424 if sub.person == user:
425 return True
426 return False
427
428 @cachedproperty
429 def latest_revisions(self):
430 return list(self.branch.latest_revisions())
341431
342432
343class BranchView(LaunchpadView, FeedsMixin):433class BranchView(LaunchpadView, FeedsMixin):
@@ -356,6 +446,10 @@
356446
357 def initialize(self):447 def initialize(self):
358 self.notices = []448 self.notices = []
449 # Replace our context with a decorated branch, if it is not already
450 # decorated.
451 if not isinstance(self.context, DecoratedBranch):
452 self.context = DecoratedBranch(self.context)
359453
360 def user_is_subscribed(self):454 def user_is_subscribed(self):
361 """Is the current user subscribed to this branch?"""455 """Is the current user subscribed to this branch?"""
@@ -421,13 +515,6 @@
421 else:515 else:
422 return None516 return None
423517
424 def edit_link_url(self):
425 """Target URL of the Edit link used in the actions portlet."""
426 # XXX: DavidAllouche 2005-12-02 bug=5313:
427 # That should go away when bug #5313 is fixed.
428 linkdata = BranchContextMenu(self.context).edit()
429 return '%s/%s' % (canonical_url(self.context), linkdata.target)
430
431 @property518 @property
432 def user_can_upload(self):519 def user_can_upload(self):
433 """Whether the user can upload to this branch."""520 """Whether the user can upload to this branch."""
@@ -517,8 +604,12 @@
517 @cachedproperty604 @cachedproperty
518 def linked_bugs(self):605 def linked_bugs(self):
519 """Return a list of DecoratedBugs linked to the branch."""606 """Return a list of DecoratedBugs linked to the branch."""
520 return [DecoratedBug(bug, self.context)607 bugs = self.context.linked_bugs
521 for bug in self.context.linked_bugs]608 if self.context.is_series_branch:
609 bugs = [
610 bug for bug in bugs
611 if bug.bugtask.status in UNRESOLVED_BUGTASK_STATUSES]
612 return bugs
522613
523 @cachedproperty614 @cachedproperty
524 def latest_code_import_results(self):615 def latest_code_import_results(self):
525616
=== modified file 'lib/lp/code/browser/tests/test_branch.py'
--- lib/lp/code/browser/tests/test_branch.py 2010-04-13 04:15:33 +0000
+++ lib/lp/code/browser/tests/test_branch.py 2010-06-11 05:08:31 +0000
@@ -3,6 +3,8 @@
33
4"""Unit tests for BranchView."""4"""Unit tests for BranchView."""
55
6from __future__ import with_statement
7
6__metaclass__ = type8__metaclass__ = type
7__all__ = ['TestBranchView', 'test_suite']9__all__ = ['TestBranchView', 'test_suite']
810
@@ -21,6 +23,8 @@
21from canonical.database.constants import UTC_NOW23from canonical.database.constants import UTC_NOW
2224
23from lp.app.interfaces.headings import IRootContext25from lp.app.interfaces.headings import IRootContext
26from lp.bugs.interfaces.bugtask import (
27 BugTaskStatus, UNRESOLVED_BUGTASK_STATUSES)
24from lp.code.browser.branch import (28from lp.code.browser.branch import (
25 BranchAddView, BranchMirrorStatusView, BranchReviewerEditView,29 BranchAddView, BranchMirrorStatusView, BranchReviewerEditView,
26 BranchSparkView, BranchView)30 BranchSparkView, BranchView)
@@ -32,7 +36,8 @@
32from lp.registry.interfaces.product import IProductSet36from lp.registry.interfaces.product import IProductSet
33from lp.code.interfaces.branchlookup import IBranchLookup37from lp.code.interfaces.branchlookup import IBranchLookup
34from lp.testing import (38from lp.testing import (
35 login, login_person, logout, ANONYMOUS, TestCaseWithFactory)39 login, login_person, logout, person_logged_in, ANONYMOUS,
40 TestCaseWithFactory)
36from lp.testing.views import create_initialized_view41from lp.testing.views import create_initialized_view
37from canonical.launchpad.webapp.servers import LaunchpadTestRequest42from canonical.launchpad.webapp.servers import LaunchpadTestRequest
38from canonical.testing import (43from canonical.testing import (
@@ -261,6 +266,33 @@
261 login_person(branch.owner)266 login_person(branch.owner)
262 self.assertFalse(view.user_can_upload)267 self.assertFalse(view.user_can_upload)
263268
269 def _addBugLinks(self, branch):
270 for status in BugTaskStatus.items:
271 bug = self.factory.makeBug(status=status)
272 branch.linkBug(bug, branch.owner)
273
274 def test_linked_bugs(self):
275 # The linked bugs for a non series branch shows all linked bugs.
276 branch = self.factory.makeAnyBranch()
277 with person_logged_in(branch.owner):
278 self._addBugLinks(branch)
279 view = create_initialized_view(branch, '+index')
280 self.assertEqual(len(BugTaskStatus), len(view.linked_bugs))
281 self.assertFalse(view.context.is_series_branch)
282
283 def test_linked_bugs_series_branch(self):
284 # The linked bugs for a series branch shows only unresolved bugs.
285 product = self.factory.makeProduct()
286 branch = self.factory.makeProductBranch(product=product)
287 with person_logged_in(product.owner):
288 product.development_focus.branch = branch
289 with person_logged_in(branch.owner):
290 self._addBugLinks(branch)
291 view = create_initialized_view(branch, '+index')
292 for bug in view.linked_bugs:
293 self.assertTrue(
294 bug.bugtask.status in UNRESOLVED_BUGTASK_STATUSES)
295
264296
265class TestBranchAddView(TestCaseWithFactory):297class TestBranchAddView(TestCaseWithFactory):
266 """Test the BranchAddView view."""298 """Test the BranchAddView view."""
267299
=== modified file 'lib/lp/code/configure.zcml'
--- lib/lp/code/configure.zcml 2010-05-30 04:06:48 +0000
+++ lib/lp/code/configure.zcml 2010-06-11 05:08:31 +0000
@@ -467,6 +467,7 @@
467 revision_count467 revision_count
468 bug_branches468 bug_branches
469 linked_bugs469 linked_bugs
470 getLinkedBugsAndTasks
470 linkBug471 linkBug
471 unlinkBug472 unlinkBug
472 spec_links473 spec_links
473474
=== modified file 'lib/lp/code/interfaces/branch.py'
--- lib/lp/code/interfaces/branch.py 2010-05-25 03:13:25 +0000
+++ lib/lp/code/interfaces/branch.py 2010-06-11 05:08:31 +0000
@@ -609,6 +609,9 @@
609 readonly=True,609 readonly=True,
610 value_type=Reference(schema=Interface))) # Really IBug610 value_type=Reference(schema=Interface))) # Really IBug
611611
612 def getLinkedBugsAndTasks():
613 """Return a result set for the bugs with their tasks."""
614
612 @call_with(registrant=REQUEST_USER)615 @call_with(registrant=REQUEST_USER)
613 @operation_parameters(616 @operation_parameters(
614 bug=Reference(schema=Interface)) # Really IBug617 bug=Reference(schema=Interface)) # Really IBug
615618
=== modified file 'lib/lp/code/model/branch.py'
--- lib/lp/code/model/branch.py 2010-05-28 09:04:16 +0000
+++ lib/lp/code/model/branch.py 2010-06-11 05:08:31 +0000
@@ -245,6 +245,17 @@
245 'Bug', joinColumn='branch', otherColumn='bug',245 'Bug', joinColumn='branch', otherColumn='bug',
246 intermediateTable='BugBranch', orderBy='id')246 intermediateTable='BugBranch', orderBy='id')
247247
248 def getLinkedBugsAndTasks(self):
249 """Return a result set for the bugs with their tasks."""
250 from lp.bugs.model.bug import Bug
251 from lp.bugs.model.bugbranch import BugBranch
252 from lp.bugs.model.bugtask import BugTask
253 return Store.of(self).find(
254 (Bug, BugTask),
255 BugBranch.branch == self,
256 BugBranch.bug == Bug.id,
257 BugTask.bug == Bug.id)
258
248 def linkBug(self, bug, registrant):259 def linkBug(self, bug, registrant):
249 """See `IBranch`."""260 """See `IBranch`."""
250 return bug.linkBranch(self, registrant)261 return bug.linkBranch(self, registrant)
251262
=== modified file 'lib/lp/code/templates/branch-import-details.pt'
--- lib/lp/code/templates/branch-import-details.pt 2010-01-22 03:16:44 +0000
+++ lib/lp/code/templates/branch-import-details.pt 2010-06-11 05:08:31 +0000
@@ -2,7 +2,7 @@
2 xmlns:tal="http://xml.zope.org/namespaces/tal"2 xmlns:tal="http://xml.zope.org/namespaces/tal"
3 xmlns:metal="http://xml.zope.org/namespaces/metal"3 xmlns:metal="http://xml.zope.org/namespaces/metal"
4 xmlns:i18n="http://xml.zope.org/namespaces/i18n"4 xmlns:i18n="http://xml.zope.org/namespaces/i18n"
5 tal:define="context_menu context/menu:context">5 tal:define="context_menu view/context/menu:context">
66
7 <tal:imported-branch tal:condition="context/branch_type/enumvalue:IMPORTED">7 <tal:imported-branch tal:condition="context/branch_type/enumvalue:IMPORTED">
8 <div id="import-details" tal:define="branch context;8 <div id="import-details" tal:define="branch context;
99
=== modified file 'lib/lp/code/templates/branch-management.pt'
--- lib/lp/code/templates/branch-management.pt 2009-09-30 12:14:24 +0000
+++ lib/lp/code/templates/branch-management.pt 2010-06-11 05:08:31 +0000
@@ -2,7 +2,7 @@
2 xmlns:tal="http://xml.zope.org/namespaces/tal"2 xmlns:tal="http://xml.zope.org/namespaces/tal"
3 xmlns:metal="http://xml.zope.org/namespaces/metal"3 xmlns:metal="http://xml.zope.org/namespaces/metal"
4 xmlns:i18n="http://xml.zope.org/namespaces/i18n"4 xmlns:i18n="http://xml.zope.org/namespaces/i18n"
5 tal:define="context_menu context/menu:context">5 tal:define="context_menu view/context/menu:context">
66
7 <div tal:condition="not: context/revision_count">7 <div tal:condition="not: context/revision_count">
8 <div tal:condition="context/branch_type/enumvalue:IMPORTED">8 <div tal:condition="context/branch_type/enumvalue:IMPORTED">
99
=== modified file 'lib/lp/code/templates/branch-metadata.pt'
--- lib/lp/code/templates/branch-metadata.pt 2010-02-17 01:37:22 +0000
+++ lib/lp/code/templates/branch-metadata.pt 2010-06-11 05:08:31 +0000
@@ -2,7 +2,7 @@
2 xmlns:tal="http://xml.zope.org/namespaces/tal"2 xmlns:tal="http://xml.zope.org/namespaces/tal"
3 xmlns:metal="http://xml.zope.org/namespaces/metal"3 xmlns:metal="http://xml.zope.org/namespaces/metal"
4 xmlns:i18n="http://xml.zope.org/namespaces/i18n"4 xmlns:i18n="http://xml.zope.org/namespaces/i18n"
5 tal:define="context_menu context/menu:context">5 tal:define="context_menu view/context/menu:context">
66
7 <div class="two-column-list">7 <div class="two-column-list">
8 <dl id="branch-format" tal:condition="context/branch_format">8 <dl id="branch-format" tal:condition="context/branch_format">
99
=== modified file 'lib/lp/code/templates/branch-pending-merges.pt'
--- lib/lp/code/templates/branch-pending-merges.pt 2010-05-22 04:19:57 +0000
+++ lib/lp/code/templates/branch-pending-merges.pt 2010-06-11 05:08:31 +0000
@@ -2,7 +2,7 @@
2 xmlns:tal="http://xml.zope.org/namespaces/tal"2 xmlns:tal="http://xml.zope.org/namespaces/tal"
3 xmlns:metal="http://xml.zope.org/namespaces/metal"3 xmlns:metal="http://xml.zope.org/namespaces/metal"
4 xmlns:i18n="http://xml.zope.org/namespaces/i18n"4 xmlns:i18n="http://xml.zope.org/namespaces/i18n"
5 tal:define="context_menu context/menu:context"5 tal:define="context_menu view/context/menu:context"
6 tal:condition="view/show_merge_links">6 tal:condition="view/show_merge_links">
77
8 <h3>Branch merges</h3>8 <h3>Branch merges</h3>
99
=== modified file 'lib/lp/code/templates/branch-portlet-subscribers.pt'
--- lib/lp/code/templates/branch-portlet-subscribers.pt 2010-01-13 00:30:26 +0000
+++ lib/lp/code/templates/branch-portlet-subscribers.pt 2010-06-11 05:08:31 +0000
@@ -4,7 +4,7 @@
4 xmlns:i18n="http://xml.zope.org/namespaces/i18n"4 xmlns:i18n="http://xml.zope.org/namespaces/i18n"
5 class="portlet" id="portlet-subscribers">5 class="portlet" id="portlet-subscribers">
6 <div class="portletBody portletContent"6 <div class="portletBody portletContent"
7 tal:define="context_menu context/menu:context">7 tal:define="context_menu view/context/menu:context">
88
9 <div>9 <div>
10 <div class="actions">10 <div class="actions">
1111
=== modified file 'lib/lp/code/templates/branch-recipes.pt'
--- lib/lp/code/templates/branch-recipes.pt 2010-05-22 02:59:19 +0000
+++ lib/lp/code/templates/branch-recipes.pt 2010-06-11 05:08:31 +0000
@@ -2,7 +2,7 @@
2 xmlns:tal="http://xml.zope.org/namespaces/tal"2 xmlns:tal="http://xml.zope.org/namespaces/tal"
3 xmlns:metal="http://xml.zope.org/namespaces/metal"3 xmlns:metal="http://xml.zope.org/namespaces/metal"
4 xmlns:i18n="http://xml.zope.org/namespaces/i18n"4 xmlns:i18n="http://xml.zope.org/namespaces/i18n"
5 tal:define="context_menu context/menu:context"5 tal:define="context_menu view/context/menu:context"
6 id="related-bugs-and-blueprints">6 id="related-bugs-and-blueprints">
77
8 <h3>Related source package recipes</h3>8 <h3>Related source package recipes</h3>
99
=== modified file 'lib/lp/code/templates/branch-related-bugs-specs.pt'
--- lib/lp/code/templates/branch-related-bugs-specs.pt 2010-05-25 04:37:27 +0000
+++ lib/lp/code/templates/branch-related-bugs-specs.pt 2010-06-11 05:08:31 +0000
@@ -2,7 +2,7 @@
2 xmlns:tal="http://xml.zope.org/namespaces/tal"2 xmlns:tal="http://xml.zope.org/namespaces/tal"
3 xmlns:metal="http://xml.zope.org/namespaces/metal"3 xmlns:metal="http://xml.zope.org/namespaces/metal"
4 xmlns:i18n="http://xml.zope.org/namespaces/i18n"4 xmlns:i18n="http://xml.zope.org/namespaces/i18n"
5 tal:define="context_menu context/menu:context">5 tal:define="context_menu view/context/menu:context">
66
7 <h3>Related bugs</h3>7 <h3>Related bugs</h3>
8 <div id="buglinks" class="actions">8 <div id="buglinks" class="actions">
99
=== modified file 'lib/lp/code/templates/branch-revisions.pt'
--- lib/lp/code/templates/branch-revisions.pt 2009-09-08 21:19:07 +0000
+++ lib/lp/code/templates/branch-revisions.pt 2010-06-11 05:08:31 +0000
@@ -2,7 +2,7 @@
2 xmlns:tal="http://xml.zope.org/namespaces/tal"2 xmlns:tal="http://xml.zope.org/namespaces/tal"
3 xmlns:metal="http://xml.zope.org/namespaces/metal"3 xmlns:metal="http://xml.zope.org/namespaces/metal"
4 xmlns:i18n="http://xml.zope.org/namespaces/i18n"4 xmlns:i18n="http://xml.zope.org/namespaces/i18n"
5 tal:define="context_menu context/menu:context">5 tal:define="context_menu view/context/menu:context">
66
7 <p tal:condition="not:context/revision_count"7 <p tal:condition="not:context/revision_count"
8 tal:define="branch context">8 tal:define="branch context">
@@ -10,7 +10,7 @@
10 </p>10 </p>
1111
12 <tal:history-available condition="context/revision_count"12 <tal:history-available condition="context/revision_count"
13 define="branch context;13 define="branch view/context;
14 revisions branch/latest_revisions">14 revisions branch/latest_revisions">
15 <metal:landing-target use-macro="branch/@@+macros/branch-revisions"/>15 <metal:landing-target use-macro="branch/@@+macros/branch-revisions"/>
1616
1717
=== modified file 'lib/lp/testing/factory.py'
--- lib/lp/testing/factory.py 2010-06-10 07:09:44 +0000
+++ lib/lp/testing/factory.py 2010-06-11 05:08:31 +0000
@@ -1092,7 +1092,8 @@
10921092
1093 def makeBug(self, product=None, owner=None, bug_watch_url=None,1093 def makeBug(self, product=None, owner=None, bug_watch_url=None,
1094 private=False, date_closed=None, title=None,1094 private=False, date_closed=None, title=None,
1095 date_created=None, description=None, comment=None):1095 date_created=None, description=None, comment=None,
1096 status=None):
1096 """Create and return a new, arbitrary Bug.1097 """Create and return a new, arbitrary Bug.
10971098
1098 The bug returned uses default values where possible. See1099 The bug returned uses default values where possible. See
@@ -1114,7 +1115,8 @@
1114 comment = self.getUniqueString()1115 comment = self.getUniqueString()
1115 create_bug_params = CreateBugParams(1116 create_bug_params = CreateBugParams(
1116 owner, title, comment=comment, private=private,1117 owner, title, comment=comment, private=private,
1117 datecreated=date_created, description=description)1118 datecreated=date_created, description=description,
1119 status=status)
1118 create_bug_params.setBugTarget(product=product)1120 create_bug_params.setBugTarget(product=product)
1119 bug = getUtility(IBugSet).createBug(create_bug_params)1121 bug = getUtility(IBugSet).createBug(create_bug_params)
1120 if bug_watch_url is not None:1122 if bug_watch_url is not None: