여기에 다시 xslt 초보자. 여기에서 질문하는 많은 사람들과 마찬가지로 저는 다른 프로그래밍 배경에서 왔기 때문에 xslt의 루프를 완전히 이해하지 못하며 시도 할 수있는 왜곡 된 방법을 생각해 냈습니다. 내가 여기서하고 싶은 일을하고, 이것이 모두 끔찍하게 오도 된 경우 다른 더 나은 방법에 대해 배우는 데 100 % 열려 있습니다.
내가하고 싶은 일 : xml 파일 모음과 출력 csv 파일을 반복합니다. 하나씩 이동하는 방법을 알고 있지만 전체 파일 배치에 대해 자동화하고 싶습니다. xslt에서 컬렉션 작업을 알아 내려고 시도했지만 많은 시도가 실패한 후 포기했습니다.
각 tei / xml 파일은 고유 한 3 자 코드 (esmpeople.xml, tdspeople.xml, ldbpeople.xml)로 이름이 지정됩니다.
이 코드를 나열하는 또 다른 tei / xml 파일이 있습니다. codes.xml
그래서 나는 codes.xml을 반복하고 각 코드를 가져온 다음 해당 xml 파일을 찾고 csv 파일을 출력한다고 생각했습니다. 내 코드는 다음과 같습니다.
codes.xml
<?xml version="1.0"?>
<?xml-model href="http://www.tei-c.org/release/xml/tei/custom/schema/relaxng/tei_all.rng" type="application/xml"
schematypens="http://purl.oclc.org/dsdl/schematron"?><?xml-stylesheet type="text/xsl" href="../xslt/csv-transform-people.xsl"?>
<TEI xmlns="http://www.tei-c.org/ns/1.0">
<teiHeader>
<fileDesc>
<titleStmt>
<title/>
</titleStmt>
<publicationStmt>
<p/>
</publicationStmt>
<sourceDesc>
<listBibl>
<bibl>
<note name="workref">OBRAESM</field>
<note name="workname">Escenas matritenses</field>
<note name="workauthor">Mesonero Romanos</field>
</bibl>
<bibl>
<note name="workref">OBRATDS</field>
<note name="workname">Tiempo de silencio</field>
<note name="workauthor">Luis Martín-Santos</field>
</bibl>
<bibl>
<note name="workref">OBRALDB</field>
<note name="workname">Luces de Bohemia</field>
<note name="workauthor">Ramón del Valle-Inclán</field>
</bibl>
</listBibl>
</sourceDesc>
</fileDesc>
<profileDesc><p/></profileDesc>
</teiHeader>
<text>
<body>
<p/>
</body>
</text>
</TEI>
esmpeople.xml
<listPerson>
<person xml:id="PERSSANISIDRO"/>
<person xml:id="PERSHORACIO"/>
<person xml:id="PERSBARTOLOMEARGENSOLA"/>
</listPerson>
tdspeople.xml
<listPerson>
<person xml:id="PERSPEDRO"/>
<person xml:id="PERSAMADOR"/>
<person xml:id="PERSRAMONYCAJAL"/>
<listPerson>
ldbpeople.xml
<listPerson>
<person xml:id="PERSMAXESTRELLA"/>
<person xml:id="PERSMADAMACOLLET"/>
<person xml:id="PERSBUEYAPIS"/>
<listPerson>
csv-transform-people.xsl
<xsl:stylesheet xmlns:xsl="http://www.w3.org/1999/XSL/Transform" xmlns:csv="csv:csv" xmlns:tei="http://www.tei-c.org/ns/1.0" version="1.0">
<xsl:output omit-xml-declaration="yes" method="text" encoding="utf-8"/>
<xsl:variable name="separator" select="','"/>
<xsl:variable name="newline" select="'
'"/>
<xsl:template match="/">
<xsl:for-each select="//tei:listBibl/tei:bibl">
<!--THIS WAS THE PROBLEM-->
<!--xsl:variable name="workref" select="//tei:note[@name='workref']"/-->
<!--FIX-->
<xsl:variable name="workref" select="tei:note[@name='workref']"/>
<xsl:variable name="workreflc" select="lower-case($workref)"/>
<xsl:variable name="workrefshort" select="replace($workref,'OBRA','')"/>
<xsl:variable name="workrefshortlc" select="lower-case($workrefshort)"/>
<xsl:variable name="sourcedocuri" select="concat('xmldb:exist://admin:[email protected]:8080/exist/xmlrpc/db/madrid/xml/',$workrefshortlc,'people.xml')"/>
<xsl:variable name="sourcedoc" select="doc($sourcedocuri)"/>
<xsl:variable name="sourcedocperson" select="$sourcedoc//tei:person"/>
<xsl:result-document href="xmldb:exist://admin:[email protected]:8080/exist/xmlrpc/db/madrid/csv/people2-{$workreflc}.csv">
<xsl:text>persref</xsl:text>
<xsl:value-of select="$separator"/>
<xsl:text>persworks</xsl:text>
<xsl:value-of select="$newline"/>
<xsl:for-each select="$sourcedocperson">
<xsl:variable name="people">
<xsl:value-of select="@xml:id"/>
</xsl:variable>
<xsl:value-of select="$people"/>
<xsl:value-of select="$separator"/>
<xsl:value-of select="$workref"/>
<xsl:value-of select="$newline"/>
</xsl:for-each>
</xsl:result-document> </xsl:for-each>
</xsl:template>
</xsl:stylesheet>
예상 결과 : 세 개의 csv 파일이 csv 디렉토리에 저장 됨 : people-obraesm.csv, people-obratds.csv, people-obraldb.csv
결과 : people-obraesm.csv가 100 % 올바르게 생성되고 있지만 다음 오류가 발생합니다.
오류가 발생했습니다. 동일한 URI에 둘 이상의 결과 문서를 쓸 수 없습니다.
따라서 모든 xml 파일에 액세스하고 권한 문제없이 / csv / 디렉토리에 파일을 쓸 수 있습니다. 오류를 감안할 때 내 스타일 시트 및 / 또는 일반 논리의 루프에 문제가있는 것 같습니다. xslt에서 루프를 사용해야 할 때마다 깊은 시행 착오 모드로 들어가기 때문에 여기서 내가 어디에서 잘못되었는지 알아 내고 싶습니다!
답변 : 위의 csv-transform-people.xsl을 Martin의 제안에 따라 변경했으며 이제 작동합니다!
내부 <xsl:for-each select="//tei:listBibl/tei:bibl">
에서 컨텍스트 노드는 처리 //tei:listBibl/tei:bibl
되므로 모든 선택은 <xsl:variable name="workref" select="//tei:note[@name='workref']"/>
원하는 대신 해당 항목에 상대적이어야합니다 <xsl:variable name="workref" select="tei:note[@name='workref']"/>
.
참고로, XSLT 2 또는 3을 사용하는 경우 XSLT 프로세서를 XPath 1.0 이전 버전과의 호환성 모드로 설정하므로 일반적으로 XSLT가 아닌 적절한 버전 (예 : version="2.0"
또는 version="3.0"
) 을 사용하는 것이 좋습니다 version="1.0"
. 이전에 XSLT 1 프로세서에서 처리 한 XSLT 1.0 스타일 시트를 XSLT 2 또는 3 프로세서로 이동하는 경우에만 그렇게 할 수 있습니다.
이 기사는 인터넷에서 수집됩니다. 재 인쇄 할 때 출처를 알려주십시오.
침해가 발생한 경우 연락 주시기 바랍니다[email protected] 삭제
몇 마디 만하겠습니다