ICTSC2025 一次予選 問題解説: 問16 - 問19
問16
あるプロジェクトで、 Go 言語と Docker Compose を使ったアプリケーションを開発している。以下に、使用しているファイルを挙げる。
以下は app.env
である。
PATH=/go/bin:/usr/local/go/bin:/usr/local/sbin:/usr/local/bin:/usr/sbin:/sbin:/bin
USER_NAME=ICTSC
以下は compose.yaml
である。
services:
app:
build:
context: .
dockerfile: ./Dockerfile
volumes:
- ".:/usr"
- type: bind
source: ./log
target: /var/log
env_file: "app.env"
以下は Dockerfile
である。
FROM golang:1.24.5-alpine
COPY main.go run.sh ./
RUN chmod +x run.sh
RUN go build -o app ./main.go
CMD ["./run.sh"]
以下は main.go
である。
package main
import (
"fmt"
"os"
)
func main() {
name := os.Getenv("USER_NAME")
fmt.Println("Hello, " + name)
}
以下は run.sh
である。
#!/bin/sh
set -euo pipefail
# マシンの起動時間をログに記録する
uptime > /var/log/app.log
./app | tee -a /var/log/app.log
開発を続けていると、ある日、以下のようなエラーが出てコンテナが起動できなくなってしまった。
./run.sh: line 4: uptime: not found
選択肢の中から、解決のために有効な作業を全て選べ。実施の有無が解決に関与しない選択肢は選んではならない。なお、 Docker Compose のバージョンは 2.23.0 とする。
選択肢(複数選択)
- Docker Compose 設定のうちボリューム設定を変更する
- 実行時は distroless イメージを使用するようにマルチステージビルドを設定する
- イメージの再ビルドとコンテナの再起動を行う
- 環境変数の設定を変更する
run.sh
の適切な場所にunalias uptime
と 追記する- Dockerfile に
RUN dnf install <任意のパッケージ>
と追記する
解説
Docker コンテナ内で特定のコマンドが実行できないトラブルでした。原因となる設定は二点あります。
PATH
環境変数から必要なパスが抜けていること- 指定の Docker イメージでは
uptime
コマンドは/usr/bin
にある PATH
の値をよく見ると/usr/bin
が抜けている
- 指定の Docker イメージでは
/usr
ディレクトリがボリューム設定により書き換えられているcompose.yaml
の7行目で、ホスト側のカレントディレクトリ.
を/usr
にバインドしている
一点目を解決して /usr/bin
を PATH
に追加しても、二点目により /usr/bin/uptime
はコンテナ内から読み取れません。
したがって解決方法は、
- Docker Compose 設定のうちボリューム設定を変更する (選択肢 1.)
- 環境変数の設定を変更する (選択肢 4.)
の二つです。
※選択肢 3. は「イメージの再ビルドを行ったのち、コンテナの再起動を行う(実際には再ビルドは必要ないため不適)」という意図で記述しておりました。しかし設定変更後にはコンテナの再起動が必要になるため、運営内で議論ののち、選択肢文がミスリーディングであると判断して、選択肢 1, 3, 4 の三つを選んだチームも正答としてカウントしています。誤解を招く表現で申し訳ございません。
問17
Git のデフォルト設定を使用している時、リポジトリに追加しない無視ファイルを記述できる場所を全て選べ。なお、 Git のバージョンは 2.47.0 とする。
選択肢(複数選択)
.gitkeep
.gitignore.local
.git/config
.git/info/ignore
$GIT_DIR/exclude
$HOME/.git/config
$XDG_CONFIG_HOME/git/config
$XDG_CONFIG_HOME/git/ignore
解説
man gitignore 5
によると、無視設定が読み込まれる場所は以下のとおりです。
.gitignore
$GIT_DIR/info/exclude
- git-config の
core.excludesFile
で指定されたファイル- デフォルトは
$XDG_CONFIG_HOME/git/ignore
$XDG_CONFIG_HOME
が空の場合$HOME/.config/git/ignore
- デフォルトは
選択肢の中でこの三つに含まれるのは 8 の $XDG_CONFIG_HOME/git/ignore
のみです。
それ以外の選択肢についての解説は以下の通りです。
- 1, 2, 4, 5 は、名前がそれっぽいが関係ない(または実在しない)ファイル
.gitkeep
: 空ディレクトリを Git でトラックするために慣例的に用いられるファイル名.gitignore.local
: Git の仕様に含まれない、名前それっぽいだけのファイル.git/info/ignore
/$GIT_DIR/exclude
:.git
(または$GIT_DIR
) 配下のinfo/exclude
が正しい
- 3, 7 は git-config ファイル
- コンフィグに無視設定は直接記述できないので不適
- 6 は名前が git-config っぽいだけの実在しないファイル
$HOME
全体をを Git 管理していれば実在しうるが、上記の通り git-config ファイルは不適
問18
問題文
fetchurl
を使って GNU Hello 2.12.2 のソース (tar.gz) をダウンロードする Nix 式を作成したい。このとき以下に示す hello.nix
において hash
に当てはまる文字列の最初の10文字を記述せよ。ただし、ハッシュ方式は SHA-256 を使用し、ダウンロードサーバは https://ftp.gnu.org/gnu/hello/ とする。
以下は hello.nix の fetchurl
使用部分である。
src = fetchurl {
url = "";
hash = "ここに入る文字列";
};
解説
ハッシュ文字列は nix hash
コマンドで計算できます。
$ curl -O https://ftp.gnu.org/gnu/hello/hello-2.12.2.tar.gz
% Total % Received % Xferd Average Speed Time Time Time Current
Dload Upload Total Spent Left Speed
100 1141k 100 1141k 0 0 325k 0 0:00:03 0:00:03 --:--:-- 325k
$ nix hash file hello-2.12.2.tar.gz
sha256-WpqZbcKSzCTc9BHO6H6S9qrluNE72caBm0x6nc4IGKs=
または、 Nix 式全体を作成して hash
が空のまま nix-build
を実行することで計算させられます。
$ cat default.nix
{
pkgs ? import <nixpkgs> { },
}:
with pkgs;
stdenv.mkDerivation rec {
pname = "hello";
version = "2.12.2";
src = fetchurl {
url = "https://ftp.gnu.org/gnu/hello/hello-2.12.2.tar.gz";
hash = "";
};
}
$ nix-build
warning: found empty hash, assuming 'sha256-AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA='
these 2 derivations will be built:
/nix/store/vvs1m9azixlxk0m59rdlf3wa2cmv8nxm-hello-2.12.2.tar.gz.drv
/nix/store/jryhi5l94d8b2v6ibqr9v7kdbwqx5ki4-hello-2.12.2.drv
building '/nix/store/vvs1m9azixlxk0m59rdlf3wa2cmv8nxm-hello-2.12.2.tar.gz.drv'...
trying https://ftp.gnu.org/gnu/hello/hello-2.12.2.tar.gz
% Total % Received % Xferd Average Speed Time Time Time Current
Dload Upload Total Spent Left Speed
100 1141k 100 1141k 0 0 270k 0 0:00:04 0:00:04 --:--:-- 285k
error: hash mismatch in fixed-output derivation '/nix/store/vvs1m9azixlxk0m59rdlf3wa2cmv8nxm-hello-2.12.2.tar.gz.drv':
specified: sha256-AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA=
got: sha256-WpqZbcKSzCTc9BHO6H6S9qrluNE72caBm0x6nc4IGKs=
error: 1 dependencies of derivation '/nix/store/jryhi5l94d8b2v6ibqr9v7kdbwqx5ki4-hello-2.12.2.drv' failed to build
この中から 先頭10文字 を取り出した sha256-Wpq
が正答です。
問19
以下の Ansible インベントリを使用する際、ホスト 10.10.0.1
はいくつのグループに該当するか、整数で答えよ。なお、デフォルトグループは考慮せず、使用する Ansible のバージョンは 2.15.5 とする。
a:
hosts:
server:
ansible_host: 10.10.0.1
children:
b:
hosts:
c:
server:
c:
children:
d:
hosts: {"router":{"ansible_host":"10.0.10.1"},"children":{"g":{}}}
d:
hosts:
nfs:
ansible_host: 10.10.1.1
e:
children:
b:
d:
f:
children:
g:
a:
hosts:
router:
nfs:
server:
解説
当該ホストはグループ a
, f
に所属するため、 2個が正答です。
-
a
のhosts
直下にserver
という名前で10.10.0.1
ホストが記述されているので、当該ホストはa
に所属する -
a
のchildren
として記述されているb
には、server
は所属しないb
のhosts
としてc
(これはグループではなく新しいホストである)が記述されており、またその直下にserver
というキーが存在するが、これはa
で作成されたserver
という名前のホストとは無関係である- ホスト定義の直下には
ansible_host
等の設定(ホスト変数)が記述されるべきであり、ここにホスト名を置いても実在しない設定項目だと解釈されるため
- ホスト定義の直下には
-
b
と同じくa
のchildren
として記述されているc
には、server
は所属しない- まず、
c
のchildren
として指定されているd
には、後述するとおりserver
は所属しない hosts
の定義もserver
を含むような設定ではないrouter
ホストはserver
と異なる IP アドレスを持つためchildren
ホストに紐づけられた変数名 としてg
というキーが定義されているが、b
と似た理由で、ここにグループ名を置いても実在しない設定項目だと解釈されるため
- まず、
-
d
には、server
は所属しない- 無関係なホスト
nfs
が定義されているだけ
- 無関係なホスト
-
e
には、server
は所属しない- 2つの
children
としてb
,d
が指定されているが、先述の通りいずれもserver
を含まない
- 2つの
-
f
には、server
が所属する- 2つの
children
としてg
,a
が指定されているが、a
がserver
を含むためf
にもserver
が所属することになる - 3つの
hosts
としてrouter
,nfs
,server
が指定されているため、server
が所属することになる - (
server
を含むことが重複して定義されていることになるが問題ない)
- 2つの
-
f
のchildren
として記述されているg
には、server
は所属しない- 内容が空っぽであるため