def test_TeamIndexMenu_registry_experts(self): login_celebrity('registry_experts') view = create_view(self.team, '+index') menu = TeamIndexMenu(view) self.assertEqual( ['administer', 'delete', 'join', 'add_my_teams'], [link.name for link in menu.iterlinks() if link.enabled])
def test_getBugTarget_deactivated_project_error(self): project = self.factory.makeProduct(name='fnord') login_celebrity('admin') project.active = False message = "There is no project named 'fnord' registered in Launchpad." self.assertRaisesWithContent(BugTargetNotFound, message, AffectsEmailCommand.getBugTarget, 'fnord')
def test_validatePluralData_invariant_error(self): # Both the number of plural forms and the plural form expression # fields must be provided together, or not at all. language = self.factory.makeLanguage(language_code='qq', name='Queque', pluralforms=None, plural_expression=None) form = { 'field.code': 'qq', 'field.englishname': 'Queque', 'field.nativename': '', 'field.pluralforms': '2', 'field.pluralexpression': '', 'field.visible': True, 'field.direction': 'LTR', 'field.actions.admin': 'Admin Language', } login_celebrity('admin') view = create_initialized_view(language, '+admin', rootsite='translations', form=form) self.assertEqual(1, len(view.errors), view.errors) self.assertEqual( 'The number of plural forms and the plural form expression ' 'must be set together, or not at all.', view.errors[0])
def test_login_celebrity(self): # login_celebrity logs in a celebrity. logout() login_celebrity('vcs_imports') vcs_imports = getUtility(ILaunchpadCelebrities).vcs_imports person = self.getLoggedInPerson() self.assertTrue(person.inTeam(vcs_imports))
def test_status_from_active(self): # The status may change from ACTIVE to DEACTIVATED or SUSPENDED. account = self.factory.makeAccount(status=AccountStatus.ACTIVE) login_celebrity('admin') self.assertCannotTransition(account, [AccountStatus.NOACCOUNT]) self.assertCanTransition( account, [AccountStatus.DEACTIVATED, AccountStatus.SUSPENDED])
def test_query_count(self): # The number of queries required to render the mirror table is # constant in the number of mirrors. person = self.factory.makePerson() distro = self.factory.makeDistribution(owner=person) login_celebrity("admin") distro.supports_mirrors = True login_person(person) distro.mirror_admin = person countries = iter(getUtility(ICountrySet)) def render_mirrors(): text = create_initialized_view( distro, self.view, principal=person).render() self.assertNotIn("We don't know of any", text) return text def create_mirror(): mirror = self.factory.makeMirror( distro, country=next(countries), official_candidate=True) self.configureMirror(mirror) recorder1, recorder2 = record_two_runs( render_mirrors, create_mirror, 10) self.assertThat(recorder2, HasQueryCount.byEquality(recorder1))
def test_license_approved_widget_no_license(self): # Projects without a licence cannot be approved. with person_logged_in(self.product.owner): self.product.licenses = [License.DONT_KNOW] login_celebrity('registry_experts') view = create_initialized_view(self.product, '+index') text = view.license_approved_widget self.assertEqual('Licence required', text)
def test_getBugTarget_deactivated_project_error(self): project = self.factory.makeProduct(name='fnord') login_celebrity('admin') project.active = False message = "There is no project named 'fnord' registered in Launchpad." self.assertRaisesWithContent( BugTargetNotFound, message, AffectsEmailCommand.getBugTarget, 'fnord')
def test_license_approved_widget_prorietary_license(self): # Proprietary projects cannot be approved. with person_logged_in(self.product.owner): self.product.licenses = [License.OTHER_PROPRIETARY] login_celebrity('registry_experts') view = create_initialized_view(self.product, '+index') text = view.license_approved_widget self.assertEqual('Commercial subscription required', text)
def test_status_from_suspended(self): # The status may change from SUSPENDED to DEACTIVATED. account = self.factory.makeAccount() login_celebrity('admin') account.status = AccountStatus.SUSPENDED self.assertCannotTransition( account, [AccountStatus.NOACCOUNT, AccountStatus.ACTIVE]) self.assertCanTransition(account, [AccountStatus.DEACTIVATED])
def test_status_from_noaccount(self): # The status may change from NOACCOUNT to ACTIVE or CLOSED. account = self.factory.makeAccount(status=AccountStatus.NOACCOUNT) login_celebrity('admin') self.assertCannotTransition( account, [AccountStatus.DEACTIVATED, AccountStatus.SUSPENDED]) self.assertCanTransition( account, [AccountStatus.ACTIVE, AccountStatus.CLOSED])
def test_redeem_with_commercial_admin_for_user(self): # A commercial admin can redeem a voucher for a user. project = self.factory.makeProduct() user = project.owner [voucher_id] = self.makeVouchers(user, 1) form = self.makeForm(project, voucher_id) login_celebrity('commercial_admin') view = create_initialized_view(user, '+vouchers', form=form) self.assertRedeem(view, project)
def test_with_commercial_admin_for_user_with_vouchers_and_projects(self): # A commercial admin can see another user's vouchers. user = self.factory.makePerson() login_person(user) self.makeVouchers(user, 1) self.factory.makeProduct(owner=user) login_celebrity('commercial_admin') view = create_initialized_view(user, '+vouchers') self.assertFields(view)
def test_license_approved_widget_any_license(self): # The licence approved widget is is unique to the product. login_celebrity('registry_experts') view = create_initialized_view(self.product, '+index') widget = view.license_approved_widget self.assertEqual('fnord-edit-license-approved', widget.content_box_id) self.assertEqual( canonical_url(self.product, view_name='+review-license'), widget.edit_url)
def test_query_count(self): product = self.factory.makeProduct() removeSecurityProxy(product).official_blueprints = True self.factory.makeSpecification(product=product) limit = BrowsesWithQueryLimit(37, product.owner, rootsite='blueprints') self.assertThat(product, limit) login_celebrity('admin') [self.factory.makeSpecification(product=product) for i in range(4)] self.assertThat(product, limit)
def test_status_from_deactivated(self): # The status may change from DEACTIVATED to ACTIVATED or CLOSED. account = self.factory.makeAccount() login_celebrity('admin') account.setStatus(AccountStatus.DEACTIVATED, None, 'gbcw') self.assertCannotTransition( account, [AccountStatus.NOACCOUNT, AccountStatus.SUSPENDED]) self.assertCanTransition( account, [AccountStatus.ACTIVE, AccountStatus.CLOSED])
def test_widget_id_for_name_dots(self): # Dots are replaced with dashes to make a valid CSS Id. login_celebrity('registry_experts') self.product.name = 'fnord.dom' view = create_initialized_view(self.product, '+index') self.assertEqual('fnord-dom-edit-active', view.active_widget.content_box_id) self.assertEqual('fnord-dom-edit-project-reviewed', view.project_reviewed_widget.content_box_id) self.assertEqual('fnord-dom-edit-license-approved', view.license_approved_widget.content_box_id)
def test_cannot_merge_person_with_ppa(self): # A person with a PPA cannot be merged. login_celebrity('admin') self.dupe_person.createPPA() view = self.getView() self.assertEqual( [html_escape( u"dupe-person has a PPA that must be deleted before it can " "be merged. It may take ten minutes to remove the deleted " "PPA's files.")], view.errors)
def test_cannot_merge_person_with_ppa(self): # A person with a PPA cannot be merged. login_celebrity('admin') self.dupe_person.createPPA() view = self.getView() self.assertEqual([ html_escape( u"dupe-person has a PPA that must be deleted before it can " "be merged. It may take ten minutes to remove the deleted " "PPA's files.") ], view.errors)
def test_cannot_merge_person_with_private_branches(self): # A team or user with a private branches cannot be merged. self.factory.makeBranch( owner=self.dupe, information_type=InformationType.USERDATA) login_celebrity('registry_experts') view = create_initialized_view( self.person_set, '+requestmerge', form=self.getForm()) self.assertEqual( [u"dupe owns private branches that must be deleted or " "transferred to another owner first."], view.errors)
def test_cannot_merge_person_with_private_git_repositories(self): # A team or user with a private Git repository cannot be merged. self.factory.makeGitRepository( owner=self.dupe, information_type=InformationType.USERDATA) login_celebrity('registry_experts') view = create_initialized_view(self.person_set, '+requestmerge', form=self.getForm()) self.assertEqual([ u"dupe owns private Git repositories that must be deleted or " "transferred to another owner first." ], view.errors)
def test_cannot_merge_person_with_ppas(self): # A team with a PPA cannot be merged. login_celebrity('admin') self.dupe.createPPA() login_celebrity('registry_experts') view = create_initialized_view( self.person_set, '+requestmerge', form=self.getForm()) self.assertEqual( [html_escape( u"dupe has a PPA that must be deleted before it can be " "merged. It may take ten minutes to remove the deleted PPA's " "files.")], view.errors)
def test_cannot_merge_team_with_ppa(self): # A team with a PPA cannot be merged. login_celebrity('admin') self.dupe_team.membership_policy = TeamMembershipPolicy.MODERATED self.dupe_team.createPPA() login_celebrity('registry_experts') view = self.getView() self.assertEqual( [html_escape( u"dupe-team has a PPA that must be deleted before it can be " "merged. It may take ten minutes to remove the deleted PPA's " "files.")], view.errors)
def test_cannot_merge_team_with_ppa(self): # A team with a PPA cannot be merged. login_celebrity('admin') self.dupe_team.membership_policy = TeamMembershipPolicy.MODERATED self.dupe_team.createPPA() login_celebrity('registry_experts') view = self.getView() self.assertEqual([ html_escape( u"dupe-team has a PPA that must be deleted before it can be " "merged. It may take ten minutes to remove the deleted PPA's " "files.") ], view.errors)
def test_widget_id_for_name_dots(self): # Dots are replaced with dashes to make a valid CSS Id. login_celebrity('registry_experts') self.product.name = 'fnord.dom' view = create_initialized_view(self.product, '+index') self.assertEqual( 'fnord-dom-edit-active', view.active_widget.content_box_id) self.assertEqual( 'fnord-dom-edit-project-reviewed', view.project_reviewed_widget.content_box_id) self.assertEqual( 'fnord-dom-edit-license-approved', view.license_approved_widget.content_box_id)
def test_cannot_merge_person_with_ppas(self): # A team with a PPA cannot be merged. login_celebrity('admin') self.dupe.createPPA() login_celebrity('registry_experts') view = create_initialized_view(self.person_set, '+requestmerge', form=self.getForm()) self.assertEqual([ html_escape( u"dupe has a PPA that must be deleted before it can be " "merged. It may take ten minutes to remove the deleted PPA's " "files.") ], view.errors)
def test_searchForTerms_commercial_admin(self): # Users with launchpad.Commercial can search for any active project. expert = login_celebrity('commercial_admin') self.vocab = CommercialProjectsVocabulary(context=expert) self.assertEqual(1, len(self.vocab.searchForTerms(u'open-widget'))) self.assertEqual( 0, len(self.vocab.searchForTerms(u'norwegian-blue-widget')))
def test_admin_sees_visibility_field(self): personset = getUtility(IPersonSet) admin = login_celebrity('admin') view = create_initialized_view( personset, name=self.view_name, principal=admin) self.assertIn( 'visibility', [field.__name__ for field in view.form_fields])
def test_redeem_twice_causes_error(self): # If a voucher is redeemed twice, the second attempt is rejected. commercial_admin = login_celebrity('commercial_admin') voucher_id_1, voucher_id_2 = self.makeVouchers(commercial_admin, 2) project_1 = self.factory.makeProduct(name='p1') project_2 = self.factory.makeProduct(name='p2') url = canonical_url(commercial_admin, view_name='+vouchers') browser = self.getUserBrowser(url, commercial_admin) # A second browser opens the +vouchers page before the first browser # attempts to redeem the voucher. browser2 = self.getUserBrowser(url, commercial_admin) browser.getControl( 'Select the project you wish to subscribe').value = 'p1' browser.getControl( 'Select a voucher').getControl(voucher_id_1).selected = True browser.getControl('Redeem').click() with person_logged_in(commercial_admin): self.assertIsNotNone(project_1.commercial_subscription) browser2.getControl( 'Select the project you wish to subscribe').value = 'p2' browser2.getControl( 'Select a voucher').getControl(voucher_id_1).selected = True browser2.getControl('Redeem').click() with person_logged_in(commercial_admin): self.assertIsNone(project_2.commercial_subscription) error_messages = find_tags_by_class(browser2.contents, 'message') self.assertEqual(extract_text(error_messages[1]), 'Invalid value')
def test_page_batched_changes(self): self.makeFeatureFlagChanges() member = login_celebrity('admin') view = create_view( self.root, name='+feature-changelog', principal=member) tag = find_tag_by_id(view.render(), 'changes') self.assertTrue('table', tag.name)
def test_admin_can_subscribe_anyone(self): # a launchpad admin can create a structural subscription for # anyone admin = login_celebrity('admin') self.assertIsInstance( self.target.addBugSubscription(self.ordinary_subscriber, admin), StructuralSubscription)
def test_redeem_twice_causes_error(self): # If a voucher is redeemed twice, the second attempt is rejected. commercial_admin = login_celebrity('commercial_admin') voucher_id_1, voucher_id_2 = self.makeVouchers(commercial_admin, 2) project_1 = self.factory.makeProduct(name='p1') project_2 = self.factory.makeProduct(name='p2') url = canonical_url(commercial_admin, view_name='+vouchers') browser = self.getUserBrowser(url, commercial_admin) # A second browser opens the +vouchers page before the first browser # attempts to redeem the voucher. browser2 = self.getUserBrowser(url, commercial_admin) browser.getControl( 'Select the project you wish to subscribe').value = 'p1' browser.getControl('Select a voucher').getControl( voucher_id_1).selected = True browser.getControl('Redeem').click() with person_logged_in(commercial_admin): self.assertIsNotNone(project_1.commercial_subscription) browser2.getControl( 'Select the project you wish to subscribe').value = 'p2' browser2.getControl('Select a voucher').getControl( voucher_id_1).selected = True browser2.getControl('Redeem').click() with person_logged_in(commercial_admin): self.assertIsNone(project_2.commercial_subscription) error_messages = find_tags_by_class(browser2.contents, 'message') self.assertEqual(extract_text(error_messages[1]), 'Invalid value')
def test_admin(self): distribution = self.factory.makeDistribution() admin = login_celebrity('admin') create_initialized_view( distribution, '+admin', principal=admin, form={ 'field.official_packages': 'on', 'field.supports_ppas': '******', 'field.supports_mirrors': 'on', 'field.actions.change': 'change'}) self.assertThat( distribution, MatchesStructure.byEquality( official_packages=True, supports_ppas=True, supports_mirrors=True)) create_initialized_view( distribution, '+admin', principal=admin, form={ 'field.official_packages': '', 'field.supports_ppas': '', 'field.supports_mirrors': '', 'field.actions.change': 'change'}) self.assertThat( distribution, MatchesStructure.byEquality( official_packages=False, supports_ppas=False, supports_mirrors=False))
def login_for_code_imports(): """Login as a member of the vcs-imports team. CodeImports are currently hidden from regular users currently. Members of the vcs-imports team and can access the objects freely. """ return login_celebrity('vcs_imports')
def test_searchForTerms_commercial_admin(self): # Users with launchpad.Commercial can search for any active project. expert = login_celebrity('commercial_admin') self.vocab = CommercialProjectsVocabulary(context=expert) self.assertEqual( 1, len(self.vocab.searchForTerms(u'open-widget'))) self.assertEqual( 0, len(self.vocab.searchForTerms(u'norwegian-blue-widget')))
def test_contains_commercial_admin(self): # The vocabulary contains all active projects for commercial. other_project = self.factory.makeProduct() expert = login_celebrity('commercial_admin') self.vocab = CommercialProjectsVocabulary(context=expert) self.assertIs(True, other_project in self.vocab) self.assertIs(False, self.deactivated_project in self.vocab) self.assertIs(True, self.maintained_project in self.vocab)
def test_page_batched_changes(self): self.makeFeatureFlagChanges() member = login_celebrity('admin') view = create_view(self.root, name='+feature-changelog', principal=member) tag = find_tag_by_id(view.render(), 'changes') self.assertTrue('table', tag.name)
def test_admin_sees_visibility_field(self): personset = getUtility(IPersonSet) admin = login_celebrity('admin') view = create_initialized_view(personset, name=self.view_name, principal=admin) self.assertIn('visibility', [field.__name__ for field in view.form_fields])
def setUp(self): super(TestDistroAddView, self).setUp() self.owner = self.factory.makePerson() self.registrant = self.factory.makePerson() self.simple_user = self.factory.makePerson() self.admin = login_celebrity('admin') self.distributionset = getUtility(IDistributionSet) self.all_processors = getUtility(IProcessorSet).getAll()
def setUp(self): super(TestDistroAddView, self).setUp() self.owner = self.factory.makePerson() self.registrant = self.factory.makePerson() self.simple_user = self.factory.makePerson() self.admin = login_celebrity('admin') self.distributionset = getUtility(IDistributionSet) self.restricted_processors = getUtility(IProcessorSet).getRestricted()
def test_redeem_with_commercial_admin(self): # The fields are setup if the commercial admin has vouchers. commercial_admin = login_celebrity('commercial_admin') [voucher_id] = self.makeVouchers(commercial_admin, 1) project = self.factory.makeProduct() form = self.makeForm(project, voucher_id) view = create_initialized_view( commercial_admin, '+vouchers', form=form) self.assertRedeem(view, project)
def test_create_team(self): personset = getUtility(IPersonSet) team_name = self.factory.getUniqueString() form = { 'field.name': team_name, 'field.display_name': 'New Team', 'field.visibility': 'PRIVATE', 'field.membership_policy': 'RESTRICTED', 'field.actions.create': 'Create', } login_celebrity('admin') create_initialized_view(personset, name=self.view_name, form=form) team = personset.getByName(team_name) self.assertIsNotNone(team) self.assertEqual('New Team', team.displayname) self.assertEqual(PersonVisibility.PRIVATE, team.visibility) self.assertEqual(TeamMembershipPolicy.RESTRICTED, team.membership_policy)
def test_setContactAddress_after_purged_mailing_list_and_rename(self): # This is the rare case where a list is purged for a team rename, # then the contact address is set/unset sometime afterwards. # The old mailing list address belongs the team, but not the list. # 1. Create then purge a mailing list. self.createMailingListAndGetAddress() mailing_list = self.team.mailing_list mailing_list.deactivate() mailing_list.transitionToStatus(MailingListStatus.INACTIVE) mailing_list.purge() transaction.commit() # 2. Rename the team. login_celebrity('admin') self.team.name = 'beta' login_person(self.team.teamowner) # 3. Set the contact address. self.team.setContactAddress(None) self.assertEqual(None, self.team.preferredemail) self.assertEqual([], self.getAllEmailAddresses())
def test_create_team(self): personset = getUtility(IPersonSet) team_name = self.factory.getUniqueString() form = { 'field.name': team_name, 'field.displayname': 'New Team', 'field.visibility': 'PRIVATE', 'field.membership_policy': 'RESTRICTED', 'field.actions.create': 'Create', } login_celebrity('admin') create_initialized_view( personset, name=self.view_name, form=form) team = personset.getByName(team_name) self.assertIsNotNone(team) self.assertEqual('New Team', team.displayname) self.assertEqual(PersonVisibility.PRIVATE, team.visibility) self.assertEqual( TeamMembershipPolicy.RESTRICTED, team.membership_policy)
def test_reassign_distro_page_title(self): # Reassign should say maintainer instead of owner. admin = login_celebrity('admin') distribution = self.factory.makeDistribution( name="boobuntu", owner=self.owner, registrant=self.registrant) view = create_initialized_view( distribution, '+reassign', principal=admin, method='GET') header_match = soupmatchers.HTMLContains( soupmatchers.Tag( 'Header should say maintainer (not owner)', 'h1', text='Change the maintainer of Boobuntu')) self.assertThat(view.render(), header_match)
def test_pending_vouchers_excluded(self): # Vouchers pending redemption in Salesforce are not included in choice. commercial_admin = login_celebrity('commercial_admin') voucher_id_1, voucher_id_2 = self.makeVouchers(commercial_admin, 2) project_1 = self.factory.makeProduct() self.factory.makeCommercialSubscription( project_1, False, 'pending-' + voucher_id_1) view = create_initialized_view(commercial_admin, '+vouchers') vouchers = list(view.widgets['voucher'].vocabulary) # Only voucher2 in vocab since voucher1 is pending redemption. self.assertEqual(1, len(vouchers)) self.assertEqual(voucher_id_2, vouchers[0].token)
def test_getSubscribers_only_active_members_are_subscribers(self): former_member = self.factory.makePerson() pending_member = self.factory.makePerson() active_member = self.active_member = self.factory.makePerson() # Each of our members want to be subscribed to a team's mailing list # whenever they join the team. login_celebrity('admin') former_member.mailing_list_auto_subscribe_policy = ( MailingListAutoSubscribePolicy.ALWAYS) active_member.mailing_list_auto_subscribe_policy = ( MailingListAutoSubscribePolicy.ALWAYS) pending_member.mailing_list_auto_subscribe_policy = ( MailingListAutoSubscribePolicy.ALWAYS) self.team.membership_policy = TeamMembershipPolicy.MODERATED pending_member.join(self.team) self.team.addMember(former_member, reviewer=self.team.teamowner) former_member.leave(self.team) self.team.addMember(active_member, reviewer=self.team.teamowner) # Even though our 3 members want to subscribe to the team's mailing # list, only the active member is considered a subscriber. self.assertEqual( [active_member], list(self.mailing_list.getSubscribers()))