예제 #1
0
def test_entity(component_validator):
    """Test that entity can be marshaled and parsed back.

    1. Create an entity.
    2. Create JSON parser and marshaler.
    3. Marshal the entity.
    4. Parse the data.
    5. Check that parsed entity has the same data as the original one.
    """
    entity = Entity(
        classes=("entity class 1", "entity class 2"),
        properties={
            "entity property 1": 1,
            "entity property 2": [1, 2]
        },
        entities=(
            EmbeddedLink(target="/embedded/link/target",
                         relations=["relation"]),
            EmbeddedRepresentation(relations=["relation"]),
        ),
        links=[Link(target="/link/target", relations=["relation"])],
        actions=[Action(target="/action/target", name="entity action")],
        title="entity title",
    )

    entity_data = JSONMarshaler().marshal_entity(entity)
    actual_entity = JSONParser().parse_entity(entity_data)

    component_validator.validate_entity(actual_entity, entity)
예제 #2
0
def test_parse(component_validator):
    """Test that data of embedded link is properly parsed.

    1. Create an embedded link.
    2. Create an embedded link parser.
    3. Replace parser methods so that they return predefined data.
    4. Parse the embedded link.
    5. Check the parsed data.
    """
    embedded_link = EmbeddedLink(
        relations=("parsed relation 1", "parsed relation 2"),
        classes=("parsed class 1", "parsed class 2"),
        title="parsed title",
        target="/parsed/target",
        target_media_type="application/parsed+media+type",
        )

    parser = EmbeddedLinkParser(data={})
    parser.parse_relations = lambda: embedded_link.relations
    parser.parse_classes = lambda: embedded_link.classes
    parser.parse_target = lambda: embedded_link.target
    parser.parse_title = lambda: embedded_link.title
    parser.parse_target_media_type = lambda: embedded_link.target_media_type

    actual_embedded_link = parser.parse()
    component_validator.validate_embedded_link(actual_embedded_link, embedded_link)
예제 #3
0
def test_embedded_representation(component_validator):
    """Test that embedded representation can be marshaled and parsed back.

    1. Create an embedded representation.
    2. Create JSON parser and marshaler.
    3. Marshal the embedded representation.
    4. Parse the data.
    5. Check that parsed embedded representation has the same data as the original one.
    """
    representation = EmbeddedRepresentation(
        relations=["representation relation 1", "representation relation 2"],
        classes=("representation class 1", "representation class 2"),
        properties={
            "representation property 1": 1,
            "representation property 2": [1, 2]
        },
        entities=(
            EmbeddedLink(target="/embedded/link/target",
                         relations=["relation"]),
            EmbeddedRepresentation(relations=["relation"]),
        ),
        links=[Link(target="/link/target", relations=["relation"])],
        actions=[
            Action(target="/action/target", name="representation action")
        ],
        title="representation title",
    )

    representation_data = JSONMarshaler().marshal_embedded_representation(
        representation)
    actual_representation = JSONParser().parse_embedded_representation(
        representation_data)

    component_validator.validate_embedded_representation(
        actual_representation, representation)
예제 #4
0
    def parse(self):
        """Parse the embedded link.

        :returns: :class:`EmbeddedLink <lila.core.link.Link>`.
        :raises: :class:ValueError.
        """
        logger = logging.getLogger(__name__)
        logger.debug("Try to parse an embedded link")

        embedded_link_relations = self.parse_relations()
        embedded_link_classes = self.parse_classes()
        embedded_link_target = self.parse_target()
        embedded_link_title = self.parse_title()
        embedded_link_target_media_type = self.parse_target_media_type()

        try:
            embedded_link = EmbeddedLink(
                relations=embedded_link_relations,
                classes=embedded_link_classes,
                target=embedded_link_target,
                title=embedded_link_title,
                target_media_type=embedded_link_target_media_type,
            )
        except Exception as error:
            logger.error(
                "Failed to create an embedded link with provided data")
            raise ValueError(
                "Failed to create an embedded link with provided data"
            ) from error
        else:
            logger.info("Successfully parsed an embedded link")

        return embedded_link
예제 #5
0
def test_parse(component_validator):
    """Test that entity data is properly parsed.

    1. Create an entity.
    2. Create an entity parser.
    3. Replace parser methods so that they return predefined data.
    4. Parse the entity.
    5. Check the entity data.
    """
    entity = Entity(
        classes=("parsed class 1", "parsed class 2"),
        properties={
            "property 1": 1,
            "property 2": [1, 2]
        },
        entities=(
            EmbeddedLink(target="/embedded/link/target",
                         relations=["relation"]),
            EmbeddedRepresentation(relations=["relation"]),
        ),
        links=[Link(target="/link/target", relations=["relation"])],
        actions=[Action(target="/action/target", name="action")],
        title="parsed title",
    )

    parser = EntityParser(data={}, parser=JSONParser())
    parser.parse_classes = lambda: entity.classes
    parser.parse_properties = lambda: entity.properties
    parser.parse_entities = lambda: entity.entities
    parser.parse_links = lambda: entity.links
    parser.parse_actions = lambda: entity.actions
    parser.parse_title = lambda: entity.title

    actual_entity = parser.parse()
    component_validator.validate_entity(actual_entity, entity)
예제 #6
0
def test_default_classes():
    """Check default classes of an embedded link.

    1. Create an embedded link without specifying classes.
    2. Check classes of the link.
    """
    link = EmbeddedLink(relations=DEFAULT_RELATIONS, target="#")
    assert link.classes == (), "Wrong classes"
예제 #7
0
def test_invalid_classes():
    """Check that ValueError is raised if invalid classes are passed.

    1. Try to create an embedded link with non-iterable classes.
    2. Check that ValueError is raised.
    """
    with pytest.raises(ValueError):
        EmbeddedLink(relations=DEFAULT_RELATIONS, target="#", classes=1)
예제 #8
0
def test_default_target_media_type():
    """Check default target media type of an embedded link.

    1. Create an embedded link without specifying media type of the target.
    2. Check the media type of the target of the link.
    """
    link = EmbeddedLink(relations=DEFAULT_RELATIONS, target="#")
    assert link.target_media_type is None, "Wrong media type"
예제 #9
0
def test_default_title():
    """Check default title of an embedded link.

    1. Create an embedded link without specifying a title.
    2. Check the title of the link.
    """
    link = EmbeddedLink(relations=DEFAULT_RELATIONS, target="#")
    assert link.title is None, "Wrong title"
예제 #10
0
def test_invalid_relations():
    """Check that ValueError is raised if invalid relations are passed.

    1. Try to create an embedded link with non-iterable relations.
    2. Check that ValueError is raised.
    """
    with pytest.raises(ValueError):
        EmbeddedLink(relations=None, target="#")
예제 #11
0
def test_target(target, expected_target):
    """Check target of an embedded link.

    1. Create an embedded link with a target.
    2. Get target.
    3. Check the target.
    """
    link = EmbeddedLink(relations=DEFAULT_RELATIONS, target=target)
    assert link.target == expected_target, "Wrong target"
예제 #12
0
def test_relations(relations, expected_relations):
    """Test relations of an embedded link.

    1. Create an embedded link with different relations.
    2. Get relations.
    3. Check the relations.
    """
    link = EmbeddedLink(relations=relations, target="#")
    assert link.relations == expected_relations, "Wrong relations"
예제 #13
0
def test_title(title, expected_title):
    """Check title of an embedded link.

    1. Create an embedded link with different titles.
    2. Get title of the link.
    3. Check the title.
    """
    link = EmbeddedLink(relations=DEFAULT_RELATIONS, target="#", title=title)
    assert link.title == expected_title, "Wrong title"
예제 #14
0
def test_classes(classes, expected_classes):
    """Check classes of an embedded link.

    1. Create an embedded link with different classes.
    2. Get classes of the link.
    3. Check the classes.
    """
    link = EmbeddedLink(relations=DEFAULT_RELATIONS, target="#", classes=classes)
    assert link.classes == expected_classes, "Wrong classes"
예제 #15
0
def test_missing_relations():
    """Check that ValueError is raised if relations list is empty.

    1. Try to create an embedded link with empty list of relations.
    2. Check that ValueError is raised.
    3. Check error message.
    """
    with pytest.raises(ValueError) as error_info:
        EmbeddedLink(relations=[], target="#")

    assert error_info.value.args[0] == "No relations are passed to create an embedded link", (
        "Wrong error message"
        )
예제 #16
0
def test_target_media_type(target_media_type):
    """Check target media type of an embedded link.

    1. Create an embedded link with different media types of its target.
    2. Get target media type.
    3. Check the media type.
    """
    link = EmbeddedLink(
        relations=DEFAULT_RELATIONS,
        target="#",
        target_media_type=target_media_type,
        )
    assert link.target_media_type == target_media_type, "Wrong media type"
예제 #17
0
def test_default_embedded_link_marshaler(monkeypatch):
    """Test that json marshaler use EmbeddedLinkMarshaler to marshal an embedded link.

    1. Create json marshaler.
    2. Replace marshal method of EmbeddedLinkMarshaler so that it returns fake data.
    3. Marshal an embedded link.
    4. Check that returned data are the same as ones from the mocked method.
    """
    monkeypatch.setattr(EmbeddedLinkMarshaler, "marshal", lambda self: "Marshaled embedded link")

    marshaled_link = JSONMarshaler().marshal_embedded_link(
        embedded_link=EmbeddedLink(relations=["self"], target="/target"),
        )
    assert marshaled_link == "Marshaled embedded link", "Wrong data of the embedded link"
예제 #18
0
def test_marshal_embedded_link():
    """Check that NotImplementedError is raised if marshal_embedded_link is called.

    1. Create an instance of Marshaler class.
    2. Try to marshal an embedded link.
    3. Check that NotImplementedError is raised.
    4. Check the error message.
    """
    link = EmbeddedLink(relations=["self"], target="/embedded/link")

    with pytest.raises(NotImplementedError) as error_info:
        Marshaler().marshal_embedded_link(embedded_link=link)

    assert error_info.value.args[0] == "Marshaler does not support embedded siren links"
예제 #19
0
def test_custom_embedded_link_marshaler():
    """Test that json marshaler use custom marshaler to marshal an embedded link.

    1. Create a sub-class of JSONMarshaler with redefined create_embedded_link_marshaler factory.
    2. Create json marshaler from the sub-class.
    3. Marshal an embedded link.
    4. Check that custom marshaler is used to marshal an embedded link.
    """
    class _CustomEmbeddedLinkMarshaler(JSONMarshaler):
        create_embedded_link_marshaler = _CustomMarshaler("Custom marshaled embedded link")

    marshaled_link = _CustomEmbeddedLinkMarshaler().marshal_embedded_link(
        embedded_link=EmbeddedLink(relations=["self"], target="/target"),
        )
    assert marshaled_link == "Custom marshaled embedded link", "Wrong data of the embedded link"
예제 #20
0
def test_embedded_link(component_validator):
    """Test that embedded link can be marshaled and parsed back.

    1. Create an embedded link.
    2. Create JSON parser and marshaler.
    3. Marshal the embedded link.
    4. Parse the data.
    5. Check that parsed embedded link has the same data as the original one.
    """
    embedded_link = EmbeddedLink(
        relations=("embedded link relation 1", "embedded link relation 2"),
        classes=("embedded link class 1", "embedded link class 2"),
        title="embedded link title",
        target="/embedded/link/target",
        target_media_type="application/embedded+link",
    )

    embedded_link_data = JSONMarshaler().marshal_embedded_link(embedded_link)
    actual_embedded_link = JSONParser().parse_embedded_link(embedded_link_data)

    component_validator.validate_embedded_link(actual_embedded_link,
                                               embedded_link)
예제 #21
0
def test_parse(component_validator):
    """Test that data of embedded representation is properly parsed.

    1. Create an embedded representation.
    2. Create an embedded representation parser.
    3. Replace parser methods so that they return predefined data.
    4. Parse the embedded representation.
    5. Check the data of the embedded representation.
    """
    representation = EmbeddedRepresentation(
        relations=["parsed relation"],
        classes=("parsed class 1", "parsed class 2"),
        properties={
            "property 1": 1,
            "property 2": [1, 2]
        },
        entities=(
            EmbeddedLink(target="/embedded/link/target",
                         relations=["relation"]),
            EmbeddedRepresentation(relations=["relation"]),
        ),
        links=[Link(target="/link/target", relations=["relation"])],
        actions=[Action(target="/action/target", name="action")],
        title="parsed title",
    )

    parser = EmbeddedRepresentationParser(data={}, parser=JSONParser())
    parser.parse_relations = lambda: representation.relations
    parser.parse_classes = lambda: representation.classes
    parser.parse_properties = lambda: representation.properties
    parser.parse_entities = lambda: representation.entities
    parser.parse_links = lambda: representation.links
    parser.parse_actions = lambda: representation.actions
    parser.parse_title = lambda: representation.title

    actual_representation = parser.parse()
    component_validator.validate_embedded_representation(
        actual_representation, representation)
                                           "entities")
    marshaler = RepresentationMarshaler(
        marshaler=JSONMarshaler(),
        embedded_representation=SubEntitiesRepresentation(entities=None),
    )
    with pytest.raises(ValueError) as error_info:
        marshaler.marshal_entities()

    expected_message = "Failed to iterate over sub-entities of the embedded representation"
    assert error_info.value.args[0] == expected_message, "Wrong error"


@pytest.mark.parametrize(
    argnames="sub_entity",
    argvalues=[
        EmbeddedLink(target="/embedded/link", relations=["relation"]),
        EmbeddedRepresentation(relations=["relation"]),
    ],
    ids=[
        "Link",
        "Representation",
    ],
)
def test_non_marshalable_sub_entities(sub_entity):
    # pylint: disable=line-too-long
    """Test that ValueError is raised if one of sub-entities of the embedded representation is not marshallable.

    1. Create json marshaler that raises exception when either marshal_embedded_link or
       marshal_embedded_representation is called.
    2. Create an embedded representation marshaler.
    3. Try to call marshal_entities method.
예제 #23
0
               target="/third",
               title="Second action with non-unique name"),
    ]

    with pytest.raises(ValueError) as error_info:
        Entity(actions=actions)

    assert error_info.value.args[
        0] == "Some of the actions have the same name", "Wrong error"


@pytest.mark.parametrize(
    argnames="entities",
    argvalues=[
        [],
        [EmbeddedLink(relations=["self"], target="/self")],
        [EmbeddedRepresentation(relations=["self"])],
        [
            EmbeddedLink(relations=["first"], target="/first"),
            EmbeddedRepresentation(relations=["second"]),
            EmbeddedLink(relations=["third"], target="/third"),
            EmbeddedRepresentation(relations=["forth"]),
        ],
    ],
    ids=[
        "Without entities",
        "Single embedded link",
        "Single embedded representation",
        "Several enitities of different types",
    ],
)
        Action(name="duplicate", target="/first", title="First action with non-unique name"),
        Action(name="unique", target="/second", title="Action with unique name"),
        Action(name="duplicate", target="/third", title="Second action with non-unique name"),
        ]

    with pytest.raises(ValueError) as error_info:
        EmbeddedRepresentation(relations=DEFAULT_RELATIONS, actions=actions)

    assert error_info.value.args[0] == "Some of the actions have the same name", "Wrong error"


@pytest.mark.parametrize(
    argnames="entities",
    argvalues=[
        [],
        [EmbeddedLink(relations=["self"], target="/self")],
        [
            EmbeddedRepresentation(
                relations=["self"],
                entities=[EmbeddedRepresentation(relations=["self"])],
            ),
        ],
        [
            EmbeddedRepresentation(relations=["first"]),
            EmbeddedLink(relations=["second"], target="/second"),
            EmbeddedRepresentation(relations=["third"]),
            EmbeddedLink(relations=["forth"], target="/forth"),
        ],
    ],
    ids=[
        "Without entities",