вопрос - XSL-поиск с использованием значений из переменной по нескольким XML-файлам - PullRequest
0 голосов
/ 03 октября 2018

У меня есть токенизированная переменная, которая содержит список имен файлов из .txt списка каталогов.Я хочу найти эти имена файлов в ряде XML-файлов в ряде подкаталогов.Если имя файла найдено, я хочу вывести, что «имя файла» было найдено в «xmlfile».

Существует много каталогов xml, и они не являются статичными.То же самое с файлами XML.Имена файлов не помечены в xml, поэтому я просто ищу их появление в файле.

Любая помощь будет признательна.

, чтобы упростить примеры - я хочуиспользовать

$ filenames_to_find (токенизированный список имен файлов из списка каталогов .txt)

для поиска по

dir1/*.xml  
dir2/*.xml

с выводом

имя файла было найдено в xmlfilename


Я использую академическую версию Oxygen XML, поэтому я думаю, что через Saxon у меня есть, и у меня есть автономный Saxon-файл для запуска этого из командной строки.

Благодаря полученным ответам и большему количеству поисковых запросов в Google, я получил это, что не работает.Я знаю, что он сломан, но я не знаю, как это исправить!

<xsl:stylesheet xmlns:xsl="http://www.w3.org/1999/XSL/Transform"
    xmlns:xs="http://www.w3.org/2001/XMLSchema"
    xmlns:h="http://www.w3.org/1999/xhtml"
    exclude-result-prefixes="xs"
    version="3.0"
    expand-text="yes"
    >

    <xsl:variable name="filenames_from_directory_listing" as="xs:string" select="unparsed-text('filenames_from_directory_listing.txt')"/>
    <xsl:variable name="filenames_to_find" select="tokenize($filenames_from_directory_listing, '\s+')"/>

    <xsl:template match="/">
        <xsl:for-each select="collection('.?select=*.xml;recurse=yes')"/>
            <xsl:variable name="xml_filenames" select="."/>
                <xsl:for-each select="$filenames_to_find">
                    <xsl:if test="(contains($t, .))">
                        <xsl:message>{document-uri($xml_filenames)} contains {.}</xsl:message>
                    </xsl:if>
                </xsl:for-each>
    </xsl:template>
</xsl:stylesheet>

Есть предложения?Очевидно, я новичок в XSL.Спасибо за ваше терпение.

1 Ответ

0 голосов
/ 03 октября 2018

Предполагая, что Saxon или другой продукт, который сопоставляет URI коллекции с именами каталогов аналогичным образом, вы можете сделать

<xsl:for-each select="collection('.?select=*.xml;recurse=yes')">
   <xsl:variable name="doc" select="."/>
   <xsl:for-each select="$filenames">
     <xsl:if test="some $t in $doc//text() satisfies(contains($t, .))">
       <xsl:message>{document-uri($doc)} contains {.}</xsl:message>

На самом деле вы можете заменить xsl: if test на test="contains($doc, .)", но это может бытьменее эффективен, если документы большие, так как он включает в себя сборку всего строкового значения документа в виде строки в памяти.

Другой альтернативой может быть обработка файлов в виде неразобранных текстовых файлов, а не файлов XML, но этопотребовалось бы немного поработать с конфигурацией Saxon, чтобы он автоматически не анализировал файлы с расширением «.xml» как XML.

...