Example #1
0
def test_fes20_c5_example14():
    """This example restricts the active set of objects to those instances of
    the Person type that are older than 50 years old and live in Toronto. This
    filter expression uses an XPath (as given in W3C XML Path Language)
    expression to reference the complex attributes of the Person type.
    """
    xml_text = """
        <fes:Filter
           xmlns:fes="http://www.opengis.net/fes/2.0"
           xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
           xsi:schemaLocation="http://www.opengis.net/fes/2.0
           http://schemas.opengis.net/filter/2.0/filterAll.xsd">
           <fes:And>
              <fes:PropertyIsGreaterThan>
                 <fes:ValueReference>Person/age</fes:ValueReference>
                 <fes:Literal>50</fes:Literal>
              </fes:PropertyIsGreaterThan>
              <fes:PropertyIsEqualTo>
                 <fes:ValueReference>Person/mailAddress/Address/city</fes:ValueReference>
                 <fes:Literal>Toronto</fes:Literal>
              </fes:PropertyIsEqualTo>
           </fes:And>
        </fes:Filter>
    """.strip()
    result = Filter.from_string(xml_text)
    expected = Filter(predicate=BinaryLogicOperator(
        operands=[
            BinaryComparisonOperator(
                operatorType=BinaryComparisonName.PropertyIsGreaterThan,
                expression=(
                    ValueReference(xpath="Person/age"),
                    Literal(raw_value="50"),
                ),
                matchCase=True,
                matchAction=MatchAction.Any,
            ),
            BinaryComparisonOperator(
                operatorType=BinaryComparisonName.PropertyIsEqualTo,
                expression=(
                    ValueReference(xpath="Person/mailAddress/Address/city"),
                    Literal(raw_value="Toronto"),
                ),
                matchCase=True,
                matchAction=MatchAction.Any,
            ),
        ],
        operatorType=BinaryLogicType.And,
    ))
    assert result == expected, f"result={result!r}"

    # Test SQL generating
    query = result.compile_query()
    assert query == CompiledQuery(lookups=[
        Q(Person__age__gt=50)
        & Q(Person__mailAddress__Address__city__exact="Toronto")
    ]), repr(query)
Example #2
0
def test_fes20_c5_example2():
    """A simple non-spatial filter comparing a property value to a literal.
    In this case, the DEPTH is checked to find instances where it is less than
    30 - possibly to identify areas that need dredging.
    """
    xml_text = """
        <fes:Filter
            xmlns:fes="http://www.opengis.net/fes/2.0"
            xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
            xsi:schemaLocation="http://www.opengis.net/fes/2.0
            http://schemas.opengis.net/filter/2.0/filterAll.xsd">
            <fes:PropertyIsLessThan>
                <fes:ValueReference>DEPTH</fes:ValueReference>
                <fes:Literal>30</fes:Literal>
            </fes:PropertyIsLessThan>
        </fes:Filter>
    """.strip()
    expected = Filter(
        BinaryComparisonOperator(
            BinaryComparisonName.PropertyIsLessThan,
            expression=(ValueReference("DEPTH"), Literal("30")),
        ))
    result = Filter.from_string(xml_text)
    assert result == expected, f"result={result!r}"

    # Test SQL generating
    query = result.compile_query()
    assert query == CompiledQuery(lookups=[Q(DEPTH__lt=30)]), repr(query)
Example #3
0
def test_fes20_c5_example1():
    """A simple non-spatial filter checking to see if SomeProperty is equal to 100."""
    xml_text = """
        <fes:Filter
            xmlns:fes="http://www.opengis.net/fes/2.0"
            xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
            xsi:schemaLocation="http://www.opengis.net/fes/2.0
            http://schemas.opengis.net/filter/2.0/filterAll.xsd">
            <fes:PropertyIsEqualTo>
                <fes:ValueReference>SomeProperty</fes:ValueReference>
                <fes:Literal>100</fes:Literal>
            </fes:PropertyIsEqualTo>
        </fes:Filter>
    """.strip()
    expected = Filter(
        BinaryComparisonOperator(
            BinaryComparisonName.PropertyIsEqualTo,
            expression=(
                ValueReference("SomeProperty"),
                Literal("100"),
            ),
        ))
    result = Filter.from_string(xml_text)
    assert result == expected, f"result={result!r}"

    # Test SQL generating
    query = result.compile_query()
    assert query == CompiledQuery(lookups=[Q(
        SomeProperty__exact=100)]), repr(query)
Example #4
0
def test_fes10_no_namespace(leading_whitespace):
    """Test that omitting a namespace still parses the object."""
    xml_text = """
        <Filter>
            <PropertyIsEqualTo>
                <ValueReference>SomeProperty</ValueReference>
                <Literal>100</Literal>
            </PropertyIsEqualTo>
        </Filter>
    """

    if leading_whitespace:
        xml_text = xml_text.strip()

    expected = Filter(predicate=BinaryComparisonOperator(
        operatorType=BinaryComparisonName.PropertyIsEqualTo,
        expression=(
            ValueReference(xpath="SomeProperty"),
            Literal(raw_value="100"),
        ),
        matchCase=True,
        matchAction=MatchAction.Any,
    ))
    result = Filter.from_string(xml_text)
    assert result == expected, f"result={result!r}"
Example #5
0
def test_fes20_c5_example7():
    """This example assumes that the server advertises support for a function
    called "Add" in its filter capabilities document. The example encodes a
    filter that includes an arithmetic expression. This filter is equivalent
    to the expression PROPA = PROPB + 100.
    """
    @function_registry.register(
        name="Add",
        arguments=dict(value1=XsdTypes.double, value2=XsdTypes.double),
        returns=XsdTypes.double,
    )
    def fes_add(value1: F, value2: str):
        # value1 is already an F value (thanks to ValueReference)
        return value1 + value2

    xml_text = """
        <fes:Filter
        xmlns:fes="http://www.opengis.net/fes/2.0"
        xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
        xsi:schemaLocation="http://www.opengis.net/fes/2.0
        http://schemas.opengis.net/filter/2.0/filterAll.xsd">
            <fes:PropertyIsEqualTo>
                <fes:ValueReference>PROPA</fes:ValueReference>
                <fes:Function name="Add">
                    <fes:ValueReference>PROPB</fes:ValueReference>
                    <fes:Literal>100</fes:Literal>
                </fes:Function>
            </fes:PropertyIsEqualTo>
        </fes:Filter>
    """.strip()
    expected = Filter(predicate=BinaryComparisonOperator(
        operatorType=BinaryComparisonName.PropertyIsEqualTo,
        expression=(
            ValueReference(xpath="PROPA"),
            Function(
                name="Add",
                arguments=[
                    ValueReference(xpath="PROPB"),
                    Literal(raw_value="100")
                ],
            ),
        ),
        matchCase=True,
        matchAction=MatchAction.Any,
    ))
    result = Filter.from_string(xml_text)
    assert result == expected, f"result={result!r}"

    # Test SQL generating
    # Testing against repr() because CombinedExpression / Value doesn't do __eq__ testing.
    query = result.compile_query()
    assert repr(query) == repr(
        CompiledQuery(lookups=[Q(PROPA__exact=F("PROPB") + 100)])), repr(query)
Example #6
0
def test_fes10_add_sub():
    """A simple non-spatial filter checking to see if SomeProperty is equal to 100."""
    xml_text = """
        <fes:Filter
            xmlns:fes="http://www.opengis.net/fes/2.0"
            xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
            xsi:schemaLocation="http://www.opengis.net/fes/2.0
            http://schemas.opengis.net/filter/2.0/filterAll.xsd">
            <fes:PropertyIsEqualTo>
                <fes:ValueReference>SomeProperty</fes:ValueReference>
                <fes:Add>
                    <fes:Sub>
                        <fes:Literal>100</fes:Literal>
                        <fes:Literal>50</fes:Literal>
                    </fes:Sub>
                    <fes:Literal>200</fes:Literal>
                </fes:Add>
            </fes:PropertyIsEqualTo>
        </fes:Filter>
    """.strip()
    expected = Filter(predicate=BinaryComparisonOperator(
        operatorType=BinaryComparisonName.PropertyIsEqualTo,
        expression=(
            ValueReference(xpath="SomeProperty"),
            BinaryOperator(
                _operatorType=BinaryOperatorType.Add,
                expression=(
                    BinaryOperator(
                        _operatorType=BinaryOperatorType.Sub,
                        expression=(
                            Literal(raw_value="100"),
                            Literal(raw_value="50"),
                        ),
                    ),
                    Literal(raw_value="200"),
                ),
            ),
        ),
        matchCase=True,
        matchAction=MatchAction.Any,
    ))
    result = Filter.from_string(xml_text)
    assert result == expected, f"result={result!r}"

    # Test SQL generating
    query = result.compile_query()
    integer_field = models.IntegerField()
    assert query == CompiledQuery(lookups=[
        Q(SomeProperty__exact=(Value(100, output_field=integer_field) -
                               Value(50, output_field=integer_field) +
                               Value(200, output_field=integer_field)))
    ]), repr(query)
Example #7
0
def test_fes20_c5_example6():
    """The following filter includes the encoding of a function. This filter
    identifies all features where the sine() of the property named
    DISPERSION_ANGLE is 1.
    """
    @function_registry.register(
        name="SIN",
        arguments=dict(value1="xsd:double"),
        returns="xsd:double",
    )
    def fes_sin(value1):
        return Sin(value1)

    xml_text = """
        <fes:Filter
        xmlns:fes="http://www.opengis.net/fes/2.0"
        xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
        xsi:schemaLocation="http://www.opengis.net/fes/2.0
        http://schemas.opengis.net/filter/2.0/filterAll.xsd">
            <fes:PropertyIsEqualTo>
                <fes:Function name="SIN">
                    <fes:ValueReference>DISPERSION_ANGLE</fes:ValueReference>
                </fes:Function>
                <fes:Literal>1</fes:Literal>
            </fes:PropertyIsEqualTo>
        </fes:Filter>
    """.strip()
    expected = Filter(predicate=BinaryComparisonOperator(
        operatorType=BinaryComparisonName.PropertyIsEqualTo,
        expression=(
            Function(
                name="SIN",
                arguments=[ValueReference(xpath="DISPERSION_ANGLE")],
            ),
            Literal(raw_value="1"),
        ),
        matchCase=True,
        matchAction=MatchAction.Any,
    ))
    result = Filter.from_string(xml_text)
    assert result == expected, f"result={result!r}"

    # Test SQL generating
    query = result.compile_query()
    assert query == CompiledQuery(
        annotations={"a1": Sin(F("DISPERSION_ANGLE"))},
        lookups=[Q(a1__exact=1)]), repr(query)
Example #8
0
def test_fes20_c5_example12():
    """In this example, a more complex scalar predicate is encoded using the
    logical operators AND and OR. The example is equivalent to the expression:

    ((FIELD1=10 OR FIELD1=20) AND (STATUS="VALID"))
    """
    xml_text = """
        <fes:Filter
           xmlns:fes="http://www.opengis.net/fes/2.0"
           xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
           xsi:schemaLocation="http://www.opengis.net/fes/2.0
           http://schemas.opengis.net/filter/2.0/filterAll.xsd">
           <fes:And>
              <fes:Or>
                 <fes:PropertyIsEqualTo>
                    <fes:ValueReference>FIELD1</fes:ValueReference>
                    <fes:Literal>10</fes:Literal>
                 </fes:PropertyIsEqualTo>
                 <fes:PropertyIsEqualTo>
                    <fes:ValueReference>FIELD1</fes:ValueReference>
                    <fes:Literal>20</fes:Literal>
                 </fes:PropertyIsEqualTo>
              </fes:Or>
              <fes:PropertyIsEqualTo>
                 <fes:ValueReference>STATUS</fes:ValueReference>
                 <fes:Literal>VALID</fes:Literal>
              </fes:PropertyIsEqualTo>
           </fes:And>
        </fes:Filter>
    """.strip()
    expected = Filter(predicate=BinaryLogicOperator(
        operands=[
            BinaryLogicOperator(
                operands=[
                    BinaryComparisonOperator(
                        operatorType=BinaryComparisonName.PropertyIsEqualTo,
                        expression=(
                            ValueReference(xpath="FIELD1"),
                            Literal(raw_value="10"),
                        ),
                        matchCase=True,
                        matchAction=MatchAction.Any,
                    ),
                    BinaryComparisonOperator(
                        operatorType=BinaryComparisonName.PropertyIsEqualTo,
                        expression=(
                            ValueReference(xpath="FIELD1"),
                            Literal(raw_value="20"),
                        ),
                        matchCase=True,
                        matchAction=MatchAction.Any,
                    ),
                ],
                operatorType=BinaryLogicType.Or,
            ),
            BinaryComparisonOperator(
                operatorType=BinaryComparisonName.PropertyIsEqualTo,
                expression=(
                    ValueReference(xpath="STATUS"),
                    Literal(raw_value="VALID"),
                ),
                matchCase=True,
                matchAction=MatchAction.Any,
            ),
        ],
        operatorType=BinaryLogicType.And,
    ))
    result = Filter.from_string(xml_text)
    assert result == expected, f"result={result!r}"

    # Test SQL generating
    query = result.compile_query()
    assert query == CompiledQuery(
        lookups=[(Q(FIELD1__exact=10) | Q(FIELD1__exact=20))
                 & Q(STATUS__exact="VALID")]), repr(query)
Example #9
0
def test_fes20_c5_example4():
    """In this example, Examples 2 and 3 are combined with the logical
    operator AND. The predicate is thus interpreted as seeking all features
    that interact with the specified bounding box and have a DEPTH value of
    less than 30 m."""
    xml_text = """
        <?xml version="1.0"?>
        <fes:Filter
             xmlns:fes="http://www.opengis.net/fes/2.0"
             xmlns:gml="http://www.opengis.net/gml/3.2"
             xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
             xsi:schemaLocation="http://www.opengis.net/fes/2.0
             http://schemas.opengis.net/filter/2.0/filterAll.xsd
             http://www.opengis.net/gml
             http://schemas.opengis.net/gml/2.1.2/geometry.xsd">
            <fes:And>
                <fes:PropertyIsLessThan>
                    <fes:ValueReference>DEPTH</fes:ValueReference>
                    <fes:Literal>30</fes:Literal>
                </fes:PropertyIsLessThan>
                <fes:Not>
                    <fes:Disjoint>
                        <fes:ValueReference>Geometry</fes:ValueReference>
                        <gml:Envelope srsName="http://www.opengis.net/def/crs/epsg/0/4326">
                            <gml:lowerCorner>13.0983 31.5899</gml:lowerCorner>
                            <gml:upperCorner>35.5472 42.8143</gml:upperCorner>
                        </gml:Envelope>
                    </fes:Disjoint>
                </fes:Not>
            </fes:And>
        </fes:Filter>
    """.strip()
    expected = Filter(predicate=BinaryLogicOperator(
        operands=[
            BinaryComparisonOperator(
                operatorType=BinaryComparisonName.PropertyIsLessThan,
                expression=(
                    ValueReference(xpath="DEPTH"),
                    Literal(raw_value="30"),
                ),
                matchCase=True,
                matchAction=MatchAction.Any,
            ),
            UnaryLogicOperator(
                operands=BinarySpatialOperator(
                    operatorType=SpatialOperatorName.Disjoint,
                    operand1=ValueReference(xpath="Geometry"),
                    operand2=GEOSGMLGeometry(
                        srs=WGS84,
                        geos_data=GEOSGeometry(
                            "POLYGON ((13.0983 31.5899, 35.5472 31.5899"
                            ", 35.5472 42.8143, 13.0983 42.8143, 13.0983 31.5899))",
                            srid=4326,
                        ),
                    ),
                ),
                operatorType=UnaryLogicType.Not,
            ),
        ],
        operatorType=BinaryLogicType.And,
    ))
    result = Filter.from_string(xml_text)
    assert result == expected, f"result={result!r}"

    # Test SQL generating
    query = result.compile_query()
    assert query == CompiledQuery(lookups=[
        Q(DEPTH__lt=30)
        & ~Q(Geometry__disjoint=GEOSGeometry(
            "POLYGON ((13.0983 31.5899, 35.5472 31.5899"
            ", 35.5472 42.8143, 13.0983 42.8143, 13.0983 31.5899))",
            srid=4326,
        ))
    ]), repr(query)