2016-07-27 4 views
0

현재 기본 사항을 완벽하게 설명하지 못하는 몇 가지 기본 websocket 예제를 테스트하고 있습니다. C#으로 서버에 리스너를 만들고 요청을 웹 소켓으로 업그레이드하는 방법을 알고 있습니다. 자바 스크립트에서 서버로 보낸 문자열을 검색하는 데 도움이 필요합니다.C# websocket server 자바 스크립트에서 텍스트를 수신합니다.

C# 코드 : 웹 소켓에 연결하기위한

class Program 
{ 
    private static void ThreadProc(object obj) 
    { 
     var client = (TcpClient)obj; 

     var address = client.Client.RemoteEndPoint.ToString().Split(':'); 

     Console.WriteLine(String.Format("A client is connected from {0}", address[0])); 

     NetworkStream stream = client.GetStream(); 

     //enter to an infinite cycle to be able to handle every change in stream 
     while (true) 
     { 
      while (!stream.DataAvailable) ; 

      Byte[] bytes = new Byte[client.Available]; 

      stream.Read(bytes, 0, bytes.Length); 

      //translate bytes of request to string 
      String data = Encoding.UTF8.GetString(bytes); 

      if (new Regex("^GET").IsMatch(data)) 
      { 
       Byte[] response = Encoding.UTF8.GetBytes("HTTP/1.1 101 Switching Protocols" + Environment.NewLine 
        + "Connection: Upgrade" + Environment.NewLine 
        + "Upgrade: websocket" + Environment.NewLine 
        + "Sec-WebSocket-Accept: " + Convert.ToBase64String(
         SHA1.Create().ComputeHash(
          Encoding.UTF8.GetBytes(
           new Regex("Sec-WebSocket-Key: (.*)").Match(data).Groups[1].Value.Trim() + "258EAFA5-E914-47DA-95CA-C5AB0DC85B11" 
          ) 
         ) 
        ) + Environment.NewLine 
        + Environment.NewLine); 

       stream.Write(response, 0, response.Length); 
      } 
      else 
      { 
       Console.WriteLine(data); 
      } 
     } 
    } 

    static void Main(string[] args) 
    { 
     TcpListener server = new TcpListener(IPAddress.Parse("127.0.0.1"), 80); 

     server.Start(); 
     Console.WriteLine("Server has started on 127.0.0.1:80.{0}Waiting for a connection...", Environment.NewLine); 

     while (true) 
     { 
      var clientConnection = server.AcceptTcpClient(); 
      ThreadPool.QueueUserWorkItem(ThreadProc, clientConnection); 
     } 

    } 
} 

자바 스크립트.

var host = window.location.origin.replace("http", "ws"); 
    var socket = new WebSocket("ws://127.0.0.1:80"); 

    socket.onopen = function (openEvent) { 
     console.log("Socket connection is open."); 
     sendTextMessage(); 
    }; 

    function sendTextMessage() { 
     if (socket.readyState != WebSocket.OPEN) 
     { 
      console.log("Socket is not open for connection."); 
      return; 
     } 
     socket.send("MDN"); 
    } 

업데이트 나는 메시지가 지금에 오는 것을 볼 수 있습니다. 그러나 MDN 문자열을 얻지 못하고 일부 펑키 문자를 다시 얻습니다. 변경 내용을 표시하도록 C# 코드를 업데이트했습니다.

저는 자바 스크립트에서 내 서버로 문자열을 보내고 콘솔에서 해당 문자열을 읽으려고합니다. 다른 사람이 여러 웹 브라우저를 동시에 연결하는 방법을 더 설명 할 수 있다면 동시에 멋지게 될 것입니다. 또한 누군가가 연결된 모든 웹 브라우저로 메시지를 보내는쪽으로 나를 가리킬 수 있다면하십시오.

복제본 인 경우 올바른 방향으로 알려주십시오.

+0

동일한 문제가 있고이 게시물의 기능인 DecodeMessage가 나를 도왔습니다. http://stackoverflow.com/questions/34372639/sending-a-message-back-to-client-using-tcplistener-server/34372944 –

+0

실제로, 나는이 코드에 많은 문제가 있었고, 지금은 SignalR을 사용하고 있습니다.이 예제는 많은 도움이됩니다. https://code.msdn.microsoft.com/windowsdesktop/Using-SignalR-in-WinForms- f1ec847b –

답변

1

질문 : 응답하는 데 필요한 속성을

while(serverIsOn){ 
    TcpClient cliTemp = server.AcceptTcpClient(); 
    NetworkStream netTemp = cliTemp.GetStream(); 
    Client cli = new Client(Necessary attributes); 
    clientsList.Add(cli); 
} 

하나 개 연결 (클래스 클라이언트 만들기) 새 개체의 모든 속성을 넣어 얻을 때마다 "가 동시에 연결된 여러 웹 브라우저"/해당 클라이언트의 예 (하여 TcpClient,는 NetworkStream, CLIENTNAME ...)에서받을

새로운 루프 클라이언트 목록을 통해 호출 읽기 전에 [또 다른 스레드] :

루프 (clientsList)

if(cli.networkStream.DataAvailable){ 
    cli.networkStream.Read(buffer, 0, buffer.Lenght); 
} 

질문 "업데이트라는 메시지가 지금에 오는 것을 볼 수 있습니다. 그러나 MDN 문자열을 얻지 못하고 일부 펑키 문자를 다시 얻습니다. 변화를 보여 내 C# 코드를 업데이트했습니다. " 나는 당신이 자바 스크립트에서 메시지 응답 메시지가 메시지 해독하는 키 코드가 얼마나 오래 최종 경우 표시 특정 비트를 포함 말합니다이 튜토리얼 https://developer.mozilla.org/en-US/docs/Web/API/WebSockets_API/Writing_WebSocket_server

을 다음 한 가정 ! 메시지 여기서 작은 해결책 :

public byte[] javaScriptUser(Byte[] data) 
    { 
     //encoded[1] => size of msg 
     Byte[] encoded = new Byte[((int)data[1] - 128)]; 
     Array.Copy(data, 6, encoded, 0, encoded.Length); 
     Byte[] decoded = new Byte[((int)data[1] - 128)]; 

     //KeyCode positions 
     Byte[] key = new Byte[4] { data[2], data[3], data[4], data[5] }; 

     for (int i = 0; i < encoded.Length; i++) 
     { 
      decoded[i] = (Byte)(encoded[i]^key[i % 4]); 
     } 
     Array.Copy(decoded, data, decoded.Length); 
     return decoded; 
    } 

이 부분을 포함하지 않는 ("는 126에서 다음 2 바이트 (16 비트 부호없는 정수)의 경우 (127), 다음 8 바이트 인 경우 (64 비트 부호없는 정수) 길이입니다. ") 이 마지막 부분은 약간 지저분한 것이지만 몇 분 안에 끝났습니다. 그러나 당신이 더 잘 만들 수 있다고 확신합니다.

관련 문제