这周基本没干成什么事。
给一个朋友写的小工具,跑在服务器上的定时脚本,之前跑得好好的,上周三开始报错。报错也很普通,sqlite3.OperationalError: unable to open database file。就这一句。
我看到这个的第一反应是权限问题,老演员了。上去 ls -l 一看,文件好好在那躺着,权限 644,属主也没错。加了 chmod 777 试了一下,没用。我知道 777 不该加,加了也没用,这属于病急乱投医。删掉重来。
然后我怀疑路径写错了。脚本里确实用的是相对路径,./data/xxx.db。这玩意是我两个月前写的,写的时候本地跑,在一个目录里 python main.py,起来就完了,从来没想过 cron 里跑会怎样。我一度觉得自己找到答案了——cron 的工作目录不是脚本所在的目录。改成了绝对路径,重启,还是那个错。那一刻真的很想砸键盘。就那么一瞬间,冷静了一下没有砸,键盘挺贵的。
中间还试了些别的,不一一说了,说了就变成教程了,我不想写教程。反正就是反复看日志、反复改、反复重启。我甚至一度怀疑是 sqlite 本身的版本问题。打住,不列排查步骤了,列出来就有人要截图拿去发。
说句实话,这事最让我难受的不是报错本身,是我发现自己手上这点东西已经开始生疏了。当年我还在写代码的时候,这种问题最多十分钟。现在一个路径问题卡我两天,第二天下午我才反应过来要去看一眼 cron 到底在哪个目录下跑的。
对,答案就是这个。
我写绝对路径的时候,改的是脚本里读数据库那一处。但那个脚本开头还有一段读配置文件的代码,用的还是 ./config.yaml。它先在这个文件上挂了,根本走不到数据库那一步。报错是数据库报的,因为……算了,具体逻辑我懒得解释了,反正就是它先挂了,报出来的错指向别的地方。这个我没看仔细,两天都在盯着数据库查。
真正发现是从终端里 cd / 然后手动执行了一遍脚本,瞬间复现。前后不超过五秒。
那一瞬间特别复杂。爽,因为终于找到了。想骂人,因为骂的是自己。
我朋友问我怎么解决的,我说路径问题。他说哦,那挺简单。我说对,挺简单。我没说花了多久。这种事说出来太丢人。
这两天我睡得也不好,前天晚上刷手机刷到两点多,明知道第二天早起还要查,就是睡不着。这属于我自己的毛病,跟报错没关系,但确实是一起发生的,想起来就烦。
所以你说要不要写点什么总结经验。不用了,我没什么经验可给。要说教训也谈不上,一个路径写错,能有什么教训。顶多以后写脚本开头统一加个 cd $(dirname $0),但这句话写出来是不是又像教程了。行吧,这句当我没说。
这篇不推荐任何东西,也没什么东西可推的。
就说到这。