Merge pull request #562 from normanjaeckel/Listen_To_Syncdb

Builtin Workflows and Groups are now created by listening to a signal
This commit is contained in:
Oskar Hahn 2013-03-12 14:00:35 -07:00
commit 80b7597022
21 changed files with 254 additions and 611 deletions

View File

@ -8,3 +8,4 @@ install:
script: script:
- coverage run ./manage.py test tests && coverage report -m - coverage run ./manage.py test tests && coverage report -m
- pep8 --max-line-length=150 --exclude="urls.py," --statistics openslides - pep8 --max-line-length=150 --exclude="urls.py," --statistics openslides
- pep8 --max-line-length=150 --statistics tests

View File

@ -22,9 +22,6 @@ from openslides.utils.views import FormView, TemplateView
from .forms import GeneralConfigForm from .forms import GeneralConfigForm
from .models import config from .models import config
# TODO: Do not import the participant module in config
from openslides.participant.api import get_or_create_anonymous_group
class GeneralConfig(FormView): class GeneralConfig(FormView):
""" """
@ -62,7 +59,6 @@ class GeneralConfig(FormView):
# system # system
if form.cleaned_data['system_enable_anonymous']: if form.cleaned_data['system_enable_anonymous']:
config['system_enable_anonymous'] = True config['system_enable_anonymous'] = True
get_or_create_anonymous_group()
else: else:
config['system_enable_anonymous'] = False config['system_enable_anonymous'] = False

View File

View File

@ -0,0 +1,16 @@
#!/usr/bin/env python
# -*- coding: utf-8 -*-
"""
openslides.core.signals
~~~~~~~~~~~~~~~~~~~~~~~~~
Core Signals.
:copyright: (c) 2011-2013 by the OpenSlides team, see AUTHORS.
:license: GNU GPL, see LICENSE for more details.
"""
from django.dispatch import Signal
post_database_setup = Signal()

View File

@ -27,6 +27,7 @@ from django.core.management import execute_from_command_line
from openslides import get_version from openslides import get_version
from openslides.utils.tornado_webserver import run_tornado from openslides.utils.tornado_webserver import run_tornado
CONFIG_TEMPLATE = """#!/usr/bin/env python CONFIG_TEMPLATE = """#!/usr/bin/env python
# -*- coding: utf-8 -*- # -*- coding: utf-8 -*-
@ -270,7 +271,6 @@ def run_syncdb():
# now initialize the database # now initialize the database
argv = ["", "syncdb", "--noinput"] argv = ["", "syncdb", "--noinput"]
execute_from_command_line(argv) execute_from_command_line(argv)
execute_from_command_line(["", "loaddata", "groups_de"])
def set_system_url(url): def set_system_url(url):

View File

@ -1,280 +0,0 @@
[
{
"pk":1,
"model":"motion.workflow",
"fields":{
"name":"Simple Workflow",
"first_state":1
}
},
{
"pk":2,
"model":"motion.workflow",
"fields":{
"name":"Complex Workflow",
"first_state":5
}
},
{
"pk":1,
"model":"motion.state",
"fields":{
"name":"submitted",
"workflow":1,
"dont_set_new_version_active":false,
"allow_submitter_edit":true,
"next_states":[
2,
3,
4
],
"allow_support":true,
"action_word":"",
"icon":"",
"versioning":false,
"allow_create_poll":true
}
},
{
"pk":2,
"model":"motion.state",
"fields":{
"name":"accepted",
"workflow":1,
"dont_set_new_version_active":false,
"allow_submitter_edit":false,
"next_states":[
],
"allow_support":false,
"action_word":"accept",
"icon":"",
"versioning":false,
"allow_create_poll":false
}
},
{
"pk":3,
"model":"motion.state",
"fields":{
"name":"rejected",
"workflow":1,
"dont_set_new_version_active":false,
"allow_submitter_edit":false,
"next_states":[
],
"allow_support":false,
"action_word":"reject",
"icon":"",
"versioning":false,
"allow_create_poll":false
}
},
{
"pk":4,
"model":"motion.state",
"fields":{
"name":"not decided",
"workflow":1,
"dont_set_new_version_active":false,
"allow_submitter_edit":false,
"next_states":[
],
"allow_support":false,
"action_word":"do not decide",
"icon":"",
"versioning":false,
"allow_create_poll":false
}
},
{
"pk":5,
"model":"motion.state",
"fields":{
"name":"published",
"workflow":2,
"dont_set_new_version_active":false,
"allow_submitter_edit":true,
"next_states":[
6,
9,
14
],
"allow_support":true,
"action_word":"",
"icon":"",
"versioning":false,
"allow_create_poll":false
}
},
{
"pk":6,
"model":"motion.state",
"fields":{
"name":"permitted",
"workflow":2,
"dont_set_new_version_active":true,
"allow_submitter_edit":true,
"next_states":[
7,
8,
9,
10,
11,
12,
13
],
"allow_support":false,
"action_word":"permit",
"icon":"",
"versioning":true,
"allow_create_poll":true
}
},
{
"pk":7,
"model":"motion.state",
"fields":{
"name":"accepted",
"workflow":2,
"dont_set_new_version_active":false,
"allow_submitter_edit":false,
"next_states":[
],
"allow_support":false,
"action_word":"accept",
"icon":"",
"versioning":true,
"allow_create_poll":false
}
},
{
"pk":8,
"model":"motion.state",
"fields":{
"name":"rejected",
"workflow":2,
"dont_set_new_version_active":false,
"allow_submitter_edit":false,
"next_states":[
],
"allow_support":false,
"action_word":"reject",
"icon":"",
"versioning":true,
"allow_create_poll":false
}
},
{
"pk":9,
"model":"motion.state",
"fields":{
"name":"withdrawed",
"workflow":2,
"dont_set_new_version_active":false,
"allow_submitter_edit":false,
"next_states":[
],
"allow_support":false,
"action_word":"withdraw",
"icon":"",
"versioning":true,
"allow_create_poll":false
}
},
{
"pk":10,
"model":"motion.state",
"fields":{
"name":"adjourned",
"workflow":2,
"dont_set_new_version_active":false,
"allow_submitter_edit":false,
"next_states":[
],
"allow_support":false,
"action_word":"adjourn",
"icon":"",
"versioning":true,
"allow_create_poll":false
}
},
{
"pk":11,
"model":"motion.state",
"fields":{
"name":"not concerned",
"workflow":2,
"dont_set_new_version_active":false,
"allow_submitter_edit":false,
"next_states":[
],
"allow_support":false,
"action_word":"",
"icon":"",
"versioning":true,
"allow_create_poll":false
}
},
{
"pk":12,
"model":"motion.state",
"fields":{
"name":"commited a bill",
"workflow":2,
"dont_set_new_version_active":false,
"allow_submitter_edit":false,
"next_states":[
],
"allow_support":false,
"action_word":"commit a bill",
"icon":"",
"versioning":true,
"allow_create_poll":false
}
},
{
"pk":13,
"model":"motion.state",
"fields":{
"name":"needs review",
"workflow":2,
"dont_set_new_version_active":false,
"allow_submitter_edit":false,
"next_states":[
],
"allow_support":false,
"action_word":"",
"icon":"",
"versioning":true,
"allow_create_poll":false
}
},
{
"pk":14,
"model":"motion.state",
"fields":{
"name":"rejected (not authorized)",
"workflow":2,
"dont_set_new_version_active":false,
"allow_submitter_edit":false,
"next_states":[
],
"allow_support":false,
"action_word":"reject (not authorized)",
"icon":"",
"versioning":true,
"allow_create_poll":false
}
}
]

View File

@ -349,7 +349,8 @@ class Motion(SlideMixin, models.Model):
if self.state: if self.state:
self.state = self.state.workflow.first_state self.state = self.state.workflow.first_state
else: else:
self.state = Workflow.objects.get(pk=config['motion_workflow']).first_state self.state = (Workflow.objects.get(pk=config['motion_workflow']).first_state or
Workflow.objects.get(pk=config['motion_workflow']).state_set.all()[0])
def slide(self): def slide(self):
"""Return the slide dict.""" """Return the slide dict."""
@ -716,7 +717,7 @@ class Workflow(models.Model):
name = models.CharField(max_length=255) name = models.CharField(max_length=255)
"""A string representing the workflow.""" """A string representing the workflow."""
first_state = models.OneToOneField(State, related_name='+') first_state = models.OneToOneField(State, related_name='+', null=True)
"""A one-to-one relation to a state, the starting point for the workflow.""" """A one-to-one relation to a state, the starting point for the workflow."""
def __unicode__(self): def __unicode__(self):
@ -733,5 +734,5 @@ class Workflow(models.Model):
def check_first_state(self): def check_first_state(self):
"""Checks whether the first_state itself belongs to the workflow.""" """Checks whether the first_state itself belongs to the workflow."""
if not self.first_state.workflow == self: if self.first_state and not self.first_state.workflow == self:
raise WorkflowError('%s can not be first state of %s because it does not belong to it.' % (self.first_state, self)) raise WorkflowError('%s can not be first state of %s because it does not belong to it.' % (self.first_state, self))

View File

@ -11,9 +11,12 @@
""" """
from django.dispatch import receiver from django.dispatch import receiver
from django.utils.translation import ugettext as _ from django.utils.translation import ugettext as _, ugettext_noop
from openslides.config.signals import default_config_value from openslides.config.signals import default_config_value
from openslides.core.signals import post_database_setup
from .models import Workflow, State
@receiver(default_config_value, dispatch_uid="motion_default_config") @receiver(default_config_value, dispatch_uid="motion_default_config")
@ -28,3 +31,76 @@ def default_config(sender, key, **kwargs):
'motion_pdf_preamble': '', 'motion_pdf_preamble': '',
'motion_allow_disable_versioning': False, 'motion_allow_disable_versioning': False,
'motion_workflow': 1}.get(key) 'motion_workflow': 1}.get(key)
@receiver(post_database_setup, dispatch_uid='motion_create_builtin_workflows')
def create_builtin_workflows(sender, **kwargs):
"""
Creates a simple and a complex workflow.
"""
workflow_1 = Workflow.objects.create(name=ugettext_noop('Simple Workflow'))
state_1_1 = State.objects.create(name=ugettext_noop('submitted'),
workflow=workflow_1,
allow_create_poll=True,
allow_support=True,
allow_submitter_edit=True)
state_1_2 = State.objects.create(name=ugettext_noop('accepted'),
workflow=workflow_1,
action_word=ugettext_noop('Accept'))
state_1_3 = State.objects.create(name=ugettext_noop('rejected'),
workflow=workflow_1,
action_word=ugettext_noop('Reject'))
state_1_4 = State.objects.create(name=ugettext_noop('not decided'),
workflow=workflow_1,
action_word=ugettext_noop('Do not decide'))
state_1_1.next_states.add(state_1_2, state_1_3, state_1_4)
workflow_1.first_state = state_1_1
workflow_1.save()
workflow_2 = Workflow.objects.create(name=ugettext_noop('Complex Workflow'))
state_2_1 = State.objects.create(name=ugettext_noop('published'),
workflow=workflow_2,
allow_support=True,
allow_submitter_edit=True)
state_2_2 = State.objects.create(name=ugettext_noop('permitted'),
workflow=workflow_2,
action_word=ugettext_noop('Permit'),
allow_create_poll=True,
allow_submitter_edit=True,
versioning=True,
dont_set_new_version_active=True)
state_2_3 = State.objects.create(name=ugettext_noop('accepted'),
workflow=workflow_2,
action_word=ugettext_noop('Accept'),
versioning=True)
state_2_4 = State.objects.create(name=ugettext_noop('rejected'),
workflow=workflow_2,
action_word=ugettext_noop('Reject'),
versioning=True)
state_2_5 = State.objects.create(name=ugettext_noop('withdrawed'),
workflow=workflow_2,
action_word=ugettext_noop('Withdraw'),
versioning=True)
state_2_6 = State.objects.create(name=ugettext_noop('adjourned'),
workflow=workflow_2,
action_word=ugettext_noop('Adjourn'),
versioning=True)
state_2_7 = State.objects.create(name=ugettext_noop('not concerned'),
workflow=workflow_2,
action_word=ugettext_noop('Do not concern'),
versioning=True)
state_2_8 = State.objects.create(name=ugettext_noop('commited a bill'),
workflow=workflow_2,
action_word=ugettext_noop('Commit a bill'),
versioning=True)
state_2_9 = State.objects.create(name=ugettext_noop('needs review'),
workflow=workflow_2,
versioning=True)
state_2_10 = State.objects.create(name=ugettext_noop('rejected (not authorized)'),
workflow=workflow_2,
action_word=ugettext_noop('reject (not authorized)'),
versioning=True)
state_2_1.next_states.add(state_2_2, state_2_5, state_2_10)
state_2_2.next_states.add(state_2_3, state_2_4, state_2_5, state_2_6, state_2_7, state_2_8, state_2_9)
workflow_2.first_state = state_2_1
workflow_2.save()

View File

@ -1,55 +0,0 @@
#!/usr/bin/env python
# -*- coding: utf-8 -*-
"""
openslides.motion.workflow
~~~~~~~~~~~~~~~~~~~~~~~~~~
This file is only for development. It will be moved out of
the openslides module before the next release.
:copyright: (c) 2011-2013 by the OpenSlides team, see AUTHORS.
:license: GNU GPL, see LICENSE for more details.
"""
from django.utils.translation import ugettext_noop
from .models import Workflow, State
def _init_builtin_workflows():
"""
Saves a simple and a complex workflow into the database.
This function is only called manually and lives here only for development.
"""
workflow_1 = Workflow(name=ugettext_noop('Simple Workflow'), id=1)
state_1_1 = State.objects.create(name=ugettext_noop('submitted'), workflow=workflow_1,
allow_create_poll=True, allow_support=True, allow_submitter_edit=True)
state_1_2 = State.objects.create(name=ugettext_noop('accepted'), workflow=workflow_1, action_word=ugettext_noop('accept'))
state_1_3 = State.objects.create(name=ugettext_noop('rejected'), workflow=workflow_1, action_word=ugettext_noop('reject'))
state_1_4 = State.objects.create(name=ugettext_noop('not decided'), workflow=workflow_1, action_word=ugettext_noop('do not decide'))
state_1_1.next_states.add(state_1_2, state_1_3, state_1_4)
state_1_1.save() # Is this neccessary?
workflow_1.first_state = state_1_1
workflow_1.save()
workflow_2 = Workflow(name=ugettext_noop('Complex Workflow'), id=2)
state_2_1 = State.objects.create(name=ugettext_noop('published'), workflow=workflow_2, allow_support=True, allow_submitter_edit=True)
state_2_2 = State.objects.create(name=ugettext_noop('permitted'), workflow=workflow_2, action_word=ugettext_noop('permit'),
allow_create_poll=True, allow_submitter_edit=True, versioning=True, dont_set_new_version_active=True)
state_2_3 = State.objects.create(name=ugettext_noop('accepted'), workflow=workflow_2, action_word=ugettext_noop('accept'), versioning=True)
state_2_4 = State.objects.create(name=ugettext_noop('rejected'), workflow=workflow_2, action_word=ugettext_noop('reject'), versioning=True)
state_2_5 = State.objects.create(name=ugettext_noop('withdrawed'), workflow=workflow_2,
action_word=ugettext_noop('withdraw'), versioning=True)
state_2_6 = State.objects.create(name=ugettext_noop('adjourned'), workflow=workflow_2, action_word=ugettext_noop('adjourn'), versioning=True)
state_2_7 = State.objects.create(name=ugettext_noop('not concerned'), workflow=workflow_2, versioning=True)
state_2_8 = State.objects.create(name=ugettext_noop('commited a bill'), workflow=workflow_2,
action_word=ugettext_noop('commit a bill'), versioning=True)
state_2_9 = State.objects.create(name=ugettext_noop('needs review'), workflow=workflow_2, versioning=True)
state_2_10 = State.objects.create(name=ugettext_noop('rejected (not authorized)'), workflow=workflow_2,
action_word=ugettext_noop('reject (not authorized)'), versioning=True)
state_2_1.next_states.add(state_2_2, state_2_5, state_2_10)
state_2_2.next_states.add(state_2_3, state_2_4, state_2_5, state_2_6, state_2_7, state_2_8, state_2_9)
state_2_1.save() # Is this neccessary?
state_2_2.save() # Is this neccessary?
workflow_2.first_state = state_2_1
workflow_2.save()

View File

@ -1,3 +1,18 @@
#!/usr/bin/env python
# -*- coding: utf-8 -*-
"""
openslides.participant
~~~~~~~~~~~~~~~~~~~~~~
The OpenSlides participant app.
:copyright: (c) 2011-2013 by the OpenSlides team, see AUTHORS.
:license: GNU GPL, see LICENSE for more details.
"""
from django.utils.translation import ugettext_noop from django.utils.translation import ugettext_noop
import openslides.participant.signals
NAME = ugettext_noop('Participant') NAME = ugettext_noop('Participant')

View File

@ -97,21 +97,8 @@ def import_users(csv_file):
return (count_success, error_messages) return (count_success, error_messages)
def get_or_create_registered_group(): def get_registered_group():
registered, created = Group.objects.get_or_create( """
name__iexact='Registered', defaults={'name': 'Registered'}) Returns the Group 'Registered'. Upper and lower case is possible.
if created: """
registered.permissions = Permission.objects.filter( return Group.objects.get(name__iexact='Registered')
codename__in=DEFAULT_PERMS)
registered.save()
return registered
def get_or_create_anonymous_group():
anonymous, created = Group.objects.get_or_create(
name__iexact='Anonymous', defaults={'name': 'Anonymous'})
if created:
anonymous.permissions = Permission.objects.filter(
codename__in=DEFAULT_PERMS)
anonymous.save()
return anonymous

View File

@ -1,233 +0,0 @@
[
{
"pk": 1,
"model": "auth.group",
"fields": {
"name": "Beobachter/in",
"permissions": [
[
"can_see_agenda",
"agenda",
"item"
],
[
"can_create_motion",
"motion",
"motion"
],
[
"can_see_motion",
"motion",
"motion"
],
[
"can_nominate_other",
"assignment",
"assignment"
],
[
"can_nominate_self",
"assignment",
"assignment"
],
[
"can_see_assignment",
"assignment",
"assignment"
],
[
"can_see_participant",
"participant",
"user"
],
[
"can_see_projector",
"projector",
"projectorslide"
],
[
"can_see_dashboard",
"projector",
"projectorslide"
]
]
}
},
{
"pk": 2,
"model": "auth.group",
"fields": {
"name": "Delegierte/r",
"permissions": [
[
"can_see_agenda",
"agenda",
"item"
],
[
"can_create_motion",
"motion",
"motion"
],
[
"can_see_motion",
"motion",
"motion"
],
[
"can_support_motion",
"motion",
"motion"
],
[
"can_nominate_other",
"assignment",
"assignment"
],
[
"can_nominate_self",
"assignment",
"assignment"
],
[
"can_see_assignment",
"assignment",
"assignment"
],
[
"can_see_participant",
"participant",
"user"
],
[
"can_see_projector",
"projector",
"projectorslide"
],
[
"can_see_dashboard",
"projector",
"projectorslide"
]
]
}
},
{
"pk": 3,
"model": "auth.group",
"fields": {
"name": "Versammlungsleitung",
"permissions": [
[
"can_manage_agenda",
"agenda",
"item"
],
[
"can_see_agenda",
"agenda",
"item"
],
[
"can_create_motion",
"motion",
"motion"
],
[
"can_manage_motion",
"motion",
"motion"
],
[
"can_see_motion",
"motion",
"motion"
],
[
"can_manage_assignment",
"assignment",
"assignment"
],
[
"can_nominate_other",
"assignment",
"assignment"
],
[
"can_nominate_self",
"assignment",
"assignment"
],
[
"can_see_assignment",
"assignment",
"assignment"
],
[
"can_manage_config",
"config",
"configstore"
],
[
"can_manage_participant",
"participant",
"user"
],
[
"can_see_participant",
"participant",
"user"
],
[
"can_manage_projector",
"projector",
"projectorslide"
],
[
"can_see_projector",
"projector",
"projectorslide"
],
[
"can_see_dashboard",
"projector",
"projectorslide"
]
]
}
},
{
"pk": 4,
"model": "auth.group",
"fields": {
"name": "Teilnehmerverwaltung",
"permissions": [
[
"can_see_agenda",
"agenda",
"item"
],
[
"can_manage_participant",
"participant",
"user"
],
[
"can_see_participant",
"participant",
"user"
],
[
"can_see_projector",
"projector",
"projectorslide"
],
[
"can_see_dashboard",
"projector",
"projectorslide"
]
]
}
}
]

View File

@ -19,7 +19,7 @@ from openslides.utils.forms import (
CssClassMixin, LocalizedModelMultipleChoiceField) CssClassMixin, LocalizedModelMultipleChoiceField)
from openslides.participant.models import User, Group from openslides.participant.models import User, Group
from openslides.participant.api import get_or_create_registered_group from openslides.participant.api import get_registered_group
class UserCreateForm(forms.ModelForm, CssClassMixin): class UserCreateForm(forms.ModelForm, CssClassMixin):
@ -30,7 +30,7 @@ class UserCreateForm(forms.ModelForm, CssClassMixin):
def __init__(self, *args, **kwargs): def __init__(self, *args, **kwargs):
if kwargs.get('instance', None) is None: if kwargs.get('instance', None) is None:
initial = kwargs.setdefault('initial', {}) initial = kwargs.setdefault('initial', {})
registered = get_or_create_registered_group() registered = get_registered_group()
initial['groups'] = [registered.pk] initial['groups'] = [registered.pk]
super(UserCreateForm, self).__init__(*args, **kwargs) super(UserCreateForm, self).__init__(*args, **kwargs)

View File

@ -257,9 +257,9 @@ def djangogroup_post_save(sender, instance, signal, *args, **kwargs):
@receiver(signals.post_save, sender=User) @receiver(signals.post_save, sender=User)
def user_post_save(sender, instance, *args, **kwargs): def user_post_save(sender, instance, *args, **kwargs):
from openslides.participant.api import get_or_create_registered_group
if not kwargs['created']: if not kwargs['created']:
return return
registered = get_or_create_registered_group() from openslides.participant.api import get_registered_group # TODO: Test, if global import is possible
registered = get_registered_group()
instance.groups.add(registered) instance.groups.add(registered)
instance.save() instance.save()

View File

@ -0,0 +1,70 @@
#!/usr/bin/env python
# -*- coding: utf-8 -*-
"""
openslides.participant.signals
~~~~~~~~~~~~~~~~~~~~~~~~~
Signals for the participant app.
:copyright: (c) 2011-2013 by the OpenSlides team, see AUTHORS.
:license: GNU GPL, see LICENSE for more details.
"""
from django.dispatch import receiver
from django.utils.translation import ugettext_noop
from django.contrib.contenttypes.models import ContentType
from django.contrib.auth.models import Permission
from openslides.core.signals import post_database_setup
from .models import Group
@receiver(post_database_setup, dispatch_uid='participant_create_builtin_groups')
def create_builtin_groups(sender, **kwargs):
"""
Creates the builtin groups: Anonymous, Registered, Delegates and Staff.
"""
# Anonymous and Registered
ct_projector = ContentType.objects.get(app_label='projector', model='projectorslide')
perm_1 = Permission.objects.get(content_type=ct_projector, codename='can_see_projector')
perm_2 = Permission.objects.get(content_type=ct_projector, codename='can_see_dashboard')
ct_agenda = ContentType.objects.get(app_label='agenda', model='item')
perm_3 = Permission.objects.get(content_type=ct_agenda, codename='can_see_agenda')
ct_motion = ContentType.objects.get(app_label='motion', model='motion')
perm_4 = Permission.objects.get(content_type=ct_motion, codename='can_see_motion')
ct_assignment = ContentType.objects.get(app_label='assignment', model='assignment')
perm_5 = Permission.objects.get(content_type=ct_assignment, codename='can_see_assignment')
ct_participant = ContentType.objects.get(app_label='participant', model='user')
perm_6 = Permission.objects.get(content_type=ct_participant, codename='can_see_participant')
group_anonymous = Group.objects.create(name=ugettext_noop('Anonymous'))
group_anonymous.permissions.add(perm_1, perm_2, perm_3, perm_4, perm_5, perm_6)
group_registered = Group.objects.create(name=ugettext_noop('Registered'))
group_registered.permissions.add(perm_1, perm_2, perm_3, perm_4, perm_5, perm_6)
# Delegates
perm_7 = Permission.objects.get(content_type=ct_motion, codename='can_create_motion')
perm_8 = Permission.objects.get(content_type=ct_motion, codename='can_support_motion')
perm_9 = Permission.objects.get(content_type=ct_assignment, codename='can_nominate_other')
perm_10 = Permission.objects.get(content_type=ct_assignment, codename='can_nominate_self')
group_delegates = Group.objects.create(name=ugettext_noop('Delegates'))
group_delegates.permissions.add(perm_7, perm_8, perm_9, perm_10)
# Staff
perm_11 = Permission.objects.get(content_type=ct_agenda, codename='can_manage_agenda')
perm_12 = Permission.objects.get(content_type=ct_motion, codename='can_manage_motion')
perm_13 = Permission.objects.get(content_type=ct_assignment, codename='can_manage_assignment')
perm_14 = Permission.objects.get(content_type=ct_participant, codename='can_manage_participant')
perm_15 = Permission.objects.get(content_type=ct_projector, codename='can_manage_projector')
ct_config = ContentType.objects.get(app_label='config', model='configstore')
perm_16 = Permission.objects.get(content_type=ct_config, codename='can_manage_config')
group_staff = Group.objects.create(name=ugettext_noop('Staff'))
group_staff.permissions.add(perm_7, perm_9, perm_10, perm_11, perm_12, perm_13, perm_14, perm_15, perm_16)

View File

@ -0,0 +1,25 @@
#!/usr/bin/env python
# -*- coding: utf-8 -*-
"""
openslides.utils.management.commands.syncdb
~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
Overrides the Django syncdb command to setup the database.
:copyright: (c) 2011-2013 by the OpenSlides team, see AUTHORS.
:license: GNU GPL, see LICENSE for more details.
"""
from django.core.management.commands.syncdb import Command as _Command
from openslides.core.signals import post_database_setup
class Command(_Command):
"""
Setup the database and sends the signal post_database_setup.
"""
def handle_noargs(self, *args, **kwargs):
return_value = super(Command, self).handle_noargs(*args, **kwargs)
post_database_setup.send(sender=self)
return return_value

27
openslides/utils/test.py Normal file
View File

@ -0,0 +1,27 @@
#!/usr/bin/env python
# -*- coding: utf-8 -*-
"""
openslides.utils.test
~~~~~~~~~~~~~~~~~~~~~
Unit test class.
:copyright: 2011-2013 by OpenSlides team, see AUTHORS.
:license: GNU GPL, see LICENSE for more details.
"""
from django.test import TestCase as _TestCase
from openslides.core.signals import post_database_setup
class TestCase(_TestCase):
"""
Overwrites Django's TestCase class to call the post_database_setup
signal after the preparation of every test.
"""
def _pre_setup(self, *args, **kwargs):
return_value = super(TestCase, self)._pre_setup(*args, **kwargs)
post_database_setup.send(sender=self)
return return_value

View File

@ -10,10 +10,10 @@
:license: GNU GPL, see LICENSE for more details. :license: GNU GPL, see LICENSE for more details.
""" """
from django.test import TestCase
from django.test.client import Client from django.test.client import Client
from django.db.models.query import EmptyQuerySet from django.db.models.query import EmptyQuerySet
from openslides.utils.test import TestCase
from openslides.projector.api import get_active_slide from openslides.projector.api import get_active_slide
from openslides.participant.models import User from openslides.participant.models import User
from openslides.agenda.models import Item from openslides.agenda.models import Item
@ -95,7 +95,6 @@ class ItemTest(TestCase):
self.assertEqual(self.item5.print_related_type(), 'Releateditem') self.assertEqual(self.item5.print_related_type(), 'Releateditem')
class ViewTest(TestCase): class ViewTest(TestCase):
def setUp(self): def setUp(self):
self.item1 = Item.objects.create(title='item1') self.item1 = Item.objects.create(title='item1')

View File

@ -8,8 +8,7 @@
:license: GNU GPL, see LICENSE for more details. :license: GNU GPL, see LICENSE for more details.
""" """
from django.test import TestCase from openslides.utils.test import TestCase
from openslides.participant.models import User from openslides.participant.models import User
from openslides.config.models import config from openslides.config.models import config
from openslides.motion.models import Motion, Workflow, State from openslides.motion.models import Motion, Workflow, State
@ -76,7 +75,7 @@ class ModelTest(TestCase):
self.assertEqual(motion.title, 'v2') self.assertEqual(motion.title, 'v2')
motion.version = None motion.version = None
motion.version = None # Test to set a version to None, which is already None motion.version = None # Test to set a version to None, which is already None
self.assertEqual(motion.title, 'v3') self.assertEqual(motion.title, 'v3')
with self.assertRaises(ValueError): with self.assertRaises(ValueError):
@ -113,18 +112,18 @@ class ModelTest(TestCase):
self.motion.state = State.objects.get(pk=6) self.motion.state = State.objects.get(pk=6)
self.assertEqual(self.motion.state.name, 'permitted') self.assertEqual(self.motion.state.name, 'permitted')
self.assertEqual(self.motion.state.get_action_word(), 'permit') self.assertEqual(self.motion.state.get_action_word(), 'Permit')
with self.assertRaises(WorkflowError): with self.assertRaises(WorkflowError):
self.motion.support(self.test_user) self.motion.support(self.test_user)
with self.assertRaises(WorkflowError): with self.assertRaises(WorkflowError):
self.motion.unsupport(self.test_user) self.motion.unsupport(self.test_user)
def test_new_states_or_workflows(self): def test_new_states_or_workflows(self):
workflow_1 = Workflow(name='W1', id=1000) workflow_1 = Workflow.objects.create(name='W1')
state_1 = State.objects.create(name='S1', workflow=workflow_1) state_1 = State.objects.create(name='S1', workflow=workflow_1)
workflow_1.first_state = state_1 workflow_1.first_state = state_1
workflow_1.save() workflow_1.save()
workflow_2 = Workflow(name='W2', id=2000) workflow_2 = Workflow.objects.create(name='W2')
state_2 = State.objects.create(name='S2', workflow=workflow_2) state_2 = State.objects.create(name='S2', workflow=workflow_2)
workflow_2.first_state = state_2 workflow_2.first_state = state_2
workflow_2.save() workflow_2.save()

View File

@ -7,9 +7,9 @@
:license: GNU GPL, see LICENSE for more details. :license: GNU GPL, see LICENSE for more details.
""" """
from django.test import TestCase
from openslides import get_version, get_git_commit_id from openslides import get_version, get_git_commit_id
from openslides.utils.test import TestCase
class InitTest(TestCase): class InitTest(TestCase):
def test_get_version(self): def test_get_version(self):

View File

@ -10,8 +10,7 @@
:license: GNU GPL, see LICENSE for more details. :license: GNU GPL, see LICENSE for more details.
""" """
from django.test import TestCase from openslides.utils.test import TestCase
from openslides.utils.person import get_person, Persons from openslides.utils.person import get_person, Persons
from openslides.participant.api import gen_username, gen_password from openslides.participant.api import gen_username, gen_password
from openslides.participant.models import User, Group from openslides.participant.models import User, Group