传递变量以在 Debian Jessie 安装的 preseed 文件中使用

Tim*_*oop 9 debian environment-variables preseed packer

是否可以通过引导提示向 Debian 安装程序添加变量,以便可以在预置文件中使用该变量?

特别是,我正在尝试解决以下问题:

我们有一个非常广泛的安装后脚本,通常是从服务器下载的。但是现在我想创建 Packer 映像并将安装后脚本与其他 Packer 文件一起保留在版本控制中。为了访问 preseed,我可以在引导命令中执行“preseed/url=http://{{ .HTTPIP }}:{{ .HTTPPort }}/preseed.cfg”。但现在我希望安装程序从同一位置下载安装后脚本。

目前,安装后挂钩如下所示:

d-i preseed/late_command string wget -q -O /tmp/postinstall.sh http://our.public.server/postinstall.jessie.sh ; sh /tmp/postinstall.sh
Run Code Online (Sandbox Code Playgroud)

理想情况下,我想做类似的事情:

d-i preseed/late_command string wget -q -O /tmp/postinstall.sh http://{{ .HTTPIP }}:{{ .HTTPPort }}/postinstall.jessie.sh ; sh /tmp/postinstall.sh
Run Code Online (Sandbox Code Playgroud)

但是当然 Debian 安装程序不会用所需的值替换那些。所以我在想有可能将类似环境变量的变量传递给我们可以在 preseed 文件中使用的安装程序。

任何提示或提示表示赞赏!

编辑:尝试将 late_command 添加到引导命令中,但没有被接受。

编辑:尝试预置/运行,但它在不允许目标内命令的不同环境中运行。

编辑:这可以是一种解决方法:如何在 debian preseed 文件中通过管道将命令组合在一起?但我更喜欢将脚本放在一个单独的文件中。如果不可能,那也是不可能的。

whe*_*ler 5

这取决于您使用的操作系统,但 Linux 内核允许您指定环境变量作为内核参数。Linux 内核文档有一些很好的信息(重要段落加粗):

参数列表

内核命令行被解析为以空格分隔的字符串列表(引导参数)。大多数引导参数具有以下形式:

 name[=value_1][,value_2]...[,value_10]
Run Code Online (Sandbox Code Playgroud)

其中“name”是一个唯一的关键字,用于标识相关值(如果有)将分配给内核的哪个部分。请注意,10 的限制是真实的,因为当前代码仅处理每个关键字 10 个逗号分隔的参数。(但是,在异常复杂的情况下,您可以使用最多 10 个额外参数重复使用相同的关键字,> 假设 setup 函数支持它。)

大多数排序都在内核源文件 init/main.c 中编码。首先,内核检查参数是否是任何特殊参数“root=”、“nfsroot=”、“nfsaddrs=”、“ro”、“rw”、“debug”或“init”。这些特殊参数的含义如下所述。

然后它遍历设置函数列表以查看指定的参数字符串(例如“foo”)是否与特定设备或内核的一部分的设置函数(“foo_setup()”)相关联。如果您将 foo=3,4,5,6 行传递给内核,那么内核将搜索 bootsetups 数组以查看“foo”是否已注册。如果是,那么它将调用与 'foo' (foo_setup()) 关联的设置函数,并将内核命令行上给出的参数 3、4、5 和 6 传递给它。

任何不被接受为上述设置函数的“foo=bar”形式然后被解释为要设置的环境变量。
一个(无用的?)示例是使用 'TERM=vt100' 作为引导参数。

任何未被内核选取且未被解释为环境变量的剩余参数然后被传递到 PID 1,它通常是 init(1) 程序。传递给 init 进程的最常见参数是“single”这个词,它指示它以单用户模式启动计算机,而不是启动所有常用的守护进程。检查系统上安装的 init(1) 版本的手册页,看看它接受哪些参数。

这是我的构建器中的boot_command部分virtualbox-iso(适用于 Ubuntu 18.04):

boot_command:
  - '<esc><esc><enter><wait>'
  - '/install/vmlinuz noapic fb=false '
  - 'auto=true '
  - 'hostname={{.Name}} '
  - 'url=http://{{.HTTPIP}}:{{.HTTPPort}}/ubuntu.seed '
  - 'initrd=/install/initrd.gz '
  - 'http_proxy={{user `http_proxy`}} '
  - 'packer_host={{.HTTPIP}} '
  - 'packer_port={{.HTTPPort}} '
  - 'hello=world '
  - 'quiet --- <enter>'
Run Code Online (Sandbox Code Playgroud)

http_proxypacker_hostpacker_port,和hello参数完全是可选的,并会被内核转换成环境变量。

在我的ubuntu.seed文件中,我有以下行将hello环境变量打印到文件中:

d-i preseed/late_command string echo $hello > /target/home/packer/hello
Run Code Online (Sandbox Code Playgroud)

当我导入并启动 OVA 时,该文件将world作为其内容在我的主目录中。


Tim*_*oop 3

好吧,我自己解决了(在@lieter_的帮助下)。不太自豪,但它确实有效:

d-i preseed/late_command string wget -q -O /tmp/postinstall.sh http://`cat /proc/cmdline | sed 's/.*url=\([^ ]\+\).*/\1/'`/d-i/jessie/postinstall.sh ; sh /tmp/postinstall.sh
Run Code Online (Sandbox Code Playgroud)

这满足了我的需要,因为我们在安装时总是在命令行中添加 url= 。