launchpad-reviewers team mailing list archive
-
launchpad-reviewers team
-
Mailing list archive
-
Message #11733
[Merge] lp:~stevenk/launchpad/bugtask-activity-preload into lp:launchpad
Steve Kowalik has proposed merging lp:~stevenk/launchpad/bugtask-activity-preload into lp:launchpad.
Requested reviews:
Launchpad code reviewers (launchpad-reviewers)
Related bugs:
Bug #1037532 in Launchpad itself: "BugTask:+activity Timeout looping over 100s of people"
https://bugs.launchpad.net/launchpad/+bug/1037532
For more details, see:
https://code.launchpad.net/~stevenk/launchpad/bugtask-activity-preload/+merge/123484
Change Bug:+activity to bulk load the people from ValidPersonCache. With 10 BugActivity rows, the query count drops from 13 to 5, and with 50 rows the query count drops from 53 to 5. This also required adding a personID attribute onto IBugActivity.
--
https://code.launchpad.net/~stevenk/launchpad/bugtask-activity-preload/+merge/123484
Your team Launchpad code reviewers is requested to review the proposed merge of lp:~stevenk/launchpad/bugtask-activity-preload into lp:launchpad.
=== modified file 'lib/lp/bugs/browser/bug.py'
--- lib/lp/bugs/browser/bug.py 2012-08-26 22:50:37 +0000
+++ lib/lp/bugs/browser/bug.py 2012-09-10 06:08:19 +0000
@@ -103,7 +103,9 @@
get_structural_subscriptions_for_bug,
)
from lp.registry.enums import PRIVATE_INFORMATION_TYPES
+from lp.registry.model.person import ValidPersonCache
from lp.registry.vocabularies import InformationTypeVocabulary
+from lp.services.database.bulk import load_related
from lp.services.fields import DuplicateBug
from lp.services.librarian.browser import ProxiedLibraryFileAlias
from lp.services.mail.mailwrapper import MailWrapper
@@ -605,6 +607,12 @@
page_title = 'Activity log'
+ @property
+ def activity(self):
+ activity = IBug(self.context).activity
+ load_related(ValidPersonCache, activity, ['personID'])
+ return activity
+
class BugSubscriptionPortletDetails:
"""A mixin used to collate bug subscription details for a view."""
=== modified file 'lib/lp/bugs/browser/tests/test_bug_views.py'
--- lib/lp/bugs/browser/tests/test_bug_views.py 2012-09-06 00:01:38 +0000
+++ lib/lp/bugs/browser/tests/test_bug_views.py 2012-09-10 06:08:19 +0000
@@ -5,20 +5,29 @@
__metaclass__ = type
+from datetime import (
+ datetime,
+ timedelta,
+ )
+
from BeautifulSoup import BeautifulSoup
+import pytz
import simplejson
from soupmatchers import (
HTMLContains,
Tag,
)
+from storm.store import Store
from testtools.matchers import (
Contains,
+ Equals,
MatchesAll,
Not,
)
from zope.component import getUtility
from zope.security.proxy import removeSecurityProxy
+from lp.bugs.adapters.bugchange import BugAttachmentChange
from lp.registry.enums import (
BugSharingPolicy,
InformationType,
@@ -35,12 +44,14 @@
BrowserTestCase,
login_person,
person_logged_in,
+ StormStatementRecorder,
TestCaseWithFactory,
)
from lp.testing.layers import (
DatabaseFunctionalLayer,
LaunchpadFunctionalLayer,
)
+from lp.testing.matchers import HasQueryCount
from lp.testing.pages import find_tag_by_id
from lp.testing.views import (
create_initialized_view,
@@ -673,3 +684,26 @@
'table',
{'id': 'affected-software', 'class': 'listing'})
self.assertIsNotNone(table)
+
+
+class TestBugActivityView(TestCaseWithFactory):
+
+ layer = LaunchpadFunctionalLayer
+
+ def test_bug_activity_query_count(self):
+ # Bug:+activity doesn't make O(n) queries based on the amount of
+ # activity.
+ bug = self.factory.makeBug()
+ ten_minutes_ago = datetime.now(pytz.UTC) - timedelta(minutes=10)
+ with person_logged_in(bug.owner):
+ attachment = self.factory.makeBugAttachment(bug=bug)
+ for i in range(10):
+ bug.addChange(BugAttachmentChange(
+ ten_minutes_ago, self.factory.makePerson(), 'attachment',
+ None, attachment))
+ Store.of(bug).flush()
+ with StormStatementRecorder() as recorder:
+ view = create_initialized_view(
+ bug.default_bugtask, name='+activity')
+ view.render()
+ self.assertThat(recorder, HasQueryCount(Equals(5)))
=== modified file 'lib/lp/bugs/interfaces/bugactivity.py'
--- lib/lp/bugs/interfaces/bugactivity.py 2011-12-24 16:54:44 +0000
+++ lib/lp/bugs/interfaces/bugactivity.py 2012-09-10 06:08:19 +0000
@@ -16,7 +16,10 @@
export_as_webservice_entry,
exported,
)
-from zope.interface import Interface
+from zope.interface import (
+ Attribute,
+ Interface,
+ )
from zope.schema import (
Datetime,
Text,
@@ -42,6 +45,7 @@
description=_("The date on which this activity occurred."),
readonly=True))
+ personID = Attribute('DB ID for Person')
person = exported(PersonChoice(
title=_('Person'), required=True, vocabulary='ValidPersonOrTeam',
readonly=True, description=_("The person's Launchpad ID or "
=== modified file 'lib/lp/bugs/templates/bug-activity.pt'
--- lib/lp/bugs/templates/bug-activity.pt 2010-10-10 21:54:16 +0000
+++ lib/lp/bugs/templates/bug-activity.pt 2012-09-10 06:08:19 +0000
@@ -20,7 +20,7 @@
</tr>
</thead>
<tbody>
- <tr tal:repeat="log context/bug/activity">
+ <tr tal:repeat="log view/activity">
<tal:comment condition="nothing">
XXX: Gavin Panella 2009-08-12 bug=412963: Using strftime()
here because fmt:datetime changes timezone, even though we
Follow ups