function readOnly(count){ }
Starting November 20, the site will be set to read-only. On December 4, 2023,
forum discussions will move to the Trailblazer Community.
+ Start a Discussion
chris_centrachris_centra 

context across transactions, SOQL - FOR UPDATE, test coverage...

Hello.  i started a thread a few weeks ago regarding an issue where round robin assignment was failing when two nearly-simultaneous transactions would grab the same User for assignment (https://developer.salesforce.com/forums/ForumsMain?id=906F000000094RQIAY).  a solution that works for me (in theory at least) is to use the FOR UPDATE clause in my SOQL - along with a bit of error handling to confirm that no two threads will assign the same user.   so i've updated my code - but: is it possible to write test coverage for it?  

in my test coverage, i know ahead of time which user will be assigned via the round robin, so i do a FOR UPDATE query on that record - then i start the normal flow of the code.  however my test kept failing.  after much frustration, i believe i've found the issue explained in the documentation: "While the records are locked by a client, the locking client can modify their field values in the database in the same transaction."  My problem is (i think) that in my test coverage, i'm always the same "client."  

So my question is: is there a way to be a different client in a test coverage method?

thanks for your time.
chris
Ashish_SFDCAshish_SFDC
Hi Chris, 

See which lines of code the test is not covering and if there is some code that the test example is not part of then you have to give another sample record that will pass through those specific lines of code. 

There is a code sample and similar discussion in the below link, 

https://developer.salesforce.com/forums?id=906F000000091RWIAY

Regards,
Ashish
chris_centrachris_centra
Hmmm, i appreciate your response, but maybe i'm not explaining my issue clearly.  i have no trouble getting the required code coverage.  my problem is that i'm not sure i'm able to create the scenario required to test the FOR UPDATE clause in SOQL.  the essense of the issue is that the FOR UPDATE clause requires two "clients" - but in test coverage, i don't know how to simiulate multiple clients?
thanks
chris
Ashish_SFDCAshish_SFDC
Hi Chris, 


Hope this solves the puzzle. 

Apex test class to simulate two users !
Create an Apex test class that tries to simulate the same using System.runAs().

My use case(scenario) was to create a test method in this class that :

Creates an account from the logged in user.
Query that same account back using “for update”.
Start new context using “System.runAs()” from some other user i.e. not the logged in user.
Try updating the same locked account, using that other simulation user.
Here is the apex test class, if you want to experiment.


public class TestRecordLocking {
  testmethod public static void testLocking() {
    // create a account from logged in user
    Account accoutU1 = new Account(Name = 'Abhinav Gupta');
    insert accoutU1;
    // lock the same account  
    accoutU1 = [Select Id, Name, Website from Account where Id =:accoutU1.id for update];
    
    //Start updating it
    accoutU1.website = 'www.salesforce.com';
    
    // Now lets say, some other user comes and tries to update the same record
    User u2 = [Select Id from user where id !=:UserInfo.getUserId() limit 1];
    System.runAs(u2) {
      // other user queries the same account
      Account accountU2 = [Select Id, Name, Website from Account where Id =:accoutU1.id ];
      // other user tries to update it
      accountU2.WebSite = 'www.yahoo.com';
      update accountU2;    
    }
    
    // Now update the original account back.
    update accoutU1;  
  }
}
Expected Result on Executing this Apex Test ?
It should fail, isn’t ? As I am trying to update record locked by some other user. Unfortunately it works like a charm. I believe, System.runAs() is not creating exact multi user context that might be created in real life ?

http://www.tgerm.com/2011/04/visualizing-record-locking-in-soql-ie.html


Regards,
Ashish
chris_centrachris_centra
confused by your answer.  you say, "hope this solves the puzzle" - but at the end you say it doesn't solve it, right?  yes, i can simulate two users, but the docs say different "clients" - so i don't think this helps me.  thanks for your time.
chris
Ashish_SFDCAshish_SFDC
Hi Chris, 

If the scenario is to simulate two users at the same time then the above snippet should work. 

I did not quite understand two clients, can you share the documentation where this was mentioned?

Regards,
Ashish
lawreplawrep
Hi Chris,
Has been a while but wonderd if you found a solution to this at all? I have the same problem.
Thanks,
Paul
chris_centrachris_centra
I'm afraid I have not found a solution to this. I've been meaning (for a long time) to create a simple version of the code that shows the issue so that I can submit a support ticket, but I have not yet. If you figure it out, please send me an update!! thanks chris