ansible - 使用 Ansible 的文件模块时如何防止 ToCToU 问题?
问题描述
我的工作环境:
- Ubuntu 14.04
- Ansible 2.6.3
- Ansible 剧本 2.6.3
- Python 2.7.6
我正在编写一个 Ansible 剧本,其中包含一个任务,该任务创建一个指向其他地方的目录的符号链接。任务使用file
模块(为了讨论方便,我简化了代码):
- name: Link the app configuration.
file:
path: "/home/username/appConfig.lnk"
src: "/usr/share/app_name/appConfig"
state: link
force: no
become: no
如果任务执行成功,/home/username/appConfig.lnk
则会创建一个符号链接并指向目录/usr/share/app_name/appConfiig
。
但是,在实际用例中,用户可能会修改appConfig.lnk
以指向其他内容,即适合他们需要的自定义配置。这在我们的使用中是预期和有效/usr/share/app_name/appConfig
的,并且唯一尝试提供可用的初始配置。
因此,我希望剧本任务仅appConfig.lnk
在它根本不存在时创建。如果路径/home/username/appConfig.lnk
已经存在,无论它是指向默认配置的符号链接、指向其他一些自定义配置、文件或目录的符号链接,我都想跳过创建。
但是,设置为的file
模块的行为如下:force
no
path
存在并且是一个目录:Fail。path
存在并且是一个文件:Fail。path
存在并且是指向其他位置的符号链接,而不是src
:自动重新创建指向的链接src
。
为了解决这个问题,我之前添加了一个任务来调用stat
模块:
- name: Get the app configuration status.
stat:
path: "/home/username/appConfig.lnk"
register: stat_config
become: no
- name: Link the app configuration.
when: not stat_config.stat.exists # <-- New condition
file:
path: "/home/username/appConfig.lnk"
src: "/usr/share/app_name/appConfig"
state: link
force: no
become: no
但我认为这会引入ToCToU 问题,因为尽管不太可能,但可能会在调用appConfig.lnk
后立即删除,因此模块被跳过,我最终得到一个系统,显示一切都已成功完成,但未创建链接。stat
file
所以我想知道是否有办法实现我想要的但避免可能的 ToCToU 问题。
解决方案
一种选择是使用“命令创建”结构。
- name: Create link
command: ln -s /usr/share/app_name/appConfig /home/username/appConfig.lnk
args:
creates: /home/username/appConfig.lnk
关于命令模块的讨论在这里
推荐阅读
- sql-server - 恢复超过 10GB 大小的 .bak
- python - Docker - 无法获取用户网络摄像头:getUserMedia() 不再适用于不安全的来源
- python - 使用flask从用户那里获取URL并压缩图像
- r - 在 R 中完成执行脚本时发送通知
- r - 子集仅返回具有多行的组的完整案例
- list - 按名称列出的短名单 - Angular 5 + Firebase
- r - 通过粘贴替代行来合并多个数据框
- excel - 将 Excel 公式字符串解析为 VBA 中的前面字符串、函数、参数和后函数字符串
- selenium - 代理元素: DefaultElementLocator 'By.xpath:
- ios - Sygic 问题:创建替代路线时使路线不可见