Skip to content

Instantly share code, notes, and snippets.

@TakesxiSximada
Last active June 28, 2020 22:14
Show Gist options
  • Save TakesxiSximada/fc55c113dee57de338010f1bd831917f to your computer and use it in GitHub Desktop.
Save TakesxiSximada/fc55c113dee57de338010f1bd831917f to your computer and use it in GitHub Desktop.
Register the application as initial data in Errbit
# Environment variables for demo application (Errbit client application).
#
AIRBRAKE_API_KEY=3ea6b9dcca72fe35e30dea8141031000
AIRBRAKE_ENVIRONMENT=local
AIRBRAKE_HOST=http://127.0.0.1:8080/
AIRBRAKE_PROJECT_ID=1
HOSTNAME=ng2.local
# Environment variables for Errbit container.
#
ERRBIT_ADMIN_EMAIL=admin@example.com
ERRBIT_ADMIN_PASSWORD=testing1234
ERRBIT_ADMIN_USER=admin
RACK_ENV=production

Register the application as initial data in Errbit

This is an example to register the app in Errbit in advance, doesn’t use bundle exec rake errbit:demo.

Execute the following command to start the container::

docker-compose up

You can access the Errbit launched in local using the following information.

URLhttp://127.0.0.1:8080
Emailadmin@example.com
Passwordtesting1234

Errbit has already registered the test application.

Register error in Errbit using sample code

Prepare python environment for execution.

python3 -m venv .venv
source .venv/bin/activate
pip install -r requirements.txt

Execute sample code(main.py).

python main.py

You can confirm that the error has been registered in Errbit.

{"_id":"5ef7254d96bdea0015b5a860","notify_on_errs":true,"email_at_notices":[1,10,100],"name":"testing","repository_branch":"","github_repo":"","bitbucket_repo":"","asset_host":"","current_app_version":"","notify_all_users":false,"api_key":"3ea6b9dcca72fe35e30dea8141031000","updated_at":{"$date":"2020-06-27T10:54:05.532Z"},"created_at":{"$date":"2020-06-27T10:54:05.532Z"},"issue_tracker":{"_id":{"$oid":"5ef7254d96bdea0015b5a861"},"options":{},"type_tracker":"none"},"notification_service":{"_id":{"$oid":"5ef7254d96bdea0015b5a862"},"notify_at_notices":[0],"_type":"NotificationService"},"notice_fingerprinter":{"_id":{"$oid":"5ef7254d96bdea0015b5a863"},"error_class":true,"message":true,"backtrace_lines":-1,"component":true,"action":true,"environment_name":true,"source":"site"}}

開発メモ

Errbitとは

Errbitは他のアプリケーションからエラーを収集して管理するためのツールです。 Airbrake APIに準拠しおりAirbrakeのダミーサーバーとして気軽に使えます。

事前準備

初期ユーザーの作成

bundle execコマンドを使って初期ユーザーを作成します。

bundle exec rake errbit:bootstrap
Notice: no rspec tasks available in this environment
Overwriting existing field _id in class App.
Seeding database
-------------------------------
Creating an initial admin user:
-- email:    errbit@errbit.example.com
-- password: qFAlW7av8lGL

Be sure to note down these credentials now!

出力に初期ユーザーのメールアドレスとパスワードが表示される。

環境変数

以下の環境変数を設定できる。

環境変数意味
AIRBRAKE_API_KEYAirbrakeが発行するAPIキー6dcc9b2ec85e47e14cc420b52ccdae7a
AIRBRAKE_ENVIRONMENT実行している環境名local
AIRBRAKE_HOSTAPIの送信先http://127.0.0.1:8080/
AIRBRAKE_PROJECT_IDAirbrakeが発行するプロジェクトID1
HOSTNAME実行しているホスト名ng2.local

テストコードの実行例

Python

python main.py

Errbitのアプリケーションを初回起動時に登録する

初回起動時にアプリケーションを登録する

localの開発時やC/IではあらかじめerrbitのAPI Keyを発行しておきたい。 API Keyを発行するにはErrbitにアプリケーションを登録しておく必要がある。

Docker Imageではdemoアプリの作成はエラーする

Docker Imageで起動した場合、コンテナ内で次を実行しても失敗してしまう。

# bundle exec rake errbit:demo
bundle exec rake errbit:demo
Notice: no rspec tasks available in this environment
Overwriting existing field _id in class App.
rake aborted!
LoadError: cannot load such file -- fabrication
/usr/local/bundle/ruby/2.5.0/gems/activesupport-4.2.11.1/lib/active_support/dependencies.rb:274:in `require'
/usr/local/bundle/ruby/2.5.0/gems/activesupport-4.2.11.1/lib/active_support/dependencies.rb:274:in `block in require'
/usr/local/bundle/ruby/2.5.0/gems/activesupport-4.2.11.1/lib/active_support/dependencies.rb:240:in `load_dependency'
/usr/local/bundle/ruby/2.5.0/gems/activesupport-4.2.11.1/lib/active_support/dependencies.rb:274:in `require'
/app/lib/tasks/errbit/demo.rake:4:in `block (2 levels) in <top (required)>'
/usr/local/bundle/ruby/2.5.0/gems/rake-13.0.1/exe/rake:27:in `<top (required)>'
/usr/local/bundle/gems/bundler-2.1.2/lib/bundler/cli/exec.rb:63:in `load'
/usr/local/bundle/gems/bundler-2.1.2/lib/bundler/cli/exec.rb:63:in `kernel_load'
/usr/local/bundle/gems/bundler-2.1.2/lib/bundler/cli/exec.rb:28:in `run'
/usr/local/bundle/gems/bundler-2.1.2/lib/bundler/cli.rb:476:in `exec'
/usr/local/bundle/gems/bundler-2.1.2/lib/bundler/vendor/thor/lib/thor/command.rb:27:in `run'
/usr/local/bundle/gems/bundler-2.1.2/lib/bundler/vendor/thor/lib/thor/invocation.rb:127:in `invoke_command'
/usr/local/bundle/gems/bundler-2.1.2/lib/bundler/vendor/thor/lib/thor.rb:399:in `dispatch'
/usr/local/bundle/gems/bundler-2.1.2/lib/bundler/cli.rb:30:in `dispatch'
/usr/local/bundle/gems/bundler-2.1.2/lib/bundler/vendor/thor/lib/thor/base.rb:476:in `start'
/usr/local/bundle/gems/bundler-2.1.2/lib/bundler/cli.rb:24:in `start'
/usr/local/bundle/gems/bundler-2.1.2/exe/bundle:46:in `block in <top (required)>'
/usr/local/bundle/gems/bundler-2.1.2/lib/bundler/friendly_errors.rb:123:in `with_friendly_errors'
/usr/local/bundle/gems/bundler-2.1.2/exe/bundle:34:in `<top (required)>'
/usr/local/bundle/bin/bundle:23:in `load'
/usr/local/bundle/bin/bundle:23:in `<main>'
Tasks: TOP => errbit:demo
(See full trace by running task with --trace)

パッケージを入れれば動きそうではあるが bundle install --with=test をしても Docker Image内にGCCやGNU Makeがないためビルドに失敗してしまう。 それらを apk add を使ってインストールすると今度はlinkerでエラーするようになってしまった。

MongoDBのデータをexportしておく

mongoexport -d errbit -c apps > data.json

初期データをMongoDBに登録する

MongoDBの公式のDocker Imageは /docker-entrypoint-initdb.d に配置されているshとjsを読み込む仕組みになっている。 https://github.com/docker-library/mongo/blob/be3c690cae52447831b977dab9c6a66dc993df65/3.6/docker-entrypoint.sh#L214-L219

そこで次のスクリプトを /docker-entrypoint-initdb.d に配置して初回起動時にデータを投入するようにした。

投入するデータはJSON形式で配置した。

データが取り込まれるとアプリケーションが作られており投入したAPI Keyが使えるようになっている。 この例では次の値が使用可能となる。

プロジェクトID1
API Key3ea6b9dcca72fe35e30dea8141031000

なぜ bundle exec rake errbit:demo を使わなかったのか?

公式のDockerイメージで起動したコンテナ上で bundle exec rake errbit:demo を使うためには依存ライブラリをインストールする必要がある。

参考

パッケージを入れれば動きそうではあるが bundle install --with=test をしてもDocker Image内にGCCやGNU Makeがないためビルドに失敗してしまう。 それらを apk add を使ってインストールすると今度はlinkerでエラーするようになってしまった。

例えばこれがうまくできたとしてもC/Iに組み込みたいので起動時に依存パッケージを毎回インストールすることは避けたい。 また自分で環境の整ったDockerイメージをホスティングすることもできるが、今回やりたいことは初期アプリケーションを登録することだけでありErrbitの挙動を拡張する必要はない。 そのためだけに自分用のDockerイメージをホスティングすることはしたくない。これ以上自分で管理するものを増やしたくない。

version: "3.8"
services:
errbit:
image: errbit/errbit:v0.9.0
ports:
- "8080:8080"
command: sh /entrypoint.sh
volumes:
- ./entrypoint.sh:/entrypoint.sh
depends_on:
- mongo
env_file:
- ./.errbit.env
environment:
- MONGO_URL=mongodb://mongo:27017/errbit
mongo:
image: mongo:4.1
volumes:
- ./initial_data.sh:/docker-entrypoint-initdb.d/initial_data.sh
- ./data.json:/docker-entrypoint-initdb.d/data.json
cd /app
if [ ! -e /INITIALIZED ]; then bundle exec rake errbit:bootstrap; touch /INITIALIZED; fi
bundle exec puma -C config/puma.default.rb
mongoimport -d errbit -c apps /docker-entrypoint-initdb.d/data.json
import dotenv
import airbrake
dotenv.load_dotenv(dotenv_path=".app.env")
logger = airbrake.getLogger()
try:
1 / 0
except Exception:
logger.exception("Bad math.")
[[package]]
category = "main"
description = "Python SDK for airbrake.io"
name = "airbrake"
optional = false
python-versions = "*"
version = "2.1.2"
[package.dependencies]
requests = ">=2.20.0"
[[package]]
category = "main"
description = "Python package for providing Mozilla's CA Bundle."
name = "certifi"
optional = false
python-versions = "*"
version = "2020.6.20"
[[package]]
category = "main"
description = "Universal encoding detector for Python 2 and 3"
name = "chardet"
optional = false
python-versions = "*"
version = "3.0.4"
[[package]]
category = "main"
description = "Internationalized Domain Names in Applications (IDNA)"
name = "idna"
optional = false
python-versions = ">=2.7, !=3.0.*, !=3.1.*, !=3.2.*, !=3.3.*"
version = "2.10"
[[package]]
category = "main"
description = "Add .env support to your django/flask apps in development and deployments"
name = "python-dotenv"
optional = false
python-versions = "*"
version = "0.13.0"
[package.extras]
cli = ["click (>=5.0)"]
[[package]]
category = "main"
description = "Python HTTP for Humans."
name = "requests"
optional = false
python-versions = ">=2.7, !=3.0.*, !=3.1.*, !=3.2.*, !=3.3.*, !=3.4.*"
version = "2.24.0"
[package.dependencies]
certifi = ">=2017.4.17"
chardet = ">=3.0.2,<4"
idna = ">=2.5,<3"
urllib3 = ">=1.21.1,<1.25.0 || >1.25.0,<1.25.1 || >1.25.1,<1.26"
[package.extras]
security = ["pyOpenSSL (>=0.14)", "cryptography (>=1.3.4)"]
socks = ["PySocks (>=1.5.6,<1.5.7 || >1.5.7)", "win-inet-pton"]
[[package]]
category = "main"
description = "HTTP library with thread-safe connection pooling, file post, and more."
name = "urllib3"
optional = false
python-versions = ">=2.7, !=3.0.*, !=3.1.*, !=3.2.*, !=3.3.*, !=3.4.*, <4"
version = "1.25.9"
[package.extras]
brotli = ["brotlipy (>=0.6.0)"]
secure = ["certifi", "cryptography (>=1.3.4)", "idna (>=2.0.0)", "pyOpenSSL (>=0.14)", "ipaddress"]
socks = ["PySocks (>=1.5.6,<1.5.7 || >1.5.7,<2.0)"]
[metadata]
content-hash = "27077d39f6a396e0255f8117da165bd82fc4f0cc094260d7ac7647c401cec0d9"
python-versions = "^3.8"
[metadata.files]
airbrake = [
{file = "airbrake-2.1.2-py2.py3-none-any.whl", hash = "sha256:6dcb77bdf8a2639c78762657c4f440ff4ee1c704a069a6b026fdbe4176823532"},
{file = "airbrake-2.1.2.tar.gz", hash = "sha256:998a5563116d753e3531fa45889b940fe5ea9a8f8394a3e62e6455645ff0c416"},
]
certifi = [
{file = "certifi-2020.6.20-py2.py3-none-any.whl", hash = "sha256:8fc0819f1f30ba15bdb34cceffb9ef04d99f420f68eb75d901e9560b8749fc41"},
{file = "certifi-2020.6.20.tar.gz", hash = "sha256:5930595817496dd21bb8dc35dad090f1c2cd0adfaf21204bf6732ca5d8ee34d3"},
]
chardet = [
{file = "chardet-3.0.4-py2.py3-none-any.whl", hash = "sha256:fc323ffcaeaed0e0a02bf4d117757b98aed530d9ed4531e3e15460124c106691"},
{file = "chardet-3.0.4.tar.gz", hash = "sha256:84ab92ed1c4d4f16916e05906b6b75a6c0fb5db821cc65e70cbd64a3e2a5eaae"},
]
idna = [
{file = "idna-2.10-py2.py3-none-any.whl", hash = "sha256:b97d804b1e9b523befed77c48dacec60e6dcb0b5391d57af6a65a312a90648c0"},
{file = "idna-2.10.tar.gz", hash = "sha256:b307872f855b18632ce0c21c5e45be78c0ea7ae4c15c828c20788b26921eb3f6"},
]
python-dotenv = [
{file = "python-dotenv-0.13.0.tar.gz", hash = "sha256:3b9909bc96b0edc6b01586e1eed05e71174ef4e04c71da5786370cebea53ad74"},
{file = "python_dotenv-0.13.0-py2.py3-none-any.whl", hash = "sha256:25c0ff1a3e12f4bde8d592cc254ab075cfe734fc5dd989036716fd17ee7e5ec7"},
]
requests = [
{file = "requests-2.24.0-py2.py3-none-any.whl", hash = "sha256:fe75cc94a9443b9246fc7049224f75604b113c36acb93f87b80ed42c44cbb898"},
{file = "requests-2.24.0.tar.gz", hash = "sha256:b3559a131db72c33ee969480840fff4bb6dd111de7dd27c8ee1f820f4f00231b"},
]
urllib3 = [
{file = "urllib3-1.25.9-py2.py3-none-any.whl", hash = "sha256:88206b0eb87e6d677d424843ac5209e3fb9d0190d0ee169599165ec25e9d9115"},
{file = "urllib3-1.25.9.tar.gz", hash = "sha256:3018294ebefce6572a474f0604c2021e33b3fd8006ecd11d62107a5d2a963527"},
]
[tool.poetry]
name = "fc55c113dee57de338010f1bd831917f"
version = "0.1.0"
description = ""
authors = ["TakesxiSximada <8707279+TakesxiSximada@users.noreply.github.com>"]
[tool.poetry.dependencies]
python = "^3.8"
python-dotenv = "*"
airbrake = "*"
[tool.poetry.dev-dependencies]
[build-system]
requires = ["poetry>=0.12"]
build-backend = "poetry.masonry.api"
airbrake
python-dotenv
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment