菜单项消失与偏好设置丢失,人们总用同一个本能去修,但它们是两个互不相关的问题。一个是桌面集成,另一个是应用状态,而一个新图标本身不会改变其中任何一个。把两者分开只需一次实验,却能解释这个话题上的大部分困惑。启动器负责启动程序;记住什么由程序自己决定。

看起来像一件事的两件事

桌面集成的意思是环境能够找到可执行文件、显示名称和图标,并传入正确的参数。应用状态的意思是程序把配置文件写到持久位置,并在下次启动时读回来。两者互不蕴含,所以一个能用的快捷方式也可能启动一个已经忘光一切的客户端。

通过应用自带的控件改动一项无害的显示偏好,然后以同样的方式关闭并重新打开。如果偏好回来了,说明持久化正常工作,剩下的抱怨是找不到窗口,而不是数据没保存。如果它消失了,那么快捷方式只是干扰,真正的问题是那个进程把文件放在哪里。一次只测一项偏好,因为反复要求输入密码的客户端也许是在保护机密,而不是在丢失配置。

重装之前先比较启动输入

从桌面条目入手,读一读它到底做了什么,因为从菜单启动并不自动等同于从终端启动的同一进程环境。真正关键的键是 Exec、Path,以及间接的会话所提供的环境。Exec 里的包装脚本可以设置变量、切换目录,或调用菜单永远不会显示的特权助手。重装会替换应用本来就有的文件,而那很少是发生变化的那一项。

grep -h '^Exec=' ~/.local/share/applications/*.desktop
desktop-file-validate ~/.local/share/applications/client.desktop

先看 ~/.local/share/applications 下的文件,再看 /usr/share/applications 下的,因为用户副本会遮蔽系统副本。当条目表现异常时运行 desktop-file-validate,并寻找仍指向已删除路径的陈旧副本。多数桌面仍然优先采用无效的用户副本,所以一个坏文件可以把条目从菜单里移除,而软件包自带的文件依然有效。然后再手动运行同一条命令,比较两次启动各自产出什么。

偏好设置究竟住在哪里

遵循XDG 基础目录规则的应用把配置放在 $XDG_CONFIG_HOME,把持久状态放在 $XDG_STATE_HOME,把一次性数据放在 $XDG_CACHE_HOME;当这些变量未设置时,默认使用 ~/.config、~/.local/state 和 ~/.cache。这三者只是角色而非承诺,所以某个具体的 VPN 产品完全可能记载另一套做法。读厂商自己的文档,胜过从目录名去猜路径。文档太薄时,就去观察进程,而不是文件系统。

按文件打开过滤的跟踪会显示客户端尝试过的每一条配置路径,包括它退出时写入的那条。用同一个用户、同一套环境运行它,再把这些路径与你预期的目录比对。

strace -f -e trace=openat,stat -o /tmp/vpn.log vpn-client

机密与配置文件各有其主

已保存的配置文件和已保存的凭据是两个独立对象,往往分开存储。一个可能住在配置文件里,另一个则待在按会话解锁的密钥环中,所以再次索要密码的客户端也许只是在按设计行事。为了止住提示而删掉配置文件,正是人们弄丢一份可用配置的方式。

特权启动让这更复杂,因为通过 sudo 或 PolicyKit 助手启动,可能呈现另一个家目录,从而呈现另一套配置。要修正的是应用文档所指的那个具体文件的属主,而不是递归整个家目录;然后决定今后由哪个身份拥有该配置文件,并让以后的启动保持一致。

图标能告诉你什么、不能告诉你什么

图标只能证明启动器文件能解析,仅此而已。连接状态属于客户端,所以唯一可靠的检查是界面、路由或客户端自己的状态输出。启动失败的托盘小程序会让一条正常的隧道看起来是坏的,而过期的小程序会让一条坏隧道看起来正常。分别测试连接和启动器,然后写下你真正修好的是哪一个。

如果两者都坏了,不要试图把修复当成一次改动。先修条目,确认启动,再确认隧道,并记录每一步的结果。正是这份记录,让下一次“设置丢失”的报告可以被诊断,而不是重复这一次;它也告诉下一个人,问题的哪一半是真的。

相关文章