问题

按照廖的教程 web 开发中 WSGI 接口,在分别创建了两个文件,并启动服务器文件时报错:

Traceback (most recent call last):
  File "mywsgi_server.py", line 11, in <module>
    httpd = make_server('', 8000, application)
  File "C:\Users\Administrator\AppData\Local\Programs\Python\Python37\lib\wsgirf\simple_server.py", line 153, in make_server
    server = server_class((host, port), handler_class)
  File "C:\Users\Administrator\AppData\Local\Programs\Python\Python37\lib\sockeserver.py", line 452, in __init__
    self.server_bind()
  File "C:\Users\Administrator\AppData\Local\Programs\Python\Python37\lib\wsgirf\simple_server.py", line 50, in server_bind
    HTTPServer.server_bind(self)
  File "C:\Users\Administrator\AppData\Local\Programs\Python\Python37\lib\http\erver.py", line 137, in server_bind
    socketserver.TCPServer.server_bind(self)
  File "C:\Users\Administrator\AppData\Local\Programs\Python\Python37\lib\sockeserver.py", line 466, in server_bind
    self.socket.bind(self.server_address)
OSError: [WinError 10013] 以一种访问权限不允许的方式做了一个访问套接字的尝试。

最后中文提示了错误原因,百度了一下,就是作为服务器端口的 8000 被占用。

如果8000端口已被其他程序占用,启动将失败,请修改成其他端口

解决

将创建服务器函数 make_server() 的端口参数改成其他端口,比如 8080。

为确保修改后的端口未被占用,可以使用指令查看端口使用情况。

我使用的 windows7 系统,
查看端口使用:

netstat -ano|findstr 8000

若端口未被占用,则不显示内容;
若端口已被占用,会显示类似如下的结果:

# 连接类型 监听地址              来源地址                监听状态        进程号
  TCP    0.0.0.0:8000           0.0.0.0:0              LISTENING       6472
  TCP    0.0.0.0:18000          0.0.0.0:0              LISTENING       6472
  TCP    127.0.0.1:8000         127.0.0.1:52348        TIME_WAIT       0
  TCP    127.0.0.1:8000         127.0.0.1:52353        TIME_WAIT       0
  TCP    127.0.0.1:8000         127.0.0.1:52355        TIME_WAIT       0
  TCP    127.0.0.1:8000         127.0.0.1:52358        TIME_WAIT       0
  TCP    127.0.0.1:8000         127.0.0.1:52364        TIME_WAIT       0
  TCP    127.0.0.1:8000         127.0.0.1:52368        TIME_WAIT       0
  TCP    127.0.0.1:8000         127.0.0.1:52371        TIME_WAIT       0
  TCP    127.0.0.1:8000         127.0.0.1:52377        TIME_WAIT       0
  TCP    127.0.0.1:8000         127.0.0.1:52378        TIME_WAIT       0
  TCP    127.0.0.1:52358        127.0.0.1:8000         TIME_WAIT       0
  TCP    127.0.0.1:52368        127.0.0.1:8000         TIME_WAIT       0
  TCP    127.0.0.1:52371        127.0.0.1:8000         TIME_WAIT       0

查看占用端口的进程:

tasklist | findstr 6472

# 结果如下:
进程名                        端口号 执行方式                         内存(猜测) 
CLodopPrint32.exe             6472 Console                    1     30,464 K

结束占用端口的进程:

taskkill /pid 3304 /F

我尝试过多次杀死这个进程,但它都顽强地重新启动了,所以 8000 端口一直被占用着。没办法,只能改端口了。

附 WSGI 参考代码

mywsgi.py

#!/usr/bin/env python3
# -*- coding:utf-8 -*-

# web 相应处理函数

def application(environ, start_response):
    start_response('200 OK', [('Content-Type', 'text/html')])
    body = '<h1>Hello, %s!</h1>' % (environ['PATH_INFO'][1:] or 'web')
    return [body.encode('utf-8')]

mywsgi_server.py

#!/usr/bin/env python3
# -*- coding:utf-8 -*-

# server
# 从 wsgiref 模块导入,该模块只做开发和测试使用,又名 wsgi 参考
from wsgiref.simple_server import make_server
# 导入我们自己编写的 application 函数
from mywsgi import application

# 创建一个服务器,IP 地址为空,端口是8000,处理函数是 application
httpd = make_server('', 8080, application)
print('Serving Http on port 8080...')
# 开始监听 HTTP 请求:
httpd.serve_forever()

python mywsgi_server.py 启动 server, 然后通过浏览器输入 http://localhost:8080,即可看到返回结果。