def test_citizen_has_multiple_unconfirmed_registrations(self): # national id has multiple unconfirmed registration associated with it RegistrationFactory(citizen=self.citizen) # unconfirmed registration RegistrationFactory(citizen=self.citizen) # unconfirmed registration self.receive(self.good_nid, self.conn, fields=self.fields) self.assertEqual(self.get_last_response_code(), constants.VOTER_QUERY_NOT_REGISTERED)
def test_phone_has_maximum_registrations(self): phone_number = '12345' reg = RegistrationFactory(sms__from_number=phone_number, archive_time=None) self.assertFalse(reg.phone_has_maximum_registrations) RegistrationFactory(sms__from_number=phone_number, archive_time=None) self.assertTrue(reg.phone_has_maximum_registrations)
def test_citizen_has_mutiple_unconfirmed_registration(self): # A citizen with multiple unconfirmed registration is treated the same as # one with 1 unconfirmed registrations RegistrationFactory(citizen=self.citizen) RegistrationFactory(citizen=self.citizen) result = process_registration_lookup(self.good_nid, self.sms) self.assertEqual(result.message_code, constants.VOTER_QUERY_NOT_REGISTERED)
def test_unique_registration(self): # Undeleted, confirmed registrations must be unique on citizen citizen = CitizenFactory() RegistrationFactory(citizen=citizen, deleted=False, archive_time=None) RegistrationFactory(citizen=citizen, deleted=True) RegistrationFactory(citizen=citizen, archive_time=now()) with self.assertRaises(IntegrityError): RegistrationFactory(citizen=citizen, deleted=False, archive_time=None)
def test_registration_unlocked(self): reg = RegistrationFactory() case = Case() self.assertFalse(case.registration_unlocked()) case.registration = reg self.assertFalse(case.registration_unlocked()) reg.unlocked_until = now() + datetime.timedelta(hours=1) self.assertTrue(case.registration_unlocked()) case.relock_registration() self.assertFalse(case.registration_unlocked()) case.registration = None self.assertFalse(case.registration_unlocked())
def test_can_reregister_after_reg_capability_removed(self): registration = RegistrationFactory(archive_time=None) RegistrationFactory(archive_time=None, deleted=True) # Inactivate the center registration.registration_center.reg_open = False registration.registration_center.save() # Process a new registration result = process_registration_request( center_id=self.center.center_id, national_id=registration.citizen.national_id, sms=registration.sms) # We returned the 'successful center change' message self.assertEqual(result.message_code, constants.MESSAGE_1) # Only 1 registration present regs = models.Registration.objects.filter(citizen=registration.citizen) self.assertEqual(len(regs), 1)
def test_citizen_has_no_confirmed_registrations(self): # A citizen with unconfirmed registration(s) should be informed that he # is not registered (VOTER_QUERY_NOT_REGISTERED) RegistrationFactory(citizen=self.citizen, archive_time=now()) result = process_registration_lookup(self.good_nid, self.sms) self.assertEqual(result.message_code, constants.VOTER_QUERY_NOT_REGISTERED)
def test_citizen_is_registered(self): # Citizen correctly registered will be informed about the Election Center # where they are currently registered to vote. RegistrationFactory(citizen=self.citizen, archive_time=None) result = process_registration_lookup(self.good_nid, self.sms) self.assertEqual(result.message_code, constants.VOTER_QUERY_REGISTERED_AT)
def test_removing_reg_capability_doesnt_affect_registrations(self): registration = RegistrationFactory(archive_time=None) # Disallow registrations registration.registration_center.reg_open = False registration.registration_center.save() # Registration is still there regs = models.Registration.objects.filter( registration_center=registration.registration_center) self.assertEqual(len(regs), 1)
def test_copy_center_not_mistaken_for_no_registration_center(self): """ensure that a center that's a copy of a center with registrants is recognized as such""" RegistrationFactory(registration_center=self.center, archive_time=None) center_id = self.copy_center.center_id self.input_arguments['center_ids'] = [center_id] call_command(self.command_name, self.phase, center_ids=str(center_id), output_root=self.output_path)
class RegistrationArchivingTest(TestCase): def setUp(self): # Start with a confirmed registration self.reg = RegistrationFactory(archive_time=None) def test_save_with_archive_version(self): orig_change_count = self.reg.change_count self.reg.change_count = 99 self.reg.save_with_archive_version() # See what's in the DB for this record cur_reg = Registration.objects.get(citizen=self.reg.citizen) self.assertEqual(99, cur_reg.change_count) # See if there's an archive record now archive = Registration.objects.archived().get(citizen=self.reg.citizen) self.assertNotEqual(archive.pk, self.reg.pk) self.assertEqual(orig_change_count, archive.change_count) self.assertTrue(archive.archive_time <= now()) # And the times match self.assertEqual(archive.archive_time, cur_reg.creation_date)
def test_register_after_unconfirmed_registrations(self): # We might have unconfirmed registrations due to previous changes. # Create 2 registrations for this Citizen RegistrationFactory(citizen=self.citizen, archive_time=now()) RegistrationFactory(citizen=self.citizen, archive_time=now(), deleted=True) RegistrationFactory(citizen=self.citizen, archive_time=None, deleted=True) RegistrationFactory(citizen=self.citizen, archive_time=None) # Process another registration update process_registration_request(sms=SMSFactory(), national_id=self.citizen.national_id, center_id=self.center.center_id) # There should be only one confirmed registration registrations = models.Registration.objects.filter( citizen=self.citizen) self.assertEqual(1, registrations.count())
def test_no_office_center_can_be_forgiven(self): """ensure that a center that has no office is accepted when --forgive-no-office is True""" # Give it a registration so it doesn't raise an error. RegistrationFactory(registration_center=self.no_office_center, archive_time=None) center_id = self.no_office_center.center_id self.input_arguments['center_ids'] = [center_id] self.input_arguments['forgive_no_office'] = True call_command(self.command_name, self.phase, center_ids=str(center_id), forgive_no_office=True, output_root=self.output_path)
def test_phone_reaches_only_one_more(self): number = '12345678' RegistrationFactory(sms__from_number=number, archive_time=None) new_sms = SMSFactory(from_number=number) result = process_registration_request( sms=new_sms, national_id=self.citizen.national_id, center_id=self.center.center_id) self.assertEqual(result.message_code, constants.ONE_MORE_REGISTRATION_ON_PHONE) models.Registration.objects.get(citizen=self.citizen)
def test_phone_has_max_registrations(self): number = '12345678' RegistrationFactory(sms__from_number=number, archive_time=None) new_sms = SMSFactory(from_number=number) result = process_registration_request( sms=new_sms, national_id=self.citizen.national_id, center_id=self.center.center_id) self.assertEqual(result.message_code, constants.TOO_MANY_REGISTRATIONS_ON_PHONE) with self.assertRaises(models.Registration.DoesNotExist): models.Registration.objects.get(citizen=self.citizen)
def test_registration_archived(self): citizen = CitizenFactory(fbr_number=1234) registration = RegistrationFactory(citizen=citizen, archive_time=now()) data = { 'national_id': str(citizen.national_id), 'fbr_number': citizen.fbr_number } data.update(self.captcha) rsp = self.client.post(self.url, data=data) self.assertEqual(200, rsp.status_code) content = rsp.content.decode('utf-8') self.assertIn("is not registered", content) self.assertNotIn("is registered at", content) self.assertNotIn(registration.registration_center.name, content)
def post(instance, create, extracted, **kwargs): instance.first_name = random.choice(person_names) instance.father_name = random.choice(person_names) instance.grandfather_name = random.choice(person_names) instance.family_name = random.choice(person_names) instance.mother_name = random.choice(person_names) if kwargs['center']: # Register this voter to this center reg_kwargs = dict(citizen=instance, registration_center=kwargs['center'], archive_time=None) if 'sms' in kwargs and kwargs['sms']: reg_kwargs['sms'] = kwargs['sms'] RegistrationFactory(**reg_kwargs)
def test_fbr_number_mismatch(self): citizen = CitizenFactory(fbr_number=1234) RegistrationFactory(citizen=citizen, archive_time=None) data = { 'national_id': str(citizen.national_id), 'fbr_number': '2345678' } data.update(self.captcha) rsp = self.client.post(self.url, data=data) self.assertEqual(200, rsp.status_code) context = rsp.context self.assertIn('form', context) form = context['form'] self.assertTrue(form.errors) content = rsp.content.decode('utf-8') self.assertIn(get_message(constants.FBRN_MISMATCH).msg, content)
def setUp(self): self.from_center_1 = RegistrationCenterFactory() self.from_center_2 = RegistrationCenterFactory() self.center_3 = RegistrationCenterFactory() self.to_center = RegistrationCenterFactory() # these should be moved self.reg1 = RegistrationFactory(registration_center=self.from_center_1, archive_time=None) self.reg2 = RegistrationFactory(registration_center=self.from_center_2, archive_time=None) # these should not self.reg3 = RegistrationFactory(registration_center=self.center_3, archive_time=None) self.reg4 = RegistrationFactory(registration_center=self.to_center, archive_time=None) self.changeset = ChangesetFactory( status=Changeset.STATUS_APPROVED, change=Changeset.CHANGE_CENTER, target_center=self.to_center )
def test_citizen_registered(self): # citizen has been registered RegistrationFactory(citizen=self.citizen, registration_center=self.center, archive_time=None) # let's query for the registration msg = u"{nid}".format(nid=self.good_nid) self.receive(msg, self.conn, fields=self.fields) self.assertEqual(self.get_last_response_code(), constants.VOTER_QUERY_REGISTERED_AT) context = { "person": unicode(self.citizen), "centre": self.center.name, "code": self.center.center_id } expected = self.translate(constants.VOTER_QUERY_REGISTERED_AT, context) # Arabic self.assertEqual(self.get_last_response_message(), expected)
def test_attempt_update_wrong_from_number_same_center( self, registration_open): # create a valid registration sms = SMSFactory(from_number=self.number, citizen=self.citizen) RegistrationFactory(citizen=self.citizen, registration_center=self.center, archive_time=None, sms=sms) # try to register at same center with a new number new_number = '919-888-8888' msg = "{nid}#{center}".format(nid=self.good_nid, center=self.center.center_id) new_conn = self.create_connection(data={'identity': new_number}) self.receive(msg, new_conn, fields=self.fields) # message should have the existing number in it (not new_number) context = {'centre': self.center.name, 'number': self.number[-4:]} expected = self.translate(constants.MESSAGE_2, context=context) # arabic self.assertEqual(self.get_last_response_message(), expected)
def setUp(self): # Start with a confirmed registration self.reg = RegistrationFactory(archive_time=None)
class ExecuteCenterChangeTest(TestCase): """ Test executeing center change changesets. Each test will set up a change in a different way but that ought to have the same results. Then we'll try to roll back the change, after having one voter change their registration, and check those results. """ def setUp(self): self.from_center_1 = RegistrationCenterFactory() self.from_center_2 = RegistrationCenterFactory() self.center_3 = RegistrationCenterFactory() self.to_center = RegistrationCenterFactory() # these should be moved self.reg1 = RegistrationFactory(registration_center=self.from_center_1, archive_time=None) self.reg2 = RegistrationFactory(registration_center=self.from_center_2, archive_time=None) # these should not self.reg3 = RegistrationFactory(registration_center=self.center_3, archive_time=None) self.reg4 = RegistrationFactory(registration_center=self.to_center, archive_time=None) self.changeset = ChangesetFactory( status=Changeset.STATUS_APPROVED, change=Changeset.CHANGE_CENTER, target_center=self.to_center ) def doit(self): # Execute the changeset and check out the results self.changeset.full_clean() citizens = self.changeset.get_citizens_to_change() self.assertIn(self.reg1.citizen, citizens) self.assertIn(self.reg2.citizen, citizens) self.assertNotIn(self.reg3.citizen, citizens) # citizen4 might or might not be in the 'get_citizens_to_change' result depending # on the test self.changeset.execute() self.assertEqual(self.to_center, refresh_model(self.reg1).registration_center) # There should also be an archived registration that is unchanged archives = Registration.objects.archived() self.assertEqual(1, archives.filter(citizen=self.reg1.citizen, registration_center=self.from_center_1).count()) self.assertEqual(self.to_center, refresh_model(self.reg2).registration_center) # There should also be an archived registration that is unchanged self.assertEqual(1, archives.filter(citizen=self.reg2.citizen, registration_center=self.from_center_2).count()) # reg 3 not moved, was at center 3 self.assertEqual(self.center_3, refresh_model(self.reg3).registration_center) # No archived center self.assertFalse(archives.filter(citizen=self.reg3.citizen).exists()) # reg 4 not moved, but was already at to_center self.assertEqual(self.to_center, refresh_model(self.reg4).registration_center) # No archived center self.assertFalse(archives.filter(citizen=self.reg4.citizen).exists()) changeset = refresh_model(self.changeset) if self.changeset.how_to_select == Changeset.SELECT_UPLOADED_NIDS: # Ugh - this was the only test where we could "add" citizen4 self.assertEqual(Changeset.STATUS_PARTIALLY_SUCCESSFUL, changeset.status) else: self.assertEqual(Changeset.STATUS_SUCCESSFUL, changeset.status) changes = changeset.change_records self.assertEqual(1, changes.filter(citizen=self.reg1.citizen, changed=True).count()) self.assertEqual(1, changes.filter(citizen=self.reg2.citizen, changed=True).count()) # self.reg3 shouldn't be mentioned, they weren't in the set to be changed self.assertFalse(changes.filter(citizen=self.reg3.citizen).exists()) # self.reg4 might or might not have a change record, but if it does, changed # should be False self.assertFalse(changes.filter(citizen=self.reg4.citizen, changed=True).exists()) # the citizen from self.reg2 moves themselves to another center, so they # should not be rolled back self.reg2.registration_center = self.center_3 self.reg2.save() # Do a rollback rollback = ChangesetFactory( status=Changeset.STATUS_APPROVED, change=Changeset.CHANGE_ROLLBACK, how_to_select=Changeset.SELECT_OTHER_CHANGESET, other_changeset=changeset, ) rollback.full_clean() citizens = list(rollback.get_citizens_to_change()) self.assertIn(self.reg1.citizen, citizens) self.assertIn(self.reg2.citizen, citizens) # In the list, but we won't change them self.assertNotIn(self.reg3.citizen, citizens) self.assertNotIn(self.reg4.citizen, citizens) # was not changed rollback.execute() rollback = refresh_model(rollback) self.assertEqual(Changeset.STATUS_PARTIALLY_SUCCESSFUL, rollback.status) changeset = refresh_model(changeset) self.assertEqual(Changeset.STATUS_ROLLED_BACK, changeset.status) self.assertEqual(rollback, changeset.rollback_changeset) self.assertEqual(self.from_center_1, refresh_model(self.reg1).registration_center) # reg1 was changed then changed back, so there should be two archived versions self.assertEqual(2, archives.filter(citizen=self.reg1.citizen).count()) self.assertEqual(1, archives.filter(citizen=self.reg1.citizen, registration_center=self.from_center_1).count()) self.assertEqual(1, archives.filter(citizen=self.reg1.citizen, registration_center=self.to_center).count()) self.assertEqual(self.center_3, refresh_model(self.reg2).registration_center) self.assertEqual(1, rollback.change_records.filter(citizen=self.reg1.citizen, changed=True) .count()) self.assertEqual(1, rollback.change_records.filter(citizen=self.reg2.citizen, changed=False) .count()) def test_execute_center_change_by_center_and_partial_rollback(self): # test selecting voters by center self.changeset.how_to_select = Changeset.SELECT_CENTERS self.changeset.save() self.changeset.selected_centers.add(self.from_center_1, self.from_center_2) self.doit() def test_execute_center_change_by_upload_and_partial_rollback(self): # test selecting voters by upload self.changeset.how_to_select = Changeset.SELECT_UPLOADED_NIDS self.changeset.save() self.changeset.selected_citizens.add(self.reg1.citizen, self.reg2.citizen, self.reg4.citizen) self.doit() def test_execute_center_change_by_another_changeset_and_partial_rollback(self): # test selecting voters from another changeset first_changeset = ChangesetFactory(status=Changeset.STATUS_SUCCESSFUL) ChangeRecordFactory(changeset=first_changeset, citizen=self.reg1.citizen, changed=True) ChangeRecordFactory(changeset=first_changeset, citizen=self.reg2.citizen, changed=True) # reg3 had a change record, but was not changed ChangeRecordFactory(changeset=first_changeset, citizen=self.reg3.citizen, changed=False) # reg4 doesn't show up at all self.changeset.how_to_select = Changeset.SELECT_OTHER_CHANGESET self.changeset.other_changeset = first_changeset self.changeset.save() self.doit()
def setUp(self): self.registrations_per_center = 4 self.oil_center_period_1_voters = 1 self.oil_center_period_2_voters = 2 self.offices = [OfficeFactory(region=Office.REGION_EAST), OfficeFactory(region=Office.REGION_WEST)] # Note: An oil center doesn't normally allow registrations, but it does so for # this testcase. self.oil_center = RegistrationCenterFactory(office=self.offices[0], center_type=RegistrationCenter.Types.OIL) # !reg_open won't affect election day counts but it will affect whether # or not any registrations are found self.inactive_for_reg_center = RegistrationCenterFactory(office=self.offices[1], reg_open=False) self.centers = [self.oil_center, RegistrationCenterFactory(office=self.offices[0]), RegistrationCenterFactory(office=self.offices[0]), RegistrationCenterFactory(office=self.offices[1]), self.inactive_for_reg_center, ] copy_center = RegistrationCenterFactory(office=self.offices[1], copy_of=self.centers[3]) self.centers.append(copy_center) self.election_decoy_before = ElectionFactory( name_english='decoy before', name_arabic='decoy before (ar)', polling_start_time=now() - timedelta(days=10), polling_end_time=now() - timedelta(days=9), ) self.election = ElectionFactory( name_english='%s election' % type(self).__name__, name_arabic='not Arabic', polling_start_time=now() - timedelta(hours=2), polling_end_time=now() + timedelta(hours=2), ) self.election_decoy_after = ElectionFactory( name_english='decoy after', name_arabic='decoy after (ar)', polling_start_time=now() + timedelta(days=9), polling_end_time=now() + timedelta(days=10), ) self.center_opens = [] for center in self.centers: if center != self.centers[1]: self.center_opens.append(CenterOpenFactory(election=self.election, registration_center=center)) # CenterOpen may refer to a deleted center. Make sure that we don't find those self.deleted_center = RegistrationCenterFactory(office=self.offices[0], deleted=True) self.center_open_referring_to_deleted_center = CenterOpenFactory( election=self.election, registration_center=self.deleted_center) # Performance enhancement: this dummy person and SMS allow me to avoid creation of two # spurious objects for each registration I create. self.citizen = CitizenFactory() self.sms = SMSFactory(citizen=self.citizen) # Create registrations, but be careful not to create any at the copy center # or at the center which doesn't support registrations. self.registrations = [] for center in self.centers: if center.reg_open and not center.copy_of: self.registrations += \ RegistrationFactory.create_batch(self.registrations_per_center, citizen=self.citizen, sms=self.sms, registration_center=center) # These reports include quirks such as multiple reports for a center (very common in real # life), a missing final period report, and multiple reports for the same center & period. self.reports = [ PollingReportFactory(election=self.election, registration_center=self.oil_center, period_number=FIRST_PERIOD_NUMBER, num_voters=self.oil_center_period_1_voters), PollingReportFactory(election=self.election, registration_center=self.oil_center, period_number=FIRST_PERIOD_NUMBER + 1, num_voters=self.oil_center_period_2_voters), PollingReportFactory(election=self.election, registration_center=self.centers[2], period_number=FIRST_PERIOD_NUMBER, num_voters=1), # The next two reports are for the same center & period with different num_voters # to exercise the code that sorts by modification_date. PollingReportFactory(election=self.election, registration_center=self.centers[2], period_number=FIRST_PERIOD_NUMBER + 1, num_voters=4), PollingReportFactory(election=self.election, registration_center=self.centers[2], period_number=FIRST_PERIOD_NUMBER + 1, num_voters=6), PollingReportFactory(election=self.election, registration_center=self.centers[3], period_number=FIRST_PERIOD_NUMBER, num_voters=1), PollingReportFactory(election=self.election, registration_center=self.centers[3], period_number=FIRST_PERIOD_NUMBER + 1, num_voters=4), # This report for a deleted center should be ignored PollingReportFactory(election=self.election, registration_center=self.deleted_center, period_number=FIRST_PERIOD_NUMBER + 1, num_voters=50), PollingReportFactory(election=self.election, registration_center=self.inactive_for_reg_center, period_number=FIRST_PERIOD_NUMBER + 1, num_voters=50), # This report for a copy center should count towards the original/parent center PollingReportFactory(election=self.election, registration_center=copy_center, period_number=LAST_PERIOD_NUMBER, num_voters=1), ] self.result = generate_election_day_hq_reports(self.election) # Create an alternate result which reflects that the "oil center" is # marked inactive for this election. self.inactive_on_election = CenterClosedForElection( registration_center=self.oil_center, election=self.election ) self.inactive_on_election.full_clean() self.inactive_on_election.save() self.result_with_inactive = generate_election_day_hq_reports(self.election)
def test_block_citizen(self): citizen = CitizenFactory() RegistrationFactory(citizen=citizen, archive_time=None) self.assertIsNotNone(citizen.registration) citizen.block() self.assertIsNone(citizen.registration)
def test_citizen_is_registered(self): # national id belongs to a citizen in our db and has one confirmed registration RegistrationFactory(citizen=self.citizen, archive_time=None) self.receive(self.good_nid, self.conn, fields=self.fields) self.assertEqual(self.get_last_response_code(), constants.VOTER_QUERY_REGISTERED_AT)