dialogflow-fulfillment-nodejs icon indicating copy to clipboard operation
dialogflow-fulfillment-nodejs copied to clipboard

Issue in getting response back while calling an API using axios

Open ridhimagarg opened this issue 4 years ago • 23 comments

I am using Axios library to make get and post a request for an API in dialogflow fulfillment.

I am using Axios in many intents, but in few intents, it is not able to give a response i.e, It shows "Not available" in test console but I am printing logs then logs are printing successfully but agent.add() is not working and if I am using post request then it is also saving data to my database, mainly it is not printing whatever is present in agent.add().

I am attaching a sample code of one intent only which creates a problem, there are few other intents too which are facing the same issue

function someintent(agent){
      
    const parameter1 = agent.parameters.parameter1;
    //start of If statement
    if(parameter1.toString().length == 5 || parameter1.toString().length == 7){
        
        // Parameters from previous intent 
        const parameters = agent.context.get('previous-followup');
        
        const previous_parameter1 = parameters.parameters['previous-parameter1'];
        
        var previous_parameter2 = parameters.parameters['previous-parameter2'];
        
        var previous_parameter3 = parameters.parameters['previous-parameter3'];
        
        // Some logic for parameter value
        if(previous_parameter2 == ""){
            previous_parameter2 = " ";
        }
        
        if(previous_parameter3 == ""){
            previous_parameter3 = " ";
        }
        
        //Main problem occurs here 
        return axios.post('http://some-api-call', // api to fetch data
        {
        "UserId": 1,
        "Parameter1": previous_parameter2,
        "Parameter2": previous_parameter3,
        }).then((result) => {

        console.log("API result: "+result.data);
        
        if(result.data){

            agent.add('Here is what I found:'); // Problem comes here i.e, it is not printing sometimes 
                                                      and sometimes its not printing
                                                // I tried printing inside _then_ of Axios call but same issue
            
            return axios.post('http://someapi-to-store-data', // another api call to store data
                {	
                    "storedata": result.data
                }).then((result1) => {
                    console.log(result1.data); // If this block of _if_ executes then it is printing in logs
                    console.log('Store data to api'); // It is also printing in logs
                });
            
        }  
        
        else{
            
            agent.add('I am not able to find any information'); // Same problem comes here, not printing
            agent.add('Please enter Name');
            
            return axios.post('http://someapi-to-store-data', // another api call to store data
                {	
                    "storedata": parameter1
                }).then((result1) => {
                    console.log(result1.data); // If this block of _if_ executes then it is printing in logs
                    console.log('Store data to api'); // It is also printing in logs
                });
        }
        
        }).catch(err => {
            console.log("Error calling in  API: ${err}");
            agent.add("Failed to fetch any information");
            return agent.add('Please enter name');    
            });
    
        } // end of main outer If statement
   
    // Else statement start
    else{
        
        agent.add('Please enter valid 5 or 7 digit ');
        agent.context.set({
            'name':'previous-followup'
        });
        agent.context.set({
            'name':'someintent-followup',
            'lifespan': 0
        });
    
    } // end of else statement
    
    }

I am not able to understand what is the issue here as sometimes agent.add() is working and sometimes not but logs and data saving to database is perfectly fine.

I really require a help on this. Urgent help is appreciated.

ridhimagarg avatar Dec 24 '19 11:12 ridhimagarg

People are sleeping here, we get no respond to help us

onigetoc avatar Jan 29 '20 22:01 onigetoc

Ya, seems like support is not actively responding.

ridhimagarg avatar Jan 30 '20 05:01 ridhimagarg

Hi Ridhima, it could be a timeout issue. Dialogflow has a strict timeout of 5 seconds. So if your API takes more than 5 seconds to respond, Dialogflow will just timeout with an error.

Regarding connecting Dialogflow with an external API, please watch this video that I have created https://www.youtube.com/watch?v=n4IPOeFCDxI

Anshul0305 avatar Feb 11 '20 14:02 Anshul0305

hey, @Anshul0305 database queries might take longer than 5 seconds. What is the solution in this case?

sudonitin avatar Mar 16 '20 06:03 sudonitin

You can write the database query code inside a promise and when the promise resolves, you can trigger an event in Dialogflow using agent.setFollowupEvent() function.

Anshul0305 avatar Mar 16 '20 07:03 Anshul0305

axios.post(
          'some url',
          orderDetails,
          {headers:{"Content-Type": "application/json"}})
          .then((res) => {
          	console.log(res.data.orderID);  //this one executes
        	conv.ask(res.data.orderID);  //this line does not executes
          	if(res.data.success){
              	orderDetails.orderId = res.data.orderId;
              	conv.ask("great"); //not executing
              	conv.ask(`Refer to this order id ${res.data.orderId}. Send me this order id to know the status of your order.`); //not executing
            }
        }).catch(err => {
          	console.log('failed');
        	conv.ask('Sorry a problem occured. Can you please place the order again');
        });

Have a look at this @Anshul0305 Can you please elaborate on how to create an event and use it with setFollowupEvent()

sudonitin avatar Mar 16 '20 07:03 sudonitin

Try changing conv.ask() to agent.add() Also make sure to add a "return" before axios.post()

For events, please have a look at this link: https://cloud.google.com/dialogflow/docs/events-overview#config

Anshul0305 avatar Mar 16 '20 11:03 Anshul0305

@Anshul0305

agent = dialogflow()
agent.add()

Correct me if I am wrong.

return before axios.post() ? This return should just be the keyword?

sudonitin avatar Mar 16 '20 16:03 sudonitin

Please check the default code in Inline Editor.

const {WebhookClient} = require('dialogflow-fulfillment'); const agent = new WebhookClient({ request, response }); agent.add(Welcome to my agent!);

return before axios.post() ? This return should just be the keyword? [Anshul]: Yes, that's correct return axios.post(....YOUR_CODE_HERE.....)

Anshul0305 avatar Mar 17 '20 08:03 Anshul0305

Hey @Anshul0305 , i'm trying to implement an external API with Dialogflow fullfillement the data arrives perfectly on the console on the line above but when trying to get it on agent.add(new Card({})) The Card doesn't seem to appear. Help would be really appreciated

nasirhm avatar Mar 17 '20 12:03 nasirhm

Here's the link to my code : https://gist.github.com/nasirhm/1dd2ad31e585b350b7a82b6c36a67cec

nasirhm avatar Mar 17 '20 13:03 nasirhm

I guess my error is due to dialogflow being timed out in 5 seconds although the whole function take 7 seconds, I couldn't find implementation for events. Kindly share some reference for it along with letting me know if i'm making any other errors.

Seems similar to your problem @ridhimagarg

nasirhm avatar Mar 17 '20 13:03 nasirhm

UPDATE : Tried using: agent.setFollowupEvent('Delay1'); agent.setFollowupEvent('Delay2'); before calling the response added it in the event tabs of dialogflow too. Still, the agent.add, doesn't seem to work.

nasirhm avatar Mar 17 '20 13:03 nasirhm

Yes, not working for me too. @nasirhm can you share the code format? because as @Anshul0305 said

const agent = new WebhookClient({ request, response });

but this line gives me a warning that request and response are not defined.

@Anshul0305 you have any other solution to this?

sudonitin avatar Mar 17 '20 13:03 sudonitin

@globefire the agent line works for me, the problem is somewhere in Dialogflow being timedout.

nasirhm avatar Mar 17 '20 14:03 nasirhm

Can you share your code for me to check it out, probably i can help you too.

nasirhm avatar Mar 17 '20 14:03 nasirhm

Okay @nasirhm I'll share the code in a minute.

sudonitin avatar Mar 17 '20 14:03 sudonitin

app.intent('giveOrderID-phonei/p', (conv, params) => {
	if(params['phone-number']){
		orderDetails.phone = params['phone-number'];
      	conv.ask("..........random text............");
      	axios.post(
          'https://API_URL/',
          orderDetails,
          {
      		headers:{"Content-Type": "application/json"} }).
                then((res) => {

          	if(res.data.success){
              	conv.close(`This is your order id ${res.data.orderID}`);  //>>>>>>>API response (This is not executing)
              	orderDetails.orderId = res.data.orderId;
              	conv.followup('orderIdEvent', { 'id': res.data.orderId }); //>>>>>>This is what I tried doing
            }
        }).catch(err => {
          	console.log('failed');
        	conv.ask('............................Some more random text...................................');
        });
	}
});

@nasirhm This is my code before applying what @Anshul0305 specified.

Can either of you please guide me where and what changes shall I make so that I can use the response of my API?

sudonitin avatar Mar 17 '20 14:03 sudonitin

@globefire Seems like you're using actions on google, that by default has a timeout for 10 Seconds, Does the first statement of randomText gets printed ?

nasirhm avatar Mar 18 '20 05:03 nasirhm

@nasirhm yes it does. I am able to console log my response(I can see this in firebase console). Its just the google actions where I am not able to use the response.

sudonitin avatar Mar 18 '20 06:03 sudonitin

I'm facing the same issue as the response gets displayed on the Console but when it comes to Dialogflow it doesn't show the response, Most probably it times out in 5 seconds. For google actions it's 10 seconds for the agent to be timed out, What's the response time of the API you're trying to implement.

nasirhm avatar Mar 18 '20 06:03 nasirhm

@nasirhm I am not sure how to find out that

sudonitin avatar Mar 18 '20 07:03 sudonitin

You can do that by using Postman to see how much time does the API take to return the responses.

nasirhm avatar Mar 18 '20 07:03 nasirhm