DockerやKubernetesの設定ファイルを書いていて、「この記号、どう書けばいいの?」と困ったことはありませんか?
YAMLファイルには特殊な意味を持つ文字があり、そのまま書くとエラーになることがあります。
この記事では、YAMLで文字列を正しくエスケープ(特殊文字を無効化)する方法について、初心者の方にも分かりやすく解説していきます。これを読めば、YAMLの文字列でもう悩むことはありません!
YAMLって何?まずは基礎知識から
YAML(ヤムル)は「YAML Ain’t Markup Language」の略で、人間が読みやすい形式でデータを記述するための言語です。
よく使われる場面:
- Docker Compose の設定ファイル(docker-compose.yml)
- Kubernetes のマニフェストファイル
- CI/CDツール(GitHub Actions、GitLab CI など)の設定
- アプリケーションの設定ファイル
拡張子は「.yml」または「.yaml」です。
YAMLの基本構造
YAMLはシンプルな構造をしています。
基本的な書き方:
# コメントはシャープ記号で書きます
キー: 値
# 階層構造はインデント(スペース)で表現
user:
name: 山田太郎
age: 25
email: yamada@example.com
# リストは「-」(ハイフン)で表現
fruits:
- apple
- banana
- orange
インデント(字下げ)が重要で、通常は2スペースまたは4スペースを使います。
YAMLの文字列:3つの書き方
YAMLで文字列を書く方法は、大きく分けて3つあります。
1. プレーンスタイル(クォートなし)
最もシンプルな書き方です。
書き方:
message: これは普通の文字列です
name: 山田太郎
メリット:
- 見た目がすっきりしている
- 入力が簡単
デメリット:
- 特殊文字が使えない場合がある
- 予約語(true、false、null など)と区別できない
2. シングルクォート(’)スタイル
文字列をシングルクォートで囲む書き方です。
書き方:
message: 'これはシングルクォートで囲んだ文字列です'
path: 'C:\Users\yamada\Documents'
特徴:
- ほとんどの特殊文字をそのまま書ける
- エスケープシーケンスは解釈されない
- シングルクォート自体を書きたい場合は、2つ重ねる
3. ダブルクォート(”)スタイル
文字列をダブルクォートで囲む書き方です。
書き方:
message: "これはダブルクォートで囲んだ文字列です"
path: "C:\\Users\\yamada\\Documents"
newline: "1行目\n2行目"
特徴:
- エスケープシーケンスが使える
- より柔軟な文字列表現が可能
- バックスラッシュでエスケープする
エスケープが必要な文字と状況
YAMLで特別な意味を持つ文字
以下の文字は、YAMLで特別な意味を持つため、注意が必要です。
特殊文字一覧:
- コロン(:) → キーと値の区切り
- ハイフン(-) → リストの要素
- シャープ(#) → コメント
- アンパサンド(&) → アンカー定義
- アスタリスク(*) → エイリアス参照
- 波括弧({}) → インライン辞書
- 角括弧([]) → インラインリスト
- パイプ(|) → リテラルスタイル
- 大なり(>) → フォールデッドスタイル
- 感嘆符(!) → タグ
- パーセント(%) → ディレクティブ
これらを文字列として使いたい場合、適切にエスケープする必要があります。
ダブルクォートでのエスケープシーケンス
ダブルクォートで囲んだ文字列では、バックスラッシュ(\)を使ってエスケープできます。
主なエスケープシーケンス一覧
# 改行
newline: "1行目\n2行目"
# タブ
tab: "項目1\t項目2"
# バックスラッシュ自体
backslash: "C:\\Users\\yamada"
# ダブルクォート
quote: "彼は\"こんにちは\"と言った"
# キャリッジリターン
cr: "行末\r\n"
# Unicode文字(16進数4桁)
unicode: "\u3042" # 「あ」
# Unicode文字(16進数8桁)
unicode32: "\U0001F600" # 😀
よく使うエスケープシーケンス:
エスケープ | 意味 | 使用例 |
---|---|---|
\\ | バックスラッシュ | "C:\\path\\to\\file" |
\" | ダブルクォート | "He said \"Hi\"" |
\n | 改行(LF) | "行1\n行2" |
\r | キャリッジリターン(CR) | "行末\r\n" |
\t | タブ | "列1\t列2" |
シングルクォートでのエスケープ
シングルクォート内では、エスケープシーケンスは使えません。
ただし、シングルクォート自体を表現したい場合は、2つ連続で書きます。
例:
# シングルクォート自体を含む文字列
message: 'It''s a beautiful day'
# 結果: It's a beautiful day
# パスの場合もそのまま書ける
path: 'C:\Users\yamada\Documents'
# バックスラッシュもそのまま
regex: '\d+\.\d+'
シングルクォートの特徴:
\n
は改行にならず、そのまま「\n」という2文字になる- バックスラッシュもそのまま表示される
- Windowsのファイルパスを書く時に便利
プレーンスタイルでの注意点
クォートなしで書く場合、いくつかの注意点があります。
予約語に注意
以下の文字列は、特別な意味を持ちます。
予約語の例:
# これらは真偽値として解釈される
bool1: true # 真
bool2: false # 偽
bool3: yes # 真
bool4: no # 偽
# これはnull(値なし)として解釈される
value: null
value2: ~
# 数値として解釈される
number: 123
float: 3.14
これらを文字列として扱いたい場合は、クォートで囲む必要があります。
# 文字列として扱う
string1: "true" # 文字列の"true"
string2: "123" # 文字列の"123"
string3: "null" # 文字列の"null"
先頭や末尾の空白に注意
プレーンスタイルでは、先頭と末尾の空白は自動的に削除されます。
# 先頭の空白は無視される
text: hello # "hello"として解釈される
# 空白を保持したい場合はクォートを使う
text: " hello " # " hello "として保持される
複数行文字列の書き方
長い文字列を複数行に分けて書く方法が2つあります。
リテラルスタイル(|):改行をそのまま保持
パイプ記号(|)を使うと、改行がそのまま保持されます。
書き方:
description: |
これは1行目です。
これは2行目です。
これは3行目です。
結果:
これは1行目です。
これは2行目です。
これは3行目です。
改行がそのまま残ります。
フォールデッドスタイル(>):改行を空白に変換
大なり記号(>)を使うと、改行が空白に置き換えられます。
書き方:
description: >
これは長い文章です。
複数行に分けて書いていますが、
実際には1行にまとめられます。
結果:
これは長い文章です。 複数行に分けて書いていますが、 実際には1行にまとめられます。
改行が空白になり、1行の文字列になります。
複数行文字列でエスケープが必要な場合
複数行文字列の中でも、ダブルクォートを使えばエスケープが可能です。
code: |
def hello():
print("Hello, World!")
return True
この場合、ダブルクォートはそのまま文字列として扱われます。
実際の使用例
例1:Docker Composeでの環境変数
version: '3.8'
services:
web:
image: nginx
environment:
# 特殊文字を含む環境変数
DATABASE_URL: "postgres://user:p@ssw0rd!@localhost:5432/mydb"
# パスを含む設定
LOG_PATH: "/var/log/app.log"
# 改行を含むメッセージ
WELCOME_MESSAGE: "Welcome!\nPlease log in."
ポイント:
- パスワードに特殊文字(@、!)が含まれるため、ダブルクォートで囲む
- パスもダブルクォートで囲むと安全
- 改行が必要な場合は
\n
を使う
例2:Kubernetesのシークレット
apiVersion: v1
kind: Secret
metadata:
name: my-secret
type: Opaque
stringData:
# JSONを含む設定
config.json: |
{
"api_key": "abc123",
"url": "https://api.example.com/v1"
}
# スクリプトを含む
init.sh: |
#!/bin/bash
echo "Starting application..."
export PATH="/usr/local/bin:$PATH"
ポイント:
- リテラルスタイル(|)で複数行のJSONやスクリプトを記述
- インデントが重要なので注意
例3:GitHub Actionsでのコマンド実行
name: CI
on: [push]
jobs:
build:
runs-on: ubuntu-latest
steps:
- name: Run tests
run: |
echo "Running tests..."
npm test
echo "Tests completed!"
- name: Set output with special chars
run: echo "result=success" >> $GITHUB_OUTPUT
- name: Message with quotes
run: echo "He said \"Hello, World!\""
ポイント:
- 複数のコマンドを実行する場合はリテラルスタイルが便利
- シェルのエスケープとYAMLのエスケープの両方に注意
例4:設定ファイルでの正規表現
validation:
# シングルクォートなら正規表現がそのまま
email_pattern: '^\w+@\w+\.\w+$'
# ダブルクォートならエスケープが必要
phone_pattern: "^\\d{3}-\\d{4}-\\d{4}$"
# プレーンだとバックスラッシュが問題になる場合も
url_pattern: ^https?://[\w\-\.]+
ポイント:
- 正規表現はシングルクォートで囲むと楽
- ダブルクォートの場合、バックスラッシュを二重にする必要がある
よくあるエラーと対処法
エラー1:「mapping values are not allowed here」
原因:
コロン(:)を含む文字列をクォートで囲んでいない。
NG例:
url: http://example.com:8080
OK例:
url: "http://example.com:8080"
エラー2:「found unexpected end of stream」
原因:
ダブルクォートやシングルクォートの閉じ忘れ。
NG例:
message: "Hello, World!
OK例:
message: "Hello, World!"
エラー3:「could not find expected ‘:’」
原因:
シャープ記号(#)を含む文字列をクォートで囲んでいない。
NG例:
tag: #important
OK例:
tag: "#important"
エラー4:予期しない型変換
原因:
数値や真偽値として解釈されてしまう。
NG例:
version: 1.0 # 数値として解釈される
enabled: yes # 真偽値として解釈される
OK例:
version: "1.0" # 文字列として扱われる
enabled: "yes" # 文字列として扱われる
エスケープ方法の選び方
どの方法を使えばいいか、状況別にまとめます。
シンプルな文字列 → プレーンスタイル
name: 山田太郎
city: Tokyo
特殊文字を含まない単純な文字列なら、クォートなしが一番読みやすいです。
パスや正規表現 → シングルクォート
file_path: 'C:\Users\yamada\Documents'
pattern: '^\d+\.\d+$'
バックスラッシュを多用する場合は、シングルクォートが便利です。
改行や特殊なエスケープが必要 → ダブルクォート
message: "1行目\n2行目"
quote: "He said \"Hi\""
エスケープシーケンスを使いたい場合は、ダブルクォートを選びます。
長い文章やコード → リテラル/フォールデッド
description: |
これは長い説明文です。
複数行に渡って書きます。
読みやすさを重視します。
複数行の文字列は、リテラルスタイル(|)が最適です。
YAMLのバリデーションツール
設定ファイルが正しいか確認するツールも活用しましょう。
オンラインツール
- YAML Lint(https://www.yamllint.com/)
- ブラウザで簡単にチェックできる
- エラー箇所を指摘してくれる
コマンドラインツール
# yamllintのインストール
pip install yamllint
# チェック実行
yamllint config.yml
エディタの拡張機能
- VS Code → YAML拡張機能
- IntelliJ IDEA → デフォルトで対応
- Vim/Neovim → YAMLプラグイン
これらを使えば、リアルタイムでエラーを検出できます。
よくある疑問に答えます
Q. タブ文字は使える?
使えません。
YAMLではインデントにスペースのみが使えます。タブ文字を使うとエラーになります。エディタの設定で、タブキーを押した時にスペースが入力されるようにしておきましょう。
Q. 日本語は使える?
使えます。
ファイルをUTF-8で保存すれば、日本語を含む文字列も問題なく扱えます。
message: こんにちは、世界!
description: "日本語も\nちゃんと使えます。"
Q. JSONとYAMLの違いは?
YAMLはJSONのスーパーセット(上位互換)です。
つまり、有効なJSONは、そのまま有効なYAMLでもあります。ただし、YAMLの方が人間にとって読みやすい記法を提供しています。
Q. 空白や改行が多いとエラーになる?
基本的には大丈夫です。
ただし、インデントが正しくないとエラーになります。同じ階層の要素は、同じインデント幅で揃える必要があります。
まとめ:適切なエスケープで安全なYAML
YAMLのエスケープ文字列は、特殊文字を正しく扱うための重要な知識です。
重要ポイントをおさらい:
- 文字列の書き方は3種類:プレーン、シングルクォート、ダブルクォート
- 特殊文字を含む場合はクォートで囲む
- バックスラッシュでエスケープするにはダブルクォートを使う
- シングルクォートは正規表現やパスに便利
- 複数行文字列にはリテラルスタイル(|)を使う
- 予約語(true、false、null など)を文字列にする場合はクォートが必要
- バリデーションツールでエラーをチェックする
最初は複雑に感じるかもしれませんが、基本を押さえれば、YAMLの文字列は自由自在に扱えるようになります。
DockerやKubernetesの設定ファイルを書く時も、もうエスケープで悩むことはありませんよ!
コメント