src/cm/security.py
author gibus
Mon, 15 Jul 2013 09:13:19 +0200
changeset 523 cc1cd48289e0
parent 522 c9c2148f09c9
child 540 dce127afac9d
permissions -rw-r--r--
Fixes AttributeError: 'FakeRequest' object has no attribute 'GET'
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