Выражение XPath - или не работает должным образом

1

Я пытаюсь сделать не так жесткое выражение xpath 2.0, но все же я заблокирован.

Вот файл xml:

<request>
<cmt:transmission>
    <cmt:workflow>
        <cm:work>
            <cm:expression>
                <cm:manifestation>
                    <cm:reference_manifestation format="FMX4"
                        sequence="1">file1.xml</cm:reference_manifestation>
                    <cm:reference_manifestation format="TIFF"
                        sequence="2">file2.tif</cm:reference_manifestation>
                    <cm:reference_manifestation format="FMX4"
                        sequence="3">file3.xml</cm:reference_manifestation>
                    <cm:extension xsi:type="ojext:OJManifestationExtensionType">
                        <ojext:manifestation_type>fmx4</ojext:manifestation_type>
                    </cm:extension>
                </cm:manifestation>
            </cm:expression>        
        </cm:work>
    </cmt:workflow>
</cmt:transmission>

XPath, который я пытаюсь сделать, заключается в следующем: если my manifestation_type является "fmx4", тогда формат моего reference_manifest должен быть "FMX4" или "TIFF". Если мое правило не соблюдается, я хочу получить манифестацию.

Вот мой текущий недопустимый xpath:

descendant::*:manifestation[*:extension/*:manifestation_type ='fmx4' and not (*:reference_manifestation/@format = 'FMX4' or *:reference_manifestation/@format = 'TIFF' ) ]

Может кто-нибудь мне помочь?

спасибо

  • 0
    Вы выражение работает без or ?
  • 0
    Да, если я попробую только с выражениями FMX4 или TIFF, это нормально.
Показать ещё 2 комментария
Теги:
xpath
xpath-2.0

1 ответ

1
Лучший ответ

Ну, это довольно запутанное выражение.

//*[local-name() = 'manifestation'
and *[local-name() = 'extension']/*[local-name() = 'manifestation_type'] = 'fmx4'
and *[local-name() = 'reference_manifestation']/@format[. != 'TIFF' and . != 'FMX4']]

На простом английском языке строка для строки:

Ищите элементы в любом месте документа, если их локальное имя является "проявлением".

Кроме того, должен быть хотя бы один дочерний элемент с локальным именем "extension", и этот элемент, в свою очередь, должен иметь дочерний элемент с локальным именем "manifestation_type", а его текстовое содержимое должно быть "fmx4".

Кроме того, исходный элемент "проявления" должен иметь по крайней мере один другой дочерний элемент с локальным именем "reference_manifestation" и атрибутом "формат", значение которого не является ни "TIFF", ни "FMX4".

С вашим текущим входным XML выражение пути ничего не возвращает (потому что правила соблюдаются). Если вы измените ввод на следующий (а также объявите все пространства имен, которые отсутствовали!):

<request xmlns:cm="www.example.com" xmlns:cmt="www.example2.com"
xmlns:ojext="www.example3.com"
xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance">
<cmt:transmission>
    <cmt:workflow>
        <cm:work>
            <cm:expression>
                <cm:manifestation>
                    <cm:reference_manifestation format="FMX4"
                        sequence="1">file1.xml</cm:reference_manifestation>
                    <cm:reference_manifestation format="TIFF"
                        sequence="2">file2.tif</cm:reference_manifestation>
                    <cm:reference_manifestation format="SOMETHINGELSE"
                        sequence="3">file3.xml</cm:reference_manifestation>
                    <cm:extension xsi:type="ojext:OJManifestationExtensionType">
                        <ojext:manifestation_type>fmx4</ojext:manifestation_type>
                    </cm:extension>
                </cm:manifestation>
            </cm:expression>        
        </cm:work>
    </cmt:workflow>
</cmt:transmission>
</request>

Затем возвращается выражение, поскольку один атрибут format отклоняется от разрешенных значений.


Примечание 1: в подобных случаях это безумно сложно отчасти потому, что вы игнорируете пространства имен, присутствующие в документе. Если вы зарегистрируете или объявите эти пространства имен надлежащим образом и используете префиксы в выражении пути, это очень поможет.

Примечание 2. В этом выражении пути нет ничего 2.0, и то же самое относится к вашему исходному выражению.

  • 1
    Спасибо за ваш ответ, вроде работает нормально :)

Ещё вопросы

Сообщество Overcoder
Наверх
Меню