PageRenderTime 46ms CodeModel.GetById 16ms RepoModel.GetById 0ms app.codeStats 0ms

/shabti/templates/shenu/+package+/lib/conditions.py_tmpl

https://bitbucket.org/gawel/shabti
Unknown | 215 lines | 171 code | 44 blank | 0 comment | 0 complexity | 5c5a64fc3c68088b4f4d119c7404e04f MD5 | raw file
  1. # -*- coding: utf-8 -*-
  2. from pylons import tmpl_context as c
  3. # Copied in verbatim from Turbogears 1's identity package
  4. class Predicate(object):
  5. '''
  6. Generic base class for testing true or false for a condition.
  7. '''
  8. def eval_with_object( self, obj, errors=None ):
  9. '''
  10. Determine whether the predicate is True or False for the given object.
  11. '''
  12. raise NotImplementedError
  13. def append_error_message( self, errors=None ):
  14. if errors is None:
  15. return
  16. errors.append( self.error_message % self.__dict__ )
  17. class CompoundPredicate(Predicate):
  18. '''
  19. A predicate composed of other predicates.
  20. '''
  21. def __init__(self, *predicates):
  22. self.predicates= predicates
  23. class All(CompoundPredicate):
  24. '''
  25. A compound predicate that evaluates to true only if all sub-predicates
  26. evaluate to true for the given input.
  27. '''
  28. def eval_with_object( self, obj, errors=None ):
  29. '''
  30. Return true if all sub-predicates evaluate to true.
  31. '''
  32. for p in self.predicates:
  33. if not p.eval_with_object( obj, errors ):
  34. return False
  35. return True
  36. class Any(CompoundPredicate):
  37. '''
  38. A compound predicate that evaluates to true if any one of its sub-predicates
  39. evaluates to true.
  40. '''
  41. error_message= "No predicates were able to grant access"
  42. def eval_with_object( self, obj, errors=None ):
  43. '''
  44. Return true if any sub-predicate evaluates to true.
  45. '''
  46. for p in self.predicates:
  47. if p.eval_with_object( obj, None ):
  48. return True
  49. self.append_error_message( errors )
  50. return False
  51. class IdentityPredicateHelper(object):
  52. '''
  53. A mix-in helper class for Identity Predicates.
  54. '''
  55. def __nonzero__(self):
  56. return self.eval_with_object( c.user )
  57. class in_group(Predicate, IdentityPredicateHelper):
  58. '''
  59. Predicate for requiring a group.
  60. '''
  61. error_message= "Not member of group: %(group_name)s"
  62. def __init__(self, group_name):
  63. self.group_name= group_name
  64. def eval_with_object( self, identity, errors=None ):
  65. if self.group_name in identity.groups:
  66. return True
  67. self.append_error_message( errors )
  68. return False
  69. class in_all_groups(All, IdentityPredicateHelper):
  70. '''
  71. Predicate for requiring membership in a number of groups.
  72. '''
  73. def __init__(self, *groups):
  74. group_predicates= [in_group(g) for g in groups]
  75. super(in_all_groups,self).__init__( *group_predicates )
  76. class in_any_group(Any, IdentityPredicateHelper):
  77. '''
  78. Predicate for requiring membership in at least one group
  79. '''
  80. error_message= "Not member of any group: %(group_list)s"
  81. def __init__(self, *groups):
  82. self.group_list= ", ".join(groups)
  83. group_predicates= [in_group(g) for g in groups]
  84. super(in_any_group,self).__init__( *group_predicates )
  85. class not_anonymous(Predicate, IdentityPredicateHelper):
  86. '''
  87. Predicate for checking whether current visitor is anonymous.
  88. '''
  89. error_message= "Anonymous access denied"
  90. def eval_with_object( self, identity, errors=None ):
  91. if c.user.anonymous:
  92. self.append_error_message( errors )
  93. return False
  94. return True
  95. class has_permission(Predicate, IdentityPredicateHelper):
  96. '''
  97. Predicate for checking whether the visitor has a particular permission.
  98. '''
  99. error_message= "Permission denied: %(permission_name)s"
  100. def __init__(self, permission_name):
  101. self.permission_name= permission_name
  102. def eval_with_object(self, identity, errors=None):
  103. '''
  104. Determine whether the visitor has the specified permission.
  105. '''
  106. if self.permission_name in c.user.permissions:
  107. return True
  108. self.append_error_message( errors )
  109. return False
  110. class has_all_permissions(All, IdentityPredicateHelper):
  111. '''
  112. Predicate for checking whether the visitor has all permissions.
  113. '''
  114. def __init__(self, *permissions):
  115. permission_predicates= [has_permission(p) for p in permissions]
  116. super(has_all_permissions,self).__init__( *permission_predicates )
  117. class has_any_permission(Any, IdentityPredicateHelper):
  118. '''
  119. Predicate for checking whether the visitor has at least one permission.
  120. '''
  121. error_message= "No matching permissions: %(permission_list)s"
  122. def __init__(self, *permissions):
  123. self.permission_list= ", ".join( permissions )
  124. permission_predicates= [has_permission(p) for p in permissions]
  125. super(has_any_permission,self).__init__( *permission_predicates )
  126. def _remoteHost():
  127. try:
  128. ips= cherrypy.request.headers.get( "X-Forwarded-For",
  129. cherrypy.request.remote_host )
  130. return ips.split(",")[-1].strip()
  131. except:
  132. return ""
  133. def _match_ip(cidr, ip):
  134. if not '/' in cidr:
  135. return cidr == ip
  136. else:
  137. try:
  138. b,m = cidr.split('/')
  139. shift = 32 - int(m)
  140. a1 = struct.unpack('!L', socket.inet_aton(b))[0] >> shift
  141. a2 = struct.unpack('!L', socket.inet_aton(ip))[0] >> shift
  142. return a1 == a2
  143. except:
  144. return False
  145. class from_host(Predicate, IdentityPredicateHelper):
  146. '''
  147. Predicate for checking whether the visitor's host is an allowed host.
  148. Note: We never want to announce what the list of allowed hosts is, because
  149. it is way too easy to spoof an IP address in a TCP/IP packet.
  150. '''
  151. error_message= "Access from this host is not permitted."
  152. def __init__(self, host):
  153. self.host= host
  154. def eval_with_object( self, obj, errors=None ):
  155. '''
  156. Match the visitor's host against the criteria.
  157. '''
  158. ip = _remoteHost()
  159. if _match_ip( self.host, ip ):
  160. return True
  161. self.append_error_message( errors )
  162. return False
  163. class from_any_host(Any, IdentityPredicateHelper):
  164. '''
  165. Predicate for checking whether the visitor's host is one of a number of
  166. permitted hosts.
  167. '''
  168. error_message= "Access from this host is not permitted."
  169. def __init__(self, hosts):
  170. host_predicates= [from_host(h) for h in hosts]
  171. super(from_any_host,self).__init__( *host_predicates )