Keycloak (Quarkus版) でアクセスログを出力し、任意の名前でローテートする
※2024/10/6追記
本記事の設定は、Keycloak 24以降 (試したバージョンは24.0.5) でも適用可能だった。
Keycloak 23では設定を lib\quarkus\build-system.properties
に書いていたが、Keycloak 24以降は conf\quarkus.properties
に書けば動作する。
概要
Quarkus版のKeycloak (バージョン17からのデフォルト) にて、ログローテーションしながらアクセスログを出す方法を記載する。 本エントリでは、logrotateなどの外部プログラムを使用せず、Keycloakの設定のみで行う方法を扱う。
このエントリの結論としては、以下のことができた (できなかった)。
- アクセスログを任意のファイル名で出力する。
- ログファイルの日次ローテートを行い、任意のサフィックスを付けたファイル名で保存する。
- ローテートしたファイルについて、任意の世代数だけ保持する (古いものを削除する) ことはできなかった。
動機
Quarkus版のKeycloak (バージョン17からのデフォルト) にて、アクセスログを任意のログファイルに出力したい。 さらに、そのログファイルを日次でローテーションしたい、となったときに設定方法を探したところ、なかなか設定方法にたどり着かなかったため、書き残すことにした。
実行環境・前提条件
目次
アクセスログ周りの動作
以前のWildFly版Keycloakと同様に、ログの設定はアプリケーションサーバー側 (Quarkus) で設定することになる。
KeycloakはベースとなるQuarkusの機能を使ってログをファイルに出力するようになっている。 そのため、Quarkusでアプリケーションを構築するときと同様に、JBoss Loggingの設定を行うことになる。
蛇足だが、QuarkusはHTTPサーバーとしてundertowを使用しているのだと思っていたら、Vert.xというライブラリを使用するようになっているそうだ。アクセスログを出力しているのはHTTPサーバーの機能を持っている部分であり、そこに対しての設定を行うため少し触れた。
シンプルにアクセスログを出力しようとする場合は、以下の参考サイトで説明している、
下記の設定を行うことで、Keycloakの最上位のディレクトリで、quarkus.logという名称のファイルにアクセスログが出力される。
quarkus.http.access-log.enabled=true quarkus.http.access-log.log-to-file=true
これらのデフォルト値や設定できる項目は、以下の公式ドキュメントにて確認できる。アクセスログのファイル名は公式ドキュメントでも触れられており、簡単に指定できる。
アクセスログを出力したファイルのローテートを行う場合は、quarkus.http.access-log.rotate
をtrue
にすると良さそうだが、ローテートの細かい設定はできないようだ。
quarkus.http.access-log.rotate
をtrue
にすると、日次でローテートされ、以下のような名称のファイルが作られる (accessや.logは設定で変更可能)。また、調査をしていないが、公式ドキュメントには保持するログファイルの世代数が設定できるかは明記されておらず、できるかどうかが不明だった。
access2024-01-26.log
これだと以下のようなお決まりのことをやりたい場合は機能が足りない。
- 日次でローテートする。
- 保持する世代数を指定する (ある世代数を超える場合は古いファイルを削除する)。
- ログファイルのファイルサイズが一定を超えたらローテートする。
これらを設定するためには以下で説明があるロギングの機能と組み合わせが必要になる。次は具体的な設定方法を記載する。
設定方法
設定箇所 (設定ファイル等)
Quarkusの設定を行うため、以下のファイルに対して設定値を指定する。 ビルドして設定値を反映する以外にも、システムプロパティ(-Dオプション)などを指定することもできるようだ。
Keycloak 23までは以下のファイルに、
lib\quarkus\build-system.properties
Keycloak 24からは以下のファイルに記載する。
conf\quarkus.properties
設定後は以下のようにビルドを実施し、Keycloakを起動する。
bin\kc.bat build bin\kc.bat start
設定値
具体的な設定値は以下。
quarkus.http.access-log.enabled=true quarkus.http.access-log.log-to-file=false quarkus.http.access-log.rotate=false quarkus.log.category."io.quarkus.http.access-log".level=INFO quarkus.log.category."io.quarkus.http.access-log".use-parent-handlers=false quarkus.log.category."io.quarkus.http.access-log".handlers=access-log-handler quarkus.log.handler.file.access-log-handler.enable=true quarkus.log.handler.file.access-log-handler.path=logs/access.log quarkus.log.handler.file.access-log-handler.format=%s%n quarkus.log.handler.file.access-log-handler.rotation.file-suffix=.yyyy-MM-dd quarkus.log.handler.file.access-log-handler.rotation.rotate-on-boot=false
設定値の解説
アクセスログの設定
まず、一番のポイントはquarkus.http.access-log.log-to-file
にfalse
を指定するところ。
冒頭のシンプルにアクセスログを出そうとした場合はtrue
を指定していたが、この設定を行うとアクセスログ独自のファイル出力処理が動作し、そのあとで設定しているハンドラなどが動作に反映されなかった。
この部分は公式ドキュメントには書いておらず、Quarkusのソースコードを読んでみて分かった。以下の箇所の近辺で分岐している。ここは少し不親切だと思う。
また、HTTPサーバー機能側でのローテートは不要なのでquarkus.http.access-log.rotate
はfalse
にする。
カテゴリとハンドラの関連付け
次に以下のようにしてカテゴリとハンドラを関連付ける。ここでのポイントは、カテゴリにio.quarkus.http.access-log
を指定するところ。アクセスログ側のquarkus.http.access-log.category
の値と合わせる必要がある。
quarkus.log.category."io.quarkus.http.access-log".level=INFO quarkus.log.category."io.quarkus.http.access-log".use-parent-handlers=false quarkus.log.category."io.quarkus.http.access-log".handlers=access-log-handler
ちなみに公式ドキュメントのquarkus.http.access-log.category
の説明に、base-file-name
に何も設定されていない場合は標準ログメカニズムが使用されるとある。最初にそこを読んでbase-file-name
に何も設定しないよう試行錯誤したのだが、base-file-name
は空にできないというエラーが発生し、結局Keycloakを起動できなかった。
ハンドラの定義
最後に以下のようにハンドラを定義する。
quarkus.log.handler.file.access-log-handler.enable=true quarkus.log.handler.file.access-log-handler.path=logs/access.log quarkus.log.handler.file.access-log-handler.format=%s%n quarkus.log.handler.file.access-log-handler.rotation.file-suffix=.yyyy-MM-dd quarkus.log.handler.file.access-log-handler.rotation.rotate-on-boot=false
カテゴリとの関連付けで指定したハンドラaccess-log-handler
に対して設定を行う。
ここで説明しておくのはquarkus.log.handler.file.access-log-handler.format
だが、既にアクセスログとしてフォーマットされているため、ここでは%sだけを指定している。何も設定しないと日付が2重で付与されたりする。なお、アクセスログ側の設定でフォーマットを制御できるため、ここでは特に指定しないのが良いと思う。
また、quarkus.log.handler.file.access-log-handler.rotation.file-suffix
にて任意のサフィックスを指定することができる。
このサフィックスの形式により、ローテートの動作が変わる。今回の例では.yyyy-MM-ddと指定してるので、具体的には.2024-01-26と言った値になる。この例では日次ローテートにはなるが、任意の世代数(例えば90日間分だけログを残す)を設定することはできない。
この辺りはcronなどを使って、古いファイルを削除するなど別の方法を考える必要がある。
所感
ログに限らず全般的な設定だが、WildFlyの頃のXML形式での設定に比べれば分かりやすいと感じた。
そういえば、YAML形式などで書けるのだろうか。
参考
Spring Bootアプリケーションの実行時にJava VMにVM引数を渡す方法
概要
Spring Boot Maven PluginでSpring Bootアプリケーションを起動する際に、Java VMにVM引数を渡す方法を記載する。
動機
Spring Bootを使った開発では、通常EclipseやIntelliJ IDEAなどのIDEを使うことが多い。筆者はEclipseを使うことが多いが、Eclipseは想定しないタイミングで重くなることが多く、急ぎで動作確認したいときなどはコマンドラインでSpring Bootを起動したいことがある。開発環境でのアプリ起動はSpring Boot Maven Pluginを使っている。
そして、職場の開発環境ではフォーワードプロキシがあるネットワークを使うため、外部ネットワークのサーバーと通信したいときはこのプロキシを通過できるよう構成する必要がある。
Spring FrameworkのRestTemplateクラスはVM引数でプロキシを指定できるが、Spring Boot Maven Pluginでアプリを起動するときは、プラグインに引数をバイパスしてもらう必要があったが、なかなか設定方法にたどり着けなかったので書き残すことにした。
実行環境・前提条件
目次
指定方法
公式ドキュメントのチュートリアルに記載されているように、Spring Bootアプリケーションの実行は以下のように行う。
mvn.cmd spring-boot:run
Spring Bootアプリケーションを実行しているJava VMにVM引数を渡すには、Spring Boot Maven Pluginのオプションに指定する。以下の公式ドキュメントに記載があったが、なかなか気が付かなかった。
以下が実際に指定する方法。spring-boot.run.jvmArgumentsを使ってプラグインにVM引数をバイパスしてもらう。 ここではプロキシ設定を例として渡している。
mvn.cmd spring-boot:run -Dspring-boot.run.jvmArguments="-Dhttp.proxyHost=aaa -Dhttp.proxyPort=bbb -Dhttp.proxyUser=ccc -Dhttp.proxyPassword=ddd -Dhttps.proxyHost=aaa -Dhttps.proxyPort=bbb -Dhttps.proxyUser=ccc -Dhttps.proxyPassword=ddd"
なお、以下のようにpom.xmlに記載する方法もある。公式ドキュメントからの引用である。 今回のユーザー名やパスワードが含まれるケースは、コマンドライン引数で指定するほうが望ましいだろう。
<project> <build> <plugins> <plugin> <groupId>org.springframework.boot</groupId> <artifactId>spring-boot-maven-plugin</artifactId> <configuration> <jvmArguments> -Xdebug -Xrunjdwp:transport=dt_socket,server=y,suspend=y,address=5005 </jvmArguments> </configuration> </plugin> </plugins> </build> </project>
Eclipse STSを使う場合
EclipseにSTSプラグインをインストールして使用している場合は、実行プロファイルでVM引数を指定することができる。 spring-boot.run.jvmArgumentsに渡すパラメータをそのまま実行プロファイルに指定すればよい。
参考
Keycloakの管理コンソールでIPアドレスごとのアクセス制御を行う
概要
KeycloakはWildFly上のアプリケーションとして実装されており、自身に対する、IPアドレスベースのアクセス制御などの機能はWildFlyが提供している。
WildFlyのサブシステムであるUndertowの設定を行うことで、アクセス制御を実施できる。
動機
Keycloakの前段にReverse Proxyを配置しているが、WEBの管理コンソールに直接アクセスする場合がある。
このケースでは当然Reverse Proxyでのアクセス制御はできないので、Keycloak本体にてアクセス制御をかける。
また、管理REST APIにも同様にアクセス制御をかけたい。
実行環境・前提条件
- Keycloak 17.0.0
- WildFly 26.0.0
目次
設定概要
WildFlyが提供するCLIで変更する方法や、standalone.xmlなどを直接編集する方法などがあるが、ここではstandalone.xmlを編集する方法を記載する。 ここでは動機欄に書いた通り、「Reverse Proxyの後ろでKeycloakを運用しているケースにて、管理コンソースと管理REST APIへのアクセス制御」を行う設定を想定する。
設定方法
各設定項目についての説明は参考リンク先を参照すること。
Undertowに対して、expression-filterを定義し、それを適用する。
定義は<filters><expression-filter>
で行い、<server><host><filter-ref>
で適用する。
設定例
以下は、Keycloak 17.0.0に付属するstandalone.xmlを抜粋したものに対して、修正を実施した内容である。
<subsystem xmlns="urn:jboss:domain:undertow:12.0" default-server="default-server" default-virtual-host="default-host" default-servlet-container="default" default-security-domain="other" statistics-enabled="${wildfly.undertow.statistics-enabled:${wildfly.statistics-enabled:false}}"> <buffer-cache name="default"/> <server name="default-server"> <http-listener name="default" socket-binding="http" redirect-socket="https" enable-http2="true"/> <https-listener name="https" socket-binding="https" ssl-context="applicationSSC" enable-http2="true"/> <host name="default-host" alias="localhost"> <location name="/" handler="welcome-content"/> <http-invoker http-authentication-factory="application-http-authentication"/> <!-- ★定義したexpression-filterを適用する --> <filter-ref name="kc-admin-reject"/> </host> </server> <servlet-container name="default"> <jsp-config/> <websockets/> </servlet-container> <handlers> <file name="welcome-content" path="${jboss.home.dir}/welcome-content"/> </handlers> <!-- ★expression-filterを定義する --> <filters> <expression-filter name="kc-admin-reject" expression="proxy-peer-address; regex('(^/auth$)|(^/auth/$)|(^/auth/admin)|(^/auth/realms/master)') -> ip-address-control(acl={'xxx.xxx.xxx.xxx/24 127.0.0.1 allow'})"/> </filters> <application-security-domains> <application-security-domain name="other" security-domain="ApplicationDomain"/> </application-security-domains> </subsystem>
設定例の説明
- proxy-peer-address
Reverse Proxyの後段では送信元IPアドレスがReverse Proxyのものになってしまう。一般的にReverse ProxyはX-Forwarded-Forヘッダなどに元々の送信元IPアドレスを設定する。proxy-peer-addressは送信元IPアドレスをX-Forwarded-Forの値で上書きしてくれる。 - regex
アクセス制御を行うパスを限定している。ここではKeycloakの管理コンソールや管理REST APIに関連する、以下のパスに対してアクセス制御を実施する。- /authのみのパス
- /auth/のみのパス
- /auth/adminから始まるパス
- /auth/realms/masterから始まるパス
- ip-access-control
IPアドレスによるアクセス制御を指定できる。ここではxxx.xxx.xxx.xxx/24と、127.0.0.1を許可するように設定している。
参考
pacmanでよく使うコマンド
概要
pacmanを使ってパッケージ管理を行う際のオプションをメモしておく。主に自分用。
動機
pacmanはArch LinuxやMSYS2で使用するが、それほど頻度は高くないために忘れてしまいがち。
いくつものパッケージマネージャを使っているので、オプションを混同して覚えてしまってるときがある。
pacmanのmanは親切なので読めば大体分かるが毎回読んでると時間が足りない。
目次
ユースケース
パッケージを検索する
インストール済みのパッケージを検索する
パッケージが既にインストールしてあるかどうかを見たいときに使用する。
この場合に使用するのは-Q
オペレーション。これに-s
オプションを付与する。
pacman -Qs 検索するパッケージ名
リモートリポジトリのパッケージを検索する
インストールを行いたいがパッケージ名が分からない場合や、リモートリポジトリに存在するのかを調べるときに使用する。
リモートリポジトリの検索は-S
オペレーターを使う。
pacman -Ss 検索するパッケージ名
パッケージをインストールする
パッケージのインストールは-S
オペレーションを使う。
直近で-y
オプションを使ってデータベースを更新しているなら、-y
オプションを省略してもよい。
pacman -Sy パッケージ名
パッケージを削除する
パッケージの削除は-R
オペレーションを使う。
依存するパッケージも合わせて削除するなら、-s
オプションを指定する。
pacman -Rs 削除するパッケージ名
インストール済みのパッケージを更新する
パッケージを最新化したい場合に使う。
-S
オペレーションを使用する。-y
オプションでマスターパッケージデータベースを更新し、パッケージの更新を指す-u
オプションを使う。
-u
オプションは2つつけることができ、その場合はダウングレードを許可する。安定版よりもバージョンが高いテスト版などを使用しているときで、安定版に戻したい場合に使用する。
pacman -Syu
Arch Linuxでは、キーリングが更新されている場合を考慮し、以下のようにキーリングの更新をした上でパッケージを更新するとよい。
pacman -Sy archlinux-keyring && pacman -Su
その他
パッケージキャッシュを削除する
インストールに使われたパッケージファイルは、キャッシュディレクトリに保存されている。
このパッケージファイルがストレージを圧迫するので、たまに消してあげるとよい。
-c
オプションは、1個指定すると使ってないパッケージファイルを、2個指定するとすべてのパッケージファイルを削除する。
pacman -Sc
誰からも参照されていないパッケージを検索する
以下のように実行する。
pacman -Qtd
検索したパッケージを削除したい場合は、以下を実行する1。
pacman -Rns $(pacman -Qtdq)
その他(実行環境依存)
Arch Linuxのキーリングの更新
pacmanの仕組み上、キーリングに登録されたGnuPG鍵の最新化が必要。
pacman -Sy archlinux-keyring
参考
Mavenで実行可能なjarファイルを作成する(CLIアプリケーションを作成する)
概要
JavaでCLIアプリケーションを作りたい。
実行時にclasspathやエントリポイントを指定せずに実行できるようにしたい。
Mavenを使って、ライブラリなどのパッケージ取得し、ビルドを行い、実行可能なjarファイルを作るまでの手順を記載する。
目次
- 概要
- 目次
- 実行環境・前提条件
- OpenJDKのインストール
- Mavenのインストール
- Mavenプロジェクトの作成
- pom.xmlの編集
- maven-assembly-pluginについて
- 参考:テストをスキップする
実行環境・前提条件
OpenJDKのインストール
OpenJDKとして、Eclipse Temurinを使用した。
以下のサイトからLTSのTemurin 17を選択してダウンロードし、インストールを行った。
Adoptium - Open source, prebuilt OpenJDK binaries
取得したインストーラを使って、Eclipse Temurinをインストールする。インストールはインストーラに従って操作すれば簡単にインストールできる。インストーラに従い、Windowsの環境変数に以下を設定する。
- PATH
- JAVA_HOME
Mavenのインストール
以下のサイトからMavenの実行バイナリを取得する。
ダウンロードしたファイルを任意のフォルダに展開する。展開したフォルダの中にあるbinフォルダを、Windowsの環境変数のPATHに登録する。これでコマンドプロンプトからMavenが実行可能になる。
Mavenプロジェクトの作成
Mavenの以下のドキュメントに従って、プロジェクトを作成する。
以下はドキュメントに記載されているコマンドで、これを実行するとプロジェクトのひな形が作成できる。 以後は生成されたpom.xmlを使い、プロジェクトのビルドを設定する。
>mvn archetype:generate \ -DgroupId=test \ -DartifactId=cli-app \ -DarchetypeArtifactId=maven-archetype-quickstart -DarchetypeVersion=1.4 \ -DinteractiveMode=false
groupIdやartifactIdの意味は以下のページに記載されているが、それぞれ任意に決める。
Maven – Guide to Naming Conventions
プロジェクトの生成が成功すれば、以下のコマンドでひな形のアプリケーションが起動する。
>cd cli-app >mvn package >java -cp target\cli-app-1.0-SNAPSHOT.jar test.App Hello World!
pom.xmlの編集
ただ、このままではjarファイル内のMANIFEST.MFにメインクラスが記載されないため、上記のようにメインクラスを指定しなければ実行ができない。それは手間なので、jarファイルを作成するためのMavenプラグイン(maven-jar-plugin)に追加の設定を行う。
pom.xmlを編集し、以下のように<mainClass>
でmainメソッドを持つクラスを指定する。
<build> <plugins> <plugin> <artifactId>maven-jar-plugin</artifactId> <version>3.0.2</version> <configuration> <finalName>cli-app-${project.version}</finalName> <archive> <manifest> <mainClass>test.App</mainClass> </manifest> </archive> </configuration> </plugin> </plugins> </build>
再度、コマンドプロンプトで以下のように実行すれば、メインクラスの指定なしに実行が可能になる。
>mvn clean >mvn package >java -jar target\cli-app-1.0-SNAPSHOT.jar Hello World!
maven-assembly-pluginについて
Mavenには類似のjarファイルを操作するプラグインとしてmaven-assembly-pluginがある。これはメインのビルドターゲットとは別に、jarファイル(またはzipやtarなどのファイル)を生成するために使用する。
参考:テストをスキップする
ビルド時に以下のようにオプションを付与することで、テスト用のコードのコンパイルと実行をスキップすることができる。
>mvn package -Dmaven.test.skip
システム起動時のPostgreSQLの起動をネットワーク有効化まで遅延させる
概要
OSの起動時にて、ネットワークが有効化したあとにPostgreSQLを起動したい。ネットワークが有効になるまでは、PostgreSQLがlistenしようとsocketにbindしても失敗してしまうためである。 systemdを使ってシステムを起動している場合に、PostgreSQLの起動をネットワークが有効になるまで遅延させる方法を記載する。
目次
実行環境・前提条件
- CentOS Stream 8
- NetworkManagerを使っている
- PostgreSQL 12.7
- CentOSのバンドル版ではなく、PostgreSQL公式のリポジトリから取得したパッケージを使う
NetworkManager-wait-online.serviceの有効化
NetworkManagerを使っている場合にネットワークが有効化するまで待つサービスを使用する。 このサービスが有効になっているかは、以下のコマンドで確認する。
# systemctl is-enabled NetworkManager-wait-online.service enabled
無効の場合は、以下で有効化する。
# systemctl enable NetworkManager-wait-online.service
参考リンクによるとnetwork-online.targetと共にNetworkManager-wait-online.serviceを有効化する必要があるとのこと。NetworkManager-wait-online.serviceは他との関連で有効になる可能性があるため、わざわざ指定しないでもよいと考えることできるそうだ。 わかりやすさを優先して、明示的に有効化するような手順とした。
PostgreSQLのユニットファイル編集
PostgreSQLのインストール手順は省略する。 ユニットファイルを変更するため、/etc/systemd/systemにコピーする。
systemdでは、/usr/lib/systemd/systemのユニットファイルよりも、/etc/systemd/systemのユニットファイルが優先されるようになっている(この辺りはsystemdのマニュアルに記載がある)。 また、パッケージマネージャによって/usr/lib/systemd/system/のファイルは書き換えられる可能性があるため、コピーして使用するように推奨されている。(PostgreSQLのユニットファイルのコメントより)
# cp -a /usr/lib/systemd/system/postgresql-12.service /etc/systemd/system/postgresql-12.service
PostgreSQLのユニットファイルは以下の通り、修正する。 network-online.targetのあとに起動するように指定する。
@@ -14,7 +14,7 @@ Description=PostgreSQL 12 database server Documentation=https://www.postgresql.org/docs/12/static/ After=syslog.target -After=network.target +After=network.target network-online.target [Service] Type=notify
参考
CentOS Stream 8にKeycloakをインストールする
本記事の目標
本記事では、CentOS Stream 8にKeycloakをインストールして動作させるまでを扱う。
Keycloak自体の設定は扱わない。
目次
実行環境
以下の実行環境を扱う。
- CentOS Stream 8
- Keycloak 15.0.1
- OpenJDK 11 (11.0.12.0.7-0.el8_4)
- PostgreSQL 12.7
Keycloakの持つ管理情報は、デフォルトで使用されるH2 DatabaseではなくPostgreSQLに保持させる。
システム構成はアプリケーションサーバー、およびデータベースサーバーで、それぞれ別のOS上で動作させる。IPアドレスは以下の通りとする。
- アプリケーションサーバー(192.168.1.2/24)
- データベースサーバー(192.168.1.3/24)
なお、簡略化のためSELinux、firewalldは停止させておく。
データベースサーバーの構築
データベースサーバーにはPostgreSQLを使用する。
PostgreSQL Yum Repository登録
dnfコマンドでPostgreSQLがインストールできるように、DNFにPostgreSQL Yum Repositoryを登録する。
dnf install https://download.postgresql.org/pub/repos/yum/reporpms/EL-8-x86_64/pgdg-redhat-repo-latest.noarch.rpm
PostgreSQLのインストール
CentOS Streamでは、DNFのモジュール機能を使用して複数のバージョンのPostgreSQLを切り替えることができる。
ただし、psqlコマンドを使用したときにno version information available (required by psql)
のようなメッセージが表示されるため(2021/8/12現在)、モジュール機能は使用しない。
dnf module disable postgresql dnf install postgresql12-server
psqlコマンドなどのmanを見れるようにしておく。
以下のように/etc/man_db.confを編集する。
MANDATORY_MANPATH /usr/man
MANDATORY_MANPATH /usr/share/man
MANDATORY_MANPATH /usr/local/share/man
+ MANDATORY_MANPATH /usr/pgsql-12/share/man
#---------------------------------------------------------
# set up PATH to MANPATH mapping
# ie. what man tree holds man pages for what binary directory.
PostgreSQLの初期設定
PostgreSQLの初期データベースを作成する。
データベースのエンコーディングにはUTF8を指定し、ロケールは設定しない。
KeycloakではUnicode文字列が使用可能であるが、データベース側の設定もUTF8になっている必要がある。
https://www.keycloak.org/docs/latest/server_installation/#postgresql-database
export PGSETUP_INITDB_OPTIONS="--encoding=UTF8 --no-locale" postgresql-12-setup initdb
設定ファイルの編集
postgresql.confの編集
ここでは待ち受けるIPアドレスと、ログに関する設定のみを変更している。
設定ファイルは/var/lib/pgsql/12/data/postgresql.confにある。
# - Connection Settings - -#listen_addresses = 'localhost' # what IP address(es) to listen on; +listen_addresses = '192.168.1.3,127.0.0.1' # what IP address(es) to listen on; # comma-separated list of addresses; # defaults to 'localhost'; use '*' for all # (change requires restart) # These are only used if logging_collector is on: -log_directory = 'log' # directory where log files are written, +log_directory = '/var/log/postgresql' # directory where log files are written, # can be absolute or relative to PGDATA -log_filename = 'postgresql-%a.log' # log file name pattern, +log_filename = 'postgresql-%Y%m%d.log' # log file name pattern, # can include strftime() escapes #log_file_mode = 0600 # creation mode for log files, # begin with 0 to use octal notation #debug_print_rewritten = off #debug_print_plan = off #debug_pretty_print = on -#log_checkpoints = off -#log_connections = off -#log_disconnections = off -#log_duration = off +log_checkpoints = on +log_connections = on +log_disconnections = on +log_duration = on #log_error_verbosity = default # terse, default, or verbose messages #log_hostname = off log_line_prefix = '%m [%p] ' # special values: -log_timezone = 'America/New_York' +log_timezone = 'Asia/Tokyo' -timezone = 'America/New_York' +timezone = 'Asia/Tokyo'
pg_hba.confの編集
ここでは、postgresql.confで設定した待ち受けるIPアドレスへの接続許可設定を追加する。
Keycloakから接続するデータベース名と接続に使用するユーザ名は、それぞれkeycloakとしておく。
設定ファイルは/var/lib/pgsql/12/data/pg_hba.confにある。
# IPv4 local connections: host all all 127.0.0.1/32 ident +# IPv4 remote connections: +host keycloak keycloak 192.168.1.0/24 md5 # IPv6 local connections:
ログディレクトリの作成
postgresql.confで設定したログディレクトリを作成する。
CentOSの流儀に合わせてログは/var/log配下にまとめる。
mkdir -p /var/log/postgresql chown postgres:postgres /var/log/postgresql chmod 750 /var/log/postgresql
PostgreSQLの起動
systemctl enable postgresql-12 systemctl start postgresql-12
Keycloakの管理情報用のDB作成
Keycloakの管理情報用のDBとして、以下の表のように設定する。
項目 | 値 |
---|---|
データベース名 | keycloak |
ユーザ名 | keycloak |
パスワード | ※keycloakとしておく |
スキーマ | keycloak |
psqlコマンドで、postgresユーザとしてPostgreSQLにログインし、以下のコマンドでデータベースなどを作成する。
CREATE DATABASE keycloak; CREATE USER keycloak; \password keycloak \c keycloak CREATE SCHEMA keycloak; GRANT ALL PRIVILEGES ON SCHEMA keycloak TO keycloak;
アプリケーションサーバーの構築
OpenJDKのインストール
CentOS Stream 8が提供しているOpenJDKをインストールする。 インストールはDNFを使用し、以下のように実行する。
dnf install java-11-openjdk
インストール後の結果は、以下ように実行してメッセージが表示されればよい。
# java -version openjdk version "11.0.12" 2021-07-20 LTS OpenJDK Runtime Environment 18.9 (build 11.0.12+7-LTS) OpenJDK 64-Bit Server VM 18.9 (build 11.0.12+7-LTS, mixed mode, sharing)
Keycloakの取得
以下のURLからKeycloakを取得する。
KeycloakはWildFly上のアプリケーションとして提供されるため、取得した圧縮したファイルにはWildFlyが同梱されている。
/opt配下にインストールする。
cd /opt wget https://github.com/keycloak/keycloak/releases/download/15.0.1/keycloak-15.0.1.zip tar zxvf keycloak-15.0.1.tar.gz ln -s keycloak-15.0.1 keycloak
PostgreSQLのJDBC Driver設定
Keycloakのドキュメントに従い、PostgreSQLのJDBC Driverをダウンロード、および設定を行う。
Server Installation and Configuration Guide
PostgreSQLのJDBC Driverは以下から取得する。
PostgreSQL JDBC Download
この記事を執筆した時点(2021/8/12)では、最新版がpostgresql-42.2.23.jarとなっていたため、このバージョンに合わせて設定を記載する。
cd /opt/keycloak/modules/system/layers/keycloak/org/ mkdir -p postgresql/main wget https://jdbc.postgresql.org/download/postgresql-42.2.23.jar
設定ファイルはmodule.xmlという名称で作成し、内容は以下の通り。
<?xml version="1.0" ?> <module xmlns="urn:jboss:module:1.3" name="org.postgresql"> <resources> <resource-root path="postgresql-42.2.23.jar"/> </resources> <dependencies> <module name="javax.api"/> <module name="javax.transaction.api"/> </dependencies> </module>
最終的に、以下のようにファイルが格納されていればよい。
/opt/keycloak/modules/system/layers/keycloak/org/postgresql/main/postgresql-42.2.23.jar /opt/keycloak/modules/system/layers/keycloak/org/postgresql/main/module.xml
設定ファイルの編集
standalone.xmlの編集
Keycloakでは以下の冗長構成を選択することが可能である。
詳細は下記を参照。
Server Installation and Configuration Guide
今回はスタンドアローン・モードを使用する。
スタンドアローン・モードの場合、設定ファイルはstandalone.xmlを使用することになり、standalone/configuration/配下に格納されている。
設定する内容としては、ログ出力設定と管理情報の保存先(PostgreSQL)設定となる。
@@ -114,7 +114,6 @@ <root-logger> <level name="INFO"/> <handlers> <!-- デーモンとして動作させるため、コンソールへのログ出力は抑止。 --> - <handler name="CONSOLE"/> <handler name="FILE"/> </handlers> </root-logger> @@ -137,18 +136,24 @@ <password>sa</password> </security> </datasource> <!-- 記載してあるKeycloakDSの記載を削除する --> - <datasource jndi-name="java:jboss/datasources/KeycloakDS" pool-name="KeycloakDS" enabled="true" use-java-context="true" statistics-enabled="${wildfly.datasources.statistics-enabled:${wildfly.statistics-enabled:false}}"> - <connection-url>jdbc:h2:${jboss.server.data.dir}/keycloak;AUTO_SERVER=TRUE</connection-url> - <driver>h2</driver> - <security> - <user-name>sa</user-name> - <password>sa</password> - </security> - </datasource> <!-- KeycloakDSをPostgreSQLに接続する設定に変更したものを追記。 --> <!-- ユーザ名やパスワードはPostgreSQLで設定したものを使用する --> + <datasource jndi-name="java:jboss/datasources/KeycloakDS" pool-name="KeycloakDS" enabled="true" use-java-context="true"> + <connection-url>jdbc:postgresql://192.168.1.3/keycloak</connection-url> + <driver>postgresql</driver> + <pool> + <max-pool-size>20</max-pool-size> + </pool> + <security> + <user-name>keycloak</user-name> + <password>keycloak</password> + </security> + </datasource> <drivers> <driver name="h2" module="com.h2database.h2"> <xa-datasource-class>org.h2.jdbcx.JdbcDataSource</xa-datasource-class> </driver> <!-- PostgreSQL JDBC Driverの設定を追加 --> + <driver name="postgresql" module="org.postgresql"> + <xa-datasource-class>org.postgresql.xa.PGXADataSource</xa-datasource-class> + </driver> </drivers> </datasources> </subsystem> @@ -471,6 +476,7 @@ <property name="initializeEmpty" value="true"/> <property name="migrationStrategy" value="update"/> <property name="migrationExport" value="${jboss.home.dir}/keycloak-database-update.sql"/> <!-- スキーマを指定。PostgreSQLで設定したものを使用する --> + <property name="schema" value="keycloak"/> </properties> </provider> </spi>
keycloak.confの編集
docs/contrib/scripts/systemdに、WildFlyをsystemd経由で起動するためのスクリプト、設定ファイルのひな形が格納されている。
また、簡単な手順がREADMEに記載されているため、このファイルに従ってKeycloak向けのsystemdの設定を行う。
mkdir /etc/keycloak cp -a /opt/keycloak/docs/contrib/scripts/systemd/wildfly.conf /etc/keycloak/keycloak.conf
keycloak.confに記載する内容は以下の通り。
WILDFLY_HOMEとJAVA_OPTSを追記している。
# Home directory WILDFLY_HOME=/opt/keycloak # The configuration you want to run WILDFLY_CONFIG=standalone.xml # The mode you want to run WILDFLY_MODE=standalone # The address to bind to WILDFLY_BIND=192.168.1.3 # JAVA_OPTS JAVA_OPTS="-Xms512m -Xmx1024m -XX:MetaspaceSize=96M -XX:MaxMetaspaceSize=256m -Djava.net.preferIPv4Stack=true -Djboss.modules.system.pkgs=org.jboss.byteman -Djava.awt.headless=true -Djboss.server.log.dir=/var/log/keycloak"
WILDFLY_HOMEはKeycloakをインストールしたディレクトリを指定するが、デフォルトでは/opt/wildfly
を参照するようになっている。
JAVA_OPTSはWildFlyのコンフィグファイルであるbin/standalone.conf
で設定されるが、編集するファイルを少なくするため、本ファイルに追記している。設定内容はbin/standalone.conf
に記載されているものをコピーしたのと、ログディレクトリを指定するため、-Djboss.server.log.dir=/var/log/keycloak
を追記している。
起動スクリプト(launch.sh)の編集
keycloak.confと同様に、Keycloakが用意している起動スクリプトを利用する。
cp -a /opt/keycloak/docs/contrib/scripts/systemd/launch.sh /opt/keycloak/bin/ chmod +x /opt/keycloak/bin/launch.sh
実行ユーザの作成
Keycloakをデーモンとして実行するときのOSのユーザを作成する。
groupadd -r keycloak useradd -r -g keycloak -d /opt/keycloak -s /sbin/nologin keycloak
ログディレクトリの作成
JAVA_OPTSで設定したログディレクトリを作成する。
CentOSの流儀に合わせてログは/var/log
配下にまとめる。
mkdir -p /var/log/keycloak chown -R keycloak:keycloak /var/log/keycloak
管理ユーザの作成
Keycloak上で操作を行うための管理ユーザを作成する。
以下のスクリプトで作成が可能で、ユーザ名、パスワードは任意の値が設定できる。
./add-user-keycloak.sh -r master -u admin -p password
systemdのserviceファイル作成
keycloak.confと同様に、Keycloakが用意しているserviceファイルのひな形をベースとして使用する。
[Unit] Description=The Keycloak Application Server After=syslog.target network.target [Service] Type=idle Environment=LAUNCH_JBOSS_IN_BACKGROUND=1 EnvironmentFile=-/etc/keycloak/keycloak.conf User=keycloak Group=keycloak LimitNOFILE=102642 PermissionsStartOnly=true ExecStartPre=/usr/bin/mkdir -p /var/run/keycloak ExecStartPre=/usr/bin/chown -R keycloak:keycloak /var/run/keycloak PIDFile=/var/run/keycloak/keycloak.pid ExecStart=/opt/keycloak/bin/launch.sh $WILDFLY_MODE $WILDFLY_CONFIG $WILDFLY_BIND StandardOutput=null ExecStopPost=/usr/bin/rm -rf /var/run/keycloak [Install] WantedBy=multi-user.target
Keycloakが提供するものからの変更点で、注意する部分は以下の箇所。
CentOS Stream 8では/var/run配下はシステム停止時に削除されるため、サービス起動時にディレクトリを作成するように設定している。
PermissionsStartOnly=true ExecStartPre=/usr/bin/mkdir -p /var/run/keycloak ExecStartPre=/usr/bin/chown -R keycloak:keycloak /var/run/keycloak ExecStopPost=/usr/bin/rm -rf /var/run/keycloak
Keycloakの起動
chown -R keycloak:keycloak /opt/keycloak systemctl daemon-reload systemctl enable keycloak.service systemctl start keycloak.service
Keycloakの管理画面へのアクセス
以下のURLへアクセスするとKeycloakの管理画面が表示される。
ログインに使用するのは、管理ユーザの作成で作成したユーザである。
https://192.168.1.3:8443/auth