IT

Spring Boot で AWS Systems Manager Parameter Store を使用する

少し前に Spring Boot で AWS Secrets Manager を使用する という記事を書きましたが、「パラメータの自動更新を使用しないのであれば Parameter Store でも十分」という意見をもらったので、改めてこちらについても調べてみました。

AWS Systems Manager Parameter Store とは

その名の通り、アプリケーションで必要となるパラメータを管理するためのAWSサービスです。パスワードなどのシークレットの管理にも使え、公式ドキュメントを見ると AWS Secrets Manager とも連携できるようです。Systems Manager(SSM)の一機能という立ち位置なので正式名称は少し長め。

Spring Boot からの使い方

Secrets Manager と同様、こちらも Spring Cloud にstarterプロジェクトがあるので、基本的にはこれを依存関係に追加するだけです。

  implementation group: 'org.springframework.cloud', name: 'spring-cloud-starter-aws-parameter-store-config', version: '2.2.6.RELEASE'

これによってアプリの起動時に内部で Parameter Store へアクセスするクライアントが生成され、自動的にパラメータを取得してくれます。使用する認証情報は AWS SDK の例に漏れず、環境変数やcredentials、EC2インスタンスのプロファイルとなります。

Secrets Manager では「シークレット」という単位で値を管理していましたが、Parameter Store ではパラメータを1つずつ登録していきます(「minimal-api」はサンプルのアプリケーション名です)。

登録画面はこんな感じで、タイプで「安全な文字列」を選ぶと Key Management Service の Systems Manager のAWSマネージド型キーで暗号化してくれます。Secrets Manager とほぼ同じですね(そちらでは Secrets Manager のキーが使われます)。

@RestController
public class SimpleResponseController {
	
	/** a secret parameter stored in Parameter Store */
	@Value("${application.auth.password}")
	private String password;
	
	@RequestMapping(path = "/", method = RequestMethod.GET)
	public String index() {
		return "password = " + password;
	}
}

あとはapplication.ymlの値を参照するのと同様に@Valueでキーを指定してあげるだけで使用できます。すごく簡単!(前回は苦労しましたが、今回は本当にすぐ動かせましたw) ちなみにapplication.ymlと Parameter Store の両方に同じパラメータがある場合は Parameter Store のものが優先され、application.ymlにはなくて Parameter Store にだけある場合もエラーにはならず Parameter Store のものが使われます。

設定方法や仕様

Parameter Store のアプリケーション側の設定は、application.ymlではなくbootstrap.ymlに記述する必要があります。項目はこのページの通りで、デフォルト値でも特に問題はないため、新たにbootstrap.ymlを作成しなくても使い始めることができます。

aws:
  paramstore:
#    prefix: /config
#    defaultContext: minimal-api
#    profileSeparator: _
#    failFast: true
#    name: minimal-api
    enabled: true
#    region: ap-northeast-1

bootstrap.ymlは Spring Cloud で使用する設定ファイルで、application.ymlよりも先に読み込まれ、起動処理を行うための設定を記述するためのもののようです。

Spring Boot のプロファイルも利用でき、例えばdevを指定すると「/config/{アプリケーション名}_dev」の方のパラメータを取得してくれます。

料金は標準パラメータであれば無料です。標準だとパラメータ数の上限は10,000、パラメータ値のサイズの上限は4KBです。これを超える場合は有料の詳細パラメータを使用する必要があります。

APIコールの回数でも料金が発生しますが、こちらもスタンダードスループットの範囲内であれば追加料金はありません。スタンダードスループットは40回/秒で、GetParameter、GetParameters、GetParametersByPathが対象です。

		GetParametersByPathResult paramsResult = source
				.getParametersByPath(paramsRequest);

Spring Cloud の実装を見てみると、GetParametersByPathで一括取得していました。ただ、以下の4通りのパスで取得するので、APIコールはアプリの起動ごとに4回となります(4通りのパスの全てのパラメータを取得した後、上の方にあるものが優先して使われます)。まあ十分スループットの範囲内ですね。

  • /config/{アプリケーション名}_{プロファイル}/
  • /config/{アプリケーション名}/
  • /config/application_{プロファイル}/
  • /config/application/

雑感

前回はシークレット情報ということで Secrets Manager に飛びついてしまいましたが、確かに自動更新を使わない場合は Parameter Store の方が適している…というか、無料で使える範囲があるのでこちらを使うべきですね。自前で暗号化処理を実装するのも手間ですし、AWSを使っているのであれば最初に Parameter Store を検討するのが良いと思います。