ARTICLE DETAIL

资讯详情

深耕网站建设、视觉设计与SEO优化的一线实战洞察。

data-juicer运行报错,日志文件路径无法找到:D:\WorkRes\EnvDataJuicer\dj-practice\20260320_061824_de1d34\logs\...如何解决?

data-juicer运行报错,日志文件路径无法找到:D:\WorkRes\EnvDataJuicer\dj-practice\20260320_061824_de1d34\logs\...如何解决?

🏆本文收录于 《全栈 Bug 调优(实战版)》 专栏。专栏聚焦真实项目中的各类疑难 Bug,从成因剖析 → 排查路径 → 解决方案 → 预防优化全链路拆解,形成一套可复用、可沉淀的实战知识体系。无论你是初入职场的开发者,还是负责复杂项目的资深工程师,都可以在这里构建一套属于自己的「问题诊断与性能调优」方法论,助你稳步进阶、放大技术价值。

📌特别说明:
文中问题案例来源于真实生产环境与公开技术社区,并结合多位一线资深工程师与架构师的长期实践经验,经过人工筛选与AI系统化智能整理后输出。文中的解决方案并非唯一“标准答案”,而是兼顾可行性、可复现性与思路启发性的实践参考,供你在实际项目中灵活运用与演进。

欢迎订阅本专栏,一次订阅后,专栏内所有文章可永久免费阅读,后续更新内容皆不用再次订阅,持续更新中。

📢 问题描述

详细问题描述如下:

data-juicer运行报错,日志文件路径无法找到:data-juicer日志文件路径出现了问题,按照官方网站的技术文档的uv pip方式下载的data-juicer,运行后出现报错,如何解决?

配置文件如下:

project_name:'windows-fix'dataset_path:'D:/WorkRes/EnvDataJuicer/dj-practice/raw_data.jsonl'np:4export_path:'D:/WorkRes/EnvDataJuicer/dj-practice/processed_data.jsonl'process:-language_id_score_filter:lang:'zh'min_score:0.8
(D:\WorkRes\condaData\envs_dirs\env2-dj)PSD:\WorkRes\EnvDataJuicer\dj-practice>dj-process--config.\process.yaml2026-03-2014:18:24.879|ERROR|__main__:10-An error has been caughtinfunction'<module>',process'MainProcess'(16736),thread'MainThread'(30512):Traceback(most recent call last):File"D:\WorkRes\condaData\envs_dirs\env2-dj\lib\runpy.py",line196,in_run_module_as_mainreturn_run_code(code,main_globals,None,│ │ └{'__name__':'__main__','__doc__':None,'__package__':'','__loader__':<zipimporter object "D:\WorkRes\condaData\envs_dir...│ └<code object<module>at0x000001A6B57DFD60,file"D:\WorkRes\condaData\envs_dirs\env2-dj\Scripts\dj-process.exe\__main__.py"...<function_run_code at0x000001A6B557F640>File"D:\WorkRes\condaData\envs_dirs\env2-dj\lib\runpy.py",line86,in_run_codeexec(code,run_globals)│ └{'__name__':'__main__','__doc__':None,'__package__':'','__loader__':<zipimporter object "D:\WorkRes\condaData\envs_dir...<code object<module>at0x000001A6B57DFD60,file"D:\WorkRes\condaData\envs_dirs\env2-dj\Scripts\dj-process.exe\__main__.py"...>File"D:\WorkRes\condaData\envs_dirs\env2-dj\Scripts\dj-process.exe\__main__.py",line10,in<module>sys.exit(main())│ │ └<functionmain at0x000001A6A7A15C60>│ └<built-infunctionexit><module'sys'(built-in)>File"D:\WorkRes\condaData\envs_dirs\env2-dj\Lib\site-packages\tools\process_data.py",line21,inmain cfg=init_configs()<functioninit_configs at0x000001A69E5049D0>File"D:\WorkRes\condaData\envs_dirs\env2-dj\lib\site-packages\data_juicer\config\config.py",line824,ininit_configs cfg=init_setup_from_cfg(cfg,load_configs_only)│ │ └ False │ └Namespace(config=[Path_fr(.\process.yaml,cwd=D:\WorkRes\EnvDataJuicer\dj-practice)],auto=False,auto_num=1000,hpo_config=N...<functioninit_setup_from_cfg at0x000001A69E504F70>File"D:\WorkRes\condaData\envs_dirs\env2-dj\lib\site-packages\data_juicer\config\config.py",line920,ininit_setup_from_cfgsetup_logger(<functionsetup_logger at0x000001A69C3383A0>File"D:\WorkRes\condaData\envs_dirs\env2-dj\lib\site-packages\data_juicer\utils\logger_utils.py",line170,insetup_logger logger.add(│ └<functionLogger.add at0x000001A6B76FE680><loguru.logger handlers=[(id=2,level=20,sink=<stderr>)]>File"D:\WorkRes\condaData\envs_dirs\env2-dj\lib\site-packages\loguru\_file_sink.py",line192,in__init__ self._create_file(path)│ │ └'D:\\WorkRes\\EnvDataJuicer\\dj-practice\\20260320_061824_de1d34\\logs\\export_..\\processed_data.jsonl_time_20260320141824.txt'│ └<functionFileSink._create_file at0x000001A6B76917E0><loguru._file_sink.FileSink object at0x000001A6A7B5D450>File"D:\WorkRes\condaData\envs_dirs\env2-dj\lib\site-packages\loguru\_file_sink.py",line228,in_create_file self._file=open(path,**self._kwargs)│ │ │ │ └{'mode':'a','buffering':1,'encoding':'utf8'}│ │ │ └<loguru._file_sink.FileSink object at0x000001A6A7B5D450>│ │ └'D:\\WorkRes\\EnvDataJuicer\\dj-practice\\20260320_061824_de1d34\\logs\\export_..\\processed_data.jsonl_time_20260320141824.txt'│ └ None └<loguru._file_sink.FileSink object at0x000001A6A7B5D450>FileNotFoundError:[Errno2]No such file or directory:'D:\\WorkRes\\EnvDataJuicer\\dj-practice\\20260320_061824_de1d34\\logs\\export_..\\processed_data.jsonl_time_20260320141824.txt'Traceback(most recent call last):File"D:\WorkRes\condaData\envs_dirs\env2-dj\lib\runpy.py",line196,in_run_module_as_mainreturn_run_code(code,main_globals,None,File"D:\WorkRes\condaData\envs_dirs\env2-dj\lib\runpy.py",line86,in_run_codeexec(code,run_globals)File"D:\WorkRes\condaData\envs_dirs\env2-dj\Scripts\dj-process.exe\__main__.py",line10,in<module>sys.exit(main())File"D:\WorkRes\condaData\envs_dirs\env2-dj\lib\site-packages\loguru\_logger.py",line1297,incatch_wrapperreturnfunction(*args,**kwargs)File"D:\WorkRes\condaData\envs_dirs\env2-dj\Lib\site-packages\tools\process_data.py",line21,inmain cfg=init_configs()File"D:\WorkRes\condaData\envs_dirs\env2-dj\lib\site-packages\data_juicer\config\config.py",line824,ininit_configs cfg=init_setup_from_cfg(cfg,load_configs_only)File"D:\WorkRes\condaData\envs_dirs\env2-dj\lib\site-packages\data_juicer\config\config.py",line920,ininit_setup_from_cfgsetup_logger(File"D:\WorkRes\condaData\envs_dirs\env2-dj\lib\site-packages\data_juicer\utils\logger_utils.py",line170,insetup_logger logger.add(File"D:\WorkRes\condaData\envs_dirs\env2-dj\lib\site-packages\loguru\_logger.py",line802,inadd wrapped_sink=FileSink(path,**kwargs)File"D:\WorkRes\condaData\envs_dirs\env2-dj\lib\site-packages\loguru\_file_sink.py",line192,in__init__ self._create_file(path)File"D:\WorkRes\condaData\envs_dirs\env2-dj\lib\site-packages\loguru\_file_sink.py",line228,in_create_file self._file=open(path,**self._kwargs)FileNotFoundError:[Errno2]No such file or directory:'D:\\WorkRes\\EnvDataJuicer\\dj-practice\\20260320_061824_de1d34\\logs\\export_..\\processed_data.jsonl_time_20260320141824.txt'

全文目录:

    • 📢 问题描述
    • 📣 请知悉:如下方案不保证一定适配你的问题!
      • ✅️问题理解
        • 🟢方案 A:显式把 `export_path` 放进最终 `work_dir`,这是最推荐、最稳的修复方案
        • 🟡方案 B:升级到当前最新版本,但把它当“补强”,不要把它当这次问题的唯一修复手段
        • 🔴方案 C:本地补丁修源码,适合你要批量兼容旧配置或必须保留现有路径布局时使用
      • ✅️问题延伸
      • ✅️问题预测
      • ✅️小结
    • 🌹 结语 & 互动说明
    • 🧧 文末福利:技术成长加速包 🧧
    • 🫵 Who am I?

📣 请知悉:如下方案不保证一定适配你的问题!

如下是针对上述问题进行专业角度剖析答疑,不喜勿喷,仅供参考:

✅️问题理解

你这个报错,本质上不是数据集文件找不到,也不是language_id_score_filter本身有问题,更不是uv pip安装方式直接装坏了
从你贴出的堆栈看,程序还没真正开始处理数据,就已经在初始化日志文件的阶段挂掉了:调用链是init_configs -> init_setup_from_cfg -> setup_logger -> loguru FileSink open(...),也就是说,失败点发生在正式执行 OP 之前。结合 Data-Juicer 当前主线代码,init_setup_from_cfg会先处理export_pathwork_dirjob_idevent_log_dir,然后用os.path.relpath(cfg.export_path, start=cfg.work_dir)计算相对路径,再把它拼进日志文件名里;而setup_logger最终会把save_dir和这个文件名os.path.join后交给 Loguru 打开。

你的堆栈里最关键的一段是这个路径:

D:\WorkRes\EnvDataJuicer\dj-practice\20260320_061824_de1d34\logs\export_..\processed_data.jsonl_time_20260320141824.txt

这已经把问题暴露得很清楚了:
Data-Juicer 先把work_dir变成了一个自动追加了job_id的运行目录,例如...\dj-practice\20260320_061824_de1d34;而你的export_path仍然是外层目录里的...\dj-practice\processed_data.jsonl。这样一来,os.path.relpath(export_path, work_dir)在 Windows 下就会算出..\processed_data.jsonl。随后 Data-Juicer 把它拼成日志文件名export_..\processed_data.jsonl_time_xxx.txt,Loguru 又把这个“文件名”当作了带目录层级的路径去打开,于是中间目录并不存在,最终触发FileNotFoundError。这和 Data-Juicer 当前配置解析逻辑完全吻合:如果work_dir不含{job_id}占位符,框架会自动把job_id追加到末尾;同时它确实会对work_direxport_path等字段做占位符替换。

所以,这次报错的真正根因是:export_path不在最终运行态的work_dir内部,导致生成日志文件名时出现了..\\,从而把“日志文件名”污染成了非法/不存在的层级路径。
这也是为什么你会感觉像“日志文件路径无法找到”——其实不是普通意义上的“logs 目录没建”,而是日志“文件名”里被塞进了相对路径穿越符号..和路径分隔符

下面这个流程能直观看懂这次故障链路:

### ✅️问题解决方案
🟢方案 A:显式把export_path放进最终work_dir,这是最推荐、最稳的修复方案

这是最应该采用的方案。
Data-Juicer 当前代码明确支持对work_direxport_pathdataset_pathevent_log_dir等字段做{job_id}/{work_dir}占位符替换;同时它要求最终work_dirjob_id结尾,或者自动帮你追加一个job_id。因此,正确做法不是只写死export_path,而是让export_path跟随最终运行目录一起解析出来

你可以直接把配置改成下面这样:

project_name:'windows-fix'dataset_path:'D:/WorkRes/EnvDataJuicer/dj-practice/raw_data.jsonl'work_dir:'D:/WorkRes/EnvDataJuicer/dj-practice/runs/{job_id}'export_path:'{work_dir}/processed_data.jsonl'np:4process:-language_id_score_filter:lang:'zh'min_score:0.8

这个配置为什么能解决?

第一,work_dir已经明确写成以{job_id}结尾,符合框架自己的目录规则。
第二,export_path直接引用{work_dir},这样替换完成后,导出文件就一定落在该次运行目录里面。
第三,这样os.path.relpath(cfg.export_path, start=cfg.work_dir)的结果就不再是..\processed_data.jsonl,而会变成单纯的processed_data.jsonl,日志文件名也就会是正常的:
logs/export_processed_data.jsonl_time_xxx.txt。这正好绕开了你现在的异常路径构造。

这里我再强调一个很容易踩坑的点:
不要只写work_dir: D:/.../dj-practice然后export_path: D:/.../dj-practice/processed_data.jsonl,以为这样就行。
因为当前代码会在后面自动把job_id追加到work_dir末尾,最终work_dir会变成.../dj-practice/<job_id>,而你的export_path仍然在上一级目录,结果相对路径还是会变成..\processed_data.jsonl。所以最稳妥的写法就是我上面给你的这种:work_dir自己带{job_id}export_path再引用{work_dir}

你可以改完后直接重新执行:

dj-process--config.\process.yaml
🟡方案 B:升级到当前最新版本,但把它当“补强”,不要把它当这次问题的唯一修复手段

Data-Juicer 官方当前推荐的安装方式确实是:

uv pipinstallpy-data-juicer

而 PyPI 上当前最新版本是py-data-juicer 1.5.1,发布时间为 2026-03-17。此外,官方仓库在 2025 年曾有人报告过一个相近的日志文件FileNotFoundError问题,维护者回复说“最近一个 PR 已修复,建议拉最新代码再试”。这说明日志相关问题在 Data-Juicer 里确实出现过,而且官方也持续在修。

但是要非常客观地说:
升级版本并不能替代你这次的配置修正。

原因是,你这次的问题并不是单纯“某个日志文件没有自动创建”,而是日志文件名本身被构造成了带..\的路径。只要你的export_path仍然落在最终work_dir外面,这个风险依旧成立。也就是说:

  • 低版本:更容易撞日志相关 bug;
  • 高版本:稳定性更好;
  • 但配置里如果依然让export_path跑到最终work_dir外层,仍然可能再出问题。

所以这个方案正确的使用姿势是:

先查版本:

python-c"import importlib.metadata as m; print(m.version('py-data-juicer'))"

如果不是最新,再升级:

uv pip install-U py-data-juicer

升级后,仍然要配合方案 A 的 YAML 修正一起做。这样才是长期稳定的做法。


🔴方案 C:本地补丁修源码,适合你要批量兼容旧配置或必须保留现有路径布局时使用

如果你现在有很多现成配置文件,不想一个个改,或者你就是想保留“导出文件在运行目录外层”的习惯,那就可以考虑直接补 Data-Juicer 本地源码,把日志文件名做一次“安全化处理”。

当前主线逻辑核心是:

  1. export_rel_path = os.path.relpath(cfg.export_path, start=cfg.work_dir)
  2. 生成logfile_name = f"export_{export_rel_path}_time_{timestamp}.txt"
  3. setup_logger(save_dir=cfg.event_log_dir, filename=logfile_name, ...)

问题就在第 2 步:它把一个可能含有..\/\的相对路径直接塞进了“文件名”里。

你可以在本地安装包里把这一段修成“文件名安全化”,例如改成如下思路:

export_rel_path=os.path.relpath(cfg.export_path,start=cfg.work_dir)safe_export_rel_path=(export_rel_path.replace("..","__").replace("\\","_").replace("/","_").replace(":","_"))logfile_name=f"export_{safe_export_rel_path}_time_{timestamp}.txt"

或者更保守一些,直接只取导出文件名:

safe_export_rel_path=os.path.basename(cfg.export_path)logfile_name=f"export_{safe_export_rel_path}_time_{timestamp}.txt"

这类补丁的优点是:

  • 不需要改很多 YAML;
  • 彻底杜绝日志文件名注入目录层级;
  • 对 Windows 路径特别友好。

缺点也很明显:

  • 升级包后可能被覆盖;
  • 属于“本地维护分支”,后面要自己记得合并;
  • 对团队协作不如改配置规范来得统一。

所以我的建议是:
个人临时救火可用,团队长期使用不推荐把它当第一方案。


✅️问题延伸

这个问题其实揭示了 Data-Juicer 1.x 一个非常重要的“运行目录模型”:

它不是把work_dir当普通静态目录,而是把它当“某次作业的根目录模板”。
当前代码里,resolve_job_directories明确规定:如果work_dir不带{job_id},它也会自动把job_id追加到末尾;并且logscheckpointspartitionsmetadataresults等目录都默认挂在这个最终work_dir下。也就是说,每次执行本质上都是一个独立 job workspace

所以以后你写 Data-Juicer 配置时,建议建立一个固定原则:

凡是“本次运行产生的输出”,都尽量放在{work_dir}内部。

一个推荐范式是:

work_dir:'D:/xxx/runs/{job_id}'export_path:'{work_dir}/processed_data.jsonl'event_log_dir:'{work_dir}/logs'checkpoint_dir:'{work_dir}/checkpoints'partition_dir:'{work_dir}/partitions'

这样你会得到以下收益:

  • 日志、检查点、导出数据天然同属于一次 job;
  • 清理历史运行非常方便;
  • 不会再出现relpath回退到..的问题;
  • 后续如果启用 checkpoint / tracer / ray,也更不容易出奇怪路径问题。

另外再提醒你一件“下一个可能遇到的问题”:
你现在用的是language_id_score_filter,官方文档明确说明这个 OP 依赖FastText 语言识别模型;如果本机缓存里没有相关模型,Data-Juicer 运行时可能会去下载,历史 issue 里也能看到lid.176.bin缺失后自动下载或手工放缓存目录的讨论。也就是说,你这次修完日志路径后,下一步如果网络不通,可能会遇到模型下载或缓存相关报错,但那已经是下一阶段的问题,不是这次的根因。


✅️问题预测

基于你当前环境,我很高概率预测后续会出现这几类情况:

第一,修完 YAML 后,本次FileNotFoundError会消失。
因为这次错误完全卡在 logger 初始化阶段,只要日志文件名不再含..\loguru就能正常建文件,流程就能往后走。这个判断与你当前堆栈和 Data-Juicer 的路径生成逻辑完全一致。

第二,如果是第一次跑language_id_score_filter,可能会出现模型缓存/下载相关耗时或报错。
官方文档说明该算子使用 FastText 做语言识别;历史 issue 里也出现过lid.176.bin不存在而触发下载的情况。

第三,如果你后面继续沿用“导出文件写在运行目录外层”的写法,其他依赖work_dir的功能也可能继续出路径类问题。
尤其是 checkpoint、event log、partition 等路径都围绕最终work_dir构建;一旦你把运行输出散落到外层,再遇到相对路径拼接,就很容易再冒出同类 bug。

第四,升级版本值得做,但不能替代配置规范。
当前官方最新包是 1.5.1,日志和执行框架近几个版本一直在持续修复与增强;但只要路径组织方式本身不合理,升级也不是银弹。


✅️小结

结论我给你直接下得非常明确一点:

这次不是你的数据文件路径错了,而是 Data-Juicer 在“自动 job 工作目录 + 相对路径生成日志名”这一套逻辑下,把你的export_path处理成了..\processed_data.jsonl,最终污染了日志文件名,导致 Loguru 去打开一个不存在的层级路径。

最有效、最靠谱、最工程化的修法就是:

  1. 显式设置work_dir为带{job_id}的运行目录;
  2. export_path写成{work_dir}/processed_data.jsonl
  3. 再顺手确认包版本,必要时升级到最新。

你现在直接把配置改成下面这一版,基本就是正解:

project_name:'windows-fix'dataset_path:'D:/WorkRes/EnvDataJuicer/dj-practice/raw_data.jsonl'work_dir:'D:/WorkRes/EnvDataJuicer/dj-practice/runs/{job_id}'export_path:'{work_dir}/processed_data.jsonl'np:4process:-language_id_score_filter:lang:'zh'min_score:0.8

这版改完后,再跑dj-process --config .\process.yaml,大概率就会越过你现在这个报错点。

🌹 结语 & 互动说明

希望以上分析与解决思路,能为你当前的问题提供一些有效线索或直接可用的操作路径

若你按文中步骤执行后仍未解决:

  • 不必焦虑或抱怨,这很常见——复杂问题往往由多重因素叠加引起;
  • 欢迎你将最新报错信息、关键代码片段、环境说明等补充到评论区;
  • 我会在力所能及的范围内,结合大家的反馈一起帮你继续定位 👀

💡如果你有更优或更通用的解法:

  • 非常欢迎在评论区分享你的实践经验或改进方案;
  • 你的这份补充,可能正好帮到更多正在被类似问题困扰的同学;
  • 正所谓「赠人玫瑰,手有余香」,也算是为技术社区持续注入正向循环

🧧 文末福利:技术成长加速包 🧧

文中部分问题来自本人项目实践,部分来自读者反馈与公开社区案例,也有少量经由全网社区与智能问答平台整理而来。

若你尝试后仍没完全解决问题,还请多一点理解、少一点苛责——技术问题本就复杂多变,没有任何人能给出对所有场景都 100% 套用的方案。

如果你已经找到更适合自己项目现场的做法,非常建议你沉淀成文档或教程,这不仅是对他人的帮助,更是对自己认知的再升级。

如果你还在持续查 Bug、找方案,可以顺便逛逛我专门整理的 Bug 专栏👉《全栈 Bug 调优(实战版)》👈️

这里收录的都是在真实场景中踩过的坑,希望能帮你少走弯路,节省更多宝贵时间。

✍️如果这篇文章对你有一点点帮助:

  • 欢迎给 bug菌 来个一键三连:关注 + 点赞 + 收藏
  • 你的支持,是我持续输出高质量实战内容的最大动力。

同时也欢迎关注我的硬核公众号 「猿圈奇妙屋」:

获取第一时间更新的技术干货、BAT 等互联网公司最新面试真题、4000G+ 技术 PDF 电子书、简历 / PPT 模板、技术文章 Markdown 模板等资料,通通免费领取
你能想到的绝大部分学习资料,我都尽量帮你准备齐全,剩下的只需要你愿意迈出那一步来拿。

🫵 Who am I?

我是 bug菌:

  • 热活跃于 CSDN | 掘金 | InfoQ | 51CTO | 华为云 | 阿里云 | 腾讯云 等技术社区;
  • CSDN 博客之星 Top30、华为云多年度十佳博主/卓越贡献者、掘金多年度人气作者 Top40;
  • 掘金、InfoQ、51CTO 等平台签约及优质作者;
  • 全网粉丝累计30w+

更多高质量技术内容及成长资料,可查看这个合集入口 👉 点击查看 👈️

硬核技术公众号「猿圈奇妙屋」期待你的加入,一起进阶、一起打怪升级。

- End -

返回列表