Warning: file_get_contents(/data/phpspider/zhask/data//catemap/0/xml/13.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
Java 使用JAXB解组XML而无需取消字符_Java_Xml_Escaping_Unmarshalling - Fatal编程技术网

Java 使用JAXB解组XML而无需取消字符

Java 使用JAXB解组XML而无需取消字符,java,xml,escaping,unmarshalling,Java,Xml,Escaping,Unmarshalling,设想以下情况:我们从某个外部工具收到一个xml文件。最近在这个xml中,节点名或其richcontent标记中可能有一些转义字符,如下面的示例(简化): 我是节点ä的注释ä! 在用JAXB解组文件后,这些转义字符将被取消转义。不幸的是,我需要他们保持现状,意味着逃脱。有没有什么方法可以避免在解封时将这些角色从中分离出来 在研究过程中,我发现了许多关于在出现相反问题的地方编组xml文件的问题,但这些问题也没有帮助我: 是否有可能用JAXB实现这一目标,或者我们甚至

设想以下情况:我们从某个外部工具收到一个xml文件。最近在这个xml中,节点名或其richcontent标记中可能有一些转义字符,如下面的示例(简化):



我是节点ä的注释ä!

在用JAXB解组文件后,这些转义字符将被取消转义。不幸的是,我需要他们保持现状,意味着逃脱。有没有什么方法可以避免在解封时将这些角色从中分离出来

在研究过程中,我发现了许多关于在出现相反问题的地方编组xml文件的问题,但这些问题也没有帮助我:

是否有可能用JAXB实现这一目标,或者我们甚至必须考虑更改为不同的XML读取器API?

提前谢谢大家,,
ymene

您只需将
和#
替换为
&#因此调用

unmarshaller.unmarshal(new AmpersandingStream(new FileInputStream(...)));


对于任何xml解析器来说,源文档是否包含
ä
,'ä;`或者
ä
,为什么这对您的情况很重要?问题是:导入这些XML数据后,我们将其与程序数据合并。在这里,我们更改了一些细节,然后希望用xml将这些细节写回外部工具。由于我们没有构建另一个对象图来将数据封送回xml,因此我们欺骗了使用StAX,因为这在当时更简单。从那时起,直到现在我们还没有任何转义字符,不幸的是,外部工具仍然希望转义字符能够工作。注意:构建一个文档相对容易,因为这种方法会破坏XML(例如,编码为UTF-16;在CDATA节中放置符号等)下面是一个测试用例:
。代码查找序列
&
。在CDATA中,这可能有问题,但是JAXB和CDATA呢?在别处,
&
总是有意义的。@McDowell关于UTF-16你是对的,但我认为这不太可能。
unmarshaller.unmarshal(new AmpersandingStream(new FileInputStream(...)));
import java.io.IOException;
import java.io.InputStream;

/**
* Replaces numerical entities with their notation as text.
*/
public class AmpersandingStream extends InputStream {

    private InputStream in;
    private boolean justReadAmpersand;
    private String lookAhead = "";

    public AmpersandingStream(InputStream in) {
        this.in = in;
    }

    @Override
    public int read() throws IOException {
        if (!lookAhead.isEmpty()) {
            int c = lookAhead.codePointAt(0);
            lookAhead = lookAhead.substring(Character.charCount(c));
            return c;
        }
        int c = in.read();
        if (c == (int)'#' && justReadAmpersand) {
            c = (int)'a';
            lookAhead = "mp;#";
        }
        justReadAmpersand = c == (int)'&';
        return c;
    }

    @Override
    public int available() throws IOException {
        return in.available();
    }

    @Override
    public void close() throws IOException {
        in.close();
    }

    @Override
    public synchronized void mark(int readlimit) {
        in.mark(readlimit);
    }

    @Override
    public boolean markSupported() {
        return in.markSupported();
    }

    @Override
    public int read(byte[] b) throws IOException {
        return in.read(b);
    }

    @Override
    public int read(byte[] b, int off, int len) throws IOException {
        return in.read(b, off, len);
    }

    @Override
    public synchronized void reset() throws IOException {
        in.reset();
    }

    @Override
    public long skip(long n) throws IOException {
        return in.skip(n);
    }

}