예제 #1
0
def _filter_children(parent_path, **kwargs):
    parent_node = get_node(parent_path)

    content_type = kwargs.has_key('content_type') and kwargs.pop('content_type')
    if content_type:
        return _filter_children_by_content_type(parent_node, content_type, **kwargs)

    content_types_exclude = kwargs['content_types_exclude']

    if not kwargs['content_filter_kwargs']:
        # not searching by content type and content filter not set
        # return all children
        children_nodes_qs = get_children(parent_node=parent_node)
        if kwargs['offline_filter']:
            # filter out offline recs
            children_nodes_qs = children_nodes_qs.filter(offline=False)
        if kwargs.has_key('active'):
            children_nodes_qs = children_nodes_qs.filter(active=kwargs['active'])
        return children_nodes_qs.exclude(content_type__in=content_types_exclude).order_by('content_type', 'seq_num')

    logger.warning('expensive filter across multiple content types ("ct" not specified), content filter: %s' % kwargs['content_filter_kwargs'])

    # limit search to possible children content types only
    # by inspecting children constraints
    children_nodes = []
    CHILDREN_CONSTRAINT = []
    if parent_node:
        parent_content_type = parent_node.content_type
        parent_model_class = parent_content_type.model_class()
        if hasattr(parent_model_class, 'CHILDREN_CONSTRAINT'):
            CHILDREN_CONSTRAINT = parent_model_class.CHILDREN_CONSTRAINT
    else:
        # searching children at site root
        CHILDREN_CONSTRAINT = settings.SITEROOT_CHILDREN_CONSTRAINT

    for cc in CHILDREN_CONSTRAINT:
        #XXX TEST THIS
        constraint_content_types = []

        model_cls = get_model(*cc['content_type_name'].split('.'))
        if issubclass(model_cls, TreeContent):
            constraint_content_types.append(get_content_type(*cc['content_type_name'].split('.')))
        else:
            # could be a generic parent class with concrete TreeContent subclasses
            for sc in model_cls.__subclasses__():
                if issubclass(sc, TreeContent):
                    sc_ct = get_content_type(sc._meta.app_label, sc._meta.object_name.lower())
                    constraint_content_types.append(sc_ct)

        for ct in constraint_content_types:
            if ct in content_types_exclude:
                # auth filter - exclude from results
                continue

            for n in _filter_children_by_content_type(parent_node, ct, **kwargs):
                logger.debug("found node - %s" % n.absolute_path)
                children_nodes.append(n)

    return children_nodes
예제 #2
0
def is_authorization_required(action, content_type_name='', content_type=None):
    """Is authorization required to perform `action` on objects of the content type.

    Valid action arg values: 'add', 'change', 'delete', 'read'

    """

    if not action in ['add','change','delete','read']:
        logger.error('invalid action: "%s"' % action)
        return True 
    if not content_type:
        if content_type_name:
            content_type = get_content_type(*content_type_name.split('.'))
        if not content_type:
            logger.error('invalid content type name: "%s"' % content_type_name)
            return True 

    perm_codename = action + '_' + content_type.model
    try:
        perm = Permission.objects.get(content_type=content_type, codename=perm_codename)
        # yes, need to authorize to perform `action` 
        logger.debug('Permissions "%s" for ct "%s" found. Action auth is required.' % (perm_codename, content_type))
        return True
    except Permission.DoesNotExist:
        # no permission for the content type
        return False
예제 #3
0
def create(request, tree_context_path, *args, **kwargs):
    content_type_name = request.GET.get('ct') or request.POST.get('ct')
    if not content_type_name:
        #XXX invalid request??
        logger.error('ct not set')
        raise Http404

    content_type = get_content_type(*content_type_name.split('.'))
    if not content_type:
        logger.error('invalid ct: "%s"' % content_type_name)
        raise Http404

    # when creating/adding new content, context is parent of object being added
    if request.tree_context.path == '/':
        parent_object = None
    else:
        parent_object = request.tree_context.node.content_object

    create_view_cls = query_component('CreateView', (parent_object, content_type), name=content_type_name)
    if not create_view_cls:
        # generic view     
        create_view_cls = GenericCreateView

    logger.debug("Create View class: %s" % create_view_cls)

    #hacky, needed for portlets (portlet context_processors.py)
    request.view_component = create_view_cls

    view_func = create_view_cls.as_view(parent_object=parent_object, content_type=content_type, content_type_name=content_type_name, **kwargs)
    return view_func(request)
예제 #4
0
파일: utils.py 프로젝트: stana/django-ztree
def is_authorization_required(action, content_type_name='', content_type=None):
    """Is authorization required to perform `action` on objects of the content type.

    Valid action arg values: 'add', 'change', 'delete', 'read'

    """

    if not action in ['add', 'change', 'delete', 'read']:
        logger.error('invalid action: "%s"' % action)
        return True
    if not content_type:
        if content_type_name:
            content_type = get_content_type(*content_type_name.split('.'))
        if not content_type:
            logger.error('invalid content type name: "%s"' % content_type_name)
            return True

    perm_codename = action + '_' + content_type.model
    try:
        perm = Permission.objects.get(content_type=content_type,
                                      codename=perm_codename)
        # yes, need to authorize to perform `action`
        logger.debug(
            'Permissions "%s" for ct "%s" found. Action auth is required.' %
            (perm_codename, content_type))
        return True
    except Permission.DoesNotExist:
        # no permission for the content type
        return False
예제 #5
0
def _preprocess_kwargs(kwargs):
    content_type = None
    if kwargs.has_key('ct'):
        content_type_name = kwargs.pop('ct')
        content_type = get_content_type(*content_type_name.split('.'))
        if not content_type:
            raise TreeSearchError('invalid content type: "%s"' % content_type_name)

    tree_context = kwargs.has_key('tree_context') and kwargs.pop('tree_context')
    if tree_context:
        # search within tree context checking authenticated/anonymous user
        # and user permissions

        # default - anonymous user cannot read content requiring read permission
        # nor offline content
        content_types_exclude = settings.READ_PERMISSION_CONTENT_TYPES
        offline_filter = True

        if tree_context.authenticated_user:
            # we have authenticated user
            if tree_context.authenticated_user.is_superuser:
                # can read everything
                content_types_exclude = []
                # can see offline content
                offline_filter = False
            else:
                if tree_context.user_permissions:
                    # user has perms at node, so not outside their branch
                    # auth user can see offline content inside their branch
                    offline_filter = False

                    # get user's read permissions
                    read_content_types = []
                    for p in tree_context.user_permissions:
                        if 'read_' in p.codename:
                            read_content_types.append(p.content_type)

                    # allow user to read content which she has read permissions for
                    content_types_exclude = list(set(settings.READ_PERMISSION_CONTENT_TYPES) - set(read_content_types))
    else:
        # search - no auth
        content_types_exclude = []
        offline_filter = False 

    # clean content filter kwargs
    content_filter_kwargs = kwargs.copy()
    if content_filter_kwargs.has_key('include_self'):
        # lookup search specific param - remove from content filter
        del(content_filter_kwargs['include_self'])
    if content_filter_kwargs.has_key('active'):
        # searching only 'active' nodes - remove from content filter 
        del(content_filter_kwargs['active'])
    kwargs['content_filter_kwargs'] = content_filter_kwargs

    kwargs['content_type'] = content_type
    kwargs['content_types_exclude'] = content_types_exclude 
    kwargs['offline_filter'] = offline_filter
예제 #6
0
        def authorize_wrapper(request, tree_context_path='/'):
            logger.debug('request path ' + request.path)
            if hasattr(settings, 'TREE_AUTH_OFF') and settings.TREE_AUTH_OFF:
                logger.warning(
                    'TREE_AUTH_OFF set, not performing request auth')
                return func(request, tree_context_path)

            if hasattr(request, 'user'):
                # have user object - front end with django auth enabled
                if request.user.is_authenticated(
                ) and request.user.is_active and request.user.is_superuser:
                    logger.debug("authorized superuser - running %s" %
                                 str(func))
                    return func(request, tree_context_path)

            if not self.action:
                if request.path.endswith('create'):
                    self.action = 'create'
                elif request.path.endswith('update'):
                    self.action = 'update'
                elif request.path.endswith('delete'):
                    self.action = 'delete'

            if self.action == 'create':
                create_content_type_name = request.GET.get(
                    'ct') or request.POST.get('ct')
                create_content_type = get_content_type(
                    *create_content_type_name.split('.'))
                if not create_content_type:
                    logger.error('could not set content type')
                    raise Http400  #XXX test
                if is_authorized('add',
                                 request.tree_context,
                                 content_type=create_content_type):
                    return func(request, tree_context_path)

            elif self.action == 'update':
                if is_authorized('change', request.tree_context):
                    return func(request, tree_context_path)

            elif self.action == 'delete':
                if is_authorized('delete', request.tree_context):
                    return func(request, tree_context_path)

            else:
                if is_authorized('read', request.tree_context):
                    return func(request, tree_context_path)

            # Unauthorized
            raise Http401  #XXX test this
예제 #7
0
        def authorize_wrapper(request, tree_context_path='/'):
            logger.debug('request path ' + request.path)
            if hasattr(settings, 'TREE_AUTH_OFF') and settings.TREE_AUTH_OFF:
                logger.warning('TREE_AUTH_OFF set, not performing request auth')
                return func(request, tree_context_path)

            if hasattr(request, 'user'):
                # have user object - front end with django auth enabled
                if request.user.is_authenticated() and request.user.is_active and request.user.is_superuser:
                    logger.debug("authorized superuser - running %s" % str(func))
                    return func(request, tree_context_path)

            if not self.action:
                if request.path.endswith('create'):
                    self.action = 'create'
                elif request.path.endswith('update'):
                    self.action = 'update'
                elif request.path.endswith('delete'):
                    self.action = 'delete'

            if self.action == 'create':
                create_content_type_name = request.GET.get('ct') or request.POST.get('ct')
                create_content_type = get_content_type(*create_content_type_name.split('.'))
                if not create_content_type:
                    logger.error('could not set content type')
                    raise Http400 #XXX test 
                if is_authorized('add', request.tree_context,
                                 content_type=create_content_type):
                    return func(request, tree_context_path)

            elif self.action == 'update':
                if is_authorized('change', request.tree_context):
                    return func(request, tree_context_path)

            elif self.action == 'delete':
                if is_authorized('delete', request.tree_context):
                    return func(request, tree_context_path)

            else:
                if is_authorized('read', request.tree_context):
                    return func(request, tree_context_path)

            # Unauthorized
            raise Http401 #XXX test this
예제 #8
0
def _preprocess_kwargs(kwargs):
    content_type = None
    if kwargs.has_key('ct'):
        content_type_name = kwargs.pop('ct')
        content_type = get_content_type(*content_type_name.split('.'))
        if not content_type:
            raise TreeSearchError('invalid content type: "%s"' %
                                  content_type_name)

    tree_context = kwargs.has_key('tree_context') and kwargs.pop(
        'tree_context')
    if tree_context:
        # search within tree context checking authenticated/anonymous user
        # and user permissions

        # default - anonymous user cannot read content requiring read permission
        # nor offline content
        content_types_exclude = settings.READ_PERMISSION_CONTENT_TYPES
        offline_filter = True

        if tree_context.authenticated_user:
            # we have authenticated user
            if tree_context.authenticated_user.is_superuser:
                # can read everything
                content_types_exclude = []
                # can see offline content
                offline_filter = False
            else:
                if tree_context.user_permissions:
                    # user has perms at node, so not outside their branch
                    # auth user can see offline content inside their branch
                    offline_filter = False

                    # get user's read permissions
                    read_content_types = []
                    for p in tree_context.user_permissions:
                        if 'read_' in p.codename:
                            read_content_types.append(p.content_type)

                    # allow user to read content which she has read permissions for
                    content_types_exclude = list(
                        set(settings.READ_PERMISSION_CONTENT_TYPES) -
                        set(read_content_types))
    else:
        # search - no auth
        content_types_exclude = []
        offline_filter = False

    # clean content filter kwargs
    content_filter_kwargs = kwargs.copy()
    if content_filter_kwargs.has_key('include_self'):
        # lookup search specific param - remove from content filter
        del (content_filter_kwargs['include_self'])
    if content_filter_kwargs.has_key('active'):
        # searching only 'active' nodes - remove from content filter
        del (content_filter_kwargs['active'])
    kwargs['content_filter_kwargs'] = content_filter_kwargs

    kwargs['content_type'] = content_type
    kwargs['content_types_exclude'] = content_types_exclude
    kwargs['offline_filter'] = offline_filter
예제 #9
0
def _filter_children(parent_path, **kwargs):
    parent_node = get_node(parent_path)

    content_type = kwargs.has_key('content_type') and kwargs.pop(
        'content_type')
    if content_type:
        return _filter_children_by_content_type(parent_node, content_type,
                                                **kwargs)

    content_types_exclude = kwargs['content_types_exclude']

    if not kwargs['content_filter_kwargs']:
        # not searching by content type and content filter not set
        # return all children
        children_nodes_qs = get_children(parent_node=parent_node)
        if kwargs['offline_filter']:
            # filter out offline recs
            children_nodes_qs = children_nodes_qs.filter(offline=False)
        if kwargs.has_key('active'):
            children_nodes_qs = children_nodes_qs.filter(
                active=kwargs['active'])
        return children_nodes_qs.exclude(
            content_type__in=content_types_exclude).order_by(
                'content_type', 'seq_num')

    logger.warning(
        'expensive filter across multiple content types ("ct" not specified), content filter: %s'
        % kwargs['content_filter_kwargs'])

    # limit search to possible children content types only
    # by inspecting children constraints
    children_nodes = []
    CHILDREN_CONSTRAINT = []
    if parent_node:
        parent_content_type = parent_node.content_type
        parent_model_class = parent_content_type.model_class()
        if hasattr(parent_model_class, 'CHILDREN_CONSTRAINT'):
            CHILDREN_CONSTRAINT = parent_model_class.CHILDREN_CONSTRAINT
    else:
        # searching children at site root
        CHILDREN_CONSTRAINT = settings.SITEROOT_CHILDREN_CONSTRAINT

    for cc in CHILDREN_CONSTRAINT:
        #XXX TEST THIS
        constraint_content_types = []

        model_cls = get_model(*cc['content_type_name'].split('.'))
        if issubclass(model_cls, TreeContent):
            constraint_content_types.append(
                get_content_type(*cc['content_type_name'].split('.')))
        else:
            # could be a generic parent class with concrete TreeContent subclasses
            for sc in model_cls.__subclasses__():
                if issubclass(sc, TreeContent):
                    sc_ct = get_content_type(sc._meta.app_label,
                                             sc._meta.object_name.lower())
                    constraint_content_types.append(sc_ct)

        for ct in constraint_content_types:
            if ct in content_types_exclude:
                # auth filter - exclude from results
                continue

            for n in _filter_children_by_content_type(parent_node, ct,
                                                      **kwargs):
                logger.debug("found node - %s" % n.absolute_path)
                children_nodes.append(n)

    return children_nodes