You need to enable JavaScript to run this app. incron触发Mycroft列表导出bash脚本仅执行首条cp命令故障求助
优惠活动
大模型
产品
解决方案
定价
更多

incron触发Mycroft列表导出bash脚本仅执行首条cp命令故障求助

问题背景

我的目标是将Mycroft技能"List-Manager"中的所有列表导出为格式化拆分的txt文件,传输到我的Nextcloud-Notes-Skill。谷歌助手和Alexa是更简便的方案,但我不想使用这类服务。
我编写的bash脚本在终端中可正常完成列表格式化和拆分工作。

Mycroft技能使用的文本文件内容如下:
{"Remind me": ["remind_item_1", "remind_item_2"], "shopping": ["mate", "book", "keyboard", "bavarian beer"]}

导出后会生成两个文本文件
第一个文件名为:Remind me

  • remind_item_1
  • remind_item_2

第二个文件名为:shopping

  • mate
  • book
  • keyboard
  • bavarian beer

在展示代码前先说明几点:首先我认为存在更优的实现方案,我是自学的非专业开发人员,刚接触bash脚本编写,希望使用系统自带资源实现功能并学习相关知识。

incron配置

我使用incron监控文件变更,每次修改列表时incron都会触发脚本执行,规则配置如下:

/opt/mycroft/skills/list-manager.lb803/data.json        IN_MODIFY       /bin/bash /home/pi/my_directory/notes_skill.sh
故障描述

incron运行正常,可触发下方脚本但仅能执行第一条copy命令,每次都能在目录中生成data_list_manager.txt文件,但后续命令无任何执行痕迹。incron已配置pi和root用户的执行权限,所有文件都具备pi或root权限,脚本在终端手动执行可正常运行,仅通过incron触发时会在执行完cp命令后停止,暂未找到故障原因。
当前版本代码仅支持导出2个列表,待问题解决后我会优化适配更多列表。我在echo、sed等命令前添加了/bin/绝对路径,是因为查阅资料得知incron运行环境和终端不同,需要指定命令的完整路径。

现有脚本代码
#!/bin/bashcp 
cp /opt/mycroft/skills/list-manager.lb803/data.json /home/pi/my_directory/data_list_manager.txt
#wait
foo="$(/bin/cat /home/pi/my_directory/data_list_manager.txt | /bin/sed s/[[{}"]//g)"
foo="$(/bin/echo "$foo" | /bin/sed -e s/,[[:space:]]/@@/g -e s/:[[:space:]]/@@@@/g -e s/[]]/@@@@/g)"
foo="$(/bin/echo "$foo" | /bin/sed -e s/@@@@@@/\n/g -e s/@@@@/\n@@@/g)"
/bin/echo "$foo" >/home/pi/my_directory/splitfile.txt
/usr/bin/split -l2 /home/pi/my_directory/splitfile.txt
#wait
nam="$(/bin/cat /home/pi/my_directory/xaa | /bin/sed q)"
foo="$(/bin/cat /home/pi/my_directory/xaa | /bin/sed '2!d')"
foo="$(/bin/echo "$foo" | /bin/sed -e s/@@@/\-\ [\ ]\ /g -e s/@@/\n\-\ [\ ]\ /g)"
/bin/echo "$foo" >/home/pi/my_directory/Listen/"$nam".txt
nam="$(/bin/cat /home/pi/my_directory/xab | /bin/sed q)"
foo="$(/bin/cat /home/pi/my_directory/xab | /bin/sed '2!d')"
foo="$(/bin/echo "$foo" | sed -e s/@@@/\-\ [\ ]\ /g -e s/@@/\n\-\ [\ ]\ /g)"
/bin/echo "$foo" >/home/pi/my_directory/Listen/"$nam".txt
nam="$(/bin/cat /home/pi/my_directory/xac | /bin/sed q)"
foo="$(/bin/cat /home/pi/my_directory/xac | /bin/sed '2!d')"
foo="$(/bin/echo "$foo" | /bin/sed -e s/@@@/\-\ [\ ]\ /g -e s/@@/\n\-\ [\ ]\ /g)"
/bin/echo "$foo" >/home/pi/my_directory/Listen/"$nam".txt
nam="$(/bin/cat /home/pi/my_directory/xad | /bin/sed q)"
foo="$(/bin/cat /home/pi/my_directory/xad | /bin/sed '2!d')"
foo="$(/bin/echo "$foo" | /bin/sed -e s/@@@/\-\ [\ ]\ /g -e s/@@/\n\-\ [\ ]\ /g)"
/bin/echo "$foo" >/home/pi/my_directory/Listen/"$nam".txt
修复方案
  1. 修正脚本首行的笔误,把#!/bin/bashcp改成#!/bin/bash,手动执行时你是直接指定bash运行脚本,不会触发shebang解析错误,但incron执行时会识别到错误的解释器路径直接终止运行。
  2. incron没有继承终端的工作目录配置,split命令生成的xaa/xab等文件默认会写入到系统根目录或者root目录,后续读取/home/pi/my_directory/xaa时找不到文件直接报错。可以在cp命令前加一行cd /home/pi/my_directory || exit 1强制切换工作目录,或者把split命令修改为/usr/bin/split -l2 /home/pi/my_directory/splitfile.txt /home/pi/my_directory/x指定输出路径前缀。
  3. 修正一处未写绝对路径的sed命令,处理xab的那行sed -e s/@@@/改成/bin/sed -e s/@@@/,避免incron环境找不到命令。
  4. 可选:在脚本开头加一行exec > /tmp/notes_skill.log 2>&1,所有运行输出和报错都会写入该日志文件,后续出现问题可以直接查日志定位。

内容的提问来源于stack exchange,提问作者subduck

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.10.11 09:54:02