ラベル Docker の投稿を表示しています。 すべての投稿を表示
ラベル Docker の投稿を表示しています。 すべての投稿を表示

2022年6月29日水曜日

【DockerHub】typo して間違った repository に push してしまった Docker image を正しい repository にコピーした

docker に push する先を typo してたまま CI 回しててしばらくずっと間違ったところに push してました。

oneapi が正しかったのに openapi ってなってました。
ここで今までビルドしたイメージを openapi から oneapi の方に移したいなと思ったのですが、これをやる場合 openapi から pull して oneapi に push するだけではあるのですが、すべてのタグでやるのはめんどくさかったのでスクリプトにしました。


./docker-cp-repo.sh srzzumix/openapi-cxx srzzumix/oneapi-cxx

のように使います。
jq 使うと repository のタグ一覧が簡単に取れるので便利です。
今回は以上。では。

2022年3月10日木曜日

Include-What-You-Use の docker image を更新しました

https://hub.docker.com/repository/docker/srzzumix/iwyu/general

表題どおりです。
今まで自分が使うようにイメージを置いといただけでしたが、各 clang バージョン x Ubuntu バージョン x Multi Arch(amd64/arm64) でビルドしておいておきました。
Include What You Use は C/C++ の include の最適化をしてくれるツールです。
過去に記事を書いてますのでそのへんを参考にしてください。
ブログズミ: [C++] Include-What-You-Use で依存関係を確認する


ビルドは GitHub Actions で行っています。
https://github.com/srz-zumix/docker-iwyu 

今後は複数 arch 対応の需要が上がっていく気がしてるので今回から対応してみました。
複数 arch 対応の image をローカルでビルドする場合は、レジストリに push しながらなら OK らしく(ようは実行環境の arch しかローカルビルドできないって感じかな?)勉強になりました。
今まではビルドしたあとにタグつけて push してたのですが、これだと実行環境の arch しか push できなかったため、一度ビルドしたイメージからバージョン情報とかを取り出し、タグを生成してから再度 docker/build-push-action を実行してます。

これらのイメージは定期的にビルドするものでもないので手動トリガーでビルドするようになってます。
一部の組み合わせではビルド失敗したり、clang のインストールできなくて image のビルドに失敗してます。
需要があればちゃんと見てみますので、もしあれば issue に書いてください。

以上。


2021年7月7日水曜日

[Azure Pipelines] DockerHub pull rate limit に対応する

これらのつづき

Azure Pipelines の場合は以下を参考に「Project Settings」の「Service connections」を開き、「Docker Registry」を追加すれば OK です。
Registry Type に DockerHub があるので、それを選択して、ID/パスワード(トークン)をセットします。
Service connections in Azure Pipelines - Azure Pipelines | Microsoft Docs

今回は以上。

2021年5月31日月曜日

Linux版 UnityHub の headless に対応した Docker image

Linux 版 Unity 使いたいので UnityHub CLI でインストールしようと思ったらめんどくさかったので備忘録。

Feedback - Headless Mode Isn't Really Headless - Unity Forum

なにが面倒だったというと、 headless モードが headless モードじゃなくて docker とか VM とかでディスプレイない環境だと起動ができないのです。

こんな感じのエラーで起動できません。

(unityhub-bin:919): Gtk-WARNING **: 08:08:17.580: cannot open display: 

で、xvfb で回避できるのですが、すでに回避策を講じた Docker image を同僚に教えてもらいました。このイメージを使ったら Unity のインストールとかの自動化も簡単にできそうです。
https://hub.docker.com/u/unityci

Dockerfile はこれ
https://github.com/game-ci/docker/blob/main/hub/Dockerfile

中身を読むとわかりますが、AppImage をばらして xvfb-run してます。
ちょっと気になるのは、ばらした AppImage が / に展開されることくらいですかねぇ。
Docker なら、まぁいいかもしれませんがどこかのインスタンスに入れるなら嫌だなぁと思ったので、自分なりに書き直してみました。

書き直し
イメージ

できあがったイメージと Dockerfile はこちらです。
https://hub.docker.com/r/srzzumix/unityhub
https://github.com/srz-zumix/docker-unityhub

書き直してわかったポイント

PR のコメントとして残してあります。

  • unityci/hub image は APPDIR が未定義なため / で実行されていた
  • zenity がないと unityhub-bin 起動後に進まなかった
  • ~/.config/Unity Hub/eulaAccepted ファイルを作成して EULA 確認をスキップ
  • unityhub.desktop ファイルにバージョンが書いてある
  • Mac 版だと -- --headless help のようにオプションを指定するが Linux 版で -- つけると先に進まない

以上、回避策など取らずに使えるようになってくれると嬉しいですね。では。

2021年5月27日木曜日

[Debian] pyenv install で Missing the OpenSSL lib? で失敗する場合の対応と 3.0~3.10 全部入り Dockerfile 書いた

 「Missing the OpenSSL lib?」で検索するといろいろ対策方法が出てきますが、大体ここに書いてあるので自分の環境に合わせて方法を見れば良いと思います。
https://github.com/pyenv/pyenv/issues/950

本記事では「Debian」環境で対処した方法と、pyenv install で 3 系を全部入れてみた Dockerfile を紹介します。

対処方法

libssl-dev をアンインストールして libssl1.0-dev をインストールする。以上。
apt-get remove -y libssl-dev && apt-get install -y libssl1.0-dev

OpenSSL 1.1 に対応してないかららしいですね。
ちなみに 3.10 系は libssl1.0-dev だと逆にダメでした。

全部入り Dockerfile
# development env

ARG VERSION=3.7-stretch
FROM python:$VERSION
ARG VERSION

LABEL maintainer "srz_zumix <https://github.com/srz-zumix>"

SHELL ["/bin/bash", "-o", "pipefail", "-c"]
RUN apt-get update -q -y && \
    apt-get install -y --no-install-recommends \
        make \
        build-essential \
        libssl-dev \
        zlib1g-dev \
        libbz2-dev \
        libreadline-dev \
        libsqlite3-dev \
        wget \
        curl \
        llvm \
        libncurses5-dev \
        xz-utils \
        tk-dev \
        libxml2-dev \
        libxmlsec1-dev \
        libffi-dev \
        liblzma-dev \
        && \
    apt-get remove -y libssl-dev && \
    apt-get update -q -y && \
    apt-get install -y --no-install-recommends libssl1.0-dev && \
    apt-get clean && \
    rm -rf /var/lib/apt/lists/*

ENV PATH="/root/.pyenv/bin:${PATH}"
RUN curl https://pyenv.run | bash && \
    echo "eval $(pyenv init -)" >> ~/.bashrc && \
    echo "eval $(pyenv virtualenv-init -)" >> ~/.bashrc
RUN	pyenv install -s "$(pyenv install -l | grep -e '\s3\.9[^0-9].*' | tail -1 | xargs echo -n)"
RUN	pyenv install -s "$(pyenv install -l | grep -e '\s3\.8[^0-9].*' | tail -1 | xargs echo -n)"
RUN pyenv install -s "$(pyenv install -l | grep -e '\s3\.7[^0-9].*' | tail -1 | xargs echo -n)"
RUN pyenv install -s "$(pyenv install -l | grep -e '\s3\.6[^0-9].*' | tail -1 | xargs echo -n)"
RUN pyenv install -s "$(pyenv install -l | grep -e '\s3\.5[^0-9].*' | tail -1 | xargs echo -n)"
RUN pyenv install -s "$(pyenv install -l | grep -e '\s3\.4[^0-9].*' | tail -1 | xargs echo -n)"
RUN pyenv install -s "$(pyenv install -l | grep -e '\s3\.3[^0-9].*' | tail -1 | xargs echo -n)"
RUN pyenv install -s "$(pyenv install -l | grep -e '\s3\.2[^0-9].*' | tail -1 | xargs echo -n)"
RUN pyenv install -s "$(pyenv install -l | grep -e '\s3\.1[^0-9].*' | tail -1 | xargs echo -n)"
RUN pyenv install -s "$(pyenv install -l | grep -e '\s3\.0[^0-9].*' | tail -1 | xargs echo -n)"

RUN apt-get remove -y libssl1.0-dev && \
    apt-get update -q -y && \
    apt-get install -y --no-install-recommends libssl-dev && \
    apt-get clean && \
    rm -rf /var/lib/apt/lists/*
RUN pyenv install -s "$(pyenv install -l | grep -v 'dev' | grep -e '\s3\.10[^0-9].*' | tail -1 | xargs echo -n)"  

以上。

2021年5月6日木曜日

DockerHub / GitHub Actions での docker build が No space left on device だったので CircleCI でビルドした話

無料になったIntel compilerをCentOS8にインストールしてみる - Qiita
Intel compilerが2021年になってから実質的に無料になってしまったというのを知り、勢いで作ったのが↓のリポジトリ
https://github.com/srz-zumix/docker-icx
(現在は名前変えてます。https://github.com/srz-zumix/docker-oneapi-hpckit
公式がサポートしてない Ubuntu 16.04 で oneAPI のセットアップをしてます。
(intel-basekit と intel-hpckit。パッケージリストはこちらを参照)

DockerHub Automated Build

で、いつもどおり DockerHub の Automated Build でビルドしたんですが、「No space left on device」でビルドできませんでした。


デカイからなぁ・・(上が公式、下が自前)

GitHub Actions でビルド

space を増やすのもめんどくさそうなので、別の CI サービスを使おうと考え、GitHub Actions でビルド、DockerHub に push するようにしてみました。
(とりあえず build までで https://github.com/srz-zumix/docker-icx/blob/main/.github/workflows/dockerhub.yml

「No space left on device」!!
ググると prune しろとか出てきたので試すも変わらず。うーん。

CircleCI ・・・その前に

じゃあ、しょうがないし他のサービスにするか。
というわけで次点で CircleCI !というふうに決めたわけじゃないです。
拙著「あつまれ CI サービス タダではじめる継続的インテグレーション生活」に記載されている各CIサービスの実行環境の空きディスク容量を参考にして小さいサービスを避けて決めました。




これは本から一部抜粋しましたが、GitHub Actions の Linux エージェントは 20GB ほどしか空きがないのでダメなのもなんとなく納得。
CircleCI の Linux machine:true は 90GB ありそうだったので大丈夫やろ、という気持ちで決めました。
CircleCI でビルド

というわけで、CircleCI でビルドしました。
目論見通り成功です!


最後に

作ったイメージはこちらにあります。
https://hub.docker.com/r/srzzumix/oneapi-hpckit
とはいえ、公式のイメージがあるので特に理由(Ubuntu 16.04 じゃなきゃだめとか)がなければそちらを使うのがいいと思います。(↑のは1レイヤーにまとめすぎて pull が遅い…)
https://hub.docker.com/r/intel/oneapi-hpckit

また intel-oneapi-compiler-dpcpp-cpp-and-cpp-classic パッケージだけをインストールしたイメージも作ったのでこちらに置いてあります。
https://hub.docker.com/r/srzzumix/oneapi-cxx
hpc-kit は結構イメージサイズがデカイので、 C++ Compiler だけ欲しい人がそのパッケージだけインストールしたイメージを作ると良さそうです。
私はこちらを Intel C++ Compiler でのビルド・テストに利用したいと思ってます。

今回は以上。ではでは。


2021年4月21日水曜日

docker build ログを今まで通りに表示する

 docker build したときの出力がなんかいい感じにまとめられてコンパクトになりましたね。


でも、RUN した出力を知りたいんじゃ!ってこともあります。
そんなときは docker build --progress=plain で OK




2021年3月18日木曜日

PyPI のリリースを検知して Dockerhub の image を更新する

3rd party の PyPI パッケージのリリースがあったら、自動で Dockerhub のビルドをキックして、latest の更新とバージョンのタグ付けをするパイプラインを構築しました。

できたのはこちら。
https://hub.docker.com/r/srzzumix/lizard
パイプライン
PyPI release の RSS を使い、RPA(Integromat) で定期的に読み取り、更新があったら Dockerhub のビルドトリガー URL を POST します。

Dockerhub のビルドができたら、出来上がったイメージからバージョンを取得してタグ付けをしています。
Dockerhub のビルドでは Dockerfile と同じ階層にある hooks ディレクトリに build や post_push などの shell ファイルを置くことで処理をカスタマイズできるので、post_push でタグ付けするようにしています。
#!/bin/bash
set -eu

if [ "${DOCKER_TAG}" = "latest" ]; then
  LIZARD_VERSION=$(docker run --rm ${IMAGE_NAME} --version)
  docker tag ${IMAGE_NAME} ${DOCKER_REPO}:${LIZARD_VERSION}
  docker push ${DOCKER_REPO}:${LIZARD_VERSION}
fi

これでパイプラインは完成です。

今回は以上です。では。

2021年3月5日金曜日

[Wercker] DockerHub pull rate limit に対応する

 ブログズミ: [CodeShip][Drone.io] DockerHub pull rate limit に対応する
こちらに引き続き、Wercker での対応方法をまとめます。

その前に Wercker は Oracle に買収されてから手付かずな状態なのかと思ってましたが、
Slack コミュニティは生きていて今回の対応方法も Slack コミュニティで知りました。
まだ Wercker 使ってる人は入っておくといいと思います。


DockerHub pull rate limit に対応

では本題の対応方法です。

Box に対しては以下のように box 指定で user/pass を設定します。

box:
  id: python
  username: srzzumix
  password: ${WERCKER_DOCKERHUB_PASSWORD}
  

ステップ内で docker 使う場合は普通にログインすれば OK です。

    - script:
        name: Login DockerHub
        code: |
          echo ${WERCKER_DOCKERHUB_PASSWORD} | docker login -u srzzumix --password-stdin


今回は以上です。
では。

2021年2月17日水曜日

Wekan サーバーの引っ越しで mongoDB のバックアップ・リストアした(docker-compose 編)

 とある事情で Wekan サーバーを引っ越ししました。
docker-compose で立てていたのですが、データベースのバックアップ・リストアをしたときの手順を備忘録として残しておきます。

手順はこちらを参考しました。
Dockerで起動しているMongoDBにリストアする - Qiita

環境

docker-compose はこんな感じです。

元サーバー

version: '2'
services:
  wekan:
    image: mquandalle/wekan
    restart: always
    links:
      - wekandb
    environment:
      - MONGO_URL=mongodb://wekandb/wekan
      - ROOT_URL=http://hogehoge:8088
    ports:
      - 8088:8080
    networks:
       - app_net

  wekandb:
    image: mongo:3.2.11
    volumes:
      - /mnt/sda1/docker/wekan/data:/data/db
      - /mnt/sda1/docker/wekan/configdb:/data/configdb
    restart: always
    networks:
       - app_net

networks:
  app_net:
    ipam:
      config:
        - subnet: 172.XX.XX.X/24
  

network 指定あり、db はホストにマウント済み。

移動先サーバー

version: '2'
services:

  wekan:
    image: mquandalle/wekan
    restart: always
    links:
      - wekandb
    environment:
      - MONGO_URL=mongodb://wekandb/wekan
      - ROOT_URL=http://fugafuga:8088
    ports:
      - 8088:8080

  wekandb:
    image: mongo:3.2.11
    volumes:
      - db_data:/data/db
      - db_config:/data/configdb
    restart: always

volumes:
  db_data:
    external: true
  db_config:
    external: true
  

network はなし。Windows マシンなのでホストにマウントするのがうまくいかないのでボリュームを作ってそこに永続化。

バックアップ

Qiita 記事のリストアコマンドをバックアップコマンドに変更して実行します。
元サーバーはホストに db をマウントしてるのでそこからやってもいいのかもしれませんが、mongodump しました。

また、ネットワーク作ってるのでそれを指定してます。

docker run --rm --link wekan_wekandb_1:mongo -it -v ~/wekan/backup:/backup --network wekan_app_net -w /backup mongo:3.2.11 bash -c "mongodump --host mongo"

backup ディレクトリに出力されてるはずなのでそれを引越し先サーバーにコピー。

リストア

リストアもバックアップ同様に行いました。
こちらはネットワークを指定しませんが docker-compose up すると wekan_default のようにデフォのネットワークが作られるのでそちらを指定します。
(細かいですが Windows 上なのでルートパスの / を2重化してます。この件は「ブログズミ: Docker Toolbox でホストのカレントディレクトリをマウントするときの備忘録」を参照してください。)

docker run --rm --link wekan_wekandb_1:mongo -it -v "/$(pwd)/backup/dump":/backup --network wekan_default -w //backup mongo:3.2.11 bash -c "mongorestore --host mongo /backup"


2021-01-14T08:18:03.435+0000    building a list of dbs and collections to restore from /backup dir
2021-01-14T08:18:03.484+0000    reading metadata for wekan.cfs_gridfs.attachments.chunks from /backup/wekan/cfs_gridfs.attachments.chunks.metadata.json
2021-01-14T08:18:03.484+0000    reading metadata for wekan.cfs_gridfs._tempstore.chunks from /backup/wekan/cfs_gridfs._tempstore.chunks.metadata.json
・・・
2021-01-14T08:18:04.035+0000    finished restoring wekan.customFields (0 documents)
2021-01-14T08:18:05.581+0000    restoring indexes for collection wekan.cfs_gridfs.attachments.chunks from metadata      
2021-01-14T08:18:05.665+0000    finished restoring wekan.cfs_gridfs.attachments.chunks (189 documents)
2021-01-14T08:18:05.666+0000    done

のようにできたら完了です。
移行先の Wekan にアクセスして確認しましょう。

最後に

Wekan は OSS の Trello っぽいやつです。
かなり進化していて WIP 制限とかスイムレーンとかあるので Trello よりも仕事で使えると思います。

便利なんでぜひ使ってみてください。

今回は以上です。


2021年2月12日金曜日

[CodeShip][Drone.io] DockerHub pull rate limit に対応する

DockerHub の pull rate limit への対応方法メモです。
基本的には DockerHub にログインした状態で pull することになると思います。
ログイン情報のパスワードには DockerHub の設定から API トークンを発行しそれを設定します。


ただ、このユーザー/パスワードを各 CI サービスに適用する方法はサービスによって違います。今回は CodeShip と Drone.io の設定を紹介したいと思います。

CodeShip の場合

CodeShip Pro の場合です。 Basic の場合はコマンドの中で docker login コマンドを実行する方法になると思います。

Using Docker Image Registries | CloudBees Docs
上記リンク先のドキュメントに設定方法が記載されています。

手順としては大きく分けて2つで、Dockerconfig.json の用意とリポジトリ/ YAML の設定になります。

Dockerconfig.json の用意

まず DockerHub にログインするための config.json を生成します。

{
    "auths": {
        "https://index.docker.io/v1/": {
            "auth": "your_auth_string",
            "email": "your_email"
        }
    }
}  

json ファイルの中身は上記のようなものになります。
この json ファイルは docker login したら $HOME/.docker/config.json に保存されるものを使えばよいのですが、macOS の場合保存場所が keychain になっているため、下記方法で取得します。公式ドキュメントでは「Docker Credentials On Mac OSX」のあたりです。

まずは以下のような credentials.evn ファイルを作成します。
USERNAME/PASSWORD は適宜埋めてください(PASSWORD には API TOKEN)

DOCKER_USERNAME=...
DOCKER_PASSWORD=...
DOCKER_REGISTRY=https://index.docker.io/v1/
  

続いて、以下のコマンドを実行します。

mkdir ./dockercfg
docker run -it --rm \
    --env-file=credentials.env \
    -v "$(pwd):/opt/data/" \
    -v "/var/run/docker.sock:/var/run/docker.sock" \
    codeship/dockercfg-generator /opt/data/dockercfg

すると、カレントディレクトリ/dockercfg/ に config.json が出来上がります。

リポジトリ / YAML の設定

config.json が出来上がったらそれをシークレットファイルにして、CI 環境が読み込むように YAML に設定をします。

シークレットファイルの作成のためにプロジェクトの設定ページから codeship.aes をダウンロードしてください。リポジトリのルートに配置したら不用意に commit してしまわないように .gitignore に追加しておきましょう。

aes を配置したら以下のコマンドを実行します。パスは適宜変更してください。

jet encrypt dockercfg/config.json dockercfg.encrypted

出来上がった .encrypted ファイルは git add/commit します。

続いて YAML の設定をします。
追記するのは codeship-steps.yml ファイルの方です。
以下のように encrypted_dockercfg_path を追加してください。

- name: spec
  service: gcc
  command: /work/build.sh
  encrypted_dockercfg_path: ./dockercfg.encrypted
動作確認

これで設定は以上です。変更を commit/push して動作確認してみましょう。
うまく設定できていれば DockerHub の Token 一覧画面で最終アクセス日時が更新されるはずです。

Drone.io の場合

Images | Drone
Drone の公式ドキュメントはこちらです。

CodeShip と同じように Dockerconfig.json ファイルを作成し、それを drone のシークレットファイルとして CLI から登録します。
iutest で生成用に用意した Makefile があるので参考にしてください。
https://github.com/srz-zumix/iutest/tree/master/.ci/drone

json ファイルを作成したら以下のコマンドで登録できます。

	drone secret add --repository srz-zumix/iutest \
		--name dockerconfig \
		--data @dockerconfig.json

シークレットファイルをアップデートする場合は update サブコマンドを使います。

	drone secret update --repository srz-zumix/iutest \
		--name dockerconfig \
		--data @dockerconfig.json

PR でもこのシークレットファイルを利用可能にする場合は --allow-pull-request オプションを追加してください。
シークレットファイルを登録したら以下のように、このファイルを使用するように YAML の設定をします。

kind: pipeline
name: test

image_pull_secrets:
  - dockerconfig

steps:
...


image_pull_secrets に指定するのは secret add/update したときに指定した --name オプションの名前です。

動作確認

設定は以上です。
CodeShip と同様にトークンが利用されたかどうかを確認しましょう。

まとめ

今回対応した CodeShip/Drone どちらも Dockerconfig.json ファイルをシークレットに用意してそれを環境に読ませる方法でした。

最初 Drone の方は

echo -n '<ユーザ名>:<アクセストークン>' | base64

の結果を auth に設定していて、それではうまくいかなくて手こずっていたのですが、CodeShip のやり方を知って助かりました。
(Mac 環境で base64 してるのが原因?)

ともあれ、CodeShip や Drone と同様に Docker の config.json を使った login をする CI サービスではこの方法が使えそうです。

今回は以上です。

2021年2月1日月曜日

古い gcc が欲しくて CentOS 5 の docker image を作った話

はじめに
なぜ古い GCC が必要になったのか?
個人開発している iutest では古の環境でもなるべく使えるように頑張りたいなーという気持ちがあります。(なんかこう制約をかいくぐってなんとかするの楽しいし)
Google Test の最新版で C++11 が要求されるようになったこともあり、今後昔の言語バージョンをサポートするライブラリは減っていくのかなーと思います。
当然、新しい言語バージョンを使っているのなら、そのバージョンをターゲットとしたライブラリのほうが効率が良いと思います。
iutest でももちろんなるべく新しい言語バージョンの機能を取り込んでいくつもりです。

ここで問題になってくるのはテストです。
今までは古の環境を想定して、iutest 側で言語機能がないと Config をセットしてテストしていました。
ライブラリ内部での undefined とかシンタックスエラーはこれでも検出できるのですが、やはり「ないと仮定」しても「実際にはある」ので、実は対応してなかったってのがいくらでも出てきちゃいます。

そんな感じで、一応サポートする気持ちはあるけどテストはできる限りという状態だったため、テストのカバー範囲を広げるために日々 OS やコンパイラのテスト環境を増やしている次第です。

なぜ CentOS 5 なのか?
はじめに、古い GCC が欲しいと思ったときに Ubuntu のパッケージからできるだけ古いものをインストールしようとしました。
しかし、そこまで古いものは取ってこれませんでした。

つぎに、ソースコードからビルド・インストールすることを試しました。
こちらはなかなかビルドが通らない、あと古い環境だと認証通らなくて(GPG key とか)必要な依存物が取ってくるのも大変でした。
(H8 クロスコンパイラはネット上の情報から作ることはできましたが)

で、CentOS の古いバージョンなら取ってこれるんじゃないとアドバイスもらったところ、本家のパッケージは EoL で取ってこれなかったのですが、アーカイブがあってそこからすんなりインストールすることができました。

と、いうわけで以下。そのときの手順をまとめます。

完成形 Dockerfile
その前に先に完成した Dockerfile を載せておきます。
以下、説明の参考にしてください。



CentOS 5 で gcc 3.4.6 と pyenv を使う
Python 3 系も使いたかったので pyenv のインストールまでしました。
GCC のインストールよりもこっちが大変だった。
では、見ていきましょう。

COPY CentOS-Base.repo /etc/yum.repos.d/CentOS-Base.repo
まず、CentOS 5 は既に EoL なのでリポジトリファイルを編集して、アーカイブされたパッケージを参照するように変更します。

ネットの力を借りて、それっぽく動くようにはなりましたが、「libselinux」でエラーになってしまいました。
↑の変更に加えて「libselinux」の変更も必要みたいだったので、↓を参考に設定。
無事に yum update できるようになりました。
gcc 3.4.6 のインストール
RUN yum update -y && \
    yum -y install epel-release && \
    yum install -y make gcc g++ nkf wget perl gettext libffi-devel \
        compat-gcc-34-3.4.6-4.1.x86_64 compat-gcc-34-c++-3.4.6-4.1.x86_64
gcc 3.4.6 のインストールはこのレイヤーで終わりです。
ポイントは↑のレイヤーで対応した、パッケージ参照先の変更だけです。

アーカイブされたパッケージ群から gcc と g++ をインストールしています。
pyenv のインストール
↑の方法では Python 3 系をインストールできなかったので pyenv 使って 3 系を使えるようにしました。
というわけで、pyenv のためにいろいろソースビルドしました。
以下の記事を参考にして、ソースビルド・インストールができました!ありがとうございます。

最後に
過去のものをビルドして使うのは大変だなと学びました。
そして、そういったものを Docker image にしておくことで少しでも苦労から開放されるなーと思いました。
Docker 素晴らしい。

今回作ったイメージは DockerHub にアップしてあります。
では。











2020年12月14日月曜日

[DockerHub] AutomatedBuild でバージョンタグを自動でつける

DockerHub のイメージを見てるとタグがいっぱいついてるリポジトリがありますよね。
あとは latest が最新バージョンのタグと同じになってたり、Ubuntu の xeinal -> 16.04 みたいに名前付けされてたり、バージョンがメジャー、マイナーまでになっていてそのバージョンの最新を指していたり(例: v1 -> v1.3 -> v1.3.2)、とか。



こういうのを AutomatedBuild 管理するのは面倒くさそうだなと思ってましたが、そんなことはありませんでした。

hooks で AutomatedBuild をカスタマイズできる
DockerHub AutomatedBuild では Dockerfile と同じディレクトリに hooks ディレクトリを作成し、post_build や post_push ファイルを配置することでビルドをカスタマイズできます。カスタマイズできるポイントは↑の公式ドキュメントを参照してください。

post_build や post_push では bash スクリプトを書くことができ、docker コマンドも使用できます。ビルドしたイメージを実行したり、AutomatedBuild で設定したタグ以外をつけたりできます。

バージョンタグを自動でつける
post_build のタイミングでビルド済みのイメージを実行し、バージョンを取得すればタグ付けが自動化できます。
 
#!/bin/bash
# post_build
VERSION=$(docker run --rm ${IMAGE_NAME} --version)
docker tag ${IMAGE_NAME} ${DOCKER_REPO}:${VERSION}
docker push ${DOCKER_REPO}:${VERSION}
最後に
とあるツールをインストールした Docker イメージを作ることがちょくちょくありますが、ここれからは hooks 使って管理楽ちんにしたいと思います。

ではでは。

2020年11月2日月曜日

Docker login しているか確かめる方法

前置き

 ダウンロードレート制限 | Docker ドキュメント

いよいよ DockerHub の Download Rate Limit が始まりましたね。
この制限は徐々に導入していくとありますが、さてどんな状況でしょうか?
(この記事は 11/1 に書いています)

特に懸念されていたのは CI サービスでの制限です。
DockerHub にログインしていない場合は IP に対して制限がかかるため、利用者の多いサービスではあっという間に上限越えて、制限がかかってしまうことが予想されました。
これに対し、すでに(期限付きではありますが)制限を受けないようにする交渉が完了しているサービスもあります。

DockerHub による2020/11からのコンテナイメージ Pull 回数制限のCircleCIへの影響 - Build Environment - CircleCI Discuss

ある程度猶予があるかもしれないですが…
何れにせよ、今後 DockerHub からイメージを pull して CI を回す場合は、事前に DockerHub へのログインをするようにパイプラインを更新しておくのが良さそうです。

それらへの対応方法についても、記事冒頭のドキュメントからリンクが貼られていたり、各 CI サービスから案内が出ていると思います。

筆者が開発している C++ テスティングフレームワークの iutest はめちゃくちゃたくさん CI サービスを使っているので(Docker 関係ないものもあるので全部ではないが)絶賛対応中です。

対応方法はログインするだけなんですが、各サービスやり方が異なるのでここでは対応方法は省略します。
一応、状況はこちらの issue で確認できます。
https://github.com/srz-zumix/iutest/issues/519

Docker login しているか確かめる方法

で、ようやく本題。
このログイン対応をしていて思ったのは、「設定したけど本当にログインした状態で pull できているのかをどう確認したらわからなくて不安」でした。

docker のコマンドに「それ」を確認するものがあればよかったのですが、なさそうだったので以下の方法で確認しました。

echo a | docker login

ログイン済みなら以下のように成功となります。

$ echo a | docker login
 Authenticating with existing credentials...
 Login Succeeded
$ echo $?
 0
ログインしてない場合は以下のように失敗になります。
$ echo a | docker login
 Error: Cannot perform an interactive login from a non TTY device
$ echo $?
 1
最後に
この方法をパイプラインに組み込んでみてないので、うまく CI 上で確認できるか未確認ですが、もっと簡単に確認できると嬉しいなと思います。もっと良い方アレば教えて下さい。
てか、直球なコマンドが欲しい。。

2020年10月12日月曜日

OpenSTF を Windows の Docker 上で動かす

CEDEC での講演もあって OpenSTF を使い始めた人も多いようなのでメモ。



講演でもお話ありましたが、 OpenSTF は DeviceFarmer に変わったそうですね。 (DeviceFarm と似てて検索とかしづらそう) 

OpenSTF のセットアップについては以下の記事が参考になります。

筆者もネットの情報を参考に立ち上げました。

OpenSTF 便利
OpenSTF はリモート操作のためのツールの印象が強いですが、開発者がローカルで実機確認するときにも便利です。
なぜなら、わざわざ端末を操作して社内システムにログインするためのユーザーID/パスワードの入力が必要なかったり、スクリーンショットも簡単に PC 側で取れちゃうからです。

Docker の勉強がてらローカル環境に立ててみることをオススメします。

docker-compose.yml と起動手順
使っている docker-compose.yml がこちら。コメントに手順も書いてます。


メモ
Windows でボリュームマウント
Windows だとホストマシンでマウントできる場所が限られてたりして面倒くさかったので、ホストマシンに DB の永続化をするのではなく、docker volume create したボリュームに永続化するようにしてます。(今はなんか Docker Desktop がいい感じにマウントできるようにする?って聞いてくれるので面倒くささ減ったみたいだけど)
端末が認識しない場合
adb サーバーが起動してないかも。
adb start-server をしてみてください。

端末を返却した際にインストールしたアプリをアンイストールしないようにする
デフォルト設定だと、OpenSTF で端末操作して返却するとその間の変更がクリーンナップされます。これはこれで便利なのですが、個人環境で利用する場合は不便にもなります。
クリーンナップしなくない場合は stf の起動オプションに  --no-cleanup を追加しましょう。
使ってみて困っていること・知りたいこと
たまに操作できない状態になる
USBの抜き差しで復旧したりするが、リモートワークな昨今、物理的な挿抜は難しい。
adb kill-server / start-server で復旧したりもする。
リモートで電源の通電操作が可能な機材(リブーター)が存在するので、それを使って AC 給電な USB-HUB の電源切断で、USB 挿抜をエミュレートできないかと思っている。(未検証)

ポートフォワーディング機能の使い方
端末上で実行しているアプリと特定ポートでお話できるかな?と思っているのだが、うまくいってない。機能を勘違いしているのかもしれないし、使い方・設定の問題かもしれない。

最後に
利用者が増えて知見が増えていくと嬉しいですね。
Airtest も便利なんでそっちも情報増えると嬉しい。(Android 10 になって minitouch 使えなくてツラミ)
以上。

2019年10月23日水曜日

Windows Docker toolbox (VirtualBox) で USB 接続を使う

OpenSTF を使ってみようと思って、Windows + Docker toolbox 環境でやってみようとしたところ、すんなりいかなかったのでメモ。

USB コントローラーを有効にする(VirtualBox)
まずは、
docker-machine stop default
で VM を停止します。



USB を認識させるために VirtualBox Manager の設定から「USBコントローラーを有効」にチェックをいれ、コントローラーを選択します。


設定はこれで以上の場合もありますが、Docker toolbox を起動した際に以下のようなエラーになった場合は追加のインストールが必要です。
Starting "default"...
(default) Check network to re-create if needed...
(default) Windows might ask for the permission to configure a dhcp server. Sometimes, such confirmation window is minimized in the taskbar.
Unable to start the VM: C:\Program Files\Oracle\VirtualBox\VBoxManage.exe startvm default --type headless failed:
VBoxManage.exe: error: Implementation of the USB 3.0 controller not found!
VBoxManage.exe: error: Because the USB 3.0 controller state is part of the saved VM state, the VM cannot be started. To fix this problem, either install the 'Oracle VM VirtualBox Extension Pack' or disable USB 3.0 support in the VM settings (VERR_NOT_FOUND)
VBoxManage.exe: error: Details: code E_FAIL (0x80004005), component ConsoleWrap, interface IConsole

Details: 00:00:01.074731 Power up failed (vrc=VERR_NOT_FOUND, rc=E_FAIL (0X80004005))
Looks like something went wrong in step ´Checking status on default´... Press any key to continue...
VirtualBox Extension Pack をインストールする
VirtualBox のサイトから Extension Pack をダウンロードしてインストールするだけで良いのですが、現在使用している VirtualBox の Version と同じバージョンの Extension Pack をインストールする必要があるので注意してください。


自分の環境では 5.2.8 だったので、「Download_Old_Builds – Oracle VM VirtualBox」から 5.2.8 の Extension Pack をダウンロードしました。



ダウンロードしたら、あとはインストールするだけです。
(バージョンが違うとインストールに失敗します)



これで、Docker toolbox で USB を使う準備が整いました。
今回は以上です。それでは。

2019年10月16日水曜日

Docker toolbox QuickStart ショートカットを起動したときに history にゴミが溜まるのを抑制する

Docker toolbox の QuickStart でシェルを立ち上げると、ものすごい量の history が溜まって邪魔だったので対策しました。





設定でできること
HISTCONTROL
HISTCONTROL 環境変数をセットしておくと、空白から始まるコマンドや重複するコマンドを履歴に残さないようにできます。

  • ignoredups
    直前と同じコマンドの場合は保存しない
    commandhistory
    ls
    ls
    ls
    ls
    ls -a
    ls
    ls
    ls -a
    ls
  • ignorespace
    空白から始まるコマンドは保存しない
    commandhistory
    ls
    ls
    ls
    ls
    ls -a
    ls
    ls
    ls -a
    ls
  • ignoreboth
    ignoredups + ignorespace
  • erasedups
    重複するコマンドは最新のものだけが保存される
    (履歴にある重複コマンドは削除される)

自分は以下のようにしました。
export HISTCONTROL=ignoreboth

HISTIGNORE
HISTIGNORE に履歴に残したくないコマンドを列挙できます。
コマンドとコマンドの区切り文字は ':' です。

自分は以下のようにしました。
export HISTIGNORE=history:echo:'#*'

設定だけでは限界がある・・
上記の設定をしても、すこしだけ残ってほしくない履歴が減るくらいです。
自分でコマンド打つときにも便利な設定なので、しておいて損はないですが、当初の目的はこれだけでは達成できません。

というわけで、次に続きます。





start.sh を書き換える
できれば外部から非侵入的に解決したかったのですが、自分の知識ではここまでが限界でした。
Docker Toolbox のインストールディレクトリ「C:\Program Files\Docker Toolbox」に start.sh があります。
ショートカットはこちらの .sh を呼び出しており、こちらを少し書き換えることで対策しました。

ファイルの先頭で set +o history をして履歴を無効にします。
※ここで set コマンドの前に1つスペースを上げていることに注意。最初の設定で空白で始まるコマンドを履歴に残さないようにしたので
set +o history
#!/bin/bash
 set +o history

そして、ファイルの末尾あたりで set -o history で履歴を有効にします。
bash の呼び出しあたりは先頭空白を入れて、HISTCONTROL による抑制が効くようにしました。
set -o history

 if [ $# -eq 0 ]; then
   echo "Start interactive shell"
   exec "$BASH" --login -i
 else
   echo "Start shell with command"
   exec "$BASH" -c "$*"
 fi


最後に
これで設定は以上です。
きれいになりました。

2019年3月11日月曜日

Codacy は Dockerfile の検証もしてくれてた

Codacy
Python とか Ruby とかの静的解析をしてくれるサービスは多いですが、Dockerfile も見てくれているとは!
Codacy というか Hadolint



1.13以降はMAINTAINERの代わりにLABELを使うようにしよう - Qiita
MAINTAINER じゃなくて LABEL maintainer "srz_zumix <...>" のようにするとイイらしいっす!









あ、 Visual Studio Code でも出てた


Dockerfile の書き方でこうしたほうがいいよってのがわかるので便利ですね!

2018年8月14日火曜日

依存ライブラリの GitHub を Travis CI で定期的に監視して DockerHub Automate Build を実行する(+ Codefresh ジョブを Trigger)

目的
開発中のソフトウェアがなんらかのソフトウェアに依存しており、その依存しているソフトウェアの最新の状態を常に追いたい。
具体的には、筆者が開発中の C++ テスティングフレームワーク iutest は、Google Test との互換性のために常に Google Test の最新の状態と互換性テストを行っています。

iutest では Travis CI や Circle CI といった CI サービスを利用して、変更があるたびにテストが行われる環境が整っています。
しかしながら、iutest は毎日更新があるわけではなく、最近は開発スピードも落ちているので数日変更がないこともザラです。
そのため、その間に Google Test に更新があって、いつの間にか互換性テストが通らない状態になっていたりすることがありました。

長くなりましたが、今回のゴールは
・ Google Test の更新を定期的に監視して
・ 変更があったら Docker image を更新
・ Docker image が更新されたら互換性テストが実行される
です。

構成

* 監視されるリポジトリ→ google test
* 監視するリポジトリ→docker-googletest


DockerHub Automate Build
DockerHub で Google Test の入ったイメージを作成するジョブは以下の記事で作成したものを使用します。
ブログズミ: DockerHub Automated Build を使ってみた

今回はこちらの latest イメージを毎日最新の状態にするのが目的です。
DockerHub に定期ビルド機能があればそれで良かったのですが、ないので別のサービスで実現させます。

次へ進みます。

CI の設定
必要なのは、定期ビルドが可能で、GitHub に push できるサービスです。
今回は Travis CI を使いましたが、選んだ理由は最近 GitHub push をここでやったからです。
実際使用している yml はこちらです。こちらを見ながら説明していきます。
dist: trusty
sudo: false
language: cpp

before_script:
  - git clone https://github.com/google/googletest.git ./gtest
  - cd ./gtest
  - git rev-parse HEAD > ../gtest.hash
  - cd ..

script:
  - git checkout master
  - git add -A
  - git commit -m "update head [ci skip]" || true
  - git push https://${GITHUB_TOKEN}@github.com/${TRAVIS_REPO_SLUG}.git ${TRAVIS_BRANCH}

env:
  global:
    secure: OdxIMgUsZyGyOOnV49MkJW5KrGVW7KyCwUkWgC88YmdJPCtNJ9fF69TcM8ek252+yFJsfpUrZaNH6A6igRUreveoA161zy+fsD9mMqIrrthFWx5S2fzBCsiCobreduicCDt5EJ1p8N/QlpEB2ZeUbYWqZf37r5BfYOJI86521qYMiI30IAwxsjPqhcbyFRisTKosd3LlEo4Y+K3qLgdCKEAhsaOrtIgrbxz7cM2sKh8lYTquP1XPtFwsmCoELyeRAVEJbSwADcaw3011S/NB8Kn9+sd878dxBK2iDxSilVz+3XIz+/sKZHNFGug5i2UA2yS8ZfWQhZjF9tiF3quTAzqAFzTbxDKswMLHgD8oI0saIVDmXNxc6PXLYXEjx5p5Z3E1iTb09hcp5wOqJOz+Ynie7EkVyUO2DKJhjeuGffoPxjK35L4c7/ufTNskT3+vUnGG/2U9XMA3OeXoCLp+V7BRgkZtpVZssA4viTWXPG4byaEQaiAMK0ArVOesa86m21xuKSLhdNqQ/WRT8g/eEVqs4XrT1ogIW1nsjYHv6Xmcs8QD2iQxDdWHx4pQojod8lSdwn/HFqXTOf6KxqTk5mpJmcd2ZxyDocynTEtvtt+uNtVyJh+gXt06eGD/rlbV1eC+Uc5FMQE2P1Uya3RdaZvMZjYGzVcZMrPcv/gklbY=

Google Test の更新検知
まずは肝心の Google Test (監視される側)の更新検知方法です。
いろいろやり方はあると思いますが、今回は push があるたびにトリガーするのではなく、定期的に(1日1回とか)更新があったかどうかがわかればいいので、定期ビルド実行したときの Google Test の HEAD の commit hash を自分のリポジトリに保存する方法を取りました。
更新があれば diff が出るので、これをトリガーにしています。
これを行っているのが、brfore_script の部分になります。

更新を push して他サービスをトリガーする
最新の commit hash を取得したら、それを commit/push します。
docker-googletest (監視する側)のリポジトリが更新されるので、この push をトリガーに他のサービスをキックすることができます。
監視する側のリポジトリは自身の管理下のはずなので、ここから先は自由にやることができます。

ただし、ここで注意点があります。
Travis CI のジョブもこの push をトリガーにより実行されてしまいます。
すると、この Google Test 監視ジョブが再実行されてしまい、最悪の場合は無限にジョブをキックし続けます。(監視される側の更新が止まれば止まるが、最低でも1回無駄にジョブが走る)

定期ビルド設定
最後にこれを定期ビルドするようにしましょう。
こちらは Travis CI の Web ページで設定します。
プロジェクトのページの「More options」から「Settings」を開くと、一番下に Cron Jobs があります。



DockerHub Automate Build の設定
特に必要ありません。
Google Test が更新されると、commit hash が更新されて push されるのでそれをトリガーにビルドが実行されます。

おまけ
ここまでで、当初の目的の GitHub の監視と、変更検知し DockerHub のビルドを回す、という目的は達成していますが、ついでなので、その先も紹介します。

Slack 通知
通知系は定番ですね。詳しくは過去にも記事にしているので、そちらを見てくださいmm
ブログズミ: Dockerhub Automated Build が終わったら Slack に通知する

docker-googletest の通知仲介は Zapier を使ってますが、今は Integromat もおすすめです。
そちらも記事にしているので、よければご覧ください。私的には、今後は IFTTT/Zapier よりも Integromat をメインに使っていくつもりです。

* 「ブログズミ: プレビュー "(WIP)依存ライブラリの GitHub を Travis CI で定期的に監視して DockerHub Automate Build を実行する(+ Codefresh ジョブを Trigger)"
* 「ブログズミ: CIサービスの結果を Twitter に投稿する

Codefresh のジョブを Dockerhub からの Webhook で実行する
Codefresh のトリガーに Webhook トリガーを追加します。
プロジェクトの「Pipeline」ページの真ん中あたりに「Triggers」があるので、そこで追加していきます。


「ADD TRIGGER」ボタンを押すと以下のようなウィンドウが出てくるので、「REGISTRY」を選択して次へ


続いて、「REGISTRY PROVIDER」を Dockerhub に、「NAMESPACE」と「NAME」はトリガーを発行したい Dockerhub のリポジトリを設定してください。
「ACTION」は Image 更新したときにしたいので、 「Push Image」を選択。docker-googletest にはバージョンごとのタグが複数あり、ビルド対象にしたいのは latest だけだったので、「Configure filter」を設定しました。
入力完了したら、「NEXT」ボタンを押します。


四角く囲ったところに、Webhook の URL と鍵が発行されますので、Dockerhub の Webhook に設定します。(下線のリンクから飛べます)


Dockerhub の Webhook 設定を開いたら、${ENDPOINT}&secret=${SECRET KEY} を入力します。(↑の黄色で囲った部分に出てるアドレスです)



これで完成です。


最後に
外部の依存・関係しているプロジェクトが、いつの間にか更新されていて動かなくなっていた。なんてことはよくあることなので、定期的に監視しておくのはいいことだなと思いました。
あと、この仕組がわりといい感じに組めた気がするので、iutest の Google Test 互換性テストを外部に出す対応に利用しようと思います。
では。