开发者

How to force all Java classes to have a attribute

I want all Java classes to have a logger variable:

private static final Logger logger = Logger.getLogger(Foo.class);

B开发者_开发百科ut I have to type this line in all classes.

Is there to way to automate this? Can annotations help me in this?


I guess what you really want in not inheritance. In fact inheritance is a rather bad way to incorporate a logger IMHO, as a logger is not genuinely a feature of a class but rather a cross-cutting concern of the application.

What you need is an adapted new Class template. If you are using eclipse, you can find it in the Preferences under Java->Code Style->Code Templates then switch to the right side of the dialog and select Code->New Java files

In intellij idea you can find the templates under File->Settings->File Templates->Class

The accepted answer to this question demonstrates incorporating log4j logging in a template, complete with import statements.


If you'd like to go the inheritance way, which is IMHO not very good, you could inherit from an abstract base class where a protected non-static Logger is declared like this:

protected final Logger log = Logger.getLogger(getClass().getName());

This way the logger's class will be of the implementing class. But of course there's the problem with Java allowing only single inheritance which might get you in trouble when you need to extend another class.

I, personally, am using AOP (Aspect Oriented Programming) for logging but it's not always a solution.


If you're using Eclipse, make a new Code Template for Java classes. This will add a logger reference in every new class, including the appropriate import. Adapt the import if you're not talking about log4j.

How to force all Java classes to have a attribute

And then

How to force all Java classes to have a attribute


Is there to way to automate this?

Certainly not in plain Java.

Inheritance won't solve this problem ... if you want a field that is static and/or private. The closest you could come is adding a method like this to a base class:

    protected final Logger getLogger() {
        return Logger.getLogger(this.getClass());
    }

and that's going to be rather expensive.

Alternatively, you could add a non-private, non-static field to a base class; e.g

    protected final Logger log = Logger.getLogger(this.getClass());

Or you could get your IDE or some source code processor / generator to add a static private Logger field to the source code of each class.

Can annotations help me in this?

I don't think so. You might be able to inject a field using AOP, but I don't think your code would be able to refer to it.


use inheritance

inheritance might help you


Well, what you could do is to create an abstract parent class that owns this logger variable and each of your classes inherits from this class. But as in java there is only a single inheritance allowed, you might get into trouble because the inheritance is blocked by your parent class.

Second problem is: the logger will always be initialized with the class of the abstract parent class. If this doesn't bother you ....


Learn Dependency Injection, use a framework like Seam (including Weld), Spring or Guice and then use aspect oriented programming (AOP) to automatically log all called methods (and optionally how long that method take).

There are cases where you 'll still want to define the Logger and do some logging inside some methods, but still the AOP approach will remove a lot of your boilerplate code that violates the DRY (Do not repeat yourself) principle.


A very primitive solution would be to create an abstract class containing the attritbute you want to add to all your classes. But since java does not support multiple inheritance this solution is not suitable if you need to inherit from other classes.
As far as I know, annotations are not designed to provide such functionality.


Don't do any of this, it's overengineering. Just put a separate logger in each class that needs logging and be done with it.

As a small hack you can leave out the 'private' (making the logger package protected) to avoid the pesky Eclipse 'unused' warnings when there is currently no line of code using your logger, without having to add a SuppressWarnings annotation.


Your classes should inherit this from a common base class.

I'm no Java guru but something like should be possible

public class Vehicle
{
    protected Logger logger = Logger.getLogger(this.getClass());
}

public class Car extends Vehicle
{
}

That's how it could be done in C# - it's been ages since I last used Java.

0

上一篇:

下一篇:

精彩评论

暂无评论...
验证码 换一张
取 消

最新问答

问答排行榜