13

私はwebsockets + goをいじり始めていますが、Goのwebsocketsで非常に基本的なことを誤解していると思います。

私は単に websocket 接続をリッスンし、それに応じて処理したいと思います。ただし、Go で websocket を使用して表示されるすべての例は、websocket に接続する Web ページを提供しています。これは要件ですか?

以下は、私がセットアップした基本的なエコーサーバーです。

package main

import (
  "fmt"
  "code.google.com/p/go.net/websocket"
  "net/http"
)

func webHandler(ws *websocket.Conn) {
  var s string
  fmt.Fscan(ws, &s)
  fmt.Println("Received: ", s)
}

func main() {
  fmt.Println("Starting websock server: ")
  http.Handle("/echo", websocket.Handler(webHandler))
  err := http.ListenAndServe(":8080", nil)
  if err != nil {
    panic("ListenAndServe: " + err.Error())
  }
}

これは、接続に使用される JavaScript です。

ws = new WebSocket("ws://localhost:8080/echo");
ws.onmessage = function(e) {
    console.log("websock: " + e.data);
};

ただし、これは次のようになります: 'ws://localhost:8080/echo' への WebSocket 接続に失敗しました: 予期しない応答コード: 403

4

2 に答える 2

16

Javascript から Websocket を操作する場合、フレームを直接読み取る必要はほとんどありません。正直なところ、私はそれを行う方法さえわかりません。

幸いなことに、websocket パッケージには既にタイプがあり、Codecこれが自動的に実行されます。私の提案は、事前定義された websocket.Message コーデックを代わりに使用することRecieveですSend

Message は、WebSocket 接続でフレーム内のテキスト/バイナリ データを送受信するためのコーデックです。テキストフレームの送受信には文字列型を使用します。バイナリフレームを送受信するには、[]byte 型を使用します。

websocket.Message を使用すると、webHandler は次のようになります。

func webHandler(ws *websocket.Conn) {
    var in []byte
    if err := websocket.Message.Receive(ws, &in); err != nil {
        return
    }
    fmt.Printf("Received: %s\n", string(in))
    websocket.Message.Send(ws, in)      
}

いいえ、Go が Web ページを提供することは必須ではありません。受け取った 403 エラーは、Go や websocket パッケージとは関係ありません。

于 2013-10-31T14:21:30.290 に答える
11

同様の問題があり、403 エラーの問題は、Go がhttp Origin ヘッダーを処理する方法に関連しています。

Handler は、WebSocket ブラウザー クライアントへの単純なインターフェイスです。Origin ヘッダーがデフォルトで有効な URL であるかどうかをチェックします。func で websocket.Conn.Config().Origin を確認することをお勧めします。Handler の代わりに Server を使用する場合は、websocket.Origin を呼び出して、Handshake 関数でオリジンを確認できます。したがって、Origin ヘッダーを送信しない非ブラウザー クライアントを受け入れたい場合は、 Server を使用できます。ハンドシェイクでオリジンをチェックしません。

Origin チェックを無効にするには、次のようなものを使用する必要があります。

http.HandleFunc("/echo",
    func (w http.ResponseWriter, req *http.Request) {
        s := websocket.Server{Handler: websocket.Handler(webHandler)}
        s.ServeHTTP(w, req)
    });

少なくともそれで問題は解決しました(サーバー間のWebSocket通信)。オリジンヘッダーが一致しない場合も問題を解決できると思います。

于 2014-04-27T13:56:59.590 に答える