Wider permissions

My users have a linked sales person, and quotations have a sales person field

I have the need to allow quotation for users when

  • They are the owner of the quotation
    OR
  • The quotation salesperson match their own

Why? Users usally make their own quotations, in which case they are both the owner and also has their salesperson document linked. But we also have a few assistants that make quotations on behalf of other users. In which case they both need to have permissions for that document.

I can do the first with with Role Permission Manager
I can do the second with User Permissions

But not at the same time, if combined it restricts to documents where BOTH conditions are true

I need a way to allow documents when one OR the other is true

Workaround I have found:

  • Handle the first case with Role Permission Manager and for the other use Server Scripts to add an assigment to the second user

Partial workaround:

  • Server Scripts Permission Query, I can set wathever logic here, but it only affects lists. The document itself is still accesible.

Hi

You can rely solely on a Permission Query Server Script on the Quotation Doctype. In this case if the user is Administrator there is no restriction, so there is someone who can view all the quotations

user = frappe.session.user

if user != 'Administrator':
    conditions = "created_by = '" + user + "' OR referral_sales_partner = '" + user + "'"

Permission Queries aren’t applied on document reads, meaning the user can still fetch the document if the name is known.

I made a feature request on github about that

You are totally right. I did not know that. Sorry I couldn’t help

The following approach is not really secure for a knowledgeable user, but it’s better than not implementing it, which is to write a client script on the DocType you want, in my case ToDo, to let users see only the Todo if their user matches the assigned_by or the allocated_to fields

The client script redirects the user to the ToDo List view if the conditions are not met

Client Script

frappe.ui.form.on('ToDo', {
	refresh(frm) {
        frappe.call({
            method: "myapp.api_view_restrictions.todo_view_restriction",
            args: {
                todo_name: frm.doc.name,
                user: frappe.session.user
            },
            callback: function(response) {
                if (!response.message) {
                    frappe.set_route("List", "ToDo");
                }
            }
        });
	}
});

Server Script located in myapp.api_view_restrictions.todo_view_restriction

import frappe

@frappe.whitelist()
def todo_view_restriction(todo_name, user):
    todo = frappe.get_doc("ToDo", todo_name)
    if user in [todo.allocated_to, todo.assigned_by]:
        return True

Server script + client script is working for now, a knowledgeable user could in theory still fetch with the console but I don’t have anyone ike that

I haven’t tried adding a custom app yet, I want to but I haven’t found a tutorial for my setup

I don’t have a local environment, my setup is on frappe cloud, I don’t know yet how to create an app on github to add to my bench