我有一个小的Java程序,通过bash脚本用java -jar
调用。该程序调用SOAP Web服务,我想在文件中捕获SOAP消息以备将来的麻烦。我发现在独立Java应用程序中执行此操作的唯一方法是将其添加到我的客户端类:
static
{
// Output the SOAP message to the console
System.setProperty("com.sun.xml.ws.transport.http.client.HttpTransportPipe.dump", "true");
System.setProperty("com.sun.xml.ws.transport.http.HttpAdapter.dump", "true");
}
这将SOAP消息输出到系统输出。我可以将系统重定向到一个文件,但我还有其他消息要进入系统,我希望在控制台上显示。将这些消息包含在文件中是可以的,但SOAP消息太多而无法在控制台上显示。
有没有办法可以在控制台输出上进行某种选择性重定向?
答案 0 :(得分:1)
取决于您正在使用的SOAP库,但通常大多数SOAP库都具有某种日志记录功能,用于将内容写入控制台。通常,当您使用这些日志记录工具时,SOAP库本身不会直接写入System.out。日志记录工具配置为默认将该数据写入System.out。因此,如果您确定要使用哪个SOAP库,然后找出它使用的日志记录工具,那么您可以配置日志记录以写入文件而不是System.out,但仍然将其他消息发送到System.out。
我认为你正在使用正在使用Java Util Logging的Metro。不是那么容易配置,但它可以配置多个appender和logger。我认为这对你有所帮助:
答案 1 :(得分:1)
为什么不将要捕获的邮件写入 stderr 并进行相应的重定向?您应该考虑的一个问题是 stdout 是[通常]缓冲而 stderr 不是。
您正在寻找 shell重定向和管道。假设你正在使用像shell,bash,csh等标准shell ...
command >foo.txt
将重定向 stdout 到文件foo.txt
。填写中的任何现有内容都将被替换。command >>foo.txt
将重定向 标准删除,并将其附加到foo.txt
文件foot.txt
的现有内容(如果有) foo | bar
将管道命令foo
的{{1}}内容通过命令stdout
的标准输入。A * nix进程打开了三个标准的i / o句柄:
重定向和管道操作符也可以挂钩特定的文件句柄。所以......
bar
执行以下操作:
command >foo.txt 2>&1
foo.txt
打开。其他shell可以(并且确实)使用不同但通常类似的语法。
您还应该了解一些有用的命令:
foo.txt
。
这将获取给定的stdin并将其写入命令行以及stdout中指定的文件,因此像这样的链:
tee(1)
运行some-command 2>&1 | tee some-command.log.2013-05-31.txt | less
,可能产生大量输出,将其stderr重定向到stdout,然后通过some-command
传送,生成一个日志文件tee(1)
并通过{ {1}}在您的控制台上将其翻页。
some-commmand.log.2013-05-31.txt
less(1)
less(1)
这些天通常是more(1)
的同义词。这两个都是寻呼机,它们缓冲输出并一次显示一个屏幕,让你向前翻页并向后翻页。
more
less(1)
这是* nix的在线帮助系统。要了解有关它们的更多信息,请尝试运行以下命令:
man(1)
获取apropos(1)
和* `man man`
* `man apropos`
命令的手册页。您也可以针对您正在使用的特定shell尝试man
或apropos
(例如,man tee
将为您提供man [your-shell-name]
shell的手册页,而man csh
1}}将为您提供Bourne shell(csh
)手册页,man sh
将为您提供sh
手册页。
此页面描述了C和Bourne shell系列的常用管道/重定向运算符:http://www.mathinfo.u-picardie.fr/asch/f/MeCS/courseware/users/help/general/unix/redirection.html
您还应该阅读相应的O'Reilly man bash
书:
编辑注意:
正如我在下面的评论中提到的那样,您可以将bash
和Nutshell
替换为您自己的System.Out
,其中包括:
System.Err
这将允许您挂接第三方库的输出并将其重定向到您选择的数据接收器,同时不影响您的普通输出。如果您同时挂钩PrintStream
和PrintStream originalStdOut = System.Out ;
PrintStream newStdout = CreateNewOutputSink() ;
System.Out.flush() ;
System.Out.setOut( newStdout ) ;
invokeSome3rdPartyCode() ;
System.Out.flush() ;
System.Out.setOut( originalStdout ) ;
并将它们重定向到相同的 System.Out
,您将在此过程中捕获标准和错误输出。
答案 2 :(得分:0)
您似乎不太可能在应用程序中执行此操作,因为SOAP代码将调用System.out.print。
如果您的主要目标是将输出与SOAP的输出分开,那么您可以使用特殊符号添加消息,然后通过适当的脚本过滤输出。
如果您的打印语句分布在您的代码中,您可以考虑使用AOP(即AspectJ)修改它们以插入此特殊符号。就个人而言,我通过自己的实用程序方法进行打印,以便在需要时可以在一个地方进行更改。