socket.error:[Errno 48]地址已在使用中

问题:socket.error:[Errno 48]地址已在使用中

我正在尝试从Mac终端使用python设置服务器。

我导航到文件夹位置的一种用法:

python -m SimpleHTTPServer

但这给了我错误:

socket.error: [Errno 48] Address already in use

之前,我曾使用同一命令为计算机中不同位置的其他网站打开连接。

I’m trying to set up a server with python from mac terminal.

I navigate to folder location an use:

python -m SimpleHTTPServer

But this gives me error:

socket.error: [Errno 48] Address already in use

I had previously open a connection using the same command for a different website in a different location in my machine.


回答 0

您已经有一个绑定到默认端口(8000)的进程。如果您之前已经运行过相同的模块,则很可能该进程仍绑定到端口。首先尝试找到其他过程:

$ ps -fA | grep python
  501 81651 12648   0  9:53PM ttys000    0:00.16 python -m SimpleHTTPServer

包含命令参数,因此,SimpleHTTPServer如果有多个python进程处于活动状态,则可以发现其中一个正在运行。您可能想测试是否http://localhost:8000/仍然显示本地文件的目录列表。

第二个数字是进程号;通过发送信号来停止服务器:

kill 81651

这发送一个标准SIGTERM信号;如果该过程没有响应,则您可能不得不采用更严格的方法,例如发送SIGKILLkill -s KILL <pid>kill -9 <pid>)信号。有关更多详细信息,请参见Wikipedia

可替代地,一个上运行服务器不同端口,通过指定在命令行上的备用端口:

$ python -m SimpleHTTPServer 8910
Serving HTTP on 0.0.0.0 port 8910 ...

然后以方式访问服务器http://localhost:8910; 如果8910尚未使用该端口,则可以是1024或更高版本中的任何数字。

You already have a process bound to the default port (8000). If you already ran the same module before, it is most likely that process still bound to the port. Try and locate the other process first:

$ ps -fA | grep python
  501 81651 12648   0  9:53PM ttys000    0:00.16 python -m SimpleHTTPServer

The command arguments are included, so you can spot the one running SimpleHTTPServer if more than one python process is active. You may want to test if http://localhost:8000/ still shows a directory listing for local files.

The second number is the process number; stop the server by sending it a signal:

kill 81651

This sends a standard SIGTERM signal; if the process is unresponsive you may have to resort to tougher methods like sending a SIGKILL (kill -s KILL <pid> or kill -9 <pid>) signal instead. See Wikipedia for more details.

Alternatively, run the server on a different port, by specifying the alternative port on the command line:

$ python -m SimpleHTTPServer 8910
Serving HTTP on 0.0.0.0 port 8910 ...

then access the server as http://localhost:8910; where 8910 can be any number from 1024 and up, provided the port is not already taken.


回答 1

简单的解决方案:

  1. 使用port查找过程8080

    sudo lsof -i:8080

  2. 杀死它:

    kill XXXX

Simple solution:

  1. Find the process using port 8080:
`sudo lsof -i:8080`
  1. Kill the process on that port:
`kill $PID`

PID is got from step 1’s output.


回答 2

 sudo lsof -i:5000

这将为您提供使用端口的进程列表(如果有)。给定进程列表后,使用PID列上的ID终止进程使用

 kill 379 #use the provided PID

Use

 sudo lsof -i:5000

This will give you a list of processes using the port if any. Once the list of processes is given, use the id on the PID column to terminate the process use

 kill 379 #use the provided PID

回答 3

顺便说一句,为防止发生这种情况,只需在SimpleHTTPServer仍正常运行时在终端中按Ctrl+ C。这将“正确地”停止服务器并释放端口,因此您不必在重新启动服务器之前再次查找并终止该进程。

(Mods:我确实尝试过将此评论放在它所属的最佳答案上,但是我没有足够的声誉。)

By the way, to prevent this from happening in the first place, simply press Ctrl+C in terminal while SimpleHTTPServer is still running normally. This will “properly” stop the server and release the port so you don’t have to find and kill the process again before restarting the server.

(Mods: I did try to put this comment on the best answer where it belongs, but I don’t have enough reputation.)


回答 4

简单的一行命令即可删除它,在终端中键入以下命令,

ps -a

这将列出所有进程,签出Python正在使用的结账,并在终端中键入bellow命令,

kill -9 (processID) 

例如杀死-9 33178

Simple one line command to get rid of it, type below command in terminal,

ps -a

This will list out all process, checkout which is being used by Python and type bellow command in terminal,

kill -9 (processID) 

For example kill -9 33178


回答 5

您也可以在第二高的可用端口上服务,在Python中执行以下操作:

import SimpleHTTPServer
import SocketServer

Handler = SimpleHTTPServer.SimpleHTTPRequestHandler

port = 8000
while True:
    try:
        httpd = SocketServer.TCPServer(('', port), Handler)
        print 'Serving on port', port
        httpd.serve_forever()
    except SocketServer.socket.error as exc:
        if exc.args[0] != 48:
            raise
        print 'Port', port, 'already in use'
        port += 1
    else:
        break

如果您需要对其他实用程序执行相同的操作,则作为bash脚本可能会更方便:

#!/usr/bin/env bash

MIN_PORT=${1:-1025}
MAX_PORT=${2:-65535}

(netstat -atn | awk '{printf "%s\n%s\n", $4, $4}' | grep -oE '[0-9]*$'; seq "$MIN_PORT" "$MAX_PORT") | sort -R | head -n 1

将该名称设置为可执行文件,get-free-port您可以执行以下操作:

someprogram --port=$(get-free-port)

这不如原生Python方法可靠,因为bash脚本无法捕获端口-另一个进程可以在进程捕获端口之前捕获端口(竞赛条件)-但在使用不支持该功能的实用程序时仍然足够有用没有自己尝试的方法。

You can also serve on the next-highest available port doing something like this in Python:

import SimpleHTTPServer
import SocketServer

Handler = SimpleHTTPServer.SimpleHTTPRequestHandler

port = 8000
while True:
    try:
        httpd = SocketServer.TCPServer(('', port), Handler)
        print 'Serving on port', port
        httpd.serve_forever()
    except SocketServer.socket.error as exc:
        if exc.args[0] != 48:
            raise
        print 'Port', port, 'already in use'
        port += 1
    else:
        break

If you need to do the same thing for other utilities, it may be more convenient as a bash script:

#!/usr/bin/env bash

MIN_PORT=${1:-1025}
MAX_PORT=${2:-65535}

(netstat -atn | awk '{printf "%s\n%s\n", $4, $4}' | grep -oE '[0-9]*$'; seq "$MIN_PORT" "$MAX_PORT") | sort -R | head -n 1

Set that up as a executable with the name get-free-port and you can do something like this:

someprogram --port=$(get-free-port)

That’s not as reliable as the native Python approach because the bash script doesn’t capture the port — another process could grab the port before your process does (race condition) — but still may be useful enough when using a utility that doesn’t have a try-try-again approach of its own.


回答 6

我是Python的新手,但是经过简短的研究,我发现这是典型的套接字绑定。碰巧的是,套接字仍在使用中,您可能必须等待使用它。或者,您可以添加:

tcpSocket.setsockopt(socket.SOL_SOCKET, socket.SO_REUSEADDR, 1)

这将使端口在较短的时间内可用。就我而言,它几乎可以立即使端口可用。

I am new to Python, but after my brief research I found out that this is typical of sockets being binded. It just so happens that the socket is still being used and you may have to wait to use it. Or, you can just add:

tcpSocket.setsockopt(socket.SOL_SOCKET, socket.SO_REUSEADDR, 1)

This should make the port available within a shorter time. In my case, it made the port available almost immediately.


回答 7

以防万一以上解决方案不起作用:

  1. 获取您的进程正在监听的端口:

    $ ps斧| grep python

  2. 杀死进程

    $杀死PROCESS_NAME

Just in case above solutions didn’t work:

  1. Get the port your process is listening to:

    $ ps ax | grep python

  2. Kill the Process

    $ kill PROCESS_NAME


回答 8

我有一个树莓派,并且正在使用python网络服务器(使用Flask)。我已经尝试了以上所有内容,唯一的解决方案是关闭terminal(shell),然后再次打开它。或重新启动树莓派,因为没有什么可以阻止该网络服务器…

I have a raspberry pi, and I am using python web server (using Flask). I have tried everything above, the only solution is to close the terminal(shell) and open it again. Or restart the raspberry pi, because nothing stops that webserver…


回答 9

您可以使用允许服务器重用地址allow_reuse_address

服务器是否允许重用地址。默认值为False,可以在子类中设置以更改策略。

import SimpleHTTPServer, SocketServer
PORT = 8000
httpd = SocketServer.TCPServer(("", PORT), SimpleHTTPServer.SimpleHTTPRequestHandler)
httpd.allow_reuse_address = True
print "Serving at port", PORT
httpd.serve_forever()

You can allow the server to reuse an address with allow_reuse_address.

Whether the server will allow the reuse of an address. This defaults to False, and can be set in subclasses to change the policy.

import SimpleHTTPServer, SocketServer
PORT = 8000
httpd = SocketServer.TCPServer(("", PORT), SimpleHTTPServer.SimpleHTTPRequestHandler)
httpd.allow_reuse_address = True
print "Serving at port", PORT
httpd.serve_forever()