質問をすることでしか得られない、回答やアドバイスがある。

15分調べてもわからないことは、質問しよう!

新規登録して質問してみよう
ただいま回答率
85.35%
WebSocket

WebSocketとは双方向・全二重コミュニケーションのためのAPIでありプロトコルのことを指します。WebSocketはHTML5に密接に結びついており、多くのウェブブラウザの最新版に導入されています。

Python

Pythonは、コードの読みやすさが特徴的なプログラミング言語の1つです。 強い型付け、動的型付けに対応しており、後方互換性がないバージョン2系とバージョン3系が使用されています。 商用製品の開発にも無料で使用でき、OSだけでなく仮想環境にも対応。Unicodeによる文字列操作をサポートしているため、日本語処理も標準で可能です。

Q&A

解決済

2回答

7552閲覧

pythonでwebsocketを複数稼働したい

hazata

総合スコア13

WebSocket

WebSocketとは双方向・全二重コミュニケーションのためのAPIでありプロトコルのことを指します。WebSocketはHTML5に密接に結びついており、多くのウェブブラウザの最新版に導入されています。

Python

Pythonは、コードの読みやすさが特徴的なプログラミング言語の1つです。 強い型付け、動的型付けに対応しており、後方互換性がないバージョン2系とバージョン3系が使用されています。 商用製品の開発にも無料で使用でき、OSだけでなく仮想環境にも対応。Unicodeによる文字列操作をサポートしているため、日本語処理も標準で可能です。

0グッド

1クリップ

投稿2020/09/18 12:13

編集2020/09/20 09:46

python初学者です、ネットで調べてみたのですがわからなかったので質問させていただきました。
python3,開発環境はJupiter Notebookです。
以下のようなwebSocketに接続し情報を取得するコードを書きましたが

Python

1import json 2import ast 3import websocket 4 5#web_socket OrderBook約定履歴 6def gmo_socket_board(): 7 8 websocket.enableTrace(True) 9 ws = websocket.WebSocketApp('wss://api.coin.z.com/ws/public/v1') 10 11 def on_open(self): 12 message = { 13 "command": "subscribe", 14 "channel": "orderbooks", 15 "symbol": "BTC_JPY" 16 } 17 ws.send(json.dumps(message)) 18 19 def on_message(self, message): 20 dict_message = ast.literal_eval(message) 21 ask_price = dict_message["asks"][0]["price"] #best_ask 22 bid_price = dict_message["bids"][0]["price"] #best_bid 23 print(ask_price,bid_price) 24 25 ws.on_open = on_open 26 ws.on_message = on_message 27 ws.run_forever() 28 29#web_socket Excution約定履歴 30def gmo_socket_trade(): 31 32 websocket.enableTrace(True) 33 ws2 = websocket.WebSocketApp('wss://api.coin.z.com/ws/public/v1') 34 35 def on_open2(self): 36 message2 = { 37 "command": "subscribe", 38 "channel": "trades", 39 "symbol": "BTC_JPY", 40 "option": "TAKER_ONLY" 41 } 42 ws2.send(json.dumps(message2)) 43 44 def on_message2(self, message2): 45 46 dict_message2 = ast.literal_eval(message2) 47 side = dict_message2["side"] 48 price = dict_message2["price"] 49 size = dict_message2["size"] 50 timestamp = dict_message2["timestamp"] 51 52 print(side) 53 print(size) 54 print(price) 55 print(timestamp) 56 print("=======================") 57 58 ws2.on_open = on_open2 59 ws2.on_message = on_message2 60 ws2.run_forever()

として

python

1gmo_socket_board() 2gmo_socket_trade() 3

を実行してもgmo_socket_board()しか接続されません。
タイムラグはあってもいいので両方とも接続できるような方法はございますでしょうか。
よろしくお願いします。

追記
オリジナルのサンプルコードを見ながら下記のようにコードを書き換えてみましたが、やはり同じように初めのsocketのみが接続され、これを停止すると次のsocketが接続されるような動作をします。run_forever()で処理が一時停止しているような感じがします。thread.start_new_thread(run, ())で並列処理させているつもりですがうまく動作しません。よろしくお願いします。

Python

1import websocket 2import ast 3import json 4import time 5try: 6 import thread 7except ImportError: 8 import _thread as thread 9import time 10 11 12def on_message(ws, message): 13 dict_message = ast.literal_eval(message) 14 ask_price = dict_message["asks"][0]["price"] #best_ask 15 bid_price = dict_message["bids"][0]["price"] #best_bid 16 print(ask_price,bid_price) 17 18 19def on_error(ws, error): 20 print(error) 21 22def on_close(ws): 23 print("### closed ###") 24 25def on_message2(ws2, message3): 26 dict_message2 = ast.literal_eval(message3) 27 side = dict_message2["side"] 28 price = dict_message2["price"] 29 size = dict_message2["size"] 30 timestamp = dict_message2["timestamp"] 31 32 print(side) 33 print(size) 34 print(price) 35 print(timestamp) 36 37def on_error2(ws2, error): 38 print(error) 39 40def on_close2(ws2): 41 print("### closed ###") 42 43 44def on_open(ws): 45 def run(*args): 46 47 message2 = { 48 "command": "subscribe", 49 "channel": "orderbooks", 50 "symbol": "BTC_JPY" 51 } 52 53 ws.send(json.dumps(message2)) 54 55 56 print("thread terminating...") 57 thread.start_new_thread(run, ()) 58 59def on_open2(ws2): 60 def run2(*args): 61 62 message3 = { 63 "command": "subscribe", 64 "channel": "trades", 65 "symbol": "BTC_JPY", 66 "option": "TAKER_ONLY" 67 } 68 69 ws2.send(json.dumps(message3)) 70 71 print("thread2 terminating...") 72 thread.start_new_thread(run2, ()) 73 74if __name__ == "__main__": 75 websocket.enableTrace(True) 76 ws = websocket.WebSocketApp("wss://api.coin.z.com/ws/public/v1", 77 on_message = on_message, 78 on_error = on_error, 79 on_close = on_close) 80 ws2 = websocket.WebSocketApp("wss://api.coin.z.com/ws/public/v1", 81 on_message = on_message2, 82 on_error = on_error2, 83 on_close = on_close2) 84 85 ws.on_open = on_open 86 ws.run_forever() 87 88 time.sleep(5) 89 90 ws2.on_open = on_open2 91 ws2.run_forever()

気になる質問をクリップする

クリップした質問は、後からいつでもMYページで確認できます。

またクリップした質問に回答があった際、通知やメールを受け取ることができます。

バッドをするには、ログインかつ

こちらの条件を満たす必要があります。

t_obara

2020/09/18 12:33

websocket2はどこから出てきたのでしょう?エラーになりませんか?
hazata

2020/09/18 13:10

申し訳ありません、エラーになりました。コードを修正いたします
guest

回答2

0

ベストアンサー

両方とも接続する、ということは、接続し続けるWebSocketクライアントを作る必要があります。

オリジナルのGit
https://github.com/websocket-client/websocket-client

に記載されているLong-lived connectionの形式、特にon_openにおいてスレッド実行が必要です。
質問コードは、この部分がかなり違った内容になっています。まずは、オリジナルのサンプルコードを起点に、カスタマイズするべきと思います。

投稿2020/09/18 13:38

toast-uz

総合スコア3266

バッドをするには、ログインかつ

こちらの条件を満たす必要があります。

0

修正依頼にも出ているように、websocket2websocketに修正しないと、gmo_socket_tradeは動作しない。

Diff

1- websocket2.enableTrace(True) 2+ websocket.enableTrace(True) 3- ws2 = websocket2.WebSocketApp('wss://api.coin.z.com/ws/public/v1') 4+ ws2 = websocket.WebSocketApp('wss://api.coin.z.com/ws/public/v1')

この修正を行なっても、最初に呼び出したgmo_socket_boardを終了するまでgmo_socket_tradeは呼び出されない。

gmo_socket_boardは、関数末尾に書かれたrun_foreverによって(Ctrl-Cキーで中断するまで)戻ってこないからだ。実際、ソースの修正後に、

Python

1gmo_socket_board() 2gmo_socket_trade()

を実行して、Ctrl-Cキーでgmo_socket_boardを終了すると、gmo_socket_tradeが実行された。

備考: 利用しているAPIの制限として、

Public WebSocket APIの制限

同一IPからのリクエスト(subscribe, unsubscribe)は、1秒間1回を上限とします。

制限 – APIドキュメント| GMOコイン

とあるので、1秒以内に2つの関数でsubscribeを実行した場合には、後から実行した関数で接続に失敗するだろう。

投稿2020/09/18 13:26

Daregada

総合スコア11990

バッドをするには、ログインかつ

こちらの条件を満たす必要があります。

あなたの回答

tips

太字

斜体

打ち消し線

見出し

引用テキストの挿入

コードの挿入

リンクの挿入

リストの挿入

番号リストの挿入

表の挿入

水平線の挿入

プレビュー

15分調べてもわからないことは
teratailで質問しよう!

ただいまの回答率
85.35%

質問をまとめることで
思考を整理して素早く解決

テンプレート機能で
簡単に質問をまとめる

質問する

関連した質問