mirror of
https://github.com/django/django.git
synced 2025-07-05 10:19:20 +00:00
[per-object-permissions] Very basic integration of RLPs into admin interface.
git-svn-id: http://code.djangoproject.com/svn/django/branches/per-object-permissions@3486 bcc190cf-cafb-0310-a4f2-bffc1f526a37
This commit is contained in:
parent
75c6dc967d
commit
340718bd3a
160
django/contrib/admin/media/js/row_level_permission.js
Normal file
160
django/contrib/admin/media/js/row_level_permission.js
Normal file
@ -0,0 +1,160 @@
|
|||||||
|
/**
|
||||||
|
* @author clong
|
||||||
|
*/
|
||||||
|
//dojo.require("dojo.io.*");
|
||||||
|
//dojo.require("dojo.event.*");
|
||||||
|
//dojo.require("dojo.lfx.*");
|
||||||
|
//dojo.require("dojo.widget.*");
|
||||||
|
//dojo.require("dojo.json");
|
||||||
|
|
||||||
|
function addButtonPressed(obj_ct, obj_id)
|
||||||
|
{
|
||||||
|
return;
|
||||||
|
dojo.io.bind({
|
||||||
|
url: "/rlp/add/"+obj_ct+"/"+obj_id+"/ajax/",
|
||||||
|
handler: addCallback,
|
||||||
|
formNode: dojo.byId('addRLPForm')
|
||||||
|
});
|
||||||
|
}
|
||||||
|
|
||||||
|
function addCallback(type, data, evt)
|
||||||
|
{
|
||||||
|
if (type == 'error')
|
||||||
|
alert('Error when retrieving data from the server!');
|
||||||
|
else
|
||||||
|
{
|
||||||
|
dictData = dojo.json.evalJson(data);
|
||||||
|
if(dictData.result == false)
|
||||||
|
{
|
||||||
|
//outputError(dictData.text);
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
alert("Success!");
|
||||||
|
//outputMsg(dictData.text);
|
||||||
|
//dojo.lfx.html.highlight(dojo.byId("editRLP-"+dictData.id), [184, 204, 228], 1000).play();
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
function applyButtonPressed(id)
|
||||||
|
{
|
||||||
|
return;
|
||||||
|
strArray = id.split("/");
|
||||||
|
dojo.io.bind({
|
||||||
|
url: "/rlp/change/"+id+'/ajax/',
|
||||||
|
handler: editCallback,
|
||||||
|
formNode: dojo.byId('editRLPForm-'+strArray[1])
|
||||||
|
});
|
||||||
|
}
|
||||||
|
|
||||||
|
function editCallback(type, data, evt)
|
||||||
|
{
|
||||||
|
if (type == 'error')
|
||||||
|
alert('Error when retrieving data from the server!');
|
||||||
|
else
|
||||||
|
{
|
||||||
|
dictData = dojo.json.evalJson(data);
|
||||||
|
if(dictData.result == false)
|
||||||
|
{
|
||||||
|
outputError(dictData.text);
|
||||||
|
dojo.lfx.html.highlight(dojo.byId("editRLP-"+dictData.id), [255, 0, 0], 1000).play();
|
||||||
|
alert("Error");
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
outputMessage(dictData.text);
|
||||||
|
dojo.lfx.html.highlight(dojo.byId("editRLP-"+dictData.id), [184, 204, 228], 1000).play();
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
function deleteRLP(id)
|
||||||
|
{
|
||||||
|
return;
|
||||||
|
var confirm_ans = confirm("Are you sure?");
|
||||||
|
if(confirm_ans)
|
||||||
|
{
|
||||||
|
dojo.io.bind({
|
||||||
|
url: '/rlp/delete/'+id+'/ajax',
|
||||||
|
handler: deleteCallback,
|
||||||
|
mimetype: 'text/json'
|
||||||
|
});
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
function deleteCallback(type, data, evt)
|
||||||
|
{
|
||||||
|
if (type == 'error')
|
||||||
|
alert('Error when retrieving data from the server!');
|
||||||
|
else
|
||||||
|
{
|
||||||
|
dictData = dojo.json.evalJson(data);
|
||||||
|
if(dictData.result == false)
|
||||||
|
{
|
||||||
|
//outputError(dictData.text);
|
||||||
|
dojo.lfx.html.highlight(dojo.byId("editRLP-"+dictData.id), [255, 0, 0], 1000).play();
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
outputMessage(dictData.text);
|
||||||
|
var row = dojo.byId('editRLP-'+dictData.id);
|
||||||
|
var fadeOut = dojo.lfx.fadeOut(row, 1000, null, function(n) {
|
||||||
|
var table = dojo.byId('rlpTable');
|
||||||
|
table.deleteRow(row.rowIndex);
|
||||||
|
});
|
||||||
|
dojo.lfx.html.highlight(row, [255, 0, 0], 500).play(1500);
|
||||||
|
fadeOut.play();
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
function copyToNew(id)
|
||||||
|
{
|
||||||
|
var newForm = document.addRLPForm;
|
||||||
|
var form = dojo.byId("editRLPForm-"+id);
|
||||||
|
newForm.owner.selectedIndex = form.owner.selectedIndex;
|
||||||
|
newForm.perm.selectedIndex = form.perm.selectedIndex;
|
||||||
|
newForm.negative.checked = form.negative.checked;
|
||||||
|
}
|
||||||
|
|
||||||
|
function outputErrors(errs)
|
||||||
|
{
|
||||||
|
var output = genOutput('errors', errs);
|
||||||
|
dojo.lfx.html.highlight(output, [240, 0, 0], 3000).play();
|
||||||
|
}
|
||||||
|
|
||||||
|
function outputMessage(messages)
|
||||||
|
{
|
||||||
|
var output = genOutput('messages', messages);
|
||||||
|
dojo.lfx.html.highlight(output, [184, 204, 228], 3000).play();
|
||||||
|
}
|
||||||
|
|
||||||
|
function genOutput(id, str)
|
||||||
|
{
|
||||||
|
var list = document.createElement("ul");
|
||||||
|
list.id = id;
|
||||||
|
var txt = document.createTextNode(str);
|
||||||
|
var ele = document.createElement("li");
|
||||||
|
ele.appendChild(txt);
|
||||||
|
list.appendChild(ele);
|
||||||
|
var output = dojo.byId('output');
|
||||||
|
removeChildrenFromNode(output);
|
||||||
|
output.appendChild(list);
|
||||||
|
return output;
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
function removeChildrenFromNode(node)
|
||||||
|
{
|
||||||
|
|
||||||
|
while (node.hasChildNodes())
|
||||||
|
{
|
||||||
|
node.removeChild(node.firstChild);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
function init()
|
||||||
|
{
|
||||||
|
for(var i=0; i<document.forms.length; i++)
|
||||||
|
{
|
||||||
|
document.forms[i].reset();
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
//dojo.addOnLoad(init);
|
138
django/contrib/admin/row_level_perm_manipulator.py
Normal file
138
django/contrib/admin/row_level_perm_manipulator.py
Normal file
@ -0,0 +1,138 @@
|
|||||||
|
from django import forms
|
||||||
|
from django.contrib.contenttypes.models import ContentType
|
||||||
|
from django.http import Http404, HttpResponse, HttpResponseRedirect
|
||||||
|
from django.contrib.auth.models import User, Group, Permission, RowLevelPermission
|
||||||
|
from django.db.models import manipulators
|
||||||
|
from auth import utils
|
||||||
|
|
||||||
|
class ChangeRLPManipulator(forms.Manipulator):
|
||||||
|
def __init__(self, ct=None):
|
||||||
|
perm_list = []
|
||||||
|
if ct:
|
||||||
|
self.ct = ct
|
||||||
|
perm_list = [(o.id, o.name) for o in self.ct.permission_set.order_by("name")]
|
||||||
|
|
||||||
|
obj_list = [('user', User.objects.order_by("username"))]
|
||||||
|
obj_list.extend([('group', Group.objects.order_by("name"))])
|
||||||
|
|
||||||
|
self.fields = (
|
||||||
|
MultipleObjSelectField(field_name="owner", obj_list=obj_list),
|
||||||
|
forms.SelectField(field_name="perm", choices=perm_list),
|
||||||
|
forms.CheckboxField(field_name="negative"),
|
||||||
|
)
|
||||||
|
|
||||||
|
def save(self, new_data):
|
||||||
|
|
||||||
|
rlp = RowLevelPermission.objects.get(pk=new_data['id'])
|
||||||
|
|
||||||
|
self.original_object = rlp
|
||||||
|
self.manager = rlp._default_manager
|
||||||
|
self.opts = rlp._meta
|
||||||
|
|
||||||
|
owner = MultipleObjSelectField.returnObject(new_data['owner'])
|
||||||
|
owner_ct = ContentType.objects.get_for_model(owner)
|
||||||
|
|
||||||
|
model_ct = rlp.type_ct
|
||||||
|
model = model_ct.get_object_for_this_type (pk=rlp.type_id)
|
||||||
|
|
||||||
|
perm = Permission.objects.get(pk=new_data['perm'])
|
||||||
|
|
||||||
|
|
||||||
|
field_name_list = ('owner_ct', 'owner_id', 'type_ct', 'type_id', 'permission')
|
||||||
|
field_data = owner_ct.id
|
||||||
|
all_data = {'owner_id':owner.id, 'type_ct_id':model_ct.id, 'type_id':model.id, 'permission_id':perm.id}
|
||||||
|
manipulators.manipulator_validator_unique_together(field_name_list, self.opts, self, field_data, all_data)
|
||||||
|
|
||||||
|
rlp.owner = owner
|
||||||
|
rlp.permission = perm
|
||||||
|
rlp.negative = new_data['negative']
|
||||||
|
rlp.save()
|
||||||
|
return rlp
|
||||||
|
|
||||||
|
class AddRLPManipulator(ChangeRLPManipulator):
|
||||||
|
def __init__(self, obj_instance, ct):
|
||||||
|
self.ct = ct
|
||||||
|
self.obj_instance = obj_instance
|
||||||
|
obj_list = [('user', User.objects.order_by("username"))]
|
||||||
|
obj_list.extend([('group', Group.objects.order_by("name"))])
|
||||||
|
perm_list = [(o.id, o.name) for o in self.ct.permission_set.order_by("name")]
|
||||||
|
self.fields = (
|
||||||
|
MultipleObjSelectField(field_name="owner", obj_list=obj_list),
|
||||||
|
forms.SelectMultipleField(field_name="perm", choices=perm_list, size=3),
|
||||||
|
forms.CheckboxField(field_name="negative"),
|
||||||
|
)
|
||||||
|
|
||||||
|
def save(self, new_data):
|
||||||
|
|
||||||
|
owner = MultipleObjSelectField.returnObject(new_data['owner'])
|
||||||
|
|
||||||
|
self.manager = RowLevelPermission._default_manager
|
||||||
|
self.opts = RowLevelPermission._meta
|
||||||
|
|
||||||
|
ct = ContentType.objects.get_for_model(owner)
|
||||||
|
rlp_list = []
|
||||||
|
for i in new_data.getlist('perm'):
|
||||||
|
perm = Permission.objects.get(pk=i)
|
||||||
|
|
||||||
|
field_name_list = ('owner_ct', 'owner_id', 'type_ct', 'type_id', 'permission')
|
||||||
|
field_data = ct.id
|
||||||
|
all_data = {'owner_id':owner.id, 'type_ct_id':self.ct.id, 'type_id':self.obj_instance.id, 'permission_id':perm.id}
|
||||||
|
manipulators.manipulator_validator_unique_together(field_name_list, self.opts, self, field_data, all_data)
|
||||||
|
|
||||||
|
rlp = RowLevelPermission.objects.create_row_level_permission(self.obj_instance, owner, perm, negative=new_data['negative'])
|
||||||
|
rlp_list.append(rlp)
|
||||||
|
|
||||||
|
return rlp_list
|
||||||
|
|
||||||
|
#def validate_unique_together(orig_obj, field_name_list, all_data):
|
||||||
|
#field_list = [opts.get_field(field_name) for field_name in field_name_list]
|
||||||
|
#kwargs = {}
|
||||||
|
#for f in field_list:
|
||||||
|
#field_val = all_data.get(f.attname, None)
|
||||||
|
#if field_val is None:
|
||||||
|
#return
|
||||||
|
#if isinstance(f.rel, ManyToOneRel):
|
||||||
|
#kwargs['%s__pk' % f.name] = field_val
|
||||||
|
#else:
|
||||||
|
#kwargs['%s__iexact' % f.name] = field_val
|
||||||
|
#try:
|
||||||
|
#old_obj = self.manager.get(**kwargs)
|
||||||
|
#except ObjectDoesNotExist:
|
||||||
|
#return
|
||||||
|
#if hasattr(self, 'original_object') and self.original_object._get_pk_val() == old_obj._get_pk_val():
|
||||||
|
#pass
|
||||||
|
#else:
|
||||||
|
#raise validators.ValidationError, _("%(object)s with this %(type)s already exists for the given %(field)s.") % \
|
||||||
|
#{'object': capfirst(opts.verbose_name), 'type': field_list[0].verbose_name, 'field': get_text_list(field_name_list[1:], 'and')}
|
||||||
|
|
||||||
|
|
||||||
|
class MultipleObjSelectField(forms.SelectField):
|
||||||
|
def __init__(self, field_name, obj_list=None,
|
||||||
|
default_text=None, size=1, is_required=False, validator_list=None,
|
||||||
|
member_name=None):
|
||||||
|
if default_text is None:
|
||||||
|
default_text = "Select an option"
|
||||||
|
choice_list = [('', default_text)]
|
||||||
|
for obj, obj_choices in obj_list:
|
||||||
|
ct = ContentType.objects.get(model__exact=obj)
|
||||||
|
choice_list.extend([(MultipleObjSelectField.returnKey(o), str(o)+" ("+ct.name.title()+")") for o in obj_choices])
|
||||||
|
|
||||||
|
super(MultipleObjSelectField, self).__init__(field_name, choices=choice_list,
|
||||||
|
size=size, is_required=is_required,
|
||||||
|
validator_list=validator_list,
|
||||||
|
member_name=member_name)
|
||||||
|
def returnObject(data):
|
||||||
|
data = data.split('-')
|
||||||
|
ct = ContentType.objects.get(model__exact=data[0])
|
||||||
|
obj = ct.get_object_for_this_type(pk=data[1])
|
||||||
|
return obj
|
||||||
|
|
||||||
|
def returnKey(obj):
|
||||||
|
ct = ContentType.objects.get_for_model(obj.__class__)
|
||||||
|
return ct.model+"-"+str(obj.id)
|
||||||
|
|
||||||
|
returnObject = staticmethod(returnObject)
|
||||||
|
returnKey = staticmethod(returnKey)
|
||||||
|
|
||||||
|
|
||||||
|
|
@ -64,5 +64,11 @@
|
|||||||
</script>
|
</script>
|
||||||
{% endif %}
|
{% endif %}
|
||||||
</div>
|
</div>
|
||||||
</form></div>
|
</form>
|
||||||
|
|
||||||
|
{% if rlp_form_list %}
|
||||||
|
{% include "admin/row_level_permission.html" %}
|
||||||
|
{% endif %}
|
||||||
|
|
||||||
|
</div>
|
||||||
{% endblock %}
|
{% endblock %}
|
||||||
|
@ -0,0 +1,79 @@
|
|||||||
|
{% load i18n admin_modify %}
|
||||||
|
{% include_admin_script "js/row_level_permission.js" %}
|
||||||
|
<table id="rlpTable">
|
||||||
|
<tr class="header">
|
||||||
|
<th>
|
||||||
|
{% trans "Owner" %}
|
||||||
|
</th>
|
||||||
|
<th>
|
||||||
|
{% trans "Permission" %}
|
||||||
|
</th>
|
||||||
|
<th>
|
||||||
|
{% trans "Negative" %}
|
||||||
|
</th>
|
||||||
|
<th>
|
||||||
|
{% trans "Options" %}
|
||||||
|
</th>
|
||||||
|
</tr>
|
||||||
|
<form id="addRLPForm" method="POST" name="addRLPForm" action="../../../auth/row_level_permission/add/{{ content_type_id }}/{{ object_id }}/" onSubmit="addButtonPressed({{ obj_ct }}, {{ obj_id }}); return false;">
|
||||||
|
<tr>
|
||||||
|
<th colspan=4>
|
||||||
|
{% trans "Add Permissions" %}
|
||||||
|
</th>
|
||||||
|
</tr>
|
||||||
|
<TBODY>
|
||||||
|
<tr>
|
||||||
|
<td>
|
||||||
|
<p>
|
||||||
|
{{ new_rlp_form.owner }}
|
||||||
|
</p>
|
||||||
|
</td>
|
||||||
|
<td>
|
||||||
|
<p>
|
||||||
|
{{ new_rlp_form.perm }}
|
||||||
|
</p>
|
||||||
|
</td>
|
||||||
|
<td>
|
||||||
|
<p>
|
||||||
|
{{ new_rlp_form.negative }}
|
||||||
|
</p>
|
||||||
|
</td>
|
||||||
|
<td>
|
||||||
|
<input id="addButton" type="submit" value="{% trans 'Add' %}" />
|
||||||
|
</td>
|
||||||
|
</tr>
|
||||||
|
</form>
|
||||||
|
<tr>
|
||||||
|
<th colspan=4>
|
||||||
|
{% trans "Current Permissions" %}
|
||||||
|
</th>
|
||||||
|
</tr>
|
||||||
|
{% if rlp_form_list %}
|
||||||
|
{% load row_level_permission %}
|
||||||
|
{% for o in rlp_form_list %}
|
||||||
|
<tr id="editRLP-{{ o.rlp.id }}">
|
||||||
|
<form id="editRLPForm-{{ o.rlp.id }}" method="POST" name="editRLPForm-{{ rlp.id }}" action="../../../auth/row_level_permission/{% objref o.rlp %}/change/" onSubmit="applyButtonPressed('{% objref o.rlp %}'); return false;">
|
||||||
|
<td>
|
||||||
|
{{ o.form.owner }}
|
||||||
|
</td>
|
||||||
|
<td>
|
||||||
|
{{ o.form.perm }}
|
||||||
|
</td>
|
||||||
|
<td>
|
||||||
|
{{ o.form.negative }}
|
||||||
|
</td>
|
||||||
|
<td>
|
||||||
|
<input id="applyButton-{{ o.rlp.id }}" type="submit" value="{% trans 'Apply' %}" />
|
||||||
|
<input id="cancelButton-{{ o.rlp.id }}" type="reset" value="{% trans 'Reset' %}"/>
|
||||||
|
<br/>
|
||||||
|
<a href="../../../auth/row_level_permission/{% objref o.rlp %}/delete/" onClick="deleteRLP('{% objref o.rlp %}'); return false;" class="deleteLink">{% trans 'Delete' %}</a> |
|
||||||
|
<a href="" onClick="copyToNew({{ o.rlp.id }}); return false;" class="copyToNewLink">{% trans 'Copy to New' %}</a>
|
||||||
|
</td>
|
||||||
|
</form>
|
||||||
|
</tr>
|
||||||
|
{% endfor %}
|
||||||
|
{% else %}
|
||||||
|
<tr><td>No row level permissions</td></tr>
|
||||||
|
{% endif %}
|
||||||
|
</TBODY>
|
||||||
|
</table>
|
37
django/contrib/admin/templatetags/row_level_permission.py
Normal file
37
django/contrib/admin/templatetags/row_level_permission.py
Normal file
@ -0,0 +1,37 @@
|
|||||||
|
import sha
|
||||||
|
from django.contrib.contenttypes.models import ContentType
|
||||||
|
from django import template
|
||||||
|
from django.conf import settings
|
||||||
|
|
||||||
|
register = template.Library()
|
||||||
|
|
||||||
|
#Based off work by Ian Holsman
|
||||||
|
#http://svn.zyons.python-hosting.com/trunk/zilbo/common/utils/templatetags/media.py
|
||||||
|
class objref_class(template.Node):
|
||||||
|
""" return a object reference to a given object """
|
||||||
|
def __init__(self, obj):
|
||||||
|
self.object_name= obj
|
||||||
|
|
||||||
|
def render(self, context):
|
||||||
|
object_id = template.resolve_variable( self.object_name, context )
|
||||||
|
c_obj = ContentType.objects.get_for_model( object_id ).id
|
||||||
|
#c_obj = get_content_type_id( object_id )
|
||||||
|
return "%s/%d/%s" % ( c_obj, object_id.id, sha.new("%s/%d" % (c_obj, object_id.id) + settings.SECRET_KEY).hexdigest())
|
||||||
|
|
||||||
|
#Based off work by Ian Holsman
|
||||||
|
#http://svn.zyons.python-hosting.com/trunk/zilbo/common/utils/templatetags/media.py
|
||||||
|
def objref(parser, token):
|
||||||
|
"""
|
||||||
|
{% objref <object> %}
|
||||||
|
"""
|
||||||
|
bits = token.contents.split()
|
||||||
|
tok=""
|
||||||
|
if len(bits) > 2:
|
||||||
|
raise template.TemplateSyntaxError, "'objref' statements must be 'objref <object>': %s" % token.contents
|
||||||
|
if len(bits) == 2:
|
||||||
|
tok = bits[1]
|
||||||
|
else:
|
||||||
|
tok = "object"
|
||||||
|
return objref_class(tok)
|
||||||
|
|
||||||
|
register.tag('objref', objref)
|
@ -28,6 +28,11 @@ urlpatterns = patterns('',
|
|||||||
# ('^doc/templates/$', 'django.views.admin.doc.template_index'),
|
# ('^doc/templates/$', 'django.views.admin.doc.template_index'),
|
||||||
('^doc/templates/(?P<template>.*)/$', 'django.contrib.admin.views.doc.template_detail'),
|
('^doc/templates/(?P<template>.*)/$', 'django.contrib.admin.views.doc.template_detail'),
|
||||||
|
|
||||||
|
#Row level permissions
|
||||||
|
('^auth/row_level_permission/(?P<ct_id>\d+)/(?P<rlp_id>\d+)/(?P<hash>\w+)/delete/(?P<ajax>.*)$', 'django.contrib.admin.views.row_level_permissions.delete_row_level_permission'),
|
||||||
|
('^auth/row_level_permission/(?P<ct_id>\d+)/(?P<rlp_id>\d+)/(?P<hash>\w+)/change/(?P<ajax>.*)$', 'django.contrib.admin.views.row_level_permissions.change_row_level_permission'),
|
||||||
|
('^auth/row_level_permission/add/(?P<ct_id>\d+)/(?P<obj_id>\d+)/(?P<ajax>.*)$', 'django.contrib.admin.views.row_level_permissions.add_row_level_permission'),
|
||||||
|
|
||||||
# Add/change/delete/history
|
# Add/change/delete/history
|
||||||
('^([^/]+)/([^/]+)/$', 'django.contrib.admin.views.main.change_list'),
|
('^([^/]+)/([^/]+)/$', 'django.contrib.admin.views.main.change_list'),
|
||||||
('^([^/]+)/([^/]+)/add/$', 'django.contrib.admin.views.main.add_stage'),
|
('^([^/]+)/([^/]+)/add/$', 'django.contrib.admin.views.main.add_stage'),
|
||||||
@ -36,4 +41,5 @@ urlpatterns = patterns('',
|
|||||||
('^([^/]+)/([^/]+)/(.+)/$', 'django.contrib.admin.views.main.change_stage'),
|
('^([^/]+)/([^/]+)/(.+)/$', 'django.contrib.admin.views.main.change_stage'),
|
||||||
)
|
)
|
||||||
|
|
||||||
|
|
||||||
del i18n_view
|
del i18n_view
|
||||||
|
@ -100,3 +100,14 @@ if docutils_is_available:
|
|||||||
|
|
||||||
for name, urlbase in ROLES.items():
|
for name, urlbase in ROLES.items():
|
||||||
create_reference_role(name, urlbase)
|
create_reference_role(name, urlbase)
|
||||||
|
|
||||||
|
#Based off work by Ian Holsman
|
||||||
|
#http://svn.zyons.python-hosting.com/trunk/zilbo/common/utils/misc.py
|
||||||
|
def verify_objref_hash( content_type_id, object_id, hash ):
|
||||||
|
import sha
|
||||||
|
from django.conf import settings
|
||||||
|
hash_match = sha.new("%s/%s" % (content_type_id, object_id) + settings.SECRET_KEY).hexdigest()
|
||||||
|
if hash == hash_match:
|
||||||
|
return True
|
||||||
|
else:
|
||||||
|
return False
|
||||||
|
@ -391,7 +391,26 @@ def change_stage(request, app_label, model_name, object_id):
|
|||||||
'object_id': object_id,
|
'object_id': object_id,
|
||||||
'original': manipulator.original_object,
|
'original': manipulator.original_object,
|
||||||
'is_popup': request.REQUEST.has_key('_popup'),
|
'is_popup': request.REQUEST.has_key('_popup'),
|
||||||
|
'is_row_level_perm': model._meta.row_level_permissions,
|
||||||
})
|
})
|
||||||
|
|
||||||
|
if model._meta.row_level_permissions:
|
||||||
|
from django.contrib.admin.row_level_perm_manipulator import AddRLPManipulator, ChangeRLPManipulator
|
||||||
|
model_instance = manipulator.original_object
|
||||||
|
model_ct = ContentType.objects.get_for_model(model)
|
||||||
|
rlp_list = model_instance.row_level_permissions.order_by('owner_ct', 'owner_id')
|
||||||
|
rlp_errors = rlp_new_data = {}
|
||||||
|
add_rlp_manip = AddRLPManipulator(model_instance, model_ct)
|
||||||
|
edit_rlp_manip = ChangeRLPManipulator(model_ct)
|
||||||
|
new_rlp_form = forms.FormWrapper(add_rlp_manip, rlp_new_data, rlp_errors)
|
||||||
|
rlp_form_list = []
|
||||||
|
for r in rlp_list:
|
||||||
|
owner_val = str(r.owner_ct)+"-"+str(r.owner_id)
|
||||||
|
data = {'id':r.id, 'owner':owner_val, 'perm':r.permission.id, 'negative':r.negative}
|
||||||
|
rlp_form_list.append({'form':forms.FormWrapper(edit_rlp_manip, data, rlp_errors), 'rlp':r})
|
||||||
|
rlp_context = {'new_rlp_form':new_rlp_form, 'rlp_form_list':rlp_form_list,}
|
||||||
|
c.update(rlp_context)
|
||||||
|
|
||||||
return render_change_form(model, manipulator, c, change=True)
|
return render_change_form(model, manipulator, c, change=True)
|
||||||
change_stage = staff_member_required(never_cache(change_stage))
|
change_stage = staff_member_required(never_cache(change_stage))
|
||||||
|
|
||||||
|
105
django/contrib/admin/views/row_level_permissions.py
Normal file
105
django/contrib/admin/views/row_level_permissions.py
Normal file
@ -0,0 +1,105 @@
|
|||||||
|
from django.contrib.admin import utils
|
||||||
|
from django.shortcuts import render_to_response, get_object_or_404
|
||||||
|
from django.http import Http404, HttpResponse, HttpResponseRedirect
|
||||||
|
from django.contrib.contenttypes.models import ContentType
|
||||||
|
from django.contrib.auth.models import RowLevelPermission
|
||||||
|
from django.contrib.admin.row_level_perm_manipulator import AddRLPManipulator, ChangeRLPManipulator
|
||||||
|
import simplejson
|
||||||
|
|
||||||
|
def delete_row_level_permission(request, ct_id, rlp_id, hash, ajax=None):
|
||||||
|
msg = {}
|
||||||
|
if utils.verify_objref_hash(ct_id, rlp_id, hash):
|
||||||
|
rlp = get_object_or_404(RowLevelPermission, pk=rlp_id)
|
||||||
|
ct = rlp.type_ct
|
||||||
|
obj = rlp.type
|
||||||
|
opts = rlp._meta
|
||||||
|
if not request.user.has_perm(opts.app_label + '.' + opts.get_delete_permission()):
|
||||||
|
raise PermissionDenied
|
||||||
|
if not request.user.has_perm(obj._meta.app_label + '.' + obj._meta.get_delete_permission()):
|
||||||
|
raise PermissionDenied
|
||||||
|
rlp.delete()
|
||||||
|
msg = {"result":True, "text":_("Row level permission was successful deleted"), "id":rlp_id}
|
||||||
|
else:
|
||||||
|
msg = { 'result':False, 'text': _("row level permission not found (bad hash)" )}
|
||||||
|
if ajax:
|
||||||
|
return HttpResponse(simplejson.dumps(msg), 'text/javascript')
|
||||||
|
request.user.message_set.create(message=msg['text'])
|
||||||
|
#return HttpResponseRedirect("/edit/%s/%s" % (ct.model, obj.id))
|
||||||
|
return HttpResponseRedirect("../../../../../../%s/%s/%s" % (obj._meta.app_label, obj._meta.module_name , str(obj.id)))
|
||||||
|
|
||||||
|
def add_row_level_permission(request, ct_id, obj_id, ajax=None):
|
||||||
|
msg = {}
|
||||||
|
if not request.POST:
|
||||||
|
msg = { 'result':False, 'text': _("Only POSTs are allowed" )}
|
||||||
|
if ajax:
|
||||||
|
return HttpResponse(simplejson.dumps(msg), 'text/javascript')
|
||||||
|
request.user.message_set.create(message=msg['text'])
|
||||||
|
return HttpResponseRedirect("/edit/%s/%s" % (obj_type, obj_id))
|
||||||
|
|
||||||
|
ct = get_object_or_404(ContentType, pk=ct_id)
|
||||||
|
obj = get_object_or_404(ct.model_class(), pk=obj_id)
|
||||||
|
|
||||||
|
if not request.user.has_perm(obj._meta.app_label + '.' + obj._meta.get_add_permission()):
|
||||||
|
raise PermissionDenied
|
||||||
|
|
||||||
|
manip = AddRLPManipulator(obj, ct)
|
||||||
|
|
||||||
|
new_data = request.POST.copy()
|
||||||
|
manip.do_html2python(new_data)
|
||||||
|
|
||||||
|
rlp_list = []
|
||||||
|
from django.core import validators
|
||||||
|
try:
|
||||||
|
rlp_list = manip.save(new_data)
|
||||||
|
except validators.ValidationError:
|
||||||
|
msg = {"result":False, "text":_("A row level permission already exists with the specified values.")}
|
||||||
|
else:
|
||||||
|
msg = {"result":True, "text":_("Row level permission has successful been added.")}
|
||||||
|
if not ajax:
|
||||||
|
request.user.message_set.create(message=msg['text'])
|
||||||
|
return HttpResponseRedirect("../../../../../%s/%s/%s" % (obj._meta.app_label, obj._meta.module_name , str(obj.id)))
|
||||||
|
|
||||||
|
|
||||||
|
resp_list = []
|
||||||
|
for rlp in rlp_list:
|
||||||
|
resp_list.append({"id":rlp.id, "permission":rlp.permission.id})
|
||||||
|
msg["results"]=resp_list
|
||||||
|
return HttpResponse(simplejson.dumps(msg), 'text/javascript')
|
||||||
|
|
||||||
|
def change_row_level_permission(request, ct_id, rlp_id, hash, ajax=None):
|
||||||
|
msg = {}
|
||||||
|
if not request.POST:
|
||||||
|
msg = { 'result':False, 'text': _("Only POSTs are allowed" )}
|
||||||
|
|
||||||
|
if not utils.verify_objref_hash(ct_id, rlp_id, hash):
|
||||||
|
msg = { 'result':False, 'text': _("row level permission not found (bad hash)" )}
|
||||||
|
|
||||||
|
if msg.has_key("result"):
|
||||||
|
if ajax:
|
||||||
|
return HttpResponse(simplejson.dumps(msg), 'text/javascript')
|
||||||
|
request.user.message_set.create(message=msg['text'])
|
||||||
|
return HttpResponseRedirect("/edit/%s/%s" % (obj_type, obj_id))
|
||||||
|
|
||||||
|
obj = get_object_or_404(RowLevelPermission, pk=rlp_id)
|
||||||
|
opts = obj._meta
|
||||||
|
|
||||||
|
#if not request.user.has_perm(app_label + '.' + opts.get_change_permission()):
|
||||||
|
#if not request.user.has_perm(opts.get_change_permission()):
|
||||||
|
#raise PermissionDenied
|
||||||
|
|
||||||
|
manip = ChangeRLPManipulator()
|
||||||
|
new_data = request.POST.copy()
|
||||||
|
|
||||||
|
new_data["id"] = rlp_id
|
||||||
|
manip.do_html2python(new_data)
|
||||||
|
from django.core import validators
|
||||||
|
try:
|
||||||
|
new_rlp = manip.save(new_data)
|
||||||
|
except validators.ValidationError:
|
||||||
|
msg = {"result":False, "text":_("A row level permission already exists with the specified values")}
|
||||||
|
else:
|
||||||
|
msg = {"result":True, "text":_("Row level permission has successfully been changed"), "id":rlp_id}
|
||||||
|
if ajax:
|
||||||
|
return HttpResponse(simplejson.dumps(msg), 'text/javascript')
|
||||||
|
request.user.message_set.create(message=msg['text'])
|
||||||
|
return HttpResponseRedirect("../../../../../../%s/%s/%s" % (new_rlp.type._meta.app_label, new_rlp.type._meta.module_name , str(rlp.type_id)))
|
Loading…
x
Reference in New Issue
Block a user