Merge ~cjwatson/launchpad:pyupgrade into launchpad:master

Proposed by Colin Watson
Status: Merged
Approved by: Colin Watson
Approved revision: 8e0ebdd3dd6ce056d8d4595b331b7f4cc8a400dc
Merge reported by: Otto Co-Pilot
Merged at revision: not available
Proposed branch: ~cjwatson/launchpad:pyupgrade
Merge into: launchpad:master
Diff against target: 8088 lines (+1177/-1171)
273 files modified
.git-blame-ignore-revs (+2/-0)
.pre-commit-config.yaml (+6/-0)
database/replication/helpers.py (+10/-10)
database/replication/walblock.py (+1/-1)
database/schema/preflight.py (+7/-7)
database/schema/security.py (+9/-9)
lib/devscripts/sourcecode.py (+1/-1)
lib/devscripts/tests/test_sourcecode.py (+1/-1)
lib/lp/answers/model/question.py (+4/-4)
lib/lp/answers/model/tests/test_question.py (+1/-1)
lib/lp/answers/model/tests/test_questionsubscription.py (+1/-1)
lib/lp/app/browser/launchpad.py (+4/-4)
lib/lp/app/browser/linkchecker.py (+1/-1)
lib/lp/app/browser/root.py (+4/-4)
lib/lp/app/browser/stringformatter.py (+1/-1)
lib/lp/app/browser/tales.py (+11/-11)
lib/lp/app/browser/tests/test_launchpad.py (+2/-2)
lib/lp/app/tests/test_tales.py (+2/-2)
lib/lp/app/widgets/suggestion.py (+1/-1)
lib/lp/archivepublisher/model/ftparchive.py (+2/-2)
lib/lp/archivepublisher/publishing.py (+1/-1)
lib/lp/archivepublisher/scripts/publish_ftpmaster.py (+9/-9)
lib/lp/archivepublisher/tests/test_dominator.py (+17/-17)
lib/lp/archivepublisher/tests/test_publish_ftpmaster.py (+1/-1)
lib/lp/archivepublisher/tests/test_publisher.py (+4/-4)
lib/lp/archiveuploader/changesfile.py (+2/-2)
lib/lp/archiveuploader/dscfile.py (+4/-4)
lib/lp/archiveuploader/nascentupload.py (+1/-1)
lib/lp/archiveuploader/nascentuploadfile.py (+4/-4)
lib/lp/archiveuploader/tests/__init__.py (+1/-1)
lib/lp/archiveuploader/tests/test_changesfile.py (+2/-2)
lib/lp/archiveuploader/utils.py (+1/-1)
lib/lp/blueprints/browser/person_upcomingwork.py (+2/-2)
lib/lp/blueprints/browser/specification.py (+2/-2)
lib/lp/blueprints/browser/sprint.py (+7/-7)
lib/lp/blueprints/browser/tests/test_specification.py (+3/-3)
lib/lp/blueprints/browser/tests/test_specificationsubscription.py (+3/-3)
lib/lp/blueprints/model/specificationsearch.py (+10/-10)
lib/lp/blueprints/model/sprint.py (+1/-1)
lib/lp/blueprints/tests/test_specification.py (+13/-13)
lib/lp/bugs/browser/bug.py (+3/-3)
lib/lp/bugs/browser/bugalsoaffects.py (+2/-2)
lib/lp/bugs/browser/buglisting.py (+3/-3)
lib/lp/bugs/browser/bugtarget.py (+2/-2)
lib/lp/bugs/browser/bugtask.py (+10/-10)
lib/lp/bugs/browser/bugtracker.py (+2/-2)
lib/lp/bugs/browser/structuralsubscription.py (+6/-6)
lib/lp/bugs/browser/tests/test_bugcomment.py (+1/-1)
lib/lp/bugs/browser/tests/test_bugsubscriptionfilter.py (+3/-3)
lib/lp/bugs/browser/tests/test_bugtask.py (+1/-1)
lib/lp/bugs/externalbugtracker/bugzilla.py (+4/-4)
lib/lp/bugs/interfaces/bugtasksearch.py (+3/-3)
lib/lp/bugs/interfaces/tests/test_bugtask.py (+15/-15)
lib/lp/bugs/mail/bugnotificationbuilder.py (+1/-1)
lib/lp/bugs/mail/handler.py (+2/-2)
lib/lp/bugs/model/bug.py (+7/-7)
lib/lp/bugs/model/bugsubscriptionfilter.py (+3/-3)
lib/lp/bugs/model/bugtarget.py (+1/-1)
lib/lp/bugs/model/bugtask.py (+17/-17)
lib/lp/bugs/model/bugtasksearch.py (+6/-6)
lib/lp/bugs/model/bugtracker.py (+3/-3)
lib/lp/bugs/model/cve.py (+3/-3)
lib/lp/bugs/model/personsubscriptioninfo.py (+2/-2)
lib/lp/bugs/model/structuralsubscription.py (+1/-1)
lib/lp/bugs/model/tests/test_bug.py (+11/-11)
lib/lp/bugs/model/tests/test_bugsubscriptioninfo.py (+3/-3)
lib/lp/bugs/model/tests/test_bugtask.py (+4/-4)
lib/lp/bugs/model/tests/test_bugtasksearch.py (+1/-1)
lib/lp/bugs/scripts/bugsummaryrebuild.py (+8/-8)
lib/lp/bugs/scripts/checkwatches/core.py (+5/-5)
lib/lp/bugs/scripts/tests/test_bugnotification.py (+3/-3)
lib/lp/bugs/tests/externalbugtracker.py (+9/-9)
lib/lp/bugs/tests/test_bug_messages_webservice.py (+6/-6)
lib/lp/bugs/tests/test_bugchanges.py (+9/-9)
lib/lp/bugs/tests/test_bugnotification.py (+6/-6)
lib/lp/bugs/tests/test_bugwatch.py (+1/-1)
lib/lp/bugs/tests/test_structuralsubscription.py (+14/-14)
lib/lp/bugs/tests/test_structuralsubscriptiontarget.py (+2/-2)
lib/lp/bugs/vocabularies.py (+4/-4)
lib/lp/buildmaster/manager.py (+7/-7)
lib/lp/buildmaster/model/buildqueue.py (+6/-6)
lib/lp/buildmaster/tests/test_manager.py (+3/-3)
lib/lp/buildmaster/tests/test_webservice.py (+2/-2)
lib/lp/charms/model/charmrecipe.py (+1/-1)
lib/lp/code/browser/branch.py (+1/-1)
lib/lp/code/browser/branchlisting.py (+9/-9)
lib/lp/code/browser/branchmergeproposal.py (+1/-1)
lib/lp/code/browser/tests/test_branchlisting.py (+5/-5)
lib/lp/code/browser/tests/test_branchmergeproposal.py (+3/-3)
lib/lp/code/browser/tests/test_gitrepository.py (+1/-1)
lib/lp/code/browser/tests/test_sourcepackagerecipe.py (+6/-6)
lib/lp/code/browser/tests/test_tales.py (+4/-4)
lib/lp/code/interfaces/tests/test_branch.py (+2/-2)
lib/lp/code/mail/tests/test_branchmergeproposal.py (+3/-3)
lib/lp/code/model/branch.py (+5/-5)
lib/lp/code/model/branchcollection.py (+7/-7)
lib/lp/code/model/branchjob.py (+1/-1)
lib/lp/code/model/branchlookup.py (+1/-1)
lib/lp/code/model/branchmergeproposal.py (+10/-10)
lib/lp/code/model/codereviewcomment.py (+1/-1)
lib/lp/code/model/diff.py (+5/-5)
lib/lp/code/model/gitcollection.py (+3/-3)
lib/lp/code/model/gitref.py (+1/-1)
lib/lp/code/model/gitrepository.py (+4/-4)
lib/lp/code/model/revision.py (+6/-6)
lib/lp/code/model/seriessourcepackagebranch.py (+1/-1)
lib/lp/code/model/sourcepackagerecipebuild.py (+2/-2)
lib/lp/code/model/tests/test_branch.py (+9/-9)
lib/lp/code/model/tests/test_branchjob.py (+3/-3)
lib/lp/code/model/tests/test_branchmergeproposal.py (+17/-17)
lib/lp/code/model/tests/test_codeimportjob.py (+1/-1)
lib/lp/code/model/tests/test_diff.py (+44/-44)
lib/lp/code/model/tests/test_gitrepository.py (+11/-11)
lib/lp/code/model/tests/test_revision.py (+2/-2)
lib/lp/code/model/tests/test_sourcepackagerecipe.py (+2/-2)
lib/lp/code/tests/test_bzr.py (+6/-6)
lib/lp/code/vocabularies/tests/test_branch_vocabularies.py (+3/-3)
lib/lp/code/vocabularies/tests/test_gitrepository_vocabularies.py (+2/-2)
lib/lp/codehosting/inmemory.py (+4/-4)
lib/lp/codehosting/scanner/bzrsync.py (+4/-4)
lib/lp/codehosting/scanner/tests/test_bzrsync.py (+11/-11)
lib/lp/codehosting/scanner/tests/test_mergedetection.py (+4/-4)
lib/lp/codehosting/scripts/tests/test_modifiedbranches.py (+4/-4)
lib/lp/codehosting/tests/test_sftp.py (+1/-1)
lib/lp/oci/browser/tests/test_ocirecipe.py (+1/-1)
lib/lp/registry/browser/distributionsourcepackage.py (+3/-3)
lib/lp/registry/browser/distroseries.py (+6/-6)
lib/lp/registry/browser/milestone.py (+1/-1)
lib/lp/registry/browser/pillar.py (+5/-5)
lib/lp/registry/browser/product.py (+2/-2)
lib/lp/registry/browser/sourcepackage.py (+2/-2)
lib/lp/registry/browser/tests/test_mailinglists.py (+0/-1)
lib/lp/registry/interfaces/pocket.py (+1/-1)
lib/lp/registry/model/accesspolicy.py (+7/-7)
lib/lp/registry/model/distributionsourcepackage.py (+3/-3)
lib/lp/registry/model/distroseriesdifference.py (+3/-3)
lib/lp/registry/model/person.py (+9/-9)
lib/lp/registry/model/product.py (+12/-12)
lib/lp/registry/model/sourcepackage.py (+2/-2)
lib/lp/registry/scripts/teamparticipation.py (+1/-1)
lib/lp/registry/scripts/tests/test_populate_distroseriesdiff.py (+10/-10)
lib/lp/registry/services/tests/test_sharingservice.py (+4/-4)
lib/lp/registry/tests/test_distributionmirror_prober.py (+2/-2)
lib/lp/registry/tests/test_distroseries.py (+1/-1)
lib/lp/registry/tests/test_distroseries_vocabularies.py (+7/-7)
lib/lp/registry/tests/test_distroseriesdifference.py (+16/-16)
lib/lp/registry/tests/test_initderiveddistroseries.py (+2/-2)
lib/lp/registry/tests/test_mailinglistapi.py (+2/-2)
lib/lp/registry/tests/test_milestone.py (+17/-17)
lib/lp/registry/tests/test_mlists.py (+4/-4)
lib/lp/registry/tests/test_ociproject.py (+2/-2)
lib/lp/registry/tests/test_oopsreferences.py (+14/-14)
lib/lp/registry/tests/test_person.py (+5/-5)
lib/lp/registry/tests/test_person_vocabularies.py (+4/-4)
lib/lp/registry/tests/test_prf_finder.py (+1/-1)
lib/lp/registry/tests/test_product.py (+26/-26)
lib/lp/registry/tests/test_productseries.py (+13/-13)
lib/lp/registry/tests/test_teammembership.py (+1/-1)
lib/lp/registry/vocabularies.py (+8/-8)
lib/lp/registry/xmlrpc/canonicalsso.py (+3/-3)
lib/lp/scripts/garbo.py (+1/-1)
lib/lp/scripts/tests/test_garbo.py (+6/-6)
lib/lp/scripts/utilities/importpedant.py (+15/-15)
lib/lp/scripts/utilities/warninghandler.py (+2/-2)
lib/lp/security.py (+4/-4)
lib/lp/services/config/tests/test_config.py (+1/-1)
lib/lp/services/database/bulk.py (+1/-1)
lib/lp/services/database/postgresql.py (+4/-4)
lib/lp/services/database/sqlbase.py (+1/-1)
lib/lp/services/database/tests/test_bulk.py (+5/-5)
lib/lp/services/database/tests/test_connectionstring.py (+1/-1)
lib/lp/services/features/flags.py (+2/-2)
lib/lp/services/features/scopes.py (+1/-1)
lib/lp/services/gpg/tests/test_gpghandler.py (+3/-3)
lib/lp/services/job/celeryjob.py (+2/-2)
lib/lp/services/librarianserver/librariangc.py (+2/-2)
lib/lp/services/librarianserver/swift.py (+18/-18)
lib/lp/services/librarianserver/tests/test_gc.py (+1/-1)
lib/lp/services/librarianserver/tests/test_swift.py (+5/-5)
lib/lp/services/log/logger.py (+3/-3)
lib/lp/services/mail/commands.py (+3/-3)
lib/lp/services/mail/helpers.py (+2/-2)
lib/lp/services/mail/tests/test_helpers.py (+3/-3)
lib/lp/services/messages/tests/test_message.py (+1/-1)
lib/lp/services/messaging/tests/test_rabbit.py (+2/-2)
lib/lp/services/oauth/browser/__init__.py (+2/-2)
lib/lp/services/profile/mem.py (+2/-2)
lib/lp/services/profile/profile.py (+2/-2)
lib/lp/services/profile/tests.py (+15/-15)
lib/lp/services/twistedsupport/features.py (+2/-2)
lib/lp/services/utils.py (+3/-3)
lib/lp/services/webapp/batching.py (+2/-2)
lib/lp/services/webapp/errorlog.py (+4/-4)
lib/lp/services/webapp/escaping.py (+2/-2)
lib/lp/services/webapp/menu.py (+3/-3)
lib/lp/services/webapp/tests/test_error.py (+1/-1)
lib/lp/services/webapp/tests/test_errorlog.py (+2/-2)
lib/lp/services/webhooks/model.py (+1/-1)
lib/lp/services/webhooks/tests/test_model.py (+4/-4)
lib/lp/services/worlddata/model/language.py (+2/-2)
lib/lp/snappy/tests/test_snapstoreclient.py (+1/-1)
lib/lp/snappy/vocabularies.py (+1/-1)
lib/lp/soyuz/adapters/archivedependencies.py (+2/-2)
lib/lp/soyuz/adapters/buildarch.py (+1/-1)
lib/lp/soyuz/adapters/copypolicy.py (+1/-1)
lib/lp/soyuz/adapters/overrides.py (+24/-24)
lib/lp/soyuz/adapters/tests/test_overrides.py (+13/-13)
lib/lp/soyuz/browser/distributionsourcepackagerelease.py (+1/-1)
lib/lp/soyuz/browser/queue.py (+5/-5)
lib/lp/soyuz/model/archive.py (+4/-4)
lib/lp/soyuz/model/archivefile.py (+2/-2)
lib/lp/soyuz/model/binarypackagebuild.py (+4/-4)
lib/lp/soyuz/model/distroseriesdifferencejob.py (+5/-5)
lib/lp/soyuz/model/publishing.py (+13/-13)
lib/lp/soyuz/model/queue.py (+4/-4)
lib/lp/soyuz/model/sourcepackagerelease.py (+2/-2)
lib/lp/soyuz/scripts/custom_uploads_copier.py (+1/-1)
lib/lp/soyuz/scripts/gina/handlers.py (+3/-3)
lib/lp/soyuz/scripts/gina/packages.py (+2/-2)
lib/lp/soyuz/scripts/initialize_distroseries.py (+2/-2)
lib/lp/soyuz/scripts/packagecopier.py (+7/-7)
lib/lp/soyuz/scripts/retrydepwait.py (+1/-1)
lib/lp/soyuz/scripts/tests/test_custom_uploads_copier.py (+2/-2)
lib/lp/soyuz/scripts/tests/test_initialize_distroseries.py (+6/-6)
lib/lp/soyuz/scripts/tests/test_populatearchive.py (+7/-7)
lib/lp/soyuz/scripts/tests/test_ppa_apache_log_parser.py (+2/-2)
lib/lp/soyuz/tests/test_archive.py (+5/-5)
lib/lp/soyuz/tests/test_distroseriesdifferencejob.py (+8/-8)
lib/lp/soyuz/tests/test_packagecloner.py (+2/-2)
lib/lp/soyuz/tests/test_packagecopyjob.py (+2/-2)
lib/lp/soyuz/tests/test_packageupload.py (+6/-6)
lib/lp/soyuz/tests/test_publishing.py (+4/-4)
lib/lp/testing/__init__.py (+2/-2)
lib/lp/testing/mail_helpers.py (+3/-3)
lib/lp/testing/pages.py (+2/-2)
lib/lp/testing/swift/fakeswift.py (+4/-4)
lib/lp/testing/swift/tests/test_fixture.py (+3/-3)
lib/lp/testing/tests/test_factory.py (+2/-2)
lib/lp/testing/tests/test_pages.py (+1/-1)
lib/lp/testing/tests/test_testcase.py (+1/-1)
lib/lp/translations/browser/distroseries.py (+1/-1)
lib/lp/translations/browser/person.py (+4/-4)
lib/lp/translations/browser/productseries.py (+1/-1)
lib/lp/translations/browser/tests/test_persontranslationview.py (+3/-3)
lib/lp/translations/browser/tests/test_potemplate_views.py (+2/-2)
lib/lp/translations/browser/tests/test_translationmessage_view.py (+2/-2)
lib/lp/translations/browser/translationlinksaggregator.py (+11/-11)
lib/lp/translations/browser/translationmessage.py (+4/-4)
lib/lp/translations/model/pofile.py (+2/-2)
lib/lp/translations/model/pofiletranslator.py (+1/-1)
lib/lp/translations/model/potemplate.py (+3/-3)
lib/lp/translations/model/potmsgset.py (+11/-11)
lib/lp/translations/model/side.py (+3/-3)
lib/lp/translations/model/translationimportqueue.py (+2/-2)
lib/lp/translations/model/translationmessage.py (+3/-3)
lib/lp/translations/scripts/scrub_pofiletranslator.py (+2/-2)
lib/lp/translations/scripts/tests/test_reupload_translations.py (+1/-1)
lib/lp/translations/scripts/tests/test_scrub_pofiletranslator.py (+3/-3)
lib/lp/translations/scripts/tests/test_translations_import.py (+2/-2)
lib/lp/translations/tests/test_hastranslationtemplates.py (+4/-4)
lib/lp/translations/tests/test_potemplate.py (+9/-10)
lib/lp/translations/tests/test_potmsgset.py (+3/-3)
lib/lp/translations/tests/test_translationmerger.py (+2/-2)
lib/lp/translations/tests/test_translationpermission.py (+3/-3)
lib/lp/translations/tests/test_translationtemplatesbuildbehaviour.py (+1/-1)
lib/lp/translations/utilities/translation_import.py (+2/-2)
lib/lp/translations/utilities/translationmerger.py (+5/-5)
scripts/librarian-report.py (+2/-2)
scripts/memcached-stats.py (+1/-1)
test_on_merge.py (+1/-1)
utilities/community-contributions.py (+2/-2)
utilities/massage-bug-import-xml (+8/-8)
utilities/roundup-sniffer.py (+1/-1)
Reviewer Review Type Date Requested Status
Jürgen Gmach Approve
Review via email: mp+412005@code.launchpad.net

Commit message

Apply pyupgrade

Description of the change

I've started out with some conservative options that make minimal changes, so at the moment most of the changes are for things like using more modern set literal and dictionary comprehension syntax. We can apply further options to upgrade to Python 3 syntax as a separate step.

`contrib` is excluded (as with `flake8`) because it consists of code mainly copied from elsewhere.

Except for the change to `.pre-commit-config.yaml`, all the changes here were automatic. I've done a full test run with no errors.

To post a comment you must log in.
Revision history for this message
Jürgen Gmach (jugmac00) wrote :

LGTM

The changes mostly consist of using literal set notation, dict comprehensions, removing redundant parenthesis, converting list to set comprehensions, when they were consumed immediately afterwards, and some long strings, which were initially encoded and are now written as byte literals, and some updates to the str format syntax, ie {0} -> {}.

The commit id could be included in a git-blame-ignore-revs file.

review: Approve

Preview Diff

[H/L] Next/Prev Comment, [J/K] Next/Prev File, [N/P] Next/Prev Hunk
1diff --git a/.git-blame-ignore-revs b/.git-blame-ignore-revs
2new file mode 100644
3index 0000000..2cb1da8
4--- /dev/null
5+++ b/.git-blame-ignore-revs
6@@ -0,0 +1,2 @@
7+# apply pyupgrade
8+67e3b53a4375288983a72a7beb9a5a67ba739527
9diff --git a/.pre-commit-config.yaml b/.pre-commit-config.yaml
10index 7c8290a..4042766 100644
11--- a/.pre-commit-config.yaml
12+++ b/.pre-commit-config.yaml
13@@ -28,6 +28,12 @@ repos:
14 hooks:
15 - id: flake8
16 exclude: ^lib/contrib/
17+- repo: https://github.com/asottile/pyupgrade
18+ rev: v2.29.1
19+ hooks:
20+ - id: pyupgrade
21+ args: [--keep-percent-format]
22+ exclude: ^lib/contrib/
23 - repo: https://github.com/PyCQA/isort
24 rev: 5.9.2
25 hooks:
26diff --git a/database/replication/helpers.py b/database/replication/helpers.py
27index 726f1e6..b7e6bd4 100644
28--- a/database/replication/helpers.py
29+++ b/database/replication/helpers.py
30@@ -78,7 +78,7 @@ LPMAIN_SEED = frozenset([
31 # Explicitly list tables that should not be replicated. This includes the
32 # session tables, as these might exist in developer databases but will not
33 # exist in the production launchpad database.
34-IGNORED_TABLES = set([
35+IGNORED_TABLES = {
36 # Session tables that in some situations will exist in the main lp
37 # database.
38 'public.secret', 'public.sessiondata', 'public.sessionpkgdata',
39@@ -118,10 +118,10 @@ IGNORED_TABLES = set([
40 'public.oauth_consumer_id_seq',
41 'public.api_user_id_seq',
42 'public.oauth_nonce_id_seq',
43- ])
44+ }
45
46 # Calculate IGNORED_SEQUENCES
47-IGNORED_SEQUENCES = set('%s_id_seq' % table for table in IGNORED_TABLES)
48+IGNORED_SEQUENCES = {'%s_id_seq' % table for table in IGNORED_TABLES}
49
50
51 def slony_installed(con):
52@@ -487,7 +487,7 @@ def calculate_replication_set(cur, seeds):
53
54 # We can't easily convert the sequence name to (namespace, name) tuples,
55 # so we might as well convert the tables to dot notation for consistancy.
56- tables = set(fqn(namespace, tablename) for namespace, tablename in tables)
57+ tables = {fqn(namespace, tablename) for namespace, tablename in tables}
58
59 return tables, sequences
60
61@@ -503,24 +503,24 @@ def discover_unreplicated(cur):
62
63 # Ignore any tables and sequences starting with temp_. These are
64 # transient and not to be replicated per Bug #778338.
65- all_tables = set(
66+ all_tables = {
67 table for table in all_tables
68- if not table.startswith('public.temp_'))
69- all_sequences = set(
70+ if not table.startswith('public.temp_')}
71+ all_sequences = {
72 sequence for sequence in all_sequences
73- if not sequence.startswith('public.temp_'))
74+ if not sequence.startswith('public.temp_')}
75
76 cur.execute("""
77 SELECT tab_nspname, tab_relname FROM %s
78 WHERE tab_nspname = 'public'
79 """ % fqn(CLUSTER_NAMESPACE, "sl_table"))
80- replicated_tables = set(fqn(*row) for row in cur.fetchall())
81+ replicated_tables = {fqn(*row) for row in cur.fetchall()}
82
83 cur.execute("""
84 SELECT seq_nspname, seq_relname FROM %s
85 WHERE seq_nspname = 'public'
86 """ % fqn(CLUSTER_NAMESPACE, "sl_sequence"))
87- replicated_sequences = set(fqn(*row) for row in cur.fetchall())
88+ replicated_sequences = {fqn(*row) for row in cur.fetchall()}
89
90 return (
91 all_tables - replicated_tables - IGNORED_TABLES,
92diff --git a/database/replication/walblock.py b/database/replication/walblock.py
93index bcf48c4..49f1b61 100755
94--- a/database/replication/walblock.py
95+++ b/database/replication/walblock.py
96@@ -39,7 +39,7 @@ def main():
97 if options.verbose and not notified:
98 notified = True
99 print(
100- 'Blocking on {0} unshipped WAL'.format(
101+ 'Blocking on {} unshipped WAL'.format(
102 len(glob(ready_wal_glob))),
103 end='', file=sys.stderr)
104 time.sleep(5)
105diff --git a/database/schema/preflight.py b/database/schema/preflight.py
106index 9a8d8e5..24c5dfb 100755
107--- a/database/schema/preflight.py
108+++ b/database/schema/preflight.py
109@@ -38,32 +38,32 @@ import upgrade
110
111
112 # Ignore connections by these users.
113-SYSTEM_USERS = set(['postgres', 'slony', 'nagios', 'lagmon'])
114+SYSTEM_USERS = {'postgres', 'slony', 'nagios', 'lagmon'}
115
116 # Fail checks if these users are connected. If a process should not be
117 # interrupted by a rollout, the database user it connects as should be
118 # added here. The preflight check will fail if any of these users are
119 # connected, so these systems will need to be shut down manually before
120 # a database update.
121-FRAGILE_USERS = set([
122+FRAGILE_USERS = {
123 # process_accepted is fragile, but also fast so we likely shouldn't
124 # need to ever manually shut it down.
125 'process_accepted',
126 'process_upload',
127 'publish_distro',
128 'publish_ftpmaster',
129- ])
130+ }
131
132 # If these users have long running transactions, just kill 'em. Entries
133 # added here must come with a bug number, a if part of Launchpad holds
134 # open a long running transaction it is a bug we need to fix.
135-BAD_USERS = set([
136+BAD_USERS = {
137 'karma', # Bug #863109
138 'rosettaadmin', # Bug #863122
139 'update-pkg-cache', # Bug #912144
140 'process_death_row', # Bug #912146
141 'langpack', # Bug #912147
142- ])
143+ }
144
145 # How lagged the cluster can be before failing the preflight check.
146 # If this is set too low, perfectly normal state will abort rollouts. If
147@@ -82,7 +82,7 @@ class DatabasePreflight:
148
149 node = Node(None, None, None, True)
150 node.con = master_con
151- self.nodes = set([node])
152+ self.nodes = {node}
153 self.lpmain_nodes = self.nodes
154 self.lpmain_master_node = node
155
156@@ -343,7 +343,7 @@ class KillConnectionsPreflight(DatabasePreflight):
157 num_tries = 100
158 seconds_to_pause = 0.1
159 if self.replication_paused:
160- nodes = set([self.lpmain_master_node])
161+ nodes = {self.lpmain_master_node}
162 else:
163 nodes = self.lpmain_nodes
164
165diff --git a/database/schema/security.py b/database/schema/security.py
166index 573486a..653a126 100755
167--- a/database/schema/security.py
168+++ b/database/schema/security.py
169@@ -26,14 +26,14 @@ from lp.services.scripts import (
170 # The 'read' group does not get given select permission on the following
171 # tables. This is to stop the ro user being given access to security
172 # sensitive information that interactive sessions don't need.
173-SECURE_TABLES = set((
174+SECURE_TABLES = {
175 'public.oauthnonce',
176 'public.oauthnonce_id_seq',
177 'public.openidnonce',
178 'public.openidnonce_id_seq',
179 'public.openidconsumernonce',
180 'public.openidconsumernonce_id_seq',
181- ))
182+ }
183
184 POSTGRES_ACL_MAP = {
185 'r': 'SELECT',
186@@ -218,9 +218,9 @@ class DbSchema(dict):
187 options = (
188 'SUPERUSER', 'INHERIT', 'CREATEROLE', 'CREATEDB', 'LOGIN',
189 'REPLICATION')
190- self.roles = dict(
191- (r[0], set(opt for (opt, val) in zip(options, r[1:]) if val))
192- for r in cur.fetchall())
193+ self.roles = {
194+ r[0]: {opt for (opt, val) in zip(options, r[1:]) if val}
195+ for r in cur.fetchall()}
196
197
198 class CursorWrapper(object):
199@@ -326,9 +326,9 @@ class PermissionGatherer:
200
201 def countPrincipals(self):
202 """Count the number of different principals."""
203- return len(set(sum([
204+ return len(set(sum((
205 list(principals)
206- for principals in six.itervalues(self.permissions)], [])))
207+ for principals in six.itervalues(self.permissions)), [])))
208
209 def grant(self, cur):
210 """Grant all gathered permissions.
211@@ -422,7 +422,7 @@ def reset_permissions(con, config, options):
212 type_ = config.get(section_name, 'type')
213 assert type_ in ['user', 'group'], 'Unknown type %s' % type_
214
215- desired_opts = set(('INHERIT',))
216+ desired_opts = {'INHERIT'}
217 if type_ == 'user':
218 desired_opts.add('LOGIN')
219
220@@ -476,7 +476,7 @@ def reset_permissions(con, config, options):
221 else:
222 log.debug2("%s not in any roles", user)
223
224- managed_roles = set(['read', 'admin'])
225+ managed_roles = {'read', 'admin'}
226 for section_name in config.sections():
227 managed_roles.add(section_name)
228 if section_name != 'public':
229diff --git a/lib/devscripts/sourcecode.py b/lib/devscripts/sourcecode.py
230index 2fa821e..2dd528a 100644
231--- a/lib/devscripts/sourcecode.py
232+++ b/lib/devscripts/sourcecode.py
233@@ -128,7 +128,7 @@ def interpret_config(config_entries, public_only, use_http=False):
234
235 def _subset_dict(d, keys):
236 """Return a dict that's a subset of 'd', based on the keys in 'keys'."""
237- return dict((key, d[key]) for key in keys)
238+ return {key: d[key] for key in keys}
239
240
241 def plan_update(existing_branches, configuration):
242diff --git a/lib/devscripts/tests/test_sourcecode.py b/lib/devscripts/tests/test_sourcecode.py
243index e3abbf2..5d5f429 100644
244--- a/lib/devscripts/tests/test_sourcecode.py
245+++ b/lib/devscripts/tests/test_sourcecode.py
246@@ -171,7 +171,7 @@ class TestPlanUpdate(unittest.TestCase):
247 new, existing, removed = plan_update(['a', 'b', 'c'], {})
248 self.assertEqual({}, new)
249 self.assertEqual({}, existing)
250- self.assertEqual(set(['a', 'b', 'c']), removed)
251+ self.assertEqual({'a', 'b', 'c'}, removed)
252
253 def test_all_same(self):
254 # If the set of existing branches is the same as the set of
255diff --git a/lib/lp/answers/model/question.py b/lib/lp/answers/model/question.py
256index 0441a70..61a534c 100644
257--- a/lib/lp/answers/model/question.py
258+++ b/lib/lp/answers/model/question.py
259@@ -850,7 +850,7 @@ class QuestionSet:
260 def getOpenQuestionCountByPackages(self, packages):
261 """See `IQuestionSet`."""
262 distributions = list(
263- set(package.distribution for package in packages))
264+ {package.distribution for package in packages})
265 # We can't get counts for all packages in one query, since we'd
266 # need to match on (distribution, sourcepackagename). Issue one
267 # query per distribution instead.
268@@ -882,7 +882,7 @@ class QuestionSet:
269 sourcepackagename_set = getUtility(ISourcePackageNameSet)
270 # Only packages with open questions are included in the query
271 # result, so initialize each package to 0.
272- counts = dict((package, 0) for package in packages)
273+ counts = {package: 0 for package in packages}
274 for distro_id, spn_id, open_questions in results:
275 # The SourcePackageNames here should already be pre-fetched,
276 # so that .get(spn_id) won't issue a DB query.
277@@ -1525,6 +1525,6 @@ class QuestionTargetMixin:
278 for contact in self.answer_contacts_with_languages:
279 languages |= set(contact.languages)
280 languages.add(getUtility(ILaunchpadCelebrities).english)
281- languages = set(
282- lang for lang in languages if not is_english_variant(lang))
283+ languages = {
284+ lang for lang in languages if not is_english_variant(lang)}
285 return list(languages)
286diff --git a/lib/lp/answers/model/tests/test_question.py b/lib/lp/answers/model/tests/test_question.py
287index 0735fe3..979e2ce 100644
288--- a/lib/lp/answers/model/tests/test_question.py
289+++ b/lib/lp/answers/model/tests/test_question.py
290@@ -99,7 +99,7 @@ class TestQuestionInDirectSubscribers(TestCaseWithFactory):
291 english_person.addLanguage(getUtility(ILanguageSet)['en'])
292 spanish = getUtility(ILanguageSet)['es']
293 spanish_person = self.factory.makePerson()
294- with person_logged_in((spanish_person)):
295+ with person_logged_in(spanish_person):
296 spanish_person.addLanguage(spanish)
297 question = self.factory.makeQuestion(language=spanish)
298 with person_logged_in(question.owner):
299diff --git a/lib/lp/answers/model/tests/test_questionsubscription.py b/lib/lp/answers/model/tests/test_questionsubscription.py
300index 513914c..c20257b 100644
301--- a/lib/lp/answers/model/tests/test_questionsubscription.py
302+++ b/lib/lp/answers/model/tests/test_questionsubscription.py
303@@ -126,7 +126,7 @@ class TestQuestionSubscriptionCanBeUnsubscribedbyUser(TestCaseWithFactory):
304 """Question target answer contact can unsubscribe someone."""
305 answer_contact = self.factory.makePerson()
306 english = getUtility(ILanguageSet)['en']
307- with person_logged_in((answer_contact)):
308+ with person_logged_in(answer_contact):
309 answer_contact.addLanguage(english)
310 distro_owner = self.factory.makePerson()
311 distro = self.factory.makeDistribution(owner=distro_owner)
312diff --git a/lib/lp/app/browser/launchpad.py b/lib/lp/app/browser/launchpad.py
313index c9bb53e..6c5045f 100644
314--- a/lib/lp/app/browser/launchpad.py
315+++ b/lib/lp/app/browser/launchpad.py
316@@ -188,9 +188,9 @@ class NavigationMenuTabs(LaunchpadView):
317
318 def initialize(self):
319 menuapi = MenuAPI(self.context)
320- self.links = sorted([
321+ self.links = sorted((
322 link for link in menuapi.navigation.values()
323- if (link.enabled or config.launchpad.devmode)],
324+ if (link.enabled or config.launchpad.devmode)),
325 key=operator.attrgetter('sort_key'))
326 self.title = None
327 if len(self.links) > 0:
328@@ -273,9 +273,9 @@ class Hierarchy(LaunchpadView):
329 """The objects for which we want breadcrumbs."""
330 # Start the chain with the deepest object that has a breadcrumb.
331 try:
332- objects = [next((
333+ objects = [next(
334 obj for obj in reversed(self.request.traversed_objects)
335- if IBreadcrumb(obj, None)))]
336+ if IBreadcrumb(obj, None))]
337 except StopIteration:
338 return []
339 # Now iterate. If an object has a breadcrumb, it can override
340diff --git a/lib/lp/app/browser/linkchecker.py b/lib/lp/app/browser/linkchecker.py
341index b541907..fbdacc1 100644
342--- a/lib/lp/app/browser/linkchecker.py
343+++ b/lib/lp/app/browser/linkchecker.py
344@@ -89,7 +89,7 @@ class LinkCheckerAPI(LaunchpadView):
345 valid_links = {}
346 user = self.user
347 # List of all the bugs we are checking.
348- bugs_ids = set([int(link[len('/bugs/'):]) for link in links])
349+ bugs_ids = {int(link[len('/bugs/'):]) for link in links}
350 if bugs_ids:
351 params = BugTaskSearchParams(
352 user=user, status=None,
353diff --git a/lib/lp/app/browser/root.py b/lib/lp/app/browser/root.py
354index fa6becd..f0e85f7 100644
355--- a/lib/lp/app/browser/root.py
356+++ b/lib/lp/app/browser/root.py
357@@ -262,13 +262,13 @@ class LaunchpadSearchView(LaunchpadFormView):
358 schema = ILaunchpadSearch
359 field_names = ['text']
360
361- shipit_keywords = set([
362+ shipit_keywords = {
363 'ubuntu', 'kubuntu', 'edubuntu',
364 'ship', 'shipit', 'send', 'get', 'mail', 'free',
365- 'cd', 'cds', 'dvd', 'dvds', 'disc'])
366- shipit_anti_keywords = set([
367+ 'cd', 'cds', 'dvd', 'dvds', 'disc'}
368+ shipit_anti_keywords = {
369 'burn', 'burning', 'enable', 'error', 'errors', 'image', 'iso',
370- 'read', 'rip', 'write'])
371+ 'read', 'rip', 'write'}
372
373 def __init__(self, context, request):
374 """Initialize the view.
375diff --git a/lib/lp/app/browser/stringformatter.py b/lib/lp/app/browser/stringformatter.py
376index bc40322..500ae96 100644
377--- a/lib/lp/app/browser/stringformatter.py
378+++ b/lib/lp/app/browser/stringformatter.py
379@@ -243,7 +243,7 @@ def linkify_bug_numbers(text):
380 def extract_email_addresses(text):
381 '''Unique email addresses in the text.'''
382 matches = re.finditer(re_email_address, text)
383- return list(set([match.group() for match in matches]))
384+ return list({match.group() for match in matches})
385
386
387 def parse_diff(text):
388diff --git a/lib/lp/app/browser/tales.py b/lib/lp/app/browser/tales.py
389index 51239bb..08d2a71 100644
390--- a/lib/lp/app/browser/tales.py
391+++ b/lib/lp/app/browser/tales.py
392@@ -499,7 +499,7 @@ class NoneFormatter:
393 attributes in content classes.
394 """
395
396- allowed_names = set([
397+ allowed_names = {
398 'approximatedate',
399 'approximatedatetitle',
400 'approximateduration',
401@@ -520,7 +520,7 @@ class NoneFormatter:
402 'time',
403 'url',
404 'link',
405- ])
406+ }
407
408 def __init__(self, context):
409 self.context = context
410@@ -670,7 +670,7 @@ class ObjectFormatterAPI:
411 "for %r." % (self, self._context))
412
413 def global_css(self):
414- css_classes = set([])
415+ css_classes = set()
416 view = self._context
417
418 # XXX: Bug #1076074
419@@ -915,13 +915,13 @@ class BugTaskImageDisplayAPI(ObjectImageDisplayAPI):
420 Used for image:icon.
421 """
422
423- allowed_names = set([
424+ allowed_names = {
425 'icon',
426 'logo',
427 'mugshot',
428 'badges',
429 'sprite_css',
430- ])
431+ }
432
433 icon_template = (
434 '<span alt="%s" title="%s" class="%s"></span>')
435@@ -1424,9 +1424,9 @@ class CustomizableFormatter(ObjectFormatterAPI):
436 This summary is for use in fmt:link, which is meant to be used in
437 contexts like lists of items.
438 """
439- values = dict(
440- (k, v if v is not None else '')
441- for k, v in six.iteritems(self._link_summary_values()))
442+ values = {
443+ k: v if v is not None else ''
444+ for k, v in six.iteritems(self._link_summary_values())}
445 return structured(self._link_summary_template, **values).escapedtext
446
447 def _title_values(self):
448@@ -1446,9 +1446,9 @@ class CustomizableFormatter(ObjectFormatterAPI):
449 title_template = getattr(self, '_title_template', None)
450 if title_template is None:
451 return None
452- values = dict(
453- (k, v if v is not None else '')
454- for k, v in six.iteritems(self._title_values()))
455+ values = {
456+ k: v if v is not None else ''
457+ for k, v in six.iteritems(self._title_values())}
458 return structured(title_template, **values).escapedtext
459
460 def sprite_css(self):
461diff --git a/lib/lp/app/browser/tests/test_launchpad.py b/lib/lp/app/browser/tests/test_launchpad.py
462index a25c46c..dc697fd 100644
463--- a/lib/lp/app/browser/tests/test_launchpad.py
464+++ b/lib/lp/app/browser/tests/test_launchpad.py
465@@ -754,8 +754,8 @@ class TestIterViewRegistrations(TestCaseWithFactory):
466 """iter_view_registrations provides only registrations of class."""
467 macros = getMultiAdapter(
468 (object(), LaunchpadTestRequest()), name='+base-layout-macros')
469- names = set(
470- reg.name for reg in iter_view_registrations(macros.__class__))
471+ names = {
472+ reg.name for reg in iter_view_registrations(macros.__class__)}
473 self.assertIn('+base-layout-macros', names)
474 self.assertNotIn('+related-pages', names)
475
476diff --git a/lib/lp/app/tests/test_tales.py b/lib/lp/app/tests/test_tales.py
477index 73a8464..ffd5f91 100644
478--- a/lib/lp/app/tests/test_tales.py
479+++ b/lib/lp/app/tests/test_tales.py
480@@ -326,7 +326,7 @@ class TestNoneFormatterAPI(TestCaseWithFactory):
481 def test_valid_traversal(self):
482 # Traversal of allowed names works as expected.
483
484- allowed_names = set([
485+ allowed_names = {
486 'approximatedate',
487 'approximateduration',
488 'break-long-words',
489@@ -345,7 +345,7 @@ class TestNoneFormatterAPI(TestCaseWithFactory):
490 'time',
491 'url',
492 'link',
493- ])
494+ }
495
496 for name in allowed_names:
497 self.assertEqual('', test_tales('foo/fmt:%s' % name, foo=None))
498diff --git a/lib/lp/app/widgets/suggestion.py b/lib/lp/app/widgets/suggestion.py
499index dc2a13e..6ce8e46 100644
500--- a/lib/lp/app/widgets/suggestion.py
501+++ b/lib/lp/app/widgets/suggestion.py
502@@ -376,7 +376,7 @@ class RecipeOwnerWidget(SuggestionWidget):
503 def _getSuggestions(branch):
504 """Suggest the branch owner and current user."""
505 logged_in_user = getUtility(ILaunchBag).user
506- return set([branch.owner, logged_in_user])
507+ return {branch.owner, logged_in_user}
508
509 @staticmethod
510 def _valueDisplayname(value):
511diff --git a/lib/lp/archivepublisher/model/ftparchive.py b/lib/lp/archivepublisher/model/ftparchive.py
512index 2dcc94d..da2ecf6 100644
513--- a/lib/lp/archivepublisher/model/ftparchive.py
514+++ b/lib/lp/archivepublisher/model/ftparchive.py
515@@ -198,10 +198,10 @@ class FTPArchiveHandler:
516 spawner.complete()
517 stdout_handler.finalize()
518 stderr_handler.finalize()
519- failures = sorted([
520+ failures = sorted(
521 (tag, receiver.returncode)
522 for tag, receiver in six.iteritems(returncodes)
523- if receiver.returncode != 0])
524+ if receiver.returncode != 0)
525 if len(failures) > 0:
526 by_arch = ["%s (returned %d)" % failure for failure in failures]
527 raise AptFTPArchiveFailure(
528diff --git a/lib/lp/archivepublisher/publishing.py b/lib/lp/archivepublisher/publishing.py
529index dec1312..a1f4ec0 100644
530--- a/lib/lp/archivepublisher/publishing.py
531+++ b/lib/lp/archivepublisher/publishing.py
532@@ -143,7 +143,7 @@ def remove_suffix(path):
533
534 def get_suffixed_indices(path):
535 """Return a set of paths to compressed copies of the given index."""
536- return set([path + suffix for suffix in ('', '.gz', '.bz2', '.xz')])
537+ return {path + suffix for suffix in ('', '.gz', '.bz2', '.xz')}
538
539
540 def _getDiskPool(pubconf, log):
541diff --git a/lib/lp/archivepublisher/scripts/publish_ftpmaster.py b/lib/lp/archivepublisher/scripts/publish_ftpmaster.py
542index e691dfc..03bfe43 100644
543--- a/lib/lp/archivepublisher/scripts/publish_ftpmaster.py
544+++ b/lib/lp/archivepublisher/scripts/publish_ftpmaster.py
545@@ -95,9 +95,9 @@ def map_distro_pubconfigs(distro):
546 candidates = [
547 (archive.purpose, getPubConfig(archive))
548 for archive in get_publishable_archives(distro)]
549- return dict(
550- (purpose, config)
551- for purpose, config in candidates if config is not None)
552+ return {
553+ purpose: config
554+ for purpose, config in candidates if config is not None}
555
556
557 def newer_mtime(one_file, other_file):
558@@ -185,9 +185,9 @@ class PublishFTPMaster(LaunchpadCronScript):
559
560 So: getConfigs[distro][purpose] gives you a config.
561 """
562- return dict(
563- (distro, map_distro_pubconfigs(distro))
564- for distro in self.distributions)
565+ return {
566+ distro: map_distro_pubconfigs(distro)
567+ for distro in self.distributions}
568
569 def locateIndexesMarker(self, distribution, suite):
570 """Give path for marker file whose presence marks index creation.
571@@ -266,9 +266,9 @@ class PublishFTPMaster(LaunchpadCronScript):
572 only_unpublished=True))
573 load_related(
574 DistroArchSeries, pending_binaries, ['distroarchseriesID'])
575- return set(
576+ return {
577 pub.distroseries.name + pocketsuffix[pub.pocket]
578- for pub in pending_sources + pending_binaries)
579+ for pub in pending_sources + pending_binaries}
580
581 def getDirtySecuritySuites(self, distribution):
582 """List security suites with pending publications."""
583@@ -345,7 +345,7 @@ class PublishFTPMaster(LaunchpadCronScript):
584 arguments = (
585 ['-d', distribution.name] +
586 args +
587- sum([['-s', suite] for suite in suites], []))
588+ sum((['-s', suite] for suite in suites), []))
589
590 publish_distro = PublishDistro(
591 test_args=arguments, logger=self.logger, ignore_cron_control=True)
592diff --git a/lib/lp/archivepublisher/tests/test_dominator.py b/lib/lp/archivepublisher/tests/test_dominator.py
593index c079559..2b608fe 100755
594--- a/lib/lp/archivepublisher/tests/test_dominator.py
595+++ b/lib/lp/archivepublisher/tests/test_dominator.py
596@@ -784,10 +784,10 @@ class TestDominatorMethods(TestCaseWithFactory):
597 versions = ["1.%d" % number for number in range(4)]
598
599 # We have one package releases for each version.
600- relevant_releases = dict(
601- (version, self.factory.makeSourcePackageRelease(
602- sourcepackagename=package, version=version))
603- for version in jumble(versions))
604+ relevant_releases = {
605+ version: self.factory.makeSourcePackageRelease(
606+ sourcepackagename=package, version=version)
607+ for version in jumble(versions)}
608
609 # Each of those releases is subsequently published in
610 # different components.
611@@ -798,15 +798,15 @@ class TestDominatorMethods(TestCaseWithFactory):
612 # oldest to newest. Each re-publishing into a different
613 # component is meant to supersede publication into the previous
614 # component.
615- pubs_by_version = dict(
616- (version, [
617+ pubs_by_version = {
618+ version: [
619 self.factory.makeSourcePackagePublishingHistory(
620 archive=series.main_archive, distroseries=series,
621 pocket=pocket, status=PackagePublishingStatus.PUBLISHED,
622 sourcepackagerelease=relevant_releases[version],
623 component=component)
624- for component in components])
625- for version in jumble(versions))
626+ for component in components]
627+ for version in jumble(versions)}
628
629 ages = jumble(
630 [datetime.timedelta(age) for age in range(len(versions))])
631@@ -904,11 +904,11 @@ class TestDominatorMethods(TestCaseWithFactory):
632 def test_findPublishedSourcePackageNames_ignores_other_states(self):
633 series = self.factory.makeDistroSeries()
634 pocket = PackagePublishingPocket.RELEASE
635- spphs = dict(
636- (status, self.factory.makeSourcePackagePublishingHistory(
637+ spphs = {
638+ status: self.factory.makeSourcePackagePublishingHistory(
639 distroseries=series, archive=series.main_archive,
640- pocket=pocket, status=status))
641- for status in PackagePublishingStatus.items)
642+ pocket=pocket, status=status)
643+ for status in PackagePublishingStatus.items}
644 published_spph = spphs[PackagePublishingStatus.PUBLISHED]
645 dominator = self.makeDominator(list(spphs.values()))
646 self.assertContentEqual(
647@@ -988,13 +988,13 @@ class TestDominatorMethods(TestCaseWithFactory):
648 series = self.factory.makeDistroSeries()
649 package = self.factory.makeSourcePackageName()
650 pocket = PackagePublishingPocket.RELEASE
651- spphs = dict(
652- (status, self.factory.makeSourcePackagePublishingHistory(
653+ spphs = {
654+ status: self.factory.makeSourcePackagePublishingHistory(
655 distroseries=series, archive=series.main_archive,
656 pocket=pocket, status=status,
657 sourcepackagerelease=self.factory.makeSourcePackageRelease(
658- sourcepackagename=package)))
659- for status in PackagePublishingStatus.items)
660+ sourcepackagename=package))
661+ for status in PackagePublishingStatus.items}
662 dominator = self.makeDominator(list(spphs.values()))
663 self.assertContentEqual(
664 [spphs[PackagePublishingStatus.PUBLISHED]],
665@@ -1336,7 +1336,7 @@ class TestArchSpecificPublicationsCache(TestCaseWithFactory):
666 cache = self.makeCache()
667 self.assertContentEqual(
668 [cache.getKey(bpph) for bpph in bpphs],
669- set(cache.getKey(bpph) for bpph in bpphs * 2))
670+ {cache.getKey(bpph) for bpph in bpphs * 2})
671
672 def test_hasArchSpecificPublications_is_consistent_and_correct(self):
673 # hasArchSpecificPublications consistently, repeatably returns
674diff --git a/lib/lp/archivepublisher/tests/test_publish_ftpmaster.py b/lib/lp/archivepublisher/tests/test_publish_ftpmaster.py
675index 8e01387..1847248 100644
676--- a/lib/lp/archivepublisher/tests/test_publish_ftpmaster.py
677+++ b/lib/lp/archivepublisher/tests/test_publish_ftpmaster.py
678@@ -552,7 +552,7 @@ class TestPublishFTPMasterScript(
679 script.runFinalizeParts(distro)
680 _, kwargs = run_parts_fixture.new_value.calls[0]
681 env = kwargs["env"]
682- required_parameters = set(["ARCHIVEROOTS", "SECURITY_UPLOAD_ONLY"])
683+ required_parameters = {"ARCHIVEROOTS", "SECURITY_UPLOAD_ONLY"}
684 missing_parameters = required_parameters.difference(set(env.keys()))
685 self.assertEqual(set(), missing_parameters)
686
687diff --git a/lib/lp/archivepublisher/tests/test_publisher.py b/lib/lp/archivepublisher/tests/test_publisher.py
688index 977b626..176044a 100644
689--- a/lib/lp/archivepublisher/tests/test_publisher.py
690+++ b/lib/lp/archivepublisher/tests/test_publisher.py
691@@ -2217,9 +2217,9 @@ class TestPublisher(TestPublisherBase):
692
693 release = self.parseRelease(suite_path('Release'))
694 paths = ['Release'] + [entry['name'] for entry in release['md5sum']]
695- timestamps = set(
696+ timestamps = {
697 os.stat(suite_path(path)).st_mtime for path in paths
698- if '/dep11/' not in path and os.path.exists(suite_path(path)))
699+ if '/dep11/' not in path and os.path.exists(suite_path(path))}
700 self.assertEqual(1, len(timestamps))
701
702 # Non-core files preserve their original timestamps.
703@@ -3380,8 +3380,8 @@ class TestPublisherLite(TestCaseWithFactory):
704 paths = [path for path, _ in path_times]
705 self.makePublisher(series)._syncTimestamps(series.name, set(paths))
706
707- timestamps = set(
708- os.stat(os.path.join(location, path)).st_mtime for path in paths)
709+ timestamps = {
710+ os.stat(os.path.join(location, path)).st_mtime for path in paths}
711 self.assertEqual(1, len(timestamps))
712 # The filesystem may round off subsecond parts of timestamps.
713 self.assertEqual(int(now), int(list(timestamps)[0]))
714diff --git a/lib/lp/archiveuploader/changesfile.py b/lib/lp/archiveuploader/changesfile.py
715index 1a28b35..1a97999 100644
716--- a/lib/lp/archiveuploader/changesfile.py
717+++ b/lib/lp/archiveuploader/changesfile.py
718@@ -58,13 +58,13 @@ class CannotDetermineFileTypeError(Exception):
719 class ChangesFile(SignableTagFile):
720 """Changesfile model."""
721
722- mandatory_fields = set([
723+ mandatory_fields = {
724 "Source", "Architecture", "Version", "Distribution",
725 "Maintainer", "Files", "Changes", "Date",
726 # Changed-By is not technically mandatory according to
727 # Debian policy but Soyuz relies on it being set in
728 # various places.
729- "Changed-By"])
730+ "Changed-By"}
731
732 # Map urgencies to their dbschema values.
733 # Debian policy only permits low, medium, high, emergency.
734diff --git a/lib/lp/archiveuploader/dscfile.py b/lib/lp/archiveuploader/dscfile.py
735index 0ca6d03..50e6d70 100644
736--- a/lib/lp/archiveuploader/dscfile.py
737+++ b/lib/lp/archiveuploader/dscfile.py
738@@ -250,15 +250,15 @@ class SignableTagFile:
739 class DSCFile(SourceUploadFile, SignableTagFile):
740 """Models a given DSC file and its content."""
741
742- mandatory_fields = set([
743+ mandatory_fields = {
744 "Source",
745 "Version",
746 "Binary",
747 "Maintainer",
748 "Architecture",
749- "Files"])
750+ "Files"}
751
752- known_fields = mandatory_fields.union(set([
753+ known_fields = mandatory_fields.union({
754 "Build-Depends",
755 "Build-Depends-Indep",
756 "Build-Conflicts",
757@@ -269,7 +269,7 @@ class DSCFile(SourceUploadFile, SignableTagFile):
758 "Format",
759 "Homepage",
760 "Standards-Version",
761- ]))
762+ })
763
764 # Note that files is actually only set inside verify().
765 files = None
766diff --git a/lib/lp/archiveuploader/nascentupload.py b/lib/lp/archiveuploader/nascentupload.py
767index eba9a06..cb6e144 100644
768--- a/lib/lp/archiveuploader/nascentupload.py
769+++ b/lib/lp/archiveuploader/nascentupload.py
770@@ -458,7 +458,7 @@ class NascentUpload:
771
772 def getComponents(self):
773 """Return a set of components present in the uploaded files."""
774- return set(file.component_name for file in self.changes.files)
775+ return {file.component_name for file in self.changes.files}
776
777 def reject(self, msg):
778 """Add the provided message to the rejection message."""
779diff --git a/lib/lp/archiveuploader/nascentuploadfile.py b/lib/lp/archiveuploader/nascentuploadfile.py
780index b3d68cc..e996fc4 100644
781--- a/lib/lp/archiveuploader/nascentuploadfile.py
782+++ b/lib/lp/archiveuploader/nascentuploadfile.py
783@@ -215,7 +215,7 @@ class NascentUploadFile:
784
785 # Read in the file and compute its md5 and sha1 checksums and remember
786 # the size of the file as read-in.
787- digesters = dict((n, hashlib.new(n)) for n in self.checksums.keys())
788+ digesters = {n: hashlib.new(n) for n in self.checksums.keys()}
789 with open(self.filepath, "rb") as ckfile:
790 size = 0
791 for chunk in filechunks(ckfile):
792@@ -432,9 +432,9 @@ class BaseBinaryUploadFile(PackageUploadFile):
793 ddeb_file = None
794
795 # Capitalised because we extract these directly from the control file.
796- mandatory_fields = set(["Package", "Architecture", "Version"])
797+ mandatory_fields = {"Package", "Architecture", "Version"}
798
799- known_fields = mandatory_fields.union(set([
800+ known_fields = mandatory_fields.union({
801 "Depends",
802 "Conflicts",
803 "Breaks",
804@@ -458,7 +458,7 @@ class BaseBinaryUploadFile(PackageUploadFile):
805 "Maintainer",
806 "Source",
807 "Homepage",
808- ]))
809+ })
810
811 # Map priorities to their dbschema valuesa
812 # We treat a priority of '-' as EXTRA since some packages in some distros
813diff --git a/lib/lp/archiveuploader/tests/__init__.py b/lib/lp/archiveuploader/tests/__init__.py
814index 6fe2757..2133cd0 100644
815--- a/lib/lp/archiveuploader/tests/__init__.py
816+++ b/lib/lp/archiveuploader/tests/__init__.py
817@@ -49,7 +49,7 @@ def insertFakeChangesFile(fileID, path=None):
818
819 def insertFakeChangesFileForAllPackageUploads():
820 """Ensure all the PackageUpload records point to a valid changes file."""
821- for id in set(pu.changesfile.content.id for pu in PackageUploadSet()):
822+ for id in {pu.changesfile.content.id for pu in PackageUploadSet()}:
823 insertFakeChangesFile(id)
824
825
826diff --git a/lib/lp/archiveuploader/tests/test_changesfile.py b/lib/lp/archiveuploader/tests/test_changesfile.py
827index 6ce64e8..427b43b 100644
828--- a/lib/lp/archiveuploader/tests/test_changesfile.py
829+++ b/lib/lp/archiveuploader/tests/test_changesfile.py
830@@ -209,7 +209,7 @@ class ChangesFileTests(TestCase):
831 contents["Binary"] = "binary1\n binary2 \n binary3"
832 changes = self.createChangesFile("mypkg_0.1_i386.changes", contents)
833 self.assertEqual(
834- set(["binary1", "binary2", "binary3"]), changes.binaries)
835+ {"binary1", "binary2", "binary3"}, changes.binaries)
836
837 def test_checkFileName(self):
838 # checkFileName() yields an UploadError if the filename is invalid.
839@@ -245,7 +245,7 @@ class ChangesFileTests(TestCase):
840 changes = self.createChangesFile(
841 "mypkg_0.1_i386.changes", self.getBaseChanges())
842 self.assertEqual("i386", changes.architecture_line)
843- self.assertEqual(set(["i386"]), changes.architectures)
844+ self.assertEqual({"i386"}, changes.architectures)
845
846 def test_source(self):
847 # The source package name gets extracted from the changes file.
848diff --git a/lib/lp/archiveuploader/utils.py b/lib/lp/archiveuploader/utils.py
849index 949b37a..5ff24d2 100644
850--- a/lib/lp/archiveuploader/utils.py
851+++ b/lib/lp/archiveuploader/utils.py
852@@ -324,7 +324,7 @@ def merge_file_lists(files, checksums_sha1, checksums_sha256, changes=True):
853 (filename, file_hashes[filename], size))
854
855 # Ensure that each filename was only listed in Files once.
856- if set(six.itervalues(file_counter)) - set([1]):
857+ if set(six.itervalues(file_counter)) - {1}:
858 raise UploadError("Duplicate filenames in Files field.")
859
860 # Ensure that the Checksums-Sha1 and Checksums-Sha256 fields, if
861diff --git a/lib/lp/blueprints/browser/person_upcomingwork.py b/lib/lp/blueprints/browser/person_upcomingwork.py
862index 5646a25..37b0030 100644
863--- a/lib/lp/blueprints/browser/person_upcomingwork.py
864+++ b/lib/lp/blueprints/browser/person_upcomingwork.py
865@@ -62,7 +62,7 @@ class PersonUpcomingWorkView(LaunchpadView):
866 if total_items > 0:
867 done_or_postponed = total_done + total_postponed
868 percent_done = 100.0 * done_or_postponed / total_items
869- self.progress_per_date[date] = '{0:.0f}'.format(percent_done)
870+ self.progress_per_date[date] = '{:.0f}'.format(percent_done)
871
872 @property
873 def label(self):
874@@ -124,7 +124,7 @@ class WorkItemContainer(object):
875 done_or_postponed = (len(self.done_items) +
876 len(self.postponed_items))
877 percent_done = 100.0 * done_or_postponed / len(self._items)
878- return '{0:.0f}'.format(percent_done)
879+ return '{:.0f}'.format(percent_done)
880
881 @property
882 def has_incomplete_work(self):
883diff --git a/lib/lp/blueprints/browser/specification.py b/lib/lp/blueprints/browser/specification.py
884index cc2d3b0..2f89e1e 100644
885--- a/lib/lp/blueprints/browser/specification.py
886+++ b/lib/lp/blueprints/browser/specification.py
887@@ -1180,7 +1180,7 @@ class SpecGraph:
888 graph.link(node, related)
889 """
890 # This is a standard pattern for "flattening" a recursive algorithm.
891- to_search = set([spec])
892+ to_search = {spec}
893 visited = set()
894 while to_search:
895 current_spec = to_search.pop()
896@@ -1341,7 +1341,7 @@ class SpecGraphNode:
897 # We want to have links in the image map for all nodes
898 # except the one that were currently on the page of.
899 attrnames.append('URL')
900- attrdict = dict((name, getattr(self, name)) for name in attrnames)
901+ attrdict = {name: getattr(self, name) for name in attrnames}
902 return u'%s\n%s' % (to_DOT_ID(self.name), dict_to_DOT_attrs(attrdict))
903
904
905diff --git a/lib/lp/blueprints/browser/sprint.py b/lib/lp/blueprints/browser/sprint.py
906index a7f1fdb..3945820 100644
907--- a/lib/lp/blueprints/browser/sprint.py
908+++ b/lib/lp/blueprints/browser/sprint.py
909@@ -410,8 +410,8 @@ class SprintTopicSetView(HasSpecificationsView, LaunchpadView):
910 def initialize(self):
911 self.status_message = None
912 self.process_form()
913- self.attendee_ids = set(
914- attendance.attendeeID for attendance in self.context.attendances)
915+ self.attendee_ids = {
916+ attendance.attendeeID for attendance in self.context.attendances}
917
918 @cachedproperty
919 def spec_filter(self):
920@@ -523,8 +523,8 @@ class SprintMeetingExportView(LaunchpadView):
921 if spec.drafter is not None:
922 spec_people[spec.drafter.id] = True
923 attendee_set.add(spec.drafter.id)
924- people_by_id = dict((person.id, person) for person in
925- getUtility(IPersonSet).getPrecachedPersonsFromIDs(attendee_set))
926+ people_by_id = {person.id: person for person in
927+ getUtility(IPersonSet).getPrecachedPersonsFromIDs(attendee_set)}
928 self.specifications = [
929 dict(spec=spec, interested=[
930 dict(name=people_by_id[person_id].name, required=required)
931@@ -593,9 +593,9 @@ class SprintAttendeesCsvExportView(LaunchpadView):
932 location = attendance.attendee.location
933 if location is not None and location.visible:
934 time_zone = attendance.attendee.time_zone
935- irc_nicknames = ', '.join(sorted(set(
936- [ircid.nickname for ircid
937- in attendance.attendee.ircnicknames])))
938+ irc_nicknames = ', '.join(sorted({
939+ ircid.nickname for ircid
940+ in attendance.attendee.ircnicknames}))
941 rows.append(
942 (attendance.attendee.name,
943 attendance.attendee.displayname,
944diff --git a/lib/lp/blueprints/browser/tests/test_specification.py b/lib/lp/blueprints/browser/tests/test_specification.py
945index 19596ff..192f0c2 100644
946--- a/lib/lp/blueprints/browser/tests/test_specification.py
947+++ b/lib/lp/blueprints/browser/tests/test_specification.py
948@@ -370,7 +370,7 @@ NEW_SPEC_FROM_ROOT_URL = 'http://blueprints.launchpad.test/specs/+new'
949
950 class NewSpecificationTests:
951
952- expected_keys = set(['PROPRIETARY', 'PUBLIC', 'EMBARGOED'])
953+ expected_keys = {'PROPRIETARY', 'PUBLIC', 'EMBARGOED'}
954
955 def _create_form_data(self, context):
956 return {
957@@ -474,7 +474,7 @@ class TestNewSpecificationFromProductView(TestCaseWithFactory,
958
959 layer = DatabaseFunctionalLayer
960
961- expected_keys = set(['PROPRIETARY', 'EMBARGOED'])
962+ expected_keys = {'PROPRIETARY', 'EMBARGOED'}
963
964 def createInitializedView(self):
965 policy = SpecificationSharingPolicy.EMBARGOED_OR_PROPRIETARY
966@@ -495,7 +495,7 @@ class TestNewSpecificationFromDistributionView(TestCaseWithFactory,
967
968 layer = DatabaseFunctionalLayer
969
970- expected_keys = set(['PUBLIC'])
971+ expected_keys = {'PUBLIC'}
972
973 def createInitializedView(self):
974 distro = self.factory.makeDistribution()
975diff --git a/lib/lp/blueprints/browser/tests/test_specificationsubscription.py b/lib/lp/blueprints/browser/tests/test_specificationsubscription.py
976index ab7ff1d..6f0d148 100644
977--- a/lib/lp/blueprints/browser/tests/test_specificationsubscription.py
978+++ b/lib/lp/blueprints/browser/tests/test_specificationsubscription.py
979@@ -41,7 +41,7 @@ class TestSpecificationPortletSubcribersIds(TestCaseWithFactory):
980 spec.subscribe(subscriber, subscriber)
981 view = create_initialized_view(
982 spec, name="+blueprint-portlet-subscribers-ids")
983- subscriber_ids = dict(
984- (subscriber.name, 'subscriber-%s' % subscriber.id)
985- for subscriber in [person, subscriber])
986+ subscriber_ids = {
987+ subscriber.name: 'subscriber-%s' % subscriber.id
988+ for subscriber in [person, subscriber]}
989 self.assertEqual(subscriber_ids, view.subscriber_ids)
990diff --git a/lib/lp/blueprints/model/specificationsearch.py b/lib/lp/blueprints/model/specificationsearch.py
991index 0e77bc2..a8404ff 100644
992--- a/lib/lp/blueprints/model/specificationsearch.py
993+++ b/lib/lp/blueprints/model/specificationsearch.py
994@@ -69,13 +69,13 @@ def search_specifications(context, base_clauses, user, sort=None,
995 store = IStore(Specification)
996 if not default_acceptance:
997 default = SpecificationFilter.INCOMPLETE
998- options = set([
999- SpecificationFilter.COMPLETE, SpecificationFilter.INCOMPLETE])
1000+ options = {
1001+ SpecificationFilter.COMPLETE, SpecificationFilter.INCOMPLETE}
1002 else:
1003 default = SpecificationFilter.ACCEPTED
1004- options = set([
1005+ options = {
1006 SpecificationFilter.ACCEPTED, SpecificationFilter.DECLINED,
1007- SpecificationFilter.PROPOSED])
1008+ SpecificationFilter.PROPOSED}
1009 if not spec_filter:
1010 spec_filter = [default]
1011
1012@@ -120,8 +120,8 @@ def search_specifications(context, base_clauses, user, sort=None,
1013 # If not specially looking for complete, we care about date
1014 # registered.
1015 order = []
1016- show_proposed = set(
1017- [SpecificationFilter.ALL, SpecificationFilter.PROPOSED])
1018+ show_proposed = {
1019+ SpecificationFilter.ALL, SpecificationFilter.PROPOSED}
1020 if default_acceptance and not (set(spec_filter) & show_proposed):
1021 order.append(Desc(Specification.date_goal_decided))
1022 order.extend([Desc(Specification.datecreated), Specification.id])
1023@@ -135,8 +135,8 @@ def search_specifications(context, base_clauses, user, sort=None,
1024 work_items_by_spec = defaultdict(list)
1025 for spec in rows:
1026 if need_people:
1027- person_ids |= set(
1028- [spec._assigneeID, spec._approverID, spec._drafterID])
1029+ person_ids |= {
1030+ spec._assigneeID, spec._approverID, spec._drafterID}
1031 if need_branches:
1032 get_property_cache(spec).linked_branches = []
1033 if need_workitems:
1034@@ -146,7 +146,7 @@ def search_specifications(context, base_clauses, user, sort=None,
1035 for workitem in work_items:
1036 person_ids.add(workitem.assignee_id)
1037 work_items_by_spec[workitem.specification_id].append(workitem)
1038- person_ids -= set([None])
1039+ person_ids -= {None}
1040 if need_people:
1041 list(getUtility(IPersonSet).getPrecachedPersonsFromIDs(
1042 person_ids, need_validity=True))
1043@@ -274,7 +274,7 @@ def _make_cache_user_can_view_spec(user):
1044 userid = user.id
1045
1046 def cache_user_can_view_spec(spec):
1047- get_property_cache(spec)._known_viewers = set([userid])
1048+ get_property_cache(spec)._known_viewers = {userid}
1049 return spec
1050 return cache_user_can_view_spec
1051
1052diff --git a/lib/lp/blueprints/model/sprint.py b/lib/lp/blueprints/model/sprint.py
1053index 65c04b8..32607bb 100644
1054--- a/lib/lp/blueprints/model/sprint.py
1055+++ b/lib/lp/blueprints/model/sprint.py
1056@@ -192,7 +192,7 @@ class Sprint(StormBase, HasDriversMixin, HasSpecificationsMixin):
1057 # need_* is provided only for interface compatibility and
1058 # need_*=True is not implemented.
1059 if filter is None:
1060- filter = set([SpecificationFilter.ACCEPTED])
1061+ filter = {SpecificationFilter.ACCEPTED}
1062 tables, query = self.spec_filter_clause(user, filter)
1063 # import here to avoid circular deps
1064 from lp.blueprints.model.specification import Specification
1065diff --git a/lib/lp/blueprints/tests/test_specification.py b/lib/lp/blueprints/tests/test_specification.py
1066index 3ce41fe..68198a6 100644
1067--- a/lib/lp/blueprints/tests/test_specification.py
1068+++ b/lib/lp/blueprints/tests/test_specification.py
1069@@ -158,9 +158,9 @@ class SpecificationTests(TestCaseWithFactory):
1070
1071 def test_get_permissions(self):
1072 expected_get_permissions = {
1073- CheckerPublic: set((
1074- 'id', 'information_type', 'private', 'userCanView')),
1075- 'launchpad.LimitedView': set((
1076+ CheckerPublic: {
1077+ 'id', 'information_type', 'private', 'userCanView'},
1078+ 'launchpad.LimitedView': {
1079 'all_blocked', 'all_deps', 'approver', 'approverID',
1080 'assignee', 'assigneeID', 'bugs', 'completer',
1081 'createDependency', 'date_completed', 'date_goal_decided',
1082@@ -182,14 +182,14 @@ class SpecificationTests(TestCaseWithFactory):
1083 'superseded_by', 'target', 'title', 'unlinkBranch',
1084 'unlinkSprint', 'unsubscribe', 'updateLifecycleStatus',
1085 'validateMove', 'whiteboard', 'work_items',
1086- 'workitems_text')),
1087- 'launchpad.Edit': set((
1088+ 'workitems_text'},
1089+ 'launchpad.Edit': {
1090 'newWorkItem', 'proposeGoal', 'retarget',
1091 'setDefinitionStatus', 'setImplementationStatus', 'setTarget',
1092- 'transitionToInformationType', 'updateWorkItems')),
1093- 'launchpad.Driver': set(('acceptBy', 'declineBy')),
1094- 'launchpad.AnyLegitimatePerson': set((
1095- 'unlinkBug', 'linkBug', 'setWorkItems')),
1096+ 'transitionToInformationType', 'updateWorkItems'},
1097+ 'launchpad.Driver': {'acceptBy', 'declineBy'},
1098+ 'launchpad.AnyLegitimatePerson': {
1099+ 'unlinkBug', 'linkBug', 'setWorkItems'},
1100 }
1101 specification = self.factory.makeSpecification()
1102 checker = getChecker(specification)
1103@@ -198,13 +198,13 @@ class SpecificationTests(TestCaseWithFactory):
1104
1105 def test_set_permissions(self):
1106 expected_get_permissions = {
1107- 'launchpad.Admin': set(('direction_approved', 'priority')),
1108- 'launchpad.AnyLegitimatePerson': set(('whiteboard', )),
1109- 'launchpad.Edit': set((
1110+ 'launchpad.Admin': {'direction_approved', 'priority'},
1111+ 'launchpad.AnyLegitimatePerson': {'whiteboard'},
1112+ 'launchpad.Edit': {
1113 'approver', 'assignee', 'definition_status', 'distribution',
1114 'drafter', 'implementation_status', 'man_days', 'milestone',
1115 'name', 'product', 'specurl', 'summary', 'superseded_by',
1116- 'title')),
1117+ 'title'},
1118 }
1119 specification = self.factory.makeSpecification()
1120 checker = getChecker(specification)
1121diff --git a/lib/lp/bugs/browser/bug.py b/lib/lp/bugs/browser/bug.py
1122index 04c4f69..f4e5eea 100644
1123--- a/lib/lp/bugs/browser/bug.py
1124+++ b/lib/lp/bugs/browser/bug.py
1125@@ -570,10 +570,10 @@ class BugView(LaunchpadView, BugViewMixin):
1126 """
1127 duplicate_bugs = list(self.context.duplicates)
1128 current_task = self.current_bugtask
1129- dupes_in_current_context = dict(
1130- (bugtask.bug, bugtask)
1131+ dupes_in_current_context = {
1132+ bugtask.bug: bugtask
1133 for bugtask in current_task.target.searchTasks(
1134- BugTaskSearchParams(self.user, bug=any(*duplicate_bugs))))
1135+ BugTaskSearchParams(self.user, bug=any(*duplicate_bugs)))}
1136 dupes = []
1137 for bug in duplicate_bugs:
1138 # Don't disclose even the ID of a private bug. The link will
1139diff --git a/lib/lp/bugs/browser/bugalsoaffects.py b/lib/lp/bugs/browser/bugalsoaffects.py
1140index d1bfe3e..40f30f4 100644
1141--- a/lib/lp/bugs/browser/bugalsoaffects.py
1142+++ b/lib/lp/bugs/browser/bugalsoaffects.py
1143@@ -650,8 +650,8 @@ class ProductBugTaskCreationStep(BugTaskCreationStep):
1144 # link_upstream_how has _displayItemForMissingValue=False
1145 # so that renderItems() doesn't return an extra radio button which
1146 # prevents it from matching widget.vocabulary's ordering.
1147- return dict((entry.token, items[i])
1148- for i, entry in enumerate(widget.vocabulary))
1149+ return {entry.token: items[i]
1150+ for i, entry in enumerate(widget.vocabulary)}
1151
1152 def main_action(self, data):
1153 link_upstream_how = data.get('link_upstream_how')
1154diff --git a/lib/lp/bugs/browser/buglisting.py b/lib/lp/bugs/browser/buglisting.py
1155index 8e8e49e..3a4a6c3 100644
1156--- a/lib/lp/bugs/browser/buglisting.py
1157+++ b/lib/lp/bugs/browser/buglisting.py
1158@@ -1070,8 +1070,8 @@ class BugTaskSearchListingView(LaunchpadFormView, FeedsMixin, BugsInfoMixin):
1159 not FeedsLayer.providedBy(self.request) and
1160 not self.request.form.get('advanced')):
1161 cache = IJSONRequestCache(self.request)
1162- view_names = set(reg.name for reg
1163- in iter_view_registrations(self.__class__))
1164+ view_names = {reg.name for reg
1165+ in iter_view_registrations(self.__class__)}
1166 if len(view_names) != 1:
1167 raise AssertionError("Ambiguous view name.")
1168 cache.objects['view_name'] = view_names.pop()
1169@@ -1157,7 +1157,7 @@ class BugTaskSearchListingView(LaunchpadFormView, FeedsMixin, BugsInfoMixin):
1170 "are out of date or you changed the URL by hand?" %
1171 field_name)
1172
1173- sort_column_names = set(sort_key[0] for sort_key in SORT_KEYS)
1174+ sort_column_names = {sort_key[0] for sort_key in SORT_KEYS}
1175 orderby = get_sortorder_from_request(self.request)
1176 for orderby_col in orderby:
1177 if orderby_col.startswith("-"):
1178diff --git a/lib/lp/bugs/browser/bugtarget.py b/lib/lp/bugs/browser/bugtarget.py
1179index a8bfe2e..d140bca 100644
1180--- a/lib/lp/bugs/browser/bugtarget.py
1181+++ b/lib/lp/bugs/browser/bugtarget.py
1182@@ -1222,12 +1222,12 @@ class BugTargetBugTagsView(LaunchpadView):
1183 self.user, 10, official_tags)
1184
1185 return sorted(
1186- [dict(
1187+ (dict(
1188 tag=tag,
1189 count=count,
1190 url=self._getSearchURL(tag),
1191 )
1192- for (tag, count) in six.iteritems(tags)],
1193+ for (tag, count) in six.iteritems(tags)),
1194 key=lambda item: (-item['count'], item['tag']))
1195
1196 @property
1197diff --git a/lib/lp/bugs/browser/bugtask.py b/lib/lp/bugs/browser/bugtask.py
1198index 5852a49..a4b0fc0 100644
1199--- a/lib/lp/bugs/browser/bugtask.py
1200+++ b/lib/lp/bugs/browser/bugtask.py
1201@@ -284,7 +284,7 @@ def get_visible_comments(comments, user=None):
1202 # so that checking owner.is_valid_person, when rendering the link,
1203 # won't issue a DB query. Note that this should be obsolete now with
1204 # getMessagesForView improvements.
1205- commenters = set(comment.owner for comment in visible_comments)
1206+ commenters = {comment.owner for comment in visible_comments}
1207 getUtility(IPersonSet).getValidPersons(commenters)
1208
1209 # If a user is supplied, we can also strip out comments that the user
1210@@ -602,8 +602,8 @@ class BugTaskView(LaunchpadView, BugViewMixin, FeedsMixin):
1211 activity_item for activity_item in activity
1212 if interesting_match(activity_item.whatchanged) is not None]
1213 # Pre-load the doers of the activities in one query.
1214- person_ids = set(
1215- activity_item.personID for activity_item in activity_items)
1216+ person_ids = {
1217+ activity_item.personID for activity_item in activity_items}
1218 list(getUtility(IPersonSet).getPrecachedPersonsFromIDs(
1219 person_ids, need_validity=True))
1220
1221@@ -703,10 +703,10 @@ class BugTaskView(LaunchpadView, BugViewMixin, FeedsMixin):
1222 activities, attrgetter("target"))]
1223
1224 def comment_event_dict(comment):
1225- actors = set(activity.person for activity in comment.activity)
1226+ actors = {activity.person for activity in comment.activity}
1227 actors.add(comment.owner)
1228 assert len(actors) == 1, actors
1229- dates = set(activity.datechanged for activity in comment.activity)
1230+ dates = {activity.datechanged for activity in comment.activity}
1231 dates.add(comment.datecreated)
1232 comment.activity = group_activities_by_target(comment.activity)
1233 return {
1234@@ -716,9 +716,9 @@ class BugTaskView(LaunchpadView, BugViewMixin, FeedsMixin):
1235 }
1236
1237 def activity_event_dict(activities):
1238- actors = set(activity.person for activity in activities)
1239+ actors = {activity.person for activity in activities}
1240 assert len(actors) == 1, actors
1241- dates = set(activity.datechanged for activity in activities)
1242+ dates = {activity.datechanged for activity in activities}
1243 return {
1244 "activity": group_activities_by_target(activities),
1245 "date": min(dates),
1246@@ -1173,7 +1173,7 @@ class BugTaskEditView(LaunchpadEditFormView, BugTaskBugWatchMixin,
1247 if 'importance' in editable_field_names:
1248 editable_field_names.remove("importance")
1249 else:
1250- editable_field_names = set(('bugwatch', ))
1251+ editable_field_names = {'bugwatch'}
1252 if self.context.bugwatch is None:
1253 editable_field_names.update(('status', 'assignee'))
1254 if ('importance' in self.default_field_names
1255@@ -1250,8 +1250,8 @@ class BugTaskEditView(LaunchpadEditFormView, BugTaskBugWatchMixin,
1256 if self.user is None:
1257 status_noshow = set(BugTaskStatus.items)
1258 else:
1259- status_noshow = set((
1260- BugTaskStatus.UNKNOWN, BugTaskStatus.EXPIRED))
1261+ status_noshow = {
1262+ BugTaskStatus.UNKNOWN, BugTaskStatus.EXPIRED}
1263 status_noshow.update(
1264 status for status in BugTaskStatus.items
1265 if not self.context.canTransitionToStatus(
1266diff --git a/lib/lp/bugs/browser/bugtracker.py b/lib/lp/bugs/browser/bugtracker.py
1267index 95c1479..dee3683 100644
1268--- a/lib/lp/bugs/browser/bugtracker.py
1269+++ b/lib/lp/bugs/browser/bugtracker.py
1270@@ -375,9 +375,9 @@ class BugTrackerEditView(LaunchpadEditFormView):
1271
1272 # If the bugtracker is a celebrity then we protect it from
1273 # deletion.
1274- celebrities_set = set(
1275+ celebrities_set = {
1276 getattr(celebrities, name)
1277- for name in ILaunchpadCelebrities.names())
1278+ for name in ILaunchpadCelebrities.names()}
1279 if self.context in celebrities_set:
1280 reasons.append(
1281 'This bug tracker is protected from deletion.')
1282diff --git a/lib/lp/bugs/browser/structuralsubscription.py b/lib/lp/bugs/browser/structuralsubscription.py
1283index 66415f3..5506bee 100644
1284--- a/lib/lp/bugs/browser/structuralsubscription.py
1285+++ b/lib/lp/bugs/browser/structuralsubscription.py
1286@@ -155,10 +155,10 @@ class StructuralSubscriptionView(LaunchpadFormView):
1287 be removed, else return None.
1288 """
1289 teams = set(self.user_teams)
1290- other_subscriptions = set(
1291+ other_subscriptions = {
1292 subscription.subscriber
1293 for subscription
1294- in self.context.bug_subscriptions)
1295+ in self.context.bug_subscriptions}
1296
1297 # Teams and the current user have their own UI elements. Remove
1298 # them to avoid duplicates.
1299@@ -196,9 +196,9 @@ class StructuralSubscriptionView(LaunchpadFormView):
1300 def initial_values(self):
1301 """See `LaunchpadFormView`."""
1302 teams = set(self.user_teams)
1303- subscribed_teams = set(team
1304+ subscribed_teams = {team
1305 for team in teams
1306- if self.isSubscribed(team))
1307+ if self.isSubscribed(team)}
1308 return {
1309 'subscribe_me': self.currentUserIsSubscribed(),
1310 'subscriptions_team': subscribed_teams,
1311@@ -261,8 +261,8 @@ class StructuralSubscriptionView(LaunchpadFormView):
1312 target = self.context
1313 teams = set(self.user_teams)
1314 form_selected_teams = teams & set(form_selected_teams)
1315- subscriptions = set(
1316- team for team in teams if self.isSubscribed(team))
1317+ subscriptions = {
1318+ team for team in teams if self.isSubscribed(team)}
1319
1320 for team in form_selected_teams - subscriptions:
1321 target.addBugSubscription(team, self.user)
1322diff --git a/lib/lp/bugs/browser/tests/test_bugcomment.py b/lib/lp/bugs/browser/tests/test_bugcomment.py
1323index c23f3b0..f93a5c9 100644
1324--- a/lib/lp/bugs/browser/tests/test_bugcomment.py
1325+++ b/lib/lp/bugs/browser/tests/test_bugcomment.py
1326@@ -129,7 +129,7 @@ class TestGroupCommentsWithActivities(TestCase):
1327 activity2 = BugActivityStub(next(self.time_index)[0])
1328 comment2 = BugCommentStub(*next(self.time_index))
1329
1330- activities = set([activity1, activity2])
1331+ activities = {activity1, activity2}
1332 comments = list([comment1, comment2])
1333
1334 self.assertEqual(
1335diff --git a/lib/lp/bugs/browser/tests/test_bugsubscriptionfilter.py b/lib/lp/bugs/browser/tests/test_bugsubscriptionfilter.py
1336index c0db2c2..342e984 100644
1337--- a/lib/lp/bugs/browser/tests/test_bugsubscriptionfilter.py
1338+++ b/lib/lp/bugs/browser/tests/test_bugsubscriptionfilter.py
1339@@ -160,7 +160,7 @@ class TestBugSubscriptionFilterAPIModifications(
1340 self.assertTrue(self.subscription_filter.include_any_tags)
1341 self.assertTrue(self.subscription_filter.exclude_any_tags)
1342 self.assertEqual(
1343- set(["*", "-*", "foo", "-bar"]),
1344+ {"*", "-*", "foo", "-bar"},
1345 self.subscription_filter.tags)
1346
1347 def test_modify_description(self):
1348@@ -189,7 +189,7 @@ class TestBugSubscriptionFilterAPIModifications(
1349
1350 # Updated state.
1351 self.assertEqual(
1352- set([BugTaskStatus.NEW, BugTaskStatus.TRIAGED]),
1353+ {BugTaskStatus.NEW, BugTaskStatus.TRIAGED},
1354 self.subscription_filter.statuses)
1355
1356 def test_modify_importances(self):
1357@@ -204,7 +204,7 @@ class TestBugSubscriptionFilterAPIModifications(
1358
1359 # Updated state.
1360 self.assertEqual(
1361- set([BugTaskImportance.LOW, BugTaskImportance.HIGH]),
1362+ {BugTaskImportance.LOW, BugTaskImportance.HIGH},
1363 self.subscription_filter.importances)
1364
1365 def test_delete(self):
1366diff --git a/lib/lp/bugs/browser/tests/test_bugtask.py b/lib/lp/bugs/browser/tests/test_bugtask.py
1367index 4cc1c9c..5eb97d6 100644
1368--- a/lib/lp/bugs/browser/tests/test_bugtask.py
1369+++ b/lib/lp/bugs/browser/tests/test_bugtask.py
1370@@ -2491,7 +2491,7 @@ class TestBugTaskSearchListingView(BrowserTestCase):
1371 view = self.makeView()
1372 cache = IJSONRequestCache(view.request)
1373 json_sort_keys = cache.objects['sort_keys']
1374- json_sort_keys = set(key[0] for key in json_sort_keys)
1375+ json_sort_keys = {key[0] for key in json_sort_keys}
1376 valid_keys = set(orderby_expression.keys())
1377 self.assertEqual(
1378 valid_keys, json_sort_keys,
1379diff --git a/lib/lp/bugs/externalbugtracker/bugzilla.py b/lib/lp/bugs/externalbugtracker/bugzilla.py
1380index 7a84697..a84a575 100644
1381--- a/lib/lp/bugs/externalbugtracker/bugzilla.py
1382+++ b/lib/lp/bugs/externalbugtracker/bugzilla.py
1383@@ -845,8 +845,8 @@ class BugzillaAPI(Bugzilla):
1384 del comments[comment_id]
1385
1386 # Ensure that comment IDs are converted to ints.
1387- comments_with_int_ids = dict(
1388- (int(id), comments[id]) for id in comments)
1389+ comments_with_int_ids = {
1390+ int(id): comments[id] for id in comments}
1391 self._bugs[actual_bug_id]['comments'] = comments_with_int_ids
1392
1393 def getPosterForComment(self, remote_bug_id, comment_id):
1394@@ -1090,8 +1090,8 @@ class BugzillaLPPlugin(BugzillaAPI):
1395 comment_list = bug_comments_dict['bugs'][str(actual_bug_id)]
1396
1397 # Transfer the comment list into a dict.
1398- bug_comments = dict(
1399- (comment['id'], comment) for comment in comment_list)
1400+ bug_comments = {
1401+ comment['id']: comment for comment in comment_list}
1402
1403 self._bugs[actual_bug_id]['comments'] = bug_comments
1404
1405diff --git a/lib/lp/bugs/interfaces/bugtasksearch.py b/lib/lp/bugs/interfaces/bugtasksearch.py
1406index ce3970a..7c18d58 100644
1407--- a/lib/lp/bugs/interfaces/bugtasksearch.py
1408+++ b/lib/lp/bugs/interfaces/bugtasksearch.py
1409@@ -217,7 +217,7 @@ class BugTaskSearchParams:
1410 if isinstance(information_type, collections.Iterable):
1411 self.information_type = set(information_type)
1412 elif information_type:
1413- self.information_type = set((information_type,))
1414+ self.information_type = {information_type}
1415 else:
1416 self.information_type = None
1417 self.ignore_privacy = ignore_privacy
1418@@ -674,7 +674,7 @@ def get_person_bugtasks_search_params(user, context, **kwargs):
1419 # modified the query in an invalid way by overwriting all user
1420 # related parameters
1421 raise IllegalRelatedBugTasksParams(
1422- ('Cannot search for related tasks to \'%s\', at least one '
1423+ 'Cannot search for related tasks to \'%s\', at least one '
1424 'of these parameter has to be empty: %s'
1425- % (context.name, ", ".join(relevant_fields))))
1426+ % (context.name, ", ".join(relevant_fields)))
1427 return search_params
1428diff --git a/lib/lp/bugs/interfaces/tests/test_bugtask.py b/lib/lp/bugs/interfaces/tests/test_bugtask.py
1429index 3c33527..f940c15 100644
1430--- a/lib/lp/bugs/interfaces/tests/test_bugtask.py
1431+++ b/lib/lp/bugs/interfaces/tests/test_bugtask.py
1432@@ -17,9 +17,9 @@ class TestFunctions(TestCase):
1433
1434 def test_get_bugtask_status(self):
1435 # Compose a map of BugTaskStatusSearch members from their values.
1436- expected = dict(
1437- (status.value, status)
1438- for status in BugTaskStatusSearch.items)
1439+ expected = {
1440+ status.value: status
1441+ for status in BugTaskStatusSearch.items}
1442 # Update the expected status map - overwriting some entries - from
1443 # BugTaskStatus members and their values.
1444 expected.update(
1445@@ -27,9 +27,9 @@ class TestFunctions(TestCase):
1446 for status in BugTaskStatus.items)
1447 # Compose a map of statuses as discovered by value for each member of
1448 # BugTaskStatusSearch.
1449- observed = dict(
1450- (status.value, get_bugtask_status(status.value))
1451- for status in BugTaskStatusSearch.items)
1452+ observed = {
1453+ status.value: get_bugtask_status(status.value)
1454+ for status in BugTaskStatusSearch.items}
1455 # Update the expected status map with statuses discovered by value for
1456 # each member of BugTaskStatus.
1457 observed.update(
1458@@ -52,9 +52,9 @@ class TestFunctions(TestCase):
1459 BugTaskStatus.UNKNOWN: BugTaskStatus.UNKNOWN,
1460 BugTaskStatus.WONTFIX: BugTaskStatus.WONTFIX,
1461 }
1462- observed = dict(
1463- (status, normalize_bugtask_status(status))
1464- for status in BugTaskStatus.items)
1465+ observed = {
1466+ status: normalize_bugtask_status(status)
1467+ for status in BugTaskStatus.items}
1468 self.assertEqual(expected, observed)
1469
1470 def test_normalize_bugtask_status_from_BugTaskStatusSearch(self):
1471@@ -75,9 +75,9 @@ class TestFunctions(TestCase):
1472 BugTaskStatusSearch.TRIAGED: BugTaskStatus.TRIAGED,
1473 BugTaskStatusSearch.WONTFIX: BugTaskStatus.WONTFIX,
1474 }
1475- observed = dict(
1476- (status, normalize_bugtask_status(status))
1477- for status in BugTaskStatusSearch.items)
1478+ observed = {
1479+ status: normalize_bugtask_status(status)
1480+ for status in BugTaskStatusSearch.items}
1481 self.assertEqual(expected, observed)
1482
1483 def test_normalize_bugtask_status_from_BugTaskStatusSearchDisplay(self):
1484@@ -99,7 +99,7 @@ class TestFunctions(TestCase):
1485 BugTaskStatusSearchDisplay.TRIAGED: BugTaskStatus.TRIAGED,
1486 BugTaskStatusSearchDisplay.WONTFIX: BugTaskStatus.WONTFIX,
1487 }
1488- observed = dict(
1489- (status, normalize_bugtask_status(status))
1490- for status in BugTaskStatusSearchDisplay.items)
1491+ observed = {
1492+ status: normalize_bugtask_status(status)
1493+ for status in BugTaskStatusSearchDisplay.items}
1494 self.assertEqual(expected, observed)
1495diff --git a/lib/lp/bugs/mail/bugnotificationbuilder.py b/lib/lp/bugs/mail/bugnotificationbuilder.py
1496index 9c95348..7b381a1 100644
1497--- a/lib/lp/bugs/mail/bugnotificationbuilder.py
1498+++ b/lib/lp/bugs/mail/bugnotificationbuilder.py
1499@@ -117,7 +117,7 @@ class BugNotificationBuilder:
1500 # Add the -Bug-Commenters header, a space-separated list of
1501 # distinct IDs of people who have commented on the bug. The
1502 # list is sorted to aid testing.
1503- commenters = set(message.owner.name for message in bug.messages)
1504+ commenters = {message.owner.name for message in bug.messages}
1505 self.common_headers.append(
1506 ('X-Launchpad-Bug-Commenters', ' '.join(sorted(commenters))))
1507
1508diff --git a/lib/lp/bugs/mail/handler.py b/lib/lp/bugs/mail/handler.py
1509index 7265336..fadb5bc 100644
1510--- a/lib/lp/bugs/mail/handler.py
1511+++ b/lib/lp/bugs/mail/handler.py
1512@@ -360,14 +360,14 @@ class MaloneHandler:
1513 # application/ms-tnef attachment are created by Outlook; they
1514 # seem to store no more than an RTF representation of an email.
1515
1516- irrelevant_content_types = set((
1517+ irrelevant_content_types = {
1518 'application/applefile', # the resource fork of a MacOS file
1519 'application/pgp-signature',
1520 'application/pkcs7-signature',
1521 'application/x-pkcs7-signature',
1522 'text/x-vcard',
1523 'application/ms-tnef',
1524- ))
1525+ }
1526
1527 def processAttachments(self, bug, message, signed_mail):
1528 """Create Bugattachments for "reasonable" mail attachments.
1529diff --git a/lib/lp/bugs/model/bug.py b/lib/lp/bugs/model/bug.py
1530index 6088100..52c413a 100644
1531--- a/lib/lp/bugs/model/bug.py
1532+++ b/lib/lp/bugs/model/bug.py
1533@@ -287,7 +287,7 @@ def get_bug_tags_open_count(context_condition, user, tag_limit=0,
1534 )
1535 tags = {}
1536 if include_tags:
1537- tags = dict((tag, 0) for tag in include_tags)
1538+ tags = {tag: 0 for tag in include_tags}
1539 where_conditions = [
1540 BugSummary.status.is_in(UNRESOLVED_BUGTASK_STATUSES),
1541 BugSummary.tag != None,
1542@@ -560,7 +560,7 @@ class Bug(SQLBase, InformationTypeMixin):
1543 # in storm with very large bugs by not joining and instead
1544 # querying a second time. If this starts to show high db
1545 # time, we can left outer join instead.
1546- owner_ids = set(message.ownerID for message in messages)
1547+ owner_ids = {message.ownerID for message in messages}
1548 owner_ids.discard(None)
1549 if not owner_ids:
1550 return
1551@@ -571,7 +571,7 @@ class Bug(SQLBase, InformationTypeMixin):
1552 # message, or joining in the database (though perhaps in
1553 # future we should do that), we do a single separate query
1554 # for the message content.
1555- message_ids = set(message.id for message in messages)
1556+ message_ids = {message.id for message in messages}
1557 chunks = store.find(
1558 MessageChunk, MessageChunk.messageID.is_in(message_ids))
1559 chunks.order_by(MessageChunk.id)
1560@@ -896,7 +896,7 @@ class Bug(SQLBase, InformationTypeMixin):
1561 clear_property_cache(self)
1562 # Ensure the unsubscriber is in the _known_viewer cache for the bug so
1563 # that the permissions are such that the operation can succeed.
1564- get_property_cache(self)._known_viewers = set([unsubscribed_by.id])
1565+ get_property_cache(self)._known_viewers = {unsubscribed_by.id}
1566 if person is None:
1567 person = unsubscribed_by
1568
1569@@ -1431,8 +1431,8 @@ class Bug(SQLBase, InformationTypeMixin):
1570
1571 def getVisibleLinkedMergeProposals(self, user, eager_load=False):
1572 """See `IBug`."""
1573- linked_merge_proposal_ids = set(
1574- bmp.id for bmp in self.linked_merge_proposals)
1575+ linked_merge_proposal_ids = {
1576+ bmp.id for bmp in self.linked_merge_proposals}
1577 if not linked_merge_proposal_ids:
1578 return EmptyResultSet()
1579 else:
1580@@ -1863,7 +1863,7 @@ class Bug(SQLBase, InformationTypeMixin):
1581 """Set the tags from a list of strings."""
1582 # Sets provide an easy way to get the difference between the old and
1583 # new tags.
1584- new_tags = set([tag.lower() for tag in tags])
1585+ new_tags = {tag.lower() for tag in tags}
1586 old_tags = set(self.tags)
1587 # The cache will be stale after we add/remove tags, clear it.
1588 del get_property_cache(self)._cached_tags
1589diff --git a/lib/lp/bugs/model/bugsubscriptionfilter.py b/lib/lp/bugs/model/bugsubscriptionfilter.py
1590index c3568d6..bf01a36 100644
1591--- a/lib/lp/bugs/model/bugsubscriptionfilter.py
1592+++ b/lib/lp/bugs/model/bugsubscriptionfilter.py
1593@@ -186,11 +186,11 @@ class BugSubscriptionFilter(StormBase):
1594 # Deal with other tags.
1595 tags = tags - wildcards
1596 store = IStore(BugSubscriptionFilterTag)
1597- current_tag_filters = dict(
1598- (tag_filter.qualified_tag, tag_filter)
1599+ current_tag_filters = {
1600+ tag_filter.qualified_tag: tag_filter
1601 for tag_filter in store.find(
1602 BugSubscriptionFilterTag,
1603- BugSubscriptionFilterTag.filter == self))
1604+ BugSubscriptionFilterTag.filter == self)}
1605 # Remove unused tags.
1606 for tag in set(current_tag_filters).difference(tags):
1607 tag_filter = current_tag_filters.pop(tag)
1608diff --git a/lib/lp/bugs/model/bugtarget.py b/lib/lp/bugs/model/bugtarget.py
1609index f7272d3..0f7f748 100644
1610--- a/lib/lp/bugs/model/bugtarget.py
1611+++ b/lib/lp/bugs/model/bugtarget.py
1612@@ -150,7 +150,7 @@ class OfficialBugTagTargetMixin:
1613
1614 def _setOfficialTags(self, tags):
1615 """Set the official bug tags from a list of strings."""
1616- new_tags = set([tag.lower() for tag in tags])
1617+ new_tags = {tag.lower() for tag in tags}
1618 old_tags = set(self.official_bug_tags)
1619 added_tags = new_tags.difference(old_tags)
1620 removed_tags = old_tags.difference(new_tags)
1621diff --git a/lib/lp/bugs/model/bugtask.py b/lib/lp/bugs/model/bugtask.py
1622index 14eeec1..dff8df5 100644
1623--- a/lib/lp/bugs/model/bugtask.py
1624+++ b/lib/lp/bugs/model/bugtask.py
1625@@ -1397,8 +1397,8 @@ class BugTaskSet:
1626 Bug,
1627 BugTag,
1628 )
1629- bugtask_ids = set(bugtask.id for bugtask in bugtasks)
1630- bug_ids = set(bugtask.bug_id for bugtask in bugtasks)
1631+ bugtask_ids = {bugtask.id for bugtask in bugtasks}
1632+ bug_ids = {bugtask.bug_id for bugtask in bugtasks}
1633 tags = IStore(BugTag).find(
1634 (BugTag.tag, BugTask.id),
1635 BugTask.bug == Bug.id,
1636@@ -1418,8 +1418,8 @@ class BugTaskSet:
1637 [bugtask.assignee_id for bugtask in bugtasks] +
1638 [bugtask.bug.ownerID for bugtask in bugtasks])
1639 people = getUtility(IPersonSet).getPrecachedPersonsFromIDs(people_ids)
1640- return dict(
1641- (person.id, person) for person in people)
1642+ return {
1643+ person.id: person for person in people}
1644
1645 def getBugTaskBadgeProperties(self, bugtasks):
1646 """See `IBugTaskSet`."""
1647@@ -1427,11 +1427,11 @@ class BugTaskSet:
1648 from lp.bugs.model.bug import Bug
1649 from lp.bugs.model.bugbranch import BugBranch
1650
1651- bug_ids = set(bugtask.bug_id for bugtask in bugtasks)
1652- bug_ids_with_specifications = set(
1653+ bug_ids = {bugtask.bug_id for bugtask in bugtasks}
1654+ bug_ids_with_specifications = {
1655 int(id) for _, id in getUtility(IXRefSet).findFromMany(
1656 [(u'bug', six.text_type(bug_id)) for bug_id in bug_ids],
1657- types=[u'specification']).keys())
1658+ types=[u'specification']).keys()}
1659 bug_ids_with_branches = set(IStore(BugBranch).find(
1660 BugBranch.bug_id, BugBranch.bug_id.is_in(bug_ids)))
1661 # Badging looks up milestones too : eager load into the storm cache.
1662@@ -1445,9 +1445,9 @@ class BugTaskSet:
1663 # Check if the bugs are cached. If not, cache all uncached bugs
1664 # at once to avoid one query per bugtask. We could rely on the
1665 # Storm cache, but this is explicit.
1666- bugs = dict(
1667- (bug.id, bug)
1668- for bug in IStore(Bug).find(Bug, Bug.id.is_in(bug_ids)).cached())
1669+ bugs = {
1670+ bug.id: bug
1671+ for bug in IStore(Bug).find(Bug, Bug.id.is_in(bug_ids)).cached()}
1672 uncached_ids = bug_ids.difference(bug_id for bug_id in bugs)
1673 if len(uncached_ids) > 0:
1674 bugs.update(dict(IStore(Bug).find((Bug.id, Bug),
1675@@ -1474,7 +1474,7 @@ class BugTaskSet:
1676 # Query the database, returning the results in a dictionary:
1677 if len(task_ids) > 0:
1678 tasks = IStore(BugTask).find(BugTask, BugTask.id.is_in(task_ids))
1679- return dict([(task.id, task) for task in tasks])
1680+ return {task.id: task for task in tasks}
1681 else:
1682 return {}
1683
1684@@ -1715,9 +1715,9 @@ class BugTaskSet:
1685 privacy=bug_privacy_filter)
1686 cur = cursor()
1687 cur.execute(query)
1688- return dict(
1689- (get_bugtask_status(status_id), count)
1690- for (status_id, count) in cur.fetchall())
1691+ return {
1692+ get_bugtask_status(status_id): count
1693+ for (status_id, count) in cur.fetchall()}
1694
1695 def findExpirableBugTasks(self, min_days_old, user,
1696 bug=None, target=None, limit=None):
1697@@ -1894,7 +1894,7 @@ class BugTaskSet:
1698 def getBugCountsForPackages(self, user, packages):
1699 """See `IBugTaskSet`."""
1700 distributions = sorted(
1701- set(package.distribution for package in packages),
1702+ {package.distribution for package in packages},
1703 key=attrgetter('name'))
1704 counts = []
1705 for distribution in distributions:
1706@@ -1955,9 +1955,9 @@ class BugTaskSet:
1707
1708 # Only packages with open bugs were included in the query. Let's
1709 # add the rest of the packages as well.
1710- all_packages = set(
1711+ all_packages = {
1712 (distro_package.distribution, distro_package.sourcepackagename)
1713- for distro_package in packages)
1714+ for distro_package in packages}
1715 for distribution, sourcepackagename in all_packages.difference(
1716 packages_with_bugs):
1717 package_counts = dict(
1718diff --git a/lib/lp/bugs/model/bugtasksearch.py b/lib/lp/bugs/model/bugtasksearch.py
1719index 4599d67..fd1ec25 100644
1720--- a/lib/lp/bugs/model/bugtasksearch.py
1721+++ b/lib/lp/bugs/model/bugtasksearch.py
1722@@ -558,9 +558,9 @@ def _build_query(params):
1723
1724 # It's much faster to query for a single archive, so don't
1725 # include partner unless we have to.
1726- archive_ids = set(
1727+ archive_ids = {
1728 distroseries.distribution.getArchiveByComponent(c.name).id
1729- for c in components)
1730+ for c in components}
1731
1732 extra_clauses.append(
1733 BugTaskFlat.sourcepackagename_id.is_in(
1734@@ -806,13 +806,13 @@ def _process_order_by(params):
1735 else:
1736 in_unique_context = False
1737
1738- unambiguous_cols = set([
1739+ unambiguous_cols = {
1740 BugTaskFlat.date_last_updated,
1741 BugTaskFlat.datecreated,
1742 BugTaskFlat.bugtask_id,
1743 Bug.datecreated,
1744 BugTask.date_assigned,
1745- ])
1746+ }
1747 if in_unique_context:
1748 unambiguous_cols.add(BugTaskFlat.bug)
1749
1750@@ -907,7 +907,7 @@ def _build_status_clause(col, status):
1751 values = list(status.query_values)
1752 # Since INCOMPLETE isn't stored as a single value any more, we need to
1753 # expand it before generating the SQL.
1754- old = set([BugTaskStatus.INCOMPLETE, BugTaskStatusSearch.INCOMPLETE])
1755+ old = {BugTaskStatus.INCOMPLETE, BugTaskStatusSearch.INCOMPLETE}
1756 accepted_values = list(set(values) - old)
1757 if len(accepted_values) < len(values):
1758 accepted_values.extend(DB_INCOMPLETE_BUGTASK_STATUSES)
1759@@ -1345,7 +1345,7 @@ def _make_cache_user_can_view_bug(user):
1760 userid = user.id
1761
1762 def cache_user_can_view_bug(bugtask):
1763- get_property_cache(bugtask.bug)._known_viewers = set([userid])
1764+ get_property_cache(bugtask.bug)._known_viewers = {userid}
1765 return bugtask
1766 return cache_user_can_view_bug
1767
1768diff --git a/lib/lp/bugs/model/bugtracker.py b/lib/lp/bugs/model/bugtracker.py
1769index d89145d..57edcb6 100644
1770--- a/lib/lp/bugs/model/bugtracker.py
1771+++ b/lib/lp/bugs/model/bugtracker.py
1772@@ -558,7 +558,7 @@ class BugTracker(SQLBase):
1773
1774 def _get_aliases(self):
1775 """See `IBugTracker.aliases`."""
1776- alias_urls = set(alias.base_url for alias in self._bugtracker_aliases)
1777+ alias_urls = {alias.base_url for alias in self._bugtracker_aliases}
1778 # Although it does no harm if the current baseurl is also an
1779 # alias, we hide it and all its permutations to avoid
1780 # confusion.
1781@@ -572,8 +572,8 @@ class BugTracker(SQLBase):
1782 else:
1783 alias_urls = set(alias_urls)
1784
1785- current_aliases_by_url = dict(
1786- (alias.base_url, alias) for alias in self._bugtracker_aliases)
1787+ current_aliases_by_url = {
1788+ alias.base_url: alias for alias in self._bugtracker_aliases}
1789 # Make a set of the keys, i.e. a set of current URLs.
1790 current_alias_urls = set(current_aliases_by_url)
1791
1792diff --git a/lib/lp/bugs/model/cve.py b/lib/lp/bugs/model/cve.py
1793index 7e37d78..07c26db 100644
1794--- a/lib/lp/bugs/model/cve.py
1795+++ b/lib/lp/bugs/model/cve.py
1796@@ -203,10 +203,10 @@ class CveSet:
1797 Cve, Cve.sequence.is_in([seq for _, seq in bugcve_ids]))
1798
1799 if cve_mapper is None:
1800- cvemap = dict((cve.sequence, cve) for cve in cves)
1801+ cvemap = {cve.sequence: cve for cve in cves}
1802 else:
1803- cvemap = dict((cve.sequence, cve_mapper(cve)) for cve in cves)
1804- bugmap = dict((bug.id, bug) for bug in bugs)
1805+ cvemap = {cve.sequence: cve_mapper(cve) for cve in cves}
1806+ bugmap = {bug.id: bug for bug in bugs}
1807 return [
1808 (bugmap[bug_id], cvemap[cve_sequence])
1809 for bug_id, cve_sequence in bugcve_ids
1810diff --git a/lib/lp/bugs/model/personsubscriptioninfo.py b/lib/lp/bugs/model/personsubscriptioninfo.py
1811index a5a6651..d0da76e 100644
1812--- a/lib/lp/bugs/model/personsubscriptioninfo.py
1813+++ b/lib/lp/bugs/model/personsubscriptioninfo.py
1814@@ -267,9 +267,9 @@ class PersonSubscriptions(object):
1815 'subscription': get_id(info.subscription),
1816 'principal_is_reporter': info.principal_is_reporter,
1817 # We won't add bugtasks yet unless we need them.
1818- 'bug_supervisor_pillars': sorted(set(
1819+ 'bug_supervisor_pillars': sorted({
1820 get_id(d['pillar']) for d
1821- in info.bug_supervisor_tasks)),
1822+ in info.bug_supervisor_tasks}),
1823 }
1824 direct = {}
1825 from_duplicate = {}
1826diff --git a/lib/lp/bugs/model/structuralsubscription.py b/lib/lp/bugs/model/structuralsubscription.py
1827index 8f02d00..c964d95 100644
1828--- a/lib/lp/bugs/model/structuralsubscription.py
1829+++ b/lib/lp/bugs/model/structuralsubscription.py
1830@@ -563,7 +563,7 @@ def _get_structural_subscriptions(find, targets, *conditions):
1831 get_structural_subscription_targets.
1832 :param conditions: additional conditions to filter the results.
1833 """
1834- targets = set(target for bugtask, target in targets)
1835+ targets = {target for bugtask, target in targets}
1836 target_descriptions = [
1837 IStructuralSubscriptionTargetHelper(bugtarget).join
1838 for bugtarget in targets]
1839diff --git a/lib/lp/bugs/model/tests/test_bug.py b/lib/lp/bugs/model/tests/test_bug.py
1840index 3ce02e0..d5bda2a 100644
1841--- a/lib/lp/bugs/model/tests/test_bug.py
1842+++ b/lib/lp/bugs/model/tests/test_bug.py
1843@@ -133,7 +133,7 @@ class TestBug(TestCaseWithFactory):
1844 bug.subscribe(team2, person)
1845 bug.subscribe(person, person)
1846 self.assertEqual(
1847- set([person, team1, team2]),
1848+ {person, team1, team2},
1849 set(bug.getSubscribersForPerson(person)))
1850
1851 def test_get_subscribers_for_person_from_duplicates_too(self):
1852@@ -148,7 +148,7 @@ class TestBug(TestCaseWithFactory):
1853 bug.subscribe(person, person)
1854 bug.markAsDuplicate(real_bug)
1855 self.assertEqual(
1856- set([person, team1, team2]),
1857+ {person, team1, team2},
1858 set(real_bug.getSubscribersForPerson(person)))
1859
1860 def test_getSubscriptionsFromDuplicates(self):
1861@@ -704,9 +704,9 @@ class TestBugPrivateAndSecurityRelatedUpdatesProject(TestCaseWithFactory):
1862
1863 (bug, bug_owner, bugtask_a, bugtask_b, default_bugtask) = (
1864 self.createBugTasksAndSubscribers())
1865- initial_subscribers = set((
1866+ initial_subscribers = {
1867 self.factory.makePerson(name='subscriber'), bugtask_a.owner,
1868- bug_owner))
1869+ bug_owner}
1870 initial_subscribers.update(bug.getDirectSubscribers())
1871
1872 with person_logged_in(bug_owner):
1873@@ -726,8 +726,8 @@ class TestBugPrivateAndSecurityRelatedUpdatesProject(TestCaseWithFactory):
1874
1875 (bug, bug_owner, bugtask_a, bugtask_b, default_bugtask) = (
1876 self.createBugTasksAndSubscribers())
1877- initial_subscribers = set((
1878- self.factory.makePerson(name='subscriber'), bug_owner))
1879+ initial_subscribers = {
1880+ self.factory.makePerson(name='subscriber'), bug_owner}
1881
1882 with person_logged_in(bug_owner):
1883 for subscriber in initial_subscribers:
1884@@ -745,9 +745,9 @@ class TestBugPrivateAndSecurityRelatedUpdatesProject(TestCaseWithFactory):
1885
1886 (bug, bug_owner, bugtask_a, bugtask_b, default_bugtask) = (
1887 self.createBugTasksAndSubscribers(private_security_related=True))
1888- initial_subscribers = set((
1889+ initial_subscribers = {
1890 self.factory.makePerson(), bug_owner, bugtask_a.pillar.driver,
1891- bugtask_a.pillar.bug_supervisor))
1892+ bugtask_a.pillar.bug_supervisor}
1893
1894 with person_logged_in(bug_owner):
1895 for subscriber in initial_subscribers:
1896@@ -756,7 +756,7 @@ class TestBugPrivateAndSecurityRelatedUpdatesProject(TestCaseWithFactory):
1897 bug.transitionToInformationType(
1898 InformationType.PUBLICSECURITY, who)
1899 subscribers = bug.getDirectSubscribers()
1900- expected_subscribers = set((default_bugtask.pillar.driver, bug_owner))
1901+ expected_subscribers = {default_bugtask.pillar.driver, bug_owner}
1902 expected_subscribers.update(initial_subscribers)
1903 self.assertContentEqual(expected_subscribers, subscribers)
1904
1905@@ -766,9 +766,9 @@ class TestBugPrivateAndSecurityRelatedUpdatesProject(TestCaseWithFactory):
1906
1907 (bug, bug_owner, bugtask_a, bugtask_b, default_bugtask) = (
1908 self.createBugTasksAndSubscribers(private_security_related=True))
1909- initial_subscribers = set((
1910+ initial_subscribers = {
1911 self.factory.makePerson(name='subscriber'), bug_owner,
1912- bugtask_a.pillar.driver))
1913+ bugtask_a.pillar.driver}
1914
1915 with person_logged_in(bug_owner):
1916 for subscriber in initial_subscribers:
1917diff --git a/lib/lp/bugs/model/tests/test_bugsubscriptioninfo.py b/lib/lp/bugs/model/tests/test_bugsubscriptioninfo.py
1918index b3d6a24..9a1ad47 100644
1919--- a/lib/lp/bugs/model/tests/test_bugsubscriptioninfo.py
1920+++ b/lib/lp/bugs/model/tests/test_bugsubscriptioninfo.py
1921@@ -61,9 +61,9 @@ class TestSubscriptionRelatedSets(TestCaseWithFactory):
1922 super(TestSubscriptionRelatedSets, self).setUp()
1923 make_person = lambda displayname, name: (
1924 self.factory.makePerson(displayname=displayname, name=name))
1925- subscribers = dict(
1926- (name_pair, make_person(*name_pair))
1927- for name_pair in self.name_pairs)
1928+ subscribers = {
1929+ name_pair: make_person(*name_pair)
1930+ for name_pair in self.name_pairs}
1931 self.subscribers_set = frozenset(six.itervalues(subscribers))
1932 self.subscribers_sorted = tuple(
1933 subscribers[name_pair] for name_pair in self.name_pairs_sorted)
1934diff --git a/lib/lp/bugs/model/tests/test_bugtask.py b/lib/lp/bugs/model/tests/test_bugtask.py
1935index e16ca9e..fdf666b 100644
1936--- a/lib/lp/bugs/model/tests/test_bugtask.py
1937+++ b/lib/lp/bugs/model/tests/test_bugtask.py
1938@@ -759,8 +759,8 @@ class TestBugTaskDelta(TestCaseWithFactory):
1939 # expected_delta is assumed to be None in the delta.
1940 delta = bug_task_after.getDelta(bug_task_before)
1941 expected_delta.setdefault('bugtask', bug_task_after)
1942- names = set(
1943- name for interface in providedBy(delta) for name in interface)
1944+ names = {
1945+ name for interface in providedBy(delta) for name in interface}
1946 for name in names:
1947 self.assertEqual(getattr(delta, name), expected_delta.get(name))
1948
1949@@ -3282,8 +3282,8 @@ class TestTargetNameCache(TestCase):
1950 stderr=subprocess.PIPE, universal_newlines=True)
1951 (out, err) = process.communicate()
1952
1953- self.assertTrue(err.startswith(("INFO Creating lockfile: "
1954- "/var/lock/launchpad-launchpad-targetnamecacheupdater.lock")))
1955+ self.assertTrue(err.startswith("INFO Creating lockfile: "
1956+ "/var/lock/launchpad-launchpad-targetnamecacheupdater.lock"))
1957 self.assertTrue('INFO Updating targetname cache of bugtasks' in err)
1958 self.assertTrue('INFO Calculating targets.' in err)
1959 self.assertTrue('INFO Will check ' in err)
1960diff --git a/lib/lp/bugs/model/tests/test_bugtasksearch.py b/lib/lp/bugs/model/tests/test_bugtasksearch.py
1961index d4c909f..5357a66 100644
1962--- a/lib/lp/bugs/model/tests/test_bugtasksearch.py
1963+++ b/lib/lp/bugs/model/tests/test_bugtasksearch.py
1964@@ -1775,7 +1775,7 @@ class TestBugTaskSetStatusSearchClauses(TestCase):
1965 # in a "NOT".
1966 status = BugTaskStatus.INCOMPLETE
1967 base_query = self.searchClause(status)
1968- expected_negative_query = 'NOT ({0})'.format(base_query)
1969+ expected_negative_query = 'NOT ({})'.format(base_query)
1970 self.assertEqual(
1971 expected_negative_query,
1972 self.searchClause(not_equals(status)))
1973diff --git a/lib/lp/bugs/scripts/bugsummaryrebuild.py b/lib/lp/bugs/scripts/bugsummaryrebuild.py
1974index ab72f5a..58daf6b 100644
1975--- a/lib/lp/bugs/scripts/bugsummaryrebuild.py
1976+++ b/lib/lp/bugs/scripts/bugsummaryrebuild.py
1977@@ -76,9 +76,9 @@ def get_bugtask_targets():
1978 )).config(distinct=True))
1979 # BugSummary counts package tasks in the packageless totals, so
1980 # ensure that there's also a packageless total for each distro(series).
1981- new_targets.update(set(
1982+ new_targets.update({
1983 (p, ps, d, ds, None, None)
1984- for (p, ps, d, ds, spn, ocip) in new_targets))
1985+ for (p, ps, d, ds, spn, ocip) in new_targets})
1986 return new_targets
1987
1988
1989@@ -111,8 +111,8 @@ def format_target(target):
1990 def _get_bugsummary_constraint_bits(target):
1991 raw_key = bug_target_to_key(target)
1992 # Map to ID columns to work around Storm bug #682989.
1993- return dict(
1994- ('%s_id' % k, v.id if v else None) for (k, v) in raw_key.items())
1995+ return {
1996+ '%s_id' % k: v.id if v else None for (k, v) in raw_key.items()}
1997
1998
1999 def get_bugsummary_constraint(target, cls=RawBugSummary):
2000@@ -233,10 +233,10 @@ def apply_bugsummary_changes(target, added, updated, removed):
2001
2002 def rebuild_bugsummary_for_target(target, log):
2003 log.debug("Rebuilding %s" % format_target(target))
2004- existing = dict(
2005- (v[:-1], v[-1]) for v in get_bugsummary_rows(target))
2006- expected = dict(
2007- (v[:-1], v[-1]) for v in calculate_bugsummary_rows(target))
2008+ existing = {
2009+ v[:-1]: v[-1] for v in get_bugsummary_rows(target)}
2010+ expected = {
2011+ v[:-1]: v[-1] for v in calculate_bugsummary_rows(target)}
2012 added, updated, removed = calculate_bugsummary_changes(existing, expected)
2013 if added:
2014 log.debug('Added %r' % added)
2015diff --git a/lib/lp/bugs/scripts/checkwatches/core.py b/lib/lp/bugs/scripts/checkwatches/core.py
2016index c659a77..db59005 100644
2017--- a/lib/lp/bugs/scripts/checkwatches/core.py
2018+++ b/lib/lp/bugs/scripts/checkwatches/core.py
2019@@ -486,9 +486,9 @@ class CheckwatchesMaster(WorkingBase):
2020
2021 with self.transaction:
2022 reload(bug_watches)
2023- old_bug_watches = set(
2024+ old_bug_watches = {
2025 bug_watch for bug_watch in bug_watches
2026- if bug_watch.lastchecked is not None)
2027+ if bug_watch.lastchecked is not None}
2028 if len(old_bug_watches) == 0:
2029 oldest_lastchecked = None
2030 else:
2031@@ -500,10 +500,10 @@ class CheckwatchesMaster(WorkingBase):
2032 ACCEPTABLE_TIME_SKEW + timedelta(minutes=1))
2033 # Collate the remote IDs.
2034 remote_old_ids = sorted(
2035- set(bug_watch.remotebug for bug_watch in old_bug_watches))
2036+ {bug_watch.remotebug for bug_watch in old_bug_watches})
2037 remote_new_ids = sorted(
2038- set(bug_watch.remotebug for bug_watch in bug_watches
2039- if bug_watch not in old_bug_watches))
2040+ {bug_watch.remotebug for bug_watch in bug_watches
2041+ if bug_watch not in old_bug_watches})
2042 # If the remote system is not configured to sync comments,
2043 # don't bother checking for any to push.
2044 if remotesystem.sync_comments:
2045diff --git a/lib/lp/bugs/scripts/tests/test_bugnotification.py b/lib/lp/bugs/scripts/tests/test_bugnotification.py
2046index d56ddf2..d5ec852 100644
2047--- a/lib/lp/bugs/scripts/tests/test_bugnotification.py
2048+++ b/lib/lp/bugs/scripts/tests/test_bugnotification.py
2049@@ -192,9 +192,9 @@ class FakeBugNotificationSetUtility:
2050
2051 def getRecipientFilterData(self, bug, recipient_to_sources,
2052 notifications):
2053- return dict(
2054- (recipient, {'sources': sources, 'filter descriptions': []})
2055- for recipient, sources in recipient_to_sources.items())
2056+ return {
2057+ recipient: {'sources': sources, 'filter descriptions': []}
2058+ for recipient, sources in recipient_to_sources.items()}
2059
2060
2061 class MockBugActivity:
2062diff --git a/lib/lp/bugs/tests/externalbugtracker.py b/lib/lp/bugs/tests/externalbugtracker.py
2063index cdce45f..5caceae 100644
2064--- a/lib/lp/bugs/tests/externalbugtracker.py
2065+++ b/lib/lp/bugs/tests/externalbugtracker.py
2066@@ -115,8 +115,8 @@ def print_bugwatches(bug_watches, convert_remote_status=None):
2067 used to convert the watches' remote statuses to Launchpad
2068 BugTaskStatuses and these will be output instead.
2069 """
2070- watches = dict((int(bug_watch.remotebug), bug_watch)
2071- for bug_watch in bug_watches)
2072+ watches = {int(bug_watch.remotebug): bug_watch
2073+ for bug_watch in bug_watches}
2074
2075 for remote_bug_id in sorted(watches.keys()):
2076 status = watches[remote_bug_id].remotestatus
2077@@ -542,7 +542,7 @@ class TestBugzillaXMLRPCTransport(RequestsTransport):
2078
2079 @property
2080 def auth_cookie(self):
2081- if len(set(cookie.domain for cookie in self.cookie_jar)) > 1:
2082+ if len({cookie.domain for cookie in self.cookie_jar}) > 1:
2083 raise AssertionError(
2084 "There should only be cookies for one domain.")
2085
2086@@ -719,9 +719,9 @@ class TestBugzillaXMLRPCTransport(RequestsTransport):
2087
2088 def _copy_comment(self, comment, fields_to_return=None):
2089 # Copy wanted fields.
2090- return dict(
2091- (key, value) for (key, value) in six.iteritems(comment)
2092- if fields_to_return is None or key in fields_to_return)
2093+ return {
2094+ key: value for (key, value) in six.iteritems(comment)
2095+ if fields_to_return is None or key in fields_to_return}
2096
2097 def comments(self, arguments):
2098 """Return comments for a given set of bugs."""
2099@@ -1389,7 +1389,7 @@ class TestTracXMLRPCTransport(RequestsTransport):
2100 # this method. See bugs 203564, 158703 and 158705.
2101
2102 # We sort the list of bugs for the sake of testing.
2103- bug_ids = sorted([bug_id for bug_id in self.remote_bugs.keys()])
2104+ bug_ids = sorted(bug_id for bug_id in self.remote_bugs.keys())
2105 bugs_to_return = []
2106 missing_bugs = []
2107
2108@@ -1476,8 +1476,8 @@ class TestTracXMLRPCTransport(RequestsTransport):
2109
2110 # For each of the missing ones, return a dict with a type of
2111 # 'missing'.
2112- comment_ids_to_return = sorted([
2113- comment['id'] for comment in comments_to_return])
2114+ comment_ids_to_return = sorted(
2115+ comment['id'] for comment in comments_to_return)
2116 missing_comments = [
2117 {'id': comment_id, 'type': 'missing'}
2118 for comment_id in comments
2119diff --git a/lib/lp/bugs/tests/test_bug_messages_webservice.py b/lib/lp/bugs/tests/test_bug_messages_webservice.py
2120index 44393d5..96c7f2e 100644
2121--- a/lib/lp/bugs/tests/test_bug_messages_webservice.py
2122+++ b/lib/lp/bugs/tests/test_bug_messages_webservice.py
2123@@ -91,16 +91,16 @@ class TestBugMessage(TestCaseWithFactory):
2124 # are the same set.
2125 with admin_logged_in():
2126 bug = self.factory.makeBug()
2127- created_attachment_ids = set(
2128- self.factory.makeBugAttachment(bug).id for i in range(3))
2129+ created_attachment_ids = {
2130+ self.factory.makeBugAttachment(bug).id for i in range(3)}
2131 bug_url = api_url(bug)
2132 self.assertThat(created_attachment_ids, HasLength(3))
2133
2134 webservice = webservice_for_person(None)
2135 bug_attachments = webservice.get(
2136 bug_url + '/attachments').jsonBody()['entries']
2137- bug_attachment_ids = set(
2138- int(att['self_link'].rsplit('/', 1)[1]) for att in bug_attachments)
2139+ bug_attachment_ids = {
2140+ int(att['self_link'].rsplit('/', 1)[1]) for att in bug_attachments}
2141 self.assertContentEqual(created_attachment_ids, bug_attachment_ids)
2142
2143 messages = webservice.get(bug_url + '/messages').jsonBody()['entries']
2144@@ -110,9 +110,9 @@ class TestBugMessage(TestCaseWithFactory):
2145 attachments = webservice.get(attachments_url).jsonBody()['entries']
2146 self.assertThat(attachments, HasLength(1))
2147 message_attachments.append(attachments[0])
2148- message_attachment_ids = set(
2149+ message_attachment_ids = {
2150 int(att['self_link'].rsplit('/', 1)[1])
2151- for att in message_attachments)
2152+ for att in message_attachments}
2153 self.assertContentEqual(bug_attachment_ids, message_attachment_ids)
2154
2155
2156diff --git a/lib/lp/bugs/tests/test_bugchanges.py b/lib/lp/bugs/tests/test_bugchanges.py
2157index 5786c0e..71daeab 100644
2158--- a/lib/lp/bugs/tests/test_bugchanges.py
2159+++ b/lib/lp/bugs/tests/test_bugchanges.py
2160@@ -83,9 +83,9 @@ class TestBugChanges(TestCaseWithFactory):
2161 if bug is None:
2162 bug = self.bug
2163 old_activities = set(bug.activity)
2164- old_notification_ids = set(
2165+ old_notification_ids = {
2166 notification.id for notification in IStore(BugNotification).find(
2167- BugNotification, bug=bug))
2168+ BugNotification, bug=bug)}
2169
2170 if append:
2171 self.old_activities.update(old_activities)
2172@@ -173,23 +173,23 @@ class TestBugChanges(TestCaseWithFactory):
2173 level=BugNotificationLevel.METADATA)
2174 self.assertEqual(
2175 set(expected_recipients),
2176- set(recipient.person
2177- for recipient in added_notification.recipients))
2178+ {recipient.person
2179+ for recipient in added_notification.recipients})
2180 if expected_recipient_reasons:
2181 self.assertEqual(
2182 set(expected_recipient_reasons),
2183- set(recipient.reason_header
2184- for recipient in added_notification.recipients))
2185+ {recipient.reason_header
2186+ for recipient in added_notification.recipients})
2187
2188 def assertRecipients(self, expected_recipients):
2189 notifications = self.getNewNotifications()
2190 notifications, omitted, messages = construct_email_notifications(
2191 notifications)
2192- recipients = set(message['to'] for message in messages)
2193+ recipients = {message['to'] for message in messages}
2194
2195 self.assertEqual(
2196- set(recipient.preferredemail.email
2197- for recipient in expected_recipients),
2198+ {recipient.preferredemail.email
2199+ for recipient in expected_recipients},
2200 recipients)
2201
2202 def test_subscribe(self):
2203diff --git a/lib/lp/bugs/tests/test_bugnotification.py b/lib/lp/bugs/tests/test_bugnotification.py
2204index c1d673e..e58328d 100644
2205--- a/lib/lp/bugs/tests/test_bugnotification.py
2206+++ b/lib/lp/bugs/tests/test_bugnotification.py
2207@@ -373,9 +373,9 @@ class TestNotificationsForDuplicates(TestCaseWithFactory):
2208 self.dupe_bug.owner, subject='subject', content='content')
2209 latest_notification = IStore(BugNotification).find(
2210 BugNotification).order_by(BugNotification.id).last()
2211- recipients = set(
2212+ recipients = {
2213 recipient.person
2214- for recipient in latest_notification.recipients)
2215+ for recipient in latest_notification.recipients}
2216 self.assertEqual(self.dupe_subscribers, recipients)
2217
2218 def test_duplicate_edit_notifications(self):
2219@@ -385,9 +385,9 @@ class TestNotificationsForDuplicates(TestCaseWithFactory):
2220 self.dupe_bug.description = 'A changed description'
2221 latest_notification = IStore(BugNotification).find(
2222 BugNotification).order_by(BugNotification.id).last()
2223- recipients = set(
2224+ recipients = {
2225 recipient.person
2226- for recipient in latest_notification.recipients)
2227+ for recipient in latest_notification.recipients}
2228 self.assertEqual(self.dupe_subscribers, recipients)
2229
2230 def test_branch_linked_notification(self):
2231@@ -400,9 +400,9 @@ class TestNotificationsForDuplicates(TestCaseWithFactory):
2232 self.dupe_bug.linkBranch(branch, self.dupe_bug.owner)
2233 latest_notification = IStore(BugNotification).find(
2234 BugNotification).order_by(BugNotification.id).last()
2235- recipients = set(
2236+ recipients = {
2237 recipient.person
2238- for recipient in latest_notification.recipients)
2239+ for recipient in latest_notification.recipients}
2240 self.assertEqual(self.dupe_subscribers, recipients)
2241
2242
2243diff --git a/lib/lp/bugs/tests/test_bugwatch.py b/lib/lp/bugs/tests/test_bugwatch.py
2244index 7b1ac7c..6dca2df 100644
2245--- a/lib/lp/bugs/tests/test_bugwatch.py
2246+++ b/lib/lp/bugs/tests/test_bugwatch.py
2247@@ -584,7 +584,7 @@ class TestBugWatchSetBulkOperations(TestCaseWithFactory):
2248 def test_bulkAddActivity_with_iterator(self):
2249 # Any iterator can be passed in.
2250 getUtility(IBugWatchSet).bulkAddActivity(
2251- (bug_watch for bug_watch in self.bug_watches))
2252+ bug_watch for bug_watch in self.bug_watches)
2253 self._checkActivityForBugWatches(
2254 BugWatchActivityStatus.SYNC_SUCCEEDED, None, None)
2255
2256diff --git a/lib/lp/bugs/tests/test_structuralsubscription.py b/lib/lp/bugs/tests/test_structuralsubscription.py
2257index 334cfcf..d67bba2 100644
2258--- a/lib/lp/bugs/tests/test_structuralsubscription.py
2259+++ b/lib/lp/bugs/tests/test_structuralsubscription.py
2260@@ -491,8 +491,8 @@ class TestGetStructuralSubscriptionTargets(TestCaseWithFactory):
2261 bug = self.factory.makeBug(target=product, milestone=milestone)
2262 bugtask = bug.bugtasks[0]
2263 result = get_structural_subscription_targets(bug.bugtasks)
2264- self.assertEqual(set(result), set(
2265- ((bugtask, product), (bugtask, milestone))))
2266+ self.assertEqual(set(result), {
2267+ (bugtask, product), (bugtask, milestone)})
2268
2269 def test_sourcepackage_target(self):
2270 actor = self.factory.makePerson()
2271@@ -506,9 +506,9 @@ class TestGetStructuralSubscriptionTargets(TestCaseWithFactory):
2272 product_bugtask = bug.bugtasks[0]
2273 sourcepackage_bugtask = bug.bugtasks[1]
2274 result = get_structural_subscription_targets(bug.bugtasks)
2275- self.assertEqual(set(result), set(
2276- ((product_bugtask, product),
2277- (sourcepackage_bugtask, distroseries))))
2278+ self.assertEqual(set(result), {
2279+ (product_bugtask, product),
2280+ (sourcepackage_bugtask, distroseries)})
2281
2282 def test_distribution_source_package_target(self):
2283 actor = self.factory.makePerson()
2284@@ -522,10 +522,10 @@ class TestGetStructuralSubscriptionTargets(TestCaseWithFactory):
2285 product_bugtask = bug.bugtasks[0]
2286 dist_sourcepackage_bugtask = bug.bugtasks[1]
2287 result = get_structural_subscription_targets(bug.bugtasks)
2288- self.assertEqual(set(result), set(
2289- ((product_bugtask, product),
2290+ self.assertEqual(set(result), {
2291+ (product_bugtask, product),
2292 (dist_sourcepackage_bugtask, dist_sourcepackage),
2293- (dist_sourcepackage_bugtask, distribution))))
2294+ (dist_sourcepackage_bugtask, distribution)})
2295
2296 def test_product_with_project_group(self):
2297 # get_structural_subscription_targets() will yield both a
2298@@ -541,7 +541,7 @@ class TestGetStructuralSubscriptionTargets(TestCaseWithFactory):
2299 bug = self.factory.makeBug(target=product)
2300 result = get_structural_subscription_targets(bug.bugtasks)
2301 self.assertEqual(
2302- set([(bug.bugtasks[0], product), (bug.bugtasks[0], projectgroup)]),
2303+ {(bug.bugtasks[0], product), (bug.bugtasks[0], projectgroup)},
2304 set(result))
2305
2306
2307@@ -580,7 +580,7 @@ class TestGetStructuralSubscriptionsForBug(TestCaseWithFactory):
2308 sub2 = self.milestone.addBugSubscription(
2309 self.subscriber, self.subscriber)
2310 subscriptions = self.getSubscriptions(self.subscriber)
2311- self.assertEqual(set([sub1, sub2]), set(subscriptions))
2312+ self.assertEqual({sub1, sub2}, set(subscriptions))
2313
2314 def test_two_bugtasks_one_subscription(self):
2315 sub = self.product.addBugSubscription(
2316@@ -598,7 +598,7 @@ class TestGetStructuralSubscriptionsForBug(TestCaseWithFactory):
2317 sub2 = product2.addBugSubscription(
2318 self.subscriber, self.subscriber)
2319 subscriptions = self.getSubscriptions(self.subscriber)
2320- self.assertEqual(set([sub1, sub2]), set(subscriptions))
2321+ self.assertEqual({sub1, sub2}, set(subscriptions))
2322
2323 def test_ignore_other_subscriptions(self):
2324 sub1 = self.product.addBugSubscription(
2325@@ -626,7 +626,7 @@ class TestGetStructuralSubscriptionsForBug(TestCaseWithFactory):
2326 team_sub = self.product.addBugSubscription(
2327 self.team, self.team.teamowner)
2328 subscriptions = self.getSubscriptions(self.subscriber)
2329- self.assertEqual(set([self_sub, team_sub]), set(subscriptions))
2330+ self.assertEqual({self_sub, team_sub}, set(subscriptions))
2331
2332 def test_subscriptions_from_parent(self):
2333 # get_structural_subscriptions_for_bug() will return any
2334@@ -642,7 +642,7 @@ class TestGetStructuralSubscriptionsForBug(TestCaseWithFactory):
2335 bug = self.factory.makeBug(target=product)
2336 subscriptions = get_structural_subscriptions_for_bug(
2337 bug, subscriber)
2338- self.assertEqual(set([self_sub]), set(subscriptions))
2339+ self.assertEqual({self_sub}, set(subscriptions))
2340
2341
2342 class TestGetStructuralSubscriptions(TestCaseWithFactory):
2343@@ -783,7 +783,7 @@ class TestGetStructuralSubscribers(TestCaseWithFactory):
2344
2345 subscribers = get_structural_subscribers(bug, None, None, None)
2346 self.assertIsInstance(subscribers, RESULT_SETS)
2347- self.assertEqual(set([subscriber1, subscriber2]), set(subscribers))
2348+ self.assertEqual({subscriber1, subscriber2}, set(subscribers))
2349
2350 def test_getStructuralSubscribers_recipients(self):
2351 # If provided, get_structural_subscribers() calls the appropriate
2352diff --git a/lib/lp/bugs/tests/test_structuralsubscriptiontarget.py b/lib/lp/bugs/tests/test_structuralsubscriptiontarget.py
2353index 9d75005..696d7c5 100644
2354--- a/lib/lp/bugs/tests/test_structuralsubscriptiontarget.py
2355+++ b/lib/lp/bugs/tests/test_structuralsubscriptiontarget.py
2356@@ -473,7 +473,7 @@ class TestGetAllStructuralSubscriptionsForTarget(TestCaseWithFactory):
2357 team_sub = self.product.addBugSubscription(
2358 self.team, self.team.teamowner)
2359 subscriptions = self.getSubscriptions()
2360- self.assertEqual(set([self_sub, team_sub]), set(subscriptions))
2361+ self.assertEqual({self_sub, team_sub}, set(subscriptions))
2362
2363 def test_subscribed_to_project_group(self):
2364 # If a user is subscribed to a project group, calls to
2365@@ -486,7 +486,7 @@ class TestGetAllStructuralSubscriptionsForTarget(TestCaseWithFactory):
2366 self.subscriber, self.subscriber)
2367 subscriptions = get_structural_subscriptions_for_target(
2368 product, self.subscriber)
2369- self.assertEqual(set([projectgroup_sub]), set(subscriptions))
2370+ self.assertEqual({projectgroup_sub}, set(subscriptions))
2371
2372
2373 def distributionSourcePackageSetUp(test):
2374diff --git a/lib/lp/bugs/vocabularies.py b/lib/lp/bugs/vocabularies.py
2375index 8801a71..b4e5f2d 100644
2376--- a/lib/lp/bugs/vocabularies.py
2377+++ b/lib/lp/bugs/vocabularies.py
2378@@ -352,8 +352,8 @@ class BugTaskMilestoneVocabulary:
2379 self.default_bugtask = default_bugtask
2380 self._milestones = None
2381 if milestones is not None:
2382- self._milestones = dict(
2383- (str(milestone.id), milestone) for milestone in milestones)
2384+ self._milestones = {
2385+ str(milestone.id): milestone for milestone in milestones}
2386
2387 def _load_milestones(self, bugtask):
2388 # If the milestones have not already been cached, load them for the
2389@@ -362,8 +362,8 @@ class BugTaskMilestoneVocabulary:
2390 bugtask_set = getUtility(IBugTaskSet)
2391 milestones = list(
2392 bugtask_set.getBugTaskTargetMilestones([bugtask]))
2393- self._milestones = dict(
2394- (str(milestone.id), milestone) for milestone in milestones)
2395+ self._milestones = {
2396+ str(milestone.id): milestone for milestone in milestones}
2397 return self._milestones
2398
2399 @property
2400diff --git a/lib/lp/buildmaster/manager.py b/lib/lp/buildmaster/manager.py
2401index f893d85..9cec957 100644
2402--- a/lib/lp/buildmaster/manager.py
2403+++ b/lib/lp/buildmaster/manager.py
2404@@ -140,9 +140,9 @@ class PrefetchedBuildCandidates:
2405 # each builder group, and then re-sort the combined list in exactly
2406 # the same way.
2407 grouped_candidates = sorted(
2408- [(builder_group_key, self.candidates[builder_group_key][0])
2409+ ((builder_group_key, self.candidates[builder_group_key][0])
2410 for builder_group_key in builder_group_keys
2411- if self.candidates[builder_group_key]],
2412+ if self.candidates[builder_group_key]),
2413 key=lambda key_candidate: self.sort_keys[key_candidate[1]])
2414 if grouped_candidates:
2415 builder_group_key, candidate_id = grouped_candidates[0]
2416@@ -264,9 +264,9 @@ class PrefetchedBuilderFactory(BaseBuilderFactory):
2417 ).find((Builder, BuildQueue)))
2418 getUtility(IBuilderSet).preloadProcessors(
2419 [b for b, _ in builders_and_current_bqs])
2420- self.vitals_map = dict(
2421- (b.name, extract_vitals_from_db(b, bq))
2422- for b, bq in builders_and_current_bqs)
2423+ self.vitals_map = {
2424+ b.name: extract_vitals_from_db(b, bq)
2425+ for b, bq in builders_and_current_bqs}
2426 self.candidates = PrefetchedBuildCandidates(
2427 list(self.vitals_map.values()))
2428 transaction.abort()
2429@@ -736,8 +736,8 @@ class BuilddManager(service.Service):
2430
2431 def checkForNewBuilders(self):
2432 """Add and return any new builders."""
2433- new_builders = set(
2434- vitals.name for vitals in self.builder_factory.iterVitals())
2435+ new_builders = {
2436+ vitals.name for vitals in self.builder_factory.iterVitals()}
2437 old_builders = set(self.current_builders)
2438 extra_builders = new_builders.difference(old_builders)
2439 self.current_builders.extend(extra_builders)
2440diff --git a/lib/lp/buildmaster/model/buildqueue.py b/lib/lp/buildmaster/model/buildqueue.py
2441index ac1ece2..6556b64 100644
2442--- a/lib/lp/buildmaster/model/buildqueue.py
2443+++ b/lib/lp/buildmaster/model/buildqueue.py
2444@@ -141,7 +141,7 @@ class BuildQueue(StormBase):
2445 from lp.buildmaster.model.buildfarmjob import BuildFarmJob
2446 queues = [removeSecurityProxy(bq) for bq in queues]
2447 load_related(BuildFarmJob, queues, ['_build_farm_job_id'])
2448- bfj_to_bq = dict((bq._build_farm_job, bq) for bq in queues)
2449+ bfj_to_bq = {bq._build_farm_job: bq for bq in queues}
2450 key = attrgetter('_build_farm_job.job_type')
2451 for job_type, group in groupby(sorted(queues, key=key), key=key):
2452 source = getUtility(ISpecificBuildFarmJobSource, job_type.name)
2453@@ -267,8 +267,8 @@ class BuildQueueSet(object):
2454 def preloadForBuilders(self, builders):
2455 # Populate builders' currentjob cachedproperty.
2456 queues = load_referencing(BuildQueue, builders, ['builder_id'])
2457- queue_builders = dict(
2458- (queue.builder_id, queue) for queue in queues)
2459+ queue_builders = {
2460+ queue.builder_id: queue for queue in queues}
2461 for builder in builders:
2462 cache = get_property_cache(builder)
2463 cache.currentjob = queue_builders.get(builder.id, None)
2464@@ -282,9 +282,9 @@ class BuildQueueSet(object):
2465 BuildQueue._build_farm_job_id.is_in(
2466 [removeSecurityProxy(b).build_farm_job_id for b in builds])))
2467 load_related(Builder, bqs, ['builder_id'])
2468- prefetched_data = dict(
2469- (removeSecurityProxy(buildqueue)._build_farm_job_id, buildqueue)
2470- for buildqueue in bqs)
2471+ prefetched_data = {
2472+ removeSecurityProxy(buildqueue)._build_farm_job_id: buildqueue
2473+ for buildqueue in bqs}
2474 for build in builds:
2475 bq = prefetched_data.get(
2476 removeSecurityProxy(build).build_farm_job_id)
2477diff --git a/lib/lp/buildmaster/tests/test_manager.py b/lib/lp/buildmaster/tests/test_manager.py
2478index fd84f13..cd02bce 100644
2479--- a/lib/lp/buildmaster/tests/test_manager.py
2480+++ b/lib/lp/buildmaster/tests/test_manager.py
2481@@ -1214,10 +1214,10 @@ class TestBuilddManager(TestCase):
2482 self._stub_out_scheduleNextScanCycle()
2483
2484 manager = BuilddManager()
2485- builder_names = set(
2486- builder.name for builder in getUtility(IBuilderSet))
2487+ builder_names = {
2488+ builder.name for builder in getUtility(IBuilderSet)}
2489 scanners = manager.addScanForBuilders(builder_names)
2490- scanner_names = set(scanner.builder_name for scanner in scanners)
2491+ scanner_names = {scanner.builder_name for scanner in scanners}
2492 self.assertEqual(builder_names, scanner_names)
2493
2494 def test_startService_adds_scanBuilders_loop(self):
2495diff --git a/lib/lp/buildmaster/tests/test_webservice.py b/lib/lp/buildmaster/tests/test_webservice.py
2496index 34aeb90..d39292d 100644
2497--- a/lib/lp/buildmaster/tests/test_webservice.py
2498+++ b/lib/lp/buildmaster/tests/test_webservice.py
2499@@ -66,8 +66,8 @@ class TestBuildersCollection(TestCaseWithFactory):
2500
2501 builders = self.webservice.get(
2502 '/builders', api_version='devel').jsonBody()
2503- current_builds = dict(
2504- (b['name'], b['current_build_link']) for b in builders['entries'])
2505+ current_builds = {
2506+ b['name']: b['current_build_link'] for b in builders['entries']}
2507 self.assertEqual(
2508 'tag:launchpad.net:2008:redacted', current_builds['restricted'])
2509 self.assertEqual(
2510diff --git a/lib/lp/charms/model/charmrecipe.py b/lib/lp/charms/model/charmrecipe.py
2511index 7629c1b..2ee38d4 100644
2512--- a/lib/lp/charms/model/charmrecipe.py
2513+++ b/lib/lp/charms/model/charmrecipe.py
2514@@ -487,7 +487,7 @@ class CharmRecipe(StormBase, WebhookTargetMixin):
2515 for charm_base in store.find(
2516 CharmBase,
2517 CharmBase.distro_series_id.is_in(
2518- set(das.distroseriesID for das in all_buildable_dases)))}
2519+ {das.distroseriesID for das in all_buildable_dases}))}
2520 return [
2521 das for das in all_buildable_dases
2522 if self._isBuildableArchitectureAllowed(
2523diff --git a/lib/lp/code/browser/branch.py b/lib/lp/code/browser/branch.py
2524index 87b43b2..f6e5d03 100644
2525--- a/lib/lp/code/browser/branch.py
2526+++ b/lib/lp/code/browser/branch.py
2527@@ -676,7 +676,7 @@ class BranchEditFormView(LaunchpadEditFormView):
2528 # If we're stacked on a private branch, only show that
2529 # information type.
2530 if self.context.stacked_on and self.context.stacked_on.private:
2531- shown_types = set([self.context.stacked_on.information_type])
2532+ shown_types = {self.context.stacked_on.information_type}
2533 else:
2534 shown_types = (
2535 InformationType.PUBLIC,
2536diff --git a/lib/lp/code/browser/branchlisting.py b/lib/lp/code/browser/branchlisting.py
2537index 64355b2..d3ecb66 100644
2538--- a/lib/lp/code/browser/branchlisting.py
2539+++ b/lib/lp/code/browser/branchlisting.py
2540@@ -354,7 +354,7 @@ class BranchListingItemsMixin:
2541 spec_branches = getUtility(
2542 ISpecificationBranchSet).getSpecificationBranchesForBranches(
2543 self.visible_branches_for_view, self.view_user)
2544- return set(spec_branch.branch.id for spec_branch in spec_branches)
2545+ return {spec_branch.branch.id for spec_branch in spec_branches}
2546
2547 @cachedproperty
2548 def branch_ids_with_merge_proposals(self):
2549@@ -366,7 +366,7 @@ class BranchListingItemsMixin:
2550 branches = self.visible_branches_for_view
2551 collection = self.getBranchCollection()
2552 proposals = collection.getMergeProposals(for_branches=branches)
2553- return set(proposal.source_branch.id for proposal in proposals)
2554+ return {proposal.source_branch.id for proposal in proposals}
2555
2556 @cachedproperty
2557 def tip_revisions(self):
2558@@ -378,8 +378,8 @@ class BranchListingItemsMixin:
2559 revisions = []
2560
2561 # Key the revisions by revision id.
2562- revision_map = dict(
2563- (revision.revision_id, revision) for revision in revisions)
2564+ revision_map = {
2565+ revision.revision_id: revision for revision in revisions}
2566
2567 # Cache display information for authors of branches' respective
2568 # last revisions.
2569@@ -388,9 +388,9 @@ class BranchListingItemsMixin:
2570 need_icon=True)
2571
2572 # Return a dict keyed on branch id.
2573- return dict(
2574- (branch.id, revision_map.get(branch.last_scanned_id))
2575- for branch in self.visible_branches_for_view)
2576+ return {
2577+ branch.id: revision_map.get(branch.last_scanned_id)
2578+ for branch in self.visible_branches_for_view}
2579
2580 def _createItem(self, branch):
2581 last_commit = self.tip_revisions[branch.id]
2582@@ -1321,8 +1321,8 @@ class GroupedDistributionSourcePackageBranchesView(LaunchpadView,
2583 # Sort the branches by the last modified date, and ignore any that are
2584 # official.
2585 ordered_branches = sorted(
2586- [branch for branch in branches
2587- if branch not in official_branches],
2588+ (branch for branch in branches
2589+ if branch not in official_branches),
2590 key=attrgetter('date_last_modified'), reverse=True)
2591 num_branches = len(ordered_branches)
2592 num_official = len(official_branches)
2593diff --git a/lib/lp/code/browser/branchmergeproposal.py b/lib/lp/code/browser/branchmergeproposal.py
2594index 96b22d8..b7c157a 100644
2595--- a/lib/lp/code/browser/branchmergeproposal.py
2596+++ b/lib/lp/code/browser/branchmergeproposal.py
2597@@ -157,7 +157,7 @@ def latest_proposals_for_each_branch(proposals):
2598 targets[target] = (proposal, date_created)
2599
2600 return sorted(
2601- [proposal for proposal, date_created in six.itervalues(targets)],
2602+ (proposal for proposal, date_created in six.itervalues(targets)),
2603 key=operator.attrgetter('date_created'), reverse=True)
2604
2605
2606diff --git a/lib/lp/code/browser/tests/test_branchlisting.py b/lib/lp/code/browser/tests/test_branchlisting.py
2607index 1c4ad36..3f33640 100644
2608--- a/lib/lp/code/browser/tests/test_branchlisting.py
2609+++ b/lib/lp/code/browser/tests/test_branchlisting.py
2610@@ -129,7 +129,7 @@ class TestPersonOwnedBranchesView(TestCaseWithFactory,
2611 def test_branch_ids_with_bug_links(self):
2612 # _branches_for_current_batch should return a list of all branches in
2613 # the current batch.
2614- branch_ids = set([self.branches[0].id])
2615+ branch_ids = {self.branches[0].id}
2616
2617 view = create_initialized_view(
2618 self.barney, name="+branches", rootsite='code')
2619@@ -140,7 +140,7 @@ class TestPersonOwnedBranchesView(TestCaseWithFactory,
2620 def test_branch_ids_with_spec_links(self):
2621 # _branches_for_current_batch should return a list of all branches in
2622 # the current batch.
2623- branch_ids = set([self.branches[1].id])
2624+ branch_ids = {self.branches[1].id}
2625
2626 view = create_initialized_view(
2627 self.barney, name="+branches", rootsite='code')
2628@@ -151,7 +151,7 @@ class TestPersonOwnedBranchesView(TestCaseWithFactory,
2629 def test_branch_ids_with_merge_propoasls(self):
2630 # _branches_for_current_batch should return a list of all branches in
2631 # the current batch.
2632- branch_ids = set([])
2633+ branch_ids = set()
2634 view = create_initialized_view(
2635 self.barney, name="+branches", rootsite='code')
2636 self.assertEqual(
2637@@ -680,8 +680,8 @@ class TestProjectGroupBranches(TestCaseWithFactory,
2638 self.projectgroup, name='+branches', rootsite='code')
2639 displayname = self.projectgroup.displayname
2640 expected_text = normalize_whitespace(
2641- ("Launchpad does not know where any of %s's "
2642- "projects host their code." % displayname))
2643+ "Launchpad does not know where any of %s's "
2644+ "projects host their code." % displayname)
2645 no_branch_div = find_tag_by_id(view(), "no-branchtable")
2646 text = normalize_whitespace(extract_text(no_branch_div))
2647 self.assertEqual(expected_text, text)
2648diff --git a/lib/lp/code/browser/tests/test_branchmergeproposal.py b/lib/lp/code/browser/tests/test_branchmergeproposal.py
2649index 18bd572..519ec9a 100644
2650--- a/lib/lp/code/browser/tests/test_branchmergeproposal.py
2651+++ b/lib/lp/code/browser/tests/test_branchmergeproposal.py
2652@@ -2044,16 +2044,16 @@ class TestBranchMergeProposalChangeStatusView(TestCaseWithFactory):
2653 # generated vocabulary.
2654 login_person(user)
2655 vocabulary = self._createView()._createStatusVocabulary()
2656- vocab_tokens = sorted([term.token for term in vocabulary])
2657+ vocab_tokens = sorted(term.token for term in vocabulary)
2658 self.assertEqual(
2659 sorted(tokens), vocab_tokens)
2660
2661 def assertAllStatusesAvailable(self, user, except_for=None):
2662 # All options should be available to the user, except for SUPERSEDED,
2663 # which is only provided through resubmit.
2664- desired_statuses = set([
2665+ desired_statuses = {
2666 'WORK_IN_PROGRESS', 'NEEDS_REVIEW', 'MERGED', 'CODE_APPROVED',
2667- 'REJECTED'])
2668+ 'REJECTED'}
2669 if except_for is not None:
2670 desired_statuses -= set(except_for)
2671 self.assertStatusVocabTokens(desired_statuses, user)
2672diff --git a/lib/lp/code/browser/tests/test_gitrepository.py b/lib/lp/code/browser/tests/test_gitrepository.py
2673index 367c2c0..faca389 100644
2674--- a/lib/lp/code/browser/tests/test_gitrepository.py
2675+++ b/lib/lp/code/browser/tests/test_gitrepository.py
2676@@ -1400,7 +1400,7 @@ class TestGitRepositoryPermissionsView(BrowserTestCase):
2677 def test__getRuleGrants(self):
2678 rule = self.factory.makeGitRule()
2679 grantees = sorted(
2680- [self.factory.makePerson() for _ in range(3)],
2681+ (self.factory.makePerson() for _ in range(3)),
2682 key=attrgetter("name"))
2683 for grantee in (grantees[1], grantees[0], grantees[2]):
2684 self.factory.makeGitRuleGrant(rule=rule, grantee=grantee)
2685diff --git a/lib/lp/code/browser/tests/test_sourcepackagerecipe.py b/lib/lp/code/browser/tests/test_sourcepackagerecipe.py
2686index 3f12008..a54af33 100644
2687--- a/lib/lp/code/browser/tests/test_sourcepackagerecipe.py
2688+++ b/lib/lp/code/browser/tests/test_sourcepackagerecipe.py
2689@@ -308,10 +308,10 @@ class TestSourcePackageRecipeAddViewInitialValuesMixin:
2690 with person_logged_in(archive.owner):
2691 view = create_initialized_view(branch, '+new-recipe')
2692 series = set(view.initial_values['distroseries'])
2693- initial_series = set([development, current])
2694+ initial_series = {development, current}
2695 self.assertEqual(initial_series, series.intersection(initial_series))
2696- other_series = set(
2697- [experimental, frozen, supported, obsolete, future])
2698+ other_series = {
2699+ experimental, frozen, supported, obsolete, future}
2700 self.assertEqual(set(), series.intersection(other_series))
2701
2702
2703@@ -440,7 +440,7 @@ class TestSourcePackageRecipeAddViewMixin:
2704 options = browser.getControl(name='field.owner.owner').displayOptions
2705 self.assertEqual(
2706 ['Good Chefs (good-chefs)', 'Master Chef (chef)'],
2707- sorted([str(option) for option in options]))
2708+ sorted(str(option) for option in options))
2709
2710 def test_create_new_recipe_team_owner(self):
2711 # New recipes can be owned by teams that the user is a member of.
2712@@ -1499,8 +1499,8 @@ class TestSourcePackageRecipeViewMixin:
2713 # Our recipe has a Warty distroseries
2714 self.assertEqual(['Warty'], build_distros)
2715 self.assertEqual(
2716- set([2510]),
2717- set(build.buildqueue_record.lastscore for build in builds))
2718+ {2510},
2719+ {build.buildqueue_record.lastscore for build in builds})
2720
2721 def test_request_daily_builds_disabled_archive(self):
2722 # Requesting a daily build from a disabled archive is a user error.
2723diff --git a/lib/lp/code/browser/tests/test_tales.py b/lib/lp/code/browser/tests/test_tales.py
2724index 8452d35..1f928f7 100644
2725--- a/lib/lp/code/browser/tests/test_tales.py
2726+++ b/lib/lp/code/browser/tests/test_tales.py
2727@@ -165,8 +165,8 @@ class TestPreviewDiffFormatter(TestCaseWithFactory):
2728
2729 def test_fmt_stale_non_empty_diff(self):
2730 # If there is no diff, there is no link.
2731- diffstat = dict(
2732- (self.factory.getUniqueString(), (2, 3)) for x in range(23))
2733+ diffstat = {
2734+ self.factory.getUniqueString(): (2, 3) for x in range(23)}
2735 preview = self._createStalePreviewDiff(
2736 500, 89, 340, diffstat=diffstat)
2737 expected_diffstat = '<br/>'.join(
2738@@ -183,8 +183,8 @@ class TestPreviewDiffFormatter(TestCaseWithFactory):
2739
2740 def test_fmt_stale_non_empty_diff_with_conflicts(self):
2741 # If there is no diff, there is no link.
2742- diffstat = dict(
2743- (self.factory.getUniqueString(), (2, 3)) for x in range(23))
2744+ diffstat = {
2745+ self.factory.getUniqueString(): (2, 3) for x in range(23)}
2746 preview = self._createStalePreviewDiff(
2747 500, 89, 340, 'conflicts', diffstat=diffstat)
2748 expected_diffstat = '<br/>'.join(
2749diff --git a/lib/lp/code/interfaces/tests/test_branch.py b/lib/lp/code/interfaces/tests/test_branch.py
2750index b2c987a..a9bb02b 100644
2751--- a/lib/lp/code/interfaces/tests/test_branch.py
2752+++ b/lib/lp/code/interfaces/tests/test_branch.py
2753@@ -37,8 +37,8 @@ class TestFormatSupport(TestCase):
2754 def breezy_is_subset(self, breezy_formats, launchpad_enum):
2755 """Ensure the Breezy format marker list is a subset of Launchpad."""
2756 breezy_format_strings = set(breezy_formats)
2757- launchpad_format_strings = set(
2758- six.ensure_binary(format.title) for format in launchpad_enum.items)
2759+ launchpad_format_strings = {
2760+ six.ensure_binary(format.title) for format in launchpad_enum.items}
2761 self.assertEqual(
2762 set(), breezy_format_strings.difference(launchpad_format_strings))
2763
2764diff --git a/lib/lp/code/mail/tests/test_branchmergeproposal.py b/lib/lp/code/mail/tests/test_branchmergeproposal.py
2765index 06bc638..537918f 100644
2766--- a/lib/lp/code/mail/tests/test_branchmergeproposal.py
2767+++ b/lib/lp/code/mail/tests/test_branchmergeproposal.py
2768@@ -147,7 +147,7 @@ class TestMergeProposalMailing(TestCaseWithFactory):
2769 'Baz Qux <mp+%d@%s>' % (bmp.id, config.launchpad.code_domain),
2770 ctrl.from_addr)
2771 reviewer_id = format_address_for_person(reviewer)
2772- self.assertEqual(set([reviewer_id, bmp.address]), set(ctrl.to_addrs))
2773+ self.assertEqual({reviewer_id, bmp.address}, set(ctrl.to_addrs))
2774 mailer.sendAll()
2775
2776 def test_forCreation_without_commit_message(self):
2777@@ -304,7 +304,7 @@ class TestMergeProposalMailing(TestCaseWithFactory):
2778 bmp.registrant)
2779 reviewer = request.recipient
2780 reviewer_id = format_address_for_person(reviewer)
2781- self.assertEqual(set([reviewer_id, bmp.address]), set(ctrl.to_addrs))
2782+ self.assertEqual({reviewer_id, bmp.address}, set(ctrl.to_addrs))
2783
2784 def test_to_addrs_excludes_team_reviewers(self):
2785 """Addresses for the to header exclude requested team reviewers."""
2786@@ -318,7 +318,7 @@ class TestMergeProposalMailing(TestCaseWithFactory):
2787 subscriber)
2788 reviewer = bmp.target_branch.owner
2789 reviewer_id = format_address_for_person(reviewer)
2790- self.assertEqual(set([reviewer_id, bmp.address]), set(ctrl.to_addrs))
2791+ self.assertEqual({reviewer_id, bmp.address}, set(ctrl.to_addrs))
2792
2793 def test_to_addrs_excludes_people_with_hidden_addresses(self):
2794 """The to header excludes those with hidden addresses."""
2795diff --git a/lib/lp/code/model/branch.py b/lib/lp/code/model/branch.py
2796index c2a0de5..1a9bcc4 100644
2797--- a/lib/lp/code/model/branch.py
2798+++ b/lib/lp/code/model/branch.py
2799@@ -249,9 +249,9 @@ class Branch(SQLBase, WebhookTargetMixin, BzrIdentityMixin):
2800 self.information_type not in PUBLIC_INFORMATION_TYPES):
2801 aasource = getUtility(IAccessArtifactSource)
2802 [abstract_artifact] = aasource.ensure([self])
2803- wanted_links = set(
2804+ wanted_links = {
2805 (abstract_artifact, policy) for policy in
2806- getUtility(IAccessPolicySource).findByTeam([self.owner]))
2807+ getUtility(IAccessPolicySource).findByTeam([self.owner])}
2808 else:
2809 # We haven't yet quite worked out how distribution privacy
2810 # works, so only work for products for now.
2811@@ -941,9 +941,9 @@ class Branch(SQLBase, WebhookTargetMixin, BzrIdentityMixin):
2812 """See `IBranch`."""
2813 alteration_operations, deletion_operations, = (
2814 self._deletionRequirements(eager_load=eager_load))
2815- result = dict(
2816- (operation.affected_object, ('alter', operation.rationale)) for
2817- operation in alteration_operations)
2818+ result = {
2819+ operation.affected_object: ('alter', operation.rationale) for
2820+ operation in alteration_operations}
2821 # Deletion entries should overwrite alteration entries.
2822 result.update(
2823 (operation.affected_object, ('delete', operation.rationale)) for
2824diff --git a/lib/lp/code/model/branchcollection.py b/lib/lp/code/model/branchcollection.py
2825index 524fa69..6ba75ec 100644
2826--- a/lib/lp/code/model/branchcollection.py
2827+++ b/lib/lp/code/model/branchcollection.py
2828@@ -245,8 +245,8 @@ class GenericBranchCollection:
2829 load_related(SourcePackageName, branches, ['sourcepackagenameID'])
2830 load_related(DistroSeries, branches, ['distroseriesID'])
2831 load_related(Product, branches, ['productID'])
2832- caches = dict((branch.id, get_property_cache(branch))
2833- for branch in branches)
2834+ caches = {branch.id: get_property_cache(branch)
2835+ for branch in branches}
2836 branch_ids = caches.keys()
2837 for cache in caches.values():
2838 cache._associatedProductSeries = []
2839@@ -326,7 +326,7 @@ class GenericBranchCollection:
2840 *self._convertListingSortToOrderBy(sort_by))
2841
2842 def do_eager_load(rows):
2843- branch_ids = set(branch.id for branch in rows)
2844+ branch_ids = {branch.id for branch in rows}
2845 if not branch_ids:
2846 return
2847 GenericBranchCollection.preloadDataForBranches(rows)
2848@@ -338,8 +338,8 @@ class GenericBranchCollection:
2849
2850 def cache_permission(branch):
2851 if self._user:
2852- get_property_cache(branch)._known_viewers = set(
2853- [self._user.id])
2854+ get_property_cache(branch)._known_viewers = {
2855+ self._user.id}
2856 return branch
2857
2858 eager_load_hook = (
2859@@ -531,8 +531,8 @@ class GenericBranchCollection:
2860 merge_proposals = self.getMergeProposals(
2861 target_branch=branch, merged_revnos=rev_nos,
2862 statuses=[BranchMergeProposalStatus.MERGED])
2863- merge_proposal_revs = dict(
2864- [(mp.merged_revno, mp) for mp in merge_proposals])
2865+ merge_proposal_revs = {
2866+ mp.merged_revno: mp for mp in merge_proposals}
2867 source_branch_ids = [mp.source_branch.id for mp in merge_proposals]
2868 linked_bugtasks = defaultdict(list)
2869
2870diff --git a/lib/lp/code/model/branchjob.py b/lib/lp/code/model/branchjob.py
2871index 172f83c..5d7c0d8 100644
2872--- a/lib/lp/code/model/branchjob.py
2873+++ b/lib/lp/code/model/branchjob.py
2874@@ -690,7 +690,7 @@ class RevisionsAddedJob(BranchJobDerived):
2875 proposals[source_id] = (proposal, date_created)
2876
2877 return sorted(
2878- [proposal for proposal, date_created in six.itervalues(proposals)],
2879+ (proposal for proposal, date_created in six.itervalues(proposals)),
2880 key=operator.attrgetter('date_created'), reverse=True)
2881
2882 def getRevisionMessage(self, revision_id, revno):
2883diff --git a/lib/lp/code/model/branchlookup.py b/lib/lp/code/model/branchlookup.py
2884index 9648e2a..80bda43 100644
2885--- a/lib/lp/code/model/branchlookup.py
2886+++ b/lib/lp/code/model/branchlookup.py
2887@@ -274,7 +274,7 @@ class BranchLookup:
2888
2889 def getByUrls(self, urls):
2890 """See `IBranchLookup`."""
2891- return dict((url, self.getByUrl(url)) for url in set(urls))
2892+ return {url: self.getByUrl(url) for url in set(urls)}
2893
2894 def getByUniqueName(self, unique_name):
2895 """Find a branch by its unique name.
2896diff --git a/lib/lp/code/model/branchmergeproposal.py b/lib/lp/code/model/branchmergeproposal.py
2897index bb4d009..a0ff7d1 100644
2898--- a/lib/lp/code/model/branchmergeproposal.py
2899+++ b/lib/lp/code/model/branchmergeproposal.py
2900@@ -510,9 +510,9 @@ class BranchMergeProposal(SQLBase, BugLinkTargetMixin):
2901 current_bug_ids = set(current_bug_ids_from_source)
2902 new_bug_ids = self._fetchRelatedBugIDsFromSource()
2903 # Only remove links marked as originating in the source branch.
2904- remove_bugs = load(Bug, set(
2905+ remove_bugs = load(Bug, {
2906 bug_id for bug_id in current_bug_ids - new_bug_ids
2907- if current_bug_ids_from_source[bug_id]))
2908+ if current_bug_ids_from_source[bug_id]})
2909 add_bugs = load(Bug, new_bug_ids - current_bug_ids)
2910 if remove_bugs or add_bugs:
2911 janitor = getUtility(ILaunchpadCelebrities).janitor
2912@@ -852,8 +852,8 @@ class BranchMergeProposal(SQLBase, BugLinkTargetMixin):
2913 # a database query to identify if there are any active proposals
2914 # with the same source and target branches.
2915 self.syncUpdate()
2916- review_requests = list(set(
2917- (vote.reviewer, vote.review_type) for vote in self.votes))
2918+ review_requests = list({
2919+ (vote.reviewer, vote.review_type) for vote in self.votes})
2920 proposal = merge_source.addLandingTarget(
2921 registrant=registrant,
2922 merge_target=merge_target,
2923@@ -1215,9 +1215,9 @@ class BranchMergeProposal(SQLBase, BugLinkTargetMixin):
2924 """See `IBranchMergeProposal`."""
2925 diffs = Store.of(self).find(IncrementalDiff,
2926 IncrementalDiff.branch_merge_proposal_id == self.id)
2927- diff_dict = dict(
2928- ((diff.old_revision, diff.new_revision), diff)
2929- for diff in diffs)
2930+ diff_dict = {
2931+ (diff.old_revision, diff.new_revision): diff
2932+ for diff in diffs}
2933 return [diff_dict.get(revisions) for revisions in revision_list]
2934
2935 def scheduleDiffUpdates(self, return_jobs=True):
2936@@ -1344,8 +1344,8 @@ class BranchMergeProposal(SQLBase, BugLinkTargetMixin):
2937 mp.prerequisite_git_path))
2938 person_ids.add(mp.registrantID)
2939 person_ids.add(mp.merge_reporterID)
2940- git_repository_ids = set(
2941- repository_id for repository_id, _ in git_ref_keys)
2942+ git_repository_ids = {
2943+ repository_id for repository_id, _ in git_ref_keys}
2944
2945 branches = load_related(
2946 Branch, branch_merge_proposals, (
2947@@ -1476,7 +1476,7 @@ class BranchMergeProposalGetter:
2948 return {}
2949 ids = [proposal.id for proposal in proposals]
2950 store = Store.of(proposals[0])
2951- result = dict([(proposal, []) for proposal in proposals])
2952+ result = {proposal: [] for proposal in proposals}
2953 # Make sure that the Person and the review comment are loaded in the
2954 # storm cache as the reviewer is displayed in a title attribute on the
2955 # merge proposal listings page, and the message is needed to get to
2956diff --git a/lib/lp/code/model/codereviewcomment.py b/lib/lp/code/model/codereviewcomment.py
2957index be85747..4b18adc 100644
2958--- a/lib/lp/code/model/codereviewcomment.py
2959+++ b/lib/lp/code/model/codereviewcomment.py
2960@@ -122,7 +122,7 @@ class CodeReviewComment(StormBase):
2961 attachments = [chunk.blob for chunk in self.message.chunks
2962 if chunk.blob is not None]
2963 # Attachments to show.
2964- good_mimetypes = set(['text/plain', 'text/x-diff', 'text/x-patch'])
2965+ good_mimetypes = {'text/plain', 'text/x-diff', 'text/x-patch'}
2966 display_attachments = [
2967 attachment for attachment in attachments
2968 if ((attachment.mimetype in good_mimetypes) or
2969diff --git a/lib/lp/code/model/diff.py b/lib/lp/code/model/diff.py
2970index abcb25c..13f633c 100644
2971--- a/lib/lp/code/model/diff.py
2972+++ b/lib/lp/code/model/diff.py
2973@@ -77,9 +77,9 @@ class Diff(SQLBase):
2974 def _get_diffstat(self):
2975 if self._diffstat is None:
2976 return None
2977- return dict((key, tuple(value))
2978+ return {key: tuple(value)
2979 for key, value
2980- in simplejson.loads(self._diffstat).items())
2981+ in simplejson.loads(self._diffstat).items()}
2982
2983 def _set_diffstat(self, diffstat):
2984 if diffstat is None:
2985@@ -385,13 +385,13 @@ class PreviewDiff(Storm):
2986 source_revision = bmp.source_branch.getBranchRevision(
2987 revision_id=self.source_revision_id)
2988 if source_revision and source_revision.sequence:
2989- source_rev = u'r{0}'.format(source_revision.sequence)
2990+ source_rev = u'r{}'.format(source_revision.sequence)
2991 else:
2992 source_rev = self.source_revision_id
2993 target_revision = bmp.target_branch.getBranchRevision(
2994 revision_id=self.target_revision_id)
2995 if target_revision and target_revision.sequence:
2996- target_rev = u'r{0}'.format(target_revision.sequence)
2997+ target_rev = u'r{}'.format(target_revision.sequence)
2998 else:
2999 target_rev = self.target_revision_id
3000 else:
3001@@ -402,7 +402,7 @@ class PreviewDiff(Storm):
3002 source_rev = self.source_revision_id[:7]
3003 target_rev = self.target_revision_id[:7]
3004
3005- return u'{0} into {1}'.format(source_rev, target_rev)
3006+ return u'{} into {}'.format(source_rev, target_rev)
3007
3008 @property
3009 def has_conflicts(self):
3010diff --git a/lib/lp/code/model/gitcollection.py b/lib/lp/code/model/gitcollection.py
3011index 444a8eb..966ea02 100644
3012--- a/lib/lp/code/model/gitcollection.py
3013+++ b/lib/lp/code/model/gitcollection.py
3014@@ -252,7 +252,7 @@ class GenericGitCollection:
3015 *self._convertListingSortToOrderBy(sort_by)))
3016
3017 def do_eager_load(rows):
3018- repository_ids = set(repository.id for repository in rows)
3019+ repository_ids = {repository.id for repository in rows}
3020 if not repository_ids:
3021 return
3022 GenericGitCollection.preloadDataForRepositories(rows)
3023@@ -262,8 +262,8 @@ class GenericGitCollection:
3024
3025 def cache_permission(repository):
3026 if self._user:
3027- get_property_cache(repository)._known_viewers = set(
3028- [self._user.id])
3029+ get_property_cache(repository)._known_viewers = {
3030+ self._user.id}
3031 return repository
3032
3033 eager_load_hook = (
3034diff --git a/lib/lp/code/model/gitref.py b/lib/lp/code/model/gitref.py
3035index 41af46a..61a7526 100644
3036--- a/lib/lp/code/model/gitref.py
3037+++ b/lib/lp/code/model/gitref.py
3038@@ -456,7 +456,7 @@ class GitRefMixin:
3039 from lp.code.model.sourcepackagerecipedata import (
3040 SourcePackageRecipeData,
3041 )
3042- revspecs = set([self.path, self.name])
3043+ revspecs = {self.path, self.name}
3044 if self.path == self.repository.default_branch:
3045 revspecs.add(None)
3046 recipes = SourcePackageRecipeData.findRecipes(
3047diff --git a/lib/lp/code/model/gitrepository.py b/lib/lp/code/model/gitrepository.py
3048index 7210ec4..812f1d7 100644
3049--- a/lib/lp/code/model/gitrepository.py
3050+++ b/lib/lp/code/model/gitrepository.py
3051@@ -618,9 +618,9 @@ class GitRepository(StormBase, WebhookTargetMixin, AccessTokenTargetMixin,
3052 self.information_type not in PUBLIC_INFORMATION_TYPES):
3053 aasource = getUtility(IAccessArtifactSource)
3054 [abstract_artifact] = aasource.ensure([self])
3055- wanted_links = set(
3056+ wanted_links = {
3057 (abstract_artifact, policy) for policy in
3058- getUtility(IAccessPolicySource).findByTeam([self.owner]))
3059+ getUtility(IAccessPolicySource).findByTeam([self.owner])}
3060 else:
3061 # We haven't yet quite worked out how distribution privacy
3062 # works, so only work for projects for now.
3063@@ -847,7 +847,7 @@ class GitRepository(StormBase, WebhookTargetMixin, AccessTokenTargetMixin,
3064 @staticmethod
3065 def fetchRefCommits(hosting_path, refs, logger=None):
3066 """See `IGitRepository`."""
3067- oids = sorted(set(info["sha1"] for info in refs.values()))
3068+ oids = sorted({info["sha1"] for info in refs.values()})
3069 if not oids:
3070 return
3071 commits = parse_git_commits(
3072@@ -1318,7 +1318,7 @@ class GitRepository(StormBase, WebhookTargetMixin, AccessTokenTargetMixin,
3073 proposals = list(group)
3074 merges = hosting_client.detectMerges(
3075 self.getInternalPath(), proposals[0].target_git_commit_sha1,
3076- set(proposal.source_git_commit_sha1 for proposal in proposals))
3077+ {proposal.source_git_commit_sha1 for proposal in proposals})
3078 for proposal in proposals:
3079 merged_revision_id = merges.get(
3080 proposal.source_git_commit_sha1)
3081diff --git a/lib/lp/code/model/revision.py b/lib/lp/code/model/revision.py
3082index 4958e32..680f3a2 100644
3083--- a/lib/lp/code/model/revision.py
3084+++ b/lib/lp/code/model/revision.py
3085@@ -120,7 +120,7 @@ class Revision(SQLBase):
3086
3087 def getProperties(self):
3088 """See `IRevision`."""
3089- return dict((prop.name, prop.value) for prop in self.properties)
3090+ return {prop.name: prop.value for prop in self.properties}
3091
3092 def allocateKarma(self, branch):
3093 """See `IRevision`."""
3094@@ -347,9 +347,9 @@ class RevisionSet:
3095 author = None
3096 author_names.append(author)
3097 # Get or make every RevisionAuthor for these revisions.
3098- revision_authors = dict(
3099- (name, author.id) for name, author in
3100- self.acquireRevisionAuthors(author_names).items())
3101+ revision_authors = {
3102+ name: author.id for name, author in
3103+ self.acquireRevisionAuthors(author_names).items()}
3104
3105 # Collect all data for making Revision objects.
3106 data = []
3107@@ -367,8 +367,8 @@ class RevisionSet:
3108 Revision.revision_author_id), data, get_objects=True)
3109
3110 # Map revision_id to Revision database ID.
3111- revision_db_id = dict(
3112- (rev.revision_id, rev.id) for rev in db_revisions)
3113+ revision_db_id = {
3114+ rev.revision_id: rev.id for rev in db_revisions}
3115
3116 # Collect all data for making RevisionParent and RevisionProperty
3117 # objects.
3118diff --git a/lib/lp/code/model/seriessourcepackagebranch.py b/lib/lp/code/model/seriessourcepackagebranch.py
3119index 5aa7d7d..051d86e 100644
3120--- a/lib/lp/code/model/seriessourcepackagebranch.py
3121+++ b/lib/lp/code/model/seriessourcepackagebranch.py
3122@@ -103,7 +103,7 @@ class SeriesSourcePackageBranchSet:
3123
3124 def findForBranches(self, branches):
3125 """See `IFindOfficialBranchLinks`."""
3126- branch_ids = set(branch.id for branch in branches)
3127+ branch_ids = {branch.id for branch in branches}
3128 return IStore(SeriesSourcePackageBranch).find(
3129 SeriesSourcePackageBranch,
3130 SeriesSourcePackageBranch.branchID.is_in(branch_ids))
3131diff --git a/lib/lp/code/model/sourcepackagerecipebuild.py b/lib/lp/code/model/sourcepackagerecipebuild.py
3132index 3a4f0ba..f10ed3c 100644
3133--- a/lib/lp/code/model/sourcepackagerecipebuild.py
3134+++ b/lib/lp/code/model/sourcepackagerecipebuild.py
3135@@ -390,9 +390,9 @@ class SourcePackageRecipeBuild(SpecificBuildFarmJobSourceMixin,
3136
3137 def getFileByName(self, filename):
3138 """See `ISourcePackageRecipeBuild`."""
3139- files = dict((lfa.filename, lfa)
3140+ files = {lfa.filename: lfa
3141 for lfa in [self.log, self.upload_log]
3142- if lfa is not None)
3143+ if lfa is not None}
3144 try:
3145 return files[filename]
3146 except KeyError:
3147diff --git a/lib/lp/code/model/tests/test_branch.py b/lib/lp/code/model/tests/test_branch.py
3148index 9379266..16858d2 100644
3149--- a/lib/lp/code/model/tests/test_branch.py
3150+++ b/lib/lp/code/model/tests/test_branch.py
3151@@ -1783,7 +1783,7 @@ class StackedBranches(TestCaseWithFactory):
3152 branch = self.factory.makeAnyBranch()
3153 stacked_branch = self.factory.makeAnyBranch(stacked_on=branch)
3154 self.assertEqual(
3155- set([stacked_branch]), set(branch.getStackedBranches()))
3156+ {stacked_branch}, set(branch.getStackedBranches()))
3157
3158 def testMultipleBranchesStacked(self):
3159 # some_branch.getStackedBranches returns a collection of branches
3160@@ -1792,7 +1792,7 @@ class StackedBranches(TestCaseWithFactory):
3161 stacked_a = self.factory.makeAnyBranch(stacked_on=branch)
3162 stacked_b = self.factory.makeAnyBranch(stacked_on=branch)
3163 self.assertEqual(
3164- set([stacked_a, stacked_b]), set(branch.getStackedBranches()))
3165+ {stacked_a, stacked_b}, set(branch.getStackedBranches()))
3166
3167 def testNoBranchesStackedOn(self):
3168 # getStackedBranches returns an empty collection if there are no
3169@@ -1806,7 +1806,7 @@ class StackedBranches(TestCaseWithFactory):
3170 branch = self.factory.makeAnyBranch()
3171 stacked_branch = self.factory.makeAnyBranch(stacked_on=branch)
3172 self.assertEqual(
3173- set([branch]), set(stacked_branch.getStackedOnBranches()))
3174+ {branch}, set(stacked_branch.getStackedOnBranches()))
3175
3176 def testMultipleBranchesStackedOn(self):
3177 # some_branch.getStackedOnBranches returns a collection of branches
3178@@ -1815,7 +1815,7 @@ class StackedBranches(TestCaseWithFactory):
3179 stacked_b = self.factory.makeAnyBranch(stacked_on=stacked_a)
3180 branch = self.factory.makeAnyBranch(stacked_on=stacked_b)
3181 self.assertEqual(
3182- set([stacked_a, stacked_b]), set(branch.getStackedOnBranches()))
3183+ {stacked_a, stacked_b}, set(branch.getStackedOnBranches()))
3184
3185
3186 class BranchAddLandingTarget(TestCaseWithFactory):
3187@@ -1976,9 +1976,9 @@ class BranchAddLandingTarget(TestCaseWithFactory):
3188 bmp = self.source._createMergeProposal(
3189 self.user, self.target, reviewers=[person1, person2],
3190 review_types=['review1', 'review2'])
3191- votes = set((vote.reviewer, vote.review_type) for vote in bmp.votes)
3192+ votes = {(vote.reviewer, vote.review_type) for vote in bmp.votes}
3193 self.assertEqual(
3194- set([(person1, 'review1'), (person2, 'review2')]), votes)
3195+ {(person1, 'review1'), (person2, 'review2')}, votes)
3196
3197
3198 class TestLandingCandidates(TestCaseWithFactory):
3199@@ -3161,9 +3161,9 @@ class TestScheduleDiffUpdates(TestCaseWithFactory):
3200 removeSecurityProxy(bmp2).target_branch.last_scanned_id = 'rev2'
3201 jobs = bmp1.source_branch.scheduleDiffUpdates()
3202 self.assertEqual(2, len(jobs))
3203- bmps_to_update = set(
3204- removeSecurityProxy(job).branch_merge_proposal for job in jobs)
3205- self.assertEqual(set([bmp1, bmp2]), bmps_to_update)
3206+ bmps_to_update = {
3207+ removeSecurityProxy(job).branch_merge_proposal for job in jobs}
3208+ self.assertEqual({bmp1, bmp2}, bmps_to_update)
3209
3210 def test_scheduleDiffUpdates_ignores_final(self):
3211 """Diffs for proposals in final states aren't updated."""
3212diff --git a/lib/lp/code/model/tests/test_branchjob.py b/lib/lp/code/model/tests/test_branchjob.py
3213index ad2dd1b..d3b7592 100644
3214--- a/lib/lp/code/model/tests/test_branchjob.py
3215+++ b/lib/lp/code/model/tests/test_branchjob.py
3216@@ -576,7 +576,7 @@ class TestRevisionsAddedJob(TestCaseWithFactory):
3217 graph = job.bzr_branch.repository.get_graph()
3218 self.addCleanup(job.bzr_branch.unlock)
3219 self.assertEqual(
3220- set([b'rev2a-id', b'rev3-id', b'rev2b-id', b'rev2c-id']),
3221+ {b'rev2a-id', b'rev3-id', b'rev2b-id', b'rev2c-id'},
3222 job.getMergedRevisionIDs(b'rev2d-id', graph))
3223
3224 def test_findRelatedBMP(self):
3225@@ -622,7 +622,7 @@ class TestRevisionsAddedJob(TestCaseWithFactory):
3226 self.addCleanup(job.bzr_branch.unlock)
3227 graph = job.bzr_branch.repository.get_graph()
3228 revision_ids = [b'rev2a-id', b'rev3-id', b'rev2b-id']
3229- self.assertEqual(set(['foo@', 'bar@', 'baz@blaine.com', 'qux@']),
3230+ self.assertEqual({'foo@', 'bar@', 'baz@blaine.com', 'qux@'},
3231 job.getAuthors(revision_ids, graph))
3232
3233 def test_getAuthors_with_ghost(self):
3234@@ -632,7 +632,7 @@ class TestRevisionsAddedJob(TestCaseWithFactory):
3235 graph = job.bzr_branch.repository.get_graph()
3236 self.addCleanup(job.bzr_branch.unlock)
3237 revision_ids = [b'rev2a-id', b'rev3-id', b'rev2b-id', b'rev2c-id']
3238- self.assertEqual(set(['foo@', 'bar@', 'baz@blaine.com', 'qux@']),
3239+ self.assertEqual({'foo@', 'bar@', 'baz@blaine.com', 'qux@'},
3240 job.getAuthors(revision_ids, graph))
3241
3242 def test_getRevisionMessage(self):
3243diff --git a/lib/lp/code/model/tests/test_branchmergeproposal.py b/lib/lp/code/model/tests/test_branchmergeproposal.py
3244index 3e58e46..ed4fdd4 100644
3245--- a/lib/lp/code/model/tests/test_branchmergeproposal.py
3246+++ b/lib/lp/code/model/tests/test_branchmergeproposal.py
3247@@ -399,7 +399,7 @@ class TestBranchMergeProposalTransitions(TestCaseWithFactory):
3248 proposal = self.factory.makeBranchMergeProposal()
3249 # It is always valid to go to the same state.
3250 self.assertValidTransitions(
3251- set([BranchMergeProposalStatus.REJECTED]),
3252+ {BranchMergeProposalStatus.REJECTED},
3253 proposal, BranchMergeProposalStatus.REJECTED,
3254 proposal.source_branch.owner)
3255
3256@@ -610,7 +610,7 @@ class TestMergeProposalAllComments(TestCase):
3257 comment3 = self.merge_proposal.createComment(
3258 self.merge_proposal.registrant, "Subject")
3259 self.assertEqual(
3260- set([comment1, comment2, comment3]),
3261+ {comment1, comment2, comment3},
3262 set(self.merge_proposal.all_comments))
3263
3264
3265@@ -816,7 +816,7 @@ class TestMergeProposalNotification(WithVCSScenarios, TestCaseWithFactory):
3266 target_owner = bmp.merge_target.owner
3267 recipients = bmp.getNotificationRecipients(
3268 CodeReviewNotificationLevel.STATUS)
3269- subscriber_set = set([source_owner, target_owner])
3270+ subscriber_set = {source_owner, target_owner}
3271 self.assertEqual(subscriber_set, set(recipients.keys()))
3272 source_subscriber = self.factory.makePerson()
3273 bmp.merge_source.subscribe(
3274@@ -856,12 +856,12 @@ class TestMergeProposalNotification(WithVCSScenarios, TestCaseWithFactory):
3275 # branches with full code review notification level set.
3276 source_owner = bmp.merge_source.owner
3277 target_owner = bmp.merge_target.owner
3278- self.assertEqual(set([full_subscriber, status_subscriber,
3279- source_owner, target_owner]),
3280+ self.assertEqual({full_subscriber, status_subscriber,
3281+ source_owner, target_owner},
3282 set(recipients.keys()))
3283 recipients = bmp.getNotificationRecipients(
3284 CodeReviewNotificationLevel.FULL)
3285- self.assertEqual(set([full_subscriber, source_owner, target_owner]),
3286+ self.assertEqual({full_subscriber, source_owner, target_owner},
3287 set(recipients.keys()))
3288
3289 def test_getNotificationRecipientsAnyBranch(self):
3290@@ -873,7 +873,7 @@ class TestMergeProposalNotification(WithVCSScenarios, TestCaseWithFactory):
3291 target_owner = bmp.merge_target.owner
3292 prerequisite_owner = bmp.merge_prerequisite.owner
3293 self.assertEqual(
3294- set([source_owner, target_owner, prerequisite_owner]),
3295+ {source_owner, target_owner, prerequisite_owner},
3296 set(recipients.keys()))
3297 source_subscriber = self.factory.makePerson()
3298 bmp.merge_source.subscribe(source_subscriber,
3299@@ -890,9 +890,9 @@ class TestMergeProposalNotification(WithVCSScenarios, TestCaseWithFactory):
3300 recipients = bmp.getNotificationRecipients(
3301 CodeReviewNotificationLevel.FULL)
3302 self.assertEqual(
3303- set([source_subscriber, target_subscriber,
3304+ {source_subscriber, target_subscriber,
3305 prerequisite_subscriber, source_owner, target_owner,
3306- prerequisite_owner]),
3307+ prerequisite_owner},
3308 set(recipients.keys()))
3309
3310 def test_getNotificationRecipientsIncludesReviewers(self):
3311@@ -906,7 +906,7 @@ class TestMergeProposalNotification(WithVCSScenarios, TestCaseWithFactory):
3312 bmp.nominateReviewer(reviewer, registrant=source_owner)
3313 recipients = bmp.getNotificationRecipients(
3314 CodeReviewNotificationLevel.STATUS)
3315- subscriber_set = set([source_owner, target_owner, reviewer])
3316+ subscriber_set = {source_owner, target_owner, reviewer}
3317 self.assertEqual(subscriber_set, set(recipients.keys()))
3318
3319 def test_getNotificationRecipientsIncludesTeamReviewers(self):
3320@@ -921,7 +921,7 @@ class TestMergeProposalNotification(WithVCSScenarios, TestCaseWithFactory):
3321 bmp.nominateReviewer(reviewer, registrant=source_owner)
3322 recipients = bmp.getNotificationRecipients(
3323 CodeReviewNotificationLevel.STATUS)
3324- subscriber_set = set([source_owner, target_owner, reviewer])
3325+ subscriber_set = {source_owner, target_owner, reviewer}
3326 self.assertEqual(subscriber_set, set(recipients.keys()))
3327
3328 def test_getNotificationRecipients_Registrant(self):
3329@@ -971,7 +971,7 @@ class TestMergeProposalNotification(WithVCSScenarios, TestCaseWithFactory):
3330 bmp = self.makeBranchMergeProposal(source=branch)
3331 recipients = bmp.getNotificationRecipients(
3332 CodeReviewNotificationLevel.STATUS)
3333- headers = set([reason.mail_header for reason in recipients.values()])
3334+ headers = {reason.mail_header for reason in recipients.values()}
3335 self.assertFalse("Owner" in headers)
3336
3337 def test_getNotificationRecipients_Owner_not_subscribed(self):
3338@@ -1325,7 +1325,7 @@ class TestBranchMergeProposalGetterGetProposals(TestCaseWithFactory):
3339 # Helper method to return tuples of source branch details.
3340 results = BranchMergeProposalGetter.getProposalsForContext(
3341 context, status, visible_by_user)
3342- return sorted([bmp.source_branch.unique_name for bmp in results])
3343+ return sorted(bmp.source_branch.unique_name for bmp in results)
3344
3345 def test_getProposalsForParticipant(self):
3346 # It's possible to get all the merge proposals for a single
3347@@ -1848,7 +1848,7 @@ class TestBranchMergeProposalNominateReviewer(
3348 votes = list(merge_proposal.votes)
3349 self.assertEqual(
3350 ['general-1', 'general-2'],
3351- sorted([review.review_type for review in votes]))
3352+ sorted(review.review_type for review in votes))
3353
3354 def test_nominate_multiple_with_same_types(self):
3355 # There can be multiple reviews for a team with the same review_type.
3356@@ -2111,9 +2111,9 @@ class TestBranchMergeProposalResubmit(TestCaseWithFactory):
3357 review_type='specious')
3358 bmp2 = bmp1.resubmit(bmp1.registrant)
3359 self.assertEqual(
3360- set([(bmp1.target_branch.owner, None), (nominee, 'nominee'),
3361- (reviewer, 'specious')]),
3362- set((vote.reviewer, vote.review_type) for vote in bmp2.votes))
3363+ {(bmp1.target_branch.owner, None), (nominee, 'nominee'),
3364+ (reviewer, 'specious')},
3365+ {(vote.reviewer, vote.review_type) for vote in bmp2.votes})
3366
3367 def test_resubmit_no_reviewers(self):
3368 """Resubmitting a proposal with no reviewers should work."""
3369diff --git a/lib/lp/code/model/tests/test_codeimportjob.py b/lib/lp/code/model/tests/test_codeimportjob.py
3370index 4ff9155..d2785a6 100644
3371--- a/lib/lp/code/model/tests/test_codeimportjob.py
3372+++ b/lib/lp/code/model/tests/test_codeimportjob.py
3373@@ -474,7 +474,7 @@ class NewEvents(object):
3374
3375 def __init__(self):
3376 event_set = getUtility(ICodeImportEventSet)
3377- self.initial = set(event.id for event in event_set.getAll())
3378+ self.initial = {event.id for event in event_set.getAll()}
3379
3380 def summary(self):
3381 """Render a summary of the newly created CodeImportEvent objects."""
3382diff --git a/lib/lp/code/model/tests/test_diff.py b/lib/lp/code/model/tests/test_diff.py
3383index 9675214..794ffbe 100644
3384--- a/lib/lp/code/model/tests/test_diff.py
3385+++ b/lib/lp/code/model/tests/test_diff.py
3386@@ -282,47 +282,47 @@ class TestDiffInScripts(DiffTestCase):
3387 self.checkExampleBzrMerge(diff.text)
3388
3389 diff_bytes = (
3390- "--- bar\t2009-08-26 15:53:34.000000000 -0400\n"
3391- "+++ bar\t1969-12-31 19:00:00.000000000 -0500\n"
3392- "@@ -1,3 +0,0 @@\n"
3393- "-a\n"
3394- "-b\n"
3395- "-c\n"
3396- "--- baz\t1969-12-31 19:00:00.000000000 -0500\n"
3397- "+++ baz\t2009-08-26 15:53:57.000000000 -0400\n"
3398- "@@ -0,0 +1,2 @@\n"
3399- "+a\n"
3400- "+b\n"
3401- "--- foo\t2009-08-26 15:53:23.000000000 -0400\n"
3402- "+++ foo\t2009-08-26 15:56:43.000000000 -0400\n"
3403- "@@ -1,3 +1,4 @@\n"
3404- " a\n"
3405- "-b\n"
3406- " c\n"
3407- "+d\n"
3408- "+e\n").encode("UTF-8")
3409+ b"--- bar\t2009-08-26 15:53:34.000000000 -0400\n"
3410+ b"+++ bar\t1969-12-31 19:00:00.000000000 -0500\n"
3411+ b"@@ -1,3 +0,0 @@\n"
3412+ b"-a\n"
3413+ b"-b\n"
3414+ b"-c\n"
3415+ b"--- baz\t1969-12-31 19:00:00.000000000 -0500\n"
3416+ b"+++ baz\t2009-08-26 15:53:57.000000000 -0400\n"
3417+ b"@@ -0,0 +1,2 @@\n"
3418+ b"+a\n"
3419+ b"+b\n"
3420+ b"--- foo\t2009-08-26 15:53:23.000000000 -0400\n"
3421+ b"+++ foo\t2009-08-26 15:56:43.000000000 -0400\n"
3422+ b"@@ -1,3 +1,4 @@\n"
3423+ b" a\n"
3424+ b"-b\n"
3425+ b" c\n"
3426+ b"+d\n"
3427+ b"+e\n")
3428
3429 diff_bytes_2 = (
3430- "--- bar\t2009-08-26 15:53:34.000000000 -0400\n"
3431- "+++ bar\t1969-12-31 19:00:00.000000000 -0500\n"
3432- "@@ -1,3 +0,0 @@\n"
3433- "-a\n"
3434- "-b\n"
3435- "-c\n"
3436- "--- baz\t1969-12-31 19:00:00.000000000 -0500\n"
3437- "+++ baz\t2009-08-26 15:53:57.000000000 -0400\n"
3438- "@@ -0,0 +1,2 @@\n"
3439- "+a\n"
3440- "+b\n"
3441- "--- foo\t2009-08-26 15:53:23.000000000 -0400\n"
3442- "+++ foo\t2009-08-26 15:56:43.000000000 -0400\n"
3443- "@@ -1,3 +1,5 @@\n"
3444- " a\n"
3445- "-b\n"
3446- " c\n"
3447- "+d\n"
3448- "+e\n"
3449- "+f\n").encode("UTF-8")
3450+ b"--- bar\t2009-08-26 15:53:34.000000000 -0400\n"
3451+ b"+++ bar\t1969-12-31 19:00:00.000000000 -0500\n"
3452+ b"@@ -1,3 +0,0 @@\n"
3453+ b"-a\n"
3454+ b"-b\n"
3455+ b"-c\n"
3456+ b"--- baz\t1969-12-31 19:00:00.000000000 -0500\n"
3457+ b"+++ baz\t2009-08-26 15:53:57.000000000 -0400\n"
3458+ b"@@ -0,0 +1,2 @@\n"
3459+ b"+a\n"
3460+ b"+b\n"
3461+ b"--- foo\t2009-08-26 15:53:23.000000000 -0400\n"
3462+ b"+++ foo\t2009-08-26 15:56:43.000000000 -0400\n"
3463+ b"@@ -1,3 +1,5 @@\n"
3464+ b" a\n"
3465+ b"-b\n"
3466+ b" c\n"
3467+ b"+d\n"
3468+ b"+e\n"
3469+ b"+f\n")
3470
3471 def test_mergePreviewWithPrerequisite(self):
3472 # Changes introduced in the prerequisite branch are ignored.
3473@@ -354,10 +354,10 @@ class TestDiffInScripts(DiffTestCase):
3474
3475 def test_generateDiffstat_with_CR(self):
3476 diff_bytes = (
3477- "--- foo\t2009-08-26 15:53:23.000000000 -0400\n"
3478- "+++ foo\t2009-08-26 15:56:43.000000000 -0400\n"
3479- "@@ -1,1 +1,1 @@\n"
3480- " a\r-b\r c\r+d\r+e\r+f\r").encode("UTF-8")
3481+ b"--- foo\t2009-08-26 15:53:23.000000000 -0400\n"
3482+ b"+++ foo\t2009-08-26 15:56:43.000000000 -0400\n"
3483+ b"@@ -1,1 +1,1 @@\n"
3484+ b" a\r-b\r c\r+d\r+e\r+f\r")
3485 self.assertEqual({'foo': (0, 0)}, Diff.generateDiffstat(diff_bytes))
3486
3487 def test_fromFileSetsDiffstat(self):
3488@@ -442,7 +442,7 @@ class TestPreviewDiff(DiffTestCase):
3489 # canonical_url of the merge proposal itself.
3490 mp = self._createProposalWithPreviewDiff()
3491 self.assertEqual(
3492- '{0}/+preview-diff/{1}'.format(
3493+ '{}/+preview-diff/{}'.format(
3494 canonical_url(mp), mp.preview_diff.id),
3495 canonical_url(mp.preview_diff))
3496
3497diff --git a/lib/lp/code/model/tests/test_gitrepository.py b/lib/lp/code/model/tests/test_gitrepository.py
3498index dbdf8d9..548cb62 100644
3499--- a/lib/lp/code/model/tests/test_gitrepository.py
3500+++ b/lib/lp/code/model/tests/test_gitrepository.py
3501@@ -1288,7 +1288,7 @@ class TestGitRepositoryModifications(TestCaseWithFactory):
3502 repository = self.factory.makeGitRepository(
3503 date_created=datetime(2015, 6, 1, tzinfo=pytz.UTC))
3504 [ref] = self.factory.makeGitRefs(repository=repository)
3505- repository.removeRefs(set([ref.path]))
3506+ repository.removeRefs({ref.path})
3507 self.assertSqlAttributeEqualsDate(
3508 repository, "date_last_modified", UTC_NOW)
3509
3510@@ -1783,7 +1783,7 @@ class TestGitRepositoryRefs(TestCaseWithFactory):
3511 },
3512 }
3513 self.assertEqual(expected_upsert, refs_to_upsert)
3514- self.assertEqual(set(["refs/heads/bar"]), refs_to_remove)
3515+ self.assertEqual({"refs/heads/bar"}, refs_to_remove)
3516
3517 def test_planRefChanges_skips_non_commits(self):
3518 # planRefChanges does not attempt to update refs that point to
3519@@ -1957,7 +1957,7 @@ class TestGitRepositoryRefs(TestCaseWithFactory):
3520 "type": GitObjectType.COMMIT,
3521 },
3522 }
3523- refs_to_remove = set(["refs/heads/bar"])
3524+ refs_to_remove = {"refs/heads/bar"}
3525 repository.synchroniseRefs(refs_to_upsert, refs_to_remove)
3526 expected_sha1s = [
3527 ("refs/heads/master", "1111111111111111111111111111111111111111"),
3528@@ -2968,10 +2968,10 @@ class TestGitRepositoryDetectMerges(TestCaseWithFactory):
3529 "Work in progress => Merged",
3530 notifications[0].get_payload(decode=True).decode("UTF-8"))
3531 self.assertEqual(proposal.address, notifications[0]["From"])
3532- recipients = set(msg["x-envelope-to"] for msg in notifications)
3533- expected = set(
3534- [proposal.source_git_repository.registrant.preferredemail.email,
3535- proposal.target_git_repository.registrant.preferredemail.email])
3536+ recipients = {msg["x-envelope-to"] for msg in notifications}
3537+ expected = {
3538+ proposal.source_git_repository.registrant.preferredemail.email,
3539+ proposal.target_git_repository.registrant.preferredemail.email}
3540 self.assertEqual(expected, recipients)
3541
3542 def test_update_detects_merges(self):
3543@@ -3009,9 +3009,9 @@ class TestGitRepositoryDetectMerges(TestCaseWithFactory):
3544 expected_events, True, repository.createOrUpdateRefs, refs_info)
3545 expected_args = [
3546 (repository.getInternalPath(), target_1.commit_sha1,
3547- set([source_1.commit_sha1, source_2.commit_sha1])),
3548+ {source_1.commit_sha1, source_2.commit_sha1}),
3549 (repository.getInternalPath(), target_2.commit_sha1,
3550- set([source_1.commit_sha1])),
3551+ {source_1.commit_sha1}),
3552 ]
3553 self.assertContentEqual(
3554 expected_args, hosting_fixture.detectMerges.extract_args())
3555@@ -3027,9 +3027,9 @@ class TestGitRepositoryDetectMerges(TestCaseWithFactory):
3556 self.assertContentEqual(
3557 [(BranchMergeProposalStatus.WORK_IN_PROGRESS,
3558 BranchMergeProposalStatus.MERGED)],
3559- set((event.object_before_modification.queue_status,
3560+ {(event.object_before_modification.queue_status,
3561 event.object.queue_status)
3562- for event in events[:2]))
3563+ for event in events[:2]})
3564
3565
3566 class TestGitRepositoryGetBlob(TestCaseWithFactory):
3567diff --git a/lib/lp/code/model/tests/test_revision.py b/lib/lp/code/model/tests/test_revision.py
3568index 376a32f..957f2ca 100644
3569--- a/lib/lp/code/model/tests/test_revision.py
3570+++ b/lib/lp/code/model/tests/test_revision.py
3571@@ -711,7 +711,7 @@ class TestOnlyPresent(TestCaseWithFactory):
3572 # onlyPresent returns a revid that is present in the database.
3573 present = self.factory.makeRevision().revision_id
3574 self.assertEqual(
3575- set([present]),
3576+ {present},
3577 set(getUtility(IRevisionSet).onlyPresent([present])))
3578
3579 def test_some_present(self):
3580@@ -719,7 +719,7 @@ class TestOnlyPresent(TestCaseWithFactory):
3581 not_present = self.factory.getUniqueString()
3582 present = self.factory.makeRevision().revision_id
3583 self.assertEqual(
3584- set([present]),
3585+ {present},
3586 set(getUtility(IRevisionSet).onlyPresent([present, not_present])))
3587
3588 def test_call_twice_in_one_transaction(self):
3589diff --git a/lib/lp/code/model/tests/test_sourcepackagerecipe.py b/lib/lp/code/model/tests/test_sourcepackagerecipe.py
3590index 274b1d9..719ab3b 100644
3591--- a/lib/lp/code/model/tests/test_sourcepackagerecipe.py
3592+++ b/lib/lp/code/model/tests/test_sourcepackagerecipe.py
3593@@ -552,7 +552,7 @@ class TestSourcePackageRecipeMixin:
3594 (old_distroseries,) = recipe.distroseries
3595 recipe.distroseries.add(distroseries)
3596 self.assertEqual(
3597- set([distroseries, old_distroseries]), set(recipe.distroseries))
3598+ {distroseries, old_distroseries}, set(recipe.distroseries))
3599 recipe.distroseries.remove(distroseries)
3600 self.assertEqual([old_distroseries], list(recipe.distroseries))
3601 recipe.distroseries.clear()
3602@@ -1195,7 +1195,7 @@ class TestWebserviceMixin:
3603 # at the moment, distroseries is not exposed in the API.
3604 transaction.commit()
3605 db_recipe = owner.getRecipe(name='toaster-1')
3606- self.assertEqual(set([db_distroseries]), set(db_recipe.distroseries))
3607+ self.assertEqual({db_distroseries}, set(db_recipe.distroseries))
3608 return recipe, ws_owner, launchpad
3609
3610 def test_createRecipe(self):
3611diff --git a/lib/lp/code/tests/test_bzr.py b/lib/lp/code/tests/test_bzr.py
3612index 24ccead..7f6939c 100644
3613--- a/lib/lp/code/tests/test_bzr.py
3614+++ b/lib/lp/code/tests/test_bzr.py
3615@@ -111,11 +111,11 @@ class TestGetAncestry(TestCaseWithTransport):
3616 tree.commit('msg b', rev_id=b'B')
3617 tree.commit('msg c', rev_id=b'C')
3618 self.assertEqual(
3619- set([b'A']), get_ancestry(branch.repository, b'A'))
3620+ {b'A'}, get_ancestry(branch.repository, b'A'))
3621 self.assertEqual(
3622- set([b'A', b'B']), get_ancestry(branch.repository, b'B'))
3623+ {b'A', b'B'}, get_ancestry(branch.repository, b'B'))
3624 self.assertEqual(
3625- set([b'A', b'B', b'C']), get_ancestry(branch.repository, b'C'))
3626+ {b'A', b'B', b'C'}, get_ancestry(branch.repository, b'C'))
3627
3628 def test_children(self):
3629 # Verify non-mainline children are included.
3630@@ -129,8 +129,8 @@ class TestGetAncestry(TestCaseWithTransport):
3631 tree.set_parent_ids([b'A', b'B'])
3632 tree.commit('msg c', rev_id=b'C')
3633 self.assertEqual(
3634- set([b'A']), get_ancestry(branch.repository, b'A'))
3635+ {b'A'}, get_ancestry(branch.repository, b'A'))
3636 self.assertEqual(
3637- set([b'B']), get_ancestry(branch.repository, b'B'))
3638+ {b'B'}, get_ancestry(branch.repository, b'B'))
3639 self.assertEqual(
3640- set([b'A', b'B', b'C']), get_ancestry(branch.repository, b'C'))
3641+ {b'A', b'B', b'C'}, get_ancestry(branch.repository, b'C'))
3642diff --git a/lib/lp/code/vocabularies/tests/test_branch_vocabularies.py b/lib/lp/code/vocabularies/tests/test_branch_vocabularies.py
3643index 8e0cef4..7773c17 100644
3644--- a/lib/lp/code/vocabularies/tests/test_branch_vocabularies.py
3645+++ b/lib/lp/code/vocabularies/tests/test_branch_vocabularies.py
3646@@ -42,7 +42,7 @@ class TestBranchVocabulary(TestCaseWithFactory):
3647 results = self.vocab.searchForTerms('fizzbuzz')
3648 expected = [
3649 u'~scotty/sprocket/fizzbuzz', u'~scotty/widget/fizzbuzz']
3650- branch_names = sorted([branch.token for branch in results])
3651+ branch_names = sorted(branch.token for branch in results)
3652 self.assertEqual(expected, branch_names)
3653
3654 def test_singleQueryResult(self):
3655@@ -99,7 +99,7 @@ class TestRestrictedBranchVocabularyOnProduct(TestCaseWithFactory):
3656 """
3657 results = self.vocab.searchForTerms('main')
3658 expected = [u'~scotty/widget/main']
3659- branch_names = sorted([branch.token for branch in results])
3660+ branch_names = sorted(branch.token for branch in results)
3661 self.assertEqual(expected, branch_names)
3662
3663 def test_singleQueryResult(self):
3664@@ -122,7 +122,7 @@ class TestRestrictedBranchVocabularyOnProduct(TestCaseWithFactory):
3665 self.factory.makeProductBranch(
3666 owner=team, product=self.product, name='mountain')
3667 results = self.vocab.searchForTerms('mountain')
3668- branch_names = sorted([branch.token for branch in results])
3669+ branch_names = sorted(branch.token for branch in results)
3670 self.assertEqual(['~scotty/widget/mountain'], branch_names)
3671
3672
3673diff --git a/lib/lp/code/vocabularies/tests/test_gitrepository_vocabularies.py b/lib/lp/code/vocabularies/tests/test_gitrepository_vocabularies.py
3674index 9d76025..774b0a1 100644
3675--- a/lib/lp/code/vocabularies/tests/test_gitrepository_vocabularies.py
3676+++ b/lib/lp/code/vocabularies/tests/test_gitrepository_vocabularies.py
3677@@ -40,7 +40,7 @@ class TestGitRepositoryVocabulary(TestCaseWithFactory):
3678 results = self.vocab.searchForTerms("fizzbuzz")
3679 expected = [
3680 u"~scotty/sprocket/+git/fizzbuzz", u"~scotty/widget/+git/fizzbuzz"]
3681- repository_names = sorted([repository.token for repository in results])
3682+ repository_names = sorted(repository.token for repository in results)
3683 self.assertEqual(expected, repository_names)
3684
3685 def test_singleQueryResult(self):
3686@@ -94,7 +94,7 @@ class TestRestrictedGitRepositoryVocabularyOnProduct(TestCaseWithFactory):
3687 """
3688 results = self.vocab.searchForTerms('mountain')
3689 expected = [u'~scotty/widget/+git/mountain']
3690- repo_names = sorted([repo.token for repo in results])
3691+ repo_names = sorted(repo.token for repo in results)
3692 self.assertEqual(expected, repo_names)
3693
3694 def test_singleQueryResult(self):
3695diff --git a/lib/lp/codehosting/inmemory.py b/lib/lp/codehosting/inmemory.py
3696index d68cc22..522f9d1 100644
3697--- a/lib/lp/codehosting/inmemory.py
3698+++ b/lib/lp/codehosting/inmemory.py
3699@@ -565,9 +565,9 @@ class FakeCodehosting:
3700 raise UnknownBranchTypeError(
3701 'Unknown branch type: %r' % (branch_type_name,))
3702 branches = sorted(
3703- [branch for branch in self._branch_set
3704+ (branch for branch in self._branch_set
3705 if branch.next_mirror_time is not None
3706- and branch.branch_type in branch_types],
3707+ and branch.branch_type in branch_types),
3708 key=operator.attrgetter('next_mirror_time'))
3709 if branches:
3710 branch = branches[-1]
3711@@ -655,8 +655,8 @@ class FakeCodehosting:
3712 # exceptions.
3713 if not registrant.inTeam(owner):
3714 raise faults.PermissionDenied(
3715- ('%s cannot create branches owned by %s'
3716- % (registrant.displayname, owner.displayname)))
3717+ '%s cannot create branches owned by %s'
3718+ % (registrant.displayname, owner.displayname))
3719 product = sourcepackage = None
3720 if data['product'] == '+junk':
3721 product = None
3722diff --git a/lib/lp/codehosting/scanner/bzrsync.py b/lib/lp/codehosting/scanner/bzrsync.py
3723index e4298ad..1f60b07 100755
3724--- a/lib/lp/codehosting/scanner/bzrsync.py
3725+++ b/lib/lp/codehosting/scanner/bzrsync.py
3726@@ -149,10 +149,10 @@ class BzrSync:
3727 revisions = Store.of(self.db_branch).find(Revision,
3728 BranchRevision.branch_id == self.db_branch.id,
3729 Revision.id == BranchRevision.revision_id)
3730- parent_map = dict(
3731- (six.ensure_binary(r.revision_id),
3732- [six.ensure_binary(revid) for revid in r.parent_ids])
3733- for r in revisions)
3734+ parent_map = {
3735+ six.ensure_binary(r.revision_id):
3736+ [six.ensure_binary(revid) for revid in r.parent_ids]
3737+ for r in revisions}
3738 parents_provider = DictParentsProvider(parent_map)
3739
3740 class PPSource:
3741diff --git a/lib/lp/codehosting/scanner/tests/test_bzrsync.py b/lib/lp/codehosting/scanner/tests/test_bzrsync.py
3742index 77ef3d5..7fe8ad3 100644
3743--- a/lib/lp/codehosting/scanner/tests/test_bzrsync.py
3744+++ b/lib/lp/codehosting/scanner/tests/test_bzrsync.py
3745@@ -443,25 +443,25 @@ class TestBzrSync(BzrSyncTestCase):
3746 added_ancestry, removed_ancestry = get_delta(b'merge', None)
3747 # All revisions are new for an unscanned branch
3748 self.assertEqual(
3749- set(['base', 'trunk', 'branch', 'merge']), added_ancestry)
3750+ {'base', 'trunk', 'branch', 'merge'}, added_ancestry)
3751 self.assertEqual(set(), removed_ancestry)
3752 added_ancestry, removed_ancestry = get_delta(b'merge', 'base')
3753 self.assertEqual(
3754- set(['trunk', 'branch', 'merge']), added_ancestry)
3755+ {'trunk', 'branch', 'merge'}, added_ancestry)
3756 self.assertEqual(set(), removed_ancestry)
3757 added_ancestry, removed_ancestry = get_delta(NULL_REVISION, 'merge')
3758 self.assertEqual(
3759 set(), added_ancestry)
3760 self.assertEqual(
3761- set(['base', 'trunk', 'branch', 'merge']), removed_ancestry)
3762+ {'base', 'trunk', 'branch', 'merge'}, removed_ancestry)
3763 added_ancestry, removed_ancestry = get_delta(b'base', 'merge')
3764 self.assertEqual(
3765 set(), added_ancestry)
3766 self.assertEqual(
3767- set(['trunk', 'branch', 'merge']), removed_ancestry)
3768+ {'trunk', 'branch', 'merge'}, removed_ancestry)
3769 added_ancestry, removed_ancestry = get_delta(b'trunk', 'branch')
3770- self.assertEqual(set(['trunk']), added_ancestry)
3771- self.assertEqual(set(['branch']), removed_ancestry)
3772+ self.assertEqual({'trunk'}, added_ancestry)
3773+ self.assertEqual({'branch'}, removed_ancestry)
3774
3775 def test_getAncestryDelta(self):
3776 """"Test ancestry delta calculations with a dirty repository."""
3777@@ -510,8 +510,8 @@ class TestBzrSync(BzrSyncTestCase):
3778 (db_branch, branch_tree), ignored = self.makeBranchWithMerge(
3779 b'r1', b'r2', b'r1.1.1', b'r3')
3780 self.makeBzrSync(db_branch).syncBranchAndClose()
3781- expected = set(
3782- [(1, 'r1'), (2, 'r2'), (3, 'r3'), (None, 'r1.1.1')])
3783+ expected = {
3784+ (1, 'r1'), (2, 'r2'), (3, 'r3'), (None, 'r1.1.1')}
3785 self.assertEqual(self.getBranchRevisions(db_branch), expected)
3786
3787 def test_sync_merged_to_merging(self):
3788@@ -538,7 +538,7 @@ class TestBzrSync(BzrSyncTestCase):
3789 self.syncBazaarBranchToDatabase(trunk_tree.branch, db_trunk)
3790 # Then sync with the merged branch.
3791 self.syncBazaarBranchToDatabase(branch_tree.branch, db_trunk)
3792- expected = set([(1, 'base'), (2, 'branch')])
3793+ expected = {(1, 'base'), (2, 'branch')}
3794 self.assertEqual(self.getBranchRevisions(db_trunk), expected)
3795
3796 def test_retrieveDatabaseAncestry(self):
3797@@ -556,8 +556,8 @@ class TestBzrSync(BzrSyncTestCase):
3798 branch_revisions = IStore(BranchRevision).find(
3799 BranchRevision, BranchRevision.branch == branch)
3800 sampledata = list(branch_revisions.order_by(BranchRevision.sequence))
3801- expected_ancestry = set(branch_revision.revision.revision_id
3802- for branch_revision in sampledata)
3803+ expected_ancestry = {branch_revision.revision.revision_id
3804+ for branch_revision in sampledata}
3805 expected_history = [branch_revision.revision.revision_id
3806 for branch_revision in sampledata
3807 if branch_revision.sequence is not None]
3808diff --git a/lib/lp/codehosting/scanner/tests/test_mergedetection.py b/lib/lp/codehosting/scanner/tests/test_mergedetection.py
3809index 66c3521..4d3a93d 100644
3810--- a/lib/lp/codehosting/scanner/tests/test_mergedetection.py
3811+++ b/lib/lp/codehosting/scanner/tests/test_mergedetection.py
3812@@ -299,10 +299,10 @@ class TestBranchMergeDetectionHandler(TestCaseWithFactory):
3813 'Work in progress => Merged',
3814 six.ensure_text(notifications[0].get_payload(decode=True)))
3815 self.assertEqual(proposal.address, notifications[0]['From'])
3816- recipients = set(msg['x-envelope-to'] for msg in notifications)
3817- expected = set(
3818- [proposal.source_branch.registrant.preferredemail.email,
3819- proposal.target_branch.registrant.preferredemail.email])
3820+ recipients = {msg['x-envelope-to'] for msg in notifications}
3821+ expected = {
3822+ proposal.source_branch.registrant.preferredemail.email,
3823+ proposal.target_branch.registrant.preferredemail.email}
3824 self.assertEqual(expected, recipients)
3825
3826 def test_mergeProposalMergeDetected_not_series(self):
3827diff --git a/lib/lp/codehosting/scripts/tests/test_modifiedbranches.py b/lib/lp/codehosting/scripts/tests/test_modifiedbranches.py
3828index 2d72544..6d1faf2 100644
3829--- a/lib/lp/codehosting/scripts/tests/test_modifiedbranches.py
3830+++ b/lib/lp/codehosting/scripts/tests/test_modifiedbranches.py
3831@@ -165,23 +165,23 @@ class TestModifiedBranchesUpdateLocations(TestCase):
3832 def test_single_path_element(self):
3833 # Adding a single element should just add that.
3834 self.script.update_locations('foo')
3835- self.assertEqual(set(['foo']), self.script.locations)
3836+ self.assertEqual({'foo'}, self.script.locations)
3837
3838 def test_single_root_element(self):
3839 # If the single element starts with a /, the locations do not include
3840 # an empty string.
3841 self.script.update_locations('/foo')
3842- self.assertEqual(set(['/foo']), self.script.locations)
3843+ self.assertEqual({'/foo'}, self.script.locations)
3844
3845 def test_multi_path_element(self):
3846 # Adding a "real" path will also include all the parents.
3847 self.script.update_locations('foo/bar/baz')
3848- expected = set(['foo', 'foo/bar', 'foo/bar/baz'])
3849+ expected = {'foo', 'foo/bar', 'foo/bar/baz'}
3850 self.assertEqual(expected, self.script.locations)
3851
3852 def test_duplicates(self):
3853 # Adding paths with common parentage doesn't cause duplicates.
3854 self.script.update_locations('foo/bar/baz')
3855 self.script.update_locations('foo/bar/who')
3856- expected = set(['foo', 'foo/bar', 'foo/bar/baz', 'foo/bar/who'])
3857+ expected = {'foo', 'foo/bar', 'foo/bar/baz', 'foo/bar/who'}
3858 self.assertEqual(expected, self.script.locations)
3859diff --git a/lib/lp/codehosting/tests/test_sftp.py b/lib/lp/codehosting/tests/test_sftp.py
3860index 5d022dd..16df390 100644
3861--- a/lib/lp/codehosting/tests/test_sftp.py
3862+++ b/lib/lp/codehosting/tests/test_sftp.py
3863@@ -558,7 +558,7 @@ class TestSFTPServer(TestCaseInTempDir, SFTPTestMixin):
3864 names = [entry[0] for entry in entries]
3865 self.assertEqual(
3866 set(names),
3867- set([child_dir.encode('UTF-8'), child_file.encode('UTF-8')]))
3868+ {child_dir.encode('UTF-8'), child_file.encode('UTF-8')})
3869
3870 def check_entry(entries, filename):
3871 t = get_transport('.')
3872diff --git a/lib/lp/oci/browser/tests/test_ocirecipe.py b/lib/lp/oci/browser/tests/test_ocirecipe.py
3873index 4cea71a..dab70d4 100644
3874--- a/lib/lp/oci/browser/tests/test_ocirecipe.py
3875+++ b/lib/lp/oci/browser/tests/test_ocirecipe.py
3876@@ -1786,7 +1786,7 @@ class TestOCIRecipeRequestBuildsView(BaseTestOCIRecipeView):
3877 ["amd64", "i386"],
3878 [build.distro_arch_series.architecturetag for build in builds])
3879 self.assertContentEqual(
3880- [2510], set(build.buildqueue_record.lastscore for build in builds))
3881+ [2510], {build.buildqueue_record.lastscore for build in builds})
3882
3883 def test_request_builds_no_architectures(self):
3884 # Selecting no architectures causes a validation failure.
3885diff --git a/lib/lp/registry/browser/distributionsourcepackage.py b/lib/lp/registry/browser/distributionsourcepackage.py
3886index bfbbb38..48def0c 100644
3887--- a/lib/lp/registry/browser/distributionsourcepackage.py
3888+++ b/lib/lp/registry/browser/distributionsourcepackage.py
3889@@ -310,11 +310,11 @@ class DistributionSourcePackageBaseView(LaunchpadView):
3890 [spr.changelog_entry for spr in sprs
3891 if not_empty(spr.changelog_entry)])
3892 if self.user:
3893- self._person_data = dict(
3894- [(email.email, person) for (email, person) in
3895+ self._person_data = {
3896+ email.email: person for (email, person) in
3897 getUtility(IPersonSet).getByEmails(
3898 extract_email_addresses(the_changelog),
3899- include_hidden=False)])
3900+ include_hidden=False)}
3901 else:
3902 self._person_data = None
3903 # Collate diffs for relevant SourcePackageReleases
3904diff --git a/lib/lp/registry/browser/distroseries.py b/lib/lp/registry/browser/distroseries.py
3905index afc2290..6b162dc 100644
3906--- a/lib/lp/registry/browser/distroseries.py
3907+++ b/lib/lp/registry/browser/distroseries.py
3908@@ -1140,13 +1140,13 @@ class DistroSeriesDifferenceBaseView(LaunchpadFormView,
3909 """If specified, return Packagesets given in the GET form data."""
3910 packageset_ids = (
3911 self.request.query_string_params.get("field.packageset", []))
3912- packageset_ids = set(
3913+ packageset_ids = {
3914 int(packageset_id) for packageset_id in packageset_ids
3915- if packageset_id.isdigit())
3916+ if packageset_id.isdigit()}
3917 packagesets = getUtility(IPackagesetSet).getBySeries(self.context)
3918- packagesets = set(
3919+ packagesets = {
3920 packageset for packageset in packagesets
3921- if packageset.id in packageset_ids)
3922+ if packageset.id in packageset_ids}
3923 return None if len(packagesets) == 0 else packagesets
3924
3925 @property
3926@@ -1157,8 +1157,8 @@ class DistroSeriesDifferenceBaseView(LaunchpadFormView,
3927 self.request.query_string_params.get("field.changed_by", ()))
3928 changed_by = (
3929 get_person_by_name(name) for name in changed_by_names)
3930- changed_by = set(
3931- person for person in changed_by if person is not None)
3932+ changed_by = {
3933+ person for person in changed_by if person is not None}
3934 return None if len(changed_by) == 0 else changed_by
3935
3936 @property
3937diff --git a/lib/lp/registry/browser/milestone.py b/lib/lp/registry/browser/milestone.py
3938index 1a2a171..3d2724e 100644
3939--- a/lib/lp/registry/browser/milestone.py
3940+++ b/lib/lp/registry/browser/milestone.py
3941@@ -384,7 +384,7 @@ class MilestoneView(
3942
3943 def getReleases(self):
3944 """See `ProductDownloadFileMixin`."""
3945- return set([self.release])
3946+ return {self.release}
3947
3948 @cachedproperty
3949 def download_files(self):
3950diff --git a/lib/lp/registry/browser/pillar.py b/lib/lp/registry/browser/pillar.py
3951index 4f185df..4c09eb2 100644
3952--- a/lib/lp/registry/browser/pillar.py
3953+++ b/lib/lp/registry/browser/pillar.py
3954@@ -221,8 +221,8 @@ class PillarInvolvementView(LaunchpadView):
3955 def enabled_links(self):
3956 """The enabled involvement links."""
3957 menuapi = MenuAPI(self)
3958- return sorted([
3959- link for link in menuapi.navigation.values() if link.enabled],
3960+ return sorted((
3961+ link for link in menuapi.navigation.values() if link.enabled),
3962 key=attrgetter('sort_key'))
3963
3964 @cachedproperty
3965@@ -239,8 +239,8 @@ class PillarInvolvementView(LaunchpadView):
3966 important_links = [
3967 involved_menu[name]
3968 for name in self.visible_disabled_link_names]
3969- return sorted([
3970- link for link in important_links if not link.enabled],
3971+ return sorted((
3972+ link for link in important_links if not link.enabled),
3973 key=attrgetter('sort_key'))
3974
3975 @property
3976@@ -451,7 +451,7 @@ class PillarPersonSharingView(LaunchpadView):
3977 self.specifications = artifacts["specifications"]
3978 self.ocirecipes = artifacts["ocirecipes"]
3979
3980- bug_ids = set([bugtask.bug.id for bugtask in self.bugtasks])
3981+ bug_ids = {bugtask.bug.id for bugtask in self.bugtasks}
3982 self.shared_bugs_count = len(bug_ids)
3983 self.shared_branches_count = len(self.branches)
3984 self.shared_gitrepositories_count = len(self.gitrepositories)
3985diff --git a/lib/lp/registry/browser/product.py b/lib/lp/registry/browser/product.py
3986index 3a853ae..942b4b9 100644
3987--- a/lib/lp/registry/browser/product.py
3988+++ b/lib/lp/registry/browser/product.py
3989@@ -755,7 +755,7 @@ class ProductWithSeries:
3990 # Get all of the releases for all of the series in a single
3991 # query. The query sorts the releases properly so we know the
3992 # resulting list is sorted correctly.
3993- series_by_id = dict((series.id, series) for series in self.series)
3994+ series_by_id = {series.id: series for series in self.series}
3995 self.release_by_id = {}
3996 milestones_and_releases = list(
3997 self.product.getMilestonesAndReleases())
3998@@ -1989,7 +1989,7 @@ class ProductSetBranchView(ReturnToReferrerMixin, LaunchpadFormView,
3999
4000 def _validSchemes(self, rcs_type):
4001 """Return the valid schemes for the repository URL."""
4002- schemes = set(['http', 'https'])
4003+ schemes = {'http', 'https'}
4004 # Extend the allowed schemes for the repository URL based on
4005 # rcs_type.
4006 extra_schemes = {
4007diff --git a/lib/lp/registry/browser/sourcepackage.py b/lib/lp/registry/browser/sourcepackage.py
4008index d5a676c..ea447c2 100644
4009--- a/lib/lp/registry/browser/sourcepackage.py
4010+++ b/lib/lp/registry/browser/sourcepackage.py
4011@@ -483,8 +483,8 @@ class SourcePackageView(LaunchpadView):
4012 def binaries(self):
4013 """Format binary packages into binarypackagename and archtags"""
4014 results = {}
4015- all_arch = sorted([arch.architecturetag for arch in
4016- self.context.distroseries.architectures])
4017+ all_arch = sorted(arch.architecturetag for arch in
4018+ self.context.distroseries.architectures)
4019 for bin in self.context.currentrelease.getBinariesForSeries(
4020 self.context.distroseries):
4021 distroarchseries = bin.build.distro_arch_series
4022diff --git a/lib/lp/registry/browser/tests/test_mailinglists.py b/lib/lp/registry/browser/tests/test_mailinglists.py
4023index f9f28e9..b1154ba 100644
4024--- a/lib/lp/registry/browser/tests/test_mailinglists.py
4025+++ b/lib/lp/registry/browser/tests/test_mailinglists.py
4026@@ -1,4 +1,3 @@
4027-
4028 # Copyright 2010 Canonical Ltd. This software is licensed under the
4029 # GNU Affero General Public License version 3 (see the file LICENSE).
4030
4031diff --git a/lib/lp/registry/interfaces/pocket.py b/lib/lp/registry/interfaces/pocket.py
4032index 10443b2..47bfdc9 100644
4033--- a/lib/lp/registry/interfaces/pocket.py
4034+++ b/lib/lp/registry/interfaces/pocket.py
4035@@ -77,4 +77,4 @@ pocketsuffix = {
4036 PackagePublishingPocket.BACKPORTS: "-backports",
4037 }
4038
4039-suffixpocket = dict((v, k) for (k, v) in pocketsuffix.items())
4040+suffixpocket = {v: k for (k, v) in pocketsuffix.items()}
4041diff --git a/lib/lp/registry/model/accesspolicy.py b/lib/lp/registry/model/accesspolicy.py
4042index ef76153..89431c7 100644
4043--- a/lib/lp/registry/model/accesspolicy.py
4044+++ b/lib/lp/registry/model/accesspolicy.py
4045@@ -67,7 +67,7 @@ def reconcile_access_for_artifacts(artifacts, information_type, pillars,
4046 abstract_artifacts = getUtility(IAccessArtifactSource).ensure(artifacts)
4047 aps = getUtility(IAccessPolicySource).find(
4048 (pillar, information_type) for pillar in pillars)
4049- missing_pillars = set(pillars) - set([ap.pillar for ap in aps])
4050+ missing_pillars = set(pillars) - {ap.pillar for ap in aps}
4051 if len(missing_pillars):
4052 pillar_str = ', '.join([p.name for p in missing_pillars])
4053 raise AssertionError(
4054@@ -79,9 +79,9 @@ def reconcile_access_for_artifacts(artifacts, information_type, pillars,
4055 apasource = getUtility(IAccessPolicyArtifactSource)
4056 wanted_links = (
4057 wanted_links or set(product(abstract_artifacts, aps)))
4058- existing_links = set([
4059+ existing_links = {
4060 (apa.abstract_artifact, apa.policy)
4061- for apa in apasource.findByArtifact(abstract_artifacts)])
4062+ for apa in apasource.findByArtifact(abstract_artifacts)}
4063 apasource.create(wanted_links - existing_links)
4064 apasource.delete(existing_links - wanted_links)
4065
4066@@ -163,7 +163,7 @@ class AccessArtifact(StormBase):
4067 # Not everything exists. Create missing ones.
4068 needed = (
4069 set(concrete_artifacts) -
4070- set(abstract.concrete_artifact for abstract in existing))
4071+ {abstract.concrete_artifact for abstract in existing})
4072
4073 insert_values = []
4074 for concrete in needed:
4075@@ -489,7 +489,7 @@ class AccessPolicyGrantFlat(StormBase):
4076 @classmethod
4077 def findGranteePermissionsByPolicy(cls, policies, grantees=None):
4078 """See `IAccessPolicyGrantFlatSource`."""
4079- policies_by_id = dict((policy.id, policy) for policy in policies)
4080+ policies_by_id = {policy.id: policy for policy in policies}
4081
4082 # A cache for the sharing permissions, keyed on grantee
4083 permissions_cache = defaultdict(dict)
4084@@ -506,8 +506,8 @@ class AccessPolicyGrantFlat(StormBase):
4085 def load_permissions(people):
4086 # We now have the grantees and policies we want in the result so
4087 # load any corresponding permissions and cache them.
4088- people_by_id = dict(
4089- (person[0].id, person[0]) for person in people)
4090+ people_by_id = {
4091+ person[0].id: person[0] for person in people}
4092 cls._populatePermissionsCache(
4093 permissions_cache, shared_artifact_info_types,
4094 people_by_id.keys(), policies_by_id, people_by_id)
4095diff --git a/lib/lp/registry/model/distributionsourcepackage.py b/lib/lp/registry/model/distributionsourcepackage.py
4096index 4606f0e..ca41f4c 100644
4097--- a/lib/lp/registry/model/distributionsourcepackage.py
4098+++ b/lib/lp/registry/model/distributionsourcepackage.py
4099@@ -426,9 +426,9 @@ class DistributionSourcePackage(BugTargetBase,
4100 sprs = [SourcePackageRelease.get(spr_id) for spr_id in spr_ids]
4101 pubs = DistributionSourcePackageRelease.getPublishingHistories(
4102 self.distribution, sprs)
4103- sprs_by_id = dict(
4104- (spr, list(pubs)) for (spr, pubs) in
4105- itertools.groupby(pubs, attrgetter('sourcepackagereleaseID')))
4106+ sprs_by_id = {
4107+ spr: list(pubs) for (spr, pubs) in
4108+ itertools.groupby(pubs, attrgetter('sourcepackagereleaseID'))}
4109 return [
4110 (DistributionSourcePackageRelease(
4111 distribution=self.distribution,
4112diff --git a/lib/lp/registry/model/distroseriesdifference.py b/lib/lp/registry/model/distroseriesdifference.py
4113index b68df3f..3845bb5 100644
4114--- a/lib/lp/registry/model/distroseriesdifference.py
4115+++ b/lib/lp/registry/model/distroseriesdifference.py
4116@@ -269,9 +269,9 @@ def eager_load_dsds(dsds):
4117 dsds, statuses=active_publishing_status,
4118 in_parent=True, match_version=True))
4119
4120- latest_comment_by_dsd_id = dict(
4121- (comment.distro_series_difference_id, comment)
4122- for comment in most_recent_comments(dsds))
4123+ latest_comment_by_dsd_id = {
4124+ comment.distro_series_difference_id: comment
4125+ for comment in most_recent_comments(dsds)}
4126 latest_comments = latest_comment_by_dsd_id.values()
4127
4128 # SourcePackageReleases of the parent and source pubs are often
4129diff --git a/lib/lp/registry/model/person.py b/lib/lp/registry/model/person.py
4130index b9f519e..36be643 100644
4131--- a/lib/lp/registry/model/person.py
4132+++ b/lib/lp/registry/model/person.py
4133@@ -842,10 +842,10 @@ class Person(
4134 # Defaults for informationalness: we don't have to do anything
4135 # because the default if nothing is said is ANY.
4136
4137- roles = set([
4138+ roles = {
4139 SpecificationFilter.CREATOR, SpecificationFilter.ASSIGNEE,
4140 SpecificationFilter.DRAFTER, SpecificationFilter.APPROVER,
4141- SpecificationFilter.SUBSCRIBER])
4142+ SpecificationFilter.SUBSCRIBER}
4143 # If no roles are given, then we want everything.
4144 if filter.intersection(roles) == set():
4145 filter.update(roles)
4146@@ -2321,7 +2321,7 @@ class Person(
4147 # These tables will be skipped since they do not risk leaking
4148 # team membership information.
4149 # Note all of the table names and columns must be all lowercase.
4150- skip = set([
4151+ skip = {
4152 ('accessartifactgrant', 'grantee'),
4153 ('accessartifactgrant', 'grantor'),
4154 ('accesspolicy', 'person'),
4155@@ -2381,7 +2381,7 @@ class Person(
4156 # user already has access to the team.
4157 ('latestpersonsourcepackagereleasecache', 'creator'),
4158 ('latestpersonsourcepackagereleasecache', 'maintainer'),
4159- ])
4160+ }
4161
4162 warnings = set()
4163 ref_query = []
4164@@ -2755,7 +2755,7 @@ class Person(
4165 AND date_consumed IS NULL
4166 """ % sqlvalues(self.id, LoginTokenType.VALIDATEEMAIL,
4167 LoginTokenType.VALIDATETEAMEMAIL)
4168- return sorted(set(token.email for token in LoginToken.select(query)))
4169+ return sorted({token.email for token in LoginToken.select(query)})
4170
4171 @property
4172 def guessedemails(self):
4173@@ -2766,8 +2766,8 @@ class Person(
4174 def pending_gpg_keys(self):
4175 """See `IPerson`."""
4176 logintokenset = getUtility(ILoginTokenSet)
4177- return sorted(set(token.fingerprint for token in
4178- logintokenset.getPendingGPGKeys(requesterid=self.id)))
4179+ return sorted({token.fingerprint for token in
4180+ logintokenset.getPendingGPGKeys(requesterid=self.id)})
4181
4182 @property
4183 def inactive_gpg_keys(self):
4184@@ -3849,9 +3849,9 @@ class PersonSet:
4185 # This has the side effect of sucking in the ValidPersonCache
4186 # items into the cache, allowing Person.is_valid_person calls to
4187 # not hit the DB.
4188- valid_person_ids = set(
4189+ valid_person_ids = {
4190 person_id.id for person_id in ValidPersonCache.select(
4191- "id IN %s" % sqlvalues(person_ids)))
4192+ "id IN %s" % sqlvalues(person_ids))}
4193 return [
4194 person for person in persons if person.id in valid_person_ids]
4195
4196diff --git a/lib/lp/registry/model/product.py b/lib/lp/registry/model/product.py
4197index 471b997..e8422d1 100644
4198--- a/lib/lp/registry/model/product.py
4199+++ b/lib/lp/registry/model/product.py
4200@@ -736,8 +736,8 @@ class Product(SQLBase, BugTargetBase, MakesAnnouncements,
4201 # information types.
4202 aps = getUtility(IAccessPolicySource)
4203 existing_policies = aps.findByPillar([self])
4204- existing_types = set([
4205- access_policy.type for access_policy in existing_policies])
4206+ existing_types = {
4207+ access_policy.type for access_policy in existing_policies}
4208 # Create the missing policies.
4209 required_types = set(information_types).difference(
4210 existing_types).intersection(PRIVATE_INFORMATION_TYPES)
4211@@ -1232,10 +1232,10 @@ class Product(SQLBase, BugTargetBase, MakesAnnouncements,
4212 @property
4213 def translatable_packages(self):
4214 """See `IProduct`."""
4215- packages = set(
4216+ packages = {
4217 package
4218 for package in self.sourcepackages
4219- if package.has_current_translation_templates)
4220+ if package.has_current_translation_templates}
4221
4222 # Sort packages by distroseries.name and package.name
4223 return sorted(packages, key=lambda p: (p.distroseries.name, p.name))
4224@@ -1245,10 +1245,10 @@ class Product(SQLBase, BugTargetBase, MakesAnnouncements,
4225 """See `IProduct`."""
4226 if not service_uses_launchpad(self.translations_usage):
4227 return []
4228- translatable_product_series = set(
4229+ translatable_product_series = {
4230 product_series
4231 for product_series in self.series
4232- if product_series.has_current_translation_templates)
4233+ if product_series.has_current_translation_templates}
4234 return sorted(
4235 translatable_product_series,
4236 key=operator.attrgetter('datecreated'))
4237@@ -1283,9 +1283,9 @@ class Product(SQLBase, BugTargetBase, MakesAnnouncements,
4238 @property
4239 def obsolete_translatable_series(self):
4240 """See `IProduct`."""
4241- obsolete_product_series = set(
4242+ obsolete_product_series = {
4243 product_series for product_series in self.series
4244- if product_series.has_obsolete_translation_templates)
4245+ if product_series.has_obsolete_translation_templates}
4246 return sorted(obsolete_product_series, key=lambda s: s.datecreated)
4247
4248 @property
4249@@ -1525,12 +1525,12 @@ def get_precached_products(products, need_licences=False,
4250 from lp.code.interfaces.gitrepository import IGitRepositorySet
4251 from lp.registry.model.projectgroup import ProjectGroup
4252
4253- product_ids = set(obj.id for obj in products)
4254+ product_ids = {obj.id for obj in products}
4255 if not product_ids:
4256 return
4257- products_by_id = dict((product.id, product) for product in products)
4258- caches = dict((product.id, get_property_cache(product))
4259- for product in products)
4260+ products_by_id = {product.id: product for product in products}
4261+ caches = {product.id: get_property_cache(product)
4262+ for product in products}
4263 for cache in caches.values():
4264 if not safe_hasattr(cache, 'commercial_subscription'):
4265 cache.commercial_subscription = None
4266diff --git a/lib/lp/registry/model/sourcepackage.py b/lib/lp/registry/model/sourcepackage.py
4267index f27672e..1df33ee 100644
4268--- a/lib/lp/registry/model/sourcepackage.py
4269+++ b/lib/lp/registry/model/sourcepackage.py
4270@@ -142,7 +142,7 @@ class SourcePackageQuestionTargetMixin(QuestionTargetMixin):
4271 set(QuestionTargetMixin.getAnswerContactsForLanguage(
4272 self, language)))
4273 return sorted(
4274- [person for person in persons], key=attrgetter('displayname'))
4275+ (person for person in persons), key=attrgetter('displayname'))
4276
4277 def getAnswerContactRecipients(self, language):
4278 """See `IQuestionTarget`."""
4279@@ -761,7 +761,7 @@ class SourcePackage(BugTargetBase, HasCodeImportsMixin,
4280
4281 def linkedBranches(self):
4282 """See `ISourcePackage`."""
4283- return dict((p.name, b) for (p, b) in self.linked_branches)
4284+ return {p.name: b for (p, b) in self.linked_branches}
4285
4286 def getBugTaskWeightFunction(self):
4287 """Provide a weight function to determine optimal bug task.
4288diff --git a/lib/lp/registry/scripts/teamparticipation.py b/lib/lp/registry/scripts/teamparticipation.py
4289index c332f51..cfca76a 100644
4290--- a/lib/lp/registry/scripts/teamparticipation.py
4291+++ b/lib/lp/registry/scripts/teamparticipation.py
4292@@ -155,7 +155,7 @@ def check_teamparticipation_consistency(log, info):
4293
4294 log.debug("Checking consistency of %d people", len(people))
4295 for person in report_progress(log, 50000, people, "people"):
4296- participants_expected = set((person,))
4297+ participants_expected = {person}
4298 participants_observed = team_participations[person]
4299 errors.extend(
4300 check_participants(
4301diff --git a/lib/lp/registry/scripts/tests/test_populate_distroseriesdiff.py b/lib/lp/registry/scripts/tests/test_populate_distroseriesdiff.py
4302index 9854fa7..fdd599f 100644
4303--- a/lib/lp/registry/scripts/tests/test_populate_distroseriesdiff.py
4304+++ b/lib/lp/registry/scripts/tests/test_populate_distroseriesdiff.py
4305@@ -143,10 +143,10 @@ class TestFindLatestSourcePackageReleases(TestCaseWithFactory, FactoryHelper):
4306
4307 def test_does_not_find_publication_outside_primary_archive(self):
4308 distroseries = self.factory.makeDistroSeries()
4309- spphs = dict(
4310- (purpose, self.makeSPPH(
4311- distroseries=distroseries, archive_purpose=purpose))
4312- for purpose in ArchivePurpose.items)
4313+ spphs = {
4314+ purpose: self.makeSPPH(
4315+ distroseries=distroseries, archive_purpose=purpose)
4316+ for purpose in ArchivePurpose.items}
4317 query = compose_sql_find_latest_source_package_releases(distroseries)
4318 self.assertContentEqual(
4319 [self.getExpectedResultFor(spphs[ArchivePurpose.PRIMARY])],
4320@@ -154,9 +154,9 @@ class TestFindLatestSourcePackageReleases(TestCaseWithFactory, FactoryHelper):
4321
4322 def test_does_not_find_publication_outside_release_pocket(self):
4323 distroseries = self.factory.makeDistroSeries()
4324- spphs = dict(
4325- (pocket, self.makeSPPH(distroseries=distroseries, pocket=pocket))
4326- for pocket in PackagePublishingPocket.items)
4327+ spphs = {
4328+ pocket: self.makeSPPH(distroseries=distroseries, pocket=pocket)
4329+ for pocket in PackagePublishingPocket.items}
4330 release_spph = spphs[PackagePublishingPocket.RELEASE]
4331 query = compose_sql_find_latest_source_package_releases(distroseries)
4332 self.assertContentEqual(
4333@@ -165,9 +165,9 @@ class TestFindLatestSourcePackageReleases(TestCaseWithFactory, FactoryHelper):
4334
4335 def test_finds_active_publication(self):
4336 distroseries = self.factory.makeDistroSeries()
4337- spphs = dict(
4338- (status, self.makeSPPH(distroseries=distroseries, status=status))
4339- for status in active_publishing_status)
4340+ spphs = {
4341+ status: self.makeSPPH(distroseries=distroseries, status=status)
4342+ for status in active_publishing_status}
4343 query = compose_sql_find_latest_source_package_releases(distroseries)
4344 self.assertContentEqual(
4345 [self.getExpectedResultFor(spph)
4346diff --git a/lib/lp/registry/services/tests/test_sharingservice.py b/lib/lp/registry/services/tests/test_sharingservice.py
4347index 5aa3c5c..e0accd8 100644
4348--- a/lib/lp/registry/services/tests/test_sharingservice.py
4349+++ b/lib/lp/registry/services/tests/test_sharingservice.py
4350@@ -795,15 +795,15 @@ class TestSharingService(TestCaseWithFactory, OCIConfigHelperMixin):
4351 another_person_data = (
4352 another, {access_policies[0]: SharingPermission.ALL}, [])
4353 expected_data.append(another_person_data)
4354- policy_permissions = dict([(
4355- policy, SharingPermission.SOME) for policy in access_policies])
4356+ policy_permissions = {
4357+ policy: SharingPermission.SOME for policy in access_policies}
4358 yet_another_person_data = (
4359 yet_another, policy_permissions,
4360 [InformationType.PRIVATESECURITY, InformationType.USERDATA])
4361 expected_data.append(yet_another_person_data)
4362 if pillar_type == 'product':
4363- policy_permissions = dict([(
4364- policy, SharingPermission.ALL) for policy in access_policies])
4365+ policy_permissions = {
4366+ policy: SharingPermission.ALL for policy in access_policies}
4367 owner_data = (pillar.owner, policy_permissions, [])
4368 expected_data.append(owner_data)
4369 self._assert_grantee_data(
4370diff --git a/lib/lp/registry/tests/test_distributionmirror_prober.py b/lib/lp/registry/tests/test_distributionmirror_prober.py
4371index c2d89d5..0146ca4 100644
4372--- a/lib/lp/registry/tests/test_distributionmirror_prober.py
4373+++ b/lib/lp/registry/tests/test_distributionmirror_prober.py
4374@@ -929,7 +929,7 @@ class TestMirrorCDImageProberCallbacks(TestCaseWithFactory):
4375 callbacks = self.makeMirrorProberCallbacks()
4376 self.assertEqual(
4377 set(callbacks.expected_failures),
4378- set([
4379+ {
4380 BadResponseCode,
4381 ProberTimeout,
4382 ConnectionSkipped,
4383@@ -937,7 +937,7 @@ class TestMirrorCDImageProberCallbacks(TestCaseWithFactory):
4384 UnknownURLSchemeAfterRedirect,
4385 InvalidHTTPSCertificate,
4386 InvalidHTTPSCertificateSkipped,
4387- ]))
4388+ })
4389 exceptions = [BadResponseCode(http.client.NOT_FOUND),
4390 ProberTimeout('http://localhost/', 5),
4391 ConnectionSkipped(),
4392diff --git a/lib/lp/registry/tests/test_distroseries.py b/lib/lp/registry/tests/test_distroseries.py
4393index bb979c3..1543eca 100644
4394--- a/lib/lp/registry/tests/test_distroseries.py
4395+++ b/lib/lp/registry/tests/test_distroseries.py
4396@@ -660,7 +660,7 @@ class TestDistroSeriesSet(TestCaseWithFactory):
4397 distro_series_set = getUtility(IDistroSeriesSet)
4398 # Get translatables as a sequence of names of the series.
4399 return sorted(
4400- [series.name for series in distro_series_set.translatables()])
4401+ series.name for series in distro_series_set.translatables())
4402
4403 def _ref_translatables(self, expected=None):
4404 # Return the reference value, merged with expected data.
4405diff --git a/lib/lp/registry/tests/test_distroseries_vocabularies.py b/lib/lp/registry/tests/test_distroseries_vocabularies.py
4406index e08ea8d..c5c30b8 100644
4407--- a/lib/lp/registry/tests/test_distroseries_vocabularies.py
4408+++ b/lib/lp/registry/tests/test_distroseries_vocabularies.py
4409@@ -73,7 +73,7 @@ class TestDistroSeriesDerivationVocabulary(TestCaseWithFactory):
4410 expected_distroseries = (
4411 set(self.all_series_with_arch).difference(
4412 distroseries.distribution.series))
4413- observed_distroseries = set(term.value for term in vocabulary)
4414+ observed_distroseries = {term.value for term in vocabulary}
4415 self.assertEqual(expected_distroseries, observed_distroseries)
4416
4417 def test_distribution_with_non_derived_series_no_arch(self):
4418@@ -83,7 +83,7 @@ class TestDistroSeriesDerivationVocabulary(TestCaseWithFactory):
4419 distroseries = self.factory.makeDistroSeries()
4420 vocabulary = DistroSeriesDerivationVocabulary(distroseries)
4421 another_parent_no_arch = self.factory.makeDistroSeries()
4422- observed_distroseries = set(term.value for term in vocabulary)
4423+ observed_distroseries = {term.value for term in vocabulary}
4424
4425 self.assertNotIn(another_parent_no_arch, observed_distroseries)
4426
4427@@ -106,7 +106,7 @@ class TestDistroSeriesDerivationVocabulary(TestCaseWithFactory):
4428 derived_series=distroseries, parent_series=parent_distroseries)
4429 vocabulary = DistroSeriesDerivationVocabulary(distroseries)
4430 expected_distroseries = set(parent_distroseries.distribution.series)
4431- observed_distroseries = set(term.value for term in vocabulary)
4432+ observed_distroseries = {term.value for term in vocabulary}
4433 self.assertContentEqual(expected_distroseries, observed_distroseries)
4434
4435 def test_distribution_with_derived_series_no_arch(self):
4436@@ -119,7 +119,7 @@ class TestDistroSeriesDerivationVocabulary(TestCaseWithFactory):
4437 self.factory.makeDistroSeriesParent(
4438 derived_series=distroseries, parent_series=parent_distroseries)
4439 vocabulary = DistroSeriesDerivationVocabulary(distroseries)
4440- observed_distroseries = set(term.value for term in vocabulary)
4441+ observed_distroseries = {term.value for term in vocabulary}
4442
4443 self.assertIn(another_parent_no_arch, observed_distroseries)
4444
4445@@ -142,7 +142,7 @@ class TestDistroSeriesDerivationVocabulary(TestCaseWithFactory):
4446 expected_distroseries = set(
4447 parent_distroseries.distribution.series).union(
4448 set(another_parent_distroseries.distribution.series))
4449- observed_distroseries = set(term.value for term in vocabulary)
4450+ observed_distroseries = {term.value for term in vocabulary}
4451 self.assertEqual(expected_distroseries, observed_distroseries)
4452
4453 def test_distribution_with_derived_series_of_self(self):
4454@@ -159,7 +159,7 @@ class TestDistroSeriesDerivationVocabulary(TestCaseWithFactory):
4455 expected_distroseries = (
4456 set(self.all_series_with_arch).difference(
4457 distroseries.distribution.series))
4458- observed_distroseries = set(term.value for term in vocabulary)
4459+ observed_distroseries = {term.value for term in vocabulary}
4460 self.assertEqual(expected_distroseries, observed_distroseries)
4461
4462 def test_distroseries(self):
4463@@ -170,7 +170,7 @@ class TestDistroSeriesDerivationVocabulary(TestCaseWithFactory):
4464 expected_distroseries = (
4465 set(self.all_series_with_arch).difference(
4466 distroseries.distribution.series))
4467- observed_distroseries = set(term.value for term in vocabulary)
4468+ observed_distroseries = {term.value for term in vocabulary}
4469 self.assertEqual(expected_distroseries, observed_distroseries)
4470
4471 def test_ordering(self):
4472diff --git a/lib/lp/registry/tests/test_distroseriesdifference.py b/lib/lp/registry/tests/test_distroseriesdifference.py
4473index 0163383..18bb640 100644
4474--- a/lib/lp/registry/tests/test_distroseriesdifference.py
4475+++ b/lib/lp/registry/tests/test_distroseriesdifference.py
4476@@ -436,7 +436,7 @@ class DistroSeriesDifferenceTestCase(TestCaseWithFactory):
4477 ds_diff, ds_diff.parent_series, 5)
4478 parent_packagesets = ds_diff.parent_packagesets
4479 self.assertEqual(
4480- sorted([packageset.name for packageset in packagesets]),
4481+ sorted(packageset.name for packageset in packagesets),
4482 [packageset.name for packageset in parent_packagesets])
4483
4484 def test_packagesets(self):
4485@@ -445,7 +445,7 @@ class DistroSeriesDifferenceTestCase(TestCaseWithFactory):
4486 packagesets = self._setupPackageSets(
4487 ds_diff, ds_diff.derived_series, 5)
4488 self.assertEqual(
4489- sorted([packageset.name for packageset in packagesets]),
4490+ sorted(packageset.name for packageset in packagesets),
4491 [packageset.name for packageset in ds_diff.packagesets])
4492
4493 def test_blocklist_unauthorised(self):
4494@@ -998,17 +998,17 @@ class DistroSeriesDifferenceSourceTestCase(TestCaseWithFactory):
4495
4496 def makeDifferencesForAllDifferenceTypes(self, derived_series):
4497 """Create DSDs of all types for `derived_series`."""
4498- return dict(
4499- (diff_type, self.factory.makeDistroSeriesDifference(
4500- derived_series, difference_type=diff_type))
4501- for diff_type in DistroSeriesDifferenceType.items)
4502+ return {
4503+ diff_type: self.factory.makeDistroSeriesDifference(
4504+ derived_series, difference_type=diff_type)
4505+ for diff_type in DistroSeriesDifferenceType.items}
4506
4507 def makeDifferencesForAllStatuses(self, derived_series):
4508 """Create DSDs of all statuses for `derived_series`."""
4509- return dict(
4510- (status, self.factory.makeDistroSeriesDifference(
4511- derived_series, status=status))
4512- for status in DistroSeriesDifferenceStatus.items)
4513+ return {
4514+ status: self.factory.makeDistroSeriesDifference(
4515+ derived_series, status=status)
4516+ for status in DistroSeriesDifferenceStatus.items}
4517
4518 def makeDerivedSeries(self, derived_series=None):
4519 """Create a derived `DistroSeries`."""
4520@@ -1337,9 +1337,9 @@ class TestMostRecentComments(TestCaseWithFactory):
4521
4522 def test_most_recent_comments(self):
4523 dsp = self.factory.makeDistroSeriesParent()
4524- dsds = set(
4525+ dsds = {
4526 self.factory.makeDistroSeriesDifference(
4527- derived_series=dsp.derived_series) for index in range(5))
4528+ derived_series=dsp.derived_series) for index in range(5)}
4529 expected_comments = set()
4530 for dsd in dsds:
4531 # Add a couple of comments.
4532@@ -1377,9 +1377,9 @@ class TestMostRecentPublications(TestCaseWithFactory):
4533 self.create_difference(derived_series),
4534 ]
4535 # Derived publication.
4536- source_pubs_by_spn_id_expected = set(
4537+ source_pubs_by_spn_id_expected = {
4538 (dsd.source_package_name.id, dsd.source_pub)
4539- for dsd in dsds)
4540+ for dsd in dsds}
4541 source_pubs_by_spn_id_found = most_recent_publications(
4542 dsds, in_parent=False, statuses=(
4543 PackagePublishingStatus.PUBLISHED,
4544@@ -1388,9 +1388,9 @@ class TestMostRecentPublications(TestCaseWithFactory):
4545 source_pubs_by_spn_id_expected,
4546 source_pubs_by_spn_id_found)
4547 # Parent publication
4548- parent_source_pubs_by_spn_id_expected = set(
4549+ parent_source_pubs_by_spn_id_expected = {
4550 (dsd.source_package_name.id, dsd.parent_source_pub)
4551- for dsd in dsds)
4552+ for dsd in dsds}
4553 parent_source_pubs_by_spn_id_found = most_recent_publications(
4554 dsds, in_parent=True, statuses=(
4555 PackagePublishingStatus.PUBLISHED,
4556diff --git a/lib/lp/registry/tests/test_initderiveddistroseries.py b/lib/lp/registry/tests/test_initderiveddistroseries.py
4557index 07b5740..ade4a6d 100644
4558--- a/lib/lp/registry/tests/test_initderiveddistroseries.py
4559+++ b/lib/lp/registry/tests/test_initderiveddistroseries.py
4560@@ -84,9 +84,9 @@ class TestDeriveDistroSeriesMultipleParents(InitializationHelperTestCase):
4561 pub_sources = series.main_archive.getPublishedSources(
4562 distroseries=series)
4563 binaries = sorted(
4564- [(p.getBuiltBinaries()[0].binarypackagerelease.sourcepackagename,
4565+ (p.getBuiltBinaries()[0].binarypackagerelease.sourcepackagename,
4566 p.getBuiltBinaries()[0].binarypackagerelease.version)
4567- for p in pub_sources])
4568+ for p in pub_sources)
4569
4570 self.assertEqual(pack_versions, binaries)
4571
4572diff --git a/lib/lp/registry/tests/test_mailinglistapi.py b/lib/lp/registry/tests/test_mailinglistapi.py
4573index be9f182..c7ea028 100644
4574--- a/lib/lp/registry/tests/test_mailinglistapi.py
4575+++ b/lib/lp/registry/tests/test_mailinglistapi.py
4576@@ -193,9 +193,9 @@ class MailingListAPITestCase(TestCaseWithFactory):
4577 def getEmails(people):
4578 email_address_set = getUtility(IEmailAddressSet)
4579 return {
4580- person.name: set(
4581+ person.name: {
4582 removeSecurityProxy(email_address).email
4583- for email_address in email_address_set.getByPerson(person))
4584+ for email_address in email_address_set.getByPerson(person)}
4585 for person in people}
4586
4587 self.assertThat(
4588diff --git a/lib/lp/registry/tests/test_milestone.py b/lib/lp/registry/tests/test_milestone.py
4589index 27764ab..f20894c 100644
4590--- a/lib/lp/registry/tests/test_milestone.py
4591+++ b/lib/lp/registry/tests/test_milestone.py
4592@@ -55,10 +55,10 @@ class MilestoneTest(unittest.TestCase):
4593
4594 def testMilestoneSetIterator(self):
4595 """Test of MilestoneSet.__iter__()."""
4596- all_milestones_ids = set(
4597- milestone.id for milestone in getUtility(IMilestoneSet))
4598+ all_milestones_ids = {
4599+ milestone.id for milestone in getUtility(IMilestoneSet)}
4600 self.assertEqual(all_milestones_ids,
4601- set((1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12)))
4602+ {1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12})
4603
4604 def testMilestoneSetGet(self):
4605 """Test of MilestoneSet.get()"""
4606@@ -130,13 +130,13 @@ class MilestoneSecurityAdaperTestCase(TestCaseWithFactory):
4607 product=self.proprietary_product)
4608
4609 expected_get_permissions = {
4610- CheckerPublic: set((
4611+ CheckerPublic: {
4612 'id', 'checkAuthenticated', 'checkUnauthenticated',
4613 'userCanView',
4614- )),
4615- 'launchpad.LimitedView': set((
4616- 'displayname', 'name', 'target', 'title',)),
4617- 'launchpad.View': set((
4618+ },
4619+ 'launchpad.LimitedView': {
4620+ 'displayname', 'name', 'target', 'title'},
4621+ 'launchpad.View': {
4622 'active', 'bug_subscriptions', 'bugtasks', 'code_name',
4623 'dateexpected', 'distribution', 'distroseries',
4624 '_getOfficialTagClause', 'getBugSummaryContextWhereClause',
4625@@ -148,15 +148,15 @@ class MilestoneSecurityAdaperTestCase(TestCaseWithFactory):
4626 'summary', 'target_type_display', 'all_specifications',
4627 'userCanAlterBugSubscription', 'userCanAlterSubscription',
4628 'userHasBugSubscriptions',
4629- )),
4630- 'launchpad.AnyAllowedPerson': set((
4631+ },
4632+ 'launchpad.AnyAllowedPerson': {
4633 'addBugSubscription', 'addBugSubscriptionFilter',
4634 'addSubscription', 'removeBugSubscription',
4635- )),
4636- 'launchpad.Edit': set((
4637+ },
4638+ 'launchpad.Edit': {
4639 'closeBugsAndBlueprints', 'createProductRelease',
4640 'destroySelf', 'setTags',
4641- )),
4642+ },
4643 }
4644
4645 def test_get_permissions(self):
4646@@ -166,10 +166,10 @@ class MilestoneSecurityAdaperTestCase(TestCaseWithFactory):
4647 self.expected_get_permissions, checker.get_permissions, 'get')
4648
4649 expected_set_permissions = {
4650- 'launchpad.Edit': set((
4651+ 'launchpad.Edit': {
4652 'active', 'code_name', 'dateexpected', 'distroseries', 'name',
4653 'product_release', 'productseries', 'summary',
4654- )),
4655+ },
4656 }
4657
4658 def test_set_permissions(self):
4659@@ -640,7 +640,7 @@ class ProjectMilestoneSecurityAdaperTestCase(TestCaseWithFactory):
4660 self.proprietary_projectgroup_milestone = milestone_1
4661
4662 expected_get_permissions = {
4663- 'launchpad.View': set((
4664+ 'launchpad.View': {
4665 '_getOfficialTagClause', 'active', 'addBugSubscription',
4666 'addBugSubscriptionFilter', 'addSubscription',
4667 'bug_subscriptions', 'bugtasks', 'closeBugsAndBlueprints',
4668@@ -653,7 +653,7 @@ class ProjectMilestoneSecurityAdaperTestCase(TestCaseWithFactory):
4669 'product_release', 'productseries', 'removeBugSubscription',
4670 'searchTasks', 'series_target', 'summary', 'target',
4671 'target_type_display', 'title', 'userCanAlterBugSubscription',
4672- 'userCanAlterSubscription', 'userHasBugSubscriptions')),
4673+ 'userCanAlterSubscription', 'userHasBugSubscriptions'},
4674 }
4675
4676 def test_get_permissions(self):
4677diff --git a/lib/lp/registry/tests/test_mlists.py b/lib/lp/registry/tests/test_mlists.py
4678index a581384..eedcfa2 100644
4679--- a/lib/lp/registry/tests/test_mlists.py
4680+++ b/lib/lp/registry/tests/test_mlists.py
4681@@ -85,7 +85,7 @@ class BaseMailingListImportTest(unittest.TestCase):
4682
4683 def assertPeople(self, *people):
4684 """Assert that `people` are members of the team."""
4685- members = set(person.name for person in self.team.allmembers)
4686+ members = {person.name for person in self.team.allmembers}
4687 expected = set(people)
4688 # Always add the team owner.
4689 expected.add(u'teamowner')
4690@@ -93,10 +93,10 @@ class BaseMailingListImportTest(unittest.TestCase):
4691
4692 def assertAddresses(self, *addresses):
4693 """Assert that `addresses` are subscribed to the mailing list."""
4694- subscribers = set([
4695+ subscribers = {
4696 address for (name, address) in
4697 getUtility(IMailingListSet).getSubscribedAddresses(
4698- [self.team.name]).get(self.team.name, [])])
4699+ [self.team.name]).get(self.team.name, [])}
4700 expected = set(addresses)
4701 self.assertEqual(subscribers, expected)
4702
4703@@ -469,7 +469,7 @@ class TestMailingListImportScript(BaseMailingListImportTest):
4704 messages = pop_notifications()
4705 self.assertEqual(len(messages), 5)
4706 # The messages are all being sent to the team owner.
4707- recipients = set(message['to'] for message in messages)
4708+ recipients = {message['to'] for message in messages}
4709 self.assertEqual(len(recipients), 1)
4710 self.assertEqual(
4711 recipients.pop(),
4712diff --git a/lib/lp/registry/tests/test_ociproject.py b/lib/lp/registry/tests/test_ociproject.py
4713index 5b0924f..03036fb 100644
4714--- a/lib/lp/registry/tests/test_ociproject.py
4715+++ b/lib/lp/registry/tests/test_ociproject.py
4716@@ -464,8 +464,8 @@ class TestOCIProjectVocabulary(TestCaseWithFactory):
4717 """
4718 naked = removeSecurityProxy
4719 self.assertEqual(
4720- set(naked(ociproject).id for ociproject in ociprojects),
4721- set(naked(term.value).id for term in search_result))
4722+ {naked(ociproject).id for ociproject in ociprojects},
4723+ {naked(term.value).id for term in search_result})
4724
4725 def test_search_with_name_substring(self):
4726 vocabulary = self.getVocabulary()
4727diff --git a/lib/lp/registry/tests/test_oopsreferences.py b/lib/lp/registry/tests/test_oopsreferences.py
4728index f06352c..175795e 100644
4729--- a/lib/lp/registry/tests/test_oopsreferences.py
4730+++ b/lib/lp/registry/tests/test_oopsreferences.py
4731@@ -38,7 +38,7 @@ class TestOopsReferences(TestCaseWithFactory):
4732 now = datetime.now(tz=utc)
4733 day = timedelta(days=1)
4734 self.assertEqual(
4735- set([oopsid]),
4736+ {oopsid},
4737 referenced_oops(now - day, now, "product=1", {}))
4738 self.assertEqual(
4739 set(),
4740@@ -52,7 +52,7 @@ class TestOopsReferences(TestCaseWithFactory):
4741 now = datetime.now(tz=utc)
4742 day = timedelta(days=1)
4743 self.assertEqual(
4744- set([oopsid]),
4745+ {oopsid},
4746 referenced_oops(now - day, now, "product=1", {}))
4747 self.assertEqual(
4748 set(),
4749@@ -67,7 +67,7 @@ class TestOopsReferences(TestCaseWithFactory):
4750 now = datetime.now(tz=utc)
4751 day = timedelta(days=1)
4752 self.assertEqual(
4753- set([oopsid]),
4754+ {oopsid},
4755 referenced_oops(now - day, now, "product=1", {}))
4756 self.assertEqual(
4757 set(),
4758@@ -82,7 +82,7 @@ class TestOopsReferences(TestCaseWithFactory):
4759 now = datetime.now(tz=utc)
4760 day = timedelta(days=1)
4761 self.assertEqual(
4762- set([oopsid]),
4763+ {oopsid},
4764 referenced_oops(now - day, now, "product=1", {}))
4765 self.assertEqual(
4766 set(),
4767@@ -95,11 +95,11 @@ class TestOopsReferences(TestCaseWithFactory):
4768 now = datetime.now(tz=utc)
4769 day = timedelta(days=1)
4770 self.assertEqual(
4771- set([oopsid]),
4772+ {oopsid},
4773 referenced_oops(now - day, now, "product=%(product)s",
4774 {'product': question.product.id}))
4775 self.assertEqual(
4776- set([]),
4777+ set(),
4778 referenced_oops(now + day, now + day, "product=%(product)s",
4779 {'product': question.product.id}))
4780
4781@@ -123,11 +123,11 @@ class TestOopsReferences(TestCaseWithFactory):
4782 now = datetime.now(tz=utc)
4783 day = timedelta(days=1)
4784 self.assertEqual(
4785- set([oopsid]),
4786+ {oopsid},
4787 referenced_oops(now - day, now, "product=%(product)s",
4788 {'product': question.product.id}))
4789 self.assertEqual(
4790- set([]),
4791+ set(),
4792 referenced_oops(now + day, now + day, "product=%(product)s",
4793 {'product': question.product.id}))
4794
4795@@ -140,11 +140,11 @@ class TestOopsReferences(TestCaseWithFactory):
4796 now = datetime.now(tz=utc)
4797 day = timedelta(days=1)
4798 self.assertEqual(
4799- set([oopsid]),
4800+ {oopsid},
4801 referenced_oops(now - day, now, "product=%(product)s",
4802 {'product': question.product.id}))
4803 self.assertEqual(
4804- set([]),
4805+ set(),
4806 referenced_oops(now + day, now + day, "product=%(product)s",
4807 {'product': question.product.id}))
4808
4809@@ -158,11 +158,11 @@ class TestOopsReferences(TestCaseWithFactory):
4810 now = datetime.now(tz=utc)
4811 day = timedelta(days=1)
4812 self.assertEqual(
4813- set([oopsid]),
4814+ {oopsid},
4815 referenced_oops(now - day, now, "distribution=%(distribution)s",
4816 {'distribution': distro.id}))
4817 self.assertEqual(
4818- set([]),
4819+ set(),
4820 referenced_oops(now + day, now + day,
4821 "distribution=%(distribution)s", {'distribution': distro.id}))
4822
4823@@ -187,8 +187,8 @@ class TestOopsReferences(TestCaseWithFactory):
4824 now = datetime.now(tz=utc)
4825 day = timedelta(days=1)
4826 self.assertEqual(
4827- set([oopsid_old, oopsid_new]),
4828+ {oopsid_old, oopsid_new},
4829 referenced_oops(now - day, now, "product=1", {}))
4830 self.assertEqual(
4831- set([]),
4832+ set(),
4833 referenced_oops(now + day, now + day, "product=1", {}))
4834diff --git a/lib/lp/registry/tests/test_person.py b/lib/lp/registry/tests/test_person.py
4835index ee75a5b..a7df518 100644
4836--- a/lib/lp/registry/tests/test_person.py
4837+++ b/lib/lp/registry/tests/test_person.py
4838@@ -1305,7 +1305,7 @@ class TestGetRecipients(TestCaseWithFactory):
4839 team = self.factory.makeTeam(owner)
4840 super_team = self.factory.makeTeam(team)
4841 recipients = get_recipients(super_team)
4842- self.assertEqual(set([owner]), set(recipients))
4843+ self.assertEqual({owner}, set(recipients))
4844
4845 def test_get_recipients_team(self):
4846 """Ensure get_recipients uses teams with preferredemail."""
4847@@ -1314,7 +1314,7 @@ class TestGetRecipients(TestCaseWithFactory):
4848 team = self.factory.makeTeam(owner, email='team@bar.com')
4849 super_team = self.factory.makeTeam(team)
4850 recipients = get_recipients(super_team)
4851- self.assertEqual(set([team]), set(recipients))
4852+ self.assertEqual({team}, set(recipients))
4853
4854 def test_get_recipients_team_with_unvalidated_address(self):
4855 """Ensure get_recipients handles teams with non-preferred addresses.
4856@@ -1336,7 +1336,7 @@ class TestGetRecipients(TestCaseWithFactory):
4857 def test_get_recipients_person(self):
4858 person = self.factory.makePerson()
4859 recipients = get_recipients(person)
4860- self.assertEqual(set([person]), set(recipients))
4861+ self.assertEqual({person}, set(recipients))
4862
4863 def test_get_recipients_person_with_disabled_account(self):
4864 """Mail is not sent to a direct recipient whose account is disabled."""
4865@@ -1367,9 +1367,9 @@ class TestGetRecipients(TestCaseWithFactory):
4866 super_team_member_team.acceptInvitationToBeMemberOf(
4867 super_team, u'Go Team!')
4868 recipients = list(get_recipients(super_team))
4869- self.assertEqual(set([owner,
4870+ self.assertEqual({owner,
4871 super_team_member_person,
4872- super_team_member_team]),
4873+ super_team_member_team},
4874 set(recipients))
4875
4876 def test_get_recipients_team_with_disabled_owner_account(self):
4877diff --git a/lib/lp/registry/tests/test_person_vocabularies.py b/lib/lp/registry/tests/test_person_vocabularies.py
4878index e10da4d..ea0cfcc 100644
4879--- a/lib/lp/registry/tests/test_person_vocabularies.py
4880+++ b/lib/lp/registry/tests/test_person_vocabularies.py
4881@@ -223,10 +223,10 @@ class TestValidPersonOrTeamPreloading(VocabularyTestBase,
4882
4883 # Remember the current values for checking later, and throw out
4884 # the cache.
4885- expected_nicks = dict(
4886- (person.id, list(person.ircnicknames)) for person in people)
4887- expected_emails = dict(
4888- (person.id, person.preferredemail) for person in people)
4889+ expected_nicks = {
4890+ person.id: list(person.ircnicknames) for person in people}
4891+ expected_emails = {
4892+ person.id: person.preferredemail for person in people}
4893 Store.of(people[0]).invalidate()
4894
4895 results = list(self.searchVocabulary(None, u'foobar'))
4896diff --git a/lib/lp/registry/tests/test_prf_finder.py b/lib/lp/registry/tests/test_prf_finder.py
4897index bbabb95..7b4c024 100644
4898--- a/lib/lp/registry/tests/test_prf_finder.py
4899+++ b/lib/lp/registry/tests/test_prf_finder.py
4900@@ -83,7 +83,7 @@ class FindReleasesDBTestCase(TestCaseWithFactory):
4901 self.factory.makeProductReleaseFile(
4902 productseries=series2, release=file2.productrelease,
4903 filename='foo-2.1.tar.gz')
4904- expected = set(['foo-1.0.tar.gz', 'foo-2.0.tar.gz', 'foo-2.1.tar.gz'])
4905+ expected = {'foo-1.0.tar.gz', 'foo-2.0.tar.gz', 'foo-2.1.tar.gz'}
4906 transaction.commit()
4907 prf = ProductReleaseFinder(self.layer.txn, logging.getLogger())
4908 found = prf.getReleaseFileNames(product.name)
4909diff --git a/lib/lp/registry/tests/test_product.py b/lib/lp/registry/tests/test_product.py
4910index da0be15..656f7ec 100644
4911--- a/lib/lp/registry/tests/test_product.py
4912+++ b/lib/lp/registry/tests/test_product.py
4913@@ -339,8 +339,8 @@ class TestProduct(TestCaseWithFactory):
4914 licenses=[License.MIT])
4915 policies = getUtility(IAccessPolicySource).findByPillar((product,))
4916 grants = getUtility(IAccessPolicyGrantSource).findByPolicy(policies)
4917- expected_grantess = set([product.owner])
4918- grantees = set([grant.grantee for grant in grants])
4919+ expected_grantess = {product.owner}
4920+ grantees = {grant.grantee for grant in grants}
4921 self.assertEqual(expected_grantess, grantees)
4922
4923 def test_open_product_creation_sharing_policies(self):
4924@@ -821,18 +821,18 @@ class TestProduct(TestCaseWithFactory):
4925 product.information_type = InformationType.PROPRIETARY
4926
4927 expected_get_permissions = {
4928- CheckerPublic: set((
4929+ CheckerPublic: {
4930 'active', 'id', 'information_type', 'pillar_category', 'private',
4931- 'userCanLimitedView', 'userCanView',)),
4932- 'launchpad.LimitedView': set((
4933+ 'userCanLimitedView', 'userCanView'},
4934+ 'launchpad.LimitedView': {
4935 'bugtargetdisplayname', 'display_name', 'displayname', 'drivers',
4936 'enable_bug_expiration', 'getBugTaskWeightFunction',
4937 'getOCIProject', 'getSpecification',
4938 'icon', 'logo', 'name', 'official_answers', 'official_anything',
4939 'official_blueprints', 'official_codehosting', 'official_malone',
4940 'owner', 'parent_subscription_target', 'pillar', 'projectgroup',
4941- 'searchTasks', 'title')),
4942- 'launchpad.View': set((
4943+ 'searchTasks', 'title'},
4944+ 'launchpad.View': {
4945 '_getOfficialTagClause', 'visible_specifications',
4946 'valid_specifications', 'api_valid_specifications',
4947 'active_or_packaged_series', 'aliases', 'all_milestones',
4948@@ -894,21 +894,21 @@ class TestProduct(TestCaseWithFactory):
4949 'translationpermission', 'translations_usage', 'ubuntu_packages',
4950 'userCanAlterBugSubscription', 'userCanAlterSubscription',
4951 'userCanEdit', 'userHasBugSubscriptions', 'uses_launchpad',
4952- 'vcs', 'wikiurl')),
4953- 'launchpad.AnyAllowedPerson': set((
4954+ 'vcs', 'wikiurl'},
4955+ 'launchpad.AnyAllowedPerson': {
4956 'addAnswerContact', 'addBugSubscription',
4957 'addBugSubscriptionFilter', 'addSubscription',
4958 'createQuestionFromBug', 'newQuestion', 'removeAnswerContact',
4959- 'removeBugSubscription')),
4960- 'launchpad.Append': set(('newFAQ', )),
4961- 'launchpad.Driver': set(('newSeries', )),
4962- 'launchpad.Edit': set((
4963+ 'removeBugSubscription'},
4964+ 'launchpad.Append': {'newFAQ'},
4965+ 'launchpad.Driver': {'newSeries'},
4966+ 'launchpad.Edit': {
4967 'addOfficialBugTag', 'removeOfficialBugTag',
4968 'setBranchSharingPolicy', 'setBugSharingPolicy',
4969- 'setSpecificationSharingPolicy', 'checkInformationType')),
4970- 'launchpad.Moderate': set((
4971+ 'setSpecificationSharingPolicy', 'checkInformationType'},
4972+ 'launchpad.Moderate': {
4973 'is_permitted', 'license_approved', 'project_reviewed',
4974- 'reviewer_whiteboard', 'setAliases')),
4975+ 'reviewer_whiteboard', 'setAliases'},
4976 }
4977
4978 def test_get_permissions(self):
4979@@ -919,12 +919,12 @@ class TestProduct(TestCaseWithFactory):
4980
4981 def test_set_permissions(self):
4982 expected_set_permissions = {
4983- 'launchpad.BugSupervisor': set((
4984+ 'launchpad.BugSupervisor': {
4985 'bug_reported_acknowledgement', 'bug_reporting_guidelines',
4986 'bugtracker', 'enable_bug_expiration',
4987 'enable_bugfiling_duplicate_search', 'official_bug_tags',
4988- 'official_malone', 'remote_product')),
4989- 'launchpad.Edit': set((
4990+ 'official_malone', 'remote_product'},
4991+ 'launchpad.Edit': {
4992 'answers_usage', 'blueprints_usage', 'bug_supervisor',
4993 'bug_tracking_usage', 'codehosting_usage',
4994 'commercial_subscription', 'description', 'development_focus',
4995@@ -935,15 +935,15 @@ class TestProduct(TestCaseWithFactory):
4996 'official_codehosting', 'owner', 'private',
4997 'programminglang', 'projectgroup',
4998 'releaseroot', 'screenshotsurl', 'sourceforgeproject',
4999- 'summary', 'uses_launchpad', 'wikiurl', 'vcs')),
5000- 'launchpad.Moderate': set((
The diff has been truncated for viewing.

Subscribers

People subscribed via source and target branches

to status/vote changes: