如何在UNIX中用source命令动态获取文件变量名以替换占位符?
动态替换占位符:无需硬编码变量名的Shell方案
当然可以实现这种不用提前知晓变量名的动态替换!下面我会给你一套完整的解决方案,直接就能用:
核心思路
- 利用
source命令加载param1.txt中的所有变量到当前Shell环境 - 自动识别出从
param1.txt中加载的变量(避免混入系统原有变量) - 为每个变量动态生成
sed替换规则,把source1.txt中的{变量名}占位符替换为对应的值 - 一次性执行所有替换,输出结果文件
完整脚本实现
#!/bin/bash # 定义文件路径 PARAM_FILE="/root/parameters/param1.txt" SOURCE_FILE="/root/sources/source1.txt" OUTPUT_FILE="/root/parameters/Output.txt" # 记录source前的环境变量(用于后续识别新增变量) PRE_SOURCE_VARS=$(compgen -v) # 加载参数文件中的变量 source "$PARAM_FILE" # 找出新增的变量(即param1.txt中的变量) POST_SOURCE_VARS=$(compgen -v) NEW_VARS=$(comm -13 <(echo "$PRE_SOURCE_VARS" | sort) <(echo "$POST_SOURCE_VARS" | sort)) # 构建sed替换命令 SED_CMD="" for VAR in $NEW_VARS; do # 获取变量的值 VAR_VALUE="${!VAR}" # 转义sed中的特殊字符(比如/、&、\等),避免替换出错 ESCAPED_VALUE=$(printf '%s\n' "$VAR_VALUE" | sed -e 's/[\/&]/\\&/g') # 添加替换规则:不区分大小写(如果不需要可以去掉I参数) SED_CMD+="s/{$VAR}/$ESCAPED_VALUE/gI;" done # 执行替换并输出结果 sed "$SED_CMD" "$SOURCE_FILE" > "$OUTPUT_FILE" echo "替换完成,结果已保存到$OUTPUT_FILE"
关键细节说明
- 识别新增变量:用
compgen -v获取环境变量列表,通过comm命令对比source前后的变量差异,精准提取出param1.txt中的变量,不会误处理系统原有变量 - 特殊字符处理:用
sed -e 's/[\/&]/\\&/g'转义变量值中的特殊字符,避免这些字符破坏sed的替换规则 - 动态生成sed规则:循环遍历每个新增变量,自动生成
sed的替换语句,完全不需要硬编码变量名 - 不区分大小写替换:保留了你原脚本中的
gI参数,如果你不需要大小写不敏感,去掉I即可
测试你的示例文件
针对你给出的文件内容:
param1.txt:
PLANT_NAME=abc DB_NAME=gef
source1.txt:kdashkdhkasdkj {PLANT_NAME} jhdbjhasdjdhas kashdkahdk asdkhakdshk hfkahfkajdfk ljsadjalsdj {PLANT_NAME} {DB_NAME}
运行脚本后,Output.txt的内容会变成:
kdashkdhkasdkj abc jhdbjhasdjdhas kashdkahdk asdkhakdshk hfkahfkajdfk ljsadjalsdj abc gef
额外优化建议
如果你的param1.txt后续可能变成每行一个变量的格式(比如PLANT_NAME=abc单独一行),这个脚本也完全兼容,不需要做任何修改。
内容的提问来源于stack exchange,提问作者Arnab Basu
相关产品推荐
相关产品推荐

