From ed11ad30e8fa47d592fbf034e382554c5b501b4f Mon Sep 17 00:00:00 2001 From: Rikuoja Date: Fri, 29 Apr 2016 16:27:01 +0300 Subject: [PATCH] Add organization to hearing --- .../migrations/0015_add_organization_model.py | 42 +++++++++++++++++++ democracy/models/__init__.py | 2 + democracy/models/hearing.py | 7 +++- democracy/models/organization.py | 18 ++++++++ democracy/tests/conftest.py | 7 +++- democracy/tests/test_hearing.py | 14 ++++++- democracy/views/hearing.py | 6 ++- 7 files changed, 92 insertions(+), 4 deletions(-) create mode 100644 democracy/migrations/0015_add_organization_model.py create mode 100644 democracy/models/organization.py diff --git a/democracy/migrations/0015_add_organization_model.py b/democracy/migrations/0015_add_organization_model.py new file mode 100644 index 00000000..a276de6b --- /dev/null +++ b/democracy/migrations/0015_add_organization_model.py @@ -0,0 +1,42 @@ +# -*- coding: utf-8 -*- +# Generated by Django 1.9 on 2016-05-19 08:11 +from __future__ import unicode_literals + +from django.conf import settings +from django.db import migrations, models +import django.db.models.deletion +import django.utils.timezone + + +class Migration(migrations.Migration): + + dependencies = [ + migrations.swappable_dependency(settings.AUTH_USER_MODEL), + ('democracy', '0014_non_editable_id'), + ] + + operations = [ + migrations.CreateModel( + name='Organization', + fields=[ + ('created_at', models.DateTimeField(db_index=True, default=django.utils.timezone.now, editable=False, verbose_name='time of creation')), + ('modified_at', models.DateTimeField(default=django.utils.timezone.now, editable=False, verbose_name='time of last modification')), + ('published', models.BooleanField(db_index=True, default=True, verbose_name='public')), + ('deleted', models.BooleanField(db_index=True, default=False, editable=False, verbose_name='deleted')), + ('id', models.CharField(editable=False, max_length=32, primary_key=True, serialize=False, verbose_name='identifier')), + ('name', models.CharField(max_length=255, unique=True, verbose_name='name')), + ('admin_users', models.ManyToManyField(blank=True, related_name='admin_organizations', to=settings.AUTH_USER_MODEL)), + ('created_by', models.ForeignKey(blank=True, editable=False, null=True, on_delete=django.db.models.deletion.CASCADE, related_name='organization_created', to=settings.AUTH_USER_MODEL, verbose_name='created by')), + ('modified_by', models.ForeignKey(blank=True, editable=False, null=True, on_delete=django.db.models.deletion.CASCADE, related_name='organization_modified', to=settings.AUTH_USER_MODEL, verbose_name='last modified by')), + ], + options={ + 'verbose_name': 'organization', + 'verbose_name_plural': 'organizations', + }, + ), + migrations.AddField( + model_name='hearing', + name='organization', + field=models.ForeignKey(blank=True, null=True, on_delete=django.db.models.deletion.CASCADE, related_name='hearings', to='democracy.Organization', verbose_name='organization'), + ), + ] diff --git a/democracy/models/__init__.py b/democracy/models/__init__.py index d3b9135b..c12bf544 100644 --- a/democracy/models/__init__.py +++ b/democracy/models/__init__.py @@ -1,6 +1,7 @@ from .hearing import Hearing, HearingComment, HearingImage from .label import Label from .section import Section, SectionComment, SectionImage, SectionType +from .organization import Organization __all__ = [ "Hearing", @@ -11,4 +12,5 @@ "SectionComment", "SectionImage", "SectionType", + "Organization", ] diff --git a/democracy/models/hearing.py b/democracy/models/hearing.py index 312a67aa..f57799e0 100644 --- a/democracy/models/hearing.py +++ b/democracy/models/hearing.py @@ -18,6 +18,7 @@ from .base import BaseModelManager, Commentable, StringIdBaseModel from .comment import BaseComment from .images import BaseImage +from .organization import Organization class HearingQueryset(models.QuerySet): @@ -37,7 +38,11 @@ class Hearing(Commentable, StringIdBaseModel): borough = models.CharField(verbose_name=_('borough'), blank=True, default='', max_length=200) servicemap_url = models.CharField(verbose_name=_('service map URL'), default='', max_length=255, blank=True) geojson = GeometryField(blank=True, null=True, verbose_name=_('area')) - + organization = models.ForeignKey( + Organization, + verbose_name=_('organization'), + related_name="hearings", blank=True, null=True + ) labels = models.ManyToManyField("Label", verbose_name=_('labels'), blank=True) followers = models.ManyToManyField( settings.AUTH_USER_MODEL, diff --git a/democracy/models/organization.py b/democracy/models/organization.py new file mode 100644 index 00000000..c413f9b9 --- /dev/null +++ b/democracy/models/organization.py @@ -0,0 +1,18 @@ +from .base import StringIdBaseModel +from django.db import models +from django.conf import settings +from django.utils.translation import ugettext_lazy as _ + + +class Organization(StringIdBaseModel): + name = models.CharField(verbose_name=_('name'), max_length=255, unique=True) + admin_users = models.ManyToManyField( + settings.AUTH_USER_MODEL, blank=True, related_name='admin_organizations' + ) + + class Meta: + verbose_name = _('organization') + verbose_name_plural = _('organizations') + + def __str__(self): + return self.name diff --git a/democracy/tests/conftest.py b/democracy/tests/conftest.py index 81f76779..f840069e 100644 --- a/democracy/tests/conftest.py +++ b/democracy/tests/conftest.py @@ -7,7 +7,7 @@ from democracy.enums import Commenting, InitialSectionType from democracy.factories.hearing import HearingFactory, LabelFactory -from democracy.models import Hearing, HearingComment, Label, Section, SectionType +from democracy.models import Hearing, HearingComment, Label, Section, SectionType, Organization from democracy.tests.utils import assert_ascending_sequence, create_default_images @@ -30,6 +30,11 @@ def pytest_configure(): ) +@pytest.fixture() +def default_organization(): + return Organization.objects.create(name='The department for squirrel welfare') + + @pytest.fixture() def default_hearing(john_doe): """ diff --git a/democracy/tests/test_hearing.py b/democracy/tests/test_hearing.py index 1120d75c..912f9c1b 100644 --- a/democracy/tests/test_hearing.py +++ b/democracy/tests/test_hearing.py @@ -121,7 +121,7 @@ def test_8_get_detail_check_properties(api_client, default_hearing): assert set(data.keys()) >= { 'abstract', 'borough', 'close_at', 'closed', 'created_at', 'id', 'images', 'labels', 'n_comments', 'open_at', 'sections', 'servicemap_url', - 'title' + 'title', 'organization' } @@ -213,6 +213,18 @@ def test_8_get_detail_labels(api_client): assert label_one.label in data['labels'] +@pytest.mark.django_db +def test_8_get_detail_organization(api_client, default_hearing, default_organization): + default_hearing.organization = default_organization + default_hearing.save() + response = api_client.get(get_detail_url(default_hearing.id)) + + data = get_data_from_response(response) + + assert 'results' not in data + assert data['organization'] == default_organization.name + + @pytest.mark.django_db def test_7_get_detail_servicemap(api_client): hearing = Hearing( diff --git a/democracy/views/hearing.py b/democracy/views/hearing.py index ef36870c..e1e8b749 100644 --- a/democracy/views/hearing.py +++ b/democracy/views/hearing.py @@ -48,6 +48,10 @@ class HearingSerializer(serializers.ModelSerializer): comments = HearingCommentSerializer.get_field_serializer(many=True, read_only=True) commenting = EnumField(enum_type=Commenting) geojson = JSONField() + organization = serializers.SlugRelatedField( + read_only=True, + slug_field='name' + ) def get_sections(self, hearing): queryset = hearing.sections.all() @@ -65,7 +69,7 @@ class Meta: 'commenting', 'published', 'labels', 'open_at', 'close_at', 'created_at', 'servicemap_url', 'images', 'sections', 'images', - 'closed', 'comments', 'geojson', 'slug' + 'closed', 'comments', 'geojson', 'organization', 'slug' ]