Briefcase as a service

if you include Qty into BusinessProcessor.UserUpdateFields, update SQL will be generated like

update ..
set ...
where
  (pk = :pk) and (Qty = :Qty)

in this case, update from app2 won’t be applied. you can detect and handle it

Can I have BusinessProcessor.UserUpdateFields on client side, let say app1 can generate and set BusinessProcessor.UserUpdateFields = to app1_Qty field?
That will be very neat.

no, BusinessProcessor is server-side things.

If you like to identity what application performs update, you can easily pass this information via LoginString in LoginEx method:

  IBaseLoginService = interface(IROService)
  ['{C349DB54-9DFB-454E-AD23-6F2166A624A6}']
    function LoginEx(const aLoginString: ROUTF8String): Boolean;
    procedure Logout;
  end;

UpdatedBy field can be added as well.
and may be with script on server side, if I can engineer custom update based on new UpdatedBy data and use it on “beforeProcessDeltaChange” or may be it should be “afterProcessDeltaChange” :

function beforeProcessDeltaChange(delta, deltachange, wasRefreshed, canRemove)
	{
if (inLocalAccess)
		return;
		
	inLocalAccess = true;
	
	try
	{
    var itemId = change.newValues['Id'];
    var userId = change.newValues['UpdatedBy'];
	var oldValues = { Id: itemId };
    if (userId = 1)
	    var newValues = { Id: itemId , App1_Qty: App1_Qty };
    else if  (userId = 2)
        var newValues = { Id: itemId , App2_Qty: App2_Qty };

        lda.update ( 'Products' , oldValues, newValues);
        lda.applyChanges();
	}
	finally 
	{
		inLocalAccess = false;
	}
}

You can put any value into Session and read that value in this method

“afterProcessDeltaChange” might be the right way to go, if there is no function like “insteadProcessDeltaChange”

we have only before* and after*

Sorry : does “beforeProcessDeltaChange” working as “Instead” on update or data posted in this function will be overwritten by during Processing DeltaChange ( if app applying updates to the same ‘Products’ DB) ?
In other words I have to catch all the changes in “afterProcessDeltaChange” and then change what ever to old Values?

Another thought - usually it’s not right thing to do - change data with update statement on before * because of the record lock which might happens, but may be as middle tier Remote Objects server working in different way, and processing all those before * and after * before actual SQL update statement.

how things work:

  • beforeProcessDeltaChange. here you can override values in delta change
  • process delta change and put changes to DB
  • afterProcessDeltaChange

so catching all the changes in afterProcessDeltaChange will be wrong.

Note: in beforeProcessDeltaChange you can perform select and get actual values from DB


btw, your script contains some errors, like, global variables like inLocalAccess aren’t supported, this event will update Products table for any delta change in any table

Thank you.

Hi Evgeny

By some odd reason having a script error : “System.IndexOutOfRangeException: Index was outside the bounds of the array”
after some changes of script above came over with something like :

function beforeProcessDeltaChange(delta, deltachange, wasRefreshed, canRemove) { if (userId = 2) { lda.update("Products", { ID: change.originalRow["ID"]}, { App2_Qty: App2_Qty }, { updatedBy: userId });} }

where “ID” is a Primary index

you are using App2_Qty and userId. where you get these values?

note: global variables don’t work here

Those : App2_Qty and updatedBy are fields in “Products” database
Sorry didn’t show it in message above :

function beforeProcessDeltaChange(delta, deltachange, wasRefreshed, canRemove)
 { 
  var userId = change.newValues['UpdatedBy'];
  var vApp2_Qty = change.newValues['App2_Qty'];

 if (userId = 2) { 
   lda.update("Products", { ID: change.originalRow["ID"]}, { App2_Qty: vApp2_Qty }, { updatedBy: userId });
   lda.applyChanges();
} 
}

Does Products delta contain UpdatedBy & App2_Qty fields?
this exception can be raised if some fields aren’t found in delta change

I can see them on debug script screen that pops up on DAVCLReconcileProvider1 script error
Some fields are green and white , is it related somehow to delta?
“ID” is white and App2_Qty is green.

DAVCLReconcileProvider1 shows changed fields in different color. it isn’t related to actual error.

there was an error at the beginning with a first script above, showing that RO RS cannot process empty fields , so I have to write all the “Product” database fields and assign some data to each field (which was different from what RO DA have in sample PCTradeOffice, in the way I get it :slightly_smiling_face: ):

function beforeProcessDeltaChange(delta, deltachange, wasRefreshed, canRemove)
	{
    var itemId = change.newValues['Id'];
    var userId = change.newValues['UpdatedBy'];
    var vApp1_Qty = change.newValues['App1_Qty'];
    var vApp2_Qty = change.newValues['App2_Qty'];
	var oldValues = { Id: itemId };

    if (userId = 1)
	    {var newValues = { Id: itemId , App1_Qty: vApp1_Qty, App2_Qty: vApp2_Qty, UpdatedBy: userId, Updated: new Date()  };}
    else if  (userId = 2)
        {var newValues = { Id: itemId , App1_Qty: vApp1_Qty, App2_Qty: vApp2_Qty, UpdatedBy: userId, Updated: new Date()   };}

        lda.update ( 'Products' , oldValues, newValues);
        lda.applyChanges();
}

and after all script wasn’t happy with Updated: new Date() saying that it’s not right value
so after reading RO DA documentation I came up with script:

function beforeProcessDeltaChange(delta, deltachange, wasRefreshed, canRemove)
 { 
  var userId = change.newValues['UpdatedBy'];
  var vApp2_Qty = change.newValues['App2_Qty'];

 if (userId = 2) { 
   lda.update("Products", { ID: change.originalRow["ID"]}, { App2_Qty: vApp2_Qty }, { updatedBy: userId });
   lda.applyChanges();
} 
}

that diving me an error on “System.IndexOutOfRangeException: Index was outside the bounds of the array”:slightly_smiling_face:

And now have script changed to addopt finalRow and originalRow, with the same error System.IndexOutOfRangeException:

function beforeProcessDeltaChange(delta, deltachange, wasRefreshed, canRemove)
{
lda.update(“Products”, { ID: change.originalRow[“ID”]}, { App2_Qty: change.finalRow[“App2_Qty”] }, { updatedBy: change.finalRow[“UpdatedBy”] });

lda.applyChanges();
}

So this System.IndexOutOfRangeException exception happens when you send an update to the server and the script is executed.

Could you show structure of the table you are updating? Or (even better) to send the schema to support@ and tell which exactly table you’re updating?

Hi Anton
DB table structure:

Products ( 
      ID Char( 18 ),
      Qty Numeric( 10 ,0 ),
      App1_Qty Char( 50 ),
      App2_Qty Char( 50 ),
      App3_Qty Char( 50 ),
      App4_Qty Char( 50 ),
      App5_Qty Char( 50 ),
      UpdatedBy Integer,
      Updated TimeStamp )

There are some extra fields ,I hope they will make no difference, because they have same structure.

How it is defined in Schema ?

Also am I right that you send an update from the client app to the Products table and then try to update it one more time from the script?