テストや検証目的でAWSにYellowfinを構築することがよくあります。いろいろ試した結果、現時点で最適だと思える構築手順を公開します。
AWSコンソールでの作業
まずはAWSコンソールでEC2のインスタンスを立ち上げます。
EC2インスタンスの作成
ここでは事前に定義しておいたセキュリティグループを適用して、必要なポートを開けます。
Elastic IPアドレスの割り当て
取得したIPアドレスを先ほど作成したインスタンスに関連付けます。
どのインスタンスに紐付けたIPかわかりやすくなるように、タグを設定しておきます。
DNSの設定
割り当てたElastic IPを使ってドメインも設定しますが、ここでは割愛。
環境に合わせて適宜設定してください。
SSHでの作業
ここから先はSSHで作業を進めます。
SSHで接続
以下のコマンドで接続します。
$ ssh -i <キーペアのpemファイル> ec2-user@<IPアドレスやドメイン名>
SELinuxとfirewalldの状態確認
Amazon LinuxはSELinuxとfirewalldがデフォルトで無効になっています。
一応、確認だけしておきます。
[ec2-user@xxxxxx ~]$ getenforce
Disabled
[ec2-user@xxxxxx ~]$ systemctl status firewalld.service
Unit firewalld.service could not be found.
rootの有効化
デフォルトではrootパスワードが設定されていないので、以下で有効化します。
sudo passwd root
タイムゾーン設定
タイムゾーンをAsia/Tokyoに。
sudo timedatectl set-timezone Asia/Tokyo
ロケール設定
ロケールを日本語に。
sudo localectl set-locale LANG=ja_JP.UTF-8
日本語フォントのインストール
日本語フォントをインストールします。
(Yellowfin 9以降はOSフォントを使用しないため、この手順は不要になります)
sudo yum install -y ibus-kkc
sudo yum install google-noto-sans-japanese-fonts ipa-gothic-fonts ipa-mincho-fonts ipa-pgothic-fonts ipa-pmincho-fonts vlgothic-fonts vlgothic-p-fonts
ホスト名設定
任意のホスト名を設定します。
sudo hostnamectl set-hostname <ホスト名>
dstatのインストール
サーバーリソース監視ツールのdstatをインストールします。
sudo yum install dstat
PostgreSQLのインストール
リポジトリからインストール
Amazon Linux 2の標準のPostgreSQLはバージョンが古いので、現時点で最新の12を使うように小細工します。
まず、リポジトリパッケージをダウンロード。
wget https://download.postgresql.org/pub/repos/yum/10/redhat/rhel-7-x86_64/pgdg-redhat-repo-latest.noarch.rpm
ダウンロードしたリポジトリパッケージをインストール。
sudo rpm -Uvh --nodeps pgdg-redhat-repo-latest.noarch.rpm
現状では依存ライブラリのチェックでエラーになります。
回避のためにリポジトリを直接修正してしまいます。
sudo sed --in-place -e "s/\$releasever/7/g" /etc/yum.repos.d/pgdg-redhat-all.repo
そしてPostgreSQL 12をインストールします。
sudo yum install -y postgresql12-server
初期設定
文字コードのオプションを指定して初期化コマンドを実行。
PGSETUP_INITDB_OPTIONS='--encoding=UTF-8 --locale=C' sudo /usr/pgsql-12/bin/postgresql-12-setup initdb
サービスに登録。
sudo systemctl enable postgresql-12
サービスを起動。
sudo systemctl start postgresql-12
postgresユーザーのパスワードを設定。
sudo passwd postgres
postgresユーザーに切り替え。
以降の作業はpostgresユーザーで行います。
su - postgres
ロールのパスワードを変更します。
psql -c "alter role postgres with password '<postgresユーザーのパスワード>'" ;
パスワード(暗号化)認証で接続するようにpg_hba.confを編集します。
vi /var/lib/pgsql/12/data/pg_hba.conf
# TYPE DATABASE USER ADDRESS METHOD
# "local" is for Unix domain socket connections only
#local all all peer
local all all md5
# IPv4 local connections:
#host all all 127.0.0.1/32 ident
host all all 0.0.0.0/0 md5
# IPv6 local connections:
#host all all ::1/128 ident
host all all ::1/128 md5
# Allow replication connections from localhost, by a user with the
# replication privilege.
#local replication postgres peer
#host replication postgres 127.0.0.1/32 ident
#host replication postgres ::1/128 ident
PostgreSQLの簡易チューニング
PGTuneを使って適切な設定値を算出します。
PostgreSQLのバージョンは12、OSはLinux、タイプはWebアプリケーション、メモリは1GB、ストレージはSSDを指定します。
PostgreSQLはpostgresql.confを編集してメモリなどの設定を行っていましたが、バージョン9.4からALTER SYSTEMコマンドで設定できるようになりました。
コマンドの方が楽なのでALTER SYSTEMコマンドから設定します。
ALTER SYSTEMをコピーします。
psqlを起動。
psql
先ほどのALTER SYSTEMを実行します。
ALTER SYSTEM SET
max_connections = '200';
ALTER SYSTEM SET
shared_buffers = '256MB';
ALTER SYSTEM SET
effective_cache_size = '768MB';
ALTER SYSTEM SET
maintenance_work_mem = '64MB';
ALTER SYSTEM SET
checkpoint_completion_target = '0.7';
ALTER SYSTEM SET
wal_buffers = '7864kB';
ALTER SYSTEM SET
default_statistics_target = '100';
ALTER SYSTEM SET
random_page_cost = '1.1';
ALTER SYSTEM SET
effective_io_concurrency = '200';
ALTER SYSTEM SET
work_mem = '655kB';
ALTER SYSTEM SET
min_wal_size = '1GB';
ALTER SYSTEM SET
max_wal_size = '4GB';
PostgreSQLはデフォルトではlocalhostからしか待ち受けをしていません。
外部からの接続も待ち受けるようにpsqlに続けて下記のコマンドを実行します。
ALTER SYSTEM SET
listen_addresses = '*';
psqlを終了し、postgresユーザーを抜けてec2-userに戻り、PostgreSQLを再起動します。
sudo systemctl restart postgresql-12
httpdのインストール
今回の構成ではTomcatに直接アクセスするのではなく、Apacheを中継する形にします。
SSL証明書の設定・更新がApacheの方が楽にできるからです。
リポジトリからインストール
sudo yum install httpd mod_ssl
httpd.confの編集
sudo vi /etc/httpd/conf/httpd.conf
以下のようにコメントアウトしポート80(httpのデフォルトポート)を無効にします。
#Listhen 80
proxy-ajp.confの作成
httpdがYellowfinのTomcatと連携するための設定を行います。
proxy-ajp.confは存在しないので新規作成します。
sudo vi /etc/httpd/conf.d/proxy-ajp.conf
SECRET_KEYはAJP Connectorに接続するためのパスワードを指定します。
後述のserver.xmlの設定と合わせる必要があります。
ProxyRequests Off
ProxyPass / ajp://localhost:8009/ secret=SECRET_KEY timeout=1860
ProxyPassReverse / ajp://localhost:8009/ secret=SECRET_KEY
SSLの設定
/etc/httpd/crtに証明書ファイルを配置し、ssl.confを編集します。
今回は証明書、認証キー、中間証明書を使用する例です。
sudo vi /etc/httpd/conf.d/ssl.conf
SSLCertificateFile /etc/httpd/crt/ssl_certificate.crt
SSLCertificateKeyFile /etc/httpd/crt/xxxxxxxxxx.key
SSLCACertificateFile /etc/httpd/crt/IntermediateCA.crt
Javaのインストール
今回はOpenJDKディストリビューションのAmazon Corretto 11をインストールします。
sudo yum install java-11-amazon-corretto
Yellowfinのインストール
インストーラの実行
事前に入手したインストーラを使用して、Yellowfinをインストールします。
sudo java -jar yellowfin-x.x.x-xxxxxxxx-full.jar
インストール先ディレクトリは**/usr/local/yellowfin**にします。
その他、インストール手順の詳細はサポートサイトの記事を参照してください。
インストーラが終了したら、ファイルを展開するため一旦Yellowfinを起動し、起動後に再び停止します。
sudo /usr/local/yellowfin/appserver/bin/startup.sh
sudo /usr/local/yellowfin/appserver/bin/shutdown.sh
Yellowfinのサーバー設定変更
TomcatのNative Libraryのインストール
Tomcat Native LibraryをインストールしなくてもYellowfinは動作しますので不要な方は"依存ライブラリのインストール"と”Tomcat Native Libraryのビルド”はスキップしてください。
詳細は、Apache Tomcat Native Library を参照して下さい。
Yellowfinを起動すると標準出力に下記のようなメッセージが表示されます。
ss-May-yyyy hh:mi:ss.000 情報 [main] org.apache.catalina.core.AprLifecycleListener.lifecycleEvent 商用環境に最適な性能を発揮する APR ベースの Tomcat ネイティブライブラリが java.library.path [/Users/nishikenichirou/Library/Java/Extensions:/Library/Java/Extensions:/Network/Library/Java/Extensions:/System/Library/Java/Extensions:/usr/lib/java:.] に存在しません。
これはTomcat Native Libraryがインストールされていないために出力されます。
Native LibraryはTomcatのhttpやSSL機能を強化、拡張するライブラリです。
詳細は、Apache Tomcat Native Library を参照して下さい。
今回はTomcatのWebサーバー機能は使用しないので直接は関係ありませんが、毎回起動時のログに出力されて気持ちが悪いのでNative Libraryをインストールします。
インストールすることでHTTP/2などが使用できるようになります。
設定の詳細は、Apache Tomcat 9 Configuration Reference を参照して下さい。
依存ライブラリのインストール
Tomcat Native Libraryは環境毎にソースをコンパイルしてインストールする必要があります。
コンパイルに必要なツールとライブラリをインストールします。
sudo yum install gcc openssl apr-devel openssl-devel
Tomcat Native Libraryのビルド
Tomcat Native Libraryのソースは、"/usr/local/yellowfin/appserver/bin/tomcat-native.tar.gz" に格納されています。
上記のファイルを解凍し、ビルド・インストールを行います。
# cd /usr/local/yellowfin/appserver/bin
# tar zxvf tomcat-native.tar.gz
# cd ./tomcat-native-xx.xx.xx-src/native/
# ./configure --with-java-home=/usr/lib/jvm/java-11-amazon-corretto.x86_64 #JDKのインストールディレクトリ \
--prefix=/usr/local/yellowfin/appserver #Tomcatのインストールディレクトリ
# make && make install
catalina.shの編集
sudo vi /usr/local/yellowfin/appserver/bin/catalina.sh
JAVA_HOME変数には自動的にインストール時のシステムデフォルトのJavaのパスが指定されています。
Javaをバージョンアップする度にシステムデフォルトのJavaのパスは変更されるため、その度にJAVA_HOMEの指定も変更する必要があります。
非常に面倒臭いのでシステムデフォルトのJavaのパスを探して自動的にセットするように小細工をします。
以下を既存の"JAVA_HOME=xxxxxx"の行と置き換えます。
pathtojava=$(readlink -e $(which java))
JAVA_HOME="${pathtojava%/*/*}"
最近のほとんどのOSはIPv4とIPv6の両方が使えますがIPv6を優先で使用します。
ネットワークの一部でIPv6が使えない場合は途中で迷子になって通信が遅くなったり、不安定になることがあります。
今回は通信をIPv4に限定します。
以下を適切な位置に追記します。
JAVA_OPTS="$JAVA_OPTS -Djava.net.preferIPv4Stack=true"
setenv.shの作成
Tomcatにはデフォルトでは有効になっていない機能があります。
一部の機能を有効にします。
setenv.shは存在しないので新規作成します。
sudo vi /usr/local/yellowfin/appserver/bin/setenv.sh
Tomcatが停止しない場合に強制停止できる機能を有効にします。
#!/bin/sh
CATALINA_PID=/var/run/catalina.pid
下記のようにforceオプションをつけることで強制的にTomcatを停止できます。
shutdown.sh -force
Tomcat Native Libraryの参照PATHを有効にします。
※Tomcat Native Libraryをインストールしていない場合はこの設定は不要です。
LD_LIBRARY_PATH=$LD_LIBRARY_PATH:$CATALINA_HOME/lib
export LD_LIBRARY_PATH
server.xmlの編集
sudo vi /usr/local/yellowfin/appserver/conf/server.xml
httpd(Apache)と連携するためのAJPプロトコルを有効にします。
各種パラメータも指定します。
以下を適切な位置に追記します。
TOMCAT_IP_ADDRESSには、指定したポート(下記の例であれば8009)でリッスンするために使用するアドレスを記述します。
今回は接続するWebサーバーが同一マシンで稼働しているので、TOMCAT_IP_ADDRESSに"127.0.0.1"を指定します。
別サーバーから参照される場合は、Yellowfinサーバーに割り当てられたパブリックまたはプライベートのIPアドレスを指定します。
SECRET_KEYはAJP Connectorに接続するためのパスワードを指定します。
前述のproxy-ajp.confの設定と合わせる必要があります。
<Connector port="8009" protocol="AJP/1.3" redirectPort="8443"
maxThreads="500" minSpareThreads="25"
enableLookups="false" acceptCount="100"
connectionTimeout="20000"
URIEncoding="UTF-8"
maxPostSize="10485760" maxParameterCount="50000"
address="TOMCAT_IP_ADDRESS"
secretRequired="true" secret="SECRET_KEY"
/>
8080ポートのhttpを無効にします。
下記のようにコメントアウトします。
<!--
<Connector port="8080" protocol="HTTP/1.1" maxHttpHeaderSize="8192"
maxThreads="150" minSpareThreads="25"
enableLookups="false" redirectPort="8443" acceptCount="100"
connectionTimeout="20000" disableUploadTimeout="true"
URIEncoding="UTF-8" compression="on" compressionMinSize="512"
noCompressionUserAgents="gozilla, traviata"
compressibleMimeType="text/html,application/x-javascript,text/css,application/javascript,text/javascript,text/plain,text/xml,application/json,application/vnd.ms-fontobject,application/x-font-opentype,application/x-font-truetype,application/x-font-ttf,application/xml,font/eot,font/opentype,font/otf,image/svg+xml,image/vnd.microsoft.icon,image/svg,text/comma-separated-values,application/csv,application/vnd.yellowfin.api-v1+json"
useSendfile="false" />
-->
log4j.propertiesの編集
sudo vi /usr/local/yellowfin/appserver/webapps/ROOT/WEB-INF/log4j.properties
コンテンツのクエリSQLをログに残すようにします。
以下を追記します。
# Report execution Log
log4j.appender.reportlog=org.apache.log4j.RollingFileAppender
log4j.appender.reportlog.File=${catalina.home}/logs/report_exec.log
log4j.appender.reportlog.MaxFileSize=1024KB
log4j.appender.reportlog.MaxBackupIndex=9
log4j.appender.reportlog.layout=org.apache.log4j.PatternLayout
log4j.appender.reportlog.layout.ConversionPattern=%d{yyyy-MM-dd HH:mm:ss.SSS} (%M) - %m%n
log4j.category.com.hof.mi.process.MIReportGeneratorProcess=DEBUG,reportlog
log4j.category.com.hof.mi.util.background.QueueItem=DEBUG,reportlog
log4j.category.com.hof.adapter.JDBCEventCreation=DEBUG,reportlog
# set additivity to false so it doesn't also log to standard log files
log4j.additivity.com.hof.mi.process.MIReportGeneratorProcess=false
log4j.additivity.com.hof.mi.util.background.QueueItem=false
log4j.additivity.com.hof.adapter.JDBCEventCreation=false
web.xmlの編集
sudo vi /usr/local/yellowfin/appserver/webapps/ROOT/WEB-INF/web.xml
リポジトリDBとの接続のタイムアウトを設定して、時間のかかるコンテンツも表示できるようにします。
以下をInitConnectionPoolのセクション内に追記します。
<init-param>
<param-name>JDBCTimeout</param-name>
<param-value>1800</param-value>
</init-param>
カーネルのチューニング
yellowfin.confの作成
sudo vi /etc/sysctl.d/yellowfin.conf
TCPの受信及び送信のソケットの上限を増やします。
net.core.wmem_max=10485760
net.core.rmem_max=10485760
Yellowfinのサービス登録
yellowfin.serviceの作成
sudo vi /etc/systemd/system/yellowfin.service
[Unit]
Description=Yellowfin
After=syslog.target network.target postgresql-12.service
#After=network.target
[Service]
Type=forking
#User=yellowfin
#Group=yellowfin
ExecStart=/usr/local/yellowfin/appserver/bin/startup.sh
ExecStop=/usr/local/yellowfin/appserver/bin/shutdown.sh
WorkingDirectory=/usr/local/yellowfin
#RemainAfterExit=yes
Restart=on-failure
[Install]
WantedBy=multi-user.target
Alias=yellowfin.service
yellowfin.service内のファイルディスクリプタ数の上限を設定します。
sudo mkdir /etc/systemd/system/yellowfin.service.d
sudo vi /etc/systemd/system/yellowfin.service.d/limits.conf
[Service]
# Max open files
LimitNOFILE=65536
# Max processes
LimitNPROC=65536
Yellowfinのサービス起動
sudo systemctl start yellowfin
Yellowfinの接続確認
httpdをここで再起動しておきます。
sudo systemctl restart httpd
その後にインストールしたYellowfinのURLにブラウザでアクセスし、正しく表示されればOKです。
httpdとYellowfinのサービスの自動起動
既に自動起動設定がされていることもありますが、念のために自動起動を有効にします。
sudo systemctl enable httpd
sudo systemctl enable yellowfin
OSの再起動
カーネルパラメータの変更やサービスの自動起動の設定をしたので、OSを再起動し正しくOS及びYellowfinが起動できるか確認します。
Yellowfinの初期設定
サポートサイトの記事に従って初期設定を行ってください。