Creating Buttons through Custom action throwing error

Hello everyone, I am trying to create an on the go button. So I copied one of RasaHQ codes for the same but seem to create an error at dispatcher point. I don’t know what went wrong. Please do help me out.

class Actionstory(Action):
    
    def name(self):
        return "action_story_telling"

    def run(self, dispatcher, tracker, domain):
        try:
            is_name=tracker.get_slot('user_name')
            if is_name == None or is_name == "":
                data = access_db()
                is_name = str(data[0])
            conn = sqlite3.connect(DB_file_name)

            c = conn.cursor()
            c.execute("SELECT name FROM sqlite_master WHERE type='table';")
            tables=[v[0] for v in c.fetchall() if v[0] != "sqlite_sequence"]
            

            if "user_story" not in tables:
                print(1)
                c.execute("CREATE TABLE user_story(id integer, name text, story integer)")
                c.execute("INSERT INTO user_story VALUES(?, ?,?)",[1, is_name, 1])
                id = 1
                story = 1
                conn.commit()

            else:
                print(2)
                c.execute("SELECT id, story FROM user_story ORDER BY id DESC, story DESC LIMIT 1")
                val = c.fetchone()
                id = val[0]
                story = val[1]
                if int(story) == 8:
                    story = 1
                    id = id +1
                    c.execute("INSERT INTO user_story VALUES(?, ?,?)",[id, is_name, story])
                    conn.commit()
                
                

            df = pd.read_csv(STORY_file_name)
            
            x = id - 1
            y = (story * 2)
            listed = df.iat[x,y]
            listed = listed.split("&;")

            for sent in listed:
                dispatcher.utter_message(text=sent)
            y = y + 1
            pay = df.iat[x,y]
            
            c.execute("SELECT story FROM user_story ORDER BY id DESC, story DESC LIMIT 1")
            val = c.fetchone()
            story_update = int(val[0]) + 1
            c.execute("INSERT INTO user_story VALUES(?, ?,?)",[id, is_name, story_update])
            c.execute("SELECT * FROM user_story")
            print(c.fetchall())
            button = []
            button.append({'title': "{}".format(pay), 'payload': '/storying'})
            print(button)
            conn.commit()
            conn.close()
            return True
        except Error as e:
            print(e)
            return False
        finally:
            if conn:
                conn.close()

        
        try:
            if pay != 'yesno':
                
                dispatcher.utter_message(buttons = button)  
        except:

            traceback.print_exc()
        return []

This is the error I am receiveing when I run rasa x in the Rasa run actions terminal. I am sure the problem is dispatcher or the way buttons are formated. Please let me know what’s the issue.

[(1, 'Ashwin', 1), (1, 'Ashwin', 2), (1, 'Ashwin', 3), (1, 'Ashwin', 4), (1, 'Ashwin', 5), (1, 'Ashwin', 6), (1, 'Ashwin', 7), (1, 'Ashwin', 8), (2, 'Ashwin', 1), (2, 'Ashwin', 2), (2, 'Ashwin', 3)]
[{'title': 'hmmm', 'payload': '/storying'}]
Exception occurred while handling uri: 'http://localhost:5055/webhook'
Traceback (most recent call last):
  File "/home/ashwinrk/anaconda3/envs/machinelearn/lib/python3.7/site-packages/sanic/app.py", line 976, in handle_request
    response = await response
  File "/home/ashwinrk/anaconda3/envs/machinelearn/lib/python3.7/site-packages/rasa_sdk/endpoint.py", line 102, in webhook
    result = await executor.run(action_call)
  File "/home/ashwinrk/anaconda3/envs/machinelearn/lib/python3.7/site-packages/rasa_sdk/executor.py", line 393, in run
    validated_events = self.validate_events(events, action_name)
  File "/home/ashwinrk/anaconda3/envs/machinelearn/lib/python3.7/site-packages/rasa_sdk/executor.py", line 340, in validate_events
    for e in events:
TypeError: 'bool' object is not iterable

Hi @AshRK1997, I believe this is happening because you are using return False and return True when this method needs to return a list of events (hence return [] at the end).

Maybe this code was copied from another program you have? I believe you should be able to get by without them.

1 Like

Noticed a new problem, when I ran rasa shell (Rasa version:- 1.10.7 Python version:-3.7.7)command in terminal, it asked me an input, I gave “hi” as the input, then after a few seconds this error came in:-

Your input ->  hi                                                               
2020-07-10 10:34:59 ERROR    asyncio  - Task exception was never retrieved
future: <Task finished coro=<configure_app.<locals>.run_cmdline_io() done, defined at /home/ashwinrk/anaconda3/envs/machinelearn/lib/python3.7/site-packages/rasa/core/run.py:128> exception=TimeoutError()>
Traceback (most recent call last):
  File "/home/ashwinrk/anaconda3/envs/machinelearn/lib/python3.7/site-packages/rasa/core/run.py", line 134, in run_cmdline_io
    sender_id=conversation_id,
  File "/home/ashwinrk/anaconda3/envs/machinelearn/lib/python3.7/site-packages/rasa/core/channels/console.py", line 151, in record_messages
    async for response in bot_responses:
  File "/home/ashwinrk/anaconda3/envs/machinelearn/lib/python3.7/site-packages/rasa/core/channels/console.py", line 107, in send_message_receive_stream
    async for line in resp.content:
  File "/home/ashwinrk/anaconda3/envs/machinelearn/lib/python3.7/site-packages/aiohttp/streams.py", line 39, in __anext__
    rv = await self.read_func()
  File "/home/ashwinrk/anaconda3/envs/machinelearn/lib/python3.7/site-packages/aiohttp/streams.py", line 328, in readline
    await self._wait('readline')
  File "/home/ashwinrk/anaconda3/envs/machinelearn/lib/python3.7/site-packages/aiohttp/streams.py", line 296, in _wait
    await waiter
  File "/home/ashwinrk/anaconda3/envs/machinelearn/lib/python3.7/site-packages/aiohttp/helpers.py", line 596, in __exit__
    raise asyncio.TimeoutError from None
concurrent.futures._base.TimeoutError
Transport closed @ ('127.0.0.1', 40318) and exception experienced during error handling

Are the two problems corelated? If so is there any solution to this? The rasa run actions commannd was running parellaly. Rasa x and rasa train has no issues.

Edit 1:- I also created a new environment in anaconda with Py 3.6.10, pip installed rasa and rasa-x. But when I run hi, it throws out this error. Will try the output with your suggested modification for actions.py Rasa version here is:- 1.10.7

Edit 2:- Checked with the modifications, but the same error is still being displayed

Hello @erohmensing, I understood it now, seems like messed it up badly with multiple returns. Now, there is no error being thrown but the button is ot being dispatched for some reason. The print function right after the dispatch function is printing out the values properly. The value being sent to dispatch is: [{'title': 'What is the joke', 'payload': '/storying'}].

class Actionstory(Action):
    
    def name(self):
        return "action_story_telling"

    def run(self, dispatcher, tracker, domain):
        try:
            is_name=tracker.get_slot('user_name')
            if is_name == None or is_name == "":
                data = access_db()
                is_name = str(data[0])
            conn = sqlite3.connect(DB_file_name)

            c = conn.cursor()
            c.execute("SELECT name FROM sqlite_master WHERE type='table';")
            tables=[v[0] for v in c.fetchall() if v[0] != "sqlite_sequence"]
            

            if "user_story" not in tables:
                
                c.execute("CREATE TABLE user_story(id integer, name text, story integer)")
                c.execute("INSERT INTO user_story VALUES(?, ?,?)",[1, is_name, 1])
                id = 1
                story = 1
                conn.commit()

            else:
                
                c.execute("SELECT id, story FROM user_story ORDER BY id DESC, story DESC LIMIT 1")
                val = c.fetchone()
                id = val[0]
                story = val[1]
                if int(story) == 8:
                    story = 1
                    id = id +1
                    c.execute("INSERT INTO user_story VALUES(?, ?,?)",[id, is_name, story])
                    conn.commit()
                
                

            df = pd.read_csv(STORY_file_name)
            
            x = id - 1
            y = (story * 2)
            listed = df.iat[x,y]
            listed = listed.split("&;")

            for sent in listed:
                dispatcher.utter_message(text=sent)
            y = y + 1
            pay = df.iat[x,y]
            
            c.execute("SELECT story FROM user_story ORDER BY id DESC, story DESC LIMIT 1")
            val = c.fetchone()
            story_update = int(val[0]) + 1
            c.execute("INSERT INTO user_story VALUES(?, ?,?)",[id, is_name, story_update])
            c.execute("SELECT * FROM user_story")
            print(c.fetchall())
            buttons = []
            buttons.append({'title': "{}".format(pay), 'payload': '/storying'})
            if pay != 'yesno':
                dispatcher.utter_message(buttons = buttons)
            print(buttons)
            conn.commit()
            conn.close()
            
        except Error as e:
            print(e)
            
        finally:
            if conn:
                conn.close()

        return []

May I know what is the mistake I did now?

Hello Mam, I suppose the problem is dispatcher.utter_message() isn’t working when we only send buttons alone. It works when I send some text along with it. I am guessing it’s a bug. The issue on rasa shell isn’t resolved yet. Please do help me with that.

Hi @AshRK1997, indeed, you need text with the buttons. You can always pass text = "" to get around that!