- Feature Articles
- CodeSOD
- Error'd
- Forums
-
Other Articles
- Random Article
- Other Series
- Alex's Soapbox
- Announcements
- Best of…
- Best of Email
- Best of the Sidebar
- Bring Your Own Code
- Coded Smorgasbord
- Mandatory Fun Day
- Off Topic
- Representative Line
- News Roundup
- Editor's Soapbox
- Software on the Rocks
- Souvenir Potpourri
- Sponsor Post
- Tales from the Interview
- The Daily WTF: Live
- Virtudyne
Admin
Just because I said you need it doesn't mean I necessarily know what it is.
But for production use, you need something fast, too, which means it won't be cheap. (RFC 1925.2.7a)
Admin
Unix standard logging uses seven levels. Not a big improvement, but I've seen it replicated more places than I've seen any other type of logging levels. I've even used it myself a few times, when the need for debug logging wasn't much.
The next most common logging I've seen uses a bitstream to determine what is logged and what isn't. Of course, I haven't seen any standard logging package that does this; it's just a design pattern I've seen a lot of places. I use it for most of my own code.
For all log levels higher than debug, I agree. For debug, most should probably be in the programming domain - however, probably farther down the bitstream than most people need to go. (For example, one program I wrote uses bits 0, 1, 2, and 3 for debugging in the application domain. 4, 5, 6, 7, 8, 9, and 10 debugged various programming domain features. 11 and 12 reported hardware/OS details.)
That having been said, enter/exit debugging should only be used on complex functions. One to three line routines should probably only have an enter debug line, if they need even that much. (Exception: if the routine consists of a single if statement with no else clause, it may make sense to add another debug line - but I'd generally do it by adding an else clause and debug the 'and nothing happened' part, rather than an exit line.)
I'd comply with a group coding standard if one instructed otherwise, because I know the cost of an if not taken is very low. However, I would at least let it be known that I felt it was overkill for such simple functions.
Admin
It doesn't necessarily take complexity. Say they use an OOP style. Say they follow the 'abstract everything' anti-pattern. Say their library vendors have done the same. Repeat a few times. Now, imagine that many of these 'vendors' are actually different in-house groups which have the same programming requirement.
Oh, and I forgot to mention, they're all OOP purists, so there's no direct use of any member variables outside of getters and setters, and every unit of work which is conceivable to reuse elsewhere is a separate method, even if it's not actually used. (That is, most methods end up being about 5-8 lines, including the logging lines, return statement, and so forth.)
And finally, remember: he didn't say that the logging added 5 minutes, but that the total time was 5 minutes. While they should be the same thing, within a margin of error, they may not be - I've seen some ATMs which took close to a minute to dispense cash. (Of course, for all I know, they were logging every function, method, and subroutine entry and exit too.)
Admin
Admin
Ditto here, have seen this live.
Admin
Isn't an architect someone who "designs" architecture? He doesn't "architect" architecture. Right?
OK, OK, the dictionary does indeed include architect as a verb, but it sure sounds weird to me.
Admin
WTF?
duh... here i am trying to read a funny WTF article and some loser lowers the tone with his boring dribble.
yawn.
Admin
So the real WTFs :- Walter used DEBUG when he should have used FINEST. Walter rolled his own rather than just let AOP handle it.
Admin
FINE - Stuff that is rarely useful for the support team but the developer may need every now and again.
FINEST - Worthless shit the developer /thinks/ he needs when he is completely confused as to what the hell is going on. Turned off 99.999% of the time. Only enabled when the unit tests work gosh darn it. What the hell is going on!?
Admin
TRWTF is that the setter doesn't log the parameter.
Admin
Secondly, if the JVM is too high level then you must mean that logging should be at the processor level. That's certainly the lowest level, but I think it's so fine-grained as to be completely useless.
That's not OOP purism: it's completely misunderstanding encapsulation. But that's a completely separate rant.Admin
That depends, I would say :-) Wouldn't be doVeryImportantBusinessLogicStaff() then a side-effect I rely on when doing logging just for informational purposes? Not that this could never happen, as we all know ;-P
Admin
Surely "dictionaried the verb 'architect'"
Admin
You mispelled "Kill me." ;-)
Admin
if(this == null) logger.error("Null reference");
Admin
I'm working on a project right now that has this pattern everywhere in its data access objects, and I am not allowed to remove it.
Fortunately, I was at least allowed to update it, so inconsequential things are logged at log4j info level, and moving the errors that actually mean something to the warn, error, and fatal levels.
Oh, and log4j is set to only log error and fatal level errors.
Admin
Yes, yes, if there's ONE pointless message repeated endlessly in the log files, you could grep -v it out. But what happens when there are dozens? I suppose I could write a script to grep -v out all the junk. But then, our log files role over every day at 4:00 am, and they are still hundreds of MB long. Just opening a log file in vi takes forever.
Admin
Clbuttic!
Admin
From the point of view of the application domain, I'd like to see "related to the comms stack," "parse error," and "DB error." Or suchlike. Easy to do if 0x00000001, 0x00000002 and 0x00000004 are used as "levels." Bonus! You can OR them together! (As you know.) You can also write a trivial filter to collect the results.
As far as I can see, there's no reason to treat the "debug" level differently. (I'd like to associate this with your comment lower down, but I'm running out of patience with the site parentheses.)
Which is where we disagree, I guess. Entry/Exit logging should never be used. It's irrelevant to the problem/application domain, and a fuckton of low signal/noise output for the programming domain. As far as I'm concerned, it's cargo-cult logging ... I've seen it a thousand times, and I've never seen it work once.Like the Robert Frost allusion with "the if not taken..."
Apologies to pjt33, btw. I committed the cardinal sin of engaging fingers before brain. My (very) bad.
Mind you, it's not like any of us disagree in any fundamental way. A sensible approach to logging is far more important than the average PHB (or, these days, Junior Designer) will ever comprehend.
Perhaps there is a best-selling book in this.
Admin
I see so many slow Java apps because of silly things like this - Use SAN, log to a separate filesystem, there is a world of difference between a development Windows system with a "C:" drive and a UNIX system with SAN, active/active multipathing, and all sorts of features that simply do not seem to ever get mentioned to Java developers. These devs then see nothing wrong with logging to the same place as the data, or similar evils.
I still doubt that a 40% speedup was achieved just by removing the logging as mentioned, though - there must be more to the story than what we have been told.
Admin
Blah, blah. I read dkAllen's part twice (the second time after your post), and I still fail to see where he suggested logging into the database. Or, to put it in a way more appropriate to you:
Learn to read.
Learn to read.
Admin
Admin
I told him repeatedly how stupid that is (especially on production systems), but he never get out of that habit.
The fact that he left the team largely improved the code quality of our project.
Admin
OK, I'll: what's so brain-dead about severity levels? And why are the standard logging packages so dumb?
You have logs for at least three different purposes:
You seem to focus on the audit purposes. Well and good, but 'logging' serves multiple concerns. Otherwise, we seem to be in agreement. And Amen! to your concluding remark -- I'll help hold them down, and possibly set the knobbly things on fire once inserted.
To conclude: the WTF is leaving DEBUG turned on in production, across an entire application, without the excuse of ongoing fault isolation. Not exactly a world-class WTF, that; I've helped track down much worse config problems caused by development and test configurations infecting production environments. Logging getters and setters is at worst a mild annoyance, especially if decent log filtering is supported.
Admin
Clogged, even.
Admin
Admin
Admin
Yeah, we do that at my current job. It's more often:
Admin
lol that is obviously a bit daft, but the common pattern
avoids the call to complexDataModel.toString() and the subsequent string concatenation, the pattern itself is not a WTF.
Admin
The real WTF is that, if he really did want that sort of logging, why he didn't just roll a bit of AOP code to do it
Admin
Yep, you are right..
Also, in C/C++ you probably need the macro to get the FUNCTION and LINE thingy from the preprocessor.
My daily WTF is something like dudes saying. "I am a programmer. I can only program in java" .. hahahah
Admin
AOP, anyone?
Admin
@Sam
If your log message is of the form:
logger.debug("[method] X: " + x + ", Y: " + y");
then you wrap it in
if (logger.isDebugEnabled()) { logger.debug("[method] X: " + x + ", Y: " + y"); }
to avoid the StringBuffer/StringBuilder creation for the arguments, because Java doesn't do lazy evaluation, although this is a great example of where it would be useful.
Only if you have something like:
logger.debug("[foo} I am at HERE!!!");
should you not wrap with the check, even though the method itself includes the check.
Admin
If you're writing Java code there really is no reason why there should be much (if any) actual logging code directly visible in your source code. The easiest way to do this is to use Aspect Oriented Programming, like AspectJ for instance, which can "leave" the logging code where you need it as defined by the join points. The entire "method start, method end" type of logging could handled by a simple pointcut like: execution(* ()), which matches every return type or every class of every method with any parameters (that's what those asterisks mean).
Anyway, just read the article on http://en.wikipedia.org/wiki/Aspect-oriented_programming to get an idea of what this means.