0

My principal problem is how to find out whitch object type called specific method.

Is out there any solution that do no use stack trace ?

If not why such information are not avaiable ? it could be very helpfull.

Andrey Agibalov
  • 7,624
  • 8
  • 66
  • 111
  • That is a solution, but i dislike to use complicated thing to have simple functionality – Damian Leszczyński - Vash Sep 02 '11 at 23:01
  • 1
    Well, I won't call your problem a "simple functionality". It's quite a non-traditional feature, so solution is also non-traditional: you should either work with stack trace, or use AOP, I believe. The idea is, the information you want to have violates encapsulation - method call is a "message object receives", it's not a "message someone sent" (hope you understand what I mean) – Andrey Agibalov Sep 02 '11 at 23:16
  • @loki2302: Can you describe how OP would use AspectJ? – Ruan Mendes Sep 02 '11 at 23:20
  • possible duplicate of [In Java, how do i find the caller of a method using stacktrace or reflection?](http://stackoverflow.com/questions/421280/in-java-how-do-i-find-the-caller-of-a-method-using-stacktrace-or-reflection) – McDowell Sep 02 '11 at 23:29
  • @Juan Mendes: `aspect CallInterceptorAspect { before(): call(* *.*(*)) { System.out.printf("'%s' calls '%s'\n", thisJoinPoint.getThis(), thisJoinPoint.getSignature()); } }`. The only question here is how to pass this data to method that needs to know this information. But it's obvious. – Andrey Agibalov Sep 02 '11 at 23:30
  • @Vash: Please clarify in your question what you're accomplishing with this. It will help direct the answers. – Ben Zotto Sep 02 '11 at 23:34
  • @quixoto, just for test test purpose i would like to have that information, that good (good for me) object called some method. – Damian Leszczyński - Vash Sep 03 '11 at 08:16

3 Answers3

2

Is out there any solution that do no use stack trace ?

Basically, no. Certainly, there is no good solution that doesn't use exception objects and stack traces under the hood. (However, you don't need to parse the stack trace text. You can get hold of the array of StackFrame objects that contain the same information.)

In theory, you could avoid using the stacktrace mechanisms by passing an extra parameter to say who the caller is. However this is complicated and really messes up your code if you do it by hand, and problematic if you try to do it automatically.

If not why such information are not available ?

Because:

  • making the information available cheaply is going to cause ordinary method calls to be more expensive due to necessary changes to the method call/return "protocol",

  • in general, it is a bad idea for the behavior of a method to depend on what method called it, and

  • the stack trace mechanism does the job anyway, especially if you are only capturing the calling method for diagnostic / tracing purposes.

Stephen C
  • 698,415
  • 94
  • 811
  • 1,216
1

Throw an exception, catch it, then call the exception's getStackTrace() method which returns an array of StackTraceElements

http://download.oracle.com/javase/1.5.0/docs/api/java/lang/StackTraceElement.html http://download.oracle.com/javase/1.4.2/docs/api/java/lang/Throwable.html#getStackTrace()

Ruan Mendes
  • 90,375
  • 31
  • 153
  • 217
  • 2
    Using exceptions to control primary logic is a really bad idea. – Andrey Agibalov Sep 02 '11 at 23:11
  • So you think determining behavior based on who called a method is a good thing? I'm just answering the question. Hopefully the OP doesn't want to control flow based on who called the method. And this is not using exceptions to control flow, it's just using exceptions to know who called you! That's the Java approach, if you need to know the stack trace, you need to incur the cost of throwing an exception, instead of always making it available to the program. – Ruan Mendes Sep 02 '11 at 23:14
  • Well, my comment mostly for proposing AOP (AspectJ) as a "better" solution. I do agree, it's not a fact if what you propose or what I propose is better, just for me it looks like there's less hacking in applying AOP here. – Andrey Agibalov Sep 02 '11 at 23:22
  • @loki2302: I don't have much experience with AOP, that's why I'm asking how AOP could help the OP – Ruan Mendes Sep 02 '11 at 23:23
  • Also, it looks like your solution may work without involving exceptions here: `Thread.currentThread().getStackTrace()` – Andrey Agibalov Sep 02 '11 at 23:49
  • 1
    @loki2302: That's an illusion, `Thread.currentThread().getStackTrace()` throws an exception under the hood, see http://stackoverflow.com/questions/421280/in-java-how-do-i-find-the-caller-of-a-method-using-stacktrace-or-reflection – Ruan Mendes Sep 02 '11 at 23:59
1

If the method is yours, you may add a Object parameter in your method, to which you pass your calling class/object when you call the method.

For instance:

public class MethodClass
{
    public static void someMethod(int arg1, Object caller)
    {
        // should print "MyCallingClass":
        System.out.println("Calling class is: " + caller.getClass().getName());
    }
}
public class MyCallingClass
{
    public MyCallingClass()
    {
        //...
    }
    public void myCaller()
    {
        MethodClass.someMethod(123, this);
    }
}

Edit: replaced type of caller parameter in someMethod from Class to Object, so it should now work.

poplitea
  • 3,585
  • 1
  • 25
  • 39
  • If you're going to control the behavior of the method based on who calls it, this may be the least hackish way! – Ruan Mendes Sep 02 '11 at 23:16