Merged in feature/user-import (pull request #18)

Feature/user import
This commit is contained in:
Ramon Wenger 2019-07-04 11:29:34 +00:00 committed by Christian Cueni
commit be076f1550
12 changed files with 126 additions and 15 deletions

View File

@ -2,7 +2,7 @@
<div class="room-group-widget">
<group></group>
<span>
{{name}} - {{year}}
{{name}}
</span>
</div>
</template>
@ -11,7 +11,7 @@
import Group from '@/components/icons/Group.vue';
export default {
props: ['name', 'year'],
props: ['name'],
components: {
Group

View File

@ -1,5 +1,4 @@
fragment SchoolClassParts on SchoolClassNode {
id
name
year
}

View File

@ -0,0 +1,9 @@
Vorname,Nachname,Klassen,Rolle,Email
Dwight,Schrute,Scranton Branch,Schüler,dwight@dundermifflin.com
Michael,Scott,"Scranton Branch,Stanford Branch",Lehrer,michael@dundermifflin.com
Jim,Halpert,Scranton Branch,Schüler,jim@dundermifflin.com
Pam,Beasley,Scranton Branch,Schüler,pam@dundermifflin.com
Karen,Filippelli,Stanford Branch,Schüler,karen@dundermifflin.com
Oscar,Martinez,Scranton Branch,Schüler,oscar@dundermifflin.com
Meredith,Palmer,Scranton Branch,Schüler,meredith@dundermifflin.com
Ryan,Howard,Scranton Branch,Schüler,ryan@dundermifflin.com
1 Vorname Nachname Klassen Rolle Email
2 Dwight Schrute Scranton Branch Schüler dwight@dundermifflin.com
3 Michael Scott Scranton Branch,Stanford Branch Lehrer michael@dundermifflin.com
4 Jim Halpert Scranton Branch Schüler jim@dundermifflin.com
5 Pam Beasley Scranton Branch Schüler pam@dundermifflin.com
6 Karen Filippelli Stanford Branch Schüler karen@dundermifflin.com
7 Oscar Martinez Scranton Branch Schüler oscar@dundermifflin.com
8 Meredith Palmer Scranton Branch Schüler meredith@dundermifflin.com
9 Ryan Howard Scranton Branch Schüler ryan@dundermifflin.com

View File

@ -0,0 +1,48 @@
import csv
from django.core.management import BaseCommand
import os
from django.conf import settings
from users.models import User, SchoolClass, Role, UserRole
class Command(BaseCommand):
def add_arguments(self, parser):
parser.add_argument('csv_file')
def handle(self, *args, **options):
self.stdout.write('Importing from {}!'.format(options['csv_file']))
dir_path = settings.BASE_DIR
rel_path = options['csv_file']
abs_path = os.path.join(dir_path, rel_path)
try:
with open(abs_path) as f:
reader = csv.DictReader(f)
for row in reader:
email = row['Email'].lower()
school_class_names = [c.strip() for c in row['Klassen'].split(',')]
first_name = row['Vorname']
last_name = row['Nachname']
self.stdout.write("Creating user {} {}, {}".format(first_name, last_name, email))
user, created = User.objects.get_or_create(email=email, username=email)
user.first_name = first_name
user.last_name = last_name
user.save()
if row['Rolle'] == 'Lehrer':
self.stdout.write("Assigning teacher role")
teacher = Role.objects.get(key='teacher')
UserRole.objects.get_or_create(user=user, role=teacher)
self.stdout.write("Adding to class(es) {}".format(', '.join(school_class_names)))
for school_class_name in school_class_names:
school, _ = SchoolClass.objects.get_or_create(name=school_class_name)
user.school_classes.add(school)
self.stdout.write("")
except Exception as e:
self.stdout.write(e)

View File

@ -0,0 +1,18 @@
from django.test import TestCase, Client
from django.core import management
from users.models import User, Role
class ImportUsersTestCase(TestCase):
def test_import(self):
Role.objects.create_default_roles()
management.call_command('import_users', 'Benutzer.sample.csv')
self.assertEqual(User.objects.count(), 8)
michael = User.objects.get(email='michael@dundermifflin.com')
self.assertEqual(michael.first_name, 'Michael')
self.assertEqual(michael.school_classes.count(), 2)
self.assertTrue(michael.has_perm('users.can_manage_school_class_content'))

View File

@ -15,8 +15,7 @@ class RoleInline(admin.TabularInline):
@admin.register(SchoolClass)
class SchoolClassAdmin(admin.ModelAdmin):
list_display = ('id', 'name', 'year')
list_filter = ('year',)
list_display = ('id', 'name')
@admin.register(Role)
@ -37,13 +36,17 @@ class CustomUserAdmin(UserAdmin):
add_form = CustomUserCreationForm
form = CustomUserChangeForm
model = User
list_display = ('username', 'first_name', 'last_name',)
list_display = ('username', 'first_name', 'last_name', 'school_classes_list')
list_filter = ('school_classes',)
inlines = [
SchoolClassInline,
RoleInline,
]
def school_classes_list(self, obj):
return ', '.join([s.name for s in obj.school_classes.all()])
# fieldsets = UserAdmin.fieldsets + (
# (None, {'fields': ('school_classes',)}),
# )

View File

@ -17,7 +17,6 @@ class SchoolClassFactory(factory.django.DjangoModelFactory):
model = SchoolClass
name = factory.Sequence(lambda n: '{}{}{}'.format(random.choice(class_types), '18', class_suffix[n % len(class_suffix)]))
year = factory.LazyAttribute(lambda x: random.choice([2017, 2018, 2019]))
is_deleted = False
@factory.post_generation

View File

@ -5,7 +5,6 @@ from graphene import InputObjectType
class SchoolClassInput(InputObjectType):
id = graphene.ID()
name = graphene.String()
year = graphene.Int()
class PasswordUpdateInput(InputObjectType):

View File

@ -0,0 +1,22 @@
# Generated by Django 2.0.6 on 2019-07-03 09:55
from django.db import migrations, models
class Migration(migrations.Migration):
dependencies = [
('users', '0004_user_avatar_url'),
]
operations = [
migrations.RemoveField(
model_name='schoolclass',
name='year',
),
migrations.AlterField(
model_name='user',
name='email',
field=models.EmailField(max_length=254, unique=True, verbose_name='email address'),
),
]

View File

@ -0,0 +1,18 @@
# Generated by Django 2.0.6 on 2019-07-03 09:59
from django.db import migrations, models
class Migration(migrations.Migration):
dependencies = [
('users', '0005_auto_20190703_0955'),
]
operations = [
migrations.AlterField(
model_name='schoolclass',
name='name',
field=models.CharField(max_length=100, unique=True),
),
]

View File

@ -13,6 +13,7 @@ DEFAULT_SCHOOL_ID = 1
class User(AbstractUser):
last_module = models.ForeignKey('books.Module', related_name='+', on_delete=models.SET_NULL, null=True)
avatar_url = models.CharField(max_length=254, blank=True, default='')
email = models.EmailField(_('email address'), unique=True)
def get_role_permissions(self):
perms = set()
@ -43,14 +44,12 @@ class User(AbstractUser):
class SchoolClass(models.Model):
name = models.CharField(max_length=100, blank=False, null=False)
year = models.PositiveIntegerField(blank=False, null=False,
validators=[MinValueValidator(1900), MaxValueValidator(2200)])
name = models.CharField(max_length=100, blank=False, null=False, unique=True)
is_deleted = models.BooleanField(blank=False, null=False, default=False)
users = models.ManyToManyField(get_user_model(), related_name='school_classes')
def __str__(self):
return 'SchoolClass {}-{}-{}'.format(self.id, self.name, self.year)
return 'SchoolClass {}-{}'.format(self.id, self.name)
def is_user_in_schoolclass(self, user):
return user.is_superuser or user.school_classes.filter(pk=self.id).count() > 0

View File

@ -21,7 +21,6 @@ def create_users(data=None):
SchoolClassFactory(
users=[teacher] + students,
year='2018',
name='skillbox'
)
teacher2 = UserFactory(username='teacher2')
@ -30,7 +29,6 @@ def create_users(data=None):
UserRole.objects.create(user=student_second_class, role=student_role)
SchoolClassFactory(
users=[teacher2, student_second_class],
year='2018',
name='second_class'
)
@ -59,5 +57,4 @@ def create_users(data=None):
SchoolClassFactory(
users=students + [teacher],
name=school_class.get('class'),
year='2018'
)