Fish Shell中从其他脚本获取变量值失败的问题排查
问题原因
你的问题出在Fish Shell和POSIX Shell(如bash、dash)的变量赋值语法差异上:
- Fish Shell里用
set 变量名 '值'定义变量,这是Fish的特有语法。 - 但你的脚本开头指定了
#!/bin/sh,会调用系统默认的POSIX兼容Shell(比如Ubuntu的dash),而POSIX Shell里的set命令是用来设置位置参数或Shell选项的,不是用来定义普通变量的。所以当autostart_once.sh以/bin/sh运行时,latlong.sh里的set latlong 'x.xxxxxx:x.xxxxxx'根本没有给latlong变量赋值,后续调用时自然为空。 - 而你在Fish终端里source脚本时,遵循的是Fish的语法规则,
set命令能正确赋值,所以echo $latlong能输出内容。
解决方案
修改latlong.sh的变量赋值语法,改成POSIX Shell兼容的格式,同时满足你的需求:
- 修改
latlong.sh内容:
#!/bin/sh latlong='x.xxxxxx:x.xxxxxx'
这是POSIX标准的变量赋值方式,所有兼容POSIX的Shell(sh、bash、dash等)都能识别。
- 保持
autostart_once.sh不变:
#!/bin/sh . ./latlong.sh # some start up commands redshift-gtk -l $latlong -t 6500:3600 &
修改后,latlong变量只会在autostart_once.sh的Shell进程内有效,不会泄露到外部环境;同时latlong.sh依然可以单独加密,不影响autostart_once.sh的公开使用。
补充:如果你的系统默认/bin/sh是bash,也可以用local latlong='xxx'在latlong.sh里定义局部变量,但local是bash扩展,并非POSIX标准。如果要严格兼容所有POSIX Shell,用普通赋值即可——source脚本后变量本来就只在当前Shell会话内,已经满足你“不希望变量在启动脚本外部可访问”的需求。
内容的提问来源于stack exchange,提问作者SunnyMonster
相关产品推荐
相关产品推荐

