GWT 2.6.1 + SuperDevMode:服务器上的堆栈跟踪未进行反混淆

3
直到今年5月,我一直在使用 GWT 2.5.1简单的 DevMode,并且能够通过 这篇精彩的文章使用符号映射将混淆的异常和堆栈跟踪信息发送到服务器并进行反混淆。这对我很有帮助。
自从6月以来,我成功地切换到了 GWT 2.6.1SuperDevMode,相比于 简单的 DevMode,提供了相当不错的体验并且更加容易使用。
然而,我发现我的堆栈跟踪信息在服务器上无法正确反混淆。即使进行了反混淆,我仍然收到混淆的堆栈跟踪信息。
下面是相关的 *.gwt.xml 文件内容:
<module rename-to="somemodule">

    <!-- inherits, stylesheet, entry-point, source elements are going here -->

    <add-linker name="xsiframe" />

    <extend-property name="locale" values="uk" />
    <set-property-fallback name="locale" value="uk" />

    <set-property name="compiler.stackMode" value="emulated" />
    <set-configuration-property name="compiler.emulatedStack.recordLineNumbers" value="true" />

    <set-property name="gwt.logging.logLevel" value="INFO" />            
    <set-property name="gwt.logging.enabled" value="TRUE" />  
    <set-property name="gwt.logging.developmentModeHandler" value="ENABLED" />    
    <set-property name="gwt.logging.systemHandler" value="DISABLED" />  
    <set-property name="gwt.logging.popupHandler" value="DISABLED" />  
    <set-property name="gwt.logging.consoleHandler" value="ENABLED" />   
    <set-property name="gwt.logging.firebugHandler" value="ENABLED" />
</module>

以下是处理客户端异常的服务器端代码:
import static com.google.gwt.user.client.rpc.RpcRequestBuilder.STRONG_NAME_HEADER;
import com.google.gwt.core.client.impl.SerializableThrowable;
import com.google.gwt.logging.server.StackTraceDeobfuscator;

// ....

@Override
public void logClientException(final SerializableThrowable ex, final String userAgent, final String platform, final String moduleName) {
    final HttpServletRequest request = getThreadLocalRequest();

    final String symbolMapsDirectory = "webapps/" + getTomcatWebappFolder(request.getServletContext()) + "/WEB-INF/deploy/" + moduleName + "/symbolMaps";
    final String permutationName = request.getHeader(STRONG_NAME_HEADER);
    final Throwable original = new StackTraceDeobfuscator(symbolMapsDirectory).deobfuscateThrowable(ex.getThrowable(), permutationName);

    logClientException(original, userAgent, platform);
}

GWT 2.5.1 转移到 GWT 2.6.1 时,我是否忽略了一些内容?

非常感谢您提前的帮助!

2个回答

3

这是一个不幸的已知问题,请参见此处此处

问题在于每次重新编译都会创建一个全新的增量目录树(请参见compile-1、compile-2等子目录)。因此,运行应用程序服务器(托管您的servlet的服务器)将无法选择正确的compile-x/extras//symbolMaps目录来使用调用setSymbolMapsDirectory(如@Vadim所指出的那样)。当然,每次重新编译时复制此类symbolMaps到预期目录相当麻烦(我甚至不确定它是否适用于置换名称)。

这对于SuperDevMode时代的GWT-RPC也一样,但不同的是,代码服务器(SDM)现在直接公开所有这些*.gwt.rpc输出文件,如果使用gwt.codeserver.port java标志,您的servlet将自动下载策略文件(仅在本地主机,并且GTW>= 2.5.1)。

无论如何,重点是让代码服务器以某种方式公开/服务于symbolMaps文件(它已经以某种方式通过访问http://localhost:9876/sourcemaps//gwtSourceMap.json来提供,但仅适用于sourcemaps,并且不是在StackTraceCreator可理解的方式中),如第一个问题所述。

幸运的是,在开发过程中,堆栈跟踪并不是太难处理。


谢谢你的回答!基本上我一天前就得出了同样的结论,但是没有机会写出类似的答案,因此接受了你的答案!是的,我同意在开发过程中这不是一个很大的问题。让我们希望GWT团队能够在最近的将来解决这个问题。 - Yuriy Nakonechnyy

2

就在昨天我也遇到了类似的问题。唯一不同的是,我们在GWT日志记录中使用了内置的反混淆功能。所以我的问题在于symbolMapsDirectory路径设置不正确。这里的坏消息是,如果你的symbolMaps路径不正确,GWT不会告诉你:

com.google.gwt.core.server.StackTraceDeobfuscator#loadSymbolMap:

try {
  BufferedReader bin = ...
} catch (IOException e) {
  // If the symbol map isn't found or there's an I/O error reading the file, the returned
  // mapping may contain some or all empty data (see below).
}

所以我们的工作解决方案如下:

setSymbolMapsDirectory(getServletContext().getRealPath("/WEB-INF/deploy/" + moduleName + "/symbolMaps/"));

感谢您的回答!但是您是否尝试在“SuperDevMode”(而不是普通的“DevMode”或生产模式)中使用此反混淆器?因为在“DevMode”或生产模式下,一切都很正常,唯一的问题在于“SuperDevMode”。 - Yuriy Nakonechnyy
不,我没有尝试过。在SDM中,您使用由localhost:9876托管的symbolMap进行工作。但是GWT模块会向/remote_logger发送请求,以连接到您的实际应用程序服务器。如果您不将symbolMap从localhost:9876放置到实际应用程序服务器上,则/remote_logger将无法解密堆栈跟踪,因为缺少symbolMap。我认为这就是问题所在。 - Vadim
是的,你说得对 - 我也得出了这个结论。让我们等待GWT团队发布解决方案 :) - Yuriy Nakonechnyy

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接