Add code to school class, add form and mutation to join class
This commit is contained in:
parent
17fd7575b4
commit
a4a5e37268
|
|
@ -0,0 +1,5 @@
|
||||||
|
mutation JoinClass($input: JoinClassInput!) {
|
||||||
|
joinClass(input: $input) {
|
||||||
|
success
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
@ -1,9 +1,52 @@
|
||||||
<template>
|
<template>
|
||||||
<div>
|
<div>
|
||||||
<h1>Join Class</h1>
|
<h1>Schulklasse beitreten {{code}}</h1>
|
||||||
<div>
|
<div>
|
||||||
<input data-cy="input-class-code">
|
<div v-if="error">
|
||||||
<a data-cy="join-class">Beitreten</a>
|
{{error}}
|
||||||
|
</div>
|
||||||
|
<input
|
||||||
|
class="skillbox-input"
|
||||||
|
data-cy="input-class-code"
|
||||||
|
:value="code"
|
||||||
|
@input="updateCode">
|
||||||
|
|
||||||
|
<div>
|
||||||
|
<a class="button" data-cy="join-class" @click="joinClass(code)">Beitreten</a>
|
||||||
|
</div>
|
||||||
|
|
||||||
</div>
|
</div>
|
||||||
</div>
|
</div>
|
||||||
</template>
|
</template>
|
||||||
|
|
||||||
|
<script>
|
||||||
|
import JOIN_CLASS_MUTATION from '@/graphql/gql/mutations/joinClass.gql';
|
||||||
|
|
||||||
|
export default {
|
||||||
|
data: () => ({
|
||||||
|
code: '',
|
||||||
|
error: ''
|
||||||
|
}),
|
||||||
|
|
||||||
|
methods: {
|
||||||
|
updateCode(event) {
|
||||||
|
this.code = event.target.value;
|
||||||
|
this.error = '';
|
||||||
|
},
|
||||||
|
joinClass(code) {
|
||||||
|
this.$apollo.mutate({
|
||||||
|
mutation: JOIN_CLASS_MUTATION,
|
||||||
|
variables: {
|
||||||
|
input: {
|
||||||
|
code
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}).catch(e => {
|
||||||
|
console.debug(e);
|
||||||
|
console.error(e.message)
|
||||||
|
this.error = 'Code ist nicht gültig';
|
||||||
|
})
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
</script>
|
||||||
|
|
|
||||||
|
|
@ -15,7 +15,7 @@ class RoleInline(admin.TabularInline):
|
||||||
|
|
||||||
@admin.register(SchoolClass)
|
@admin.register(SchoolClass)
|
||||||
class SchoolClassAdmin(admin.ModelAdmin):
|
class SchoolClassAdmin(admin.ModelAdmin):
|
||||||
list_display = ('id', 'name')
|
list_display = ('name', 'code', 'is_deleted')
|
||||||
|
|
||||||
|
|
||||||
@admin.register(Role)
|
@admin.register(Role)
|
||||||
|
|
|
||||||
|
|
@ -0,0 +1,18 @@
|
||||||
|
# Generated by Django 2.1.15 on 2020-02-11 10:14
|
||||||
|
|
||||||
|
from django.db import migrations, models
|
||||||
|
|
||||||
|
|
||||||
|
class Migration(migrations.Migration):
|
||||||
|
|
||||||
|
dependencies = [
|
||||||
|
('users', '0009_auto_20191009_0905'),
|
||||||
|
]
|
||||||
|
|
||||||
|
operations = [
|
||||||
|
migrations.AddField(
|
||||||
|
model_name='schoolclass',
|
||||||
|
name='code',
|
||||||
|
field=models.CharField(blank=True, default=None, max_length=10, null=True, unique=True, verbose_name='Code zum Beitreten'),
|
||||||
|
),
|
||||||
|
]
|
||||||
|
|
@ -70,9 +70,14 @@ class SchoolClass(models.Model):
|
||||||
name = models.CharField(max_length=100, blank=False, null=False, unique=True)
|
name = models.CharField(max_length=100, blank=False, null=False, unique=True)
|
||||||
is_deleted = models.BooleanField(blank=False, null=False, default=False)
|
is_deleted = models.BooleanField(blank=False, null=False, default=False)
|
||||||
users = models.ManyToManyField(get_user_model(), related_name='school_classes', blank=True)
|
users = models.ManyToManyField(get_user_model(), related_name='school_classes', blank=True)
|
||||||
|
code = models.CharField('Code zum Beitreten', blank=True, null=True, max_length=10, unique=True, default=None)
|
||||||
|
|
||||||
|
class Meta:
|
||||||
|
verbose_name = 'Schulklasse'
|
||||||
|
verbose_name_plural = 'Schulklassen'
|
||||||
|
|
||||||
def __str__(self):
|
def __str__(self):
|
||||||
return 'SchoolClass {}-{}'.format(self.id, self.name)
|
return '{}'.format(self.name)
|
||||||
|
|
||||||
@classmethod
|
@classmethod
|
||||||
def generate_default_group_name(cls):
|
def generate_default_group_name(cls):
|
||||||
|
|
@ -99,6 +104,11 @@ class SchoolClass(models.Model):
|
||||||
def get_teacher(self):
|
def get_teacher(self):
|
||||||
return self.users.filter(user_roles__role__key='teacher').first()
|
return self.users.filter(user_roles__role__key='teacher').first()
|
||||||
|
|
||||||
|
def save(self, *args, **kwargs):
|
||||||
|
if self.code == '': # '' can't be unique, so we null it
|
||||||
|
self.code = None
|
||||||
|
super().save(*args, **kwargs)
|
||||||
|
|
||||||
|
|
||||||
class Role(models.Model):
|
class Role(models.Model):
|
||||||
key = models.CharField(_('Key'), max_length=100, blank=False, null=False, unique=True)
|
key = models.CharField(_('Key'), max_length=100, blank=False, null=False, unique=True)
|
||||||
|
|
@ -165,4 +175,3 @@ class UserRole(models.Model):
|
||||||
class UserSetting(models.Model):
|
class UserSetting(models.Model):
|
||||||
user = models.OneToOneField(get_user_model(), on_delete=models.CASCADE, related_name='user_setting')
|
user = models.OneToOneField(get_user_model(), on_delete=models.CASCADE, related_name='user_setting')
|
||||||
selected_class = models.ForeignKey(SchoolClass, blank=True, null=True, on_delete=models.CASCADE)
|
selected_class = models.ForeignKey(SchoolClass, blank=True, null=True, on_delete=models.CASCADE)
|
||||||
|
|
||||||
|
|
|
||||||
|
|
@ -9,6 +9,10 @@ from users.models import SchoolClass, UserSetting
|
||||||
from users.serializers import PasswordSerialzer, AvatarUrlSerializer
|
from users.serializers import PasswordSerialzer, AvatarUrlSerializer
|
||||||
|
|
||||||
|
|
||||||
|
class CodeNotFoundException(Exception):
|
||||||
|
pass
|
||||||
|
|
||||||
|
|
||||||
class FieldError(graphene.ObjectType):
|
class FieldError(graphene.ObjectType):
|
||||||
code = graphene.String()
|
code = graphene.String()
|
||||||
|
|
||||||
|
|
@ -102,8 +106,28 @@ class UpdateSetting(relay.ClientIDMutation):
|
||||||
errors = graphene.List(UpdateError)
|
errors = graphene.List(UpdateError)
|
||||||
|
|
||||||
|
|
||||||
|
class JoinClass(relay.ClientIDMutation):
|
||||||
|
class Input:
|
||||||
|
code = graphene.String(required=True)
|
||||||
|
|
||||||
|
success = graphene.Boolean()
|
||||||
|
|
||||||
|
@classmethod
|
||||||
|
def mutate_and_get_payload(cls, root, info, **kwargs):
|
||||||
|
user = info.context.user
|
||||||
|
code = kwargs.get('code')
|
||||||
|
try:
|
||||||
|
school_class = SchoolClass.objects.get(code__iexact=code)
|
||||||
|
|
||||||
|
school_class.users.add(user)
|
||||||
|
|
||||||
|
return cls(success=True)
|
||||||
|
except SchoolClass.DoesNotExist:
|
||||||
|
raise CodeNotFoundException('Code ist nicht gültig')
|
||||||
|
|
||||||
|
|
||||||
class ProfileMutations:
|
class ProfileMutations:
|
||||||
update_password = UpdatePassword.Field()
|
update_password = UpdatePassword.Field()
|
||||||
update_avatar = UpdateAvatar.Field()
|
update_avatar = UpdateAvatar.Field()
|
||||||
update_setting = UpdateSetting.Field()
|
update_setting = UpdateSetting.Field()
|
||||||
|
join_class = JoinClass.Field()
|
||||||
|
|
|
||||||
Loading…
Reference in New Issue