models.py 12.7 KB
Newer Older
1
from django.db import models
2
from django.core.mail import send_mail
3
from djangoldp.models import Model
4
from django.conf import settings
5
from django.contrib.auth import get_user_model
6
from django.db.models.signals import post_save, m2m_changed
7
from django.dispatch import receiver
8 9
from djangoldp_conversation.models import Conversation, Message
from djangoldp_like.models import Like
10 11 12
from django.utils import timezone

from django.template import loader
13

14 15 16 17 18 19 20
class Country (Model):
    code = models.CharField(max_length=2, verbose_name="ISO Code")
    name = models.CharField(max_length=64, verbose_name="Country name")
    
    def __str__(self):
        return self.name

21 22 23 24 25 26 27 28 29 30 31 32 33 34
class Language (Model):
    code = models.CharField(max_length=2, verbose_name="ISO Code")
    name = models.CharField(max_length=64, verbose_name="Language name")

    def __str__(self):
        return self.name

class Organisation (Model):
    name = models.CharField(max_length=128, verbose_name="Name")
    website = models.CharField(max_length=4096, verbose_name="Website")

    def __str__(self):
        return self.name

Benoit Alessandroni's avatar
Benoit Alessandroni committed
35 36 37
class Step (Model):
    name = models.CharField(max_length=128, verbose_name="Name")
    order = models.IntegerField(verbose_name="Order", blank=True, null=True, default=0)
38 39 40
    
    class Meta:
        anonymous_perms = ['view']
Benoit Alessandroni's avatar
Benoit Alessandroni committed
41
        serializer_fields=["@id", "resources", "name", "order"]
42 43 44 45
        nested_fields=["resources"]
        container_path = 'steps/'
        rdf_type = 'coopstarter:step'
    
Benoit Alessandroni's avatar
Benoit Alessandroni committed
46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66
    def __str__(self):
        return self.name

class Format (Model):
    name = models.CharField(max_length=128, verbose_name="Title")

    def __str__(self):
        return self.name

class Field (Model):
    name = models.CharField(max_length=128, verbose_name="Title")

    def __str__(self):
        return self.name

class Type (Model):
    name = models.CharField(max_length=128, verbose_name="Title")

    def __str__(self):
        return self.name

67
class Entrepreneur(Model):
68
    user = models.OneToOneField(settings.AUTH_USER_MODEL, related_name="entrepreneur_profile")
69
    organisation = models.ForeignKey(Organisation, null=True, on_delete=models.CASCADE, related_name="entrepreneurs")
70 71
    
    class Meta:
Benoit Alessandroni's avatar
Benoit Alessandroni committed
72 73 74 75 76
        auto_author = 'user'
        owner_field = 'user'
        owner_perms = ['inherit', 'change', 'control', 'delete']
        anonymous_perms = ['view']
        authenticated_perms = ['inherit', 'add']
77
        serializer_fields=["@id", "user", "organisation"]
78 79 80 81
        nested_fields=["user", "organisation"]
        container_path = 'entrepreneurs/'
        rdf_type = 'coopstarter:entrepreneur'
    
82 83 84 85
    def __str__(self):
        return self.user.get_full_name()

class Mentor(Model):
86
    user = models.OneToOneField(settings.AUTH_USER_MODEL, related_name="mentor_profile")
87
    phone = models.CharField(max_length=25, null=True, blank=True, verbose_name='Phone number')
88 89
    organisation = models.ForeignKey(Organisation, null=True, on_delete=models.CASCADE, related_name="mentors")
    country = models.ForeignKey(Country, null=True, related_name="mentors")
Benoit Alessandroni's avatar
Benoit Alessandroni committed
90
    languages = models.ManyToManyField(Language, blank=True)
91 92

    headline = models.CharField(max_length=256, blank=True, verbose_name='Headline or current position')
93
    city = models.CharField(max_length=256, blank=True, verbose_name='City')
94 95 96 97

    biography = models.TextField(blank=True, verbose_name="Tell us more about your activities")
    skills = models.TextField(blank=True, verbose_name="What skills can you share with our entrepreneurs ?")

Benoit Alessandroni's avatar
Benoit Alessandroni committed
98 99
    fields = models.ManyToManyField(Field, blank=True)

100 101
    linkedin = models.CharField(max_length=256, null=True, blank=True, verbose_name='Linkedin account')
    twitter = models.CharField(max_length=256, null=True, blank=True, verbose_name='Twitter account')
102
    registered_on = models.DateTimeField(default=timezone.now)
103

104
    class Meta:
Benoit Alessandroni's avatar
Benoit Alessandroni committed
105
        auto_author = 'user'
106 107 108
        serializer_fields=["@id", "phone", "headline", "biography", "city", "skills", "linkedin",\
                           "twitter", "organisation", "fields", "languages", "country"]
        nested_fields=["user", "organisation", "fields", "languages", "country"]
109 110
        container_path = 'mentors/'
        rdf_type = 'coopstarter:mentor'
Benoit Alessandroni's avatar
Benoit Alessandroni committed
111 112 113 114
        owner_field = 'user'
        owner_perms = ['inherit', 'change', 'control', 'delete']
        anonymous_perms = ['view']
        authenticated_perms = ['inherit', 'add']
115

116 117
    def __str__(self):
        return self.user.get_full_name()
118

119 120 121
class Review (Model):
    comment =  models.TextField(verbose_name="Comment", blank=True)
    status = models.CharField(max_length=32, choices=(('pending', 'Pending'), ('inappropriate', 'Inappropriate'), ('validated', 'Validated'), ('to_improve', 'Improvement required')), verbose_name="Resource status", blank=True, null=True)
122
    reviewer = models.ForeignKey(settings.AUTH_USER_MODEL, null=True, on_delete=models.CASCADE, related_name='reviews')
123 124

    class Meta:
125
        owner_field = 'reviewer'
126
        anonymous_perms = ['view']
127
        authenticated_perms = ['inherit', 'add', 'change']
128 129
        serializer_fields=["@id", "reviewer", "resource", "comment", "status"]
        nested_fields=["reviewer", "resource"]
130 131 132 133 134 135 136
        owner_perms = ['inherit', 'change', 'control', 'delete']
        container_path = 'reviews/'
        rdf_type = 'coopstarter:review'

    def __str__(self):
        return self.comment

137 138
class Resource (Model):
    # Mandatory Fields
139
    name = models.CharField(max_length=32, verbose_name="Title")
140

Benoit Alessandroni's avatar
Benoit Alessandroni committed
141
    format = models.ForeignKey(Format, null=True, related_name='resources')
142
    publication_year = models.IntegerField(verbose_name="Publication Year")
Benoit Alessandroni's avatar
Benoit Alessandroni committed
143
    language = models.ForeignKey(Language, blank=True, verbose_name="Language", related_name='resources')
144
    fields = models.ManyToManyField(Field, blank=True, related_name='resources')
145
    country = models.ForeignKey(Country, null=True)
146
    uri = models.CharField(max_length=4086, verbose_name="Location/weblink")
147 148
    author = models.CharField(max_length=32, verbose_name="Author")
    skills = models.TextField(verbose_name="Learning outcomes/skills")
149

150
    # Complementary fields
151
    description = models.TextField(verbose_name="Description", null=True)
152
    iframe_link = models.TextField(verbose_name="Iframe link", blank=True, null=True)
153
    preview_image = models.URLField(blank=True, null=True)
154

155
    # Classification Fields
Benoit Alessandroni's avatar
Benoit Alessandroni committed
156
    target = models.CharField(max_length=32, choices=(('mentor', 'Mentor'), ('entrepreneur', 'Entrepreneur'), ('public', 'Public')), verbose_name="Target audience", blank=True, null=True)
157
    type = models.ForeignKey(Type, blank=True, verbose_name="Type of content", related_name='resources')
Benoit Alessandroni's avatar
Benoit Alessandroni committed
158

159
    steps = models.ManyToManyField(Step, blank=True, related_name="resources")
160
    sharing = models.CharField(max_length=32, choices=(('private', 'Private (nobody)'), ('public', 'Public (everybody)')), verbose_name="Sharing profile", blank=True, null=True)
161

162
    # Relations to other models
163
    submitter = models.ForeignKey(settings.AUTH_USER_MODEL, null=True, on_delete=models.CASCADE, related_name='resources')
164
    related = models.ManyToManyField("self", blank=True)
165
    conversations = models.ManyToManyField(Conversation, blank=True, related_name='resources')
166
    likes = models.ManyToManyField(Like, blank=True, related_name='resources')
167
    review = models.OneToOneField(Review, null=True, verbose_name="Associated review", related_name='resource')
168
 
169
    class Meta:
170
        auto_author='submitter'
Benoit Alessandroni's avatar
Benoit Alessandroni committed
171 172
        owner_field = 'submitter'
        owner_perms = ['inherit', 'change', 'control', 'delete']
173
        nested_fields=["format", "conversations", "steps", "language", "fields",\
174
                       "type", "submitter", "related", "likes", "review", "country"]
175
        serializer_fields=["@id", "name", "description", "skills", "author", "target", "uri", "publication_year", "format",\
Benoit Alessandroni's avatar
Benoit Alessandroni committed
176
                           "conversations", "steps", "language", "fields", "country",\
177
                           "type", "submitter", "related", "likes", "review", "sharing", "preview_image"]
178 179
        container_path = 'resources/'
        rdf_type = 'coopstarter:resource'
180 181
        anonymous_perms = ['view']
        authenticated_perms = ['inherit', 'add']
182 183
        rdf_context = {'preview_image': 'foaf:depiction'}

184
    def __str__(self):
185
        return self.name
186 187 188

class Request (Model):
    # Mandatory Fields
189
    name = models.CharField(max_length=32, verbose_name="Title")
190
    description = models.TextField(verbose_name="Description")
Alice's avatar
Alice committed
191
    status = models.TextField(verbose_name="Status", choices=(('untreated', 'Untreated'), ('dealt-with', 'Dealt With')), default="untreated")
192 193
    
    language = models.ForeignKey(Language, blank=True, verbose_name="Language")
194
    fields = models.ManyToManyField(Field, blank=True)
195
    country = models.ForeignKey(Country, null=True)
196
    
Benoit Alessandroni's avatar
Benoit Alessandroni committed
197
    organisation = models.ForeignKey(Organisation, on_delete=models.CASCADE, related_name="requests")
198
    skills = models.TextField(verbose_name="Learning outcomes/skills")
Benoit Alessandroni's avatar
Benoit Alessandroni committed
199 200
    target = models.CharField(max_length=32, choices=(('mentor', 'Mentor'), ('entrepreneur', 'Entrepreneur'), ('public', 'Public')), verbose_name="Target audience", blank=True, null=True)
    
201
    submitter = models.ForeignKey(settings.AUTH_USER_MODEL, null=True, on_delete=models.CASCADE, related_name='requests')
Alice's avatar
Alice committed
202
<<<<<<< Updated upstream
203
    reviewer = models.ForeignKey(Mentor, null=True, verbose_name="Reviewer", related_name='requests')
Alice's avatar
Alice committed
204 205 206 207
=======
    reviewer = models.ForeignKey(settings.AUTH_USER_MODEL, null=True, on_delete=models.CASCADE, related_name='reviewed_requests')

>>>>>>> Stashed changes
208
    created_on = models.DateTimeField(default=timezone.now)
209 210

    class Meta:
211 212
        ordering = ['-created_on']
        auto_author='submitter'
213
        anonymous_perms = ['view']
214
        authenticated_perms = ['inherit', 'add', 'change']
215
        owner_field = 'submitter'
Alice's avatar
Alice committed
216
<<<<<<< Updated upstream
217
        serializer_fields=["@id", "name", "description", "status", "skills", "fields", "language", "organisation", "submitter", "reviewer", "created_on", "target", "country"]
Alice's avatar
Alice committed
218 219 220 221
=======
        serializer_fields=["@id", "name", "description", "skills", "fields", "language",\
                           "organisation", "submitter", "reviewer", "created_on", "target", "country"]
>>>>>>> Stashed changes
222
        owner_perms = ['inherit', 'change', 'control', 'delete']
223
        nested_fields=["language", "fields", "organisation", "submitter", "country"]
224 225 226
        container_path = 'requests/'
        rdf_type = 'coopstarter:request'
        
227
    def __str__(self):
228 229
        return self.name

230 231 232
@receiver(post_save, sender=Resource)
def create_review(sender, instance, created, **kwargs):
    if created:
Benoit Alessandroni's avatar
Benoit Alessandroni committed
233 234 235 236
        if not instance.review:
            reviewInstance = Review.objects.create(resource=instance, status="pending")
            instance.review = reviewInstance
            instance.save()
237
    if not created:
Benoit Alessandroni's avatar
Benoit Alessandroni committed
238 239 240 241 242 243 244 245 246 247 248 249 250 251 252 253 254 255 256
        if instance.review:
            if instance.review.status == 'to_improve':
                review = instance.review
                review.status='pending'
                review.save()
                message = loader.render_to_string(
                    'reviewer_modification_notification.txt', 
                    {
                        'review': review,
                        'resource': instance
                    }
                )

                send_mail(
                    'The resource you reviewed has been modified',
                    message,
                    review.reviewer.email,
                    [review.reviewer.email]
                )
257

258 259 260 261 262 263 264 265 266
@receiver(post_save, sender=Review)
def update_review(sender, instance, created, **kwargs):
    if not created:
        if instance.resource:
            resource = instance.resource
            if instance.status == 'validated':
                message = loader.render_to_string(
                    'resource_validation_notification.txt', 
                    {
267
                        'review': instance,
268 269 270 271 272 273 274
                        'resource': resource
                    }
                )
            elif instance.status == 'to_improve':
                message = loader.render_to_string(
                    'resource_improvement_notification.txt', 
                    {
275
                        'review': instance,
276 277 278
                        'resource': resource
                    }
                )
279
            elif instance.status == 'inappropriate':
280 281 282
                message = loader.render_to_string(
                    'resource_refusal_notification.txt', 
                    {
283
                        'review': instance,
284 285 286 287
                        'resource': resource
                    }
                )

288 289 290 291 292 293 294
            if instance.status != 'pending':
                send_mail(
                    'The resource you submitted has been reviewed',
                    message,
                    resource.submitter.email,
                    [resource.submitter.email]
                )