所以我想出了一个令人满意的方法来解决我自己的问题。
我设法得到了这个非常实用的结果:
请注意,我的模板仅适用于扩展名为 .html 的文件,尽管它可以轻松增强以支持其他文件扩展名。
这是我最终确定的templates\template.html 文件:
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8">
<title>Docs Demo</title>
<link rel="stylesheet" href="{{ url_for('static', filename='styles.css') }}">
</head>
<body>
<div id="container">
<div class="left_frame">
<h1>{{ tree.name }}</h1>
<ul>
{%- for item in tree.children recursive %}
{% if '.html' in item.name %}
<li><a href="docs/{{ item.name }}" target="iframe1">
{{ item.name.split('/')[-1:][0] }}
{%- if item.children -%}
<ul>{{ loop(item.children) }}</ul>
{%- endif %}</a></li>
{% else %}
<li>{{ item.name }}
{%- if item.children -%}
<ul>{{ loop(item.children) }}</ul>
{%- endif %}</li>
{% endif %}
{%- endfor %}
</ul>
</div>
<div class="right_frame">
<iframe name="iframe1"></iframe>
</div>
</div>
</body>
</html>
您可以参考 King Reload 的回答来分析我在 template.html 文件中所做的更改以使其正常工作。
这里是 demo_app.py 脚本,它通过 Flask 为我的文档 HTML 文件提供服务:
import threading
import os
import webbrowser
from flask import Flask, render_template, send_from_directory
app = Flask(__name__, static_folder='static')
ROOT = os.path.dirname(os.path.abspath(__file__))
DOCS_ROOT = os.path.join(app.static_folder, 'docs')
@app.route('/')
def docs_tree():
return render_template('template.html', tree=make_tree(DOCS_ROOT))
@app.route('/docs/<path:filename>')
def send_docs(filename):
return send_from_directory(directory=DOCS_ROOT, 'docs'), filename=filename)
def make_tree(path):
tree = dict(name=os.path.basename(path), children=[])
try:
lst = os.listdir(path)
except OSError:
pass # ignore errors
else:
for name in lst:
fn = os.path.join(path, name)
if os.path.isdir(fn):
tree['children'].append(make_tree(fn))
else:
np = os.path.join(path.replace(DOCS_ROOT, ''), name).replace('\\', '/')
if np.startswith('/'):
np = np[1:]
tree['children'].append(dict(name=np))
return tree
if __name__ == '__main__':
host = 'localhost'
port = '8888'
url = 'http://{h}:{p}'.format(h=host, p=port)
threading.Timer(3, lambda: webbrowser.open(url)).start()
app.run(host=host, port=port, debug=False)
自问我最初的问题以来,demo_app.py 最显着的变化如下:
- 初始化
app后,我使用app.static_folder设置DOCS_ROOT;
- 在函数
send_docs()中,我将send_from_directory()的directory参数改为使用DOCS_ROOT;
-
在make_tree() 内部,在for 循环的else 块内,我添加了:
np = os.path.join(path.replace(DOCS_ROOT, ''), name).replace('\\', '/')
if np.startswith('/'):
np = np[1:]
所有这一切都是取name的绝对路径,删除匹配DOCS_ROOT的,只留下相对路径(然后将\\替换为/),从而得到来自@的简单相对路径987654345@。如果相对路径以/ 开头,我将其删除(因为在template.html 中有来自docs 的尾随/。
对于任何对我使用的简单样式表 (static\styles.css) 感兴趣的人(以及一些更新的增强功能):
html {
min-height:100%;
position:relative;
}
body {
overflow:hidden;
}
.container {
width:100%;
overflow:auto;
}
.left_frame {
float:left;
background:#E8F1F5;
width:25%;
height:100vh;
}
.right_frame {
float:right;
background:#FAFAFA;
width:75%;
height:100vh;
}
.right_frame iframe {
display:block;
width:100%;
height:100%;
border:none;
}