2020/05/10

python-socketioでAttributeError: 'module' object has no attribute 'main_thread'が出る場合の対処法

背景


Python2.7でpython-socketioを使用したとき時、下記のエラーが発生した。
  1. $ python ./test_socketio_client.py
  2. Traceback (most recent call last):
  3. File "./test_socketio_client.py", line 123, in
  4. sio_client = SocketIOClient('127.0.0.1', 10000, 'test', 'secret')
  5. File "./test_socketio_client.py", line 76, in __init__
  6. self.sio_ = socketio.Client()
  7. File "/home/emptyset/.local/lib/python2.7/site-packages/socketio/client.py", line 88, in __init__
  8. threading.current_thread() == threading.main_thread():
  9. AttributeError: 'module' object has no attribute 'main_thread'

記事の目的


python-socketioのAttributeErrorを解決する

原因と対策


エラー原因

threadingモジュールのバージョン問題である。threadingの説明によると、main_thread関数は、バージョン 3.4以降で追加されたメソッドであるため、Python2系では使用できない。

対策

該当モジュールのmain_thread関数を修正する。
  1. python-socketioの該当モジュール(例/home/emptyset/.local/lib/python2.7/site-packages/socketio/client.py)を修正する
  2. 修正前
    1. global original_signal_handler
    2. if original_signal_handler is None and \
    3. threading.current_thread() == threading.main_thread():
    4. original_signal_handler = signal.signal(signal.SIGINT,
    5. signal_handler)
    修正後
    1. global original_signal_handler
    2. if original_signal_handler is None and\
    3. threading.current_thread().isDaemon() is False:
    4. original_signal_handler = signal.signal(signal.SIGINT,
    5. signal_handler)
    Clientのインスタンス生成がmainスレッドでのみ可能になってるが、この部分を削除した。代わりに、スレッドがデーモンかの判定を追加した。(mainスレッド以外がデーモンであると仮定)
  3. python-engineioの該当モジュール(例/home/emptyset/.local/lib/python2.7/site-packages/engineio/client.py)を修正する
  4. 修正前
    1. global original_signal_handler
    2. if original_signal_handler is None and \
    3. threading.current_thread() == threading.main_thread():
    4. original_signal_handler = signal.signal(signal.SIGINT,
    5. signal_handler)
    修正後
    1. global original_signal_handler
    2. if original_signal_handler is None and \
    3. threading.current_thread().isDaemon() is False:
    4. original_signal_handler = signal.signal(signal.SIGINT,
    5. signal_handler)
    Clientのインスタンス生成がmainスレッドでのみ可能になってるが、この部分を削除した。代わりに、スレッドがデーモンかの判定を追加した。(mainスレッド以外がデーモンであると仮定)
  5. 動作確認を行う
    1. $ python ./test_socketio_client.py
    2. Try to connect to server(localhost:10000, namespace="/test", query="secret")
    3. Namespace may be invalid.(namespace="/test")
    4. Connected to server (localhost:10000, namespace="/test", query="secret")
    5. Send message {'test_data': 'send_from_client'} (namespace="/test")
    6. Emit message {'test_data': 'emit_from_client'} (namespace="/test")
    7. Received message {u'test_ack': u'send_from_server'}
    8. Received message {u'test_ack': u'emit_from_server'}
    9. ...

まとめ


  • python-socketioでAttributeError: 'module' object has no attribute 'main_thread'が出る場合の対処法について調査、記載した

参考文献



変更履歴


  1. 2020/05/10: 新規作成

0 件のコメント:

コメントを投稿

MQTTの導入

背景 IoTデバイスの接続環境構築のため、MQTT(mosquitto)の導入を行った。 記事の目的 MQTT(mosquitto)をUbuntuに導入する mosquitto ここではmosquittoについて記載する。 MQTT MQTT(Message Qu...