When is OnCurrentSaleSaved called in a VBscript?

Hi Guys.

I'm running a VB-script, that calls a CRM script upon saving a sale. Both the VBscript and CRM script are using the links.

The CRM script is called with an async MSXML2.XMLHTTP object.

But I'm having problems when trying to remove a link between a sale and a project. Here is the flow. On each step both VB-script and CRM script return what links it sees attached to the sale:

  1. Adding Project link to Sale -> Saving.
    'OnCurrentSaleSaved' -> Somessagebox gives me link-ID 1732.
    CRM script -> Returns link-ID 1732.
  2. Removing Project link from Sale -> Saving.
    'OnCurrentSaleSaved' -> Somessagebox gives no link-ID.
    CRM script -> Returns link-ID 1732.
  3. The links looks like its missing from the sale, but can be seen on the project (after pressing f5).
  4. Link appears again on sale after restarting SO.

I would expect 'OnCurrentSaleSaved' to trigger after both the sale, and all attached objects have finished saving. This way there should be no problems calling the CRM script. But this doesn't seem to be the case.

I don't have any problems adding any links. It's only when I try to remove them from the sale.

What am I missing?

 

Customer is running SO 84R4.

 

RE: When is OnCurrentSaleSaved called in a VBscript?

Win, Script events:
Start by giving yourself this function level preference and restart socrn.

This shoud give you a menu:

Select Show viewer
Script Evens tab:

 

This will give you real-time feedback of the script events system.

Now, I suspect this is somehow related to your previous post:

https://community.superoffice.com/en/technical/Forum/rooms/topic/superoffice-product-group/crm-windows-application/question-regarding-relations-between-sale-and-project-in-db/

I had some questions over there.
Also, I wouldn't mind more context, perhaps even some snippet of your vb scripts and what you are trying to achieve.

Conrad

Av: Conrad Weyns 6. mai 2019

RE: When is OnCurrentSaleSaved called in a VBscript?

Hi Conrad.

Thank you for responding :). I already have the script utility enabled.

Below is the seperate code-snippets (i've dummed them a bit down). The first is vb, and the rest is CRM.

It looks like the projectEntity in the third code-snippet is responsible for the hijacking. When I don't save the object, there is no problems. But when I save the projectEntity, the problem occurs.

Sub OnCurrentSaleSaved()
	url = baseScriptUrl & "&includeId=" & saleId &"&key="& saleKey & "&sale_id=" & CurrentSale.Identity
	
	somessagebox "vb: "& GetProjectLinks() //getting all links from currentSale
	result = CallWeb(url, false) //calling async crm-script
	somessagebox "crm: "& result //crm is returning all links from crm script

End Sub
NSLink[] links = saleEntity.GetLinks();
String linkIds = "-1";

for(Integer i = 0; i < links.length(); i++)
{
  NSLink link = links[i];
  linkIds += ","+link.GetId().toString();
  S09_UpdateProject(link.GetId()); //updating project on some values
}

print(linkIds) //returns to vb-script
Void S09_UpdateProject(Integer projectId)
{
  NSProjectAgent projAgent;
  NSProjectEntity project = projAgent.GetProjectEntity(projectId);
  Map udef = project.GetUserDefinedFields();
  String progId;
  Integer amount;

  project.SetUserDefinedFields(udef);
  projAgent.SaveProjectEntity(project);

}
Av: Kasper Rosenlund 6. mai 2019

RE: When is OnCurrentSaleSaved called in a VBscript?

Hmm.. I think I see the reason to my problem.

'OnProjectSaved' is triggered, when changing the link.

Hmm.. is it at all safe to call a CRM script then, without knowing when all triggers are done being called? 

*EDIT* Nope, this wan't the issue. Tried to call CRM from 'OnSaleEditComplete' trigger, but there was no difference.

Av: Kasper Rosenlund 6. mai 2019

RE: When is OnCurrentSaleSaved called in a VBscript?

I'm confused. Why would you want to call into CRMScript from a Windows vbscript when you could simply get the Project in the OnCurrentSaleSaved event handler and update the project there... Why the cross-platform calls?

Av: Tony Yates 6. mai 2019

RE: When is OnCurrentSaleSaved called in a VBscript?

Simple answer: In the future the customer want's to go Online, but for now they want to use Windows.

This way I only needs to a little as possible duplicate code :).

Av: Kasper Rosenlund 6. mai 2019

RE: When is OnCurrentSaleSaved called in a VBscript?

Your strategy is flawed.
You are missing one crusial point: Anything you do with CRM Script and/or some netserver API from inside a SoCrm VB Script event, will happen behind the Win client's back! (Actually this would also be true if you were to instantiate our SuperOfficeDB COM object from within our application and use it to change entities) 
A simple analogy is to modify some entity in the Win client, then move to another client and modify the same entity or some related entity.

Also I don't see what this  async in CallWeb can possibly be. It would have to be blocking from the p.o.v. of the vb script event hook.

When we Save a change in activity links, the partner entity is also changed merely because we want to keep these activeLinks fields updated. I suspect that if this was designed today, we would not have these cached fields and simply pay the price to count records in the relation table..

I am still not entirely sure what you are trying to achieve It seems perhaps that when adding a project activtiy link to a sale, you need to update a project-udef field.

Then I sugest you try Tony's strategy: use the Win's API to change the project from within the Sale save event. That should be legal and Win will then have at least a chance of seeing consistent resident data.

Whatever you do, drop to dual-universe method!
Also, if you need to flush afterwards, you are most probably on the wrong track.
Conrad

 

 

Av: Conrad Weyns 6. mai 2019

RE: When is OnCurrentSaleSaved called in a VBscript?

Hi Conrad.

I see your points. That is why I called in on the after-save, to interfer as little as possible. But this strategi works in every other aspects except this (what I've seen at least).

I'm calling the CRM-script with this function:

Function CallWeb(url, isAsync)
	Dim o
	Set o = CreateObject("MSXML2.XMLHTTP")

	o.open "POST", url, (isAsync OR debugMode)
	o.send
	CallWeb = cstr(o.responseText)
	
	IF debugMode THEN
		somessagebox CallWeb
	END IF
End Function

 

I guess the activity links is saved after this, thus creating this problem. 

 

Av: Kasper Rosenlund 6. mai 2019

RE: When is OnCurrentSaleSaved called in a VBscript?

How are you removing the link?
From the GUI or via one of your scripts?

1. From the GUI:
Can you reproduce it when scripting events are turned off?
If so, we are back to your other post. I could not reproduce that and I had some questions related to it.
If this is a real bug, then it needs fixing first. I will look into it if I can somehow figure out how to reprocude it!

2. From within one of your scripts:
If you are removing a link from within the OnCurrentSaleSaved event, then it is a different game.
(I suggest you look into doing this in the OnCurrentSaleBeforeSave event instead, but all using our own API!)


As a rule, *Save* events are called when all related data of the underlying entity is saved. 
However, the partner entity of an activity link that needs updating, like in your case, the project.activeLinks fields is not part of this.
One could argue that it should be. But the potential issues with nested Save calls and COM are huge and very hard to handle so this is in fact delayed until the application is idle. From your script p.o.v, as long as you have control, anything can happen in between. But again, as long as you use the application's API, we will have a fair chance of seeing consistent resident data.

Note also in this event log, I have added a project link to the current sale:
2: 15:35:32:404 OnCurrentSaleBeforeSave (1)
3: 15:35:33:517 OnSaleFieldsChanged (1) [VT_BSTR] SaveModel, [VT_UI4]76, [VT_BSTR] UPDATED, [VT_INT]3357
4: 15:35:33:522 OnCurrentSaleFieldChanged (1) [VT_BSTR] sale.UPDATED
5: 15:35:33:536 OnCurrentSaleSaved (1)
6: 15:35:33:672 OnProjectFieldsChanged (1) [VT_BSTR] SetNumberOfLinks, [VT_UI4]76, [VT_BSTR] ACTIVELINKS, [VT_INT]2835
7: 15:35:34:494 OnProjectFieldsChanged (1) [VT_BSTR] SaveModel, [VT_UI4]76, [VT_BSTR] UPDATED, [VT_INT]2825
8: ....
9: 15:35:35:749 OnEditSaleComplete (1)

No OnCurrentProjectSaved but a OnProjectFieldsChanged with SaveModel action. This is because adding this link did not cause the current project to change. The partner project's activeLinks got updated, but it is not current. You's need the so called "New" messages to get this. I reckon New is now well over 10 years old :-)
If you add links to various Appnt, Doc, Proj and Sale, all will get their activeLinks fields updated in due time. This is normaly as soon as the application goes into Idle. Definately after your script has returned to us.

/conrad




 

 

Av: Conrad Weyns 6. mai 2019

RE: When is OnCurrentSaleSaved called in a VBscript?

Hi Conrad.

Im removing the link from the GUI in SuperOffice Windows. Thats it.

I'm not doing anything in the VB-script, other than calling the URL and using a few somessagebox.

I would still expext ALL sale-related objects was saved on the 'OnCurrentSaleSaven' event.

Av: Kasper Rosenlund 6. mai 2019

RE: When is OnCurrentSaleSaved called in a VBscript?

I want to know, if you can reproduce this without any script events running?
I.o.w. a mere Win related issue, nothing external.
If this is the case, then there must be a bug somewhere.
But I repeated the actions you decribed in the other thread several times and could not reproduce.
Again, I had a question in that threat that was meaningfull:
Look into the DB, does the relation record get deleted and was a new one (thus with a new id) created?
And is there anythng interesting in the log like an error from a DeleteRecord for example.

a.f.a. the related partner activeLinks fields are concerned, this is not going to change.
Note also that when this delayed updating occurs, nothing should happen to the activity links system - unless something in between (like a script) caused it to become dirty.

/conrad

 

Av: Conrad Weyns 6. mai 2019