]> git.parisson.com Git - mezzo.git/commitdiff
First complete person data import (beta version)
authorGuillaume Pellerin <guillaume.pellerin@ircam.fr>
Fri, 16 Sep 2016 12:46:54 +0000 (14:46 +0200)
committerGuillaume Pellerin <guillaume.pellerin@ircam.fr>
Fri, 16 Sep 2016 12:46:54 +0000 (14:46 +0200)
app/organization/network/admin.py
app/organization/network/management/commands/import-ircam-person-xls.py
app/organization/network/migrations/0008_person_email.py [new file with mode: 0644]
app/organization/network/migrations/0009_auto_20160916_1229.py [new file with mode: 0644]
app/organization/network/migrations/0010_personactivity_weeks.py [new file with mode: 0644]
app/organization/network/migrations/0011_auto_20160916_1246.py [new file with mode: 0644]
app/organization/network/migrations/0012_auto_20160916_1423.py [new file with mode: 0644]
app/organization/network/models.py
app/organization/network/translation.py
app/scripts/app.sh
requirements.txt

index 582aeeb79a7b7a61b567cad2b4c2ed2f3220a74b..ea481d52a4d8e3ff47ee4acb1b2fd31dfaacb850 100644 (file)
@@ -105,6 +105,7 @@ class PersonAdmin(BaseTranslationModelAdmin):
     model = Person
     inlines = [PersonActivityInline, PersonAudioInline, PersonImageInline, PersonVideoInline, PersonBlockInline, PersonLinkInline ]
     first_fields = ['last_name', 'first_name', 'title', 'gender', 'user']
+    search_fields = ['last_name', 'first_name']
 
     def get_fieldsets(self, request, obj = None):
         res = super(PersonAdmin, self).get_fieldsets(request, obj)
@@ -121,3 +122,4 @@ admin.site.register(DepartmentPage, DepartmentPageAdmin)
 admin.site.register(Team, TeamAdmin)
 admin.site.register(TeamPage, TeamPageAdmin)
 admin.site.register(Person, PersonAdmin)
+admin.site.register(ActivityStatus)
index 86c9606bdb695ea8a0fa700487af2d56064a1fb9..ea0bddea08cabe492c91bf4039444abb7379eca8 100644 (file)
@@ -46,7 +46,7 @@ def get_instance(model, field, value):
 class IrcamXLS:
 
     sheet_id = 2
-    first_row = 21
+    first_row = 20
 
     def __init__(self, file):
         self.book = xlrd.open_workbook(file)
@@ -69,6 +69,7 @@ class IrcamPerson(object):
         self.datemode = datemode
         last_name = self.row[0].value
         first_name = self.row[1].value
+        print(last_name)
         title = ' '.join((first_name, last_name))
 
         self.person, c = Person.objects.get_or_create(title=title, first_name=first_name, last_name=last_name)
@@ -85,12 +86,50 @@ class IrcamPerson(object):
         if birthday:
             self.person.birthday = datetime.datetime(*xlrd.xldate_as_tuple(birthday, self.datemode))
 
+        # self.person.nationality = self.get_or_create_name(Nationality, self.row[33].value)
+
         self.person.save()
 
     def get_or_create_name(self, model, column_id):
         return model.objects.get_or_create(name=self.row[column_id].value)[0] if self.row[column_id].value else None
 
+    def get_person(self, value):
+        if value:
+            name_exceptions = ['de', 'von']
+
+            names = value.split(' / ')[0]
+            names = names.split(' ')
+
+            if names[0] == 'M.':
+                names.remove('M.')
+
+            if names[0] == 'Mm.':
+                names.remove('Mm.')
+
+            first_name = names[0].capitalize()
+
+            last_name = []
+            for name in names[1:]:
+                if name:
+                    if name[0] != '(' and not name in name_exceptions:
+                        last_name.append(name.capitalize())
+            last_name = ' '.join(last_name)
+
+            title = ' '.join((first_name, last_name))
+            person, c = Person.objects.get_or_create(title=title)
+
+            return person
+
+        return None
+
     def get_activity(self):
+        self.activity.date_begin = datetime.datetime(*xlrd.xldate_as_tuple(self.row[4].value, self.datemode)) if self.row[4].value else None
+        self.activity.date_end = datetime.datetime(*xlrd.xldate_as_tuple(self.row[5].value, self.datemode)) if self.row[5].value else None
+        try:
+            self.activity.weeks = int(self.row[6].value) if self.row[6].value else None
+        except:
+            pass
+
         self.activity.status = self.get_or_create_name(ActivityStatus, 10)
         self.activity.is_permanent = True if self.row[11].value else False
         self.activity.framework = self.get_or_create_name(ActivityFramework, 12)
@@ -101,22 +140,43 @@ class IrcamPerson(object):
         self.activity.second_employer = self.get_or_create_name(Organization, 16)
         self.activity.umr = self.get_or_create_name(UMR, 17)
 
-        self.activity.team, c = Team.objects.get_or_create(name=self.row[18].value, organization=self.organization) if self.row[18].value else (None, False)
-        self.activity.second_team, c = Team.objects.get_or_create(name=self.row[19].value, organization=self.organization) if self.row[19].value else (None, False)
-        self.activity.project, c = Project.objects.get_or_create(title=self.row[19].value) if self.row[19].value else (None, False)
+        self.activity.team, c = Team.objects.get_or_create(code=self.row[19].value, organization=self.organization) if self.row[19].value else (None, False)
+        self.activity.second_team, c = Team.objects.get_or_create(code=self.row[21].value, organization=self.organization) if self.row[21].value else (None, False)
+        self.activity.project, c = Project.objects.get_or_create(title=self.row[22].value) if self.row[22].value else (None, False)
 
-        quota = self.row[21].value
+        quota = self.row[23].value
         try:
             self.activity.rd_quota_float = float(quota)
         except:
             self.activity.rd_quota_text = str(quota)
 
-        self.activity.phd_doctoral_school = self.get_or_create_name(Organization, 23)
-        self.activity.phd_director, c = Person.objects.get_or_create(title=self.row[24].value.capitalize()) if self.row[24].value else (None, False)
-        self.activity.phd_officer_1, c = Person.objects.get_or_create(title=self.row[25].value.capitalize()) if self.row[25].value else (None, False)
-        self.activity.phd_officer_2, c = Person.objects.get_or_create(title=self.row[26].value.capitalize()) if self.row[26].value else (None, False)
-        # self.activity.phd_defense_date = datetime.datetime(*xlrd.xldate_as_tuple(self.row[27].value, self.datemode)) if self.row[27].value else None
-        # self.activity.phd_title = self.row[28].value
+        self.activity.phd_doctoral_school = self.get_or_create_name(Organization, 25)
+        self.activity.phd_director = self.get_person(self.row[26].value)
+        self.activity.phd_officer_1 = self.get_person(self.row[27].value)
+        self.activity.phd_officer_2 = self.get_person(self.row[28].value)
+
+        self.activity.training_type = self.get_or_create_name(TrainingType, 29)
+        self.activity.training_level = self.get_or_create_name(TrainingLevel, 30)
+        self.activity.training_topic = self.get_or_create_name(TrainingTopic, 31)
+        self.activity.training_speciality = self.get_or_create_name(TrainingSpectiality, 32)
+        self.activity.function = self.get_or_create_name(ActivityFunction, 34)
+
+        if self.activity.phd_director:
+            self.activity.phd_title = self.row[35].value
+            try:
+                self.activity.phd_defense_date = datetime.datetime(*xlrd.xldate_as_tuple(self.row[38].value, self.datemode)) if self.row[38].value else None
+            except:
+                pass
+            self.activity.phd_postdoctoralsituation = self.row[39].value
+        elif self.activity.training_type:
+            self.activity.training_title = self.row[35].value
+
+        self.activity.rd_program = self.row[36].value
+        self.activity.comments = self.row[37].value
+        self.activity.hdr = self.row[40].value
+        self.activity.budget_code = self.get_or_create_name(BudgetCode, 41)
+        self.activity.date_modified_manual = datetime.datetime(*xlrd.xldate_as_tuple(self.row[42].value, self.datemode)) if self.row[42].value else None
+        self.activity.record_piece = self.get_or_create_name(RecordPiece, 43) if self.row[43].value else None
 
         self.activity.save()
 
diff --git a/app/organization/network/migrations/0008_person_email.py b/app/organization/network/migrations/0008_person_email.py
new file mode 100644 (file)
index 0000000..5c177cb
--- /dev/null
@@ -0,0 +1,20 @@
+# -*- coding: utf-8 -*-
+# Generated by Django 1.9.7 on 2016-09-16 09:35
+from __future__ import unicode_literals
+
+from django.db import migrations, models
+
+
+class Migration(migrations.Migration):
+
+    dependencies = [
+        ('organization-network', '0007_auto_20160914_1818'),
+    ]
+
+    operations = [
+        migrations.AddField(
+            model_name='person',
+            name='email',
+            field=models.EmailField(blank=True, max_length=254, null=True, verbose_name='email'),
+        ),
+    ]
diff --git a/app/organization/network/migrations/0009_auto_20160916_1229.py b/app/organization/network/migrations/0009_auto_20160916_1229.py
new file mode 100644 (file)
index 0000000..a102b76
--- /dev/null
@@ -0,0 +1,49 @@
+# -*- coding: utf-8 -*-
+# Generated by Django 1.9.7 on 2016-09-16 10:29
+from __future__ import unicode_literals
+
+from django.db import migrations, models
+
+
+class Migration(migrations.Migration):
+
+    dependencies = [
+        ('organization-network', '0008_person_email'),
+    ]
+
+    operations = [
+        migrations.RemoveField(
+            model_name='personactivity',
+            name='content',
+        ),
+        migrations.RemoveField(
+            model_name='personactivity',
+            name='content_en',
+        ),
+        migrations.RemoveField(
+            model_name='personactivity',
+            name='content_fr',
+        ),
+        migrations.RemoveField(
+            model_name='personactivity',
+            name='description',
+        ),
+        migrations.RemoveField(
+            model_name='personactivity',
+            name='description_en',
+        ),
+        migrations.RemoveField(
+            model_name='personactivity',
+            name='description_fr',
+        ),
+        migrations.AddField(
+            model_name='personactivity',
+            name='comments_en',
+            field=models.TextField(blank=True, null=True, verbose_name='comments'),
+        ),
+        migrations.AddField(
+            model_name='personactivity',
+            name='comments_fr',
+            field=models.TextField(blank=True, null=True, verbose_name='comments'),
+        ),
+    ]
diff --git a/app/organization/network/migrations/0010_personactivity_weeks.py b/app/organization/network/migrations/0010_personactivity_weeks.py
new file mode 100644 (file)
index 0000000..3c7aa03
--- /dev/null
@@ -0,0 +1,20 @@
+# -*- coding: utf-8 -*-
+# Generated by Django 1.9.7 on 2016-09-16 10:38
+from __future__ import unicode_literals
+
+from django.db import migrations, models
+
+
+class Migration(migrations.Migration):
+
+    dependencies = [
+        ('organization-network', '0009_auto_20160916_1229'),
+    ]
+
+    operations = [
+        migrations.AddField(
+            model_name='personactivity',
+            name='weeks',
+            field=models.IntegerField(blank=True, null=True, verbose_name='number of weeks'),
+        ),
+    ]
diff --git a/app/organization/network/migrations/0011_auto_20160916_1246.py b/app/organization/network/migrations/0011_auto_20160916_1246.py
new file mode 100644 (file)
index 0000000..9fdfd02
--- /dev/null
@@ -0,0 +1,26 @@
+# -*- coding: utf-8 -*-
+# Generated by Django 1.9.7 on 2016-09-16 10:46
+from __future__ import unicode_literals
+
+from django.db import migrations, models
+import django.db.models.deletion
+
+
+class Migration(migrations.Migration):
+
+    dependencies = [
+        ('organization-network', '0010_personactivity_weeks'),
+    ]
+
+    operations = [
+        migrations.AddField(
+            model_name='team',
+            name='code',
+            field=models.CharField(blank=True, max_length=64, null=True, verbose_name='code'),
+        ),
+        migrations.AlterField(
+            model_name='personactivity',
+            name='umr',
+            field=models.ForeignKey(blank=True, null=True, on_delete=django.db.models.deletion.SET_NULL, to='organization-network.UMR', verbose_name='UMR'),
+        ),
+    ]
diff --git a/app/organization/network/migrations/0012_auto_20160916_1423.py b/app/organization/network/migrations/0012_auto_20160916_1423.py
new file mode 100644 (file)
index 0000000..2327b7a
--- /dev/null
@@ -0,0 +1,32 @@
+# -*- coding: utf-8 -*-
+# Generated by Django 1.9.7 on 2016-09-16 12:23
+from __future__ import unicode_literals
+
+from django.db import migrations, models
+import django.db.models.deletion
+
+
+class Migration(migrations.Migration):
+
+    dependencies = [
+        ('organization-network', '0011_auto_20160916_1246'),
+    ]
+
+    operations = [
+        migrations.CreateModel(
+            name='ActivityFunction',
+            fields=[
+                ('id', models.AutoField(auto_created=True, primary_key=True, serialize=False, verbose_name='ID')),
+                ('name', models.CharField(max_length=512, verbose_name='name')),
+                ('description', models.TextField(blank=True, verbose_name='description')),
+            ],
+            options={
+                'verbose_name': 'activity function',
+            },
+        ),
+        migrations.AddField(
+            model_name='personactivity',
+            name='function',
+            field=models.ForeignKey(blank=True, null=True, on_delete=django.db.models.deletion.SET_NULL, to='organization-network.ActivityFunction', verbose_name='function'),
+        ),
+    ]
index 26b7fd3a40bec545c41ff58314179b4bc008aeaa..4bcf5b09d7895681efa3d56b14660a1ef3c9b0a4 100644 (file)
@@ -136,6 +136,7 @@ class Team(Named, URL):
 
     organization = models.ForeignKey('Organization', verbose_name=_('organization'), related_name="teams", blank=True, null=True, on_delete=models.SET_NULL)
     department = models.ForeignKey('Department', verbose_name=_('department'), related_name="teams", blank=True, null=True, on_delete=models.SET_NULL)
+    code = models.CharField(_('code'), max_length=64, blank=True, null=True)
 
     class Meta:
         verbose_name = _('team')
@@ -168,6 +169,7 @@ class Person(Displayable, AdminThumbMixin):
     gender = models.CharField(_('gender'), max_length=16, choices=GENDER_CHOICES, blank=True)
     first_name = models.CharField(_('first name'), max_length=255, blank=True, null=True)
     last_name = models.CharField(_('last name'), max_length=255, blank=True, null=True)
+    email = models.EmailField(_('email'), blank=True, null=True)
     birthday = models.DateField(_('birthday'), blank=True, null=True)
     bio = RichTextField(_('biography'), blank=True)
 
@@ -251,6 +253,12 @@ class ActivityFramework(Named):
         verbose_name = _('activity framework')
 
 
+class ActivityFunction(Named):
+
+    class Meta:
+        verbose_name = _('activity function')
+
+
 class BudgetCode(Named):
 
     class Meta:
@@ -293,20 +301,22 @@ class UMR(Named):
         verbose_name = _('UMR')
 
 
-class PersonActivity(Description, Period, RichText):
+class PersonActivity(Period):
     """(Activity description)"""
 
     person = models.ForeignKey('Person', verbose_name=_('person'))
 
+    weeks = models.IntegerField(_('number of weeks'), blank=True, null=True)
     status = models.ForeignKey(ActivityStatus, verbose_name=_('status'), blank=True, null=True, on_delete=models.SET_NULL)
     is_permanent = models.BooleanField(_('permanent'), default=False)
     framework = models.ForeignKey(ActivityFramework, verbose_name=_('framework'), blank=True, null=True, on_delete=models.SET_NULL)
     grade = models.ForeignKey(ActivityGrade, verbose_name=_('grade'), blank=True, null=True, on_delete=models.SET_NULL)
+    function = models.ForeignKey(ActivityFunction, verbose_name=_('function'), blank=True, null=True, on_delete=models.SET_NULL)
 
     employer = models.ForeignKey(Organization, verbose_name=_('employer'), related_name='employer_activity', blank=True, null=True, on_delete=models.SET_NULL)
     attachment_organization = models.ForeignKey(Organization, verbose_name=_('attachment organization'), related_name='attachment_activity', blank=True, null=True, on_delete=models.SET_NULL)
     second_employer = models.ForeignKey(Organization, verbose_name=_('second employer'), related_name='second_employer_activity', blank=True, null=True, on_delete=models.SET_NULL)
-    umr = models.ForeignKey(UMR, verbose_name=_('training type'), blank=True, null=True, on_delete=models.SET_NULL)
+    umr = models.ForeignKey(UMR, verbose_name=_('UMR'), blank=True, null=True, on_delete=models.SET_NULL)
     team = models.ForeignKey('Team', verbose_name=_('team'), related_name='team_activity', blank=True, null=True, on_delete=models.SET_NULL)
     second_team = models.ForeignKey('Team', verbose_name=_('second team'), related_name='second_team_activity', blank=True, null=True, on_delete=models.SET_NULL)
 
@@ -332,6 +342,7 @@ class PersonActivity(Description, Period, RichText):
     training_title = models.TextField(_('Training title'), blank=True)
 
     record_piece = models.ForeignKey(RecordPiece, blank=True, null=True, on_delete=models.SET_NULL)
+
     date_added = models.DateTimeField(_('add date'), auto_now_add=True)
     date_modified = models.DateTimeField(_('modification date'), auto_now=True)
     date_modified_manual = models.DateTimeField(_('manual modification date'), blank=True, null=True)
@@ -342,5 +353,8 @@ class PersonActivity(Description, Period, RichText):
         verbose_name = _('activity')
         verbose_name_plural = _('activities')
 
-    def __unicode__(self):
-        return ' - '.join((self.person, self.role, self.date_begin, self.date_end))
+    def __str__(self):
+        if self.status:
+            return ' - '.join((self.status.name, str(self.date_begin), str(self.date_end)))
+        else:
+            return ' - '.join((str(self.date_begin), str(self.date_end)))
index 8f330ee0bd974d25ad05f89c58a5cb400dea854e..b9f06353e45b2af2abdd8fbb515f3656365af272 100644 (file)
@@ -42,7 +42,7 @@ class PersonTranslationOptions(TranslationOptions):
 @register(PersonActivity)
 class PersonActivityTranslationOptions(TranslationOptions):
 
-    fields = ('description', 'content')
+    fields = ('comments',)
 
 
 @register(PersonAudio)
index 6faf3f03851b1d3b6a4333114d975de7f1c24cba..00c0cabf1749ae021f28d783381cacff5d58f83a 100644 (file)
@@ -18,7 +18,7 @@ gid='www-data'
 patterns='*.js;*.css;*.jpg;*.jpeg;*.gif;*.png;*.svg;*.ttf;*.eot;*.woff;*.woff2'
 
 # Staging
-# pip install cartridge
+pip install xlrd
 # pip install -U https://forge.ircam.fr/p/django-eve/source/download/dev/
 # pip install -U https://github.com/stephenmcd/grappelli-safe/archive/dynamic_stacked.zip
 # pip install django-querysetsequence
index 30aafe4142dd5eac2158e830c9f63543dc6c2f43..6618a48b0d673b0b4986b47a6d36d9577211319b 100644 (file)
@@ -16,3 +16,4 @@ django-querysetsequence
 django-autocomplete-light
 ipython
 cartridge
+xlrd