From 8b5a639b82b68209efe57c2854aac06404923f51 Mon Sep 17 00:00:00 2001 From: Seth Birkholz Date: Thu, 24 Aug 2017 19:04:40 +0000 Subject: [PATCH] This should be the final fix to resolve the meeting registration problem where a Person object was not being created - Legacy-Id: 14076 --- ietf/stats/tests.py | 26 ++++++++++++++++++- ietf/stats/utils.py | 63 ++++++++++++++++++++++++++++++++++++++++++--- 2 files changed, 84 insertions(+), 5 deletions(-) diff --git a/ietf/stats/tests.py b/ietf/stats/tests.py index ad30b4ef3..e4c57f3a1 100644 --- a/ietf/stats/tests.py +++ b/ietf/stats/tests.py @@ -5,6 +5,7 @@ from pyquery import PyQuery from requests import Response from django.urls import reverse as urlreverse +from django.contrib.auth.models import User from ietf.utils.test_data import make_test_data, make_review_data from ietf.utils.test_utils import login_testing_unauthorized, TestCase, unicontent @@ -13,11 +14,12 @@ import ietf.stats.views from ietf.submit.models import Submission from ietf.doc.models import Document, DocAlias, State, RelatedDocument, NewRevisionDocEvent from ietf.meeting.factories import MeetingFactory -from ietf.person.models import Person +from ietf.person.models import Person, Email from ietf.name.models import FormalLanguageName, DocRelationshipName, CountryName from ietf.stats.models import MeetingRegistration, CountryAlias from ietf.stats.utils import get_meeting_registration_data + class StatisticsTests(TestCase): def test_stats_index(self): url = urlreverse(ietf.stats.views.stats_index) @@ -199,3 +201,25 @@ class StatisticsTests(TestCase): get_meeting_registration_data(meeting) query = MeetingRegistration.objects.filter(first_name='John',last_name='Smith',country_code='US') self.assertTrue(query.count(), 1) + self.assertTrue(isinstance(query[0].person,Person)) + + @patch('requests.get') + def test_get_meeting_registration_data_user_exists(self, mock_get): + response = Response() + response.status_code = 200 + response._content = '[{"LastName":"Smith","FirstName":"John","Company":"ABC","Country":"US","Email":"john.doe@example.us"}]' + email = "john.doe@example.us" + user = User.objects.create(username=email) + user.save() + + mock_get.return_value = response + meeting = MeetingFactory(type_id='ietf', date=datetime.date(2016,7,14), number="96") + get_meeting_registration_data(meeting) + query = MeetingRegistration.objects.filter(first_name='John',last_name='Smith',country_code='US') + emails = Email.objects.filter(address=email) + self.assertTrue(query.count(), 1) + self.assertTrue(isinstance(query[0].person, Person)) + self.assertTrue(len(emails)>=1) + self.assertEqual(query[0].person, emails[0].person) + + diff --git a/ietf/stats/utils.py b/ietf/stats/utils.py index d700395d6..00920f016 100644 --- a/ietf/stats/utils.py +++ b/ietf/stats/utils.py @@ -6,6 +6,10 @@ from django.conf import settings from ietf.stats.models import AffiliationAlias, AffiliationIgnoredEnding, CountryAlias, MeetingRegistration from ietf.name.models import CountryName +from ietf.person.models import Person, Email +from django.contrib.auth.models import User +from unidecode import unidecode + def compile_affiliation_ending_stripping_regexp(): parts = [] @@ -226,7 +230,11 @@ def get_meeting_registration_data(meeting): else: raise RuntimeError("Could not decode response from registrations API: '%s...'" % (response.content[:64], )) + + # for each user identified in the Registration system + # Create a DataTracker MeetingRegistration object for registration in decoded: + person = None object, created = MeetingRegistration.objects.get_or_create( meeting_id=meeting.pk, first_name=registration['FirstName'], @@ -235,6 +243,57 @@ def get_meeting_registration_data(meeting): country_code=registration['Country'], email=registration['Email'], ) + + # Add a Person object to MeetingRegistration object + # if valid email is available + if not object.person and registration["Email"] and '@' in registration["Email"]: + # If the person already exists do not try to create a new one + emails = Email.objects.filter(address=registration["Email"]) + # there can only be on Email object with a unique email address (primary key) + if len(emails) == 1: + person = emails[0].person + # Create a new Person object + else: + # ascii_name - convert from unicode if necessary + regname = "%s %s" % (registration["FirstName"], registration["LastName"]) + # if there are any unicode characters decode the string to ascii + ascii_name = unidecode(regname).strip() + + # Create a new user object if it does not exist already + # if the user already exists do not try to create a new one + users = User.objects.filter(username=registration["Email"]) + if len(users) > 0: + user = users[0] + else: + # Create a new user. + user = User.objects.create( + first_name=registration["FirstName"], + last_name=registration["LastName"], + username=registration["Email"], + email=registration["Email"] + ) + user.save() + + # Create the new Person object. + person = Person.objects.create( + name=regname, + ascii=ascii_name, + affiliation=registration["Company"], + user=user + ) + person.save() + + # Create an associated Email address for this new Person + Email.objects.create( + person=person, + address=registration["Email"], + primary=True + ) + + # update the person object to an actual value + object.person = person + object.save() + if created: num_created += 1 num_processed += 1 @@ -242,7 +301,3 @@ def get_meeting_registration_data(meeting): raise RuntimeError("Bad response from registrations API: %s, '%s'" % (response.status_code, response.content)) num_total = MeetingRegistration.objects.filter(meeting_id=meeting.pk).count() return num_created, num_processed, num_total - - - -