4

Java アプリケーション FreeMind は、XSLT を使用して古いファイルから更新します。XSLT は、静的な Java 関数を使用して文字列操作を簡素化します。これは Java 7 update 2 までは問題なく動作し、Windows の java7 update 4 では次の例外が発生します。

STDERR: ERROR:  'The first argument to the non-static Java function 'replaceSpacesToNonbreakableSpaces' is not a valid object reference.'
STDERR: FATAL ERROR:  'Could not compile stylesheet'May 26, 2012 10:50:06 PM freemind.main.Resources logException
SEVERE: An exception occured: 
javax.xml.transform.TransformerConfigurationException: Could not compile stylesheet
    at com.sun.org.apache.xalan.internal.xsltc.trax.TransformerFactoryImpl.newTemplates(Unknown Source)
    at com.sun.org.apache.xalan.internal.xsltc.trax.TransformerFactoryImpl.newTransformer(Unknown Source)
    at freemind.main.Tools$1TransformerRunnable.run(Tools.java:1023)
    at java.lang.Thread.run(Unknown Source)

最小限の例に落とし込むと、カスタム SecurityManager が犯人であることがわかります。設定されている場合、コードは失敗します。コメントアウトされている場合、コードは機能します。update 2 と update 4 の間に java7 のセキュリティ システムで何が変更されたか、または他に何が原因であるかを知っている人はいますか?

さらに最小限の例を次に示します。

package freemind.main;

import java.io.StringReader;
import java.io.StringWriter;

import javax.xml.transform.Result;
import javax.xml.transform.Transformer;
import javax.xml.transform.TransformerFactory;
import javax.xml.transform.stream.StreamResult;
import javax.xml.transform.stream.StreamSource;

public final class FreeMindSecurityTest  {

    public static void main(String[] args) throws Exception {
        // if commented out, this program works as expected.
        System.setSecurityManager(new SecurityManager());
        String input = "<map version=\"0.9.0\">"
                + "</map>";
        String xslt = "<?xml version=\"1.0\" encoding=\"UTF-8\"?>"
                + "     <xsl:stylesheet version=\"1.0\" xmlns:xsl=\"http://www.w3.org/1999/XSL/Transform\" xmlns:FreeMindSecurityTest=\"xalan://freemind.main.FreeMindSecurityTest\" exclude-result-prefixes=\"FreeMindSecurityTest\">"
                + "         <xsl:template               match=\"/ | node() | @* | comment() | processing-instruction()\">"
                + "             <xsl:value-of select=\"FreeMindSecurityTest:replaceSpacesToNonbreakableSpaces('test')\"/>"
                + "         </xsl:template>" + "        </xsl:stylesheet>";
        StringWriter writer = new StringWriter();
        final Result result = new StreamResult(writer);

        final StreamSource sr = new StreamSource(new StringReader(input));
        // create an instance of TransformerFactory
        TransformerFactory transFact = TransformerFactory.newInstance();
        Transformer trans = transFact.newTransformer(new StreamSource(
                new StringReader(xslt)));

        trans.transform(sr, result);

        System.out.println("Transformed: " + writer.getBuffer());
        writer.close();
    }

    public static String replaceSpacesToNonbreakableSpaces(String input) {
        return input;
    }



}

簡単に言えば、Java はメソッドが静的ではなく (しかし静的である)、オブジェクト参照を見逃していると考えています。

TIA、FreeMind のクリス

編集: 最短の例 (通常のセキュリティ マネージャーのコピーを設定するだけで十分です) が追加されました。

4

1 に答える 1

2

JAXP 1.4.6(Java 7 Update 4)にバグがある可能性があります。Java 7u4での変更点は、JAXP1.4.6へのアップグレードがあったことです。Javaリリースノートを参照してください。

回避策/解決策(おそらく最良の選択ではありません)は、 Java承認フォルダーを介して追加のパッチなしでXalan2.7.1を使用することです。(xalan 2.7.1 jarsをにコピーしますjre/libs/endorsed)または、Xalanをサードパーティのライブラリとして使用します。

Linux64でJ7U4とXalan2.7.1を使用して動作しました

Transformed: <?xml version="1.0" encoding="UTF-8"?>test
于 2012-05-28T16:28:38.860 に答える