You can not select more than 25 topics Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.
 
 
 
 
 
 

170 lines
5.0 KiB

  1. # Copyright (c) 2013, Web Notes Technologies Pvt. Ltd. and Contributors
  2. # MIT License. See license.txt
  3. from __future__ import unicode_literals
  4. import frappe
  5. from frappe import _, msgprint, _dict
  6. from frappe.utils import cint
  7. rights = ["read", "write", "create", "submit", "cancel", "amend",
  8. "report", "import", "export", "print", "email", "restrict", "delete", "restricted"]
  9. def check_admin_or_system_manager():
  10. if ("System Manager" not in frappe.get_roles()) and \
  11. (frappe.session.user!="Administrator"):
  12. msgprint("Only Allowed for Role System Manager or Administrator", raise_exception=True)
  13. def has_permission(doctype, ptype="read", refdoc=None, verbose=True):
  14. """check if user has permission"""
  15. if frappe.is_table(doctype):
  16. return True
  17. meta = frappe.get_doctype(doctype)
  18. if ptype=="submit" and not cint(meta[0].is_submittable):
  19. return False
  20. if ptype=="import" and not cint(meta[0].allow_import):
  21. return False
  22. if frappe.session.user=="Administrator":
  23. return True
  24. # get user permissions
  25. if not get_user_perms(meta).get(ptype):
  26. return False
  27. if refdoc:
  28. if isinstance(refdoc, basestring):
  29. refdoc = frappe.doc(meta[0].name, refdoc)
  30. if not has_unrestricted_access(meta, refdoc, verbose=verbose):
  31. return False
  32. if not has_additional_permission(refdoc):
  33. return False
  34. return True
  35. def get_user_perms(meta, user=None):
  36. cache_key = (meta[0].name, user)
  37. if not frappe.local.user_perms.get(cache_key):
  38. perms = frappe._dict()
  39. user_roles = frappe.get_roles(user)
  40. for p in meta.get({"doctype": "DocPerm"}):
  41. if cint(p.permlevel)==0 and (p.role=="All" or p.role in user_roles):
  42. for ptype in rights:
  43. if ptype == "restricted":
  44. perms[ptype] = perms.get(ptype, 1) and cint(p.get(ptype))
  45. else:
  46. perms[ptype] = perms.get(ptype, 0) or cint(p.get(ptype))
  47. frappe.local.user_perms[cache_key] = perms
  48. return frappe.local.user_perms[cache_key]
  49. def has_unrestricted_access(meta, refdoc, verbose=True):
  50. from frappe.defaults import get_restrictions
  51. restrictions = get_restrictions()
  52. if get_user_perms(meta).restricted:
  53. if refdoc.owner == frappe.session.user:
  54. # owner is always allowed for restricted permissions
  55. return True
  56. elif not restrictions:
  57. return False
  58. else:
  59. if not restrictions:
  60. return True
  61. # evaluate specific restrictions
  62. fields_to_check = meta.get_restricted_fields(restrictions.keys())
  63. has_restricted_data = False
  64. for df in fields_to_check:
  65. if refdoc.get(df.fieldname) and refdoc.get(df.fieldname) not in restrictions[df.options]:
  66. if verbose:
  67. msg = "{not_allowed}: {doctype} {having} {label} = {value}".format(
  68. not_allowed=_("Sorry, you are not allowed to access"), doctype=_(df.options),
  69. having=_("having"), label=_(df.label), value=refdoc.get(df.fieldname))
  70. if refdoc.parentfield:
  71. msg = "{doctype}, {row} #{idx}, ".format(doctype=_(refdoc.doctype),
  72. row=_("Row"), idx=refdoc.idx) + msg
  73. msgprint(msg)
  74. has_restricted_data = True
  75. # check all restrictions before returning
  76. return False if has_restricted_data else True
  77. def has_additional_permission(doc):
  78. if doc.fields.get("__islocal"):
  79. bean = frappe.bean([doc])
  80. else:
  81. bean = frappe.bean(doc.doctype, doc.name)
  82. condition_methods = frappe.get_hooks("has_permission:" + doc.doctype)
  83. for method in frappe.get_hooks("has_permission:" + doc.doctype):
  84. if not frappe.call(frappe.get_attr(method), doc=doc, bean=bean):
  85. return False
  86. return True
  87. def can_restrict_user(user, doctype, docname=None):
  88. if not can_restrict(doctype, docname):
  89. return False
  90. meta = frappe.get_doctype(doctype)
  91. # check if target user does not have restrict permission
  92. if has_only_non_restrict_role(meta, user):
  93. return True
  94. return False
  95. def can_restrict(doctype, docname=None):
  96. # System Manager can always restrict
  97. if "System Manager" in frappe.get_roles():
  98. return True
  99. meta = frappe.get_doctype(doctype)
  100. # check if current user has read permission for docname
  101. if docname and not has_permission(doctype, "read", docname):
  102. return False
  103. # check if current user has a role with restrict permission
  104. if not has_restrict_permission(meta):
  105. return False
  106. return True
  107. def has_restrict_permission(meta=None, user=None):
  108. return get_user_perms(meta, user).restrict==1
  109. def has_only_non_restrict_role(meta, user):
  110. # check if target user does not have restrict permission
  111. if has_restrict_permission(meta, user):
  112. return False
  113. # and has non-restrict role
  114. return get_user_perms(meta, user).restrict==0
  115. def can_import(doctype, raise_exception=False):
  116. if not ("System Manager" in frappe.get_roles() or has_permission(doctype, "import")):
  117. if raise_exception:
  118. raise frappe.PermissionError("You are not allowed to import: {doctype}".format(doctype=doctype))
  119. else:
  120. return False
  121. return True
  122. def can_export(doctype, raise_exception=False):
  123. if not ("System Manager" in frappe.get_roles() or has_permission(doctype, "export")):
  124. if raise_exception:
  125. raise frappe.PermissionError("You are not allowed to export: {doctype}".format(doctype=doctype))
  126. else:
  127. return False
  128. return True