brpc icon indicating copy to clipboard operation
brpc copied to clipboard

http协议set-cookie header格式不符合mdn文档要求

Open pirDOL opened this issue 1 year ago • 6 comments

Describe the bug (描述bug)

Set-Cookie - HTTP | MDN

To send multiple cookies, multiple Set-Cookie headers should be sent in the same response.

To Reproduce (复现方法) 使用example/http_c++,server调用多次set-cookie,client只能收到一个set-cookie

Expected behavior (期望行为) 对于set-cookie字段应同时满足http和mdn文档规范要求,否则brpc的http-server会存在功能缺陷

Versions (各种版本) OS: Compiler: brpc: protobuf:

Additional context/screenshots (更多上下文/截图)

pirDOL avatar Mar 18 '24 08:03 pirDOL

多次通过调用SetHeader("Set-Cookie", "xxx")来设置cookie吗?

chenBright avatar Mar 18 '24 09:03 chenBright

@chenBright 根据HttpHeader接口来看,只有SetHeader和AppendHeader,两个接口都不能构造出http server返回响应报文中有多个set-cookie的场景,可以使用如下代码构造复现场景。 使用brpc channel访问这个server获取响应后,通过controller.http_response获取set-cookie的值是a=b;,c=d;,这个不是一个合法的set-cookie格式

#!/noah/bin/python
import socket

def handle_request(client_socket):
    request = client_socket.recv(1024)
    response = 'HTTP/1.1 200 OK\r\n'
    response += 'Set-Cookie: a=b;\r\n'
    response += 'Set-Cookie: c=d;\r\n'
    response += 'Content-Type: text/plain\r\n'
    response += 'Content-Length: 4\r\n'
    response += '\r\n'
    response += 'echo'

    client_socket.sendall(response.encode())
    client_socket.close()

def start_server(port):
    server_socket = socket.socket(socket.AF_INET, socket.SOCK_STREAM)
    server_socket.setsockopt(socket.SOL_SOCKET, socket.SO_REUSEADDR, 1)
    server_socket.bind(('0.0.0.0', port))
    server_socket.listen(5)
    print('Server is listening on port {port}...')

    while True:
        client_socket, client_address = server_socket.accept()
        print('Accepted connection from {client_address}')
        handle_request(client_socket)

if __name__ == '__main__':
    PORT = 1024
    start_server(PORT)

pirDOL avatar Mar 18 '24 10:03 pirDOL

RFC-7230 Field Order In practice, the "Set-Cookie" header field ([RFC6265]) often appears multiple times in a response message and does not use the list syntax, violating the above requirements on multiple header fields with the same name. Since it cannot be combined into a single field-value, recipients ought to handle "Set-Cookie" as a special case while processing header fields. (See Appendix A.2.3 of [Kri2001] for details.)

RFC-6265 Overview Origin servers SHOULD NOT fold multiple Set-Cookie header fields into a single header field. The usual mechanism for folding HTTP headers fields (i.e., as defined in [RFC2616]) might change the semantics of the Set-Cookie header field because the %x2C (",") character is used by Set-Cookie in a way that conflicts with such folding.

根据HTTP标准定义,不能将多个Set-Cookie合并到一个header。bRPC的处理方式有问题,需要针对Set-Cookie进行特殊处理。

另外,多个Cookie之间不能使用,分隔,应该要用;分隔。

chenBright avatar Mar 18 '24 15:03 chenBright

@chenBright

;Attributes分隔符,因此如果bRPC中需要特殊处理应使用其他符号

另外,多个Cookie之间不能使用,分隔,应该要用;分隔。

pirDOL avatar Mar 19 '24 03:03 pirDOL

@chenBright

;Attributes分隔符,因此如果bRPC中需要特殊处理应使用其他符号

另外,多个Cookie之间不能使用,分隔,应该要用;分隔。

嗯嗯,我指的是cookie这个header。

set-cookie这个header的话,HttpHeader不将其合并,每个set-cookie独立一项。

chenBright avatar Mar 19 '24 12:03 chenBright

@pirDOL 试试 #2577 能不能解决问题

chenBright avatar Mar 20 '24 08:03 chenBright