1 new commit in galaxy-central: https://bitbucket.org/galaxy/galaxy-central/commits/1df960b4892a/ Changeset: 1df960b4892a User: jmchilton Date: 2013-11-11 06:37:56 Summary: PEP-8 cleanups of lib/galaxy/security/__init__.py. Affected #: 1 file diff -r b5a149b877a5f14861a66bec2a2f1bb22ba55a22 -r 1df960b4892ae935840455de9ac058e396ec9410 lib/galaxy/security/__init__.py --- a/lib/galaxy/security/__init__.py +++ b/lib/galaxy/security/__init__.py @@ -2,7 +2,9 @@ Galaxy Security """ -import logging, socket, operator +import logging +import socket +import operator from datetime import datetime, timedelta from galaxy.util.bunch import Bunch from galaxy.util import listify @@ -10,96 +12,131 @@ log = logging.getLogger(__name__) + class Action( object ): def __init__( self, action, description, model ): self.action = action self.description = description self.model = model + class RBACAgent: """Class that handles galaxy security""" permitted_actions = Bunch( - DATASET_MANAGE_PERMISSIONS = Action( "manage permissions", "Users having associated role can manage the roles associated with permissions on this dataset", "grant" ), - DATASET_ACCESS = Action( "access", "Users having associated role can import this dataset into their history for analysis", "restrict" ), - LIBRARY_ACCESS = Action( "access library", "Restrict access to this library to only users having associated role", "restrict" ), - LIBRARY_ADD = Action( "add library item", "Users having associated role can add library items to this library item", "grant" ), - LIBRARY_MODIFY = Action( "modify library item", "Users having associated role can modify this library item", "grant" ), - LIBRARY_MANAGE = Action( "manage library permissions", "Users having associated role can manage roles associated with permissions on this library item", "grant" ), + DATASET_MANAGE_PERMISSIONS=Action( "manage permissions", "Users having associated role can manage the roles associated with permissions on this dataset", "grant" ), + DATASET_ACCESS=Action( "access", "Users having associated role can import this dataset into their history for analysis", "restrict" ), + LIBRARY_ACCESS=Action( "access library", "Restrict access to this library to only users having associated role", "restrict" ), + LIBRARY_ADD=Action( "add library item", "Users having associated role can add library items to this library item", "grant" ), + LIBRARY_MODIFY=Action( "modify library item", "Users having associated role can modify this library item", "grant" ), + LIBRARY_MANAGE=Action( "manage library permissions", "Users having associated role can manage roles associated with permissions on this library item", "grant" ), # Request type permissions - REQUEST_TYPE_ACCESS = Action( "access request_type", "Restrict access to this request type to only users having associated role", "restrict" ) + REQUEST_TYPE_ACCESS=Action( "access request_type", "Restrict access to this request type to only users having associated role", "restrict" ) + ) - ) def get_action( self, name, default=None ): """Get a permitted action by its dict key or action name""" for k, v in self.permitted_actions.items(): if k == name or v.action == name: return v return default + def get_actions( self ): """Get all permitted actions as a list of Action objects""" return self.permitted_actions.__dict__.values() + def get_item_actions( self, action, item ): raise 'No valid method of retrieving action (%s) for item %s.' % ( action, item ) - def guess_derived_permissions_for_datasets( self, datasets = [] ): + + def guess_derived_permissions_for_datasets( self, datasets=[] ): raise "Unimplemented Method" + def can_access_dataset( self, roles, dataset ): raise "Unimplemented Method" + def can_manage_dataset( self, roles, dataset ): raise "Unimplemented Method" + def can_access_library( self, roles, library ): raise "Unimplemented Method" + def can_add_library_item( self, roles, item ): raise "Unimplemented Method" + def can_modify_library_item( self, roles, item ): raise "Unimplemented Method" + def can_manage_library_item( self, roles, item ): raise "Unimplemented Method" + def associate_components( self, **kwd ): raise 'No valid method of associating provided components: %s' % kwd + def create_private_user_role( self, user ): raise "Unimplemented Method" + def get_private_user_role( self, user ): raise "Unimplemented Method" + def get_accessible_request_types( self, trans, user ): raise "Unimplemented Method" + def user_set_default_permissions( self, user, permissions={}, history=False, dataset=False ): raise "Unimplemented Method" + def history_set_default_permissions( self, history, permissions=None, dataset=False, bypass_manage_permission=False ): raise "Unimplemented Method" + def set_all_dataset_permissions( self, dataset, permissions ): raise "Unimplemented Method" + def set_dataset_permission( self, dataset, permission ): raise "Unimplemented Method" + def set_all_library_permissions( self, trans, dataset, permissions ): raise "Unimplemented Method" + def library_is_public( self, library ): raise "Unimplemented Method" + def make_library_public( self, library ): raise "Unimplemented Method" + def get_accessible_libraries( self, trans, user ): raise "Unimplemented Method" + def get_permitted_libraries( self, trans, user, actions ): raise "Unimplemented Method" + def folder_is_public( self, library ): raise "Unimplemented Method" + def make_folder_public( self, folder, count=0 ): raise "Unimplemented Method" + def dataset_is_public( self, dataset ): raise "Unimplemented Method" + def make_dataset_public( self, dataset ): raise "Unimplemented Method" + def get_permissions( self, library_dataset ): raise "Unimplemented Method" + def get_all_roles( self, trans, cntrller ): raise "Unimplemented Method" + def get_legitimate_roles( self, trans, item, cntrller ): raise "Unimplemented Method" + def derive_roles_from_access( self, trans, item_id, cntrller, library=False, **kwd ): raise "Unimplemented Method" + def get_component_associations( self, **kwd ): raise "Unimplemented Method" + def components_are_associated( self, **kwd ): return bool( self.get_component_associations( **kwd ) ) + def convert_permitted_action_strings( self, permitted_action_strings ): """ When getting permitted actions from an untrusted source like a @@ -107,6 +144,7 @@ """ return filter( lambda x: x is not None, [ self.permitted_actions.get( action_string ) for action_string in permitted_action_strings ] ) + class GalaxyRBACAgent( RBACAgent ): def __init__( self, model, permitted_actions=None ): self.model = model @@ -118,10 +156,12 @@ ( self.model.LibraryFolder, self.model.LibraryFolderPermissions ), ( self.model.LibraryDataset, self.model.LibraryDatasetPermissions ), ( self.model.LibraryDatasetDatasetAssociation, self.model.LibraryDatasetDatasetAssociationPermissions ) ) + @property def sa_session( self ): """Returns a SQLAlchemy session""" return self.model.context + def sort_by_attr( self, seq, attr ): """ Sort the sequence of objects by object's attribute @@ -137,19 +177,20 @@ intermed = map( None, map( getattr, seq, ( attr, ) * len( seq ) ), xrange( len( seq ) ), seq ) intermed.sort() return map( operator.getitem, intermed, ( -1, ) * len( intermed ) ) + def get_all_roles( self, trans, cntrller ): admin_controller = cntrller in [ 'library_admin' ] roles = set() if not trans.user: return trans.sa_session.query( trans.app.model.Role ) \ - .filter( and_( self.model.Role.table.c.deleted==False, + .filter( and_( self.model.Role.table.c.deleted == False, self.model.Role.table.c.type != self.model.Role.types.PRIVATE, self.model.Role.table.c.type != self.model.Role.types.SHARING ) ) \ .order_by( self.model.Role.table.c.name ) if admin_controller: # The library is public and the user is an admin, so all roles are legitimate for role in trans.sa_session.query( trans.app.model.Role ) \ - .filter( self.model.Role.table.c.deleted==False ) \ + .filter( self.model.Role.table.c.deleted == False ) \ .order_by( self.model.Role.table.c.name ): roles.add( role ) else: @@ -160,12 +201,13 @@ roles.add( role ) # Add all remaining non-private, non-sharing roles for role in trans.sa_session.query( trans.app.model.Role ) \ - .filter( and_( self.model.Role.table.c.deleted==False, + .filter( and_( self.model.Role.table.c.deleted == False, self.model.Role.table.c.type != self.model.Role.types.PRIVATE, self.model.Role.table.c.type != self.model.Role.types.SHARING ) ) \ .order_by( self.model.Role.table.c.name ): roles.add( role ) return self.sort_by_attr( [ role for role in roles ], 'name' ) + def get_legitimate_roles( self, trans, item, cntrller ): """ Return a sorted list of legitimate roles that can be associated with a permission on @@ -215,6 +257,7 @@ if admin_controller or self.ok_to_display( trans.user, ura.role ): roles.add( ura.role ) return self.sort_by_attr( [ role for role in roles ], 'name' ) + def ok_to_display( self, user, role ): """ Method for checking if: @@ -257,7 +300,6 @@ break return ret_val - def get_actions_for_items( self, trans, action, permission_items ): # TODO: Rename this; it's a replacement for get_item_actions, but it # doesn't represent what it's really doing, which is confusing. @@ -345,7 +387,6 @@ return ret_permissions - def allow_action_on_libitems( self, trans, user_roles, action, items ): """ This should be the equivalent of allow_action defined on multiple items. @@ -359,7 +400,7 @@ # Change item to lib_dataset or vice-versa. for item in items: - if all_items_actions.has_key( item.id ): + if item.id in all_items_actions: item_actions = all_items_actions[ item.id ] if self.permitted_actions.DATASET_ACCESS == action: @@ -399,7 +440,6 @@ log.debug( "allow_action_for_items: test end" ) return ret_allow_action - # DELETEME: SM: DO NOT TOUCH! This actually works. def dataset_access_mapping( self, trans, user_roles, datasets ): ''' @@ -432,7 +472,8 @@ # so this will have to be rewritten to support other items. libitems_public_map = self.datasets_are_public( trans, libitems ) libitems_allow_action_map = self.allow_action_on_libitems( - trans, user_roles, self.permitted_actions.DATASET_ACCESS, libitems ) + trans, user_roles, self.permitted_actions.DATASET_ACCESS, libitems + ) can_access = {} for libitem in libitems: can_access[ libitem.id ] = libitems_public_map[ libitem.id ] or libitems_allow_action_map[ libitem.id ] @@ -440,15 +481,18 @@ def item_permission_map_for_modify( self, trans, user_roles, libitems ): return self.allow_action_on_libitems( - trans, user_roles, self.permitted_actions.LIBRARY_MODIFY, libitems ) + trans, user_roles, self.permitted_actions.LIBRARY_MODIFY, libitems + ) def item_permission_map_for_manage( self, trans, user_roles, libitems ): return self.allow_action_on_libitems( - trans, user_roles, self.permitted_actions.LIBRARY_MANAGE, libitems ) + trans, user_roles, self.permitted_actions.LIBRARY_MANAGE, libitems + ) def item_permission_map_for_add( self, trans, user_roles, libitems ): return self.allow_action_on_libitems( - trans, user_roles, self.permitted_actions.LIBRARY_ADD, libitems ) + trans, user_roles, self.permitted_actions.LIBRARY_ADD, libitems + ) def can_access_dataset( self, user_roles, dataset ): # SM: dataset_is_public will access dataset.actions, which is a @@ -458,8 +502,10 @@ def can_manage_dataset( self, roles, dataset ): return self.allow_action( roles, self.permitted_actions.DATASET_MANAGE_PERMISSIONS, dataset ) + def can_access_library( self, roles, library ): return self.library_is_public( library ) or self.allow_action( roles, self.permitted_actions.LIBRARY_ACCESS, library ) + def get_accessible_libraries( self, trans, user ): """Return all data libraries that the received user can access""" accessible_libraries = [] @@ -480,6 +526,7 @@ .order_by( trans.app.model.Library.name ): accessible_libraries.append( library ) return accessible_libraries + def has_accessible_folders( self, trans, folder, user, roles, search_downward=True ): if self.has_accessible_library_datasets( trans, folder, user, roles, search_downward=search_downward ) or \ self.can_add_library_item( roles, folder ) or \ @@ -490,20 +537,23 @@ for folder in folder.active_folders: return self.has_accessible_folders( trans, folder, user, roles, search_downward=search_downward ) return False + def has_accessible_library_datasets( self, trans, folder, user, roles, search_downward=True ): for library_dataset in trans.sa_session.query( trans.model.LibraryDataset ) \ .filter( and_( trans.model.LibraryDataset.table.c.deleted == False, - trans.app.model.LibraryDataset.table.c.folder_id==folder.id ) ): + trans.app.model.LibraryDataset.table.c.folder_id == folder.id ) ): if self.can_access_library_item( roles, library_dataset, user ): return True if search_downward: return self.__active_folders_have_accessible_library_datasets( trans, folder, user, roles ) return False + def __active_folders_have_accessible_library_datasets( self, trans, folder, user, roles ): for active_folder in folder.active_folders: if self.has_accessible_library_datasets( trans, active_folder, user, roles ): return True return False + def can_access_library_item( self, roles, item, user ): if type( item ) == self.model.Library: return self.can_access_library( roles, item ) @@ -514,12 +564,15 @@ elif type( item ) == self.model.LibraryDatasetDatasetAssociation: return self.can_access_library( roles, item.library_dataset.folder.parent_library ) and self.can_access_dataset( roles, item.dataset ) else: - log.warning( 'Unknown library item type: %s' % type ( item ) ) + log.warning( 'Unknown library item type: %s' % type( item ) ) return False + def can_add_library_item( self, roles, item ): return self.allow_action( roles, self.permitted_actions.LIBRARY_ADD, item ) + def can_modify_library_item( self, roles, item ): return self.allow_action( roles, self.permitted_actions.LIBRARY_MODIFY, item ) + def can_manage_library_item( self, roles, item ): return self.allow_action( roles, self.permitted_actions.LIBRARY_MANAGE, item ) @@ -554,6 +607,7 @@ # join existing roles with new roles perms[ action ].extend( filter( lambda x: x not in perms[ action ], roles ) ) return perms + def associate_components( self, **kwd ): if 'user' in kwd: if 'group' in kwd: @@ -567,26 +621,31 @@ if 'dataset' in kwd and 'role' in kwd: return self.associate_action_dataset_role( kwd['action'], kwd['dataset'], kwd['role'] ) raise 'No valid method of associating provided components: %s' % kwd + def associate_user_group( self, user, group ): assoc = self.model.UserGroupAssociation( user, group ) self.sa_session.add( assoc ) self.sa_session.flush() return assoc + def associate_user_role( self, user, role ): assoc = self.model.UserRoleAssociation( user, role ) self.sa_session.add( assoc ) self.sa_session.flush() return assoc + def associate_group_role( self, group, role ): assoc = self.model.GroupRoleAssociation( group, role ) self.sa_session.add( assoc ) self.sa_session.flush() return assoc + def associate_action_dataset_role( self, action, dataset, role ): assoc = self.model.DatasetPermissions( action, dataset, role ) self.sa_session.add( assoc ) self.sa_session.flush() return assoc + def create_private_user_role( self, user ): # Create private role role = self.model.Role( name=user.email, description='Private Role for ' + user.email, type=self.model.Role.types.PRIVATE ) @@ -595,6 +654,7 @@ # Add user to role self.associate_components( role=role, user=user ) return role + def get_private_user_role( self, user, auto_create=False ): role = self.sa_session.query( self.model.Role ) \ .filter( and_( self.model.Role.table.c.name == user.email, @@ -606,11 +666,13 @@ else: return None return role + def get_sharing_roles( self, user ): return self.sa_session.query( self.model.Role ) \ .filter( and_( ( self.model.Role.table.c.name ).like( "Sharing role for: %" + user.email + "%" ), self.model.Role.table.c.type == self.model.Role.types.SHARING ) ) - def user_set_default_permissions( self, user, permissions={}, history=False, dataset=False, bypass_manage_permission=False, default_access_private = False ): + + def user_set_default_permissions( self, user, permissions={}, history=False, dataset=False, bypass_manage_permission=False, default_access_private=False ): # bypass_manage_permission is used to change permissions of datasets in a userless history when logging in flush_needed = False if user is None: @@ -637,6 +699,7 @@ if history: for history in user.active_histories: self.history_set_default_permissions( history, permissions=permissions, dataset=dataset, bypass_manage_permission=bypass_manage_permission ) + def user_get_default_permissions( self, user ): permissions = {} for dup in user.default_permissions: @@ -646,6 +709,7 @@ else: permissions[ action ] = [ dup.role ] return permissions + def history_set_default_permissions( self, history, permissions={}, dataset=False, bypass_manage_permission=False ): # bypass_manage_permission is used to change permissions of datasets in a user-less history when logging in flush_needed = False @@ -680,6 +744,7 @@ continue if bypass_manage_permission or self.can_manage_dataset( user.all_roles(), dataset ): self.set_all_dataset_permissions( dataset, permissions ) + def history_get_default_permissions( self, history ): permissions = {} for dhp in history.default_permissions: @@ -689,6 +754,7 @@ else: permissions[ action ] = [ dhp.role ] return permissions + def set_all_dataset_permissions( self, dataset, permissions={} ): """ Set new permissions on a dataset, eliminating all current permissions @@ -721,6 +787,7 @@ if flush_needed: self.sa_session.flush() return "" + def set_dataset_permission( self, dataset, permission={} ): """ Set a specific permission on a dataset, leaving all other current permissions on the dataset alone @@ -741,6 +808,7 @@ flush_needed = True if flush_needed: self.sa_session.flush() + def get_permissions( self, item ): """ Return a dictionary containing the actions and associated roles on item @@ -755,6 +823,7 @@ else: permissions[ action ] = [ item_permission.role ] return permissions + def get_accessible_request_types( self, trans, user ): """Return all RequestTypes that the received user has permission to access.""" accessible_request_types = [] @@ -775,13 +844,15 @@ .order_by( trans.app.model.RequestType.name ): accessible_request_types.append( request_type ) return accessible_request_types + def copy_dataset_permissions( self, src, dst ): if not isinstance( src, self.model.Dataset ): src = src.dataset if not isinstance( dst, self.model.Dataset ): dst = dst.dataset self.set_all_dataset_permissions( dst, self.get_permissions( src ) ) - def privately_share_dataset( self, dataset, users = [] ): + + def privately_share_dataset( self, dataset, users=[] ): intersect = None for user in users: roles = [ ura.role for ura in user.roles if ura.role.type == self.model.Role.types.SHARING ] @@ -801,13 +872,14 @@ sharing_role = role break if sharing_role is None: - sharing_role = self.model.Role( name = "Sharing role for: " + ", ".join( [ u.email for u in users ] ), - type = self.model.Role.types.SHARING ) + sharing_role = self.model.Role( name="Sharing role for: " + ", ".join( [ u.email for u in users ] ), + type=self.model.Role.types.SHARING ) self.sa_session.add( sharing_role ) self.sa_session.flush() for user in users: self.associate_components( user=user, role=sharing_role ) self.set_dataset_permission( dataset, { self.permitted_actions.DATASET_ACCESS : [ sharing_role ] } ) + def set_all_library_permissions( self, trans, library_item, permissions={} ): # Set new permissions on library_item, eliminating all current permissions flush_needed = False @@ -828,6 +900,9 @@ # so it is possible that some Datasets have no roles associated with the DATASET_MANAGE_PERMISSIONS # permission. In this case, we'll reset this permission to the library_item user's private role. if not library_item.dataset.has_manage_permissions_roles( trans ): + # Well this looks like a bug, this should be looked at. + # Default permissions above is single hash that keeps getting reeditted here + # because permission is being defined instead of permissions. -John permission = {} permissions[ self.permitted_actions.DATASET_MANAGE_PERMISSIONS ] = [ trans.app.security_agent.get_private_user_role( library_item.user ) ] self.set_dataset_permission( library_item.dataset, permissions ) @@ -840,6 +915,7 @@ self.set_dataset_permission( library_item.dataset, permissions ) if flush_needed: self.sa_session.flush() + def library_is_public( self, library, contents=False ): if contents: # Check all contained folders and datasets to find any that are not public @@ -847,6 +923,7 @@ return False # A library is considered public if there are no "access" actions associated with it. return self.permitted_actions.LIBRARY_ACCESS.action not in [ a.action for a in library.actions ] + def make_library_public( self, library, contents=False ): flush_needed = False if contents: @@ -859,6 +936,7 @@ flush_needed = True if flush_needed: self.sa_session.flush() + def folder_is_public( self, folder ): for sub_folder in folder.folders: if not self.folder_is_public( sub_folder ): @@ -868,6 +946,7 @@ if ldda and ldda.dataset and not self.dataset_is_public( ldda.dataset ): return False return True + def make_folder_public( self, folder ): # Make all of the contents (include deleted contents, but not purged contents) of folder public for sub_folder in folder.folders: @@ -909,7 +988,6 @@ datasets_public[ permission.dataset_id ] = False return datasets_public - def make_dataset_public( self, dataset ): # A dataset is considered public if there are no "access" actions associated with it. Any # other actions ( 'manage permissions', 'edit metadata' ) are irrelevant. @@ -920,6 +998,7 @@ flush_needed = True if flush_needed: self.sa_session.flush() + def derive_roles_from_access( self, trans, item_id, cntrller, library=False, **kwd ): # Check the access permission on a dataset. If library is true, item_id refers to a library. If library # is False, item_id refers to a dataset ( item_id must currently be decoded before being sent ). The @@ -1017,6 +1096,7 @@ else: permissions[ self.get_action( v.action ) ] = in_roles return permissions, in_roles, error, msg + def copy_library_permissions( self, trans, source_library_item, target_library_item, user=None ): # Copy all relevant permissions from source. permissions = {} @@ -1037,13 +1117,14 @@ # Make sure user's private role is included private_role = self.model.security_agent.get_private_user_role( user ) for name, action in self.permitted_actions.items(): - if not permission_class.filter_by( role_id = private_role.id, action = action.action ).first(): + if not permission_class.filter_by( role_id=private_role.id, action=action.action ).first(): lp = permission_class( action.action, target_library_item, private_role ) self.sa_session.add( lp ) self.sa_session.flush() else: raise 'Invalid class (%s) specified for target_library_item (%s)' % \ ( target_library_item.__class__, target_library_item.__class__.__name__ ) + def get_permitted_libraries( self, trans, user, actions ): """ This method is historical (it is not currently used), but may be useful again at some @@ -1073,6 +1154,7 @@ if can_show: libraries[ library ] = hidden_folder_ids return libraries + def show_library_item( self, user, roles, library_item, actions_to_check, hidden_folder_ids='' ): """ This method must be sent an instance of Library() or LibraryFolder(). Recursive execution produces a @@ -1097,6 +1179,7 @@ else: hidden_folder_ids = '%d' % folder.id return False, hidden_folder_ids + def get_showable_folders( self, user, roles, library_item, actions_to_check, hidden_folder_ids=[], showable_folders=[] ): """ This method must be sent an instance of Library(), all the folders of which are scanned to determine if @@ -1115,6 +1198,7 @@ for folder in library_item.active_folders: self.get_showable_folders( user, roles, folder, actions_to_check, showable_folders=showable_folders ) return showable_folders + def set_entity_user_associations( self, users=[], roles=[], groups=[], delete_existing_assocs=True ): for user in users: if delete_existing_assocs: @@ -1131,6 +1215,7 @@ self.associate_components( user=user, role=role ) for group in groups: self.associate_components( user=user, group=group ) + def set_entity_group_associations( self, groups=[], users=[], roles=[], delete_existing_assocs=True ): for group in groups: if delete_existing_assocs: @@ -1144,6 +1229,7 @@ self.associate_components( group=group, role=role ) for user in users: self.associate_components( group=group, user=user ) + def set_entity_role_associations( self, roles=[], users=[], groups=[], delete_existing_assocs=True ): for role in roles: if delete_existing_assocs: @@ -1157,20 +1243,22 @@ self.associate_components( user=user, role=role ) for group in groups: self.associate_components( group=group, role=role ) + def get_component_associations( self, **kwd ): assert len( kwd ) == 2, 'You must specify exactly 2 Galaxy security components to check for associations.' if 'dataset' in kwd: if 'action' in kwd: - return self.sa_session.query( self.model.DatasetPermissions ).filter_by( action = kwd['action'].action, dataset_id = kwd['dataset'].id ).first() + return self.sa_session.query( self.model.DatasetPermissions ).filter_by( action=kwd['action'].action, dataset_id=kwd['dataset'].id ).first() elif 'user' in kwd: if 'group' in kwd: - return self.sa_session.query( self.model.UserGroupAssociation ).filter_by( group_id = kwd['group'].id, user_id = kwd['user'].id ).first() + return self.sa_session.query( self.model.UserGroupAssociation ).filter_by( group_id=kwd['group'].id, user_id=kwd['user'].id ).first() elif 'role' in kwd: - return self.sa_session.query( self.model.UserRoleAssociation ).filter_by( role_id = kwd['role'].id, user_id = kwd['user'].id ).first() + return self.sa_session.query( self.model.UserRoleAssociation ).filter_by( role_id=kwd['role'].id, user_id=kwd['user'].id ).first() elif 'group' in kwd: if 'role' in kwd: - return self.sa_session.query( self.model.GroupRoleAssociation ).filter_by( role_id = kwd['role'].id, group_id = kwd['group'].id ).first() + return self.sa_session.query( self.model.GroupRoleAssociation ).filter_by( role_id=kwd['role'].id, group_id=kwd['group'].id ).first() raise 'No valid method of associating provided components: %s' % kwd + def check_folder_contents( self, user, roles, folder, hidden_folder_ids='' ): """ This method must always be sent an instance of LibraryFolder(). Recursive execution produces a @@ -1210,6 +1298,7 @@ else: hidden_folder_ids = '%d' % sub_folder.id return False, hidden_folder_ids + def can_access_request_type( self, roles, request_type ): action = self.permitted_actions.REQUEST_TYPE_ACCESS request_type_actions = [] @@ -1224,12 +1313,12 @@ ret_val = True break return ret_val + def set_request_type_permissions( self, request_type, permissions={} ): # Set new permissions on request_type, eliminating all current permissions for role_assoc in request_type.actions: self.sa_session.delete( role_assoc ) # Add the new permissions on request_type - item_class = self.model.RequestType permission_class = self.model.RequestTypePermissions flush_needed = False for action, roles in permissions.items(): @@ -1241,6 +1330,7 @@ if flush_needed: self.sa_session.flush() + class HostAgent( RBACAgent ): """ A simple security agent which allows access to datasets based on host. @@ -1249,30 +1339,33 @@ """ # TODO: Make sites user configurable sites = Bunch( - ucsc_main = ( 'hgw1.cse.ucsc.edu', 'hgw2.cse.ucsc.edu', 'hgw3.cse.ucsc.edu', 'hgw4.cse.ucsc.edu', + ucsc_main=( 'hgw1.cse.ucsc.edu', 'hgw2.cse.ucsc.edu', 'hgw3.cse.ucsc.edu', 'hgw4.cse.ucsc.edu', 'hgw5.cse.ucsc.edu', 'hgw6.cse.ucsc.edu', 'hgw7.cse.ucsc.edu', 'hgw8.cse.ucsc.edu' ), - ucsc_test = ( 'hgwdev.cse.ucsc.edu', ), - ucsc_archaea = ( 'lowepub.cse.ucsc.edu', ) + ucsc_test=( 'hgwdev.cse.ucsc.edu', ), + ucsc_archaea=( 'lowepub.cse.ucsc.edu', ) ) + def __init__( self, model, permitted_actions=None ): self.model = model if permitted_actions: self.permitted_actions = permitted_actions + @property def sa_session( self ): """Returns a SQLAlchemy session""" return self.model.context + def allow_action( self, addr, action, **kwd ): if 'dataset' in kwd and action == self.permitted_actions.DATASET_ACCESS: hda = kwd['dataset'] if action == self.permitted_actions.DATASET_ACCESS and action.action not in [ dp.action for dp in hda.dataset.actions ]: log.debug( 'Allowing access to public dataset with hda: %i.' % hda.id ) - return True # dataset has no roles associated with the access permission, thus is already public + return True # dataset has no roles associated with the access permission, thus is already public hdadaa = self.sa_session.query( self.model.HistoryDatasetAssociationDisplayAtAuthorization ) \ - .filter_by( history_dataset_association_id = hda.id ).first() + .filter_by( history_dataset_association_id=hda.id ).first() if not hdadaa: log.debug( 'Denying access to private dataset with hda: %i. No hdadaa record for this dataset.' % hda.id ) - return False # no auth + return False # no auth # We could just look up the reverse of addr, but then we'd also # have to verify it with the forward address and special case any # IPs (instead of hosts) in the server list. @@ -1284,22 +1377,23 @@ # balancing their connections (as UCSC does), this is okay. try: if socket.gethostbyname( server ) == addr: - break # remote host is in the server list + break # remote host is in the server list except ( socket.error, socket.gaierror ): - pass # can't resolve, try next + pass # can't resolve, try next else: log.debug( 'Denying access to private dataset with hda: %i. Remote addr is not a valid server for site: %s.' % ( hda.id, hdadaa.site ) ) - return False # remote addr is not in the server list + return False # remote addr is not in the server list if ( datetime.utcnow() - hdadaa.update_time ) > timedelta( seconds=60 ): log.debug( 'Denying access to private dataset with hda: %i. Authorization was granted, but has expired.' % hda.id ) - return False # not authz'd in the last 60 seconds + return False # not authz'd in the last 60 seconds log.debug( 'Allowing access to private dataset with hda: %i. Remote server is: %s.' % ( hda.id, server ) ) return True else: raise 'The dataset access permission is the only valid permission in the host security agent.' + def set_dataset_permissions( self, hda, user, site ): hdadaa = self.sa_session.query( self.model.HistoryDatasetAssociationDisplayAtAuthorization ) \ - .filter_by( history_dataset_association_id = hda.id ).first() + .filter_by( history_dataset_association_id=hda.id ).first() if hdadaa: hdadaa.update_time = datetime.utcnow() else: @@ -1307,6 +1401,7 @@ self.sa_session.add( hdadaa ) self.sa_session.flush() + def get_permitted_actions( filter=None ): '''Utility method to return a subset of RBACAgent's permitted actions''' if filter is None: Repository URL: https://bitbucket.org/galaxy/galaxy-central/ -- This is a commit notification from bitbucket.org. You are receiving this because you have the service enabled, addressing the recipient of this email.