diff --git a/product/ERP5Type/dtml/editGuardForm.dtml b/product/ERP5Type/dtml/editGuardForm.dtml
new file mode 100644
index 0000000000000000000000000000000000000000..5318e4789b2bf89df37826269844ad49def818e2
--- /dev/null
+++ b/product/ERP5Type/dtml/editGuardForm.dtml
@@ -0,0 +1,28 @@
+<dtml-var manage_page_header>
+<dtml-var manage_tabs>
+
+<form action="manage_setGuard" method="POST">
+<table>
+
+<tr>
+<th align="left" valign="top">Guard</th>
+<td>
+<dtml-with getGuard>
+<table>
+<tr>
+<th align="left">Permission(s)</th>
+<td><input type="text" name="guard_permissions" value="&dtml-getPermissionsText;" /></td>
+<th align="left">Role(s)</th>
+<td><input type="text" name="guard_roles" value="&dtml-getRolesText;" /></td>
+<th align="left">Group(s)</th>
+<td><input type="text" name="guard_groups" value="&dtml-getGroupsText;" /></td>
+</tr>
+</table>
+</dtml-with>
+</td>
+</tr>
+
+</table>
+<input type="submit" name="submit" value="Save changes" />
+</form>
+<dtml-var manage_page_footer>
diff --git a/product/ERP5Type/patches/PythonScript.py b/product/ERP5Type/patches/PythonScript.py
index 75588a1d0192566561b4b08dfc1180629a0c7433..45fd969211f4a0353c23b2982baf211d1aa44ce3 100644
--- a/product/ERP5Type/patches/PythonScript.py
+++ b/product/ERP5Type/patches/PythonScript.py
@@ -10,11 +10,16 @@
 # FOR A PARTICULAR PURPOSE
 #
 ##############################################################################
+from Products.CMFCore.utils import _checkPermission
+from Products.DCWorkflow.Guard import Guard
 from Products.PythonScripts.PythonScript import PythonScript
 from App.special_dtml import DTMLFile
 from Products.ERP5Type import _dtmldir
+from AccessControl import ModuleSecurityInfo, getSecurityManager
 from OFS.misc_ import p_
 from App.ImageFile import ImageFile
+from Acquisition import aq_base, aq_parent
+from zExceptions import Forbidden
 
 def haveProxyRole(self):
   """if a script has proxy role, return True"""
@@ -50,3 +55,95 @@ PythonScript.manage = manage_editForm
 PythonScript.manage_main = manage_editForm
 PythonScript.manage_editDocument = manage_editForm
 PythonScript.manage_editForm = manage_editForm
+
+security = ModuleSecurityInfo('Products.PythonScripts.PythonScript.PythonScript')
+
+PythonScript.manage_options += (
+  {
+    'label':'Guard',
+    'action':'manage_guardForm',
+  },
+)
+PythonScript._guard_form = DTMLFile(
+  'editGuardForm', _dtmldir)
+
+def manage_guardForm(self, REQUEST, manage_tabs_message=None):
+  '''
+  '''
+  return self._guard_form(REQUEST,
+                          management_view='Guard',
+                          manage_tabs_message=manage_tabs_message,
+    )
+PythonScript.manage_guardForm = manage_guardForm
+security.declareProtected('View management screens', 'manage_guardForm')
+
+def manage_setGuard(self, props=None, REQUEST=None):
+  '''
+  '''
+  g = Guard()
+  if g.changeFromProperties(props or REQUEST):
+    self.guard = g
+  else:
+    self.guard = None
+  if REQUEST is not None:
+    return self.manage_guardForm(REQUEST, 'Properties changed.')
+PythonScript.manage_setGuard = manage_setGuard
+security.declareProtected('Change Python Scripts', 'manage_setGuard')
+
+def getGuard(self):
+  guard = getattr(self, 'guard', None)
+  if guard is not None:
+    return guard
+  else:
+    return Guard().__of__(self)  # Create a temporary guard.
+PythonScript.getGuard = getGuard
+
+def checkGuard(guard, ob):
+  # returns 1 if guard passes against ob, else 0.
+  # TODO : implement TALES evaluation by defining an appropriate
+  # context.
+  u = None
+  if guard.permissions:
+    for p in guard.permissions:
+      if _checkPermission(p, ob):
+        break
+      else:
+        return 0
+  if guard.roles:
+    if u is None:
+      u = getSecurityManager().getUser()
+    # Require at least one of the given roles.
+    u_roles = u.getRolesInContext(ob)
+    for role in guard.roles:
+      if role in u_roles:
+        break
+    else:
+      return 0
+  if guard.groups:
+    # Require at least one of the specified groups.
+    if u is None:
+      u = getSecurityManager().getUser()
+    b = aq_base( u )
+    if hasattr( b, 'getGroupsInContext' ):
+      u_groups = u.getGroupsInContext( ob )
+    elif hasattr( b, 'getGroups' ):
+      u_groups = u.getGroups()
+    else:
+      u_groups = ()
+    for group in guard.groups:
+      if group in u_groups:
+        break
+    else:
+      return 0
+  return 1
+
+PythonScript_exec = PythonScript._exec
+def _exec(self, *args):
+  # PATCH BEGIN : check guard against context, if guard exists.
+  guard = getattr(self, 'guard', None)
+  if guard is not None:
+    if not checkGuard(guard, aq_parent(self)):
+      raise Forbidden, 'Calling %s %s is denied by Guard.' % (self.meta_type, self.id)
+  # PATCH END
+  return PythonScript_exec(self, *args)
+PythonScript._exec = _exec