Can the Asynchronous Message Bus (AMB) be used directly within an Application (client-subscribe, server-publish)?

David Hubbard
Tera Guru

Hi

I am aware that ServiceNow uses it's Asynchronous Message Bus (AMB) for forum level field updates (record watcher?) and for Mid Server triggering.

But can it be used in a bespoke fashion within an Application, such that a client screen (Workbench panel?) may subscribe to a bespoke topic and a server-side script (on an Event?) can publish to the topic?

I can see there may be alternative ways of doing this (e.g. This community link) but that seems to rely on an external message broker setup (per client instance). 

If it is available for use, can you point me at documentations please?

Thanks

1 ACCEPTED SOLUTION

Hi Rishabh

Very helpful, thanks

I was a bit daunted looking at those scripts but think the key part was it showed how to get the message client from the amb variable. 

   function getChannelRW(table, filter) {
            var t = '/rw/default/' + table + '/' + getFilterString(filter);
            return amb.getClient().getChannel(t);
        }

The key being the "amb.getClient()" rather than "amb"

This change seems to have worked, with a successful subscribe. 

I guess in terms of my initial question the server-side publish part is down to table updates and appropriate subscriptions.

Thanks again for helping me out.    

P.S. For completeness I attach the angular-based reworking of the first link you sent which can work in a UI Script

View solution in original post

13 REPLIES 13

Rishabh Jha
Mega Guru

Hi David,

As far as I know, Servicenow uses Bayeux protocol and CometD client for AMB. I'm not really sure about any official documentation around this, but you can find the amb related scripts here (and maybe try to reverse-engineer your way out!):

https://<your-instance>.service-now.com/scripts/js_includes_amb.js

https://<your-instance>.service-now.com/scripts/js_includes_ng_amb.js

 

Please mark the response as helpful/correct, if it helped you in any way!

 

Thanks & Regards,

Rishabh Jha

Aavenir (https://www.aavenir.com/)

Hi Rishabh

Very helpful, thanks

I was a bit daunted looking at those scripts but think the key part was it showed how to get the message client from the amb variable. 

   function getChannelRW(table, filter) {
            var t = '/rw/default/' + table + '/' + getFilterString(filter);
            return amb.getClient().getChannel(t);
        }

The key being the "amb.getClient()" rather than "amb"

This change seems to have worked, with a successful subscribe. 

I guess in terms of my initial question the server-side publish part is down to table updates and appropriate subscriptions.

Thanks again for helping me out.    

P.S. For completeness I attach the angular-based reworking of the first link you sent which can work in a UI Script

Hi David,

I'm glad that it helped you finding your way out!

Yes, the server side publishing should automatically occur on record insert/updates, and you'd need to point the client to the appropriate channel, to be able to subscribe to the updates to records inserted/updated in a particular table.

 

Thanks & Regards,

Rishabh Jha

Aavenir (https://www.aavenir.com/)

Community Alums
Not applicable

Hi @Rishabh Jha and @David Hubbard,

 

I stumbled upon this discussion and it might help me out as well. 

I don't (yet) fully understand these mechanisms, so bare with me please.

My question would be, how can I subscribe to those events that happen on record insert/update?

 

My use case would be the following: 

I want to intercept/listen/subscribe to the transaction that happens on a record insert or update on a task child record. Namely I want to catch the Assignment Rule that is being run when the Assignment Group is updated on the Incident record for example.

 

In the transaction logs, I see several information that happens during this update action and some of those that stood out were:

 

2023-09-25 01:19:48 (885) http-33 [AMB] AMBClusterBroadcastExtension channel_id=/meta/subscribe message_id=30 cometd_session_id=307ywtuy24a4hgw15shpfwgsub53 glide_session_id=E192CCFC1BA1F95048B860A7234BCB02 user_id=LLLLL glideSessionMappedToHttpSession: true, canReestablishGlideSession: true, isPublicOrUserSet: true, contextName: send /amb/meta/subscribe /sn/rp/sysrule_assignment/4d0682331b99f910e9cc5208624bcb10

 

amb/meta/subscribe /sn/rp/sysrule_assignment/4d0682331b99f910e9cc5208624bcb10

 

 

2023-09-25 01:20:11 (577) Default-thread-7 E192CCFC1BA1F95048B860A7234BCB02 txid=904324f01ba5 DEBUG: #475623 [REST API] RESTAPIProcessor : Request Header: referer:https://AAAAAA.service-now.com/now/nav/ui/classic/params/target/sysrule_assignment.do%3Fsys_id%3D4d0682331b99f910e9cc5208624bcb10%26sysparm_stack%3Dno%26sysparm_domain%3Dglobal%26sysparm_domain_scope%3Drecord

 

RESTAPIProcessor : Request Header: referer:https://AAAAA.service-now.com/now/nav/ui/classic/params/target/sysrule_assignment.do%

 

Now I don't know if this helps or not, but this is the path that I started going down on.

 

Any type of help is greatly appreciated, undocumented APIs/classes etc. or even if that's just a know-how of the mechanisms how these work.

 

Best regards,

Lor

Hi Lor (@Community Alums) 

 

Can I ask what your client-side environment is - is it a Next Experience Custom Component?

 

I don't recall where we were focussing when I posted the initial question, but we have ended up with Custom Component and using "createAmbSubscriptionEffect", which is described in this community article.  That import handles all the internal amb integration for you. 

 

This should handle "update" to records pretty well, but I suspect that capturing a record "insert" may be tricky, since AFAIK the basis of this is to define a "table" and an "encodedQuery".  So you can watch a set of records if you know the sys_ids (and get updates) but as the "sys_id" of inserts is not known in advance these won't trigger the AMB. 

 

For the insert - it may be possible to watch some lower level table (e.g. "sys_audit" ?) and use the encodedQuery to filter on your table, but there may be performance implications of doing that.    

 

Hope that helps.


Edit:  Thinking on this a little - you may be able to get "inserts" if your query is based on other columns e.g. "typeINA,B,C", rather than using "sys_id" as my examples above. We haven't needed this so I haven't tested it.

 

Regards

David