def resource_delete(context, data_dict):
    '''
    Nearly plain copying of resource_delete: CKAN calls local package_delete, thus passing our local version of it.

    :param context: context
    :param data_dict: data_dict
    :return: dict with success and optional msg
    '''

    model = context['model']
    user = context.get('user')
    resource = logic_auth.get_resource_object(context, data_dict)

    # check authentication against package
    pkg = model.Package.get(resource.package_id)
    if not pkg:
        raise NotFound(_('No package found for this resource, cannot check auth.'))

    pkg_dict = {'id': pkg.id}
    authorized = package_delete(context, pkg_dict).get('success')

    if not authorized:
        return {'success': False, 'msg': _('User %s not authorized to delete resource %s') % (user, resource.id)}
    else:
        return {'success': True}
def resource_show(context, data_dict):
    # This function is needed since CKAN resource_show function uses the default package_show
    # function instead of the one defined in the plugin.
    # A bug is openend in order to be able to remove this function
    # https://github.com/ckan/ckan/issues/1818
    # It's fixed now, so this function can be deleted when the new version is released.
    _model = context['model']
    user = context.get('user')
    resource = logic_auth.get_resource_object(context, data_dict)

    # check authentication against package
    query = _model.Session.query(_model.Package)\
        .join(_model.ResourceGroup)\
        .join(_model.Resource)\
        .filter(_model.ResourceGroup.id == resource.resource_group_id)
    pkg = query.first()
    if not pkg:
        raise tk.ObjectNotFound(_('No package found for this resource, cannot check auth.'))

    pkg_dict = {'id': pkg.id}
    authorized = package_show(context, pkg_dict).get('success')

    if not authorized:
        return {'success': False, 'msg': _('User %s not authorized to read resource %s') % (user, resource.id)}
    else:
        return {'success': True}
Beispiel #3
0
def resource_create(context, data_dict):
    model = context['model']
    user = context.get('user')

    package_id = data_dict.get('package_id')
    if not package_id and data_dict.get('id'):
        # This can happen when auth is deferred, eg from `resource_view_create`
        resource = logic_auth.get_resource_object(context, data_dict)
        package_id = resource.package_id

    if not package_id:
        raise logic.NotFound(
            _('No dataset id provided, cannot check auth.')
        )

    # check authentication against package
    pkg = model.Package.get(package_id)
    if not pkg:
        raise logic.NotFound(
            _('No package found for this resource, cannot check auth.')
        )

    pkg_dict = {'id': pkg.id}
    authorized = authz.is_authorized('package_update', context, pkg_dict).get('success')

    if not authorized:
        return {'success': False,
                'msg': _('User %s not authorized to create resources on dataset %s') %
                        (str(user), package_id)}
    else:
        return {'success': True}
Beispiel #4
0
def resource_update(context, data_dict):
    model = context['model']
    user = context.get('user')
    resource = logic_auth.get_resource_object(context, data_dict)

    # check authentication against package
    query = model.Session.query(model.Package)\
        .join(model.ResourceGroup)\
        .join(model.Resource)\
        .filter(model.ResourceGroup.id == resource.resource_group_id)
    pkg = query.first()
    if not pkg:
        raise logic.NotFound(
            _('No package found for this resource, cannot check auth.')
        )

    pkg_dict = {'id': pkg.id}
    authorized = new_authz.is_authorized('package_update', context, pkg_dict).get('success')

    if not authorized:
        return {'success': False,
                'msg': _('User %s not authorized to edit resource %s') %
                        (str(user), resource.id)}
    else:
        return {'success': True}
Beispiel #5
0
def resource_view_delete(fb, context, data_dict):
    user = context['auth_user_obj']
    resource_view = get_resource_view_object(context, data_dict)
    resource = get_resource_object(context, {'id': resource_view.resource_id})
    if user_owns_package_as_member(user, resource.resource_group.package):
        return {'success': True}
    elif user_is_member_of_package_org(user, resource.resource_group.package):
        return {'success': False}

    return fb(context, data_dict)
Beispiel #6
0
def resource_update(fb, context, data_dict):
    user = context['auth_user_obj']
    resource = get_resource_object(context, data_dict)
    package = resource.resource_group.package
    if user_owns_package_as_member(user, package):
        return {'success': True}
    elif user_is_member_of_package_org(user, package):
        return {'success': False}

    return fb(context, data_dict)
def resource_view_update(context, data_dict):
    user = context['auth_user_obj']
    resource_view = get_resource_view_object(context, data_dict)
    resource = get_resource_object(context, {'id': resource_view.resource_id})
    if user_owns_package_as_member(user, resource.resource_group.package):
        return {'success': True}
    elif user_is_member_of_package_org(user, resource.resource_group.package):
        return {'success': False}

    fallback = get_default_auth('update', 'resource_view_update')
    return fallback(context, data_dict)
def resource_delete(context, data_dict):
    user = context['auth_user_obj']
    resource = get_resource_object(context, data_dict)
    package = resource.resource_group.package
    if user_owns_package_as_member(user, package):
        return {'success': True}
    elif user_is_member_of_package_org(user, package):
        return {'success': False}

    fallback = get_default_auth('delete', 'resource_delete')
    return fallback(context, data_dict)
Beispiel #9
0
def resource_show(context, data_dict):
    """ Resource show permission checks the user group if the package state is deleted """
    model = context['model']
    user = context.get('user')
    resource = get_resource_object(context, data_dict)
    package = resource.resource_group.package

    if package.state == 'deleted':
        userobj = model.User.get( user )
        if not userobj:
            return {'success': False, 'msg': _('User %s not authorized to read resource %s') % (str(user),package.id)}
        if not _groups_intersect( userobj.get_groups('organization'), package.get_groups('organization') ):
            return {'success': False, 'msg': _('User %s not authorized to read package %s') % (str(user),package.id)}

    pkg_dict = {'id': package.id}
    return package_show(context, pkg_dict)
Beispiel #10
0
    def test_get_resource_object_with_id(self):

        user_name = helpers.call_action('get_site_user')['name']
        dataset = helpers.call_action('package_create',
                                      context={'user': user_name},
                                      name='test_dataset')
        resource = helpers.call_action('resource_create',
                                       context={'user': user_name},
                                       package_id=dataset['id'],
                                       url='http://foo')

        context = {'model': core_model}
        obj = logic_auth.get_resource_object(context, {'id': resource['id']})

        assert obj.id == resource['id']
        assert context['resource'] == obj
Beispiel #11
0
def resource_delete(context, data_dict):
    model = context['model']
    user = context.get('user')
    resource = get_resource_object(context, data_dict)

    # check authentication against package
    pkg = model.Package.get(resource.package_id)
    if not pkg:
        raise logic.NotFound(_('No package found for this resource, cannot check auth.'))

    pkg_dict = {'id': pkg.id}
    authorized = authz.is_authorized('package_delete', context, pkg_dict).get('success')

    if not authorized:
        return {'success': False, 'msg': _('User %s not authorized to delete resource %s') % (user, resource.id)}
    else:
        return {'success': True}
Beispiel #12
0
def edit_resource(context, data_dict):
    '''
    Check if a user is allowed edit a resource.

    :param context: context
    :param data_dict: data dictionary

    :rype: dictionary
    '''
    auth_dict = update.resource_update(context, data_dict)

    resource = logic_auth.get_resource_object(context, data_dict)

    if resource.resource_type == settings.RESOURCE_TYPE_DATASET:
        return {'success': False, 'msg': _('Resource %s not editable') % (data_dict['id'])}
    else:
        return auth_dict
Beispiel #13
0
def resource_show(context, data_dict):
    model = context["model"]
    user = context.get("user")
    resource = get_resource_object(context, data_dict)

    # check authentication against package
    pkg = model.Package.get(resource.package_id)
    if not pkg:
        raise logic.NotFound(_("No package found for this resource, cannot check auth."))

    pkg_dict = {"id": pkg.id}
    authorized = authz.is_authorized("package_show", context, pkg_dict).get("success")

    if not authorized:
        return {"success": False, "msg": _("User %s not authorized to read resource %s") % (user, resource.id)}
    else:
        return {"success": True}
Beispiel #14
0
def resource_show(context, data_dict):
    model = context['model']
    user = context.get('user')
    resource = get_resource_object(context, data_dict)

    # check authentication against package
    pkg = model.Package.get(resource.package_id)
    if not pkg:
        raise logic.NotFound(_('No package found for this resource, cannot check auth.'))

    pkg_dict = {'id': pkg.id}
    authorized = authz.is_authorized('package_show', context, pkg_dict).get('success')

    if not authorized:
        return {'success': False, 'msg': _('User %s not authorized to read resource %s') % (user, resource.id)}
    else:
        return {'success': True}
Beispiel #15
0
def resource_update(context, data_dict):
    """
    Update resource permission checks the user is in a group that the resource's 
    package is also a member of.
    """
    model = context['model']
    user = context.get('user')
    resource = get_resource_object(context, data_dict)
    userobj = model.User.get( user )
    
    if not userobj:
        return {'success': False, 'msg': _('User %s not authorized to edit resources in this package') % str(user)}        
        
    if not _groups_intersect( userobj.get_groups('publisher'), resource.resource_group.package.get_groups('publisher') ):
        return {'success': False, 'msg': _('User %s not authorized to edit resources in this package') % str(user)}

    return {'success': True}
Beispiel #16
0
def resource_show_ext(context, data_dict):
    model = context['model']
    user = context.get('user')
    userobj = context.get('auth_user_obj')
    resource = get_resource_object(context, data_dict)

    # check authentication against package
    pkg = model.Package.get(resource.package_id)
    if not pkg:
        raise logic.NotFound(
            _('No package found for this resource, cannot check auth.'))

    pkg_dict = {'id': pkg.id}
    authorized = authz.is_authorized('package_show', context,
                                     pkg_dict).get('success')

    if not authorized:
        return {
            'success':
            False,
            'msg':
            _('User %s not authorized to read resource %s') %
            (user, resource.id)
        }

    if 'res_access' in data_dict:
        res_access = data_dict['res_access']
    else:
        res_access = True

    if userobj == None:
        mydataset = False
    else:
        mydataset = (userobj.id == pkg.creator_user_id)

    if not (mydataset or res_access):
        return {
            'success':
            False,
            'msg':
            _('User %s not authorized to read resource (access not public) %s')
            % (user, resource.id)
        }

    return {'success': True}
Beispiel #17
0
    def test_get_resource_object_with_id(self):

        user_name = helpers.call_action("get_site_user")["name"]
        dataset = helpers.call_action("package_create",
                                      context={"user": user_name},
                                      name="test_dataset")
        resource = helpers.call_action(
            "resource_create",
            context={"user": user_name},
            package_id=dataset["id"],
            url="http://foo",
        )

        context = {"model": core_model}
        obj = logic_auth.get_resource_object(context, {"id": resource["id"]})

        assert obj.id == resource["id"]
        assert context["resource"] == obj
def resource_show(context, data_dict):

    user = context.get('user')
    user_obj = context.get('auth_user_obj')
    resource = logic_auth.get_resource_object(context, data_dict)
    # check authentication against package
    package_dict = {'id': resource.package_id}
    package = logic_auth.get_package_object(context, package_dict)
    if not package:
        raise tk.ObjectNotFound(_('No package found for this resource, cannot check auth.'))

    if package and user_obj and package.creator_user_id == user_obj.id:
        return {'success': True}

    # active packages can only be seen by its owners
    if package.state == 'active':

        # anyone can see a public package
        if not package.private:
            return {'success': True}

        # if the user has rights to read in the organization or in the group
        if package.owner_org:
            authorized = authz.has_user_permission_for_group_or_org(
                package.owner_org, user, 'read')
        else:
            authorized = False

        if not authorized:
            # Init the model
            db.init_db(context['model'])

            # Branch not executed if the database return an empty list
            if db.AllowedUser.get(package_id=package.id, user_name=user):
                authorized = True

        if not authorized:
            return {'success': False, 'msg': _('User %s not authorized to read resource %s') % (user, resource.id)}

        else:
            return {'success': True}

    else:
        return {'success': False, 'msg': _('User %s not authorized to read resource %s') % (user, resource.id)}
def resource_view_create(context, data_dict):
    user = context['auth_user_obj']
    # data_dict provides 'resource_id', while get_resource_object expects 'id'. This is not consistent with the rest of
    # the API - so future proof it by catering for both cases in case the API is made consistent (one way or the other)
    # later.
    if data_dict and 'resource_id' in data_dict:
        dc = {'id': data_dict['resource_id'], 'resource_id': data_dict['resource_id']}
    elif data_dict and 'id' in data_dict:
        dc = {'id': data_dict['id'], 'resource_id': data_dict['id']}
    else:
        dc = data_dict
    resource = get_resource_object(context, dc)
    if user_owns_package_as_member(user, resource.resource_group.package):
        return {'success': True}
    elif user_is_member_of_package_org(user, resource.resource_group.package):
        return {'success': False}

    fallback = get_default_auth('create', 'resource_view_create')
    return fallback(context, data_dict)
def resource_view_create(context, data_dict):
    user = context['auth_user_obj']
    # data_dict provides 'resource_id', while get_resource_object expects 'id'. This is not consistent with the rest of
    # the API - so future proof it by catering for both cases in case the API is made consistent (one way or the other)
    # later.
    if data_dict and 'resource_id' in data_dict:
        dc = {'id': data_dict['resource_id'], 'resource_id': data_dict['resource_id']}
    elif data_dict and 'id' in data_dict:
        dc = {'id': data_dict['id'], 'resource_id': data_dict['id']}
    else:
        dc = data_dict
    resource = get_resource_object(context, dc)
    if user_owns_package_as_member(user, resource.package):
        return {'success': True}
    elif user_is_member_of_package_org(user, resource.package):
        return {'success': False}

    fallback = get_default_auth('create', 'resource_view_create')
    return fallback(context, data_dict)
Beispiel #21
0
def edit_resource(context, data_dict):
    '''
    Check if a user is allowed edit a resource.

    :param context: context
    :param data_dict: data dictionary

    :rype: dictionary
    '''
    auth_dict = update.resource_update(context, data_dict)

    resource = logic_auth.get_resource_object(context, data_dict)

    if resource.resource_type == settings.RESOURCE_TYPE_DATASET:
        return {
            'success': False,
            'msg': _('Resource %s not editable') % (data_dict['id'])
        }
    else:
        return auth_dict
Beispiel #22
0
def resource_delete(next_auth, context, data_dict):
    '''
    :param next_auth:
    :param context:
    :param data_dict:

    '''
    user = context['auth_user_obj']
    resource = get_resource_object(context, data_dict)
    package = resource.package
    if user_owns_package_as_member(user, package):
        return {
            'success': True
        }
    elif user_is_member_of_package_org(user, package):
        return {
            'success': False
        }

    return next_auth(context, data_dict)
Beispiel #23
0
def resource_update(context, data_dict):
    model = context['model']
    user = context.get('user')
    resource = get_resource_object(context, data_dict)

    # check authentication against package
    query = model.Session.query(model.Package)\
        .join(model.ResourceGroup)\
        .join(model.Resource)\
        .filter(model.ResourceGroup.id == resource.resource_group_id)
    pkg = query.first()
    if not pkg:
        raise logic.NotFound(_('No package found for this resource, cannot check auth.'))

    pkg_dict = {'id': pkg.id}
    authorized = package_update(context, pkg_dict).get('success')

    if not authorized:
        return {'success': False, 'msg': _('User %s not authorized to edit resource %s') % (str(user), resource.id)}
    else:
        return {'success': True}
Beispiel #24
0
def resource_show(context, data_dict):
    '''Override ckan's auth function
    '''
    resource_id = data_dict.get('id')
    user = context.get('user')

    if has_user_record_for_resource(resource_id, user):
        if has_user_permission_for_resource(resource_id, user, 'read'):
            return {'success': True}
        return {'success': False}

    resourceObj = get_resource_object(context, data_dict)
    packageObj = get_package_object(context, {'id': resourceObj.package_id})
    if packageObj.private:
        userobj = model.User.get(user)
        if userobj:
            org_ids = userobj.get_group_ids('organization')
            if packageObj.owner_org in org_ids:
                return {'success': True}
            return {'success': False}

    return ckan_package_show(context, {'id': resourceObj.package_id})
Beispiel #25
0
def restricted_resource_show(context, data_dict=None):
    # Ensure user who can edit the package can see the resource
    resource = data_dict.get('resource', context.get('resource', {}))
    if not resource:
        resource = logic_auth.get_resource_object(context, data_dict)
    if type(resource) is not dict:
        resource = resource.as_dict()

    if authz.is_authorized('package_update', context, {
            'id': resource.get('package_id')
    }).get('success'):
        return ({'success': True})

    user_name = logic.restricted_get_username_from_context(context)

    package = data_dict.get('package', {})
    if not package:
        model = context['model']
        package = model.Package.get(resource.get('package_id'))
        package = package.as_dict()

    return (logic.restricted_check_user_resource_access(
        user_name, resource, package))
Beispiel #26
0
def initiatives_resource_show(context, data_dict=None):
    resource = data_dict.get("resource", context.get("resource", {}))
    if not resource:
        resource = logic_auth.get_resource_object(context, data_dict)
    if type(resource) is not dict:
        resource = resource.as_dict()

    # Ensure user who can edit the package can see the resource
    if authz.is_authorized("package_update", context, {
            "id": resource.get("package_id")
    }).get("success"):
        return {"success": True}

    user_name = logic.initiatives_get_username_from_context(context)

    package = data_dict.get("package", {})
    if not package:
        model = context["model"]
        package = model.Package.get(resource.get("package_id"))
        package = package.as_dict()

    return logic.initiatives_check_user_resource_access(
        user_name, resource, package)
Beispiel #27
0
def resource_show(context, data_dict):
    model = context["model"]
    user = context.get("user")
    resource = get_resource_object(context, data_dict)

    # check authentication against package
    query = (
        model.Session.query(model.Package)
        .join(model.ResourceGroup)
        .join(model.Resource)
        .filter(model.ResourceGroup.id == resource.resource_group_id)
    )
    pkg = query.first()
    if not pkg:
        raise logic.NotFound(_("No package found for this resource, cannot check auth."))

    pkg_dict = {"id": pkg.id}
    authorized = package_show(context, pkg_dict).get("success")

    if not authorized:
        return {"success": False, "msg": _("User %s not authorized to read resource %s") % (user, resource.id)}
    else:
        return {"success": True}
Beispiel #28
0
def resource_create(context, data_dict):
    model = context['model']
    user = context.get('user')

    package_id = data_dict.get('package_id')
    if not package_id and data_dict.get('id'):
        # This can happen when auth is deferred, eg from `resource_view_create`
        resource = logic_auth.get_resource_object(context, data_dict)
        package_id = resource.package_id

    if not package_id:
        raise logic.NotFound(_('No dataset id provided, cannot check auth.'))

    # check authentication against package
    pkg = model.Package.get(package_id)
    if not pkg:
        raise logic.NotFound(
            _('No package found for this resource, cannot check auth.'))

    pkg_dict = {'id': pkg.id}
    authorized = authz.is_authorized('package_update', context,
                                     pkg_dict).get('success')

    if not authorized:
        return {
            'success':
            False,
            'msg':
            _('User %s not authorized to create resources on dataset %s') %
            (str(user), package_id)
        }
    else:
        if authz.config.get('ckan.gov_theme.is_back'):
            return {'success': True}
        else:
            return {'success': False}
def resource_view_show(context, data_dict):
    resourceObj = get_resource_object(context, data_dict)
    return resource_show(context, {'id': resourceObj.id})
Beispiel #30
0
def resource_tracker_create(context, data_dict):
    '''Authorization check for creating a log for a resource
    '''
    resource_id = data_dict.get('el')
    resourceObj = get_resource_object(context, {'id': resource_id})
    return auth.resource_show(context, {'id': resourceObj.id})
Beispiel #31
0
def resource_download(context, data_dict):
    '''
    This is a new auth function that specifically controls access to the download
    of a resource file, as opposed to seeing the metadata of a resource (handled
    by `resource_show`

    If this resource is marked as public or private in the custom visibility
    field, the authorization check is deferred to `resource_show` as the standard
    logic applies (we assume that the necessary validators are applied to keep
    `visibility` and `private` fields in sync).

    If this resource is marked as `restricted` then only users belonging to
    the dataset organization can download the file.
    '''

    # Prepare all the parts
    context['model'] = context.get('model') or model
    user = context.get('user')
    resource = get_resource_object(context, data_dict)
    dataset = toolkit.get_action('package_show')({
        'ignore_auth': True
    }, {
        'id': resource.package_id
    })
    visibility = resource.extras.get('visibility')

    # Use default check
    user_id = getattr(context.get('auth_user_obj'), 'id', None)
    is_deposit = dataset.get('type') == 'deposited-dataset'
    if is_deposit:
        is_depositor = dataset.get('creator_user_id') == user_id
        curators = [u['id'] for u in helpers.get_data_curation_users(dataset)]
        is_curator = user_id in curators
    else:
        is_depositor = False
        is_curator = False

    if not user or is_depositor or is_curator or not visibility or visibility != 'restricted':
        try:
            toolkit.check_access('resource_show', context, data_dict)
            return {'success': True}
        except toolkit.NotAuthorized:
            return {'success': False}

    # Restricted visibility (public metadata but private downloads)
    if dataset.get('owner_org'):
        user_orgs = toolkit.get_action('organization_list_for_user')(
            {
                'ignore_auth': True
            }, {
                'id': user
            })
        user_in_owner_org = any(org['id'] == dataset['owner_org']
                                for org in user_orgs)
        if user_in_owner_org:
            return {'success': True}

    # Check if the user is a dataset collaborator
    action = toolkit.get_action('package_collaborator_list_for_user')
    if user and action:
        datasets = action(context, {'id': user})
        return {
            'success': resource.package_id
            in [d['package_id'] for d in datasets]
        }

    return {'success': False}