我可以将一个 WTForm 用于多个 @app.route 吗?
Can I use one WTForm for multiple @app.route's?
我需要从我的 app.py
中多个 @app.route 中的 WTForm 访问信息,以便我可以 post 我的应用程序的数据可视化。目前,我有一个 @app.route(/home/)
页面,用户在此页面上输入的文本由 WTForm 处理,然后传递给 @app.route(/results/
),我的代码在其中进行一些数据分析,然后 1) 显示一些结果和2) 将一些其他信息保存到JSON中,用于D3自身@app.route(/visualization/)
。由于 Javascript 的复杂性,我想在自己的 iframe
中显示我的 D3 可视化。现在我可以加载 /home/
页面,输入文本并点击 "Submit",然后将我重定向到 /results/
,并正确打印除 iframe
之外的所有内容。问题是:我无法让 @app.route(/visualization/)
从我的 WTForm 中获取信息(与 results
能够获取的信息相同),因此图像可以加载正确的 JSON文件。
下面是我的一些代码,可以更好地说明问题。
app.py
:
# Home
@app.route("/home/", methods=["GET", "POST"])
def gohome():
error = None
with open('somedata.pickle', 'rb')as f:
some_content = pickle.load(f)
try:
if request.method == "POST":
attempted_pmid = request.form['pmid']
except Exception as e:
#flash(e)
return render_template("dashboard.html", error=error)
return render_template("dashboard.html", some_content=some_content)
# My WTForm for handling user-entered pmids
class pmidForm(Form):
pmid = TextField('PubmedID')
# Results
@app.route("/results/", methods=["GET", "POST"])
def trying():
form = pmidForm(secret_key='potato')
try:
if request.method == 'POST':
entry = form.pmid.data #THIS IS THE USER INPUT FROM THE FORM #referencing 'class pmidForm'
pmid_list = multiple_pmid_input(entry) #list for handling multiple pmids
print(pmid_list)
for user_input in pmid_list:
print(str(user_input))
user_input = str(user_input)
# DO STUFF HERE #
# SAVE A JSON FILE TO A FOLDER #
return render_template('results.html')
except Exception as e:
return(str(e))
# Visualization
@app.route('/visualization/', methods=["GET", "POST"]) #for iframe
def visualization():
#need to get last user_input
form = pmidForm(secret_key='potato')
try:
if request.method == 'POST':
entry = form.pmid.data
pmid_list = multiple_pmid_input(entry)
for user_input in pmid_list:
print("This is the user input on /visualization/")
print(str(user_input))
user_input = str(user_input)
#Load
if user_input == pmid_list[-1]:
load_path = '/the/path/'+str(user_input)+'/'
completeName = os.path.join(load_path, ((str(user_input))+'.json'))
print(completeName)
with open(completeName, 'w') as load_data:
jsonDict = json.load(load_data)
print(jsonDict)
return render_template('visualization.html', jsonDict=jsonDict)
except Exception as e:
return(str(e))
因此,正如我现在所拥有的,home
和 results
与我现有的 WTForm 一起工作得很好。我会做好一切。但是在 results.html
中,我需要像这样在 iframe
中加载 visualization.html
:
results.html
中的行:
<iframe id="vis1" src="https://www.website.com/visualization/" width="1000" height="1000"></iframe>
使用此配置,如果我 运行 我的 app.py
,除了 iframe
显示:
之外,一切都显示正常
local variable 'jsonDict' referenced before assignment
在这里,我假设这是参考我的 visualization.html
,它有 Jinja 代码:
var myjson = {{ jsonDict|tojson }};
很明显 @app.route(/visualization/)
没有从 WTForm 中获取信息。我怎样才能让这第二个 @app.route
识别 WTForm 中的内容,就像它与 results
一起工作一样?
此外,这可能看起来很老套,但我有很好的理由将我的 D3 放在 iframe
中。这是因为我需要能够在多个 html 之间切换,例如 /visualization
/ 每个都有相互冲突的复杂 Javascript。我能做的最好的事情就是将它们全部隔离在 iframe
中。
答案是否定的,您不能将一个表单提交到多个路由或在多个路由之间共享数据。对于需要在多个路由之间共享数据的问题,我的解决方案是创建动态 URL。因此,它不会总是转到 results
页面,而是会转到 results/1234
,这样我就能够访问“1234”并在 html 中使用它。
我需要从我的 app.py
中多个 @app.route 中的 WTForm 访问信息,以便我可以 post 我的应用程序的数据可视化。目前,我有一个 @app.route(/home/)
页面,用户在此页面上输入的文本由 WTForm 处理,然后传递给 @app.route(/results/
),我的代码在其中进行一些数据分析,然后 1) 显示一些结果和2) 将一些其他信息保存到JSON中,用于D3自身@app.route(/visualization/)
。由于 Javascript 的复杂性,我想在自己的 iframe
中显示我的 D3 可视化。现在我可以加载 /home/
页面,输入文本并点击 "Submit",然后将我重定向到 /results/
,并正确打印除 iframe
之外的所有内容。问题是:我无法让 @app.route(/visualization/)
从我的 WTForm 中获取信息(与 results
能够获取的信息相同),因此图像可以加载正确的 JSON文件。
下面是我的一些代码,可以更好地说明问题。
app.py
:
# Home
@app.route("/home/", methods=["GET", "POST"])
def gohome():
error = None
with open('somedata.pickle', 'rb')as f:
some_content = pickle.load(f)
try:
if request.method == "POST":
attempted_pmid = request.form['pmid']
except Exception as e:
#flash(e)
return render_template("dashboard.html", error=error)
return render_template("dashboard.html", some_content=some_content)
# My WTForm for handling user-entered pmids
class pmidForm(Form):
pmid = TextField('PubmedID')
# Results
@app.route("/results/", methods=["GET", "POST"])
def trying():
form = pmidForm(secret_key='potato')
try:
if request.method == 'POST':
entry = form.pmid.data #THIS IS THE USER INPUT FROM THE FORM #referencing 'class pmidForm'
pmid_list = multiple_pmid_input(entry) #list for handling multiple pmids
print(pmid_list)
for user_input in pmid_list:
print(str(user_input))
user_input = str(user_input)
# DO STUFF HERE #
# SAVE A JSON FILE TO A FOLDER #
return render_template('results.html')
except Exception as e:
return(str(e))
# Visualization
@app.route('/visualization/', methods=["GET", "POST"]) #for iframe
def visualization():
#need to get last user_input
form = pmidForm(secret_key='potato')
try:
if request.method == 'POST':
entry = form.pmid.data
pmid_list = multiple_pmid_input(entry)
for user_input in pmid_list:
print("This is the user input on /visualization/")
print(str(user_input))
user_input = str(user_input)
#Load
if user_input == pmid_list[-1]:
load_path = '/the/path/'+str(user_input)+'/'
completeName = os.path.join(load_path, ((str(user_input))+'.json'))
print(completeName)
with open(completeName, 'w') as load_data:
jsonDict = json.load(load_data)
print(jsonDict)
return render_template('visualization.html', jsonDict=jsonDict)
except Exception as e:
return(str(e))
因此,正如我现在所拥有的,home
和 results
与我现有的 WTForm 一起工作得很好。我会做好一切。但是在 results.html
中,我需要像这样在 iframe
中加载 visualization.html
:
results.html
中的行:
<iframe id="vis1" src="https://www.website.com/visualization/" width="1000" height="1000"></iframe>
使用此配置,如果我 运行 我的 app.py
,除了 iframe
显示:
local variable 'jsonDict' referenced before assignment
在这里,我假设这是参考我的 visualization.html
,它有 Jinja 代码:
var myjson = {{ jsonDict|tojson }};
很明显 @app.route(/visualization/)
没有从 WTForm 中获取信息。我怎样才能让这第二个 @app.route
识别 WTForm 中的内容,就像它与 results
一起工作一样?
此外,这可能看起来很老套,但我有很好的理由将我的 D3 放在 iframe
中。这是因为我需要能够在多个 html 之间切换,例如 /visualization
/ 每个都有相互冲突的复杂 Javascript。我能做的最好的事情就是将它们全部隔离在 iframe
中。
答案是否定的,您不能将一个表单提交到多个路由或在多个路由之间共享数据。对于需要在多个路由之间共享数据的问题,我的解决方案是创建动态 URL。因此,它不会总是转到 results
页面,而是会转到 results/1234
,这样我就能够访问“1234”并在 html 中使用它。