cancel
Showing results for 
Search instead for 
Did you mean: 

Multi-threaded creation of users in MDM repository problems (.Net API)

Former Member
0 Kudos

<<Text removed by moderator>>

I am working with a highly multithreaded application which wants to create users in bulk or one at a time as they are requested. Imagine a system which takes bulk uploads (in parallel) of user creation requests and tries to create them as fast as possible.

I have code that works, but I am thinking that I am not doing this in the best way possible. Basically, I find that I have to try to create the record up to 10 times, and if all 10 attempts fail, then give up. This seems very expensive and error prone.

I think the problem is that I don't really follow how the "ChangeStamp" stuff works, or why it is even required. I understand the concept of getting a unique key for an insert statement for parallel processes, but surely MDM offers a better way to insert a user to a repository?

When I run the below process, 5 at a time, normally, one of the processes will fail with the below error.

com.sap.mdm.commands.CommandException: com.sap.mdm.intern.protocol.manual.ServerException: MDM repository data is out-of-date or is locked by another MDM Server. Refresh the data and try the operation again. If the error persists, contact the system administrator. [0xffab4128]
   at com.sap.mdm.intern.protocol.manual.AbstractProtocolCommand.execute(PassportSupport passportSupport)

So, my questions are this:

1. Is "InChangeStamp" really required? If so, why?

2. If so, am I getting the InChangeStamp the best way possible? Executing a GetUserListCommand seems like a very expensive and risky way to get a value just to add a user record?

The code:

//  Get a u201Ccontextu201D, whatever that is?
RepSessionCtx = new RepositorySessionContext(u201CServeru201D, u201CRepositoryu201D, u201CUseru201D);

// Get an actual session connection 
RepSession = SessionManager.Instance.createSession(RepSessionCtx, SessionTypes.REPOSITORY_SESSION_TYPE, u201Cpasswordu201D);

// Get a CreateUserCommand 
CreateUserCommand cmd = new CreateUserCommand(RepSessionCtx);
cmd.Session = RepSession;

// Set the user
cmd.User = newUser;
cmd.User.setPassword("PASSWORD");

// Get a new user ID for the command
UserId uid = cmd.getNewUserId();

// Get a valid InChangeStamp <-- not sure what exactly InChangeStamp is? 
GetUserListCommand userListCmd = new GetUserListCommand(mSession.RepSessionCtx);

//Console.WriteLine("outer attempt " + i);
for (int i = 0; i < 10; i++)
{
try  // Try very fast up to 10 times to get a unique valid inchangestamp
{
userListCmd.execute();
cmd.InChangeStamp = userListCmd.getChangeStamp();

cmd.execute();

userCreated = true;
break; // Successful
}
catch (Exception ex)
{
Console.WriteLine(ex.Message);
//Console.WriteLine("Could not create the user at " + i);
}
}

Edited by: Wardell Castles on Nov 4, 2010 3:10 PM

Edited by: Matt on Nov 10, 2010 4:30 PM

Accepted Solutions (0)

Answers (1)

Answers (1)

Former Member
0 Kudos

Ok, I think I can narrow this down to a more simple question:

I have a highly threaded application where multiple threads are trying to create users. In each thread, I get a repository session, and within the thread try to create the user like below:


RepSessionCtx = new RepositorySessionContext(u201CServeru201D, u201CRepositoryu201D, u201CUseru201D);
RepSession = SessionManager.Instance.createSession(RepSessionCtx, SessionTypes.REPOSITORY_SESSION_TYPE, u201Cpasswordu201D);

CreateUserCommand CreateUsercmd = new CreateUserCommand(RepSessionCtx);
GetUserListCommand userListCmd = new GetUserListCommand(mSession.RepSessionCtx);

userListCmd.execute(); // <-- THIS SEEMS LIKE A VERY BAD WAY TO GET A CHANGESTAMP TO CREATE A USER?!
CreateUsercmd.InChangeStamp = userListCmd.getChangeStamp();

CreateUsercmd.execute(); // <-- ERROR THROWN HERE!!!

It seems that my CreateUsercmd will not run, because some other thread has grabbed its ChangeStamp before it runs?!

The error is:

com.sap.mdm.intern.protocol.manual.ServerException: MDM repository data is out-of-date or is locked by another MDM Server. Refresh the data and try the operation again. If the error persists, contact the system administrator. [0xffab4128]
   at com.sap.mdm.intern.protocol.manual.AbstractProtocolCommand.execute(PassportSupport passportSupport)

But if I try to run the above code in a loop, say 10 times, it normally will end up working.

What do I do to create a user reliably in my thread?

Former Member
0 Kudos

Hi,

Please let me know if you were able to fix this issue and how did you fix it ?

Thanks,

Vinit Pugaliya