I'm looking for confirmation that what I'm seeing is real, and if this is a bug or an intentional breaking change.

Create the following test class:

public class TestLimits{
    public static testmethod void test1()
        for(Integer x = 0; x<100000; x++);
        system.debug(LoggingLevel.Info, 'Script limits: ' + Limits.getLimitScriptStatements() + ' Script Statements ' + limits.getScriptStatements());

On Winter 14 or earlier, you'll get:

Script limits 200000 Script statements 0

On Spring 14 you'll get:

Script limits 200000 Script statements 200000

Yes, I know that script limits no longer apply... but...

The problem is that any existing application that uses the limits statements to decide if it is safe to run (to avoid exceeding limits) will fail - as it thinks it has already exceeded limits.

Worse - this change impacts code that is running on older version APIs.

Thoughts? Comments? Help!!!

  • 2
    It looks like they are changing the behavior of this method - the spring 14 docs are different from winter 14 - but they did not version the change. So any code running on an older API can break! – kibitzer Feb 11 '14 at 22:00
  • An additional minor annoyance is that the debug log now says "Number of code statements: 200000 out of 200000 ******* CLOSE TO LIMIT" all the time. – David Cheng Feb 12 '14 at 1:33
  • Agreed. This could be a big deal. – Steven Herod Feb 13 '14 at 11:39

Josh Kaplan just tweeted a blog post explaining that this functionality is changing, and explains the issue quite well.

Essentially, Salesforce is going to change the return value of Limits.getScriptStatements() to be % of CPU limits used * script statement limit, as a way to continue to control flow, while giving a rough estimate of overall limits, leveraging the new CPU Limits.

Josh warns:

Please keep in mind that this number is not what it says it is. It is NOT the number of statements. It is a representation of what the statement count might have been, relative to your limit. It will, in nearly every situation, undercount the number of statements done. The intention with this mimicry is to allow your code to probably do what it used to do without an immediate failure.

  • It's a good post and I think a very sound solution to the problem. – kibitzer Feb 15 '14 at 9:08

Salesforce have issued via the Partner Portal an update (shown below), it talks about the method being depreciated but does not really be all that clear on the change in behaviour (though the Apex docs do elaborate). A better approach would be to make it platform API version driven i also agree.

Though i can imagine that internally retaining the statement calculation is proving difficult (and ironcailly consuming CPU itself perhaps?). That said it's clearly having an impact for those that have been using it to implement code path decisions (e.g. batch vs interactive) or better end user facing messages.

Salesforce Recommendation The recommendation from Salesforce (in the docs below) is to move to using the new CPU limit methods, however these are non deterministic so be aware of this. Personally my advice is if your looking to manage limits and split code paths accordingly, try to calibrate the decision around something that is end user facing and deterministic, such as the type of filter they enter, the number of rows or a custom setting to allow for calibration in the subscriber org.

Tests that Test Governor Limit Variance. I will miss being able to assert on a level of tolerance in the statement limit consumption being breached in test scenario, i'm not convinced using CPU limit in this case will be stable enough, so for these tests designed to "test" the codes consumption of platform resources it looks like another solution needs to be found in respect to CPU time at least.

Hopefully Saleforce will take a look at this feedback and give further thought to this change and how to give some facility to allow developers more time to phase it out of their code...

enter image description here

The link shown in the image is here.

The Apex Developer guide now shows this...

enter image description here

  • I have noticed doing CPU limits testing (when trying to optimize my code) that on a class before optimization: (1) measure CPU time as C0, (2) change code to optimize and remeasure CPU time as C1; and (3) run again without further optimization and measure CPU time as C2. Frequently, I would see C2 < C1; C2 < C0 but C1 > C0. That is, the results of the optimization might not really be known until you had done two runs - whether this is do to with caching of the compiled code or Sobjects, I could not decide. Point being that CPU measurement on two identical runs yield different results. – cropredy Feb 13 '14 at 17:19
  • Yes - I saw that. I have no issue with the change itself. I have an issue with the fact that it isn't versioned. The fact that this change is applied automatically to code running on older APIs means that they are expecting everyone to audit their existing code base, and all package vendors to release updates, and have all customers deploy those updates, by this weekend when NA1 transitions to Spring 14. This obviously isn't going to happen. This is why I believe it is a serious problem. – kibitzer Feb 13 '14 at 17:41
  • Yep as i said in my answer, i agree with that perspective as well, just thought I'd also clarify the current documentation and Salesforce recommendations for others viewing the question. I've also given the Salesforce PM a heads up on this discussion btw. – Andrew Fawcett Feb 13 '14 at 18:12
  • Thank you! Great points and I always appreciate references to the documentation. – Christian Anderson Feb 13 '14 at 19:38
  • Hopefully the Salesforce PMs are getting an earful about this one. It's exactly for this reason that API versions exist :-) – kibitzer Feb 13 '14 at 22:43

I'm confirming I see the same behavior.

My two sandboxes that were upgraded to Spring '14 over the weekend are returning 200000 when executing:

System.debug('Script Statement Limit: ' + Limits.getScriptStatements());

My Winter '14 sandbox and my Winter '14 Production Org are returning '1' when executing the above statement.

The code I maintain throws exceptions in several spots if Limits.getScriptStatements() goes above 190000. As you may have guessed, I'm getting exceptions thrown throughout the code. Thanks to my coworker for finding this in her newly updated sandbox. Otherwise, we probably wouldn't have caught it as strangely my Sandbox isn't due to be updated to Spring '14 until after our Prod instance.

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service, privacy policy and cookie policy

Not the answer you're looking for? Browse other questions tagged or ask your own question.