class MobiPIP implements PIP {

    @Override
    public List<Literal> findAttribute(AttributeDesignator attributeDesignator, Request request)
            throws MissingAttributeException, ProcessingException {
        IRI attributeId = attributeDesignator.attributeId();
        IRI category = attributeDesignator.category();
        IRI pathSource;
        if (category.equals(request.getSubjectCategory())) {
            pathSource = request.getSubjectId();
        } else if (category.equals(request.getResourceCategory())) {
            pathSource = request.getResourceId();
        } else {
            return Collections.emptyList();
        }

        try (RepositoryConnection conn = repo.getConnection()) {
            if (attributeId.stringValue().startsWith(PROP_PATH_NAMESPACE)) {
                int firstIdx = attributeId.stringValue().lastIndexOf("(") + 1;
                int lastIdx = attributeId.stringValue().lastIndexOf(")");
                String path = decode(attributeId.stringValue().substring(firstIdx, lastIdx));
                TupleQuery query = conn.prepareTupleQuery(String.format(PROP_PATH_QUERY, path));
                query.setBinding("sub", pathSource);
                return StreamSupport.stream(query.evaluate().spliterator(), false)
                        .map(bindings -> bindings.getBinding("value").get().getValue())
                        .map(value -> {
                            if (Literal.class.isAssignableFrom(value.getClass())) {
                                return (Literal) value;
                            } else {
                                return vf.createLiteral(value.stringValue());
                            }
                        })
                        .collect(Collectors.toList());
            } else {
                return StreamSupport.stream(conn.getStatements(pathSource, attributeId, null).spliterator(), false)
                        .map(Statement::getObject)
                        .map(value -> value instanceof Literal ? (Literal) value
                                : vf.createLiteral(value.stringValue()))
                        .collect(Collectors.toList());
            }
        }
    }

}