33

To enable logging for apache commons HttpClient in normal Java application I used:

System.setProperty("org.apache.commons.logging.Log", "org.apache.commons.logging.impl.SimpleLog");
System.setProperty("org.apache.commons.logging.simplelog.showdatetime", "true");
System.setProperty("org.apache.commons.logging.simplelog.log.httpclient.wire", "debug");
System.setProperty("org.apache.commons.logging.simplelog.log.org.apache.commons.httpclient", "debug");

But on android I don't see logs in LogCat.

Am I missing some thing?

skaffman
  • 390,936
  • 96
  • 800
  • 764
alex2k8
  • 41,158
  • 56
  • 165
  • 218

4 Answers4

65

Ignore my earlier comment. I found the solution on the org.apache.http logging page. Your original answer was referring to httpclient-3.x logging, and the working code for recent versions comes from http-components logging

java.util.logging.Logger.getLogger("org.apache.http.wire").setLevel(java.util.logging.Level.FINEST);
java.util.logging.Logger.getLogger("org.apache.http.headers").setLevel(java.util.logging.Level.FINEST);

System.setProperty("org.apache.commons.logging.Log", "org.apache.commons.logging.impl.SimpleLog");
System.setProperty("org.apache.commons.logging.simplelog.showdatetime", "true");
System.setProperty("org.apache.commons.logging.simplelog.log.httpclient.wire", "debug");
System.setProperty("org.apache.commons.logging.simplelog.log.org.apache.http", "debug");
System.setProperty("org.apache.commons.logging.simplelog.log.org.apache.http.headers", "debug");

and properties:

adb shell setprop log.tag.org.apache.http VERBOSE
adb shell setprop log.tag.org.apache.http.wire VERBOSE
adb shell setprop log.tag.org.apache.http.headers VERBOSE

The difference is in the logging tag names.

blahdiblah
  • 32,000
  • 21
  • 97
  • 150
Joe
  • 41,698
  • 13
  • 44
  • 61
  • 1
    Have you been able to get context logging to work? I tried extending your solution with similar lines for the org.apache.http.impl.client logger, but I'm not seeing anything from classes in that package or subpackage. I do get the wire and header logging however. – gnuf May 11 '11 at 16:49
  • Seriously. Thank you for this. – Lo-Tan Jan 18 '13 at 01:16
  • works great! This definitely needs to be the accepted answer. – Chad Schultz May 09 '13 at 21:03
  • @joe - Why do you need to set the adb shell properties? – AlikElzin-kilaka Feb 18 '14 at 10:08
  • Also, to see the headers, only this line was needed: `java.util.logging.Logger.getLogger("org.apache.http.headers").setLevel(java.util.logging.Level.FINEST);`. I didn't need to set any java system property. – AlikElzin-kilaka Feb 18 '14 at 10:12
  • The lines were just showing what *could* be set if you want parts of the logging. If you only need one of the log tags, then you only need to set that one. The setprop is used for making sure that the "httpclient.wire.header" tag gets logged. If you wanted to change the log behavior (or disable the log entirely), you could use that command to change the level at which logcat will show those logs. – Joe Feb 18 '14 at 22:11
  • Are you suggesting that we hard-code this into the application? Surely the whole point of setting this outside the app is so the logging is configurable! Please would you explain what you are doing in more detail or better yet, provide an example on github? Thanks! – Alex Worden Jun 17 '15 at 21:25
9

Here is a solution (without digging into details)

Console:

adb shell setprop log.tag.httpclient.wire.header VERBOSE
adb shell setprop log.tag.httpclient.wire.content VERBOSE

Code:

java.util.logging.Logger.getLogger("httpclient.wire.header").setLevel(java.util.logging.Level.FINEST);
java.util.logging.Logger.getLogger("httpclient.wire.content").setLevel(java.util.logging.Level.FINEST);

Test:

java.util.logging.Logger.getLogger("httpclient.wire.content").log(java.util.logging.Level.CONFIG, "hola");
alex2k8
  • 41,158
  • 56
  • 165
  • 218
  • 1
    I tried this in my app, and am not seeing any log messages delivered from the HttpClient. Does this work using the HttpClient that is in the current SDK? That is, org.apache.http, vs org.apache.commons.http. I do see the test log message ("hola" in your example), but nothing from the HttpClient calls. – Joe Jul 21 '10 at 18:46
  • 1
    with recent SDKs you need to use prefix used in the first response, "org.apache.http" instead of "httpclient", at least this worked for me on a 2.1 Device. – HefferWolf Jun 14 '11 at 12:16
  • @alex2k8 - Why do you need to set the adb shell properties? – AlikElzin-kilaka Feb 18 '14 at 10:14
  • Do you happen to know if there's a way to see MORE detail than what you get with enabling DEBUG mode on the wire? Like low level TCP information? – Kevin M May 12 '15 at 17:50
3

You just need to use

java.util.logging.Logger.getLogger(yourFullClassName).setLevel(java.util.logging.Level.All);

and

adb shell setprop log.tag.correspondingTag VERBOSE

Android use this function to get correspondingTag from class full name:

public static String loggerNameToTag(String loggerName)
  {
    if (loggerName == null) {
      return "null";
    }

    int length = loggerName.length();
    if (length <= 23) {
      return loggerName;
    }

    int lastPeriod = loggerName.lastIndexOf(".");
    return length - (lastPeriod + 1) <= 23 ? loggerName.substring(lastPeriod + 1) : loggerName.substring(loggerName.length() - 23);
  }

so for example,I want to enable logging for “org.apache.http.impl.client.DefaultRequestDirector” class,do such things below:

String clzName = "org.apache.http.impl.client.DefaultRequestDirector";
String newClzName = loggerNameToTag(clzName);
System.out.println("className:" + clzName + " tagName is " + newClzName);    //get tagName from class full name,and then it will be used in setprop
Logger jdkLogger = Logger.getLogger(clzName);
jdkLogger.setLevel(Level.ALL);
if (jdkLogger.isLoggable(Level.FINE))
{
        jdkLogger.log(Level.FINE, "jdk log msg");    
        jdkLogger.log(Level.Fine,"tagName is")
}

And then in adb shell

setprop log.tag.DefaultRequestDirector VERBOSE
nut
  • 345
  • 2
  • 13
3

The devil is in the details. I'm running the 2.3.3 emulator and got it working with:

java.util.logging.Logger.getLogger("org.apache.http.wire").setLevel(java.util.logging.Level.FINEST);
java.util.logging.Logger.getLogger("org.apache.http.headers").setLevel(java.util.logging.Level.FINEST);

and in the adb shell

# setprop log.tag.org.apache.http.wire VERBOSE
# setprop log.tag.org.apache.http.headers VERBOSE

Thus it seems the log specifiers are different.

Michael
  • 31
  • 1