0

I have an empApi subscription to a Platform Event. When that event fires, I want to pull data from its fields and showToast.

I'm copying the code straight from the docs, and I can get the platform event data inserted into a console.log, but I can't use it to set variables or to call other methods.

I have my import declarations:

import { LightningElement, track } from 'lwc';
import { subscribe, unsubscribe, onError, setDebugFlag, isEmpEnabled } from 'lightning/empApi';
import { ShowToastEvent } from 'lightning/platformShowToastEvent'

And this method to set up the empApi subscription:

    handleSubscribe() {
    // Callback invoked whenever a new event message is received

    const messageCallback = function(response) {
        let toastData = response.data.payload;
        console.log('toastData: ' + JSON.stringify(toastData));
        //can't set variables here
        //can't call the showToast() method here
    };

    // Invoke subscribe method of empApi. Pass reference to messageCallback
    subscribe(this.channelName, -1, messageCallback).then(response => {
        // Response contains the subscription information on successful subscribe call
        console.log('Successfully subscribed to : ', JSON.stringify(response.channel));
        this.subscription = response;
        this.toggleSubscribeButton(true);
    });
}

I think the issue is that the callback method is asynchronous, so how can I get the @track variables or other methods into the scope of the messageCallback?

I tried putting the code from the showToast() function directly into the messageCallback function, but it does nothing -- I think because within the scope of that messageCallback function it doesn't have access to the imported functions (not sure about that.)

Any recommendations? Can I call to show toast without using the imported ShowtoastEvent (like we used to do with Aura)?

1 Answer 1

0

Can I call to show toast without using the imported ShowtoastEvent (like we used to do with Aura)?

No, you can't use force:showToast.

I think the issue is that the callback method is asynchronous, so how can I get the @track variables or other methods into the scope of the messageCallback?

Don't make a separate context, but instead use the existing context. To do this, use an arrow function:

const messageCallback = response => {

This syntax specifically preserves the context of where you are.

Alternatively, make a separate function:

messageCallbackHandler(response) {
  // ...
}
...
const messageCallback = this.messageCallbackHandler.bind(this);

Using Function.bind sets the context to a particular object, in this case, this, which is the LightningElement you're in.

3
  • Thanks, Brian! I'll give it a try and report back to close the loop. Mar 13, 2020 at 14:48
  • That first approach worked for me. I tried the alternate and it didn't work... maybe I didn't implement it correctly. Mar 13, 2020 at 15:02
  • @PatMcClellan__c Possibly? At any rate, you've got a solution that works, so I'd go with it. The first one is a bit easier to read anyways, in my opinion.
    – sfdcfox
    Mar 13, 2020 at 15:14

You must log in to answer this question.

Not the answer you're looking for? Browse other questions tagged .