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

Af: Conrad Weyns 6. maj 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);

}
Af: Kasper Rosenlund 6. maj 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.

Af: Kasper Rosenlund 6. maj 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?

Af: Tony Yates 6. maj 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 :).

Af: Kasper Rosenlund 6. maj 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

 

 

Af: Conrad Weyns 6. maj 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. 

 

Af: Kasper Rosenlund 6. maj 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




 

 

Af: Conrad Weyns 6. maj 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.

Af: Kasper Rosenlund 6. maj 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

 

Af: Conrad Weyns 6. maj 2019

RE: When is OnCurrentSaleSaved called in a VBscript?

Hi Conrad, sorry.

No, I can't reproduce it when Events are disabled. When events are disabled, I'm not calling the CRM-script.

In the older thread I hadn't yet realized what role the HTTP call had.

This is what I experience (with events enabled):

  1. Removing link (between sale and project) from sale in SuperOffice Windows through GUI.
  2. What I notice:
    1. Database: Visible (with the same ID) (relDef type 10 project -> sale) 
    2. Sale entity: Not visible -> f5 -> not visible
    3. Project links: Not visible -> f5 -> visible 
  3. Restarts SuperOffice
    1. Database: Visible (relDef type 10 project -> sale) 
    2. Sale entity: visible
    3. Project links: visible

This is ONLY when I'm through script have the following conditions:

  • On 'OnCurrentSaleSaved' event calling a CRM script with function 'CreateObject("MSXML2.XMLHTTP")'
  • CRM script is getting either the related sale or project object, and later saving it (se box 3 in my first answer to this thread).

It looks like it works alright, when I'm not having a reference to the project-object in my CRM-code.

If I don't save the project (se box 3 in my first answer to this thread), then the CRM-script return the correct number of links.

Af: Kasper Rosenlund 6. maj 2019

RE: When is OnCurrentSaleSaved called in a VBscript?

Hi Kasper,

ok, so I think we can reasonably conclude that this is a side effect of your scripts.
Can you describe what your ultimate aim is? What are you trying to achieve?

If I understand you correctly:

1. You add a link from the current Sale to some Project, and click Save.
2. Your script is doing things (some of which is behind our back) in the OnCurrentSaleSaved event.
3. You obserse a new relation record in the db. Say relations.relation_id=123. (reldef_id is not important)
4.1. Now you edit the same Sale, Delete the link to the Project and click Save again.
4.2. Your script is running again! What happened now?
5. You observe the same relation record in the database, thus the record with relations.relation_id=123. Correct??
I am having a hard time believing this since the Sale's activitylink code will actually delete the relations record.
(Unless your Async web method running at some later time re-creates the same relation record with the same relaltion_id somehow - unlikely I think but the internals of netserver is not exactly my cup of tea - so I would realy like to see the traffic in the your relations table. Are you 100% sure that the relations.relation_id remains at 123?)
If this is true, then deleting the link failed for some reason. (My gutt feeling is that your script of step 2 or 4.2 caused our internal data to become inconsistent but without a thourough examination of your scripts it is just a guess..)
6. In the Sale/Links tab view you are not seeing the link anymore. (This is not necessarily a correct reflection of what is in the DB since the view might make some assumptions)
7. In the related Project/Links tab view the link remains visible. (Indicates that our internal data is inconsistent)
8. After a F5 (or shift-f5), the Sale/Link view is showing the link again - sounds correct since the link was never deleted from the db.

i.o.w. deleting the link had no effect on the database relations table at all, correct?

I am not sure how to help you further. I think I need more context for that.
Conrad

 

 

Af: Conrad Weyns 6. maj 2019