在Django
应用
程序中,如果要启动后台进程并使用
Streaming
HttpResponse将进程输出发送到客户端,则会出现问题:当客户端从流中断开连接时,后台进程仍然在继续运行。为了解决这个问题,我们需要确保在客户端断开连接时退出P
open
进程。
以下是
解决方案
的示例代码:
import subprocess
from django.http import StreamingHttpResponse
def my_streaming_view(request):
# 启动后台进程来产生输出
process = subprocess.Popen(['my_long_running_command'], stdout=subprocess.PIPE)
def stream_response():
# 连续从进程输出流读取数据并发送到客户端
while True:
output = process.stdout.readline()
if output == b'' and process.poll() is not None:
break
yield output
# 使用流响应将进程输出发送到客户端
response = StreamingHttpResponse(stream_response(), content_type='text/plain')
response['Content-Disposition'] = 'attachment; filename="output.txt"'
# 关闭进程,当客户端从流中断开连接时
def close_process(response):
response.streaming_content.close()
process.terminate()
response.streaming_content.on_close(lambda: close_process(response))
return response
在这个示例代码中,我们使用Python的子进程模块subprocess启动一个后台进程,并从进程的stdout流中连续读取输出数据并发送到客户端。当客户端从流中断开连接时,我们使用StreamingHttpResponse对象的on_close()方法来关闭进程。
使用这个方案,当客户端从流中断开连接时,我们可以优雅地退出Popen进程。