1
0

Delete article

Deleted articles cannot be recovered.

Draft of this article would be also deleted.

Are you sure you want to delete this article?

More than 1 year has passed since last update.

1Password CLIを使った環境変数の管理とDocker Composeでの読み込み方法

1
Last updated at Posted at 2024-08-15

1PasswordのCLIを使って、環境変数の安全な管理ができるようになった。さらに、1Passwordの値を直接読み取って、docker composeも実行できるようにした。

TL;DR

  • 1Passwordに現在の環境変数をインポートする
    • 手動でもできるが、opコマンド(1PasswordのCLI)を使うと楽
  • .env.localから1Passwordの値を書き換える
.env.local
OP_ROOT_ENV_PATH="hoge-vault/local/root-env"
MYSQL_ROOT_PASSWORD="op://${OP_ROOT_ENV_PATH}/MYSQL_ROOT_PASSWORD"
MYSQL_DATABASE="op://${OP_ROOT_ENV_PATH}/MYSQL_DATABASE"
  • .envから1Passwordの値を読み込める形でdocker composeを実行する
cp .env.local .env && \
op run --env-file="./.env" -- docker compose up -d && docker compose ps

はじめに

ローカル環境変数の値を.env.localにベタ書きしていたが、git管理されてしまうため、セキュリティ上の問題がある。以前勤務していた会社では、

  • 社内wikiの記述や特定の管理者のみが管理
  • 必要になればslackのDMでのやりとり
  • サーバーで直接環境変数を設定する

とかなり手間をかけて環境変数を扱っていた。セキュリティや事故防止を考えれば苦肉の策だったかもしれないが、当時の自分にもいい代替案は提示できなかった。

その後転職先で1Passwordを知った。家族との諸々のアカウント共有にも便利で家庭内でも導入した。いろいろ試しているうちに、開発にも利用できることがわかったため、さっそく導入してみた。

移行前の状況

環境変数

.env.localにベタ書きで保持されている

.env.local
# MySQL 環境変数
MYSQL_ROOT_PASSWORD=hogeroot
MYSQL_DATABASE=hogedb
MYSQL_DATABASE_TEST=test_hoge
MYSQL_USER=hogedb
MYSQL_PASSWORD=hogepassword

コンテナ起動コマンド

.env.localを.envにコピーして、コンテナを起動

cp .env.local .env && docker compose up -d && docker compose ps

1Passwordの開発者設定

下記の記事を参考にした。

1Password>設定>開発者で
1Password CLIと連携
にチェックを入れる

現行の.envの内容を1Passwordにインポートする

vault、セクション、環境の構成を決める

私は下記の構成にした。

  • vault: hoge-vault
  • アイテムタイプ: セキュアノート
  • アイテム名: local(環境)
  • セクション: root-env

他の記事を見ると、環境変数ごとにアイテムを作成し、セクションと環境を割り当てる方法もあるようだ。

vault、アイテムを作成する

私は1PasswordのGUIからアイテムを作成した。
image.png

現行の.envから、opコマンドを作成する

.env.localから各環境変数ごとのopコマンドを作成するために、雛形用ファイルを作成する。

cp .env.local .env_to_op_command

VSCodeの置換機能を使って、各環境変数ごとのopコマンドを作成する。下記の置換方法は一例だ。作成したコマンドや.envの内容によって、置換方法は異なる。

検索:
^(.+)$
置換:
op item edit --vault hoge-vault local root-env.$1
.env_to_op_command
op item edit --vault hoge-vault local root-env.MYSQL_ROOT_PASSWORD=hogeroot
op item edit --vault hoge-vault local root-env.MYSQL_DATABASE=hogedb
op item edit --vault hoge-vault local root-env.MYSQL_DATABASE_TEST=test_hoge
op item edit --vault hoge-vault local root-env.MYSQL_USER=hogedb
op item edit --vault hoge-vault local root-env.MYSQL_PASSWORD=hogepassword

作成したコマンドをターミナルにコピペして実行すると、1Passwordに.env.localの内容がインポートされる。

インポートが確認できたら、.env_to_op_commandは削除する。

現行の.env.localが1Passwordの値を読み取れるようにする

1Passwordの秘密参照を.env.localに書き換える

1PasswordのセクションまでのパスをOP_ROOT_ENV_PATHとして設定する。まずVSCodeの置換機能を使って、既存の.env.localの値を書き換える。

検索:
^(.+?)=(.+)$
置換:
$1="op://${OP_ROOT_ENV_PATH}/$1"
.env.local
# MySQL 環境変数
MYSQL_ROOT_PASSWORD="op://${OP_ROOT_ENV_PATH}/MYSQL_ROOT_PASSWORD"
MYSQL_DATABASE="op://${OP_ROOT_ENV_PATH}/MYSQL_DATABASE"
MYSQL_DATABASE_TEST="op://${OP_ROOT_ENV_PATH}/MYSQL_DATABASE_TEST"
MYSQL_USER="op://${OP_ROOT_ENV_PATH}/MYSQL_USER"
MYSQL_PASSWORD="op://${OP_ROOT_ENV_PATH}/MYSQL_PASSWORD"

1Passwordの秘密参照を取得

1PasswordのGUIで、各変数の値を右クリックし、秘密参照をコピーを選択して、秘密参照を取得する。"op://hoge-vault/local/root-env/MYSQL_ROOT_PASSWORD"のような形式だ。

.env.localに上記1Password秘密参照のセクション部分までを変数として設定する。

.env.local
# 1Passwordのパス
OP_ROOT_ENV_PATH="hoge-vault/local/root-env"

# MySQL 環境変数
MYSQL_ROOT_PASSWORD="op://${OP_ROOT_ENV_PATH}/MYSQL_ROOT_PASSWORD"
MYSQL_DATABASE="op://${OP_ROOT_ENV_PATH}/MYSQL_DATABASE"
MYSQL_DATABASE_TEST="op://${OP_ROOT_ENV_PATH}/MYSQL_DATABASE_TEST"
MYSQL_USER="op://${OP_ROOT_ENV_PATH}/MYSQL_USER"
MYSQL_PASSWORD="op://${OP_ROOT_ENV_PATH}/MYSQL_PASSWORD"

補足

ここでOP_ROOT_ENV_PATHは文字列として扱いたいので、op://をつけない。

もし、

 OP_ROOT_ENV_PATH="op://hoge-vault/local/root-env"

op://をつけると、1Passwordの読み込みが始まってしまう。

公式ドキュメント

によれば、秘密参照のルールは

op://<vault-name>/<item-name>/[section-name/]<field-name>

となっているが、上記例ではセクション名のroot-envで終わっている。
そのためエラーが出てしまうので、op://をつけないようにする。

1Password CLI起点のdocker composeコマンドを作成

既存のコマンドは

cp .env.local .env && docker compose up -d && docker compose ps

となっているが、このまま実行すると、.envで1Passwordの値を読み取れない。そのため、1Passwordの値を読み取れるように、docker composeコマンドを修正する。

op runオプションの追加

公式ドキュメント

を参考に下記のオプションを利用する

  • --env-file="./.env"
    • 環境変数を読み取るファイルを相対パスで指定する
  • --
    • 1Passwordの環境変数をロードして実行したいコマンドを指定する
      上記を使い、元のコマンドを下記のように修正する。
cp .env.local .env && \
op run --env-file="./.env" -- docker compose up -d && docker compose ps

これで、1Passwordに格納されている値を利用して、コンテナ実行を行うことが可能となった。

今後やってみたいこと

1Passowrd Service Accountの導入

公式ドキュメントを読んでいると、

We recommend using 1Password Service Accounts to follow the principle of least privilege. Service accounts support restricting 1Password CLI to specific vaults, so that processes in your authorized terminal session can only access items required for a given purpose.

最小限の権限の原則に従うために、1Passwordサービスアカウントを使用することをお勧めします。サービスアカウントは、1Password CLIを特定のVaultに制限することをサポートします。したがって、承認されたターミナルセッション内のプロセスは、特定の目的に必要なアイテムにのみアクセスできます。

とあった。個人開発のローカル環境作成だと大げさかもしれないが、web公開する場合は導入してみたい。
またこれを利用すれば、理屈上実際の値を意識、一切利用しない開発が可能になるかもしれない

.env.localの環境変数をまとめる

# MySQL 環境変数
MYSQL_ROOT_PASSWORD="op://${OP_ROOT_ENV_PATH}/MYSQL_ROOT_PASSWORD"
MYSQL_DATABASE="op://${OP_ROOT_ENV_PATH}/MYSQL_DATABASE"
MYSQL_DATABASE_TEST="op://${OP_ROOT_ENV_PATH}/MYSQL_DATABASE_TEST"
MYSQL_USER="op://${OP_ROOT_ENV_PATH}/MYSQL_USER"
MYSQL_PASSWORD="op://${OP_ROOT_ENV_PATH}/MYSQL_PASSWORD"

の書き方であれば、これらの値は環境を意識する必要がないので.env.localからは切り離し、

環境を切り替える仕組みは

.env.local
# 1Passwordのパス
OP_ROOT_ENV_PATH="hoge-vault/local/root-env"

だけに集約できないかなと考えている

1
0
0

Register as a new user and use Qiita more conveniently

  1. You get articles that match your needs
  2. You can efficiently read back useful information
  3. You can use dark theme
What you can do with signing up
1
0

Delete article

Deleted articles cannot be recovered.

Draft of this article would be also deleted.

Are you sure you want to delete this article?