Merge lp:~jtv/launchpad/bug-403992 into lp:launchpad
- bug-403992
- Merge into devel
Status: | Merged | ||||
---|---|---|---|---|---|
Approved by: | Brad Crittenden | ||||
Approved revision: | no longer in the source branch. | ||||
Merged at revision: | not available | ||||
Proposed branch: | lp:~jtv/launchpad/bug-403992 | ||||
Merge into: | lp:launchpad | ||||
Diff against target: | None lines | ||||
To merge this branch: | bzr merge lp:~jtv/launchpad/bug-403992 | ||||
Related bugs: |
|
Reviewer | Review Type | Date Requested | Status |
---|---|---|---|
Brad Crittenden (community) | Approve | ||
Review via email: mp+9690@code.launchpad.net |
Commit message
Description of the change
Jeroen T. Vermeulen (jtv) wrote : | # |
Brad Crittenden (bac) wrote : | # |
Hi Jeroen,
This branch is a nice clean up. I've got a few comments on style.
I'm curious also about your/Danilo's choice to re-open a bug that was
fix-committed to make these clean-up changes. Seems like an odd way
to handle it, but not really any of my concern here.
> === modified file 'lib/lp/
> --- lib/lp/
> +++ lib/lp/
> @@ -15,3 +15,10 @@
>
> >>> retcode
> 0
> +
> +
> +# The script modified the database, even though the database layer may
> +# not have noticed it.
> +
> + >>> from canonical.
> + >>> LaunchpadTestSe
> === modified file 'lib/lp/
> --- lib/lp/
> +++ lib/lp/
Would you mind fixing the __all__ line to make it multi-line (is that our convention when there is just one entry?) or remove the extra spaces.
> @@ -8,8 +8,9 @@
> from zope.component import getUtility
> from zope.security.proxy import removeSecurityProxy
>
> +from canonical.
> from lp.translations
> -from canonical.
> +from lp.translations
> from lp.registry.
> from lp.registry.
> from lp.services.
> @@ -146,6 +147,8 @@
>
> class MessageSharingM
>
> + templateset = None
How about 'template_set' as it follows our coding standard?
> def add_my_
> self.parser.
> help="Distribution to merge messages for.")
> @@ -166,6 +169,16 @@
> action=
> help="Dry run, don't really make any changes.")
>
> + def _setUpUtilities
> + """Prepare a few members that several methods need.
> +
> + Calling this again later does nothing.
> + """
> + if self.templateset is None:
> + self.templateset = getUtility(
> + self.compare_
> + self.templatese
> +
> def main(self):
> actions = (
> self.options.
> @@ -214,7 +227,9 @@
> "Unknown source package name: '%s'" %
> self.options.
>
> - subset = getUtility(
> + self._setUpUtil
> +
> + subset = self.templatese
> product=product, distribution=
> sourcepackagena
> equivalence...
Jeroen T. Vermeulen (jtv) wrote : | # |
Hi Brad! Thanks for the review. This branch has been lying around for
a while, waiting for someone to review it. Unlike its cherry-pickable
sibling it's not urgent, but I'm glad to have it out of the way.
> I'm curious also about your/Danilo's choice to re-open a bug that was
> fix-committed to make these clean-up changes. Seems like an odd way
> to handle it, but not really any of my concern here.
I wouldn't say that was our "choice." What happened was that I prepared
two branches for the same problem: one immediate, absolutely minimal fix
for cherry-picking, and this conventional full fix as a superset of the
former. The cherry-picking branch has landed, and the bug went through
a brief tentative phase of being "fix committed" because of that. But
it all happened well after this branch here went up for review.
> > === modified file 'lib/lp/
> > --- lib/lp/
> 04:41:14 +0000
> > +++ lib/lp/
> 11:44:49 +0000
>
> Would you mind fixing the __all__ line to make it multi-line (is that our
> convention when there is just one entry?) or remove the extra spaces.
Don't mind at all. Done.
> > @@ -146,6 +147,8 @@
> >
> > class MessageSharingM
> >
> > + templateset = None
>
> How about 'template_set' as it follows our coding standard?
In English you never really know two words have become one until one of
them changes, like the "sheep" in "shepherd."
I think I chose "templateset" to distinguish the utility from a mere set
of templates. Then again, naming variables after their type should not
be taken this far anyway.
> > @@ -361,7 +370,13 @@
> > potmsgset (because we start out with one) and potemplate (because
> > that's sorted out in the nested dicts).
> > """
> > - return (tm.language, tm.variant) + tuple(tm.
> > + tm = removeSecurityP
> > + msgstr_ids = [
> > + getattr(tm, 'msgstr%dID' % form)
> > + for form in xrange(
> > + ]
>
> The ] should be dedented by 4.
Ah, my editor is showing a mind of its own. Can't have that.
Hi ho, hi ho, to PQM I go!
Jeroen
Preview Diff
1 | === modified file 'lib/lp/translations/doc/message-sharing-merge-script.txt' | |||
2 | --- lib/lp/translations/doc/message-sharing-merge-script.txt 2009-07-06 08:04:08 +0000 | |||
3 | +++ lib/lp/translations/doc/message-sharing-merge-script.txt 2009-08-04 13:37:57 +0000 | |||
4 | @@ -15,3 +15,10 @@ | |||
5 | 15 | 15 | ||
6 | 16 | >>> retcode | 16 | >>> retcode |
7 | 17 | 0 | 17 | 0 |
8 | 18 | |||
9 | 19 | |||
10 | 20 | # The script modified the database, even though the database layer may | ||
11 | 21 | # not have noticed it. | ||
12 | 22 | |||
13 | 23 | >>> from canonical.launchpad.ftests.harness import LaunchpadTestSetup | ||
14 | 24 | >>> LaunchpadTestSetup().force_dirty_database() | ||
15 | 18 | 25 | ||
16 | === modified file 'lib/lp/translations/scripts/message_sharing_migration.py' | |||
17 | --- lib/lp/translations/scripts/message_sharing_migration.py 2009-07-19 04:41:14 +0000 | |||
18 | +++ lib/lp/translations/scripts/message_sharing_migration.py 2009-08-05 11:44:49 +0000 | |||
19 | @@ -8,8 +8,9 @@ | |||
20 | 8 | from zope.component import getUtility | 8 | from zope.component import getUtility |
21 | 9 | from zope.security.proxy import removeSecurityProxy | 9 | from zope.security.proxy import removeSecurityProxy |
22 | 10 | 10 | ||
23 | 11 | from canonical.launchpad.utilities.orderingcheck import OrderingCheck | ||
24 | 11 | from lp.translations.interfaces.potemplate import IPOTemplateSet | 12 | from lp.translations.interfaces.potemplate import IPOTemplateSet |
26 | 12 | from canonical.launchpad.utilities.orderingcheck import OrderingCheck | 13 | from lp.translations.interfaces.translations import TranslationConstants |
27 | 13 | from lp.registry.interfaces.product import IProductSet | 14 | from lp.registry.interfaces.product import IProductSet |
28 | 14 | from lp.registry.interfaces.sourcepackagename import ISourcePackageNameSet | 15 | from lp.registry.interfaces.sourcepackagename import ISourcePackageNameSet |
29 | 15 | from lp.services.scripts.base import ( | 16 | from lp.services.scripts.base import ( |
30 | @@ -146,6 +147,8 @@ | |||
31 | 146 | 147 | ||
32 | 147 | class MessageSharingMerge(LaunchpadScript): | 148 | class MessageSharingMerge(LaunchpadScript): |
33 | 148 | 149 | ||
34 | 150 | templateset = None | ||
35 | 151 | |||
36 | 149 | def add_my_options(self): | 152 | def add_my_options(self): |
37 | 150 | self.parser.add_option('-d', '--distribution', dest='distribution', | 153 | self.parser.add_option('-d', '--distribution', dest='distribution', |
38 | 151 | help="Distribution to merge messages for.") | 154 | help="Distribution to merge messages for.") |
39 | @@ -166,6 +169,16 @@ | |||
40 | 166 | action='store_true', | 169 | action='store_true', |
41 | 167 | help="Dry run, don't really make any changes.") | 170 | help="Dry run, don't really make any changes.") |
42 | 168 | 171 | ||
43 | 172 | def _setUpUtilities(self): | ||
44 | 173 | """Prepare a few members that several methods need. | ||
45 | 174 | |||
46 | 175 | Calling this again later does nothing. | ||
47 | 176 | """ | ||
48 | 177 | if self.templateset is None: | ||
49 | 178 | self.templateset = getUtility(IPOTemplateSet) | ||
50 | 179 | self.compare_template_precedence = ( | ||
51 | 180 | self.templateset.compareSharingPrecedence) | ||
52 | 181 | |||
53 | 169 | def main(self): | 182 | def main(self): |
54 | 170 | actions = ( | 183 | actions = ( |
55 | 171 | self.options.merge_potmsgsets or | 184 | self.options.merge_potmsgsets or |
56 | @@ -214,7 +227,9 @@ | |||
57 | 214 | "Unknown source package name: '%s'" % | 227 | "Unknown source package name: '%s'" % |
58 | 215 | self.options.sourcepackage) | 228 | self.options.sourcepackage) |
59 | 216 | 229 | ||
61 | 217 | subset = getUtility(IPOTemplateSet).getSharingSubset( | 230 | self._setUpUtilities() |
62 | 231 | |||
63 | 232 | subset = self.templateset.getSharingSubset( | ||
64 | 218 | product=product, distribution=distribution, | 233 | product=product, distribution=distribution, |
65 | 219 | sourcepackagename=sourcepackagename) | 234 | sourcepackagename=sourcepackagename) |
66 | 220 | equivalence_classes = subset.groupEquivalentPOTemplates( | 235 | equivalence_classes = subset.groupEquivalentPOTemplates( |
67 | @@ -250,6 +265,7 @@ | |||
68 | 250 | 265 | ||
69 | 251 | def _mergePOTMsgSets(self, potemplates): | 266 | def _mergePOTMsgSets(self, potemplates): |
70 | 252 | """Merge POTMsgSets for given sequence of sharing templates.""" | 267 | """Merge POTMsgSets for given sequence of sharing templates.""" |
71 | 268 | self._setUpUtilities() | ||
72 | 253 | 269 | ||
73 | 254 | # Map each POTMsgSet key (context, msgid, plural) to its | 270 | # Map each POTMsgSet key (context, msgid, plural) to its |
74 | 255 | # representative POTMsgSet. | 271 | # representative POTMsgSet. |
75 | @@ -267,8 +283,7 @@ | |||
76 | 267 | # through the templates, starting at the most representative and | 283 | # through the templates, starting at the most representative and |
77 | 268 | # moving towards the least representative. For any unique potmsgset | 284 | # moving towards the least representative. For any unique potmsgset |
78 | 269 | # key we find, the first POTMsgSet is the representative one. | 285 | # key we find, the first POTMsgSet is the representative one. |
81 | 270 | templateset = getUtility(IPOTemplateSet) | 286 | order_check = OrderingCheck(cmp=self.compare_template_precedence) |
80 | 271 | order_check = OrderingCheck(cmp=templateset.compareSharingPrecedence) | ||
82 | 272 | 287 | ||
83 | 273 | for template in potemplates: | 288 | for template in potemplates: |
84 | 274 | order_check.check(template) | 289 | order_check.check(template) |
85 | @@ -288,13 +303,7 @@ | |||
86 | 288 | # translation messages. We don't need do this for subordinates | 303 | # translation messages. We don't need do this for subordinates |
87 | 289 | # because the algorithm will refuse to add new duplicates to the | 304 | # because the algorithm will refuse to add new duplicates to the |
88 | 290 | # representative POTMsgSet anyway. | 305 | # representative POTMsgSet anyway. |
96 | 291 | existing_tms = self._scrubPOTMsgSetTranslations(representative) | 306 | self._scrubPOTMsgSetTranslations(representative) |
90 | 292 | |||
91 | 293 | # Keep track of current/imported TranslationMessages for | ||
92 | 294 | # representative. These will matter when we try to merge | ||
93 | 295 | # subordinate TranslationMessages into the representative, some | ||
94 | 296 | # of which may be current or imported as well. | ||
95 | 297 | current_tms, imported_tms = self._findUsedMessages(existing_tms) | ||
97 | 298 | 307 | ||
98 | 299 | seen_potmsgsets = set([representative]) | 308 | seen_potmsgsets = set([representative]) |
99 | 300 | 309 | ||
100 | @@ -309,8 +318,8 @@ | |||
101 | 309 | message = removeSecurityProxy(message) | 318 | message = removeSecurityProxy(message) |
102 | 310 | 319 | ||
103 | 311 | clashing_current, clashing_imported, twin = ( | 320 | clashing_current, clashing_imported, twin = ( |
106 | 312 | self._findClashesFromDicts( | 321 | self._findClashes( |
107 | 313 | existing_tms, current_tms, imported_tms, message)) | 322 | message, representative, message.potemplate)) |
108 | 314 | 323 | ||
109 | 315 | if clashing_current or clashing_imported: | 324 | if clashing_current or clashing_imported: |
110 | 316 | saved = self._saveByDiverging( | 325 | saved = self._saveByDiverging( |
111 | @@ -345,8 +354,8 @@ | |||
112 | 345 | 354 | ||
113 | 346 | def _mergeTranslationMessages(self, potemplates): | 355 | def _mergeTranslationMessages(self, potemplates): |
114 | 347 | """Share `TranslationMessage`s between templates where possible.""" | 356 | """Share `TranslationMessage`s between templates where possible.""" |
117 | 348 | templateset = getUtility(IPOTemplateSet) | 357 | self._setUpUtilities() |
118 | 349 | order_check = OrderingCheck(cmp=templateset.compareSharingPrecedence) | 358 | order_check = OrderingCheck(cmp=self.compare_template_precedence) |
119 | 350 | for template in potemplates: | 359 | for template in potemplates: |
120 | 351 | order_check.check(template) | 360 | order_check.check(template) |
121 | 352 | for potmsgset in template.getPOTMsgSets(False): | 361 | for potmsgset in template.getPOTMsgSets(False): |
122 | @@ -361,7 +370,13 @@ | |||
123 | 361 | potmsgset (because we start out with one) and potemplate (because | 370 | potmsgset (because we start out with one) and potemplate (because |
124 | 362 | that's sorted out in the nested dicts). | 371 | that's sorted out in the nested dicts). |
125 | 363 | """ | 372 | """ |
127 | 364 | return (tm.language, tm.variant) + tuple(tm.all_msgstrs) | 373 | tm = removeSecurityProxy(tm) |
128 | 374 | msgstr_ids = [ | ||
129 | 375 | getattr(tm, 'msgstr%dID' % form) | ||
130 | 376 | for form in xrange(TranslationConstants.MAX_PLURAL_FORMS) | ||
131 | 377 | ] | ||
132 | 378 | |||
133 | 379 | return (tm.language, tm.variant) + tuple(msgstr_ids) | ||
134 | 365 | 380 | ||
135 | 366 | def _mapExistingMessages(self, potmsgset): | 381 | def _mapExistingMessages(self, potmsgset): |
136 | 367 | """Map out the existing TranslationMessages for `potmsgset`. | 382 | """Map out the existing TranslationMessages for `potmsgset`. |
137 | @@ -387,33 +402,6 @@ | |||
138 | 387 | 402 | ||
139 | 388 | return existing_tms | 403 | return existing_tms |
140 | 389 | 404 | ||
141 | 390 | def _findUsedMessages(self, translations): | ||
142 | 391 | """Fish current and imported messages out of translations dict. | ||
143 | 392 | |||
144 | 393 | :param translations: a dict as returned by | ||
145 | 394 | `_mapExistingMessages` or `_scrubPOTMsgSetTranslations`. All | ||
146 | 395 | information is taken from this dict; no other messages are | ||
147 | 396 | considered. | ||
148 | 397 | :return: a pair of dicts, each mapping (potemplate, language, | ||
149 | 398 | variant) to a TranslationMessage or to None. The dicts map | ||
150 | 399 | out current and imported messages, respectively. Shared | ||
151 | 400 | messages have a POTemplate of None. | ||
152 | 401 | """ | ||
153 | 402 | current_messages = {} | ||
154 | 403 | imported_messages = {} | ||
155 | 404 | for per_template in translations.itervalues(): | ||
156 | 405 | for tms in per_template.itervalues(): | ||
157 | 406 | assert len(tms) == 1, ( | ||
158 | 407 | "Unexpected list size: %d items." % len(tms)) | ||
159 | 408 | tm = tms[0] | ||
160 | 409 | key = (tm.potemplate, tm.language, tm.variant) | ||
161 | 410 | if tm.is_current: | ||
162 | 411 | current_messages[key] = tm | ||
163 | 412 | if tm.is_imported: | ||
164 | 413 | imported_messages[key] = tm | ||
165 | 414 | |||
166 | 415 | return current_messages, imported_messages | ||
167 | 416 | |||
168 | 417 | def _scrubPOTMsgSetTranslations(self, potmsgset): | 405 | def _scrubPOTMsgSetTranslations(self, potmsgset): |
169 | 418 | """Map out translations for `potmsgset`, and eliminate duplicates. | 406 | """Map out translations for `potmsgset`, and eliminate duplicates. |
170 | 419 | 407 | ||
171 | @@ -487,41 +475,6 @@ | |||
172 | 487 | # message can be merged into the twin without problems. | 475 | # message can be merged into the twin without problems. |
173 | 488 | return filter_clashes(clashing_current, clashing_imported, twin) | 476 | return filter_clashes(clashing_current, clashing_imported, twin) |
174 | 489 | 477 | ||
175 | 490 | def _findClashesFromDicts(self, existing_tms, current_tms, imported_tms, | ||
176 | 491 | message): | ||
177 | 492 | """Like `_findClashes`, but from cached dicts. | ||
178 | 493 | |||
179 | 494 | This saves some database querying for the common case. | ||
180 | 495 | |||
181 | 496 | :param existing_tms: a dict as returned by | ||
182 | 497 | `_mapExistingMessages`. | ||
183 | 498 | :param current_tms: a dict as returned by `_findUsedMessages`. | ||
184 | 499 | """ | ||
185 | 500 | twins_dict = existing_tms.get( | ||
186 | 501 | self._getPOTMsgSetTranslationMessageKey(message)) | ||
187 | 502 | if twins_dict is None: | ||
188 | 503 | twin = None | ||
189 | 504 | else: | ||
190 | 505 | twins = twins_dict.get(message.potemplate) | ||
191 | 506 | if twins is None: | ||
192 | 507 | twin = None | ||
193 | 508 | else: | ||
194 | 509 | assert len(twins) == 1, "Did not expect %d twins." % ( | ||
195 | 510 | len(twins)) | ||
196 | 511 | twin = twins[0] | ||
197 | 512 | |||
198 | 513 | subkey = message.potemplate, message.language, message.variant | ||
199 | 514 | if message.is_current: | ||
200 | 515 | clashing_current = current_tms.get(subkey) | ||
201 | 516 | else: | ||
202 | 517 | clashing_current = None | ||
203 | 518 | if message.is_imported: | ||
204 | 519 | clashing_imported = imported_tms.get(subkey) | ||
205 | 520 | else: | ||
206 | 521 | clashing_imported = None | ||
207 | 522 | |||
208 | 523 | return filter_clashes(clashing_current, clashing_imported, twin) | ||
209 | 524 | |||
210 | 525 | def _saveByDiverging(self, message, target_potmsgset, source_potmsgset): | 478 | def _saveByDiverging(self, message, target_potmsgset, source_potmsgset): |
211 | 526 | """Avoid a TranslationMessage clash during POTMsgSet merge. | 479 | """Avoid a TranslationMessage clash during POTMsgSet merge. |
212 | 527 | 480 | ||
213 | @@ -539,8 +492,10 @@ | |||
214 | 539 | # This message was shared. Maybe we can still save it for at | 492 | # This message was shared. Maybe we can still save it for at |
215 | 540 | # least one template by making it diverged. | 493 | # least one template by making it diverged. |
216 | 541 | target_ttis = source_potmsgset.getAllTranslationTemplateItems() | 494 | target_ttis = source_potmsgset.getAllTranslationTemplateItems() |
219 | 542 | for tti in target_ttis: | 495 | target_templates = [tti.potemplate for tti in target_ttis] |
220 | 543 | if self._divergeTo(message, target_potmsgset, tti.potemplate): | 496 | target_templates.sort(self.compare_template_precedence) |
221 | 497 | for template in target_templates: | ||
222 | 498 | if self._divergeTo(message, target_potmsgset, template): | ||
223 | 544 | return True | 499 | return True |
224 | 545 | 500 | ||
225 | 546 | # No, there's no place where this message can be preserved. It'll | 501 | # No, there's no place where this message can be preserved. It'll |
226 | 547 | 502 | ||
227 | === modified file 'lib/lp/translations/scripts/tests/test_message_sharing_migration.py' | |||
228 | --- lib/lp/translations/scripts/tests/test_message_sharing_migration.py 2009-07-19 04:41:14 +0000 | |||
229 | +++ lib/lp/translations/scripts/tests/test_message_sharing_migration.py 2009-08-05 11:44:49 +0000 | |||
230 | @@ -41,7 +41,7 @@ | |||
231 | 41 | self.stable_template.iscurrent = False | 41 | self.stable_template.iscurrent = False |
232 | 42 | self.templates = [self.trunk_template, self.stable_template] | 42 | self.templates = [self.trunk_template, self.stable_template] |
233 | 43 | 43 | ||
235 | 44 | self.script = MessageSharingMerge('tms-merging-test') | 44 | self.script = MessageSharingMerge('tms-merging-test', test_args=[]) |
236 | 45 | self.script.logger.setLevel(ERROR) | 45 | self.script.logger.setLevel(ERROR) |
237 | 46 | 46 | ||
238 | 47 | 47 | ||
239 | @@ -617,47 +617,6 @@ | |||
240 | 617 | 617 | ||
241 | 618 | self.assertEqual(map, expected) | 618 | self.assertEqual(map, expected) |
242 | 619 | 619 | ||
243 | 620 | def test_FindNoUsedMessage(self): | ||
244 | 621 | # Test _findUsedMessage against a case where there are no used | ||
245 | 622 | # messages. | ||
246 | 623 | message = self._makeTranslationMessage( | ||
247 | 624 | pofile=self.trunk_pofile, potmsgset=self.trunk_potmsgset, | ||
248 | 625 | text='godot', diverged=False) | ||
249 | 626 | message.is_current = False | ||
250 | 627 | key = self.script._getPOTMsgSetTranslationMessageKey(message) | ||
251 | 628 | map = {key: {self.trunk_template: [message]}} | ||
252 | 629 | |||
253 | 630 | self.assertEqual(self.script._findUsedMessages(map), ({}, {})) | ||
254 | 631 | |||
255 | 632 | def test_FindUsedMessages(self): | ||
256 | 633 | # _findUsedMessages maps diverged messages based on template, | ||
257 | 634 | # language, and variant. The difference for shared messages is | ||
258 | 635 | # that their template is None. | ||
259 | 636 | imported_message = self._makeTranslationMessage( | ||
260 | 637 | pofile=self.trunk_pofile, potmsgset=self.trunk_potmsgset, | ||
261 | 638 | text='pog', diverged=True) | ||
262 | 639 | imported_message.is_current = False | ||
263 | 640 | imported_message.is_imported = True | ||
264 | 641 | current_message = self._makeTranslationMessage( | ||
265 | 642 | pofile=self.trunk_pofile, potmsgset=self.trunk_potmsgset, | ||
266 | 643 | text='klexdigal', diverged=False) | ||
267 | 644 | |||
268 | 645 | current_key = self.script._getPOTMsgSetTranslationMessageKey( | ||
269 | 646 | current_message) | ||
270 | 647 | imported_key = self.script._getPOTMsgSetTranslationMessageKey( | ||
271 | 648 | imported_message) | ||
272 | 649 | |||
273 | 650 | map = { | ||
274 | 651 | current_key: {self.trunk_template: [current_message]}, | ||
275 | 652 | imported_key: { self.trunk_template: [imported_message]}, | ||
276 | 653 | } | ||
277 | 654 | |||
278 | 655 | expected = ( | ||
279 | 656 | {(None, self.dutch, None): current_message}, | ||
280 | 657 | {(self.trunk_template, self.dutch, None): imported_message}) | ||
281 | 658 | |||
282 | 659 | self.assertEqual(self.script._findUsedMessages(map), expected) | ||
283 | 660 | |||
284 | 661 | def test_ScrubPOTMsgSetTranslationsWithoutDuplication(self): | 620 | def test_ScrubPOTMsgSetTranslationsWithoutDuplication(self): |
285 | 662 | # _scrubPOTMsgSetTranslations eliminates duplicated | 621 | # _scrubPOTMsgSetTranslations eliminates duplicated |
286 | 663 | # TranslationMessages. If it doesn't find any, nothing happens. | 622 | # TranslationMessages. If it doesn't find any, nothing happens. |
287 | @@ -776,95 +735,6 @@ | |||
288 | 776 | self.assertEqual(imported_clash, None) | 735 | self.assertEqual(imported_clash, None) |
289 | 777 | self.assertEqual(twin, trunk_message) | 736 | self.assertEqual(twin, trunk_message) |
290 | 778 | 737 | ||
291 | 779 | def test_FindCurrentClashFromDicts(self): | ||
292 | 780 | # Like test_FindCurrentClash, but using cached dicts. | ||
293 | 781 | trunk_message, stable_message = self._makeTranslationMessages( | ||
294 | 782 | 'ex', 'why', trunk_diverged=False, stable_diverged=False) | ||
295 | 783 | |||
296 | 784 | trunk_key = self.script._getPOTMsgSetTranslationMessageKey( | ||
297 | 785 | trunk_message) | ||
298 | 786 | stable_key = self.script._getPOTMsgSetTranslationMessageKey( | ||
299 | 787 | stable_message) | ||
300 | 788 | |||
301 | 789 | existing = self.script._mapExistingMessages(self.trunk_potmsgset) | ||
302 | 790 | current, imported = self.script._findUsedMessages(existing) | ||
303 | 791 | current_clash, imported_clash, twin = ( | ||
304 | 792 | self.script._findClashesFromDicts( | ||
305 | 793 | existing, current, imported, stable_message)) | ||
306 | 794 | |||
307 | 795 | self.assertEqual(current_clash, trunk_message) | ||
308 | 796 | self.assertEqual(imported_clash, None) | ||
309 | 797 | self.assertEqual(twin, None) | ||
310 | 798 | |||
311 | 799 | |||
312 | 800 | def test_FindImportedClashFromDicts(self): | ||
313 | 801 | # Like test_FindImportedClash, but using cached dicts. | ||
314 | 802 | trunk_message, stable_message = self._makeTranslationMessages( | ||
315 | 803 | 'ex', 'why', trunk_diverged=False, stable_diverged=False) | ||
316 | 804 | |||
317 | 805 | for message in (trunk_message, stable_message): | ||
318 | 806 | message.is_current = False | ||
319 | 807 | message.is_imported = True | ||
320 | 808 | |||
321 | 809 | existing = self.script._mapExistingMessages(self.trunk_potmsgset) | ||
322 | 810 | current, imported = self.script._findUsedMessages(existing) | ||
323 | 811 | current_clash, imported_clash, twin = ( | ||
324 | 812 | self.script._findClashesFromDicts( | ||
325 | 813 | existing, current, imported, stable_message)) | ||
326 | 814 | |||
327 | 815 | self.assertEqual(current_clash, None) | ||
328 | 816 | self.assertEqual(imported_clash, trunk_message) | ||
329 | 817 | self.assertEqual(twin, None) | ||
330 | 818 | |||
331 | 819 | def test_FindTwinFromDicts(self): | ||
332 | 820 | # Like test_FindTwin, but using cached dicts. | ||
333 | 821 | trunk_message, stable_message = self._makeTranslationMessages( | ||
334 | 822 | 'klob', 'klob', trunk_diverged=False, stable_diverged=False) | ||
335 | 823 | trunk_message.is_current = False | ||
336 | 824 | |||
337 | 825 | existing = self.script._mapExistingMessages(self.trunk_potmsgset) | ||
338 | 826 | current, imported = self.script._findUsedMessages(existing) | ||
339 | 827 | current_clash, imported_clash, twin = ( | ||
340 | 828 | self.script._findClashesFromDicts( | ||
341 | 829 | existing, current, imported, stable_message)) | ||
342 | 830 | |||
343 | 831 | self.assertEqual(current_clash, None) | ||
344 | 832 | self.assertEqual(imported_clash, None) | ||
345 | 833 | self.assertEqual(twin, trunk_message) | ||
346 | 834 | |||
347 | 835 | def test_FindClashesWithTwinFromDicts(self): | ||
348 | 836 | # Like test_FindClashesWithTwin, but using cached dicts. | ||
349 | 837 | trunk_message, stable_message = self._makeTranslationMessages( | ||
350 | 838 | 'sniw', 'sniw', trunk_diverged=False, stable_diverged=False) | ||
351 | 839 | |||
352 | 840 | existing = self.script._mapExistingMessages(self.trunk_potmsgset) | ||
353 | 841 | current, imported = self.script._findUsedMessages(existing) | ||
354 | 842 | current_clash, imported_clash, twin = ( | ||
355 | 843 | self.script._findClashesFromDicts( | ||
356 | 844 | existing, current, imported, stable_message)) | ||
357 | 845 | |||
358 | 846 | self.assertEqual(current_clash, None) | ||
359 | 847 | self.assertEqual(imported_clash, None) | ||
360 | 848 | self.assertEqual(twin, trunk_message) | ||
361 | 849 | |||
362 | 850 | def test_FindClashesWithNonTwinFromDicts(self): | ||
363 | 851 | # Like test_FindClashesWithNonTwin, but using cached dicts. | ||
364 | 852 | trunk_message, stable_message = self._makeTranslationMessages( | ||
365 | 853 | 'sniw', 'sniw', trunk_diverged=False, stable_diverged=False) | ||
366 | 854 | trunk_message.is_current = False | ||
367 | 855 | current_message = self._makeTranslationMessage( | ||
368 | 856 | self.trunk_pofile, self.trunk_potmsgset, 'gah', False) | ||
369 | 857 | |||
370 | 858 | existing = self.script._mapExistingMessages(self.trunk_potmsgset) | ||
371 | 859 | current, imported = self.script._findUsedMessages(existing) | ||
372 | 860 | current_clash, imported_clash, twin = ( | ||
373 | 861 | self.script._findClashesFromDicts( | ||
374 | 862 | existing, current, imported, stable_message)) | ||
375 | 863 | |||
376 | 864 | self.assertEqual(current_clash, current_message) | ||
377 | 865 | self.assertEqual(imported_clash, None) | ||
378 | 866 | self.assertEqual(twin, trunk_message) | ||
379 | 867 | |||
380 | 868 | 738 | ||
381 | 869 | def test_suite(): | 739 | def test_suite(): |
382 | 870 | return TestLoader().loadTestsFromName(__name__) | 740 | return TestLoader().loadTestsFromName(__name__) |
= Bug 403992 =
This is a more complete fix for bug 403992 than the one I'm hoping to of-the- service aftercare.
cherrypick from lp:~jtv/launchpad/cp-bug-403992. You could see it as
all-part-
Besides the fix in that branch, this one adds some related improvements:
* Make sure the database knows it's dirty after running the script in
the doctest. It doesn't seem to change anything, but it's the right
thing to do.
* Cache some stuff in the script object, mostly so the identifiers get
a bit shorter and the main code easier to read. A matter of taste,
mostly.
* When trying to diverge a shared message that can't be accommodated as
shared on the representative potmsgset, try it on the most
representative of the potemplates it participates in first, then the
second-best, and so on. This is slightly more proper than sorting
purely by id, although it probably doesn't matter too much.
* Cull some now-dead methods and variables: current_tms, imported_tms, sages. And their unit tests, of course.
_findUsedMes
* Make the unit tests' setUp pass test_args to the script object
constructor. Otherwise the script would receive the arguments that
the test driver (./bin/test) got on the command line. That _usually_
isn't a problem, but when the test driver invokes itself recursively
to run this test, it adds a --resume-layer argument which of course
means nothing to the script object. This broke the unit tests in
some combined test runs, but not in individual ones or more fortunate
combinations.
To test,
{{{
./bin/test -vv -t message.sharing
}}}
To Q/A, run this on staging: rosetta/ message- sharing- merge -vvv -P -p elisa
{{{
scripts/
}}}
No lint complaints.
Jeroen