Warning: file_get_contents(/data/phpspider/zhask/data//catemap/3/sockets/2.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
Sockets 如何响应http连接请求?_Sockets_Http_Proxy - Fatal编程技术网

Sockets 如何响应http连接请求?

Sockets 如何响应http连接请求?,sockets,http,proxy,Sockets,Http,Proxy,我想在kotlin中创建一个带有套接字的代理。我创建了一个套接字服务器,它将客户端google.com连接到一个套接字。来自google的http请求是: CONNECT www.google.com:443 HTTP/1.1 Host: www.google.com:443 Proxy-Connection: keep-alive User-Agent: Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, l

我想在kotlin中创建一个带有套接字的代理。我创建了一个套接字服务器,它将客户端google.com连接到一个套接字。来自google的http请求是:

CONNECT www.google.com:443 HTTP/1.1
Host: www.google.com:443
Proxy-Connection: keep-alive
User-Agent: Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/76.0.3809.132 Safari/537.36
因此,我向套接字发送:

HTTP/1.1 200 Connection Established
Connection: close
然后谷歌发送:

; 7����r���9 ����l&�����cO��9���� �.rW�Vs9�T���}�$_aX�ys��&�X "���+�/�,�0̨̩�� � � / 5 
 ���        www.google.com   �   

zz       #     hhttp/1.1       
      3 + )zz     
(��>�%܇�    �fT5
��5��ue�u��` -  + 
**   ZZ   ) � � +c���>L����#9�����'���Ʌͩ�5��h�Bn��O�G)��    ����f�^���S�d|bC�7VT5�:���^�QSRך`MM�g#�[�|\�T�9h@�K:7?��t��49   �;`�ʛ�"��ٹ��9����H�f�@��=�����2���(��T)B�`�#�nhS���!뷊��E�ao����/z)e��}���,>�����G��B�� ! ��OF�p�-�>q

我使用新的ssl套接字将这些字节发送到域google.com和端口443,但这不起作用。答复是:

HTTP/1.0 400 Bad Request
Content-Length: 54
Content-Type: text/html; charset=UTF-8
Date: Sat, 31 Aug 2019 14:16:46 GMT

<html><title>Error 400 (Bad Request)!!1</title></html>
我的代码:

fun createServerSocket() {
 println("Starting Server")

        val server_socket = ServerSocket(555)

        Thread{
            val connection_socket = server_socket.accept()
            //connection_socket.soTimeout = 2000
            _handleConnectionSocket(connection_socket)
        }.start()
    }

private fun _handleConnectionSocket(client_socket: Socket) {
        Thread{
            val client_inputStream = client_socket.getInputStream()
            val client_outputStream = client_socket.getOutputStream()
            val client_bufferedWriter = BufferedWriter(OutputStreamWriter(client_outputStream))

            val ssf = SSLSocketFactory.getDefault() as SSLSocketFactory
            val server_socket = ssf.createSocket("google.com", 443)
            val server_inputStream = server_socket.getInputStream()
            val server_outputStream = server_socket.getOutputStream()

            var should_save = false
            Thread{
                try {
                    val buffer = ByteArray(4096)
                    do {
                        val read = client_inputStream.read(buffer)
                        if (should_save) {
                            if (read > 0) {
                                server_outputStream.write(buffer, 0, read)
                                if (client_inputStream.available() < 1)
                                    server_outputStream.flush()
                            }
                        }
                    } while (read >= 0)
                } catch (e: java.net.SocketTimeoutException) {}
            }.start()
            Thread.sleep(1000)

            should_save = true
            val client_success_response =
                """
                HTTP/1.1 200 Connection Established
                Connection: close

                """.trimIndent()

            client_bufferedWriter.appendln(client_success_response)
            client_bufferedWriter.flush()

            Thread.sleep(800)
            try {
                val buffer = ByteArray(4096)
                do {
                    val read = server_inputStream.read(buffer)
                    if (read > 0) {
                        client_outputStream.write(buffer, 0, read)
                        if (server_inputStream.available() < 1)
                            client_outputStream.flush()
                    }
                } while (read >= 0)
            } catch (e: java.net.SocketTimeoutException) {}

            println("Fertig")
        }.start()
    }


我做错了什么?

根据代码,您似乎了解了CONNECT的工作原理。其工作应如下:

客户端浏览器向代理发送一个连接请求,其中包括主机名和要连接的端口。 代理将创建一个TCP而不是SSL,因为在您的情况下,它将连接到请求的服务器。 如果成功建立此连接,代理将发送HTTP/1.1 200已建立的连接。。。对浏览器的响应。 从那时起,代理将简单地在客户端和服务器之间双向转发所有数据。
我猜你所描述的并不是你实际做的。请显示实际代码。请注意,这些是二进制数据TLS握手和加密数据,因此在您的代码和问题中都应将它们视为二进制数据,即,将它们作为文本包含在显示中是没有意义的,将数据编码为十六进制。此外,您似乎混淆了客户端和服务器:连接是由客户端浏览器而不是google发送的。类似的二进制输出是从客户端而不是谷歌。好的,谢谢。如果这是握手,我怎么能从谷歌那里得到请求?谷歌没有请求。在HTTP和HTTPS中,客户端浏览器发送请求,服务器google在收到客户端的请求后发送响应。但在连接的情况下,您只需在客户端浏览器和服务器google之间创建一个隧道,并将所有未更改的数据从客户端转发到服务器,从服务器转发到客户端。您处理的唯一HTTP请求是从客户端到代理的连接请求,而代理发送到客户端的唯一HTTP响应。从那时起,所有的事情都会被代理转发。是的,对不起。我是如何从浏览器(例如谷歌搜索)获得请求的?我想你会完全错误地理解CONNECT的工作原理。客户端浏览器向代理发送一个连接请求,其中包括主机名和要连接的端口。代理创建到请求服务器的TCP而不是SSL连接。如果成功建立此连接,代理将发送HTTP/1.1 200已建立的连接。。。对浏览器的响应。从那时起,代理将简单地在客户端和服务器之间双向转发所有数据。