bem*_*3ry 10 html javascript python
好吧,我设法让它按我想要的方式工作(虽然有些/大多数人可能不同意这种方法).我按照下面的建议使用了Flask.可能被视为"错误"的部分是404检查循环.这是不正确的设计,如果它持续太长时间,会导致某些浏览器出现"卡住脚本"错误.但是,我想运行的脚本不会持续很长时间才能成为问题.
感谢您的帮助,如果您有任何其他建议,请与我们联系.
烧瓶应用:
import threading
import subprocess
import os
import sys
from flask import Flask
from flask import render_template, abort
app = Flask(__name__)
app.debug = True
def run_script():
theproc = subprocess.Popen([sys.executable, "run_me.py"])
theproc.communicate()
@app.route('/')
def index():
return render_template('index.html')
@app.route('/generate')
def generate():
threading.Thread(target=lambda: run_script()).start()
return render_template('processing.html')
@app.route('/is_done')
def is_done():
hfile = "templates\\itworked.html"
if os.path.isfile(hfile):
return render_template('itworked.html')
else:
abort(404)
if __name__ == "__main__":
app.run()
Run Code Online (Sandbox Code Playgroud)
processing.html:
<!DOCTYPE html>
<html>
<head>
<script src="/static/jquery.min.js"></script>
</head>
<body>
<p>Processing...</p>
<script>
setInterval(function()
{
var http = new XMLHttpRequest();
http.open('HEAD', "is_done", false);
http.send();
if (http.status==200)
window.location.replace("is_done");
},2000);
</script>
</body>
</html>
Run Code Online (Sandbox Code Playgroud)
原始问题:
我是初学者/中级Python程序员和初级Web开发人员所以请保持温和.我想要的:用户点击一个超链接,然后转到一个中间网页,上面写着"正在处理......".在后台(在服务器上),此链接触发一个python脚本,该脚本处理文件并创建新的网页.完成脚本后,用户将被重定向到新创建的页面.我拥有:我有一个脚本来处理并吐出一个新的页面.我没想到的是如何触发python脚本,然后在脚本完成时触发重定向.我看过像django和cgi脚本这样的web框架.但我还没有找到任何符合条件的东西.我很可能会错过一些完全明显的东西,所以我真的很感激任何帮助.谢谢.
解决这个问题的一个简单方法是使用像Flask这样的简单Web框架来构建系统的Web部件.在魔术链接的请求处理程序中,您需要生成脚本并跟踪它.查看脚本是否已完成并将其转发给用户的简单方法是定期发送ajax请求以检查完成情况.
例如,Flask网站可能如下所示:
import threading
import subprocess
import uuid
from flask import Flask
from flask import render_template, url_for, abort, jsonify, request
app = Flask(__name__)
background_scripts = {}
def run_script(id):
subprocess.call(["/path/to/yourscript.py", "argument1", "argument2"])
background_scripts[id] = True
@app.route('/')
def index():
return render_template('index.html')
@app.route('/generate')
def generate():
id = str(uuid.uuid4())
background_scripts[id] = False
threading.Thread(target=lambda: run_script(id)).start()
return render_template('processing.html', id=id)
@app.route('/is_done')
def is_done():
id = request.args.get('id', None)
if id not in background_scripts:
abort(404)
return jsonify(done=background_scripts[id])
Run Code Online (Sandbox Code Playgroud)
而且index.html:
<a href="{{ url_for('generate') }}">click me</a>
Run Code Online (Sandbox Code Playgroud)
而且processing.html:
<html>
<head>
<script src="/static/jquery.js"></script>
<script>
function ajaxCallback(data) {
if (data.done)
window.location.replace("http://YOUR_GENERATED_PAGE_URL");
else
window.setTimeout(function() {
$.getJSON('{{ url_for('is_done') }}', {id: {{ id }} }, ajaxCallback);
}, 3000);
}
$(document).ready(function(){
ajaxCallback({done=false});
});
</script>
</head>
<body>
Processing...
</body></html>
Run Code Online (Sandbox Code Playgroud)
这是目前所有未经测试的代码,但我希望您对如何解决此问题有所了解.另请注意,这只有在您从一个进程提供页面时才有效,因此如果您设置了Apache和mod_wsgi,请确保进程组中只有一个进程.
如果您需要更复杂的解决方案,您可能需要查看消息队列等.