src/cm/security.py
author gibus
Wed, 11 Sep 2013 23:13:01 +0200
changeset 532 0bad3613f59d
parent 523 cc1cd48289e0
child 540 dce127afac9d
permissions -rw-r--r--
Reverse to YUI 3.0.0 since with YUI.3.10.3, comment content including words 'paragraph' or 'section' do not show up on Firefox, this is weird and has to be investigated.
Ignore whitespace changes - Everywhere: Within whitespace: At end of lines:
0
40c8f766c9b8 import from internal svn r 4007
raph
parents:
diff changeset
     1
from django.conf import settings
40c8f766c9b8 import from internal svn r 4007
raph
parents:
diff changeset
     2
from django.contrib.auth import REDIRECT_FIELD_NAME
40c8f766c9b8 import from internal svn r 4007
raph
parents:
diff changeset
     3
from django.contrib.auth.models import Permission
40c8f766c9b8 import from internal svn r 4007
raph
parents:
diff changeset
     4
from django.contrib.contenttypes.models import ContentType
40c8f766c9b8 import from internal svn r 4007
raph
parents:
diff changeset
     5
from django.shortcuts import get_object_or_404
40c8f766c9b8 import from internal svn r 4007
raph
parents:
diff changeset
     6
from django.core.urlresolvers import reverse
40c8f766c9b8 import from internal svn r 4007
raph
parents:
diff changeset
     7
from django.http import HttpResponseRedirect
40c8f766c9b8 import from internal svn r 4007
raph
parents:
diff changeset
     8
from django.utils.http import urlquote
40c8f766c9b8 import from internal svn r 4007
raph
parents:
diff changeset
     9
from django.db.models import Q
287
fc5ed157ebfe add api: basic auth / unit tests / online doc (based on django-piston)
raph
parents: 210
diff changeset
    10
from piston.utils import rc
0
40c8f766c9b8 import from internal svn r 4007
raph
parents:
diff changeset
    11
import logging
522
c9c2148f09c9 improves performence of text_view_comments by memoizing permission computations.
gibus
parents: 470
diff changeset
    12
from django.core.cache import cache
c9c2148f09c9 improves performence of text_view_comments by memoizing permission computations.
gibus
parents: 470
diff changeset
    13
from hashlib import sha1
0
40c8f766c9b8 import from internal svn r 4007
raph
parents:
diff changeset
    14
40c8f766c9b8 import from internal svn r 4007
raph
parents:
diff changeset
    15
from cm.models import *
40c8f766c9b8 import from internal svn r 4007
raph
parents:
diff changeset
    16
from cm import cm_settings
40c8f766c9b8 import from internal svn r 4007
raph
parents:
diff changeset
    17
from cm.exception import UnauthorizedException
449
5387c032df35 In role_teacher model, individual students can see their own comments but also teacher's ones, whereas individual students' comments cannot be seen by students.
gibus
parents: 355
diff changeset
    18
from cm.cm_settings import DECORATED_CREATORS
0
40c8f766c9b8 import from internal svn r 4007
raph
parents:
diff changeset
    19
40c8f766c9b8 import from internal svn r 4007
raph
parents:
diff changeset
    20
def get_request_user(request):
40c8f766c9b8 import from internal svn r 4007
raph
parents:
diff changeset
    21
    if request and request.user and not request.user.is_anonymous():
40c8f766c9b8 import from internal svn r 4007
raph
parents:
diff changeset
    22
        user = request.user
40c8f766c9b8 import from internal svn r 4007
raph
parents:
diff changeset
    23
    else:
40c8f766c9b8 import from internal svn r 4007
raph
parents:
diff changeset
    24
        user = None
40c8f766c9b8 import from internal svn r 4007
raph
parents:
diff changeset
    25
    return user
40c8f766c9b8 import from internal svn r 4007
raph
parents:
diff changeset
    26
    
40c8f766c9b8 import from internal svn r 4007
raph
parents:
diff changeset
    27
## Permission functions
40c8f766c9b8 import from internal svn r 4007
raph
parents:
diff changeset
    28
class FakeRequest(object):
40c8f766c9b8 import from internal svn r 4007
raph
parents:
diff changeset
    29
    def __init__(self, user):
40c8f766c9b8 import from internal svn r 4007
raph
parents:
diff changeset
    30
        self.user = user
40c8f766c9b8 import from internal svn r 4007
raph
parents:
diff changeset
    31
40c8f766c9b8 import from internal svn r 4007
raph
parents:
diff changeset
    32
def user_has_perm(user, perm_name, text=None):
40c8f766c9b8 import from internal svn r 4007
raph
parents:
diff changeset
    33
    return has_perm(FakeRequest(user),perm_name, text)
40c8f766c9b8 import from internal svn r 4007
raph
parents:
diff changeset
    34
    
40c8f766c9b8 import from internal svn r 4007
raph
parents:
diff changeset
    35
def has_perm(request, perm_name, text=None):
40c8f766c9b8 import from internal svn r 4007
raph
parents:
diff changeset
    36
    # bypass sec if NO_SECURITY
40c8f766c9b8 import from internal svn r 4007
raph
parents:
diff changeset
    37
    if cm_settings.NO_SECURITY:
40c8f766c9b8 import from internal svn r 4007
raph
parents:
diff changeset
    38
        return True
40c8f766c9b8 import from internal svn r 4007
raph
parents:
diff changeset
    39
    
40c8f766c9b8 import from internal svn r 4007
raph
parents:
diff changeset
    40
    # make sure perm exist
40c8f766c9b8 import from internal svn r 4007
raph
parents:
diff changeset
    41
    assert Permission.objects.get(codename=perm_name)
40c8f766c9b8 import from internal svn r 4007
raph
parents:
diff changeset
    42
    
40c8f766c9b8 import from internal svn r 4007
raph
parents:
diff changeset
    43
    user = get_request_user(request)
523
cc1cd48289e0 Fixes AttributeError: 'FakeRequest' object has no attribute 'GET'
gibus
parents: 522
diff changeset
    44
    try:
cc1cd48289e0 Fixes AttributeError: 'FakeRequest' object has no attribute 'GET'
gibus
parents: 522
diff changeset
    45
      myself = request.GET.get('name', None)
cc1cd48289e0 Fixes AttributeError: 'FakeRequest' object has no attribute 'GET'
gibus
parents: 522
diff changeset
    46
    except AttributeError:
cc1cd48289e0 Fixes AttributeError: 'FakeRequest' object has no attribute 'GET'
gibus
parents: 522
diff changeset
    47
      myself = None
522
c9c2148f09c9 improves performence of text_view_comments by memoizing permission computations.
gibus
parents: 470
diff changeset
    48
    key = sha1(str((settings.SITE_URL, 'has_perm', (user, myself, text, perm_name)))).hexdigest()
c9c2148f09c9 improves performence of text_view_comments by memoizing permission computations.
gibus
parents: 470
diff changeset
    49
    val = cache.get(key)
c9c2148f09c9 improves performence of text_view_comments by memoizing permission computations.
gibus
parents: 470
diff changeset
    50
    if val != None:
c9c2148f09c9 improves performence of text_view_comments by memoizing permission computations.
gibus
parents: 470
diff changeset
    51
      return val
0
40c8f766c9b8 import from internal svn r 4007
raph
parents:
diff changeset
    52
40c8f766c9b8 import from internal svn r 4007
raph
parents:
diff changeset
    53
    if user and user.is_staff:
522
c9c2148f09c9 improves performence of text_view_comments by memoizing permission computations.
gibus
parents: 470
diff changeset
    54
        cache.set(key, True)
0
40c8f766c9b8 import from internal svn r 4007
raph
parents:
diff changeset
    55
        return True
40c8f766c9b8 import from internal svn r 4007
raph
parents:
diff changeset
    56
    
40c8f766c9b8 import from internal svn r 4007
raph
parents:
diff changeset
    57
    if not text:
522
c9c2148f09c9 improves performence of text_view_comments by memoizing permission computations.
gibus
parents: 470
diff changeset
    58
        ret = UserRole.objects.filter(user=user, text=None).filter(Q(role__permissions__codename__exact=perm_name)).count() != 0
c9c2148f09c9 improves performence of text_view_comments by memoizing permission computations.
gibus
parents: 470
diff changeset
    59
        cache.set(key, ret)
c9c2148f09c9 improves performence of text_view_comments by memoizing permission computations.
gibus
parents: 470
diff changeset
    60
        return ret
0
40c8f766c9b8 import from internal svn r 4007
raph
parents:
diff changeset
    61
    else:
40c8f766c9b8 import from internal svn r 4007
raph
parents:
diff changeset
    62
        # local role only ADDS permissions:
40c8f766c9b8 import from internal svn r 4007
raph
parents:
diff changeset
    63
        # either a global or a local role with appropriate permissions
40c8f766c9b8 import from internal svn r 4007
raph
parents:
diff changeset
    64
        #return UserRole.objects.filter(user=user).filter(Q(text=text) | Q(text=None)).filter(Q(role__permissions__codename__exact=perm_name)).count() != 0
40c8f766c9b8 import from internal svn r 4007
raph
parents:
diff changeset
    65
40c8f766c9b8 import from internal svn r 4007
raph
parents:
diff changeset
    66
        # local role OVERRIDES global role:
40c8f766c9b8 import from internal svn r 4007
raph
parents:
diff changeset
    67
        if UserRole.objects.filter(Q(user=user),Q(text=text),~Q(role=None)): # if non void local role
522
c9c2148f09c9 improves performence of text_view_comments by memoizing permission computations.
gibus
parents: 470
diff changeset
    68
            ret = UserRole.objects.filter(user=user).filter(text=text).filter(Q(role__permissions__codename__exact=perm_name)).count() != 0
c9c2148f09c9 improves performence of text_view_comments by memoizing permission computations.
gibus
parents: 470
diff changeset
    69
            cache.set(key, ret)
c9c2148f09c9 improves performence of text_view_comments by memoizing permission computations.
gibus
parents: 470
diff changeset
    70
            return ret
0
40c8f766c9b8 import from internal svn r 4007
raph
parents:
diff changeset
    71
        else:
210
e4715ab65e2d fix security pb (too restrictive): logged users should inherit anon roles (if no text role is defined)
raph
parents: 102
diff changeset
    72
            # local role for anon users
e4715ab65e2d fix security pb (too restrictive): logged users should inherit anon roles (if no text role is defined)
raph
parents: 102
diff changeset
    73
            # OR global role for anon users
e4715ab65e2d fix security pb (too restrictive): logged users should inherit anon roles (if no text role is defined)
raph
parents: 102
diff changeset
    74
            # OR global role for this user
522
c9c2148f09c9 improves performence of text_view_comments by memoizing permission computations.
gibus
parents: 470
diff changeset
    75
            ret = UserRole.objects.filter(Q(user=user) | Q(user=None)).filter(Q(text=None) | Q(text=text)).filter(Q(role__permissions__codename__exact=perm_name)).count() != 0            
c9c2148f09c9 improves performence of text_view_comments by memoizing permission computations.
gibus
parents: 470
diff changeset
    76
            cache.set(key, ret)
c9c2148f09c9 improves performence of text_view_comments by memoizing permission computations.
gibus
parents: 470
diff changeset
    77
            return ret
210
e4715ab65e2d fix security pb (too restrictive): logged users should inherit anon roles (if no text role is defined)
raph
parents: 102
diff changeset
    78
            #return UserRole.objects.filter(user=user).filter(text=None).filter(Q(role__permissions__codename__exact=perm_name)).count() != 0
0
40c8f766c9b8 import from internal svn r 4007
raph
parents:
diff changeset
    79
        
40c8f766c9b8 import from internal svn r 4007
raph
parents:
diff changeset
    80
def has_own_perm(request, perm_name, text, comment):
40c8f766c9b8 import from internal svn r 4007
raph
parents:
diff changeset
    81
    
40c8f766c9b8 import from internal svn r 4007
raph
parents:
diff changeset
    82
    user = get_request_user(request)
40c8f766c9b8 import from internal svn r 4007
raph
parents:
diff changeset
    83
    
40c8f766c9b8 import from internal svn r 4007
raph
parents:
diff changeset
    84
    if not user:
40c8f766c9b8 import from internal svn r 4007
raph
parents:
diff changeset
    85
        return False
40c8f766c9b8 import from internal svn r 4007
raph
parents:
diff changeset
    86
    
40c8f766c9b8 import from internal svn r 4007
raph
parents:
diff changeset
    87
    # bypass sec if NO_SECURITY
40c8f766c9b8 import from internal svn r 4007
raph
parents:
diff changeset
    88
    if cm_settings.NO_SECURITY:
40c8f766c9b8 import from internal svn r 4007
raph
parents:
diff changeset
    89
        return True
40c8f766c9b8 import from internal svn r 4007
raph
parents:
diff changeset
    90
    
40c8f766c9b8 import from internal svn r 4007
raph
parents:
diff changeset
    91
    # make sure perm exist
40c8f766c9b8 import from internal svn r 4007
raph
parents:
diff changeset
    92
    assert Permission.objects.get(codename=perm_name)
522
c9c2148f09c9 improves performence of text_view_comments by memoizing permission computations.
gibus
parents: 470
diff changeset
    93
523
cc1cd48289e0 Fixes AttributeError: 'FakeRequest' object has no attribute 'GET'
gibus
parents: 522
diff changeset
    94
    try:
cc1cd48289e0 Fixes AttributeError: 'FakeRequest' object has no attribute 'GET'
gibus
parents: 522
diff changeset
    95
      myself = request.GET.get('name', None)
cc1cd48289e0 Fixes AttributeError: 'FakeRequest' object has no attribute 'GET'
gibus
parents: 522
diff changeset
    96
    except AttributeError:
cc1cd48289e0 Fixes AttributeError: 'FakeRequest' object has no attribute 'GET'
gibus
parents: 522
diff changeset
    97
      myself = None
522
c9c2148f09c9 improves performence of text_view_comments by memoizing permission computations.
gibus
parents: 470
diff changeset
    98
    key = sha1(str((settings.SITE_URL, 'has_own_perm', (user, myself, text, comment, perm_name)))).hexdigest()
c9c2148f09c9 improves performence of text_view_comments by memoizing permission computations.
gibus
parents: 470
diff changeset
    99
    val = cache.get(key)
c9c2148f09c9 improves performence of text_view_comments by memoizing permission computations.
gibus
parents: 470
diff changeset
   100
    if val != None:
c9c2148f09c9 improves performence of text_view_comments by memoizing permission computations.
gibus
parents: 470
diff changeset
   101
      return val
0
40c8f766c9b8 import from internal svn r 4007
raph
parents:
diff changeset
   102
    
40c8f766c9b8 import from internal svn r 4007
raph
parents:
diff changeset
   103
    # 2 special cases for comment own edition:
40c8f766c9b8 import from internal svn r 4007
raph
parents:
diff changeset
   104
    
40c8f766c9b8 import from internal svn r 4007
raph
parents:
diff changeset
   105
    # 1
40c8f766c9b8 import from internal svn r 4007
raph
parents:
diff changeset
   106
    # if perm = can_edit_own_comment and 
40c8f766c9b8 import from internal svn r 4007
raph
parents:
diff changeset
   107
    # text is a priori moderated and
40c8f766c9b8 import from internal svn r 4007
raph
parents:
diff changeset
   108
    # comment is approved and
40c8f766c9b8 import from internal svn r 4007
raph
parents:
diff changeset
   109
    # don't have moderation rights and
40c8f766c9b8 import from internal svn r 4007
raph
parents:
diff changeset
   110
    if comment and comment.state == 'approved' and \
40c8f766c9b8 import from internal svn r 4007
raph
parents:
diff changeset
   111
       perm_name == 'can_edit_comment_own' and \
40c8f766c9b8 import from internal svn r 4007
raph
parents:
diff changeset
   112
       text.last_text_version.mod_posteriori == False and \
40c8f766c9b8 import from internal svn r 4007
raph
parents:
diff changeset
   113
       not has_perm(request, 'can_manage_text', text=text):
522
c9c2148f09c9 improves performence of text_view_comments by memoizing permission computations.
gibus
parents: 470
diff changeset
   114
        cache.set(key, False)
0
40c8f766c9b8 import from internal svn r 4007
raph
parents:
diff changeset
   115
        return False
40c8f766c9b8 import from internal svn r 4007
raph
parents:
diff changeset
   116
    
40c8f766c9b8 import from internal svn r 4007
raph
parents:
diff changeset
   117
    # 2       
40c8f766c9b8 import from internal svn r 4007
raph
parents:
diff changeset
   118
    # if perm = can_edit_own_comment and and 
40c8f766c9b8 import from internal svn r 4007
raph
parents:
diff changeset
   119
    # text is a posteriori moderated and
40c8f766c9b8 import from internal svn r 4007
raph
parents:
diff changeset
   120
    # there is a reply
40c8f766c9b8 import from internal svn r 4007
raph
parents:
diff changeset
   121
    # don't have moderation rights and
40c8f766c9b8 import from internal svn r 4007
raph
parents:
diff changeset
   122
    if comment and comment.state == 'approved' and \
40c8f766c9b8 import from internal svn r 4007
raph
parents:
diff changeset
   123
       perm_name == 'can_edit_comment_own' and \
40c8f766c9b8 import from internal svn r 4007
raph
parents:
diff changeset
   124
       text.last_text_version.mod_posteriori == True and \
40c8f766c9b8 import from internal svn r 4007
raph
parents:
diff changeset
   125
       comment.comment_set.count() != 0 and \
40c8f766c9b8 import from internal svn r 4007
raph
parents:
diff changeset
   126
       not has_perm(request, 'can_manage_text', text=text):
522
c9c2148f09c9 improves performence of text_view_comments by memoizing permission computations.
gibus
parents: 470
diff changeset
   127
        cache.set(key, False)
0
40c8f766c9b8 import from internal svn r 4007
raph
parents:
diff changeset
   128
        return False
40c8f766c9b8 import from internal svn r 4007
raph
parents:
diff changeset
   129
    
355
c926868cf7e6 if DECORATED_CREATORS take into account the "fake" username if has_own_perm()
gibus
parents: 295
diff changeset
   130
    actual_own_user = False
c926868cf7e6 if DECORATED_CREATORS take into account the "fake" username if has_own_perm()
gibus
parents: 295
diff changeset
   131
    if comment.user == request.user:
c926868cf7e6 if DECORATED_CREATORS take into account the "fake" username if has_own_perm()
gibus
parents: 295
diff changeset
   132
      if DECORATED_CREATORS:
523
cc1cd48289e0 Fixes AttributeError: 'FakeRequest' object has no attribute 'GET'
gibus
parents: 522
diff changeset
   133
        if myself == comment.get_name():
355
c926868cf7e6 if DECORATED_CREATORS take into account the "fake" username if has_own_perm()
gibus
parents: 295
diff changeset
   134
          actual_own_user = True
c926868cf7e6 if DECORATED_CREATORS take into account the "fake" username if has_own_perm()
gibus
parents: 295
diff changeset
   135
      else:
c926868cf7e6 if DECORATED_CREATORS take into account the "fake" username if has_own_perm()
gibus
parents: 295
diff changeset
   136
        actual_own_user = True
522
c9c2148f09c9 improves performence of text_view_comments by memoizing permission computations.
gibus
parents: 470
diff changeset
   137
    ret = (actual_own_user and has_perm(request, perm_name, text=text)) 
c9c2148f09c9 improves performence of text_view_comments by memoizing permission computations.
gibus
parents: 470
diff changeset
   138
    cache.set(key, ret)
c9c2148f09c9 improves performence of text_view_comments by memoizing permission computations.
gibus
parents: 470
diff changeset
   139
    return ret
0
40c8f766c9b8 import from internal svn r 4007
raph
parents:
diff changeset
   140
        
40c8f766c9b8 import from internal svn r 4007
raph
parents:
diff changeset
   141
def is_authenticated(request):
40c8f766c9b8 import from internal svn r 4007
raph
parents:
diff changeset
   142
    # We customize this to be able to monkey patch it if needed
40c8f766c9b8 import from internal svn r 4007
raph
parents:
diff changeset
   143
    return request.user.is_authenticated()
40c8f766c9b8 import from internal svn r 4007
raph
parents:
diff changeset
   144
    
40c8f766c9b8 import from internal svn r 4007
raph
parents:
diff changeset
   145
40c8f766c9b8 import from internal svn r 4007
raph
parents:
diff changeset
   146
## Content access functions
40c8f766c9b8 import from internal svn r 4007
raph
parents:
diff changeset
   147
40c8f766c9b8 import from internal svn r 4007
raph
parents:
diff changeset
   148
def get_texts_with_perm(request, perm_name):
40c8f766c9b8 import from internal svn r 4007
raph
parents:
diff changeset
   149
    assert Permission.objects.get(codename=perm_name)
40c8f766c9b8 import from internal svn r 4007
raph
parents:
diff changeset
   150
40c8f766c9b8 import from internal svn r 4007
raph
parents:
diff changeset
   151
    user = get_request_user(request)
40c8f766c9b8 import from internal svn r 4007
raph
parents:
diff changeset
   152
    
522
c9c2148f09c9 improves performence of text_view_comments by memoizing permission computations.
gibus
parents: 470
diff changeset
   153
    key = sha1(str((settings.SITE_URL, 'get_texts_with_perm', (user, perm_name)))).hexdigest()
c9c2148f09c9 improves performence of text_view_comments by memoizing permission computations.
gibus
parents: 470
diff changeset
   154
    val = cache.get(key)
c9c2148f09c9 improves performence of text_view_comments by memoizing permission computations.
gibus
parents: 470
diff changeset
   155
    if val != None:
c9c2148f09c9 improves performence of text_view_comments by memoizing permission computations.
gibus
parents: 470
diff changeset
   156
      return val
c9c2148f09c9 improves performence of text_view_comments by memoizing permission computations.
gibus
parents: 470
diff changeset
   157
0
40c8f766c9b8 import from internal svn r 4007
raph
parents:
diff changeset
   158
    if user and user.is_staff:
522
c9c2148f09c9 improves performence of text_view_comments by memoizing permission computations.
gibus
parents: 470
diff changeset
   159
        ret = Text.objects.all()
c9c2148f09c9 improves performence of text_view_comments by memoizing permission computations.
gibus
parents: 470
diff changeset
   160
        cache.set(key, ret)
c9c2148f09c9 improves performence of text_view_comments by memoizing permission computations.
gibus
parents: 470
diff changeset
   161
        return ret
0
40c8f766c9b8 import from internal svn r 4007
raph
parents:
diff changeset
   162
    
40c8f766c9b8 import from internal svn r 4007
raph
parents:
diff changeset
   163
    # local role only ADDS permissions:
40c8f766c9b8 import from internal svn r 4007
raph
parents:
diff changeset
   164
    ## global perm
40c8f766c9b8 import from internal svn r 4007
raph
parents:
diff changeset
   165
    # if UserRole.objects.filter(text=None).filter(role__permissions__codename__exact=perm_name).filter(Q(user=user) | Q(user=None) ).count() != 0:
40c8f766c9b8 import from internal svn r 4007
raph
parents:
diff changeset
   166
    #    return Text.objects.all().distinct()
40c8f766c9b8 import from internal svn r 4007
raph
parents:
diff changeset
   167
    ## only texts with role with perm
40c8f766c9b8 import from internal svn r 4007
raph
parents:
diff changeset
   168
    #else:
40c8f766c9b8 import from internal svn r 4007
raph
parents:
diff changeset
   169
    #    return Text.objects.filter(Q(userrole__role__permissions__codename__exact=perm_name), Q(userrole__user=user) | Q(userrole__user=None)).distinct()
40c8f766c9b8 import from internal svn r 4007
raph
parents:
diff changeset
   170
40c8f766c9b8 import from internal svn r 4007
raph
parents:
diff changeset
   171
    # local role OVERRIDES global role:
102
f5d3ea4bd03c fix permissions in get_text_with_perms
raph
parents: 81
diff changeset
   172
    texts_with_local_role = Text.objects.filter(userrole__in=UserRole.objects.filter(Q(user=user) | Q(user=None)).filter(~Q(role=None)))
0
40c8f766c9b8 import from internal svn r 4007
raph
parents:
diff changeset
   173
    #Text.objects.filter(Q(userrole__user=user) & ~Q(userrole__role=None))
40c8f766c9b8 import from internal svn r 4007
raph
parents:
diff changeset
   174
    texts_without_local_role = Text.objects.exclude(id__in=texts_with_local_role)
40c8f766c9b8 import from internal svn r 4007
raph
parents:
diff changeset
   175
40c8f766c9b8 import from internal svn r 4007
raph
parents:
diff changeset
   176
    texts_with_local_role_with_perm = Text.objects.filter(id__in=texts_with_local_role).filter(Q(userrole__role__permissions__codename__exact=perm_name), Q(userrole__user=user) | Q(userrole__user=None)).distinct()
40c8f766c9b8 import from internal svn r 4007
raph
parents:
diff changeset
   177
    
40c8f766c9b8 import from internal svn r 4007
raph
parents:
diff changeset
   178
    # global perm?
40c8f766c9b8 import from internal svn r 4007
raph
parents:
diff changeset
   179
    if UserRole.objects.filter(text=None).filter(role__permissions__codename__exact=perm_name).filter(Q(user=user) | Q(user=None) ).count() != 0:    
40c8f766c9b8 import from internal svn r 4007
raph
parents:
diff changeset
   180
        texts_without_local_role_with_perm = Text.objects.filter(id__in=texts_without_local_role)
40c8f766c9b8 import from internal svn r 4007
raph
parents:
diff changeset
   181
    else:
40c8f766c9b8 import from internal svn r 4007
raph
parents:
diff changeset
   182
        texts_without_local_role_with_perm = []
40c8f766c9b8 import from internal svn r 4007
raph
parents:
diff changeset
   183
    
40c8f766c9b8 import from internal svn r 4007
raph
parents:
diff changeset
   184
    ids = set([t.id for t in texts_with_local_role_with_perm]).union(set([t.id for t in texts_without_local_role_with_perm]))
522
c9c2148f09c9 improves performence of text_view_comments by memoizing permission computations.
gibus
parents: 470
diff changeset
   185
    ret = Text.objects.filter(id__in=ids)
c9c2148f09c9 improves performence of text_view_comments by memoizing permission computations.
gibus
parents: 470
diff changeset
   186
    cache.set(key, ret)
c9c2148f09c9 improves performence of text_view_comments by memoizing permission computations.
gibus
parents: 470
diff changeset
   187
    return ret
0
40c8f766c9b8 import from internal svn r 4007
raph
parents:
diff changeset
   188
    
40c8f766c9b8 import from internal svn r 4007
raph
parents:
diff changeset
   189
def get_viewable_comments(request, comments, text, order_by=('created',)):
40c8f766c9b8 import from internal svn r 4007
raph
parents:
diff changeset
   190
    """
40c8f766c9b8 import from internal svn r 4007
raph
parents:
diff changeset
   191
    Get comments visibles by user
40c8f766c9b8 import from internal svn r 4007
raph
parents:
diff changeset
   192
    comments: queryset
40c8f766c9b8 import from internal svn r 4007
raph
parents:
diff changeset
   193
    """
40c8f766c9b8 import from internal svn r 4007
raph
parents:
diff changeset
   194
    user = get_request_user(request)
523
cc1cd48289e0 Fixes AttributeError: 'FakeRequest' object has no attribute 'GET'
gibus
parents: 522
diff changeset
   195
    try:
cc1cd48289e0 Fixes AttributeError: 'FakeRequest' object has no attribute 'GET'
gibus
parents: 522
diff changeset
   196
      myself = request.GET.get('name', None)
cc1cd48289e0 Fixes AttributeError: 'FakeRequest' object has no attribute 'GET'
gibus
parents: 522
diff changeset
   197
    except AttributeError:
cc1cd48289e0 Fixes AttributeError: 'FakeRequest' object has no attribute 'GET'
gibus
parents: 522
diff changeset
   198
      myself = None
522
c9c2148f09c9 improves performence of text_view_comments by memoizing permission computations.
gibus
parents: 470
diff changeset
   199
    key = sha1(str((settings.SITE_URL, 'get_viewable_comments', (user, myself, text, comments)))).hexdigest()
c9c2148f09c9 improves performence of text_view_comments by memoizing permission computations.
gibus
parents: 470
diff changeset
   200
    val = cache.get(key)
c9c2148f09c9 improves performence of text_view_comments by memoizing permission computations.
gibus
parents: 470
diff changeset
   201
    if val != None:
c9c2148f09c9 improves performence of text_view_comments by memoizing permission computations.
gibus
parents: 470
diff changeset
   202
      return val
0
40c8f766c9b8 import from internal svn r 4007
raph
parents:
diff changeset
   203
        
40c8f766c9b8 import from internal svn r 4007
raph
parents:
diff changeset
   204
    if user and has_perm(request, 'can_view_unapproved_comment', text=text):
522
c9c2148f09c9 improves performence of text_view_comments by memoizing permission computations.
gibus
parents: 470
diff changeset
   205
        ret = list(comments.order_by(*order_by))
c9c2148f09c9 improves performence of text_view_comments by memoizing permission computations.
gibus
parents: 470
diff changeset
   206
        cache.set(key, ret)
c9c2148f09c9 improves performence of text_view_comments by memoizing permission computations.
gibus
parents: 470
diff changeset
   207
        return ret
0
40c8f766c9b8 import from internal svn r 4007
raph
parents:
diff changeset
   208
    else:
449
5387c032df35 In role_teacher model, individual students can see their own comments but also teacher's ones, whereas individual students' comments cannot be seen by students.
gibus
parents: 355
diff changeset
   209
        # Fetch role_model to process specific behaviour for role_teacher model
5387c032df35 In role_teacher model, individual students can see their own comments but also teacher's ones, whereas individual students' comments cannot be seen by students.
gibus
parents: 355
diff changeset
   210
        from cm.models import ApplicationConfiguration
5387c032df35 In role_teacher model, individual students can see their own comments but also teacher's ones, whereas individual students' comments cannot be seen by students.
gibus
parents: 355
diff changeset
   211
        role_model = ApplicationConfiguration.get_key('workspace_role_model')
5387c032df35 In role_teacher model, individual students can see their own comments but also teacher's ones, whereas individual students' comments cannot be seen by students.
gibus
parents: 355
diff changeset
   212
0
40c8f766c9b8 import from internal svn r 4007
raph
parents:
diff changeset
   213
        if has_perm(request, 'can_view_approved_comment', text=text):
40c8f766c9b8 import from internal svn r 4007
raph
parents:
diff changeset
   214
            visible_comments = comments.filter(state = 'approved').order_by(*order_by)
40c8f766c9b8 import from internal svn r 4007
raph
parents:
diff changeset
   215
            # filter comments with a non visible (i.e. moderated) comment in the above thread 
40c8f766c9b8 import from internal svn r 4007
raph
parents:
diff changeset
   216
            comments_thread_viewable = [c for c in visible_comments if c.is_thread_full_visible()]
449
5387c032df35 In role_teacher model, individual students can see their own comments but also teacher's ones, whereas individual students' comments cannot be seen by students.
gibus
parents: 355
diff changeset
   217
5387c032df35 In role_teacher model, individual students can see their own comments but also teacher's ones, whereas individual students' comments cannot be seen by students.
gibus
parents: 355
diff changeset
   218
            # for role_teacher role model, do not show 'individual student' comments
5387c032df35 In role_teacher model, individual students can see their own comments but also teacher's ones, whereas individual students' comments cannot be seen by students.
gibus
parents: 355
diff changeset
   219
            if (role_model == 'teacher'):
5387c032df35 In role_teacher model, individual students can see their own comments but also teacher's ones, whereas individual students' comments cannot be seen by students.
gibus
parents: 355
diff changeset
   220
              unfiltered_comments = list(comments_thread_viewable)
5387c032df35 In role_teacher model, individual students can see their own comments but also teacher's ones, whereas individual students' comments cannot be seen by students.
gibus
parents: 355
diff changeset
   221
              for c in unfiltered_comments:
5387c032df35 In role_teacher model, individual students can see their own comments but also teacher's ones, whereas individual students' comments cannot be seen by students.
gibus
parents: 355
diff changeset
   222
                if c.user_id and c.user_id != 1:
5387c032df35 In role_teacher model, individual students can see their own comments but also teacher's ones, whereas individual students' comments cannot be seen by students.
gibus
parents: 355
diff changeset
   223
                  try:
5387c032df35 In role_teacher model, individual students can see their own comments but also teacher's ones, whereas individual students' comments cannot be seen by students.
gibus
parents: 355
diff changeset
   224
                    userrole = UserRole.objects.get(user=c.user, text=text)
5387c032df35 In role_teacher model, individual students can see their own comments but also teacher's ones, whereas individual students' comments cannot be seen by students.
gibus
parents: 355
diff changeset
   225
                  except:
5387c032df35 In role_teacher model, individual students can see their own comments but also teacher's ones, whereas individual students' comments cannot be seen by students.
gibus
parents: 355
diff changeset
   226
                    userrole = UserRole.objects.get(user=None, text=None)
5387c032df35 In role_teacher model, individual students can see their own comments but also teacher's ones, whereas individual students' comments cannot be seen by students.
gibus
parents: 355
diff changeset
   227
                  if userrole.role_id == None:
5387c032df35 In role_teacher model, individual students can see their own comments but also teacher's ones, whereas individual students' comments cannot be seen by students.
gibus
parents: 355
diff changeset
   228
                    role = c.user.get_profile().global_userrole().role
5387c032df35 In role_teacher model, individual students can see their own comments but also teacher's ones, whereas individual students' comments cannot be seen by students.
gibus
parents: 355
diff changeset
   229
                  else:
5387c032df35 In role_teacher model, individual students can see their own comments but also teacher's ones, whereas individual students' comments cannot be seen by students.
gibus
parents: 355
diff changeset
   230
                    role = userrole.role
5387c032df35 In role_teacher model, individual students can see their own comments but also teacher's ones, whereas individual students' comments cannot be seen by students.
gibus
parents: 355
diff changeset
   231
                  if role.name == 'Individual student':
5387c032df35 In role_teacher model, individual students can see their own comments but also teacher's ones, whereas individual students' comments cannot be seen by students.
gibus
parents: 355
diff changeset
   232
                    comments_thread_viewable.remove(c)
522
c9c2148f09c9 improves performence of text_view_comments by memoizing permission computations.
gibus
parents: 470
diff changeset
   233
            cache.set(key, comments_thread_viewable)
0
40c8f766c9b8 import from internal svn r 4007
raph
parents:
diff changeset
   234
            return comments_thread_viewable 
40c8f766c9b8 import from internal svn r 4007
raph
parents:
diff changeset
   235
        elif user and has_perm(request, 'can_view_comment_own', text=text):
449
5387c032df35 In role_teacher model, individual students can see their own comments but also teacher's ones, whereas individual students' comments cannot be seen by students.
gibus
parents: 355
diff changeset
   236
            if DECORATED_CREATORS:
522
c9c2148f09c9 improves performence of text_view_comments by memoizing permission computations.
gibus
parents: 470
diff changeset
   237
              visible_comments = comments.filter(name=myself).order_by(*order_by)
449
5387c032df35 In role_teacher model, individual students can see their own comments but also teacher's ones, whereas individual students' comments cannot be seen by students.
gibus
parents: 355
diff changeset
   238
            else:
5387c032df35 In role_teacher model, individual students can see their own comments but also teacher's ones, whereas individual students' comments cannot be seen by students.
gibus
parents: 355
diff changeset
   239
              visible_comments = comments.filter(user=user).order_by(*order_by)
5387c032df35 In role_teacher model, individual students can see their own comments but also teacher's ones, whereas individual students' comments cannot be seen by students.
gibus
parents: 355
diff changeset
   240
5387c032df35 In role_teacher model, individual students can see their own comments but also teacher's ones, whereas individual students' comments cannot be seen by students.
gibus
parents: 355
diff changeset
   241
            # for role_teacher role model, add 'teacher' comments
5387c032df35 In role_teacher model, individual students can see their own comments but also teacher's ones, whereas individual students' comments cannot be seen by students.
gibus
parents: 355
diff changeset
   242
            if (role_model == 'teacher'):
5387c032df35 In role_teacher model, individual students can see their own comments but also teacher's ones, whereas individual students' comments cannot be seen by students.
gibus
parents: 355
diff changeset
   243
              with_teachers = []
5387c032df35 In role_teacher model, individual students can see their own comments but also teacher's ones, whereas individual students' comments cannot be seen by students.
gibus
parents: 355
diff changeset
   244
              for u in list(User.objects.filter(userrole__role__name = 'Teacher')):
470
077be006891e Fix filtering of teachers' comments for individual students in role_teacher role model when using DECORATED_CREATORS.
gibus
parents: 449
diff changeset
   245
                with_teachers.append(u.id)
449
5387c032df35 In role_teacher model, individual students can see their own comments but also teacher's ones, whereas individual students' comments cannot be seen by students.
gibus
parents: 355
diff changeset
   246
5387c032df35 In role_teacher model, individual students can see their own comments but also teacher's ones, whereas individual students' comments cannot be seen by students.
gibus
parents: 355
diff changeset
   247
              # add admin and current user
5387c032df35 In role_teacher model, individual students can see their own comments but also teacher's ones, whereas individual students' comments cannot be seen by students.
gibus
parents: 355
diff changeset
   248
              admin =  User.objects.get(id=1)
470
077be006891e Fix filtering of teachers' comments for individual students in role_teacher role model when using DECORATED_CREATORS.
gibus
parents: 449
diff changeset
   249
              with_teachers.append(admin.id)
449
5387c032df35 In role_teacher model, individual students can see their own comments but also teacher's ones, whereas individual students' comments cannot be seen by students.
gibus
parents: 355
diff changeset
   250
              if DECORATED_CREATORS:
470
077be006891e Fix filtering of teachers' comments for individual students in role_teacher role model when using DECORATED_CREATORS.
gibus
parents: 449
diff changeset
   251
                visible_comments = comments.filter(Q(user__id__in=with_teachers) | Q(name=myself)).order_by(*order_by)
449
5387c032df35 In role_teacher model, individual students can see their own comments but also teacher's ones, whereas individual students' comments cannot be seen by students.
gibus
parents: 355
diff changeset
   252
              else:
5387c032df35 In role_teacher model, individual students can see their own comments but also teacher's ones, whereas individual students' comments cannot be seen by students.
gibus
parents: 355
diff changeset
   253
                with_teachers.append(user.id)
5387c032df35 In role_teacher model, individual students can see their own comments but also teacher's ones, whereas individual students' comments cannot be seen by students.
gibus
parents: 355
diff changeset
   254
                visible_comments = comments.filter(user__id__in=with_teachers).order_by(*order_by)
5387c032df35 In role_teacher model, individual students can see their own comments but also teacher's ones, whereas individual students' comments cannot be seen by students.
gibus
parents: 355
diff changeset
   255
0
40c8f766c9b8 import from internal svn r 4007
raph
parents:
diff changeset
   256
            # filter comments with a non visible (i.e. moderated) comment in the above thread 
16
036705244cab FIX: comment visibility takes ownership into account
raph
parents: 0
diff changeset
   257
            comments_thread_viewable = [c for c in visible_comments if c.is_thread_full_visible(own_user=user)]
522
c9c2148f09c9 improves performence of text_view_comments by memoizing permission computations.
gibus
parents: 470
diff changeset
   258
            cache.set(key, comments_thread_viewable)
0
40c8f766c9b8 import from internal svn r 4007
raph
parents:
diff changeset
   259
            return comments_thread_viewable                
40c8f766c9b8 import from internal svn r 4007
raph
parents:
diff changeset
   260
        else:
522
c9c2148f09c9 improves performence of text_view_comments by memoizing permission computations.
gibus
parents: 470
diff changeset
   261
            cache.set(key, [])
0
40c8f766c9b8 import from internal svn r 4007
raph
parents:
diff changeset
   262
            return []
40c8f766c9b8 import from internal svn r 4007
raph
parents:
diff changeset
   263
    
40c8f766c9b8 import from internal svn r 4007
raph
parents:
diff changeset
   264
def get_viewable_activities(request=None, act_types={}, text=None):
40c8f766c9b8 import from internal svn r 4007
raph
parents:
diff changeset
   265
    """
40c8f766c9b8 import from internal svn r 4007
raph
parents:
diff changeset
   266
    Get activities user in request is allowed to see
40c8f766c9b8 import from internal svn r 4007
raph
parents:
diff changeset
   267
    """
40c8f766c9b8 import from internal svn r 4007
raph
parents:
diff changeset
   268
    from cm.security import has_perm, get_texts_with_perm, get_viewable_comments
40c8f766c9b8 import from internal svn r 4007
raph
parents:
diff changeset
   269
    
40c8f766c9b8 import from internal svn r 4007
raph
parents:
diff changeset
   270
    selected_activities = reduce(list.__add__,[Activity.VIEWABLE_ACTIVITIES[k] for k in act_types.keys() if act_types[k]], [])
40c8f766c9b8 import from internal svn r 4007
raph
parents:
diff changeset
   271
    
40c8f766c9b8 import from internal svn r 4007
raph
parents:
diff changeset
   272
    activities = Activity.objects.filter(type__in=selected_activities)
40c8f766c9b8 import from internal svn r 4007
raph
parents:
diff changeset
   273
    if text:
40c8f766c9b8 import from internal svn r 4007
raph
parents:
diff changeset
   274
        activities = activities.filter(text=text)
40c8f766c9b8 import from internal svn r 4007
raph
parents:
diff changeset
   275
        
40c8f766c9b8 import from internal svn r 4007
raph
parents:
diff changeset
   276
    if not has_perm(request, 'can_manage_workspace'):
40c8f766c9b8 import from internal svn r 4007
raph
parents:
diff changeset
   277
        texts = get_texts_with_perm(request, 'can_view_text')
40c8f766c9b8 import from internal svn r 4007
raph
parents:
diff changeset
   278
        activities = activities.filter(Q(text__in=texts))
40c8f766c9b8 import from internal svn r 4007
raph
parents:
diff changeset
   279
        
40c8f766c9b8 import from internal svn r 4007
raph
parents:
diff changeset
   280
        comments = [] 
40c8f766c9b8 import from internal svn r 4007
raph
parents:
diff changeset
   281
        [comments.extend(get_viewable_comments(request, t.last_text_version.comment_set.all(), t)) for t in texts]
40c8f766c9b8 import from internal svn r 4007
raph
parents:
diff changeset
   282
40c8f766c9b8 import from internal svn r 4007
raph
parents:
diff changeset
   283
        activities = activities.filter(Q(comment__in=comments) | Q(comment=None))
40c8f766c9b8 import from internal svn r 4007
raph
parents:
diff changeset
   284
    return activities.order_by('-created')
40c8f766c9b8 import from internal svn r 4007
raph
parents:
diff changeset
   285
40c8f766c9b8 import from internal svn r 4007
raph
parents:
diff changeset
   286
40c8f766c9b8 import from internal svn r 4007
raph
parents:
diff changeset
   287
# won't need to be overridden, should it be moved to another file ? 
40c8f766c9b8 import from internal svn r 4007
raph
parents:
diff changeset
   288
def list_viewable_comments(request, comments_list, text):
40c8f766c9b8 import from internal svn r 4007
raph
parents:
diff changeset
   289
    ret = []
40c8f766c9b8 import from internal svn r 4007
raph
parents:
diff changeset
   290
    for comment in comments_list :
40c8f766c9b8 import from internal svn r 4007
raph
parents:
diff changeset
   291
        ret += [comment] + list_viewable_comments(request, get_viewable_comments(request, comment.comment_set, text), text)
40c8f766c9b8 import from internal svn r 4007
raph
parents:
diff changeset
   292
    return ret
40c8f766c9b8 import from internal svn r 4007
raph
parents:
diff changeset
   293
40c8f766c9b8 import from internal svn r 4007
raph
parents:
diff changeset
   294
40c8f766c9b8 import from internal svn r 4007
raph
parents:
diff changeset
   295
# decorators (simple wrappers around above functions)
40c8f766c9b8 import from internal svn r 4007
raph
parents:
diff changeset
   296
def has_global_perm(perm_name, must_be_logged_in=False, redirect_field_name=REDIRECT_FIELD_NAME):
40c8f766c9b8 import from internal svn r 4007
raph
parents:
diff changeset
   297
    def _dec(view_func):
40c8f766c9b8 import from internal svn r 4007
raph
parents:
diff changeset
   298
        def _check_global_perm(request, *args, **kwargs):
40c8f766c9b8 import from internal svn r 4007
raph
parents:
diff changeset
   299
            if must_be_logged_in and not is_authenticated(request):
284
730dd9fb2c77 simplification of security check: all unauthorized exceptions are dealt with by context processors
raph
parents: 210
diff changeset
   300
                raise UnauthorizedException('Should be logged in')
0
40c8f766c9b8 import from internal svn r 4007
raph
parents:
diff changeset
   301
            
40c8f766c9b8 import from internal svn r 4007
raph
parents:
diff changeset
   302
            if has_perm(request, perm_name, text=None): 
40c8f766c9b8 import from internal svn r 4007
raph
parents:
diff changeset
   303
                return view_func(request, *args, **kwargs)
40c8f766c9b8 import from internal svn r 4007
raph
parents:
diff changeset
   304
            
40c8f766c9b8 import from internal svn r 4007
raph
parents:
diff changeset
   305
            raise UnauthorizedException('No global perm %s' % perm_name)
40c8f766c9b8 import from internal svn r 4007
raph
parents:
diff changeset
   306
        _check_global_perm.__doc__ = view_func.__doc__
40c8f766c9b8 import from internal svn r 4007
raph
parents:
diff changeset
   307
        _check_global_perm.__dict__ = view_func.__dict__
40c8f766c9b8 import from internal svn r 4007
raph
parents:
diff changeset
   308
40c8f766c9b8 import from internal svn r 4007
raph
parents:
diff changeset
   309
        return _check_global_perm
40c8f766c9b8 import from internal svn r 4007
raph
parents:
diff changeset
   310
    return _dec    
287
fc5ed157ebfe add api: basic auth / unit tests / online doc (based on django-piston)
raph
parents: 210
diff changeset
   311
fc5ed157ebfe add api: basic auth / unit tests / online doc (based on django-piston)
raph
parents: 210
diff changeset
   312
def has_perm_on_text_api(perm_name, must_be_logged_in=False, redirect_field_name=REDIRECT_FIELD_NAME):    
fc5ed157ebfe add api: basic auth / unit tests / online doc (based on django-piston)
raph
parents: 210
diff changeset
   313
    return _has_perm_on_text(perm_name, must_be_logged_in, redirect_field_name, api=True)
0
40c8f766c9b8 import from internal svn r 4007
raph
parents:
diff changeset
   314
    
287
fc5ed157ebfe add api: basic auth / unit tests / online doc (based on django-piston)
raph
parents: 210
diff changeset
   315
def has_perm_on_text(perm_name, must_be_logged_in=False, redirect_field_name=REDIRECT_FIELD_NAME, api=False):
fc5ed157ebfe add api: basic auth / unit tests / online doc (based on django-piston)
raph
parents: 210
diff changeset
   316
    return _has_perm_on_text(perm_name, must_be_logged_in, redirect_field_name, api)
fc5ed157ebfe add api: basic auth / unit tests / online doc (based on django-piston)
raph
parents: 210
diff changeset
   317
fc5ed157ebfe add api: basic auth / unit tests / online doc (based on django-piston)
raph
parents: 210
diff changeset
   318
def _has_perm_on_text(perm_name, must_be_logged_in=False, redirect_field_name=REDIRECT_FIELD_NAME, api=False):    
0
40c8f766c9b8 import from internal svn r 4007
raph
parents:
diff changeset
   319
    """
40c8f766c9b8 import from internal svn r 4007
raph
parents:
diff changeset
   320
    decorator protection checking for perm for logged in user
40c8f766c9b8 import from internal svn r 4007
raph
parents:
diff changeset
   321
    force logged in (i.e. redirect to connection screen if not if must_be_logged_in 
40c8f766c9b8 import from internal svn r 4007
raph
parents:
diff changeset
   322
    """    
40c8f766c9b8 import from internal svn r 4007
raph
parents:
diff changeset
   323
    def _dec(view_func):
40c8f766c9b8 import from internal svn r 4007
raph
parents:
diff changeset
   324
        def _check_local_perm(request, *args, **kwargs):
40c8f766c9b8 import from internal svn r 4007
raph
parents:
diff changeset
   325
            if cm_settings.NO_SECURITY:
40c8f766c9b8 import from internal svn r 4007
raph
parents:
diff changeset
   326
                return view_func(request, *args, **kwargs)
40c8f766c9b8 import from internal svn r 4007
raph
parents:
diff changeset
   327
40c8f766c9b8 import from internal svn r 4007
raph
parents:
diff changeset
   328
            if must_be_logged_in and not is_authenticated(request):
287
fc5ed157ebfe add api: basic auth / unit tests / online doc (based on django-piston)
raph
parents: 210
diff changeset
   329
                if not api:
295
7c40b98f627f Merge with b8672f57ba3cd4e876277a13c69621446b940052
raph
parents: 287 284
diff changeset
   330
                    raise UnauthorizedException('Should be logged in')
287
fc5ed157ebfe add api: basic auth / unit tests / online doc (based on django-piston)
raph
parents: 210
diff changeset
   331
                else:
fc5ed157ebfe add api: basic auth / unit tests / online doc (based on django-piston)
raph
parents: 210
diff changeset
   332
                    return rc.FORBIDDEN
fc5ed157ebfe add api: basic auth / unit tests / online doc (based on django-piston)
raph
parents: 210
diff changeset
   333
0
40c8f766c9b8 import from internal svn r 4007
raph
parents:
diff changeset
   334
            
40c8f766c9b8 import from internal svn r 4007
raph
parents:
diff changeset
   335
            if 'key' in kwargs: 
40c8f766c9b8 import from internal svn r 4007
raph
parents:
diff changeset
   336
                text = get_object_or_404(Text, key=kwargs['key'])                
40c8f766c9b8 import from internal svn r 4007
raph
parents:
diff changeset
   337
            else:
40c8f766c9b8 import from internal svn r 4007
raph
parents:
diff changeset
   338
                raise Exception('no security check possible')
287
fc5ed157ebfe add api: basic auth / unit tests / online doc (based on django-piston)
raph
parents: 210
diff changeset
   339
                
fc5ed157ebfe add api: basic auth / unit tests / online doc (based on django-piston)
raph
parents: 210
diff changeset
   340
            # in api, the view has an object as first parameter, request is args[0]
fc5ed157ebfe add api: basic auth / unit tests / online doc (based on django-piston)
raph
parents: 210
diff changeset
   341
            if not api:                
fc5ed157ebfe add api: basic auth / unit tests / online doc (based on django-piston)
raph
parents: 210
diff changeset
   342
                req = request
fc5ed157ebfe add api: basic auth / unit tests / online doc (based on django-piston)
raph
parents: 210
diff changeset
   343
            else:                    
fc5ed157ebfe add api: basic auth / unit tests / online doc (based on django-piston)
raph
parents: 210
diff changeset
   344
                req = args[0]     
fc5ed157ebfe add api: basic auth / unit tests / online doc (based on django-piston)
raph
parents: 210
diff changeset
   345
            if has_perm(req, perm_name, text=text): 
0
40c8f766c9b8 import from internal svn r 4007
raph
parents:
diff changeset
   346
                return view_func(request, *args, **kwargs)
40c8f766c9b8 import from internal svn r 4007
raph
parents:
diff changeset
   347
            #else:
40c8f766c9b8 import from internal svn r 4007
raph
parents:
diff changeset
   348
                # TODO: (? useful ?) if some user have the perm and not logged-in : redirect to login
40c8f766c9b8 import from internal svn r 4007
raph
parents:
diff changeset
   349
                #if not request.user.is_authenticated() and number_has_perm_on_text(permission, text_id) > 0:
40c8f766c9b8 import from internal svn r 4007
raph
parents:
diff changeset
   350
                #    return HttpResponseRedirect('%s?%s=%s' % (login_url, redirect_field_name, urlquote(request.get_full_path())))                    
40c8f766c9b8 import from internal svn r 4007
raph
parents:
diff changeset
   351
            # else : unauthorized
40c8f766c9b8 import from internal svn r 4007
raph
parents:
diff changeset
   352
            
287
fc5ed157ebfe add api: basic auth / unit tests / online doc (based on django-piston)
raph
parents: 210
diff changeset
   353
            if not api:
fc5ed157ebfe add api: basic auth / unit tests / online doc (based on django-piston)
raph
parents: 210
diff changeset
   354
                raise UnauthorizedException('No perm %s' % perm_name)
fc5ed157ebfe add api: basic auth / unit tests / online doc (based on django-piston)
raph
parents: 210
diff changeset
   355
            else:
fc5ed157ebfe add api: basic auth / unit tests / online doc (based on django-piston)
raph
parents: 210
diff changeset
   356
                return rc.FORBIDDEN
fc5ed157ebfe add api: basic auth / unit tests / online doc (based on django-piston)
raph
parents: 210
diff changeset
   357
0
40c8f766c9b8 import from internal svn r 4007
raph
parents:
diff changeset
   358
        _check_local_perm.__doc__ = view_func.__doc__
40c8f766c9b8 import from internal svn r 4007
raph
parents:
diff changeset
   359
        _check_local_perm.__dict__ = view_func.__dict__
40c8f766c9b8 import from internal svn r 4007
raph
parents:
diff changeset
   360
40c8f766c9b8 import from internal svn r 4007
raph
parents:
diff changeset
   361
        return _check_local_perm
40c8f766c9b8 import from internal svn r 4007
raph
parents:
diff changeset
   362
    return _dec
40c8f766c9b8 import from internal svn r 4007
raph
parents:
diff changeset
   363
        
40c8f766c9b8 import from internal svn r 4007
raph
parents:
diff changeset
   364
def has_perm_on_comment(perm_name):    
40c8f766c9b8 import from internal svn r 4007
raph
parents:
diff changeset
   365
    """
40c8f766c9b8 import from internal svn r 4007
raph
parents:
diff changeset
   366
    decorator protection checking for perm for logged in user on to comment
40c8f766c9b8 import from internal svn r 4007
raph
parents:
diff changeset
   367
    perm_name: 'virtual' permission name 
40c8f766c9b8 import from internal svn r 4007
raph
parents:
diff changeset
   368
    """    
40c8f766c9b8 import from internal svn r 4007
raph
parents:
diff changeset
   369
    def _dec(view_func):
40c8f766c9b8 import from internal svn r 4007
raph
parents:
diff changeset
   370
        def _check_local_perm(request, *args, **kwargs):
40c8f766c9b8 import from internal svn r 4007
raph
parents:
diff changeset
   371
            if cm_settings.NO_SECURITY:
40c8f766c9b8 import from internal svn r 4007
raph
parents:
diff changeset
   372
                return view_func(request, *args, **kwargs)
40c8f766c9b8 import from internal svn r 4007
raph
parents:
diff changeset
   373
            
40c8f766c9b8 import from internal svn r 4007
raph
parents:
diff changeset
   374
            if 'key' in kwargs: 
40c8f766c9b8 import from internal svn r 4007
raph
parents:
diff changeset
   375
                text = get_object_or_404(Text, key=kwargs['key'])
40c8f766c9b8 import from internal svn r 4007
raph
parents:
diff changeset
   376
                # first try permission on text                
40c8f766c9b8 import from internal svn r 4007
raph
parents:
diff changeset
   377
                if has_perm(request, perm_name, text=text) :
40c8f766c9b8 import from internal svn r 4007
raph
parents:
diff changeset
   378
                    return view_func(request, *args, **kwargs)
40c8f766c9b8 import from internal svn r 4007
raph
parents:
diff changeset
   379
                if 'comment_key' in kwargs:
40c8f766c9b8 import from internal svn r 4007
raph
parents:
diff changeset
   380
                    comment = get_object_or_404(Comment, key=kwargs['comment_key'])
40c8f766c9b8 import from internal svn r 4007
raph
parents:
diff changeset
   381
                    if has_own_perm(request, perm_name + "_own", text, comment) :
40c8f766c9b8 import from internal svn r 4007
raph
parents:
diff changeset
   382
                        return view_func(request, *args, **kwargs)
40c8f766c9b8 import from internal svn r 4007
raph
parents:
diff changeset
   383
                else:
40c8f766c9b8 import from internal svn r 4007
raph
parents:
diff changeset
   384
                    raise Exception('no security check possible: no comment key')
40c8f766c9b8 import from internal svn r 4007
raph
parents:
diff changeset
   385
            else:
40c8f766c9b8 import from internal svn r 4007
raph
parents:
diff changeset
   386
                raise Exception('no security check possible: no text key')
40c8f766c9b8 import from internal svn r 4007
raph
parents:
diff changeset
   387
40c8f766c9b8 import from internal svn r 4007
raph
parents:
diff changeset
   388
            raise UnauthorizedException('No perm %s on comment' % perm_name)
40c8f766c9b8 import from internal svn r 4007
raph
parents:
diff changeset
   389
        _check_local_perm.__doc__ = view_func.__doc__
40c8f766c9b8 import from internal svn r 4007
raph
parents:
diff changeset
   390
        _check_local_perm.__dict__ = view_func.__dict__
40c8f766c9b8 import from internal svn r 4007
raph
parents:
diff changeset
   391
40c8f766c9b8 import from internal svn r 4007
raph
parents:
diff changeset
   392
        return _check_local_perm
40c8f766c9b8 import from internal svn r 4007
raph
parents:
diff changeset
   393
    return _dec        
40c8f766c9b8 import from internal svn r 4007
raph
parents:
diff changeset
   394
    
40c8f766c9b8 import from internal svn r 4007
raph
parents:
diff changeset
   395
40c8f766c9b8 import from internal svn r 4007
raph
parents:
diff changeset
   396