0

Here I am trying to add/update group name and user permissions and i tried like this.

For add it is working fine but while updating with function edit_user_group i got problem. The problem is

Exception Type: IntegrityError Exception Value: (1062, "Duplicate entry 'Developer' for key 'name'")

I think this is because of OneToOne relation. How can I update user group here ?

views.py

@permission_required('organization.add_user_group', raise_exception=True)
def add_user_groups(request):
    form = AddUserGroupForm()
    user_permissions = Permission.objects.all()
    if request.method == 'POST':
        form = AddUserGroupForm(request.POST)
        if form.is_valid():
            group_name = form.cleaned_data['name']
            permissions = request.POST.getlist('user_permissions')
            new_group = Group.objects.create(name=group_name)
            new_group.permissions.set(permissions)
            messages.success(request, 'New group added.')
            return redirect('organization:view_user_groups')
    return render(request, 'organization/add_user_groups.html', {'user_permissions': user_permissions, 'form': form})

@permission_required('organization.edit_user_group', raise_exception=True)
def edit_user_group(request, pk):
    group = get_object_or_404(Group, pk=pk)
    user_permissions = Permission.objects.all()
    form = AddUserGroupForm()
    if request.method == 'POST':
        form = AddUserGroupForm(request.POST)
        if form.is_valid():
            name = form.cleaned_data['name']
            permissions = request.POST.getlist('user_permissions')
            group = Group.objects.update(name=name)
            group.permissions.set(permissions)
            messages.success(request, '{} group Updated.'.format(group.name))
            return redirect('organization:detail_user_group',group.pk)

    return render(request,'organization/edit_user_group.html',{'group':group,'form':form,'user_permissions':user_permissions})

forms.py

class AddUserGroupForm(forms.Form):
    name = forms.CharField(max_length=255)

template for edit group

               <form action="{% url 'organization:edit_user_group' group.pk %}" method="post">
                    {% csrf_token %}
                      <label> Group Name : </label>
                       <input type="text" value="{{group.name}}" name="name">
                      <b class="text-danger">
                       {{ form.name.errors|striptags }}
                      </b>

                    <label>Permissions ({{user_permissions|length}}):</label>
                    {% for permission in user_permissions %}              
                        <input name="user_permissions" type="checkbox" id="permission-{{permission.id}}"
                          value="{{permission.id}}"
                        {% if permission in group.permissions.all %} checked {% endif %}>
                        <label for="permission-{{permission.id}}"> {{permission.name}}</label>
                    {% endfor %}

EDIT: As @ Shashank suggested While trying get it returned model object but says

Exception Type: AttributeError
Exception Value:    
'Group' object has no attribute 'update' 

group = Group.objects.get(pk=pk).update(name=name)

And while using filter it returned int instead of instance so it throws

Exception Value:    
'int' object has no attribute 'permissions'

group = Group.objects.filter(pk=pk).update(name=name)
Hello
  • 312
  • 1
  • 5
  • 14
  • 1
    I guess you need to filter the model object first and then update it's value, like `MyModel.objects.filter(pk=pk).update(val=val)` – Shashank Sep 25 '19 at 15:03
  • `group.permissions.set(permissions)` this line is giving you error because update method might be returning `int`, can you try to split things like `group = MyModel.objects.filter(pk=pk)` so that you can get that filtered object and then `group.update` and then change permission. Make sure that group object is not a list (like after filter do `group = group[0]`) – Shashank Sep 25 '19 at 15:20

3 Answers3

2

This line that you wrote is updating every Group - group = Group.objects.update(name=name) and when it tries to it doesnt work because of the unique constraint on name.

How about replacing with group.name = name, group.save()

hancho
  • 1,345
  • 3
  • 19
  • 39
2

The integrity exception is basically telling you that somewhere in your code you are trying to set the name for different group objects into 'Developer' which is prohibited (due to UNIQUE constraint).

In your function def edit_user_group(request, pk), instead of Group.objects.update, you should do Group.objects.get(name=name)

i.e. From

group = Group.objects.update(name=name)

To

group = Group.objects.get(name=name)
mingjun
  • 119
  • 1
  • 5
2

Your intent is not totally clear - do you want to (also) change the group name or just change the permissions (and using update() instead of `get()``was just a typo) ?

In the first case, you want:

group = Group.objects.get(name=name)
group.name = name
group.save()
group.permissions.set(permissions)

But since there's a unique constraint on Group.name, you have to validate this too before saving.

In the second case, you of course just need

group = Group.objects.get(name=name)
group.permissions.set(permissions)

This being said, using modelforms would save you a lot of time and pain...

bruno desthuilliers
  • 75,974
  • 6
  • 88
  • 118