
本文介绍在 Dash 应用中通过 Tabs 组件逐个展示多个 .py 源码文件的完整方案,解决换行丢失、语法高亮缺失、可读性差等痛点,推荐使用 html.Code + html.Pre 组合或 dash_mantine_components.Code 实现专业级代码渲染。
本文介绍在 dash 应用中通过 tabs 组件逐个展示多个 `.py` 源码文件的完整方案,解决换行丢失、语法高亮缺失、可读性差等痛点,推荐使用 `html.code` + `html.pre` 组合或 `dash_mantine_components.code` 实现专业级代码渲染。
在构建 Dash 数据仪表盘或教学型应用时,常需向用户(如团队成员、学生或客户)直观展示核心 Python 脚本逻辑——例如模型训练脚本、ETL 流程或回调函数实现。直接内联代码不现实,截图又丧失可复制性与交互性。理想方案是:按 Tab 分页加载 .py 文件内容,保留原始缩进、换行与基础语法语义,并支持滚动与选择复制。
✅ 推荐方案一:原生 Dash + html.Pre + html.Code(零依赖)
Dash 内置的 html.Pre(预格式化文本容器)配合 html.Code(语义化代码标签)即可完美还原源码结构,无需第三方库:
import dash
from dash import html, dcc, callback, Input, Output
import pathlib
app = dash.Dash(__name__)
# 假设脚本存放在当前目录下的 scripts/ 文件夹中
SCRIPTS_DIR = pathlib.Path("scripts")
script_files = list(SCRIPTS_DIR.glob("*.py"))
# 构建 Tabs 的 items 列表
tabs_items = [
dcc.Tab(
label=file.stem,
value=file.name,
children=[
html.Div(
style={"padding": "16px", "overflowX": "auto", "maxHeight": "60vh"},
children=[
html.Pre(
children=[
html.Code(
children=file.read_text(encoding="utf-8"),
style={
"fontSize": "14px",
"lineHeight": "1.5",
"whiteSpace": "pre",
"tabSize": 4,
},
)
],
style={
"margin": 0,
"backgroundColor": "#f8f9fa",
"borderRadius": "4px",
"padding": "12px",
"border": "1px solid #e9ecef",
},
)
],
)
],
)
for file in script_files
]
app.layout = html.Div([
html.H2("Python 脚本源码库", style={"marginBottom": "20px"}),
dcc.Tabs(
id="script-tabs",
value=script_files[0].name if script_files else None,
children=tabs_items,
),
html.Div(id="tab-content", style={"marginTop": "20px"}),
])
# 动态加载内容(可选:延迟加载提升首屏性能)
@callback(
Output("tab-content", "children"),
Input("script-tabs", "value"),
)
def render_tab_content(tab_value):
if not tab_value or not SCRIPTS_DIR.joinpath(tab_value).exists():
return html.P("未找到对应脚本文件", style={"color": "#6c757d"})
content = SCRIPTS_DIR.joinpath(tab_value).read_text(encoding="utf-8")
return html.Pre(
children=html.Code(children=content, style={"whiteSpace": "pre", "tabSize": 4}),
style={
"backgroundColor": "#2d2d2d",
"color": "#f8f8f2",
"padding": "16px",
"borderRadius": "4px",
"overflowX": "auto",
"fontFamily": "'Fira Code', 'Consolas', monospace",
"fontSize": "13px",
},
)
if __name__ == "__main__":
app.run_server(debug=True)✅ 优势:纯 Dash 原生、轻量、兼容性极强;
<code> 组合天然保留空格、缩进与换行;支持 CSS 自定义字体、主题与滚动行为。</p></blockquote><h3>✅ 推荐方案二:dash_mantine_components.Code(增强体验)</h3><p>若项目已引入 <a href="https://www.php.cn/link/185d74f7b374c0ac461ca88fdb8c8b4a" rel="nofollow" target="_blank" >Dash Mantine Components (DMC)</a>,其 dmc.Code 组件提供开箱即用的语法高亮(基于 Prism.js)、行号、复制按钮与深色/浅色主题自动适配:</p><div class="aritcle_card flexRow"> <div class="artcardd flexRow"> <a class="aritcle_card_img" href="/xiazai/skill9965" title="macOS UI 自动化技能包 —— 用 Python 控制你的 Mac"><img src="https://img.php.cn/upload/skill/001/246/273/6adaf20dbae7c507.jpg" alt="macOS UI 自动化技能包 —— 用 Python 控制你的 Mac" ></a> <div class="aritcle_card_info flexColumn"> <a href="/xiazai/skill9965" title="macOS UI 自动化技能包 —— 用 Python 控制你的 Mac">macOS UI 自动化技能包 —— 用 Python 控制你的 Mac</a> <p>让 macOS 自动化像说话一样简单 —— 用代码控制你的 Mac,无需学习 AppleScript 系统要求 macOS 14+ (Sonoma) Python 3.9+ 需要开启:辅助功能 + 屏幕录制权限</p> </div> <a href="/xiazai/skill9965" title="macOS UI 自动化技能包 —— 用 Python 控制你的 Mac" class="aritcle_card_btn flexRow flexcenter"><b></b><span>下载</span> </a> </div> </div><p><span>立即学习</span>“<a href="https://pan.quark.cn/s/00968c3c2c15" style="text-decoration: underline !important; color: blue; font-weight: bolder;" rel="nofollow" target="_blank">Python免费学习笔记(深入)</a>”;</p><pre class="brush:php;toolbar:false;">pip install dash-mantine-componentsimport dash_mantine_components as dmc # 在 Tab 中直接使用(支持 Python 语法高亮) dmc.Code( children=script_content, language="python", withLineNumbers=True, copyLabel="复制代码", copiedLabel="已复制!", block=True, style={"marginTop": "16px"}, )✅ 优势:视觉专业、用户体验佳;一键复制降低使用门槛;支持 100+ 编程语言高亮;与 Mantine 主题系统无缝集成。
⚠️ 注意事项与避坑指南
- 编码安全:务必使用 encoding="utf-8" 读取 .py 文件,避免中文注释乱码;
- 路径健壮性:生产环境建议用 pathlib.Path.resolve() 校验脚本路径是否存在,防止 404 或异常中断;
- 大文件处理:单个脚本超 1MB 时,建议添加 html.Progress 加载指示器,或启用服务端流式读取(需搭配 Flask 后端定制);
- 避免 exec() 或 eval():切勿为“动态执行”而将用户上传的 .py 内容传入 exec() —— 这构成严重安全风险;
- 旧版转换器失效说明:问题中提到的 lxml.etree.fromstring 报错(AttributeError: 'cython_function_or_method' object has no attribute 'fromstring')源于 lxml>=5.0 移除了该方法,且 HTML→Dash 组件的自动转换在实际工程中既低效又不可控,强烈建议放弃此类方案,改用声明式静态渲染。
✅ 总结
在 Dash 中展示 Python 脚本,本质是「安全、可读、可维护地渲染纯文本」。优先采用 html.Pre + html.Code 实现零依赖可靠方案;若追求工业级体验,dash_mantine_components.Code 是当前最成熟的选择。二者均可无缝嵌入 dcc.Tabs,配合回调实现按需加载,兼顾性能与专业性。记住:代码展示 ≠ 代码执行——清晰的职责边界,才是稳健 Dashboard 的基石。

















