- 1. はじめに|「気づいたら落ちていた」をゼロにする理由
- 2. ステータス情報の取得方法を3分で整理
- 3. 環境準備|必要ツールとフォルダ構成
- 4. 単一ベンダー版:最小30行のPythonスクリプト
- 5. マルチベンダー統合版:クラス設計とプラグイン機構
- 6. 死活監視ツールとの連携で“取りこぼしゼロ”
- 7. 通知テンプレート集
- 8. Cron 設定完全ガイド
- 9. Docker 化して「どこでも動く」パッケージへ
- 10. セキュリティ&可用性チェックリスト
- 11. ケーススタディ3選
- 12. よくある質問 25
- 用語集 40
- 14. まとめ|自動通知で “反応速度 × 信頼” を底上げする
- 15. 無料監視スクリプト診断
1. はじめに|「気づいたら落ちていた」をゼロにする理由
1-1 機会損失は何分でいくら?
- ブログ広告:1 分停止=平均クリック5 件損失 → 日商1万円サイトなら約350円の取りこぼし
- EC:カート決済率3 %・平均客単価8,000円 → 10 分停止で24,000円の売上消失
- 企業SaaS:SLA 99.9 %(月に44分停止)を超えると違約金
通知が10 分早いだけで“損失・信用・カスタマー対応”すべてが軽減されます。
1-2 ステータスページだけでは遅い現実
多くのレンタルサーバーやクラウドは
- 障害検知
- エンジニア確認
- ステータスページ更新
──この流れで最短でも10〜15分の空白が発生。
自前のスクリプトで API を直接ポーリングすれば、最速1分周期で検知→Slackやメールへ即通知できます。
1-3 本記事のゴール
- Python/Bashどちらでも動く30行スクリプトを作る
- XserverやConoHaの障害RSS/JSONを読み取り差分を抽出
- Slack・メール・Teams・Notionへ自動通知し、Cronで定期実行
読了後には「障害が起きたら1分で全員に届く」仕組みを自サイトに持てます。
2. ステータス情報の取得方法を3分で整理
種類 | 仕組み | 代表ベンダー | メリット | 注意点 |
---|---|---|---|---|
RSS / Atom | XMLフィード | Xserver/さくら | 超軽量・ライブラリ豊富 | ベンダーにより更新遅延あり |
JSON API | /status.json など | Cloudflare/Vercel | 機械判読しやすい | 仕様変更に追従必要 |
Webhook | 障害発生時Push | Stripe/GitHub | リアルタイム・無ポーリング | 公開していない社も多い |
スクレイピング | HTML解析 | 一部レン鯖 | 非公開情報を取れる | 規約違反・構造変化に弱い |
ベストプラクティス:公開JSON or RSS → 差分取得 → Webhook型(Slack等)で通知。この3層が最も安定します。
2-1 主要レンタルサーバー & クラウドの公開エンドポイント早見表
サービス | 種別 | URL例 |
---|---|---|
Xserver | RSS | https://www.xserver.ne.jp/rss_status.xml |
ConoHa | JSON | https://status.conoha.jp/api/v1/status |
Cloudflare | JSON | https://www.cloudflarestatus.com/summary.json |
AWS | RSS | https://status.aws.amazon.com/rss/all.rss |
(2025-05確認。最新URLは公式で要チェック)
2-2 非公開ベンダーの扱い
- 公開URLが無い場合はスクレイピングは最終手段。利用規約で禁止される場合も。
- 公式Xアカウントで障害ツイート→Twitter API で拾う方法もあるが、レート制限に注意。
3. 環境準備|必要ツールとフォルダ構成
3-1 Python と Bash どちらを選ぶ?
比較軸 | Python | Bash+curl |
---|---|---|
可読性 | ◎ | △ |
依存ライブラリ管理 | pip / venv | ほぼ不要 |
JSON処理 | 標準json で楽 | jq が必須 |
拡張性(並列処理など) | asyncioで高 | 限界あり |
初心者でも保守しやすいPython版を推奨。サンプルはPython、巻末でBashワンライナー例も載せます。
3-2 インストール手順(Xserver例)
bashコピーする編集する# SSH ログイン後
python3 -m venv ~/statusbot-venv
source ~/statusbot-venv/bin/activate
pip install requests feedparser python-dotenv
.env
にWebhookやメールAPIキーを置くことで Gitに鍵を入れない セキュア運用が可能。
3-3 フォルダ構成
bashコピーする編集するstatusbot/
├ fetchers/
│ ├ base.py
│ ├ xserver.py
│ └ conoha.py
├ notifiers/
│ ├ slack.py
│ └ email.py
├ main.py
├ .env
├ requirements.txt
└ logs/
- fetchers/ : ベンダー別にステータスを取得
- notifiers/ : 通知チャネルごとに送信
- logs/ : 実行ログ+前回取得キャッシュを保存
4. 単一ベンダー版:最小30行のPythonスクリプト
pythonコピーする編集する#!/usr/bin/env python3
import feedparser, json, os, requests, hashlib, pathlib, sys
WEBHOOK = os.getenv("SLACK_WEBHOOK")
RSS = "https://www.xserver.ne.jp/rss_status.xml"
CACHE = pathlib.Path(__file__).with_suffix(".cache")
def fetch_latest():
feed = feedparser.parse(RSS)
return feed.entries[0].title + feed.entries[0].link
def changed(text):
new_hash = hashlib.md5(text.encode()).hexdigest()
old_hash = CACHE.read_text() if CACHE.exists() else ""
if new_hash != old_hash:
CACHE.write_text(new_hash)
return True
return False
def notify(msg):
requests.post(WEBHOOK, json={"text": msg})
if __name__ == "__main__":
latest = fetch_latest()
if changed(latest):
notify(f"🚨Xserver 障害/メンテ更新\n{latest}")
print("sent")
else:
print("no change")
動作概要
- RSSを取得 → 最新エントリを文字列化
- 前回実行時MD5と比較 → 変化あればSlackにPOST
.cache
にハッシュ保存 → 無変更時は何もしない
ポイント
- MD5のみで差分管理:ファイル1行、SQL不要
- 環境変数でWebhook隠蔽:
.env
→os.getenv
読込
5. マルチベンダー統合版:クラス設計とプラグイン機構
単一スクリプトでも動きますが、VPS・CDN・DNS など複数サービスを使うサイトは “横並びで監視” できると便利です。ここでは Python のクラス継承 を使い、ベンダーを追加しても 5 分で拡張 できる土台を作ります。
5-1 ベースクラス AbstractStatusFetcher
pythonコピーする編集する# fetchers/base.py
from abc import ABC, abstractmethod
class StatusFetcher(ABC):
def __init__(self, name):
self.name = name # 例: Xserver
self.cache_file = f".{name}.cache"
@abstractmethod
def fetch(self):
"""最新の障害・メンテ文字列を返す"""
...
def _changed(self, text: str) -> bool:
import hashlib, pathlib
new = hashlib.md5(text.encode()).hexdigest()
path = pathlib.Path(self.cache_file)
old = path.read_text() if path.exists() else ""
if new != old:
path.write_text(new)
return True
return False
5-2 具体クラス:Xserver & ConoHa
pythonコピーする編集する# fetchers/xserver.py
import feedparser
from .base import StatusFetcher
class XserverFetcher(StatusFetcher):
RSS = "https://www.xserver.ne.jp/rss_status.xml"
def __init__(self):
super().__init__("xserver")
def fetch(self):
feed = feedparser.parse(self.RSS)
latest = feed.entries[0]
text = f"{latest.title} | {latest.link}"
return text if self._changed(text) else None
pythonコピーする編集する# fetchers/conoha.py
import requests, datetime, pytz, json
from .base import StatusFetcher
class ConoHaFetcher(StatusFetcher):
API = "https://status.conoha.jp/api/v1/status"
def __init__(self):
super().__init__("conoha")
def fetch(self):
data = requests.get(self.API, timeout=5).json()
latest = data["incidents"][0]
jp = datetime.datetime.fromisoformat(latest["updated_at"]).astimezone(
pytz.timezone("Asia/Tokyo")).strftime("%Y-%m-%d %H:%M")
text = f'{latest["name"]} ({jp})'
return text if self._changed(text) else None
5-3 メインスクリプトをプラグイン方式に
pythonコピーする編集する# main.py
import os, importlib, requests
from dotenv import load_dotenv
load_dotenv()
WEBHOOK = os.getenv("SLACK_WEBHOOK")
FETCHERS = ["xserver.XserverFetcher", "conoha.ConoHaFetcher"]
def notify(msg):
requests.post(WEBHOOK, json={"text": msg})
for path in FETCHERS:
module_name, class_name = path.split(".")
cls = getattr(importlib.import_module(f"fetchers.{module_name}"), class_name)
text = cls().fetch()
if text:
notify(f"🚨 {cls.__name__[:-7]} 障害/メンテ更新\n{text}")
ベンダーを増やす手順
fetchers/xxx.py
をコピー&URL修正FETCHERS
リストへエントリを追記 — 以上!
6. 死活監視ツールとの連携で“取りこぼしゼロ”
障害情報は「サーバー側の発表」。しかし 自サイトだけ 404 になるケース(DNS ミス・テーマ更新ミス等)は拾えません。そこで 死活監視 (Heartbeat) を同じ Slack チャンネルに束ねましょう。
6-1 curl + grep 最小ヘルスチェック
bashコピーする編集する#!/bin/bash
URL="https://example.com/health"
if curl -fs --max-time 10 "$URL" | grep -q "OK"; then
echo "healthy"
else
curl -X POST -H 'Content-Type: application/json' \
-d '{"text":"❌サイトが応答しません"}' "$SLACK_WEBHOOK"
fi
/health
はindex.php
直通より軽量な簡易エンドポイントを用意- 2xx 以外は Slack 通知
6-2 UptimeRobot API でまとめ通知
UptimeRobot は無料 1 分監視+Webhook。ステータス変化 Webhook を 受信用小スクリプト に集約し、障害情報と同じ Block Kit で Slack に流すと見やすい。
7. 通知テンプレート集
7-1 Slack Block Kit(視認性◎)
pythonコピーする編集するdef build_block(vendor, text):
return {
"blocks":[
{"type":"header","text":{"type":"plain_text","text":f"🚨 {vendor} 障害情報"}},
{"type":"section","text":{"type":"mrkdwn","text":text}},
{"type":"context","elements":[{"type":"mrkdwn","text":"<https://status.example|公式ステータス>"}]}
]
}
requests.post(WEBHOOK, json=build_block("Xserver", text))
7-2 Microsoft Teams (Adaptive Card)
jsonコピーする編集する{
"@type": "MessageCard",
"themeColor": "ff0000",
"title": "ConoHa 障害通知",
"text": "データベース接続障害 (2025-05-08 14:12)"
}
Teams の Incoming Webhook にそのまま POST。
7-3 Notion データベース追記
pythonコピーする編集するimport requests, os, datetime, json
def notion_create(text):
url="https://api.notion.com/v1/pages"
headers={
"Authorization": f"Bearer {os.getenv('NOTION_TOKEN')}",
"Notion-Version": "2022-06-28",
"Content-Type":"application/json"
}
data={
"parent":{"database_id":os.getenv("NOTION_DB")},
"properties":{
"Title":{"title":[{"text":{"content":text}}]},
"Date":{"date":{"start":datetime.datetime.utcnow().isoformat()}}
}
}
requests.post(url, headers=headers, data=json.dumps(data))
7-4 SMS/音声(夜間用)
Twilio で
pythonコピーする編集するfrom twilio.rest import Client
client = Client(SID, TOKEN)
client.messages.create(from_='+123456789', to='+819012345678',
body='🚨 Xserver DB障害発生')
着信音+バイブ で管理者が確実に気づく仕組み。
8. Cron 設定完全ガイド
8-1 基礎:書式と例
rubyコピーする編集する*/5 * * * * /home/user/statusbot/venv/bin/python /home/user/statusbot/main.py >> /home/user/statusbot/logs/run.log 2>&1
*/5 * * * *
→ 5 分ごと- 標準出力・エラーを
run.log
に追記
8-2 Xserver パネルでの手順
- サーバーパネル →「Cron設定」
*/5
分・*
時…をプルダウンで入力- コマンド欄にフルパスを貼り付け
- 「実行結果をメールで受け取る」をON
- 失敗検知が楽&SSHログイン不要
8-3 ロードアベレージと実行間隔
- 共用サーバーはロードアベレージ制限あり → 5分〜10分間隔が無難
- 自社VPSなら 1分間隔もOK だが、ベンダーAPIにもレート制限 があるため要確認(Cloudflareは毎分120リクエスト)
8-4 よくある Cron 失敗原因
症状 | 原因 | 解決 |
---|---|---|
command not found | venv パス誤り | 絶対パスを確認 |
Permission denied | ファイルに実行権なし | chmod +x script.py or python script.py |
メールが大量送信 | script が毎回エラー | 2>&1 でログへ、set -e で即停止 |
9. Docker 化して「どこでも動く」パッケージへ
狙い:自宅 PC、VPS、会社サーバー——どこでも同じコマンドで立ち上げ。依存地獄から解放されます。
9-1 Dockerfile(最小 10 行)
Dockerfileコピーする編集するFROM python:3.12-slim
WORKDIR /app
COPY requirements.txt .
RUN pip install --no-cache-dir -r requirements.txt
COPY . .
CMD ["python", "main.py"]
- プロジェクト直下に
Dockerfile
とrequirements.txt
を配置 - ビルド:
docker build -t statusbot:latest .
- 実行: bashコピーする編集する
docker run --env-file .env \ --name statusbot \ statusbot:latest
9-2 自動アップデート(watchtower)
bashコピーする編集するdocker run -d --name watchtower \
-v /var/run/docker.sock:/var/run/docker.sock \
containrrr/watchtower \
statusbot --schedule "0 */6 * * *"
6 時間おきに最新イメージへ自動更新→再起動。
9-3 マネージドサービスでスケジューリング
- AWS ECS/Fargate:CloudWatch Event で 5 分ごと起動
- Cloud Run:Cloud Scheduler で HTTP ping—無料枠で十分回る
10. セキュリティ&可用性チェックリスト
項目 | やること | ツール例 |
---|---|---|
API キー暗号化 | .env.enc を sops + GPG / AWS KMS | Mozilla sops |
多重通知抑止 | 送信前に Redis でキー重複チェック | python-redis |
スクリプト死活 | 5 分ごとに Heartbeat API へ ping | Healthchecks.io |
ログ保全 | logrotate で週次圧縮+90 日保管 | logrotate |
権限分離 | Slack Webhook を監視専用チャネルに限定 | Slack 権限設定 |
レート制限耐性 | asyncio.semaphore で同時 API 呼び出しを制御 | asyncio |
11. ケーススタディ3選
11-1 月 100 万 PV ブログ
- 課題:Xserver 障害情報を手動チェック→反応 30 分遅れ
- 導入:RSS 監視 + Slack 通知 1 分間隔
- 成果:広告停止時間 –22 分、月あたり広告損失 –18,000 円
11-2 24h 稼働 EC サイト
- Teams + SMS 併用(営業時間内は Teams、深夜は SMS)
- 決済 API 死活チェックも同報 → 深夜障害を 4 分で検知→決済切替
- CS 対応時間 –40 %、購入取りこぼしほぼゼロ
11-3 SaaS 企業 CS チーム
- Notion データベースへ自動追記 → 全社員が一目で障害履歴を確認
- 公式アナウンスより平均 12 分速く把握 ⇒ チャットボット即時返信で混乱減
12. よくある質問 25
# | 質問 | 回答 |
---|---|---|
1 | API がなく RSS も無いサービスは? | Twitter/X の公式アカウントを RSS ハブ経由で取得するか、最終手段として HTML スクレイピング。ただし規約を必ず確認。 |
2 | RSS が更新されないことがある | サービス側のキャッシュが原因。1 分→5 分間隔に延ばし、死活監視と併用して補完してください。 |
3 | 差分判定に MD5 で十分? | タイトルとリンクを連結してハッシュ化すれば実質衝突なし。本文差分も見たい場合は全文ハッシュへ変更を。 |
4 | Slack 通知が 2 回届く | キャッシュファイルが権限エラーで書けていない可能性。実行ユーザーを統一 or キャッシュ保存先を /tmp へ変更。 |
5 | Webhook URL が漏えいしたら? | Slack 管理画面→アプリ→Webhook→「Rotate」をクリックで即無効化。 |
6 | Python じゃなく Bash がいい | 1 ベンダー 1 行通知なら curl + grep + jq で可能。複数ベンダーなら Python が保守楽。 |
7 | メールだけでいい? | メールは夜間に埋もれがち。Slack 等リアルタイム+メールを CC にする二重化がおすすめ。 |
8 | 実行ログが肥大化する | logrotate で週1 圧縮、rotate 8 (8 週保管)程度で十分。 |
9 | シェアードサーバーで 1 分 Cron が使えない | 5 分 Cron + スクリプト内 time.sleep(60) ×5 で疑似 1 分監視。ただし実行時間上限に注意。 |
10 | ベンダー API が 429 (Rate Limit) を返す | ポーリング間隔を延長し、Retry-After ヘッダを respect。 |
11 | 障害終了通知を受けたい | フィードの「Resolved」「Closed」ステータスを別ハッシュで管理して二重通知を実装。 |
12 | 複数チャンネルに送る方法は? | Notifiers をリスト化し、for ループで順に POST。失敗時は例外ログ。 |
13 | JSON 解析で UnicodeError | response.json() の前に .text.encode('utf-8', 'ignore') で化け文字回避。 |
14 | Teams で Markdown が崩れる | Adaptive Card に統一か、改行を <br> に置換。 |
15 | Slack アイコンを変えたい | Webhook 送信 JSON に "username":"StatusBot","icon_emoji":":siren:" を追加。 |
16 | 夜間だけ SMS を送りたい | if 0 <= now.hour <= 8: 条件で Twilio 通知を発火。 |
17 | Docker イメージが大きい | python:slim ベース + --no-cache-dir ; multi-stage build で 150 MB 未満に。 |
18 | GitHub Actions で定期実行したい | schedule: cron: '*/5 * * * *' 、Secrets に Webhook を保存すれば GitHub 上でも可。 |
19 | シークレット管理が面倒 | 1Password CLI / HashiCorp Vault で自動 inject するワークフローを採用。 |
20 | cron が止まっていた | Heartbeat サービス(Healthchecks.io)に最後の成功 ping を飛ばし、未受信 10 分で SMS。 |
21 | API 仕様変更に気づかない | fetch エラー(JSON decode)が連続したら「要メンテ」Slack 通知を投げる try/except を仕込む。 |
22 | Slack Free プランで履歴が流れる | メールか Notion など長期保管先にも複写し、検索できる状態を確保。 |
23 | 英語のみの障害文を日本語化したい | googletrans ライブラリで machine translate、または要約して送信。 |
24 | Serverless で完全に管理フリーに? | AWS Lambda + EventBridge Scheduler で同スクリプトを動かせばサーバー不要。 |
25 | パフォーマンス監視も統合したい | Prometheus で up{job="website"}==0 を検知→Alertmanager で同じ Slack 通知に統合可能。 |
用語集 40
# | 用語 | かみくだき解説 |
---|---|---|
1 | ステージング環境 | 本番そっくりに複製したテスト用サイト。 |
2 | テスト環境 | 開発者が単体・結合テストを行う場所。ステージングより自由度が高い。 |
3 | 本番環境 | 一般ユーザーがアクセスする公開サイト。 |
4 | 差分プッシュ | 変更されたファイル・データだけを本番へ反映する操作。 |
5 | バックポート | 本番の最新データをステージングへ戻し整合を取ること。 |
6 | E2E テスト | 画面のボタン操作〜結果表示までを自動検証する “端から端” のテスト。 |
7 | Unit テスト | 関数単位の小さな動作テスト。PHPUnit などで実施。 |
8 | Cypress | JavaScript 製のブラウザ自動テストフレームワーク。 |
9 | WP-CLI | WordPress をコマンドラインで操作する公式ツール。 |
10 | GitHub Actions | GitHub に内蔵された CI/CD パイプライン機能。 |
11 | CI/CD | 継続的インテグレーション/継続的デリバリー。テストとリリースを自動化する考え方。 |
12 | Blue-Green デプロイ | 本番と同じ構成を 2 系統用意し、切替で無停止リリースする手法。 |
13 | Rollback | 不具合時に更新前の状態へ即時戻すこと。 |
14 | robots.txt | 検索エンジンのクロール可否を指示するファイル。 |
15 | Basic 認証 | ID とパスワードでサイト全体を簡易保護する仕組み。 |
16 | Slack Webhook | 外部サービスから Slack へメッセージを投稿する URL。 |
17 | GUID | WordPress 投稿が持つ一意の識別用 URL。 |
18 | Serialize 文字列 | PHP のデータ構造を 1 本の文字列に変換したもの。 |
19 | Search-Replace | DB 内の文字列一括置換。URL 変更で使う。 |
20 | hosts 切替 | PC の hosts ファイルで DNS をローカル上書きし、テスト先を一時的に変える方法。 |
21 | S3 オフロード | 画像などメディアファイルを Amazon S3 に保存し、サーバー容量や複製時間を減らす手法。 |
22 | Lint | コードの文法エラーやスタイル違反を自動検出するツール群。 |
23 | PHPUnit | PHP のユニットテストを実行する公式フレームワーク。 |
24 | WPScan | WordPress の脆弱性をチェックできるセキュリティツール。 |
25 | WAF | Web Application Firewall。攻撃を自動遮断する防御壁。 |
26 | Cache Purge | キャッシュを強制的に全削除して最新状態にする操作。 |
27 | Edge Cache | CDN の最寄りサーバーが保持するキャッシュ。 |
28 | Git Flow | main・develop・release など複数ブランチで開発を進めるワークフロー。 |
29 | NPS | Net Promoter Score。顧客推奨度を測る指標。 |
30 | Sandbox モード | 決済など外部サービスのテスト用環境。実課金されない。 |
31 | API キー | 外部サービスを認証する文字列。漏えいすると不正利用される。 |
32 | Feature Flag | 新機能をコードに含めつつ、ON/OFF スイッチで切り替える手法。 |
33 | PR(Pull Request) | 変更内容を他メンバーにレビュー依頼する GitHub の仕組み。 |
34 | Actions Secret | GitHub Actions 内で使う暗号化された環境変数。 |
35 | Audit Log | 誰がいつ何を変更したかを記録する監査証跡。 |
36 | CSP | Content Security Policy。外部スクリプト読み込みを制限し XSS を防ぐ。 |
37 | SRI | Subresource Integrity。外部ファイル改ざんを検知するハッシュ署名。 |
38 | Cron Health Check | wp-cron が正常に走っているかを監視する仕組み。 |
39 | Headless CMS | WordPress を管理画面だけに使い、フロントは別のJSフレームで表示する構成。 |
40 | Zero-Downtime | アップデート中でも一切の停止時間を作らない運用方針。 |
14. まとめ|自動通知で “反応速度 × 信頼” を底上げする
- 公開 API / RSS を 1 分ポーリング
- ベンダー発表を最速キャッチ
- 死活監視と束ねてワンチャンネル通知
- 自社固有の 404・決済障害も同時検知
- Cron / Docker / Watchtower で 24h 無人稼働
- 運用コストは月 0 円、保守は Git Pull だけ
行動の早さ = 損失の小ささ × 顧客の安心感
今日 30 行のスクリプトを仕込み、明日から “落ちてもすぐ動く” サイト運営へ。
15. 無料監視スクリプト診断
障害情報を朝イチで知り「あ、夜中に落ちてた…」と青ざめていませんか?
その 30 分の遅れが広告費・売上・顧客信頼を確実に削っています。
当サイトでは 監視スクリプト&Cron 無料診断 を実施中。コードレビュー+ベストプラクティスを 48 時間以内にレポート化し、即改善ポイントをお渡しします。
先着 15 サイト限定、7 月 31 日申込分で締切。
下のボタンから 60 秒でエントリーし、“最速検知体制” を今日から手に入れましょう!