- 投稿日:2020-08-04T21:45:22+09:00
JenkinsとKubernetesでCIパイプラインを構築
JenkinsとKubernetesを連携させてCIパイプラインを構築する時に、一番悩むの点は、いろいろな方法があるために、何を選択して良いか解らない。そして、実際に実装を進めると、様々な問題が発覚して、時間がかかってしまうことがある。
Jenkinsのプラグインで、Dockerに関するものだけでも約20種類、Kubernetesの関係するもので 約17種類もある。しかも、これらが問題なく動作するという保証も無い。筆者が経験したケースでは、資料が作られた時期から時間が経過すると共にプラグインが更新され、新たな問題が生じてしまい、動作しなくなっているなどがあった。そして、ドキュメントは、Jenkinsに詳しいエンジニア向けに書かれているために、普段触り慣れないJenkins初心者には難解な内容となっていることもある。
そして、Kubernetes上でJenkinsを動作させる場合にも問題が多い。最近のKubernetesのバージョンではコンテナランタイム環境としてContainerdが使用されDockerデーモンが導入されていない。そのため、dockerコマンドを使ったビルドをKubenetesクラスタで、コンテナを簡単にビルドすることができない。DinDやKanikoとなどの環境が必要となる。
そこで、今回は、Jenkinsで、Kubernetesにデプロイするビルドパイプラインを構築するための最短策として試してみた。
構築方針
JenkinsのCI環境を簡単かつ迅速に使用可能な状態とするために、以下の方針に基づいて構築することにした。
- Jenkinsは最新バージョンを使用して、脆弱性リスクを最小化する。
- プラグインの使用は最小に抑え、プラグインの障害に遭遇する可能性を低くする
- コンテナのビルド環境は、有償サポートが受けられる Docker Enterprise に置き換えが可能となる構成とする。
上記の理由から、Kubernetes上でJenkinsを動かさず、仮想サーバー上でJenkinsサーバー構築する。
システム構成
Jenkinsはマスターと、Buildエージェント2台で構築する。
クラウドを利用しないエコな環境として、VagrantとAnsibleで環境を構築するコードを書いた。https://github.com/takara9/vagrant-jenkins
この環境の起動方法は、このリポジトリのREADME.mdの書いておいたので、クローンしてvagrant upすれば、3台のサーバーが環境が整った形で起動するので、あとは、Jenkinsのユーザー画面からプラグインを追加して、Git,Docker,Kubernetesクラスタの認証情報などを設定することで、実際に連携した操作が可能である。ビルドパイプライン
Jenkinsパイプラインのリファレンスは、https://www.jenkins.io/doc/book/pipeline/ にあるので、パイプラインの説明は、ざっくり見ておくと良い。そして、ここで利用するビルドパイプラインのサンプルコードを GitHub https://github.com/takara9/jenkins-play-1 に置いてあるでの、このコードで動作を説明する。
プラグインを追加インストールは実質的に無しである。Blue Ocean は見やすいフロー図とログを表示してくれるので、メインストリームで使うことはないが、入れておく。このJenkinsパイプラインは、4つのステージからなる。
- GiHubからソースコードのクローン
- コンテナイメージのビルド
- コンテナレジストリへプッシュ
- K8sクラスタへのデプロイ
この流れを順番に見ていく。
最初のステージは、GitHubからクローンする。この記述に関する詳細はJenkinsのデフォルトで導入される Gitプラグイン (https://www.jenkins.io/doc/pipeline/steps/git/) のドキュメントを参照すれば、認証が必要なケースでの書き方がわかる。
stages { stage('GiHubからソースコードのクローン') { steps { git 'https://github.com/takara9/jenkins-play-1' } }2番目のステージは、コンテナのビルドステージを見ていく。この中で
docker.build
に関する記述は、Docker Pipelineプラグイン (https://docs.cloudbees.com/docs/admin-resources/latest/plugins/docker-workflow#docker-workflow-sect-build) によるものだ。このリンクには、docker.
で始まるDockerコマンドに関する解説があるので、参照すると良い。stage('コンテナイメージのビルド') { steps { script { dockerImage = docker.build registry + ":$BUILD_NUMBER" } } }3番目のステージは、DockerHub レジストリへ、イメージを登録する部分である。 そこで、DockerHubのAPIのURLアドレスと、認証情報を指定する。認証情報には、DockerHubのユーザー名とパスワードが登録してあり、そのキーとなるのが、"dockerhub"である。これは事前に、「Jenkinsの管理」->「Manage Credential」から登録しておく。dockerImageは前段のステージから引き継がれるように、environmentの中で初期化しておかなければならない。
stage('コンテナレジストリへプッシュ') { steps { script { docker.withRegistry("https://index.docker.io/v1/","dockerhub") { dockerImage.push() } } } }最終ステップは、Kubenetesへのデプロイである。ここでは、kubernetes-cdを使う予定であったが、このプラグイン jackson2-api-plugin が必要とするモジュール のバージョンアップによって動作しない状態になっていた。これはJENKINS-62995 Version 2.11.1 breaking kubernetes deployment somehowに挙げられているが、執筆本日(8月4日現在)Open状態である。 この修正をまっていられないので、Jenkinsのサーバーとビルドエージェントに、kubectlコマンドをインストールして、Jenkinsの認証情報にkubeconfigのファイルを登録して、シェルで実行することにした。
stage('K8sクラスタへのデプロイ') { steps { script { sh 'kubectl cluster-info --kubeconfig $KUBECONFIG' sh 'sed s/__BUILDNUMBER__/$BUILD_NUMBER/ myweb.yaml > deploy_myweb.yaml' sh 'kubectl apply -f deploy_myweb.yaml --kubeconfig $KUBECONFIG' //kubernetesDeploy(configs: "myweb.yaml", kubeconfigId: "mykubeconfig") } } }この中でJenkins組み込みの環境変数 $BUILD_NUMBER を使っている。この環境変数の説明や他の種類については、このURL( https://wiki.jenkins.io/display/JENKINS/Building+a+software+project) を参照すると良い。また、$KUBECONFIGはJenkinsの認証情報管理から登録したkubeconfigのファイルである。
以下に、全体のJenkinsfileを掲示しておく。
pipeline { // 前提条件 Jenkinsサーバーにdocker, kubectl コマンドが導入されていること // environment { registry = "docker.io/maho/myweb" dockerImage = "" KUBECONFIG = credentials('kubeconfig') } agent any stages { stage('GiHubからソースコードのクローン') { steps { git 'https://github.com/takara9/jenkins-play-1' } } stage('コンテナイメージのビルド') { steps { script { dockerImage = docker.build registry + ":$BUILD_NUMBER" } } } stage('コンテナレジストリへプッシュ') { steps { script { docker.withRegistry("https://index.docker.io/v1/","dockerhub") { dockerImage.push() } } } } stage('K8sクラスタへのデプロイ') { steps { script { //sh 'echo $KUBECONFIG' sh 'kubectl cluster-info --kubeconfig $KUBECONFIG' sh 'sed s/__BUILDNUMBER__/$BUILD_NUMBER/ myweb.yaml > deploy_myweb.yaml' sh 'kubectl apply -f deploy_myweb.yaml --kubeconfig $KUBECONFIG' //kubernetesDeploy(configs: "myweb.yaml", kubeconfigId: "mykubeconfig") } } } } }動作確認
ジョブ jenkins-play-1を選択して、「ビルド実行」をクリックすると一連のパイプラインが実行される。スクリーンショットを見てわかる通り、GitHubのクローンから、Kubernetesのデプロイまで成功した。
新規ジョブの作成
順番が前後するが、新規ジョブの登録について、書き残しておく。
「新規ジョブ作成」から次の画面に遷移して、パイプラインを選択して、OKボタンをクリック。
プロジェクトの高度な設定で、SCMの項目でGitを選択、URLをいれる。
Gitリポジトリの更新でビルド開始
今回のJenkinsはオンプレミス上に構築しているので、GitHubのWebhookを受けることができない。そこで、5分間隔でGitHubの更新をポーリングする。そして、変更が発見されたら、ビルドを開始すると設定にする。それにはジョブのリストから選択して、設定の中のビルドトリガーに以下のような設定を施す。これで、少し間をおくことになるが、git push 後に、自動的にビルドが開始される。
コンテナによる実行
ビルドステップを、Dockerコンテナ上で動作させることができる。 「新規ジョブ作成」->「パイプライン」でスクリプトを選択して、次のように記述する。この例では、shは agentで指定されたコンテナで動作することになる。
pipeline { agent { docker { image 'node:14-alpine' } } stages { stage('Test') { steps { sh 'node --version' } } } }ここに挙げた例以外にも、ステップ単位にコンテナを変更する方法など、解説があるので、このURL (https://www.jenkins.io/doc/book/pipeline/docker/) を参照すると良い。
まとめ
Jenkinsのクラスタ上で、追加のプラグインをほとんど使わずに、また、バグを避けながら、ソースコードからコンテナのビルド、Kubernetesクラスタへのデプロイまでを実現することができた。
Jenkinsは優れたツールで小規模から大規模なソフトウェアのビルドに適用することができるので、広範囲なプロジェクトにも適用できると思う。このJenkinsは前進のHudsonから数えて10年が経過したツールで、プラグインが数多く開発されてきた。そのためか、情報が溢れて、どこから手を付けて良いかわからない状態が感じられる。
今回は基本に立ち返り、拡張を考えた簡単な構成で検証した。しかし、これからJenkinsは、仮想サーバー上で動かすべきか、それとも、Kubernetes上でコンテナとして動かすべきか選択を考えなければならない。 Jenkinsはソフトウェア製品開発にとって、基幹業務システム的な無くてはならない存在になっており、開発現場では延々とジョブを実行して、レポートを生成し続けている。そのようなシステムをKubernetes/ OpenShift で動かすメリットについて良く考えなければならない。 Kubernetes / OpneShift を利用することで、運用管理面と可用性で格段に改善できる。
一方で、Tekton やArgoなど、最初からコンテナで動かすことを前提に設計された新しいアーキテクチャのCIツールも登場してきているが、Jenkinsと比較すると成長段階といった印象と受ける。そのため、長期で考えた人材育成やスキル蓄積において検証を手掛ける必要がある。
その他、雑感
OpenShiftとの連携
OpenShiftのプラグインは、このURL(https://plugins.jenkins.io/ui/search?query=openshift) からリストしてみることができる。
また、OpenShift4でJenkinsを動かす概要について、このURL (https://www.openshift.com/blog/deploy-jenkins-pipelines-in-openshift-4-with-openshift-container-storage-4) の記事が参考になる。Jenkinsの簡単インストール
Red Hatが推進するOperator Hubには、Jenkins Oprerator が登録されている。それだけでなく、Helm チャートにも登録がある。
- Jenkins Operator https://operatorhub.io/operator/jenkins-operator
- Helm Chart https://github.com/helm/charts/tree/master/stable/jenkins
IBM Cloud ROKS/IKSでの利用
第二世代VPC環境が東京データセンターで利用できるようになっている。Jenkins、Kubernetes そして OpenShiftも、この新しいVPC上で利用可能だ。しかも、Terraform のIBM Cloudプラグインも整っているので、コードを適用するだけで、一気にインフラを構築することが可能だ。システム構成がコード化されていれば、クラウドのポータルを時間をかけて操作することなく、コードを適用するだけで、必要な数だけ、揃えることも可能である。
Jenkinsの役割的な特性上、Kubernetes/ OpenShiftクラスタは、Jenkinsの周りにテストと本番配信環境として成長していくように思う。そうすと、TerraformとAnsibleを使って、Jenkinsをすぐに構築して提供でき、安定的に運用できる環境でも良いのでは無いかとも思う。
- 投稿日:2020-08-04T18:51:13+09:00
Unsupported config option for services service: ‘app’ エラー
docker-compose.yml を書き換えた時にでたエラー
Unsupported config option for services service: ‘app’原因として、docker-compose が古いらしい
最新のバージョンに変更する必要がある
curl -L “https://github.com/docker/compose/releases/download/バージョン指定/docker-compose-$(uname -s)-$(uname -m)” -o /usr/local/bin/docker-compose最新のバージョンを見るには こちらから
完了
- 投稿日:2020-08-04T18:22:16+09:00
一時クレデンシャルを発行するローカルIMDSを作った
はじめに
AWSを使う上でクレデンシャルをEC2インスタンス上(~/.aws/credentials)に保存したり
プログラムの設定ファイルに指定することは、セキュリティ上の観点から推奨されません。
(というかアクセスキーを発行すること自体がセキュリティリスクになります)
通常は、IAMロールをEC2に紐づけてIMDS(インスタンスメタデータサービス)から一時的な
クレデンシャルを取得してAWSリソースにアクセスにすると思います。この一時クレデンシャルを提供するのが、IMDS(後述)と呼ばれるサービスですが、
ローカルで動くIMDSもどきを作ってみたので、その紹介です。インスタンスメタデータサービス(IMDS)とは
このページを抜粋
インスタンスメタデータサービス(IMDS)は、一時的な認証情報へのアクセスを提供することで クラウドユーザーにとって大きなセキュリティ上の課題を解決し、手動またはプログラムによって インスタンスに機密認証情報をハードコードしたり、配布したりする必要をなくしました。 EC2 インスタンスにアタッチされた IMDS は、特別な「リンクローカル」の IP アドレス 169.254.169.254 で接続され、インスタンスで実行中のソフトウェアだけがアクセスできます。 アプリケーションは IMDS にアクセスして、インスタンス、ネットワーク、およびストレージに関する メタデータを利用できます。 また、IMDSは、インスタンスにアタッチされている IAM ロール による AWS 認証情報を使用 できるようにします。簡単に言うと、EC2上でaws sdkを使ったプログラムやaws cliコマンドを実行すると、
http://169.254.169.254/latest/meta-data/iam/security-credentials/{iamrole}
にリクエストを送信してクレデンシャルを取得し、その認証情報を使ってAWSリソースを操作します。処理イメージ
レスポンス例
一時セキュリティ認証情報{ "Code" : "Success", "LastUpdated" : "2020-08-04T06:34:37Z", "Type" : "AWS-HMAC", "AccessKeyId" : "ASIA4KYQ77T7MF27ET2B", "SecretAccessKey" : "Q8vJapXly4HA1~~", "Token" : "IQoJb3JpZ2lu~~", "Expiration" : "2020-08-04T12:38:26Z" }ローカルIMDSとは
有効期限が切れない間隔で定期的にsts.assumeRoleして一時クレデンシャルを取得して
それをリンクローカルアドレス(169.254.169.254)へのhttpリクエストの結果として返すDocker
コンテナです。使い方
前提)
・スイッチロール元アカウントID:111111111111 / ユーザ名:miyaz@sencorp
・スイッチロール先アカウントID:222222222222 / ロール名:Devスイッチロール先IAMロールの信頼関係に下記を指定
{ "Version": "2012-10-17", "Statement": [ { "Effect": "Allow", "Principal": { "AWS": "arn:aws:iam::111111111111:root" }, "Action": "sts:AssumeRole", "Condition": { "StringLike": { "sts:RoleSessionName": "${aws:username}" } } } ] }スイッチロール元アカウントのクレデンシャルをローカルの ~/.aws/credentialsにセット
[default] aws_access_key_id=~~~ aws_secret_access_key=~~~
docker-compose.ymlを作成
docker-compose.ymlversion: '3.8' services: app: image: centos:7 tty: true ## 既存のdocker-compose.ymlで使いたい場合はここ以降をコピペでOK(RoleArnは書き換え要) imds: image: miyaz/local-imds:latest volumes: - ~/.aws:/root/.aws environment: IMDS_ROLE_ARN: "arn:aws:iam::222222222222:role/Dev" networks: default: ipv4_address: 169.254.169.254 networks: default: ipam: config: - subnet: 169.254.169.0/24実行する
以下の例では、centos7にawscliを入れて
aws s3 ls
を実行する手順です。
ちなみにimdsはエラーメッセージ以外は何もログ出力しません(念の為)docker-compose up -d docker-compose exec app bash yum -y install awscli aws s3 ls
解説
imdsコンテナがIMDSの役割を持っています。
~/.awsをボリューム共有するので、スイッチロール可能なクレデンシャルが指定され
ている必要があります。環境変数[IMDS_ROLE_ARN]に権限を引き受けるロールを指定します。
IMDS_ROLE_ARN: "arn:aws:iam::{AccountId}:role/{IamRole}"
スイッチロール元クレデンシャルのプロファイル名が
default
でなければ、
環境変数[IMDS_SOURCE_PROFILE]で指定できます。imdsが169.254.169.254というIPで動くので、そこからクレデンシャルを取得する
appコンテナが169.254.169.0/24のIPを持っていればOK。
ymlファイルに記載のdefaultのコメントアウトを外すと通常はdefaultネットワークを
使いつつ、クレデンシャル取得時のみ169.254.169.0/24ネットワークを使います。ちなみに、この設定は入れた方がいいと思ったので、roleSessionNameに自動的に
スイッチロール元のIAMユーザ名が入るようにしています。ローカルIMDSのコードはこちら
どこで使えるか?
うーん、あまり有用な使い道は思いつかないですが、、強いて言えばということで。
AWSパートナー経由で契約している場合などOrganizationsが使えない場合はスイッチ
ロール運用している会社が多いと思います。
その場合にはログイン専用アカウントのみにIAMユーザを作成し、ログイン後スイッチロール
して他のアカウントのマネジメントコンソールにアクセスしていると思います。で、開発しているアプリ(gitリポジトリ)とAWSアカウントが紐づいている場合、新たに
参加した開発者にはスイッチロール用クレデンシャルを伝えて .aws/configに追記してもらうと思います。~/.aws/configに追記する例[profile hoge-dev] region=ap-northeast-1 role_arn=arn:aws:iam::222222222222:role/Dev source_profile=default role_session_name=miyaz@sencorp
アプリのコードベースにあるdocker-compose.ymlに予めRole名が記載されて
いれば、これを伝達する必要がなくなって手間削減!!(無理やりwまとめ
思いついたので試してみたら動いた!!
て感じで、あまり運用上有用な使い方はなさそうですが、仕組みの理解は進みました\(^o^)/
- 投稿日:2020-08-04T16:15:42+09:00
# Docker Rails6 Nginx Puma Mysql環境をDockerとは別階層に作りたかっただけ
はじめに
- DockerでRails環境を作る必要があり、ネットにはいくらでも記事は載っているのでそれを見て真似ようと思ったのが発端です。
- 最終的にできたものはRails6 + Nginx + Puma + Mysqlです。使ってみる
- Mac OS
- 以下のような階層にdockerと分けた構成にしたかった。
root ├ docker │ ├ workspace │ │ └ Dockerfileなど │ ├ mysql │ │ └ Dockerfileなど │ ├ nginx │ │ └ Dockerfileなど │ └ docker-compose.yml │ ├ src ├ app │ └ ... ├ config └ ... ...多くのサイトではdocker配下にsrcを置いている構成になりますが、自分の場合はその関係になっていないことに注意してください。
なぜdockerとsrcを別の(並列した)階層にしたかったのか
完全に主観ですが、開発するときにrailsのフレームワークをいじっているのに、その階層にdocker関連のファイルがあることが許せませんでした。整頓したかっただけです。
なぜ詰まったのか
他のサイトの内容でやると以下のような現象が起きました。
- とあるライブラリがありませんみたいなエラーが出る。
Could not find public_suffix-4.0.5 in any of the sourcesたったこれだけなのですが、めちゃくちゃ詰まりました。
原因
多くのサイトはDockerfileが以下のような記述になっています。
DockerfileFROM ruby:2.5.1 # リポジトリを更新し依存モジュールをインストール RUN apt-get update -qq && \ apt-get install -y build-essential \ nodejs # ルート直下にwebappという名前で作業ディレクトリを作成(コンテナ内のアプリケーションディレクトリ) RUN mkdir /webapp WORKDIR /webapp # ホストのGemfileとGemfile.lockをコンテナにコピー ADD Gemfile /webapp/Gemfile ADD Gemfile.lock /webapp/Gemfile.lock # bundle installの実行 RUN bundle install # ホストのアプリケーションディレクトリ内をすべてコンテナにコピー ADD . /webappwebappは私の構成でいうsrcのことです。
この書き方では私のように並列しているディレクトリ構成にはできないので注意してください。このGemfileの構成は以下のようになっています。Gemfilesource 'https://rubygems.org' gem 'rails', '~> 6'これ並列にしている都合上、
docker-compose up
する度にこのほとんど何もないGemfileでbundle install
されることになります。そうすると、コンテナ側にあったGemfileが古いもので上書きされることになり、うまくRailsが起動しない原因となります。どうすれば良いのか
解決策のDockerfileの構造です。
DockerfileARG RUBY_VERSION FROM ruby:${RUBY_VERSION} RUN curl https://deb.nodesource.com/setup_12.x | bash RUN curl https://dl.yarnpkg.com/debian/pubkey.gpg | apt-key add - RUN echo "deb https://dl.yarnpkg.com/debian/ stable main" | tee /etc/apt/sources.list.d/yarn.list RUN apt-get update -qq && \ apt-get install -y build-essential \ libpq-dev \ nodejs \ yarn \ vim RUN mkdir /var/www WORKDIR /var/www ################## ここが大事!! ################ COPY entrypoint.sh /usr/bin/ RUN chmod +x /usr/bin/entrypoint.sh ENTRYPOINT ["entrypoint.sh"] ############################################## # Start the main process. CMD ["rails", "server", "-b", "0.0.0.0"]このようにして、ENTRYPOINTでシェルスクリプトを起動するようにします。entrypoint.shは以下のようになります。
entrypoint.sh#!/bin/bash set -e # Remove a potentially pre-existing server.pid for Rails. rm -f tmp/pids/server.pid if [ ! -e Gemfile ]; then ls echo "初回" echo "source 'https://rubygems.org'" > Gemfile echo "gem 'rails', '~> 6'" >> Gemfile echo "" > Gemfile.lock bundle install rails new . --force --database=mysql fi; # Then exec the container's main process (what's set as CMD in the Dockerfile). exec "$@"これだけだとコンテナにGemfileが永続化されないので、docker-compose.ymlに以下のように記述します。
docker-compose.yml### Workspace app server ################################################ workspace: build: context: ./workspace args: - RUBY_VERSION=${RUBY_VERSION} volumes: - ${APP_CODE_PATH_HOST}:${APP_CODE_PATH_CONTAINER}${APP_CODE_CONTAINER_FLAG} - ${APP_CODE_PATH_HOST}/bundle:${WORKSPACE_BUNDLE_SOURCE} ports: - "3000:3000" command: bash -c "rm -f tmp/pids/server.pid && bundle exec rails s -p 3000 -b '0.0.0.0'" depends_on: - mysqlここのvolumeでコンテナをホストのsrcでマウントします。このようにすることで、Gemfileが古いもので上書きされてしまう心配はなくなりました。
bundle installが毎回走ってしまうのでは?
本記事とは少しそれますが、
/usr/local/bundle
をマウントしないと毎回bundle install
する必要が出て、起動にかなり時間がかかるので注意してください。RailsとDockerを分けてすっきりさせたい人
作ったものをGithubにあげました。やり方もREADME.mdに書いたので数分で構築できると思います。
終わりに
かなり少数派かもしれませんが、dockerのディレクトリと分けたいと思っている方には役立ってくれるかなと思います。
- 投稿日:2020-08-04T14:05:12+09:00
Django on Dockerの環境づくりの記事を見ながら構築してたら途中でERROR: for django Cannot start service django: OCI runtime create failed: container_linux.go:349: starting container process caused "exec: \"/usr/src/app/entrypoint.sh\": permission denied": unknownと出たので解決した
エラー内容
ERROR: for django Cannot start service django: OCI runtime create failed: container_linux.go:349: starting container process caused "exec: \"/usr/src/app/entrypoint.sh\": permission denied": unknown環境
Mac OS Catalina 10.15.4
経緯
を参考にDjango REST Frameworkの環境を構築していた所、Djangoの環境をDocker上にcomposeしようとしたら以上のエラー内容が出てきたのでメモ用に記事を書いておきます。
状況としては、DjangoとpostgreSQL、nginxのDockerfileを書いた後に
entrypoinst.sh
を作成し、DjangoディレクトリのDockerfilebackend/containers/django/Dockerfile# これ COPY ./entrypoint.sh /usr/src/app/entrypoint.sh COPY . /usr/src/app/ # これ ENTRYPOINT ["/usr/src/app/entrypoint.sh"]のコメントアウトを消して再び
$ docker-compose up -d --buildコマンドを叩くと冒頭のエラーが出ました。
手っ取り早い解決策としては
Error: Starting container process caused “exec: \”/docker-entrypoint.sh\“: permission denied”
この記事を参考にしました。
エラー内容的にも権限が与えられていないのが原因とはわかっていたのですが、早く解決するためにググりました。結論としてはDjangoディレクトリで
$ chmod 755 entrypoint.shで権限を与え、再び
$ docker-compose up -d --buildしてあげると無事にDockerfileの変更が反映されます。
Dockerはいざ自分で触ると分からないことが多くて触るだけでも勉強になりますね。
- 投稿日:2020-08-04T12:58:28+09:00
VultrでKUSANAGI Runs on Dockerが動くまで(その3)
前回のおさらい
前回の記事『VultrでKUSANAGI Runs on Dockerが動くまで(その2)』ではVPC環境であるVultrにKUSANAGI RoD環境を構築しWordpressをインストールするところまで確認しました。
今回はWordpressの設定を変えていきたいと思います。動作環境など
- Ubuntu 20.04
- docker 19.03.12
- docker-compose 1.26.2
$ docker-compose ps Name Command State Ports ----------------------------------------------------------------------------------------------------------------- kusanagi01_config docker-entrypoint.sh wp -- ... Restarting kusanagi01_db docker-entrypoint.sh mysqld Up kusanagi01_ftp /bin/sh -c /docker-entrypo ... Up kusanagi01_httpd /docker-entrypoint.sh /usr ... Up 0.0.0.0:8080->8080/tcp, 0.0.0.0:8443->8443/tcp kusanagi01_php /usr/local/bin/docker-entr ... Up変更するWordpress周りの設定
- KUSANAGIパスワードの省略
- フォルダのパーミッションの変更(やらなくても大丈夫かも)
1. KUSANAGIパスワードの省略
KUSANAGIはセキュリティのためテーマやプラグインをインストールする際に以下のようにKUSANAGIパスワードを聞かれます。KUSANAGIパスワードはプロビジョニング時に指定していなければインストールディレクトリの.kusanagi.wpに記載があります。
毎回パスワードを聞かれないようにするためには、wp-config.phpのFS_METHODをftpextからdirectに変更します。
KUSANAGI RoDの場合はローカルのファイルを修正し、kusanagiコマンドでコンテナにコピーする形になります。$HOME/kusanagi01/contents/wp-config.php#define('FS_METHOD', 'ftpext'); define('FS_METHOD', 'direct'); ※ここを変更 define('FTP_HOST', 'localhost'); define('FTP_USER', 'kusanagi'); #define('FTP_PASS', '*****');以下のコマンドでコンテナにコピーします。エラー出るけど気にしなくて大丈夫です。
$ cd $HOME/kusanagi01 $ kusanagi-docker config push chown: unknown user/group kusanagi:www ERROR: Failed.コンテナにログインしてファイルがアップされているか確認します。ftpコンテナにシェルアクセスして確認します。
ホスト上で実行 $ docker-compose exec ftp sh 以下、ftpコンテナ / # ls -al /home/kusanagi/kusanagi01/ total 28 drwxr-xr-x 6 kusanagi 1001 4096 Jul 26 03:15 . drwxr-xr-x 3 kusanagi 1001 4096 Jul 26 03:29 .. drwxr-x--- 5 kusanagi 1001 4096 Jul 23 14:01 DocumentRoot drwxr-xr-x 2 kusanagi 1001 4096 Jul 16 10:24 settings drwxr-xr-x 2 kusanagi 1001 4096 Jul 18 13:56 tools drwxr-xr-x 4 kusanagi 1001 4096 Jul 16 10:24 wp-config-sample -r--r----- 1 kusanagi 1001 3345 Jul 26 03:15 wp-config.php / # cat /home/kusanagi/kusanagi01/wp-config.php |grep FS_ #define('FS_METHOD', 'ftpext'); define('FS_METHOD', 'direct');2. フォルダのパーミッション変更(やらなくても大丈夫かも)
※以下の記述はやらなくても大丈夫かもしれません。
KUSANAGIパスワードとは別の問題でデフォルト状態だとフォルダに書き込み権限がなくて色々うまくいきません。
ftpコンテナにシェルアクセスしてフォルダに権限を付与します。ftpコンテナだけrootでログインできるので何か変更する場合はftpコンテナを使います。
色々試した結果、以下のパーミッションでうまく動きました。きっとこれで大丈夫かと思います。
※kusanagi-docker configu pushをすると設定が元に戻るので要注意
- DocumentRootを750から755に変更
- DocumentRoot/wp-content配下のuploadsを755から775に変更
- DocumentRoot/wp-content配下のuploads以外は755のまま
- DocumentRoot/wp-content配下のlanguagesは750のまま
ホスト上で実行 $ docker-compose exec ftp sh 以下、ftpコンテナ / # cd /home/kusanagi/kusanagi01/ /home/kusanagi/kusanagi01 # chmod 755 DocumentRoot/ /home/kusanagi/kusanagi01 # cd DocumentRoot/ /home/kusanagi/kusanagi01/DocumentRoot # chmod -R 775 uploads/ /home/kusanagi/kusanagi01/DocumentRoot # ls -al /home/kusanagi/kusanagi01/DocumentRoot/wp-content/ total 36 drwxr-xr-x 8 kusanagi 1001 4096 Jul 18 13:56 . drwxr-xr-x 5 kusanagi 1001 4096 Jul 23 14:01 .. -rw-r--r-- 1 kusanagi 1001 28 Jul 18 13:55 index.php drwxr-x--- 4 kusanagi 1001 4096 Jul 18 13:55 languages drwxr-xr-x 3 kusanagi 1001 4096 Jul 16 10:24 mu-plugins drwxr-xr-x 4 kusanagi 1001 4096 Jul 26 09:06 plugins drwxr-xr-x 7 kusanagi 1001 4096 Jul 26 09:05 themes drwxr-xr-x 2 kusanagi 1001 4096 Jul 26 09:06 upgrade drwxrwxr-x 3 kusanagi 1001 4096 Jul 23 14:38 uploadsこれでまともにWordpressが動くようになりました。
Wordpressに好きなテーマインストールしてカスタマイズして使い倒してください。
- 投稿日:2020-08-04T12:08:00+09:00
NextcloudのOnlyOfficeとECSのコンテナを統合する方法
今回は、NextcloudのOnlyOfficeをAlibaba Cloud Elastic Compute Service (ECS)インスタンスのコンテナと連携させる方法を見ていきます。
本ブログは英語版からの翻訳です。オリジナルはこちらからご確認いただけます。一部機械翻訳を使用しております。翻訳の間違いがありましたら、ご指摘いただけると幸いです。
By Colince Azeye, Alibaba Cloud Tech Share Author. Tech Shareは、クラウドコミュニティ内で技術的な知識やベストプラクティスを共有することを奨励するAlibaba Cloudのインセンティブプログラムです。
今回の記事では、Alibaba Cloud Elastic Compute Service (ECS)インスタンスでNextcloudのOnlyOfficeとコンテナを統合する方法を見ていきたいと思います。
しかし、始める前に、このチュートリアルの各コンポーネントを簡単に紹介します。Nextcloudの詳細については、代わりにECSにNextcloudをインストールする方法についてのこちらの記事を参考にしていただければと思いますので、今のところは割愛させていただきます。
Wikipediaによると、Nextcloudはファイルホスティングサービスを作成・利用するためのクライアント・サーバ・ソフトウェアのスイートです。機能的にはDropboxに似ていますが、Nextcloudは無料でオープンソースなので、誰でもプライベートサーバーにインストールして運用することができます。
OnlyOfficeは、豊富な機能を備えた包括的なオープンオフィス、クラウドベースのオフィスおよび生産性スイートです。以前はTeamLab Officeと呼ばれていたこのソフトウェアは、オンラインドキュメントエディタ、CRM、ドキュメントおよびプロジェクト管理ツールのコア要素を持つ統合プラットフォームをユーザーに提供しています。
Spreedは、フリーのオープンソース(AGPL)のWebRTCオーディオ/ビデオ通話・会議サーバで、ブラウザ同士がピアツーピアで会話できるようにします。Spreedを使用すると、Nextcloudをインストールしたブラウザから、リッチな音声、ビデオ、テキストチャットを使って安全に通信することができます。
Dockerコンテナは、その場で作成して特定のアプリケーションや環境をデプロイすることができる標準化されたユニットです。概念的には仮想化技術に似ていますが、オペレーティングシステムがコンテナから抽象化されている点が大きな違いです。
ECS(Elastic Compute Service)は、物理サーバよりもシンプルで効率的な管理モードを備えた、弾力的な処理能力を特徴とするコンピューティングサービスの一種である。
全てをまとめる
NextcloudとOnlyofficeをECSで利用する目的を見てみましょう。オンライン資産を最新の状態に保ちながら、オフィスでのコラボレーションやプライベート共有のためのツールを必要としている組織を想像してみてください。Nextcloudは人との接続、チャット、データ共有、コラボレーションを可能にし、OnlyofficeはオンラインドキュメントエディタでNextcloudの連絡先との作業、CRMでの顧客管理を可能にします。Spreedは、あなたのNextcloud上で簡単に電話会議を持つことができるようになります。さらに、コンテナを使用してすべてを実行することで、アプリ開発の柔軟性が高まり、システムの軽量化にもつながります。
前提条件
- 有効なAlibaba Cloudアカウントが必要です。まだお持ちでない場合は、無料トライアルにサインアップすることができます。
- Ubuntu 16.04を実行しているAlibaba Cloud ECSインスタンス。
- ルートアクセスまたはルートアクセスを持つユーザー(sudoグループ内)。
- 有効なドメイン名(これはオプションですが、トラフィックを暗号化したい場合は必要です)。
ステップ1:システムをアップデートしてアップグレードします。この2つのコマンドを実行することで作業が完了します。
apt-get update apt-get updgradeステップ2: nginxサーバーのインストール
apt-get install nginxnginx の状態を確認して、動作していることを確認します。確認方法は主に2つあります。
- service nginx status" コマンドを使用する。
- ブラウザでECSインスタンスのパブリックIPアドレスを入力します。
ステップ3:Dockerをインストール:
apt-get install docker.iodockerのインストール状況はもちろん、dockerのバージョンも確認できます。
service docker status docker -v上の画像のように、私のECSではdockerが実行されており、バージョンは1.6.2になっています。
ステップ4: docker-composeをインストール:
sudo curl -L https://github.com/docker/compose/releases/download/1.17.1/docker-compose-`uname -s`-`uname -m` -o /usr/local/bin/docker-composedocker-compose をダウンロードして /usr/local/bin に入れます。フォルダの中に入って、docker-composeに実行権を与えます。
chmod +x docker-compose.イメージの中には、docker composeをインストールするために使用するすべてのステップがあります。そして最後のコマンドで彼のバージョンを確認すると、私の場合は1.17.1になっています。
Step 5: システム起動時に自動起動するようにします。
Service docer reloadステップ 6: githupレポをクローンした後、フォルダの中に入り、コマンドを入力します。
- cd docker-only-office-nextcloud - git submodule update -remote画像の中には、すべてのコマンドと結果を見ることができます docker-onlyoffice-nextcloudをクローンするために入力します。
ステップ 7: nextcloud-onlyofficeのデプロイ
今すぐコマンドを入力してください:
docker-compose up -d to start container in .yml file
スクリーンショットを見ると、dockerコンテナが正常に起動したことがわかります。ブラウザでIPアドレスを入力すると、nextcloudのインターフェイスが表示されます。
注意: 上記の手順をすべて完了しても、パブリックIPアドレスを入力しても何も表示されない場合は、トラフィックがブロックされている可能性があります。つまり、特定のポートでのトラフィックを許可する必要があります。そのためには、ECSのセキュリティグループとルールを設定する必要があります。
- Rule direction:Ingressを入力
- Action: 許可を入力
- Custom port Range:80/80を入力
- Authorization Objects:0.0.0.0.0/0を入力します。
- 説明を入力してOKを押します。
カスタムポート範囲 43/43 を指定して、上記の手順を繰り返します。
このチュートリアルを動作させるためには、ポート 80 と 43 からのトラフィックを許可しなければなりません。また、ポート80と43の両方について上記と同じ手順を繰り返す必要がありますが、ルールの方向をEgressに変更します。
完了したら、Nextcloudサーバーに再度アクセスします。
これがルールを作成するためのインターフェースです。ここでは、データベースとしてSQLiteを使用することを想定してみましょう。管理者ユーザー名と管理者パスワードを入力します。クリックして設定を終了します。
ご覧のように、最初の設定には管理者認証を入力する必要があります。数分後、あなたはあなたのウェルカムページにリダイレクトされます。
さて、ECS上でNextcloudをどのように設定したかというと、追加ボタンをクリックするとOnlyOfficeが表示されません。そこで設定するためには、CLI上でdocker-onlyoffice-nextcloudフォルダの中に立つ必要があります。その中で、bash set-configuration.shというコマンドを入力します。
しかし、OnlyOfficeが動作するためには信頼できるドメインが必要なので、その前に有効なドメイン名にパブリックIPアドレスをアタッチする必要があります。ドメイン名の設定後、以下のように表示されるはずです。
ステップ8. スプレードのインストール
Spreed WebRTCとNextcloudを同じオリジンで動作させる必要があります。つまり、SpreedとNextcloudは同じプロトコルスキーム、同じドメイン、同じポートを使ってアクセスすることができます。
Nextcloudにアクセスして、右上にある「A」のロゴを見つけます。それをクリックして、アプリをクリックします。インストールされているアプリ、アクティブなアプリ、アップデートを含むアプリのすべてのカテゴリが表示されます。今度はApp bundlesをクリックして、"talk "を探して、それをインストールするためにクリックします。
注:あなたはアプリのバンドルで話を見つけることができませんでした場合は、ちょうど上記の検索バーに "話 "を入力し、エンターキーを押します。
さて、プラットフォーム上にいない人と話したい場合はどうしますか?URLで外部のチャット参加者を招待することができます。このチャットは、ユーザーが通話から離れても開かれたままで、参加者がメッセージ、リンク、メモを簡単に交換することができます。また、パスワードで公開グループチャットを保護することもできます。
これで完了です。
結論
これが終わるまでに、私たちはAlibaba Cloud ECS上に完全なコンテナ化されたSaaSサービスを設定しました。このチュートリアルがお役に立てたことを願っています。
アリババクラウドは日本に2つのデータセンターを有し、世界で60を超えるアベラビリティーゾーンを有するアジア太平洋地域No.1(2019ガートナー)のクラウドインフラ事業者です。
アリババクラウドの詳細は、こちらからご覧ください。
アリババクラウドジャパン公式ページ
- 投稿日:2020-08-04T11:07:21+09:00
Xulu:DockerのリモートAPI不正アクセス脆弱性を利用した悪意のあるコンテナのデプロイ
Alibaba Cloudは最近、DockerのリモートAPI不正アクセス脆弱性を悪用して悪意のあるコンテナを展開するマイニングボットネット「Xulu」を検出しました。
本ブログは英語版からの翻訳です。オリジナルはこちらからご確認いただけます。一部機械翻訳を使用しております。翻訳の間違いがありましたら、ご指摘いただけると幸いです。
今月初め、DockerのリモートAPI不正アクセス脆弱性を悪用して悪意のあるDockerコンテナを被害者ホストにデプロイするマイニングボットネットを検出しました。ボットネットのマイニングでユーザー名として機能することから、このボットネットを「Xulu」と命名しました。
XuluはDockerを狙った最初のボットネット事例ではありませんが、他のボットネットとは異なり、自ら他のホストをスキャンするのではなく、OSINT(オープンソースインテリジェンス)の技術を利用し、初段を動的に検索して獲物となりうるリストを探し出します。
また、制御サーバーをTorネットワークに配置しており、ボットネットの邪悪な裏工作員を隠そうとしているのかもしれません。
Moneroを採掘する悪質なDockerイメージ
コンテナとは、コードとそのすべての依存関係をパッケージ化したソフトウェアの標準的な単位であり、アプリケーションがあるコンピューティング環境から別のコンピューティング環境へと迅速かつ確実に実行されるようにします。
docker.comのこの定義は、dockerコンテナとは何かを説明しています。今日では、マイクロサービスの人気が高まるにつれ、多くの企業がアプリケーションのデプロイにコンテナを使用しています。しかし、そのセキュリティは見落とされがちで、Dockerサービスは悪用されやすいターゲットになりかねません。
Xuluのボットネットイベントを掘り下げてみると、悪意のある「zoolu2/auto」のdockerイメージを持つコンテナが、侵害されたホスト上に作成されていることに気付きました。
コンテナには以下のプロセスが実行されています。
採掘プロセスを区別するのは簡単です。
/toolbin/darwin -o us-east.cryptonight-hub.miningpoolhub.com:20580 -u xulu.autodeploy -p x --currency monero -i 0 -c conf.txt -rminingpoolhub .comはユーザーの公開支払いデータを提供していないため、脅威となる行為者がcryptojackingからどれだけの経済的利益を得ているかはわかりません。
ボットネットの伝播と持続性
Xulu ボットネットは OSINT 技術と Tor ネットワークを使って増殖しています。
まず最初に、ボットネットは
http://wg6kw72fqds5n2q2x6qjejenrskg6i3dywe7xrcselhbeiikoxfrmnqd.onion
を制御サーバとして使用します。接尾辞の「.onion」は、Torネットワークを介して到達可能な匿名のオニオンサービス(別名「隠されたサービス」)であることを示しています。ボットネットはまた、
/toolbin/shodaemon
をメインのデーモンプロセスとして実行しています。スクリプトからは、まずリモートファイル
http://wg6kw72fqds5n2q2x6qjejenrskg6i3dywe7xrcselhbeiikoxfrmnqd.onion/shodan.txt
とローカルファイル/toolbin/hcode.txt
の内容を組み合わせて /search.txt を生成していることがわかります。各ファイルには shodan のクエリのリストが含まれており、それらは
/toolbin/shodan
によって読み込まれて送信されます。クエリは、インターネット上で開かれているDockerポート(2375)を持つホストのipsを返します。すべてが脆弱ではありませんが、脅威のアクターはshodanの情報を利用することで大量のスキャン作業を省くことができます。
重複を削除した後、侵害されたホストは、収集した各IPに "docker run "コマンドを送信します。その後、zoolu2/autoの悪意のあるコンテナは、DockerリモートAPI不正アクセスの脆弱性を持つ新しいホストにデプロイされます。
さらに、ボットネットは
http://wg6kw72fqds5n2q2x6qjejenrskg6i3dywe7xrcselhbeiikoxfrmnqd.onion/bnet1.txt
からスクリプトをダウンロードして実行し、永続化を図っています。攻撃の規模とセキュリティの推奨
https://hub.docker.com では、前述の悪意のあるドッカーイメージが 10k 回以上ダウンロードされています。
Xuluボットネットの作者は、ボットネットの亜種を積極的に開発しているようです。
このイベントはDockerユーザーのCaprico1さんも観測しており、DockerのGitHubで議論されています。
https://github.com/docker/hub-feedback/issues/1809
この記事が公開される頃には、Dockerのエンジニアによってzoolu2のアカウントが無効化されています。
悪意のある侵入やマイニングの犠牲者にならないために、以下のような推奨事項があります。
- 内部利用のためのサービス(Dockerなど)はインターネットに公開しないこと。適切な ACL やその他の認証技術を使用して、信頼できるユーザーからのアクセスのみを許可します。
- 隠されたサービスは多くのボットネットによって利用されているので、頻繁に利用しないユーザーは、以下のようなトリックを使って、隠されたサービスとの間でパケットをドロップすることができます:
echo -e "η0.0.0.0.0 .onion" >> /etc/hosts
このコマンドは、隠されたサービスとの間のトラフィックをシンクホール(リダイレクト)します。- クラウドファイアウォールは攻撃を防ぐのに便利です。Alibaba Cloud Firewallをおすすめする理由は、脅威の検知、ブロック、分析ができるからです。AI技術を味方につけて、侵入や悪意のあるマイニングから守ることができます。
- アリババクラウドマネージドセキュリティサービスを利用することで、アリババのセキュリティスペシャリストの専門知識を利用して、マルウェアのクリーンアップや設定の改善、全体的なセキュリティ強化を支援してもらうことができます。組織のセキュリティに不安を感じている方は、ぜひ一度試してみてはいかがでしょうか。
IOC
サーバーを制御:
http://wg6kw72fqds5n2q2x6qjejenrskg6i3dywe7xrcselhbeiikoxfrmnqd.onionURL:
http://wg6kw72fqds5n2q2x6qjejenrskg6i3dywe7xrcselhbeiikoxfrmnqd.onion/bnet1.txt http://wg6kw72fqds5n2q2x6qjejenrskg6i3dywe7xrcselhbeiikoxfrmnqd.onion/shodan.txtPool:
us-east.cryptonight-hub.miningpoolhub.com:20580Md5:
c29dfe75862b6aed91bec4ffc7b20b9c参照
https://twitter.com/Suprn8/status/1129877707897081856
https://www.docker.com/resources/what-container
アリババクラウドは日本に2つのデータセンターを有し、世界で60を超えるアベラビリティーゾーンを有するアジア太平洋地域No.1(2019ガートナー)のクラウドインフラ事業者です。
アリババクラウドの詳細は、こちらからご覧ください。
アリババクラウドジャパン公式ページ
- 投稿日:2020-08-04T09:36:21+09:00
Polarisを用いてKubernetesのベストプラクティスを3分でチェックする
Kubernetesにおけるベストプラクティスを取り巻く流れ
Kubernetesが成熟してきたことと、DevとOpsの責任範囲分離などの背景があり
アプリケーションエンジニアもKubernetesを扱う場面が増えてきたという話をちらほら耳にする。
ここで、Kubernetesわかるマンにとっては朝飯まであったYAMLをこねこねする作業を、誰でも行うような動きが加速しており、今後もこの状態が続いていくと想像できる。特にKubernetesのセキュリティ観点に目を向けると、CNCFが新たにKubernetesのセキュリティに特化した新試験を近日公開することもあり、Kubernetesを用いた開発をより均質化・安定化させていく動きがみられる。
https://training.linuxfoundation.org/ja/certification/certified-kubernetes-security-specialist/ここでは、手元のKubernetesクラスタがベストプラクティスに沿っているかを手軽に確認できるツールである、Polarisを紹介する。
Polarisの機能概要
FairwindsのPolarisは、クラスターの円滑な運用を維持する。様々なチェックを実行して、Kubernetesポッドとコントローラがベストプラクティスに沿っていることを確認し、将来的な問題を回避することに役立てられる。Polarisは、下記の3つのモードで実行できる。
ここではダッシュボードについて取り上げ、まとめにてValidating Webhook, CLI toolについて触れる。
- ダッシュボード
- Validating Webhook
- CLI tool
Dashboard Quick Start
クラスタの用意
ここは環境に合わせて用意ください。ここではkindを用いた例で説明します。kind create clusterporarisをダッシュボードとしてデプロイし、ダッシュボード Serviceをホストにポートフォワード
kubectl apply -f https://github.com/FairwindsOps/polaris/releases/latest/download/dashboard.yaml kubectl port-forward --namespace polaris svc/polaris-dashboard 8080:80以上で、polarisが動作している状態になります。
※port-forwardコマンドのタイミングが早すぎると、Pod起動前にポートフォワードが試行されエラーが返ります。動作確認
localhost:8080にブラウザでアクセスすると、polarisのダッシュボードを確認できる
5つのカテゴリごとにテスト結果のパーセンテージが表示される
- Health Check:
- Images
- Networking
- Resources
- Security
HealthCheck
HelathCheckのテストはシンプルで、下記のページに示されている通りReadinessProbeとLivenessProbeが定義されていなければ失敗する。デフォルトはWarningとしている
Images
Imagesのテストも下記に示されている2点のテストを行っている。
イメージのタグが指定されていないかlatestの場合に失敗する。デフォルトはdanger
イメージのpullPolicyがAlwaysじゃない場合に失敗する。デフォルトはignore
Networking
hostNetworkやhostPortが設定されている場合に失敗する。デフォルトはWarning
Resources
Resource Requests/LimitsがCPU, Memoryそれぞれに定義されていなければ失敗する。デフォルトはdanger
Security
下記の通り、特にホストマシンに影響を与える部分がdangerとなっている。
Namespace内のKind別にテスト結果を確認できる
polaris以外に特に何も動かしていないクラスタのため、Kindにデフォルトで入っているlocal-path-storageとkube-system, polaris用のnamespaceが表示されている。
kube-system namespace上のkindnetというDaemonsetに焦点を当ててみる。
Daemonsetから生成されるkindnet-cni コンテナに対して、危険なCapabilityを持っているというdangerアラートが出ている。CNIなのでこれは仕方ないが。
まとめ
Polarisを使うことで、Kubernetesクラスタがベストプラクティスに沿っているかを手軽に検証することができる。
今回紹介していないが、KubernetesのAdmission ControllerにValidating Webhookとして組み込むことで、dangerと判定されるマニフェストが適用される場合に、それを自動的に拒否する仕組みにも対応している。
また、CLIとしても動作するためCI/CDのパイプラインに組み込み、dangerやwarningなどの閾値を設定することでCI/CDパイプラインを停止させる仕組みにも対応している。
- 投稿日:2020-08-04T08:33:46+09:00
既存のRailsアプリの開発環境にDockerを導入する手順【Rails, MySQL, Docker】
こんにちは.
今回は, 既存のRailsアプリの開発環境にDockerを導入する手順をまとめてみました.
まだまだ勉強不足ですので, 修正点・改善点等ございましたら, ご指摘いただけますと幸いです.事前準備
- Docker-for-macのインストール
- 既存のRailsアプリ(今回は以前作成した簡単な家計簿アプリを使用します.)
環境
Ruby:2.5.3
Rails:5.2.4.3
MySQL:5.6
Docker:19.03.8
docker-compose:1.25.4手順
1. ルートディレクトリにDockerfile,docker-compose.ymlを追加
既存のRailsアプリのルートディレクトリ直下に
Dockerfile
とdocker-compose.yml
を作成します.
以下, それぞれのファイルの中身です.Dockerfile
DockerfileFROM ruby:2.5.3 RUN apt-get update && apt-get install -y \ build-essential \ nodejs WORKDIR /kakeibo COPY Gemfile Gemfile.lock /kakeibo/ RUN bundle install
FROM ruby:2.5.3
の部分についてはアプリのRubyのバージョンに合わせる.RUN apt-get update && apt-get install -y ~
で必要なパッケージをインストールする.WORKDIR /kakeibo
でコンテナ内にフォルダを作成.COPY Gemfile Gemfile.lock /kakeibo/
でコンテナ内にGemfileとGemfile.lockをコピーした後,bundle install
を実行する.docker-compose.yml
docker-compose.ymlversion: '3' volumes: mysql-data: services: web: build: . command: bundle exec rails s -p 3000 -b '0.0.0.0' ports: - '3000:3000' volumes: - '.:/kakeibo' tty: true stdin_open: true depends_on: - db links: - db db: image: mysql:5.6 volumes: - 'mysql-data:/var/lib/mysql' environment: - 'MYSQL_ROOT_PASSWORD=password'
Dockerfile
とdocker-compose.yml
の中身の詳しい説明はこちらの記事にわかりやすくまとめられていました.2. config/database.ymlを編集
config/database.ymldefault: &default adapter: mysql2 encoding: utf8 pool: <%= ENV.fetch("RAILS_MAX_THREADS") { 5 } %> username: root password: password host: db development: <<: *default database: kakeibo_development
config/database.yml
のpassword
とhost
をdocker-compose.ymlで設定した値に合わせます.3. コンテナ起動
terminal$ docker-compose build $ docker-compose up -d $ docker-compose exec web rails db:create $ docker-compose exec web rails db:migrateこれで http://localhost:3000 にアクセスすると無事にアプリが表示されるはずです.
参考
- 既存のrailsプロジェクトをDockerで開発する手順
- 既存のRailsアプリにDockerを導入する手順
- Dockerで既存アプリの開発環境を作成【Ruby2.6 + Rails5.2 + Mysql5.7】
- [Rails] DockerでRails + MySQLの開発環境をつくる手順
- Docker初心者がRails + PostgreSQL or MySQLで仮想環境構築した手順を丁寧にまとめる
- #Linux #Ubuntu #docker #Dockerfile のこれは何? apt-get install --no-install-recommends
- 『Dockerfile のベストプラクティス』
- 投稿日:2020-08-04T08:32:14+09:00
Railsアプリの開発環境をDockerで構築する手順【Rails, MySQL, Docker】
こんにちは.
今回は, Railsアプリの開発環境をDockerで構築する手順をまとめてみました.
まだまだ勉強不足ですので, 修正点・改善点等ございましたら, ご指摘いただけますと幸いです.事前準備
環境
Ruby: 2.5.8
Rails: 5.2.4.3
MySQL: 5.7.31
Docker: 19.03.8
Docker Compose: 1.25.4手順
1. プロジェクトのルートディレクトリを作成
terminal$ mkdir test-app初めに, プロジェクトのルートディレクトリを作成します.
2. ルートディレクトリ直下にファイルを追加
terminal$ cd test-app $ touch Dockerfile docker-compose.yml Gemfile Gemfile.lock作成したルートディレクトリの直下に
Dockerfile
,docker-compose.yml
,Gemfile
,Gemfile.lock
の4つのファイルを作成します.
それぞれのファイルの中身は以下のようになります. (Gemfile.lockは空のままにします.)DockerfileFROM ruby:2.5 RUN apt-get update && apt-get install -y \ build-essential \ nodejs WORKDIR /test-app COPY Gemfile Gemfile.lock /test-app/ RUN bundle installdocker-compose.ymlversion: '3' volumes: mysql-data: services: web: build: . command: bundle exec rails s -p 3000 -b '0.0.0.0' ports: - '3000:3000' volumes: - '.:/test-app' tty: true stdin_open: true depends_on: - db links: - db db: image: mysql:5.7 volumes: - 'mysql-data:/var/lib/mysql' environment: - 'MYSQL_ROOT_PASSWORD=test-app'Gemfilesource 'https://rubygems.org' gem 'rails', '~>5.2'3. コンテナ内にRailsのセットアップを行う
terminal$ docker-compose run --rm web rails new . --force --database=mysql --skip-bundle --skip-testwebのコンテナ内で
rails new
を実行します.
今回はテストにRSpecを使用する予定でしたので,--skip-test
も追加しています.4. 作成されたconfig/database.ymlを編集
Railsのセットアップにより作成された
config/database.yml
を以下のように編集します.config/database.ymldefault: &default adapter: mysql2 encoding: utf8 pool: <%= ENV.fetch("RAILS_MAX_THREADS") { 5 } %> username: root password: test-app #docker-compose.ymlのMYSQL_ROOT_PASSWORDの値を設定する host: db #docker-compose.ymlのservice名と合わせる development: <<: *default database: test-app_development5. コンテナの起動
terminal$ docker-compose up --build -d $ docker-compose run --rm web rails db:createこれで, http://localhost:3000 にアクセスすると, Railsのホーム画面が表示されるはずです.
参考
- 投稿日:2020-08-04T07:34:50+09:00
【2020年夏】VSCode で作る Docker 開発環境
前書き
今までスペックの低いコーディング環境だったので、EC2 に環境作って開発してたんですが、多少メモリに余裕のあるコーディング環境が用意できたので、Docker を使用した環境に移行することにしました。
が、思ったより、環境作るのに遠回りしたので、メモ書きを残しときます。
要するに「公式読め!」って記事です。たどり着ければ終了なので、ただのリンク集です。
最初に見るべきサイト
公式の記事です。
Developing inside a Container - code.visualstudio.com
remote - overview から読んだ方がよいかもしれません。環境構築自体は、ドキュメントに従って作るだけなので、ドキュメント読み慣れてる人なら問題は起こらないと思います。
設定のポイントは.devcontainer/
にできるDockerfile
とdevcontainer.json
です。
Dockerfile
とdevcontainer.json
Remote-Containers: Add Development Container Configuration Files...を叩いた後、上記の 2 ファイルが、初期ファイルとして作成されます。
これを自身の環境用に改修していきます。改修時に参照すべきは以下です。
microsoft / vscode-dev-containers「Sample projects」って項目がありますが、参照すべきはそちらでは無く、vscode-dev-containers/containers/ のようです。使いたいテンプレートを clone できないのがちょっとメンドイ。
全体を clone してそこからコピーしろということのようです。
devcontainer.json
の書式は、以下に従ってください。
devcontainer.json reference - code.visualstudio.comこれで大体必要なリンクは載せられたと思います。
まだ、実際の開発に使用していないので、いったん記事としてはここまでです。
どんどん作って壊して効率よく開発していきましょ!
- 投稿日:2020-08-04T06:39:08+09:00
コンテナのアクセスが遅いと感じたので
コンテナにアクセスしてブラウザに表示するまでが遅くて不便だったので
対策をメモdocker-compose.ymlweb: image: nginx:alpine container_name: nginx ports: - '9400:80' depends_on: - app volumes: - ./default.conf:/etc/nginx/conf.d/default.conf:delegated - .:/var/www/html:delegated app: build: ./php container_name: php volumes: - .:/var/www/html:delegated depends_on: - mysqlvolumeにdelegateオプションを付与
- 投稿日:2020-08-04T00:14:50+09:00
Dockerコンテナを止めずにapache2を再起動する方法【php7-apache】
結論
下記コマンドでreloadさせれば、変更を有効化できます。
$ /etc/init.d/Apache2 reload環境
Docker for Windows 19.03.8 DockerImage php:7.4-apache背景
Dockerでローカル環境構築中に困りました。
普段CentOSで開発していると、設定ファイル変更後に有効化させる際、下記のコマンドをたたきたくなるところですが、
この場合コンテナごと停止してしまいます。systemctl apache2[httpd] restartコンテナを止めずに設定変更の有効化をするには下記のコマンドをたたきましょう。
$ /etc/init.d/Apache2 reload