Paho MQTT не работает с Flask (механизм приложений Google)

1

В моем приложении "Ящик для Google" я должен опубликовать сообщение в брокером Mosquitto, который работает локально в терминале с портом 1884.

    import paho.mqtt.client as mqtt
    # ...
    try:
        # publish.single("Car/Command1", dict, hostname='localhost', port=1884)
        client = mqtt.Client('Flask_Publisher')
        client.connect("localhost", 1884, 60)
        client.publish("mytopic", dict)
        client.disconnect()
    except Exception as e:
        logging.warning("Exception occurred: {}".format(e))
        error = e
    # ...

Я запускаю брокера Mosquitto локально на порту 1884 в терминале, набрав следующую команду: sudo mosquitto -p 1884

Для тестирования я пишу скрипт python, который выполняет роль подписчика mqtt.

Но проблема в том, что когда я пытаюсь запустить Flask, он дает мне следующую ошибку (как пойманную из Exception), когда она пытается опубликовать сообщение: [Errno 13] Permission denied

EDIT: полная трассировка

    ERROR    2018-08-30 16:47:52,665 wsgi.py:279] 
Traceback (most recent call last):
  File "/home/santoryu/Scrivania/google-cloud-sdk/platform/google_appengine/google/appengine/runtime/wsgi.py", line 267, in Handle
    result = handler(dict(self._environ), self._StartResponse)
  File "/home/santoryu/Scrivania/IOT/gae/lib/flask/app.py", line 2309, in __call__
    return self.wsgi_app(environ, start_response)
  File "/home/santoryu/Scrivania/IOT/gae/lib/flask/app.py", line 2295, in wsgi_app
    response = self.handle_exception(e)
  File "/home/santoryu/Scrivania/IOT/gae/lib/flask_cors/extension.py", line 161, in wrapped_function
    return cors_after_request(app.make_response(f(*args, **kwargs)))
  File "/home/santoryu/Scrivania/IOT/gae/lib/flask_restful/__init__.py", line 273, in error_router
    return original_handler(e)
  File "/home/santoryu/Scrivania/IOT/gae/lib/flask/app.py", line 1741, in handle_exception
    reraise(exc_type, exc_value, tb)
  File "/home/santoryu/Scrivania/IOT/gae/lib/flask/app.py", line 2292, in wsgi_app
    response = self.full_dispatch_request()
  File "/home/santoryu/Scrivania/IOT/gae/lib/flask/app.py", line 1815, in full_dispatch_request
    rv = self.handle_user_exception(e)
  File "/home/santoryu/Scrivania/IOT/gae/lib/flask_cors/extension.py", line 161, in wrapped_function
    return cors_after_request(app.make_response(f(*args, **kwargs)))
  File "/home/santoryu/Scrivania/IOT/gae/lib/flask_restful/__init__.py", line 273, in error_router
    return original_handler(e)
  File "/home/santoryu/Scrivania/IOT/gae/lib/flask/app.py", line 1718, in handle_user_exception
    reraise(exc_type, exc_value, tb)
  File "/home/santoryu/Scrivania/IOT/gae/lib/flask/app.py", line 1813, in full_dispatch_request
    rv = self.dispatch_request()
  File "/home/santoryu/Scrivania/IOT/gae/lib/flask/app.py", line 1799, in dispatch_request
    return self.view_functions[rule.endpoint](**req.view_args)
  File "/home/santoryu/Scrivania/IOT/gae/app/handlers/my_handler.py", line 44, in funzione1
    client = mqtt.Client('Flask_Publisher')
  File "/home/santoryu/Scrivania/IOT/gae/lib/paho/mqtt/client.py", line 498, in __init__
    self._sockpairR, self._sockpairW = _socketpair_compat()
  File "/home/santoryu/Scrivania/IOT/gae/lib/paho/mqtt/client.py", line 238, in _socketpair_compat
    listensock.bind(("127.0.0.1", 0))
  File "/home/santoryu/Scrivania/google-cloud-sdk/platform/google_appengine/google/appengine/dist27/socket.py", line 227, in meth
    return getattr(self._sock,name)(*args)
  File "/home/santoryu/Scrivania/google-cloud-sdk/platform/google_appengine/google/appengine/api/remote_socket/_remote_socket.py", line 679, in bind
    raise _SystemExceptionFromAppError(e)
error: [Errno 13] Permission denied
  • 0
    Вы пытаетесь подключиться к своему локальному брокеру Mosquitto из развернутого проекта App Engine? Или вы используете оба локально?
  • 0
    Я бегу как локально на самом деле
Показать ещё 5 комментариев
Теги:
flask
google-app-engine
mqtt
mosquitto

1 ответ

2
Лучший ответ

Проблема заключается в том, что SDK App Engine предоставляет изолированную версию модуля socket Python. Когда клиентская библиотека MQTT пытается привязываться к локальному порту, он использует этот изолированный модуль вместо стандартного библиотечного модуля, который он ожидал, и не может привязываться к localhost.

Вы можете обойти это, заменив модуль socket GAE на исходный стандартный библиотечный модуль при работе в режиме разработки, позволяя вам привязываться к localhost.

В файле appengine_config.py:

import os

# Only do the following if we're in development mode
if os.environ.get('SERVER_SOFTWARE', '').startswith('Development'):
    import imp
    import inspect

    # Whitelist the ssl and socket modules
    from google.appengine.tools.devappserver2.python import sandbox
    sandbox._WHITE_LIST_C_MODULES += ['_ssl', '_socket']

    # Use the standard library socket module instead
    real_os_src_path = os.path.realpath(inspect.getsourcefile(os))
    real_socket = os.path.join(os.path.dirname(real_os_src_path), 'socket.py')
    imp.load_source('socket', real_socket)
  • 0
    Сейчас работает. большое спасибо

Ещё вопросы

Сообщество Overcoder
Наверх
Меню