Mercurial > hg > mercurial
changeset 596:a37960e1f0a0
Log stderr when hg command fails to ease troubleshooting
author | Dmitry Neverov <dmitry.neverov@jetbrains.com> |
---|---|
date | Mon, 29 Apr 2013 14:23:20 +0400 |
parents | f2a2bf159f4c |
children | 65f5e86206e6 |
files | mercurial-common/src/jetbrains/buildServer/buildTriggers/vcs/mercurial/command/CommandResult.java mercurial-common/src/jetbrains/buildServer/buildTriggers/vcs/mercurial/command/CommandUtil.java mercurial-tests/src/jetbrains/buildServer/buildTriggers/vcs/mercurial/command/CommandResultTest.java |
diffstat | 3 files changed, 44 insertions(+), 16 deletions(-) [+] |
line wrap: on
line diff
--- a/mercurial-common/src/jetbrains/buildServer/buildTriggers/vcs/mercurial/command/CommandResult.java Mon Apr 29 13:44:45 2013 +0400 +++ b/mercurial-common/src/jetbrains/buildServer/buildTriggers/vcs/mercurial/command/CommandResult.java Mon Apr 29 14:23:20 2013 +0400 @@ -40,15 +40,18 @@ private final String myCommand; private final ExecResult myDelegate; private final Set<String> myPrivateData; + private final CommandSettings mySettings; public CommandResult(@NotNull Logger logger, @NotNull String command, @NotNull ExecResult execResult, - @NotNull Set<String> privateData) { + @NotNull Set<String> privateData, + @NotNull CommandSettings settings) { myLogger = logger; myCommand = command; myDelegate = execResult; myPrivateData = privateData; + mySettings = settings; } @NotNull @@ -78,7 +81,7 @@ myLogger.warn(message); if (hasImportantException()) myLogger.error("Error during executing '" + getCommand() + "'", getException()); - throwVcsException(message); + throwVcsException(getExceptionMessage()); } private void throwVcsException(@NotNull String message) throws VcsException { @@ -146,19 +149,24 @@ } private String createCommandLogMessage() { - return "'" + getCommand() + "' command failed."; + StringBuilder message = new StringBuilder(); + message.append("'").append(getCommand()).append("' command failed."); + String stderr = getStderr(); + if (!isEmpty(stderr)) { + int logOutputLimit = mySettings.getLogOutputLimit(); + if (logOutputLimit == -1) { + message.append("\nstderr:\n").append(stderr); + } else { + message.append(StringUtil.truncateStringValueWithDotsAtEnd(stderr, logOutputLimit)); + } + } + return message.toString(); } - @Nullable private String getExceptionMessage() { - //noinspection ThrowableResultOfMethodCallIgnored - Throwable exception = getException(); - if (exception == null) - return null; - String message = exception.getMessage(); - if (message == null) - message = exception.getClass().getName(); - return message; + StringBuilder message = new StringBuilder(); + message.append("'").append(getCommand()).append("' command failed."); + return message.toString(); } private void rethrowDetectedError() throws VcsException {
--- a/mercurial-common/src/jetbrains/buildServer/buildTriggers/vcs/mercurial/command/CommandUtil.java Mon Apr 29 13:44:45 2013 +0400 +++ b/mercurial-common/src/jetbrains/buildServer/buildTriggers/vcs/mercurial/command/CommandUtil.java Mon Apr 29 14:23:20 2013 +0400 @@ -30,7 +30,7 @@ public static CommandResult runCommand(@NotNull MercurialCommandLine cli, @NotNull CommandSettings settings) throws VcsException { final String command = removePrivateData(cli.getCommandLineString(), settings.getPrivateData()); logRunCommand(cli, command, settings); - CommandResult res = run(cli, settings.getTimeout(), command, settings.getPrivateData()); + CommandResult res = run(cli, settings.getTimeout(), command, settings.getPrivateData(), settings); if (settings.isCheckForFailure() || settings.isFailWithNonEmptyStderr()) res.checkFailure(settings.isFailWithNonEmptyStderr()); logCommandOutput(command, res, settings); @@ -40,7 +40,8 @@ private static CommandResult run(@NotNull final MercurialCommandLine cli, final int executionTimeout, @NotNull final String command, - @NotNull final Set<String> privateData) { + @NotNull final Set<String> privateData, + @NotNull CommandSettings settings) { final long start = System.currentTimeMillis(); ExecResult res = SimpleCommandLineProcessRunner.runCommand(cli, null, new SimpleCommandLineProcessRunner.ProcessRunCallbackAdapter() { @Override @@ -53,7 +54,7 @@ Loggers.VCS.debug("Command " + command + " took " + duration + "ms"); } }); - return new CommandResult(Loggers.VCS, command, res, privateData); + return new CommandResult(Loggers.VCS, command, res, privateData, settings); } public static String removePrivateData(final String str, final Set<String> privateData) {
--- a/mercurial-tests/src/jetbrains/buildServer/buildTriggers/vcs/mercurial/command/CommandResultTest.java Mon Apr 29 13:44:45 2013 +0400 +++ b/mercurial-tests/src/jetbrains/buildServer/buildTriggers/vcs/mercurial/command/CommandResultTest.java Mon Apr 29 14:23:20 2013 +0400 @@ -23,6 +23,7 @@ import static org.hamcrest.Matchers.containsString; import static org.hamcrest.Matchers.not; import static org.testng.AssertJUnit.*; +import static org.testng.AssertJUnit.assertTrue; /** * @author dmitry.neverov @@ -101,12 +102,22 @@ } } + public void when_command_fails_stderr_should_be_logged() { + CommandResult cr = commandResultFor(execResult().withStderr("an important error").withExitCode(255)); + try { + cr.checkCommandFailed(); + } catch (VcsException e) { + //ignore + } + assertTrue(myLogger.contains("an important error")); + } + ExecResultBuilder execResult() { return new ExecResultBuilder(); } CommandResult commandResultFor(ExecResultBuilder builder, String... privateData) { - return new CommandResult(myLogger, "", builder.build(), new HashSet<String>(Arrays.asList(privateData))); + return new CommandResult(myLogger, "", builder.build(), new HashSet<String>(Arrays.asList(privateData)), new CommandSettings()); } private class ExecResultBuilder { @@ -159,6 +170,14 @@ private List<String> myMessages = new ArrayList<String>(); + public boolean contains(@NotNull String entry) { + for (String message : myMessages) { + if (message.contains(entry)) + return true; + } + return false; + } + public void assertLogMessagesDontContain(@NotNull String... strs) { for (String s : strs) { for (String message : myMessages)