Example #1
0
    def get_condition(self, expression: Expression,
                      remainder: List[str]) -> Any:
        if len(remainder) > 1:
            raise FieldNotQueryableException(
                f"Attribute doesn't have subfields: {'.'.join(remainder[1:])}")

        if remainder:
            attribute_key = remainder[0]
        else:
            raise UnsupportedGrammarException(
                "Missing attribute key (meta.<key>:)")

        attribute_definition = AttributeDefinition.query_for_read(
            key=attribute_key, include_hidden=True).first()

        if attribute_definition is None:
            raise ObjectNotFoundException(
                f"No such attribute: {attribute_key}")

        if (attribute_definition.hidden and expression.has_wildcard()
                and not g.auth_user.has_rights(
                    Capabilities.reading_all_attributes)):
            raise FieldNotQueryableException(
                "Wildcards are not allowed for hidden attributes")

        value = get_term_value(expression)
        attribute_value = Attribute.value[()].astext
        if expression.has_wildcard():
            value_condition = attribute_value.like(value)
        else:
            value_condition = attribute_value == value

        return self.column.any(
            and_(Attribute.key == attribute_key, value_condition))
Example #2
0
    def get(self):
        """
        ---
        summary: Get list of attribute keys
        description: |
            Returns list of attribute key definitions.
        security:
            - bearerAuth: []
        tags:
            - attribute
        parameters:
            - in: query
              name: access
              schema:
                type: string
                enum: [read, set, manage]
                default: read
              description: Type of desired access
        responses:
            200:
                description: List of attribute key definitions
                content:
                  application/json:
                    schema: AttributeDefinitionListResponseSchema
            400:
                description: When used unknown access type
            403:
                description: |
                    When requested `manage` access
                    but user doesn't have 'manage_users' capability
            503:
                description: |
                    Request canceled due to database statement timeout.
        """
        schema = AttributeDefinitionListRequestSchema()
        obj = load_schema(request.args, schema)
        access = obj["access"]

        if access == "read":
            attribute_definitions = AttributeDefinition.query_for_read()
        elif access == "set":
            attribute_definitions = AttributeDefinition.query_for_set()
        elif access == "manage":
            if not g.auth_user.has_rights(Capabilities.manage_users):
                raise Forbidden("You are not permitted to manage attributes")
            attribute_definitions = db.session.query(AttributeDefinition)
        else:
            raise BadRequest(f"Unknown desired access type '{access}'")

        attribute_definitions = attribute_definitions.order_by(
            AttributeDefinition.key
        ).all()
        schema = AttributeDefinitionListResponseSchema()
        return schema.dump({"attribute_definitions": attribute_definitions})
Example #3
0
    def get(self, access):
        """
        ---
        summary: Get list of attribute keys
        description: |
            Returns list of attribute keys which currently authenticated user
            can read or set.
        security:
            - bearerAuth: []
        tags:
            - deprecated
        parameters:
            - in: path
              name: access
              schema:
                type: string
                enum: [read, set]
              description: Type of desired access
        responses:
            200:
                description: List of attribute keys and definitions
                content:
                  application/json:
                    schema: MetakeyDefinitionListResponseSchema
            400:
                description: When used unknown access type (other than read or set)
            503:
                description: |
                    Request canceled due to database statement timeout.
        """
        if access == "read":
            metakeys = AttributeDefinition.query_for_read()
        elif access == "set":
            metakeys = AttributeDefinition.query_for_set()
        else:
            raise BadRequest(f"Unknown desired access type '{access}'")

        metakeys = metakeys.order_by(AttributeDefinition.key).all()
        schema = MetakeyDefinitionListResponseSchema()
        return schema.dump({"metakeys": metakeys})
Example #4
0
    def get_condition(self, expression: Expression,
                      remainder: List[str]) -> Any:
        if remainder:
            attribute_key = remainder[0]
        else:
            raise UnsupportedGrammarException(
                "Missing attribute key (attribute.<key>:)")

        attribute_definition = AttributeDefinition.query_for_read(
            key=attribute_key, include_hidden=True).first()

        if attribute_definition is None:
            raise ObjectNotFoundException(
                f"No such attribute: {attribute_key}")

        if (attribute_definition.hidden and expression.has_wildcard()
                and not g.auth_user.has_rights(
                    Capabilities.reading_all_attributes)):
            raise FieldNotQueryableException(
                "Wildcards are not allowed for hidden attributes")

        value = get_term_value(expression)
        json_path = make_jsonpath(remainder[1:])
        # Make aliased function call
        json_elements = func.jsonb_path_query(Attribute.value,
                                              json_path).alias("json_element")
        # Use #>>'{}' to extract value as text
        json_element = column("json_element").operate(JSONPATH_ASTEXT,
                                                      "{}",
                                                      result_type=Text)
        if expression.has_wildcard():
            condition = json_element.like(value)
        else:
            condition = json_element == value
        value_condition = exists(
            select([1]).select_from(json_elements).where(condition))
        return self.column.any(
            and_(Attribute.key == attribute_key, value_condition))