pythonflaskviberviber-botviber-bot-python

Viber Bot does not start


I run my Viber bot through gunicorn and flask on server. But when I do curl request I get error

* Curl_http_done: called premature == 0
* Connection #0 to host chatapi.viber.com left intact
{"status":1,"status_message":"Result[HttpRequest[POST / HTTP/1.1]@3f742f36 > HttpResponse[HTTP/1.1 500 INTERNAL SERVER ERROR]@16f0ed02] null","chat_hostname":"SN-CHAT-01_"}

when I open url my site I have

Method Not Allowed

The method is not allowed for the requested URL.

app.py

from flask import Flask, request, Response

from viberbot import Api
from viberbot.api.bot_configuration import BotConfiguration
from viberbot.api.messages import KeyboardMessage
from viberbot.api.messages.text_message import TextMessage
import logging

from viberbot.api.viber_requests import ViberFailedRequest
from viberbot.api.viber_requests import ViberMessageRequest
from viberbot.api.viber_requests import ViberSubscribedRequest

from keyboard import keyboard_menu

logger = logging.getLogger()
logger.setLevel(logging.DEBUG)
handler = logging.StreamHandler()
formatter = logging.Formatter('%(asctime)s - %(name)s - %(levelname)s - %(message)s')
handler.setFormatter(formatter)
logger.addHandler(handler)

app = Flask(__name__)
viber = Api(BotConfiguration(
    name='name',
    avatar='https://upload.wikimedia.org/wikipedia/commons/9/9a/Gull_portrait_ca_usa.jpg',
    auth_token='token'
))

@app.route('/', methods=['POST'])
def incoming():
    logger.debug("received request. post data: {0}".format(request.get_data()))
    # every viber message is signed, you can verify the signature using this method
    if not viber.verify_signature(request.get_data(), request.headers.get('X-Viber-Content-Signature')):
        return Response(status=403)

    # this library supplies a simple way to receive a request object
    viber_request = viber.parse_request(request.get_data())

    if isinstance(viber_request, ViberMessageRequest):
        message = TextMessage(text="test", keyboard=keyboard_menu)
        # lets echo back
        viber.send_messages(viber_request.sender.id, [
            message
        ])

    elif isinstance(viber_request, ViberSubscribedRequest):
        viber.send_messages(viber_request.get_user.id, [
            TextMessage(text="thanks for subscribing!")
        ])
    elif isinstance(viber_request, ViberFailedRequest):
        logger.warn("client failed receiving message. failure: {0}".format(viber_request))

    return Response(status=200)

wsgi.py

from app import app

if __name__ == "__main__":
    app.run()

curl

curl -# -i -g -H "X-Viber-Auth-Token:token" -d @viber.json -X POST https://chatapi.viber.com/pa/set_webhook -v

viber.json

{
  "url": "https://my.site.com"
}

What am I doing wrong?


Solution

  • Try to send POST request to that endpoint, like Viber server would do that, but using cURL. So you'll be able to see the error.

    Or update root logger to see a reason of 500 error. Propose to configure it like in documentation (see here for more details):

    from logging.config import dictConfig
    
    dictConfig({
        'version': 1,
        'formatters': {'default': {
            'format': '[%(asctime)s] %(levelname)s in %(module)s: %(message)s',
        }},
        'handlers': {'wsgi': {
            'class': 'logging.StreamHandler',
            'stream': 'ext://flask.logging.wsgi_errors_stream',
            'formatter': 'default'
        }},
        'root': {
            'level': 'INFO',
            'handlers': ['wsgi']
        }
    })
    
    app = Flask(__name__)
    

    And the last think:

    when I open url my site I have

    Method Not Allowed
    
    The method is not allowed for the requested URL.
    

    That's because when you are opening that url in browser it sends GET request, but endpoints accepts only POST http method.