2009-09-29 13 views
5

Estoy intentando utilizar xmltask de hormiga para modificar un archivo en un subdirectorio:xmltask confundido acerca de DTD

project/path/to/file.xml 

El archivo se refiere a un DTD como esto:

<!DOCTYPE data SYSTEM "mydtd.dtd"> 

I don' t tiene la flexibilidad de cambiar estos documentos.

Esta DTD se almacena en el mismo subdirectorio, que siempre ha funcionado bien:

project/path/to/mydtd.dtd 

Desafortunadamente, xmltask está tratando de localizar la DTD en el directorio de nivel superior de mi proyecto, que es donde mi fichero de construcción es se encuentra, y donde corro de:

[xmltask] java.io.FileNotFoundException: /home/me/project/mydtd.dtd (el sistema no puede encontrar el archivo especificado)

veo en la documentación xmltask que puedo corregir esto con un xmlcatalog elemento para indicarle dónde buscar el archivo. Pero necesito usar un elemento dtd, y solo puedo encontrar ejemplos para este elemento, no documentación; los ejemplos muestran solo publicId, y si entiendo XML correctamente este documento no tiene uno. No debería necesitar especificar esto, de todos modos, ¿verdad, ya que mi documento ya dice que mi DTD se almacena localmente y muestra dónde está?

¿Por qué xmltask no encuentra la DTD correctamente? ¿Cuál es la mejor manera de corregir o solucionar esta situación?

Respuesta

5

Un catálogo XML es el camino a seguir aquí, solo necesita un poco más de perseverancia.

Como señaló correctamente, el tipo estándar Ant <XmlCatalog> solo le permite especificar referencias públicas DTD cuando usa la sintaxis en línea, que no le sirve. Sin embargo, <XmlCatalog> también le permite especificar un catálogo de sintaxis OASIS estándar, que es mucho más rico, incluida la resolución de referencias de SISTEMA DTD.

catálogo un oasis (especificación completa here) tiene el siguiente aspecto:

<catalog xmlns="urn:oasis:names:tc:entity:xmlns:xml:catalog">  
    <system systemId="mydtd.dtd" uri="project/path/to/mydtd.dtd"/> 
</catalog> 

continuación, puede hacer referencia a este catálogo de la <XmlCatalog>:

<xmlcatalog refid="commonDTDs"/> 
    <catalogpath> 
    <pathelement location="path/to/oasis.catalog"/> 
    </catalogpath> 
</xmlcatalog> 

Y eso es todo. Es una buena idea crear un archivo de catálogo OASIS reutilizable y consultarlo desde varias tareas Ant relacionadas con XML, todas las cuales pueden usar <XmlCatalog>.

0

Ha intentado:

<!DOCTYPE data SYSTEM "./path/to/mydtd.dtd"> 

? O un camino absoluto?

Además, usted puede encontrar <dtd> descripción here.

+0

Eso arruinaría toda la otra manipulación de estos documentos, ya que cuando se despliegan están sentados junto a sus dtds pero no en el mismo directorio en el que estoy tratando de editarlos en tiempo de compilación. – skiphoppy

+0

La pregunta dice "No tengo la flexibilidad para cambiar estos documentos". – skaffman

+0

@skaffman, para ser justos, no dijo eso cuando originalmente pregunté, y lo agregué debido a esta respuesta. :) – skiphoppy

0

xmltask no lo encuentra porque está buscando en el directorio de trabajo actual. Ant le permite especificar un directorio base utilizando el atributo basedir del elemento <target>. Así que sugiero que intente esto:

<target basedir="path/to" ...> 
    <xmltask... 
</target> 

Me parece que no es el XML/DTD que realmente tiene el problema, pero conseguir xmltask interactuar con los dos de ellos como quiera.

Si eso falla, puede usar la tarea Ant Copy para copiar el XML y DTD a la carpeta raíz antes de procesar con xmltask, y luego copiar de nuevo.

+0

Usar las referencias relativas al SISTEMA de esta manera es una mala práctica, ya que resolverlas es difícil. Los documentos fuente deben usar referencias PÚBLICAS o referencias absolutas del SISTEMA. Afortunadamente, los catálogos XML (aplicados correctamente) pueden evitar este mal diseño. – skaffman

1

Como alternativa, parece que puedo omitir toda la validación creando un archivo en blanco con el mismo nombre que el archivo de DVD, y luego borrando el archivo cuando haya terminado. Las probabilidades son que voy a seguir esa ruta en lugar de usar el catálogo.

0

Tuve un problema similar cuando un archivo XML tenía un doctype con referencia de sistema que no se pudo cambiar.

<!DOCTYPE opencms SYSTEM "http://www.opencms.org/dtd/6.0/opencms-modules.dtd">

fui por primera vez por el camino y ha creado un archivo de catálogo con el catálogo de OASIS como se describió anteriormente, pero para ser capaz de utilizar los catálogos externos he tenido que incluir el Apache Commons Resolver 1.1 (resolver.jar) en el Ant classpath (ver http://ant.apache.org/manual/Types/xmlcatalog.html).

Como tenía varias máquinas en las que se suponía que debía ejecutar esta versión, esto parecía excesivo, especialmente porque xmltask funcionaba bien si eliminaba la definición de tipo de documento. No se me permitió eliminarlo permanentemente porque el doctype se necesitaba en otro lugar.

Al final usé esta solución alternativa: Comenté la definición del tipo de documento usando la tarea replace de Ant, ejecuté el xmltask, y luego volví a colocar el tipo de documento en el archivo.

<replace file="myxmlfile.xml"> 
    <replacetoken>&lt;!DOCTYPE opencms SYSTEM "http://www.opencms.org/dtd/6.0/opencms-modules.dtd"&gt;</replacetoken> 
    <replacevalue>&lt;!-- !DOCTYPE opencms SYSTEM "http://www.opencms.org/dtd/6.0/opencms-modules.dtd" --&gt;</replacevalue> 
</replace> 

<xmltask .../> 

<replace file="${local.opencms.webapp.webinf}/config/opencms-modules.xml"> 
    <replacetoken>&lt;!-- !DOCTYPE opencms SYSTEM "http://www.opencms.org/dtd/6.0/opencms-modules.dtd" --&gt;</replacetoken> 
    <replacevalue>&lt;!DOCTYPE opencms SYSTEM "http://www.opencms.org/dtd/6.0/opencms-modules.dtd"&gt;</replacevalue> 
</replace> 
Cuestiones relacionadas