使用BaseHTTP使用基本身份验证的Python HTTP Server

时间:2010-11-26 16:34:23

标签: python http-authentication basehttpserver

我很难尝试让基于python的网络服务器工作。

我想进行基本身份验证(发送401标头)并对用户列表进行身份验证。使用“WWW-Authorize”标头发送401响应没有问题,我可以验证用户响应(base64编码的用户名和密码),但是,成功验证后登录框会不断弹出。

import SimpleHTTPServer
import SocketServer
from BaseHTTPServer import BaseHTTPRequestHandler, HTTPServer

class Handler(BaseHTTPRequestHandler):
    ''' Main class to present webpages and authentication. '''
    def do_HEAD(self):
        print "send header"
        self.send_response(401)
        self.send_header('WWW-Authenticate', 'Basic realm=\"Test\"')
        self.send_header('Content-type', 'text/html')
        self.end_headers()

    def do_GET(self):
        ''' Present frontpage with user authentication. '''
        self.do_HEAD()

        if self.headers.getheader('Authorization') == None:
            self.wfile.write('no auth header received')
            pass
        elif self.headers.getheader('Authorization') == 'Basic dGVzdDp0ZXN0':
            self.wfile.write(self.headers.getheader('Authorization'))
            self.wfile.write('authenticated!')
            pass
        else:
            self.wfile.write(self.headers.getheader('Authorization'))
            self.wfile.write('not authenticated')
            pass

httpd = SocketServer.TCPServer(("", 10001), Handler)

httpd.serve_forever()

if __name__ == '__main__':
    main()

首次加载(http:// localhost:10001)登录框弹出,我输入test,test(正确的用户)用户验证确定,但框弹出,如果我点击取消,我到达经过验证的页面......

有人可以帮忙吗?我怀疑这与授权在do_GET下发生的事实有关,每次页面加载时都会触发授权。

2 个答案:

答案 0 :(得分:17)

尝试尺寸:

import SimpleHTTPServer
import SocketServer
from BaseHTTPServer import BaseHTTPRequestHandler, HTTPServer

class Handler(BaseHTTPRequestHandler):
    ''' Main class to present webpages and authentication. '''
    def do_HEAD(self):
        print "send header"
        self.send_response(200)
        self.send_header('Content-type', 'text/html')
        self.end_headers()

    def do_AUTHHEAD(self):
        print "send header"
        self.send_response(401)
        self.send_header('WWW-Authenticate', 'Basic realm=\"Test\"')
        self.send_header('Content-type', 'text/html')
        self.end_headers()

    def do_GET(self):
        ''' Present frontpage with user authentication. '''
        if self.headers.getheader('Authorization') == None:
            self.do_AUTHHEAD()
            self.wfile.write('no auth header received')
            pass
        elif self.headers.getheader('Authorization') == 'Basic dGVzdDp0ZXN0':
            self.do_HEAD()
            self.wfile.write(self.headers.getheader('Authorization'))
            self.wfile.write('authenticated!')
            pass
        else:
            self.do_AUTHHEAD()
            self.wfile.write(self.headers.getheader('Authorization'))
            self.wfile.write('not authenticated')
            pass

httpd = SocketServer.TCPServer(("", 10001), Handler)

httpd.serve_forever()

if __name__ == '__main__':
    main()

答案 1 :(得分:6)

那是因为你无条件地发送401和WWW-Authenticate标题作为回应。只有在请求中没有可接受的身份验证凭据时,您才需要执行此操作。如果您对请求感到满意,请发送200(或任何适当的)并且不再请求身份验证。