2016-08-24 7 views
-1

Есть ли какие-либо возможности в XSLT 1.0 или exslt для создания результирующего документа, чтобы он также создавал каталог (ы) в пути, если они не присутствуют? Или мне нужно создать каталог отдельно, прежде чем генерировать выходной документ?XSLT 1.0 генерация каталога

ОБНОВЛЕНИЕ

Я использую Perl, чтобы выполнить преобразование XSLT 1.0. Вот код, который я использую.

#!/usr/local/bin/perl -w 

use strict; 
use warnings; 
use File::Path; 
use File::Spec; 
use File::Basename; 
use XML::LibXSLT; 
use XML::LibXML; 

my $isfile; 

my ($xmlfile,$xsltfile,$samplefile) = qw/ Example.xml trans.xsl sample.xml/; 

if(-f $samplefile) 
{ 
    $isfile = "true"; 
    print "File is present\n"; 
} 
else 
{ 
    $isfile = "false"; 
    print "File is absent\n"; 
} 

my %args = ("isfile" => $isfile); 
my $xslt = XML::LibXSLT->new; 
my $stylesheet = $xslt->parse_stylesheet_file($xsltfile); 
my $results = $stylesheet->transform_file($xmlfile,XML::LibXSLT::xpath_to_string(%{args})); 

0; 

И мой файл XSL выглядит следующим образом

<?xml version="1.0"?> 
<xsl:stylesheet version="1.0" xmlns:xsl="http://www.w3.org/1999/XSL/Transform" 
    xmlns:xalan="http://xml.apache.org/xslt" 
    xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" 
    xmlns:exsl="http://exslt.org/common" 
    extension-element-prefixes="exsl"> 
    <xsl:output method="xml" version="1.0" encoding="UTF-8" indent="yes" media-type="text/xml"/> 

    <xsl:param name="isfile"/> 

    <xsl:template match="/">  
      <xsl:if test="$isfile = 'true'"> 
       <exsl:document href = "/home/USER/Documents/XSLT/Dir1/Dir2/Dir3/outputfile1.xml" method="xml" version="1.0" encoding="UTF-8" indent="yes">     
        Article:- <xsl:value-of select="/Article/Title"/> 
        Authors:- <xsl:apply-templates select="/Article/Authors/Author"/> 
       </exsl:document> 
      </xsl:if> 
     </xsl:template> 

     <xsl:template match="Author"> 
      <exsl:document href = "outputfile2.xml" method="xml" version="1.0" encoding="UTF-8" indent="yes">     
       always Generate this output!! <xsl:value-of select="." /> 
      </exsl:document> 
     </xsl:template> 
    </xsl:stylesheet> 

я получаю следующие ошибки.

runtime error: file trans.xsl line 24 element document 
Directory creation for /home/USER/Documents/XSLT/Dir1/Dir2/Dir3/outputfile1.xml refused 
runtime error: file trans.xsl line 24 element document 
xsltDocumentElem: write rights for /home/USER/Documents/XSLT/Dir1/Dir2/Dir3/outputfile1.xml denied 
at Transform.pl line 29 

Даже когда я изменить путь как Dir1/Dir2/Dir3/outputfile1.xml (так, что он использует текущую директорию, где я дал полные права доступа), в файле XSL, я получаю следующие ошибки.

runtime error: file trans.xsl line 24 element document 
Directory creation for Dir1/Dir2/Dir3/outputfile1.xml refused 
runtime error: file trans.xsl line 24 element document 
xsltDocumentElem: write rights for Dir1/Dir2/Dir3/outputfile1.xml denied 
at Transform.pl line 29 

Does libxslt in Perl 5.8.8 не поддерживает создание каталога?

+0

Рассмотрите возможность добавления тега для Perl, чтобы получить определенную помощь для Perl и libxslt. Я не уверен, что многие читатели, видя вопросы о XSLT, используют Perl для запуска таблицы стилей. –

+0

Обновлен вопрос. – Recker

+1

http://search.cpan.org/dist/XML-LibXSLT/LibXSLT.pm говорит в разделе «XML :: LibXSLT :: Security»: «По умолчанию create_dir не разрешен. Чтобы включить его, должен быть обратный вызов зарегистрировано «. так что вам кажется, что вы должны разрешить это явно, как описано там, настроив обратный вызов, возвращающий «1». –

ответ

1

Да, можно написать/прочитать файл и создать каталог в XSLT 1.0, если вы используете Perl для запуска преобразования. Как уже упоминал Мартин Хоннен, все, что мне нужно было сделать, это добавить несколько обратных вызовов безопасности, чтобы весь процесс XSLT выполнял операции с файлами. Perl-скрипт теперь выглядит как

#!/usr/local/bin/perl -w 

use strict; 
use warnings; 
use File::Path; 
use File::Spec; 
use File::Basename; 
use XML::LibXSLT; 
use XML::LibXML; 

my $isfile; 

my ($xmlfile,$xsltfile,$samplefile) = qw/ Example.xml trans.xsl sample.xml/; 

if(-f $samplefile) 
{ 
    $isfile = "true"; 
    print "File is present\n"; 
} 
else 
{ 
    $isfile = "false"; 
    print "File is absent\n"; 
} 

my %args = ("isfile" => $isfile); 
my $xslt = XML::LibXSLT->new; 
my $stylesheet = $xslt->parse_stylesheet_file($xsltfile); 

    my $security = XML::LibXSLT::Security->new(); 
    $security->register_callback(read_file => sub { return 1;}); 
    $security->register_callback(write_file => sub { return 1;}); 
    $security->register_callback(create_dir => sub { return 1;}); 
    $stylesheet->security_callbacks($security); 

my $results = $stylesheet->transform_file($xmlfile,XML::LibXSLT::xpath_to_string(%{args})); 

0; 
1

Я попытался

<?xml version="1.0" encoding="UTF-8"?> 
<xsl:stylesheet xmlns:xsl="http://www.w3.org/1999/XSL/Transform" 
    xmlns:xs="http://www.w3.org/2001/XMLSchema" 
    xmlns:exsl="http://exslt.org/common" 
    extension-element-prefixes="exsl" 
    exclude-result-prefixes="xs exsl" 
    version="1.0"> 

    <xsl:template match="/"> 
     <exsl:document href="outputTest1/test2016082403Result.xml"> 
      <foo>bar</foo> 
     </exsl:document> 
    </xsl:template> 

</xsl:stylesheet> 

с xsltproc, как это предусмотрено с кислородными и каталог outputTest1 был создан и содержится файл test2016082403Result.xml так, по крайней мере с xsltproc/LibXSLT создание каталогов, кажется, поддерживается. Я не знаю ни одного другого процессора XSLT 1.0, поддерживающего exsl:document в любом случае.