7

When trying to execute a static method from an instance of a class

testMe tmp = New testMe();
tmp.myStaticMethod('a','b');

we get the familiar:

Static method cannot be referenced from a non static context: void myStaticMethod(Id, String)

However if the class implements an interface, instantiating a new instance of that that interface allows us to execute the static method passing in the parameters

Is this expected / documented?

global interface testIt{
    void myStaticMethod(String a, String b);
}

global class testMe implements testIt{

    global static void myStaticMethod(String a, String b){
        system.debug(a + ' - ' + b);
    }

}

The following executes just fine

System.Type apiMethod = Type.forName('ns', 'testMe');
testit tmp = (testit)apiMethod.newInstance();
tmp.myStaticMethod('a','b');

17:03:46.25 (12026653450)|USER_DEBUG|[171]|DEBUG|a - b

I was expecting that the static instance would not be able to be called but it allows me to. If this is expected great, I will go ahead and use it but if it is not expected I would prefer not to package something I cannot reverse....

I suspect it has to do with the interface since the interface method is not static rather the implementation of it is static in the class. To test the theory I tried this and it executed just fine without complaining about the static method

testIt tmp = (testIt)(New testMe());
tmp.myStaticMethod('a','b');

All answers appreciated but especially thankful if there is some documentation that can be pointed to

1
  • 1
    Sneaky stuff!!! Commented Aug 8, 2017 at 2:24

2 Answers 2

2

You shouldn't depend on the behavior. The documentation states:

A class static variable can’t be accessed through an instance of that class. If class MyClass has a static variable myStaticVariable, and myClassInstance is an instance of MyClass, myClassInstance.myStaticVariable is not a legal expression.

You should always declare methods as instance methods, just to be safe.

3
  • Its not a variable it is a method. The static method (required by the interface) is part of a class that implements the interface. The method in the interface is not static (can't be). Maybe the interface method redefines the class implementation (static modifier) of that method??
    – Eric
    Commented Aug 8, 2017 at 1:21
  • @Eric The documentation for static nor interface is oddly silent, but the fact that you can't access the methods through direct compilation should be a red flag. I'll ask some of my contacts I have access to if it should be allowed or not, but I would seriously recommend not doing it, because if it's not in the documentation, it's not supported.
    – sfdcfox
    Commented Aug 8, 2017 at 1:42
  • Yea, thats why I asked. Eager to hear what you find out. And thanks btw
    – Eric
    Commented Aug 8, 2017 at 1:46
0

This is an old question but I just want to make it clear for everyone wondering if it was designed like that or not.

That is another weird behavior of Apex. The thing is, this should not be allowed at all. You should not be able to implement an interface using a static method, that simply doesn't make sense.

This is a bug.

Even if you try to make that static method @Future and then call it from the instance as you did in the example, Apex will ignore it and execute that method synchronously. And no, this case is not documented by Salesforce, as far as I could see on the Internet.

You must log in to answer this question.

Not the answer you're looking for? Browse other questions tagged .