基本仕様・設計

短期的なモチベーション維持と、長期的なリーグへの貢献を両立させるシステム設計

シーズンXP と 通算XP の二重構造システム

短期的なシーズン完走と、長期的なリーグへの功績を同時に評価するための独自設計です。

【短期】シーズン XP / レベル(2ヶ月ごとにリセット)

  • 加算挙動: ミッションクリア時に100%加算されます。
  • リセット: シーズン終了時(2ヶ月ごと)に「0」にリセットされます。
  • 報酬: シーズン限定の通常パス報酬(Lv50まで)の獲得や、シーズン毎に新設される限定称号(ロール)のアンロックに使用します。

【長期】通算 XP / レベル(永久リセットなし)

  • 加算挙動: ミッションクリア時に「シーズンXP」と同時に全額加算されます。
  • リセット: シーズンが切り替わってもリセットされず、永続的に蓄積されます。
  • 報酬: 3シーズン分(約6ヶ月)以上の長期的なやりこみを評価。最難関の永続ロール『DER Mythic』や、永久獲得できる「通算実績バッジ」の獲得条件に使用され、古参プレイヤーのこれまでの功績を証明します。

サポータープランと1日クリア上限設計

ランキング要素(リーダーボード)とは完全に隔離された「自己成長・やりこみシステム」であるため、課金プランに応じた時短要素を提供します。

一般会員は1日最大3枠クリア可能ですが、サポーター登録者は4枠、5枠とクリア上限そのものが拡張され、より早くバトルパスを進められる特典が適用されます。

プラン名 月額料金 デイリー表示枠 1日クリア上限 獲得可能XP倍率 主な特典・メリット
一般(無料枠) 0 円 3 枠 3 枠 1.0 倍 標準機能のみ。AI戦績詳細分析は「月1回」。
応援サポーター 300 円 4 枠 4 枠 1.0 倍 デイリーミッション枠+1。AI戦績詳細分析は「月30回」。専用Discordロール付与。
プレミアムサポーター 500 円 5 枠 5 枠 1.0 倍 デイリーミッション枠+2。AI戦績詳細分析は「月100回」。専用上位Discordロール付与。キラー別勝率・相性などの詳細アナリティクスの完全解放。

プラン別・到達シミュレーション・マップ

シーズンは2ヶ月間(シーズン計約31日開催 / 1日最大8〜10試合)。ミッション達成度に基づく想定到達レベルマップです。

対象グループ 稼働日数 1日デイリー消化数 シーズン累積獲得XP シーズン想定到達レベル
一般 / ライト層 16 日 平均 1.5 個 約 4,700 XP Lv 18
一般 / ミドル層 25 日 平均 2.4 個 約 11,100 XP Lv 31
一般 / ヘビー層 31 日 (全通) 1日 3 個 (全消化) 約 18,700 XP Lv 45
応援サポ / ライト層 16 日 平均 2.0 個 約 5,960 XP Lv 20
応援サポ / ミドル層 25 日 平均 3.2 個 約 14,000 XP Lv 37
応援サポ / ヘビー層 31 日 (全通) 1日 4 個 (全消化) 約 23,800 XP Lv 50 (シーズン完走)
プレミアムサポ / ヘビー層 31 日 (全通) 1日 5 個 (全消化) 約 28,900 XP Lv 50 (シーズン完走+余裕到達)

Discordロールの数と名前

シーズン終了時のリセットスクリプトを通じて、到達レベルに基づきDiscordメンバーへ自動で一括配布されます。

※Season 2より正式導入されます(現在進行中のSeason 1は対象外とすることで、誤付与を防止しています)。

ロール名 (称号) 獲得基準 (シーズンLv / 通算) 必要累計XP ロール色イメージ 付与タイミング & リセット挙動
Sx Active Player シーズンレベル 15 累計 3,300 XP ■ フォレストグリーン シーズンリセット時に回収、新シーズン名で新設
Sx Entity's Elite シーズンレベル 35 累計 11,300 XP ■ ミステリアスパープル シーズンリセット時に回収、新シーズン名で新設
Sx DER Legend シーズンレベル 50 (完走) 累計 19,800 XP ■ ネオンゴールド シーズンリセット時に回収、新シーズン名で新設
DER Mythic 通算レベル 150 累計 65,300 XP ■ ホログラムピンク 永久付与 (3シーズン以上かけて目指す殿堂入り称号)

ミッション設計とレーティング(Elo)の保護

リーグ全体の対戦品質維持とレーティング保護のため、使用キラーキャラクターを個別に強制指定するミッション(例:「トラッパーで3回全滅しろ」など)は一切排除されています。

⚠️ レーティング保護の原則(システム制限への適合)

DERリーグはゲームクライアント内の詳細ログを一切取得しません。 すべてのミッションやバッジの解除条件は、システムが取得・検証可能なデータ(ロール、対戦結果の全滅/逃げ数、使用キラー、MVP投票、総プレイ・勝利数、Eloレート)のみに限定して完全に再設計されています。

キラーキャラクターの個別指定ミッションを排除することで、不得意キラー強制によるレーティング崩壊を防ぎます。

システム構成・最適化

Firestoreへの読み書き追加回数「ゼロ」を達成した、高効率なミッション自動進行メカニズム

ミッション自動進行・反映の仕組み

システム開発の知識がなくても直感的にわかる、自動でミッションが進行し、かつFirestoreデータベースの費用と負荷を極限まで節約する高効率な処理設計です。

🔄 ミッションが自動で進む4つのステップ

  1. 1. 対戦結果の報告: プレイヤーがDiscord上で試合結果を通常通り報告・投票し、Botが結果を受理します。
  2. 2. Botが自動で丸付け: Botが「今回の結果は3人脱出か。ならサバイバー側のプレイヤーは『チーム勝利』のミッションが進むな!」と自動で判断します。
  3. 3. 戦績と一緒に保存: プレイヤーの「新レート(強さ)」を保存する際に、ミッションの進捗データも同じファイルに相乗り(マージ)して保存します。
  4. 4. 自動でXPをプレゼント: ミッションが達成されると、プレイヤーの経験値(XP)が自動で加算され、レベルアップ時にはDiscordでお祝いメッセージが飛びます。

① 「いつもの記録」のついでに保存する(追加の保存回数:ゼロ)

対戦解決時に5人の勝敗と強さをデータベースに書き込んでいますが、新しいミッションデータもこの書き込み処理にマージして1つのトランザクションで書き込みます。これにより、ミッション用の追加書き込み回数は完全にゼロ(追加費用なし)です。

② ルール(ミッション定義)はBotのメモリに暗記させる(追加の読込回数:ゼロ)

ミッションの内容やクリア条件といったマスターデータは、データベースではなくBot実行環境のインメモリに配置されています。これにより、ミッション判定のためのデータベース読み込み回数も完全にゼロになります。

③ ミッションを配るのは「必要なときだけ」(無駄な処理をカット)

「毎日深夜24時に全ユーザー分を自動抽選する」ような一斉バッチ処理を排除。プレイヤーが対戦報告を行った瞬間、または個人アナリティクス画面を開いた瞬間に、その日の日付と前回の抽選日を比較し、日付が変わっていればその場で遅延生成(Lazy Load)します。これにより無駄な空振りのデータベース書き込みを100%カットしています。

[システムエンジニア視点] 二段階判定処理シーケンス

全員の投票が完了(解決)した段階でミッション評価をアトミックに実行します。Firestoreへの追加書き込みは発生しません。

sequenceDiagram autonumber participant Discord as Discord Bot (ui_views) participant DB as Firestore (database.py) participant Master as ミッションマスタ (インメモリ) Discord->>DB: resolve_match() 実行 (5人投票完了時) Note over DB: トランザクション開始 DB->>DB: 5人のユーザーデータ読込 DB->>DB: [第1段階] 今日のミッション未配布なら抽選配布 (遅延配布) DB->>Master: プレイ数・勝利等の条件判定 Master-->>DB: 進捗加算 & XP更新 DB->>DB: レート更新 & statusをfinishedに変更 DB-->>Discord: トランザクション完了 (追加書き込み: 0回) Discord->>Discord: MVP投票 (15分制限) Discord->>DB: apply_mvp_bonus() 実行 Note over DB: トランザクション開始 DB->>DB: MVP受賞ユーザーのデータ読込 DB->>Master: [第2段階] MVP獲得系ミッションの条件判定 Master-->>DB: 進捗加算 & XP更新 DB->>DB: MVPボーナスレート加算 (+10) DB-->>Discord: トランザクション完了 (追加書き込み: 0回)

システム開発上の10の懸念点と対策(リスク管理)

バグやデータの破損を防ぎ、システムを安全に稼働させるための技術的リスクの洗い出しと設計対策です。

  • ① データの同時書き換え(衝突)の保護:Firestoreのトランザクション(同時書き込みを保護する仕組み)を使用し、衝突時はプログラムが自動的に数ミリ秒待ってから自動リトライするよう設計。
  • ② 試合の取り消し・修正時のズレの防止:「ミッション進捗および獲得XPは取り消し不可」の仕様で確定。手動報告ミスは運営による手動コマンドで解決します。
  • ③ Firestoreのドキュメントサイズ上限(1MB制限)への適合:ユーザーデータ本体のドキュメント肥大化を防ぐため、ミッションの完了履歴は親ドキュメントではなく、Firestoreのサブコレクション(mission_history)へ都度隔離して保存します。
  • ④ Bot停止・再起動時のデータ保護:データの更新順序は常にFirestoreトランザクション内で一気に行われるため、Discord Botがいつクラッシュ・再起動してもデータが中途半端な状態で残ることはありません。
  • ⑤ タイムゾーンおよび日付変更線の判定:get_japan_today_str() を通じて、すべての判定を日本時間(JST = UTC+9)ベースの日付文字列(例: "2026-07-10")に統一しました。標準時(UTC)との時差による日付のズレは発生しません。
  • ⑥ ロール付与時のDiscord API制限(レートリミット)への適合:一斉にユーザーにロールを付与するとDiscordからBotがブロックされるため、バックエンドに非同期キュー処理を実装し、0.5秒の間隔を空けて順次ロールを付与する仕組みを実装しました。
  • ⑦ ユーザー切り替えやBotの不具合時の「ロール二重付与」の防止:レベルと獲得ロールの判定をデータベース上に明示的に保存し、一致するロールのみを有効化・無効化する同期関数(Idempotent処理)を実装。
  • ⑧ 異常値・チート対策:1試合で得られるXPの最大値を内部処理でキャップ(制限)し、不正に一瞬でレベル最大になるのを防ぎます。
  • ⑨ シーズンリセット時のデータ退避・復旧体制:シーズンリセットの実行時に自動でFirestoreバックアップコレクション users_backup_{season_name} を作成。もしものリセット失敗時に元に戻せるリストアスクリプト(restore_season_backup.py)を管理者ツールとして常備。
  • ⑩ バッジ・アセットのデータ量節約とキャッシュ保護:18個 of バッジ画像(WebP圧縮)の合計サイズを100KB以下に抑え、firebase.json にて immutable 永続ブラウザキャッシュヘッダーを設定。変更時はバージョンクエリ(?v=5)で即時パージするキャッシュ制御を実装。

実装検証・品質レポート

14ケースの自動統合テストのクリアおよび、5回に渡る厳格なコード監査による安全性証明

早期解決 (Condition A) の意図的な廃止について

キラー検証の導入に伴い、キラーが使用したキャラクターの検証が完了してから対戦解決およびレート書き込みを行う仕様に統一されています。

そのため、3人目の投票で解決していた古い「早期解決(Condition A)」は廃止されており、5人全員の投票完了(またはADMINの強制介入)を待ってから解決する設計が現在の正しいプロセスです。

網羅的14パターンの動作確認結果

テストスクリプトによる自動検証をすべてクリアし、動作の整合性が証明されました

パターンID テストシナリオ 確認項目 検証ステータス
PAT-01 全員一致サバイバー勝利 レート正常変動、初回ミッション自動配布、進捗加算 合格 (Pass)
PAT-02 全員一致キラー勝利 レート正常変動、キラー勝利ミッション・処刑数進捗 合格 (Pass)
PAT-03 不一致あり解決(一部報告ズレ) 不一致ユーザーへのストライク付与、合意レート反映、ミッション進捗 合格 (Pass)
PAT-04 1回目の不一致によるリセット 5人投票時点でリセット、投票データの退避、ビュー再有効化 合格 (Pass)
PAT-05 2回目の不一致による運営裁定移行 自動的に「disputed」状態へ移行、再入力ゲートウェイ送信 合格 (Pass)
PAT-06 管理者強制裁定による解決 管理者がボタン入力で確定、不一致者へペナルティ自動付与 合格 (Pass)
PAT-07 回線落ち(dc_penalty)解決 ペナルティ数カウント加算、全メンバーのミッション評価をスキップ 合格 (Pass)
PAT-08 MVP単独受賞による解決 MVPボーナス Elo (+10) 反映、第2段階ミッション(MVP勝利等)進捗 合格 (Pass)
PAT-10 MVP複数同率受賞による解決 全員へのボーナスおよびミッション進捗反映 合格 (Pass)
PAT-11 MVP投票タイムアウト解決 15分経過で自動解決(MVPなし等)、ミッション完了履歴保存 合格 (Pass)
PAT-12 二重解決(連打・同時処理ガード) status="finished" ガードによる2回目リクエストの自動拒否 合格 (Pass)
PAT-13 日付変更線跨ぎ(JST) 日本時間の深夜24時に daily_missions_date の日付が切り替わり再抽選 合格 (Pass)
PAT-14 データベース未初期化エラー処理 Firestore未初期化時のエラーキャッチと安全なハンドリング 合格 (Pass)
PAT-15 シーズンロール自動付与(S2以降) Discord APIレートリミットを考慮した0.5秒スリープ付きの順次付与 合格 (Pass)

5回におよぶ厳格なコード監査レポート

プログラムの安全性を保証するために行った、視点別コード見直し監査の結果

監査 1〜3回目:データ整合と容量管理

  • 【1回目】データ競合とトランザクション排他制御 (合格)
    Firestoreトランザクション内での「すべての読み取りは書き込みの前に行われる」原則が厳密に順守されているか確認しました。resolve_matchapply_mvp_bonus の両方で、情報取得後に更新データをマージして最後に一括書き込みしており、デッドロックや不整合の懸念はありません。
  • 【2回目】タイムゾーンおよび日付変更線の判定漏れ (合格)
    get_japan_today_str() を通じて、すべての判定を日本時間(JST = UTC+9)ベースの日付文字列(例: "2026-07-10")に統一しました。標準時(UTC)との時差による日付のズレは発生しません。
  • 【3回目】1MB上限のFirestoreサブコレクションの挙動 (合格)
    ミッション履歴保存処理において、テスト環境(users_test)と本番環境(users)の切り替えが get_col を通じて正しく行われ、履歴が親ドキュメントサイズを肥大化させない隔離されたサブコレクション(mission_history)へ保存されることを確認しました。

監査 4〜5回目:例外フローと Bot ライフサイクル

  • 【4回目】切断(dc_penalty)や例外フローの見直し (合格)
    切断(is_dc = True)が発生した試合において、ユーザーのミッション進捗判定を完全にスキップして終了するガード処理が機能していることを確認しました。キャンセル時や無効試合時の進捗誤加算はありません。
  • 【5回目】Discord API制限とBot再起動の挙動精査 (合格)
    MVP投票期間中(15分)にBotが再起動した場合のデータ保護(Firestore側は解決済みで保存され、不整合が起きない構造)や、Discordのロール付与時のレートリミットを考慮した非同期キューでの実行安全性を確認しました。

実機動作確認手順書

管理者や対戦プレイヤーが、Discord上で意図的に再現しテストするための手動検証手順です

ケース 1: 通常対戦報告とミッション進捗・レベルアップ通知

5人全員が一致した結果を報告し、レートとミッションが正しく自動更新・通知されるかを確認します。

  • 準備: プレイヤー5名(キラー1名、サバイバー4名)で対戦報告スレッドを開始します。
  • 操作: 5名全員が同じ試合結果(例: 「4逃げ」かつキラーのキャラクター「レイス」)を選択して投票ボタンを押します。
  • 確認項目 1: 5人目の投票が完了した瞬間に合意解決が走り、「レート更新完了」メッセージが投稿されること。
  • 確認項目 2: 同時に、スレッド内に [達成] ロールを問わず累計2試合プレイする などのミッション進行状況および獲得XPが投稿されること。
  • 確認項目 3: 獲得したXPによりレベルアップ閾値を跨いだ場合、スレッドに [LEVEL UP!] 通知が流れ、該当のロール付与キューへ登録されること。

ケース 2: MVP投票フェーズとMVPミッション進捗

解決後の「第2段階」のトランザクションに乗り、MVP系ミッションがアトミックに判定されるか確認します。

  • 準備: ケース1の解決が完了し、スレッド内に「MVP投票を行ってください」パネルが出現した状態にします。
  • 操作: 投票ボタンから特定のサバイバー(例: playerA)に投票を入れます(15分待つか、全員の投票を完了させます)。
  • 確認項目 1: MVPが確定したメッセージ(例: 「playerAがMVPに決定しました」)が投稿されること。
  • 確認項目 2: playerAがMVP獲得ミッションを所持している場合、即座に [達成] サバイバーでMVPを獲得する (獲得XP: 350) という通知が投稿されること。

ケース 3: 結果不一致時の自動投票リセットと警告メンション

投票報告に齟齬があった際のリセット動作およびストライク付与を確認します。

  • 準備: プレイヤー5名で対戦報告を開始します。
  • 操作: 4名が「4逃げ」を報告し、1名だけ「3逃げ」を報告します(※4人目が投票した時点では解決が走らず、5人目が投票した段階で判定が行われます)。
  • 確認項目 1: 5人目の投票完了後、自動的に不一致が判定され「投票結果が不一致となりました。全員もう一度正しく入力してください」と警告メンションが送信されること。
  • 確認項目 2: スレッド内の投票ボタンが再び有効化(リセット)され、再投票が可能になること。
  • 確認項目 3: 不一致報告を送信したプレイヤーのプロフィール(Firestore内)に、ストライク(不一致ペナルティ)が自動加算されていること。

ケース 4: 回線落ち(dc_penalty)発生時のミッション判定スキップ

切断が発生した無効扱いのマッチで、ミッション進捗が完全にスキップ(ガード)されるか確認します。

  • 準備: プレイヤー5名で対戦報告を開始します。
  • 操作: 報告ボタンから「回線落ち(dc_penalty:ユーザー名)」を報告します(5人全員がこれに合意するか、ADMINが強制適用します)。
  • 確認項目 1: 解決メッセージにおいて、切断者のレートが減少し、その他のプレイヤーは変動なしで解決されること。
  • 確認項目 2: スレッド内にミッション進捗やXP獲得の通知が一切投稿されないこと(回線落ちでのミッション稼ぎを防止するためのガード機能の検証)。

ケース 5: 同一試合の二重解決防止(トランザクションガード)

トランザクションガードにより、多重報告や遅延時の同時書き込みエラーが防止されるか確認します。

  • 操作: 投票解決中に報告ボタンをすばやく連打するか、またはすでに解決完了してステータスが finished になったマッチに対して再度投票結果を送信するよう試みます。
  • 確認項目: システムから「既に解決済みのマッチです」というエラーテキストが応答され、レート変動やミッションの二重加算が完全にブロックされること。

ミッション・バッジ候補

実装中の140種類のミッションプール、および全18種類の3Dデザインバッジ候補一覧

採用バッジ選択数: 0 / 18 個
採用通算ミッション数: 0

赤黒ゴールド調:3D実績バッジ一覧(全18種)

ミッションやレベル達成時にWebプロフィール上に永久表示される、3Dピンズ風デザインのバッジリストです。

始まりの篝火
始まりの篝火
リーグ戦で最初の1試合を完了する
通算1試合プレイ
不屈の生存者
不屈の生存者
サバイバー勝利を累計30回達成
サバ勝利30回
エンティティの寵児
エンティティの寵児
キラー勝利(全滅)を累計30回達成
キラー全滅30回
リーグの主役
リーグの主役
サバイバーでMVP投票選出が累計10回達成
サバMVP10回
鉄の意志
鉄の意志
シーズン累計100試合プレイを達成
シーズン100試合プレイ
団結 of 絆
団結 of 絆
サバ全員脱出を累計10回経験(サバ勝利で判定)
サバ勝利10回
百戦錬磨
百戦錬磨
シーズン中異なる5種類のキラーで各1勝達成
異なる5キラーで各1勝
皆殺しの魔王
皆殺しの魔王
キラー通算「全滅50回」達成
キラー全滅50回
凱旋のシンボル
凱旋のシンボル
キラー全滅とサバMVPを両方達成(通算実績)
全滅1回かつサバMVP1回
無敗の残響
無敗の残響
ロール不問で累計「10連勝」を達成
最大10連勝
歴戦の爪痕
歴戦の爪痕
リーグ通算で累計100回勝利を達成
通算100勝
リーグの鉄人
リーグの鉄人
リーグ通算「500試合プレイ」を達成
通算500試合プレイ
DERマスター
DERマスター
シーズンレベル50到達(通常パス完走)
シーズンレベル50到達
霧の覇者
霧の覇者
通算レベル150(DER Mythic ロール)に到達
通算レベル150到達
大虐殺の権化
大虐殺の権化
キラー通算「100回全滅」を達成
キラー全滅100回
阿修羅の極み
阿修羅の極み
異なる5キラーで各10勝達成
キラー通算80勝
死神の鎌
死神の鎌
シーズン累計100人処刑
シーズン100キル
霧 of 脱出王
霧 of 脱出王
サバイバー勝利 30回を達成
シーズンサバ勝利30回

ミッションプール(140選)とバッジ選択(30選)

運営へのプレゼン用に、採用したいミッションやバッジ候補をチェックして集計(クリップボードにデータとしてコピー)できます。

No難易度ミッション内容
No難易度ミッション内容
No難易度ミッション内容
No報酬XPミッション内容
No報酬XPミッション内容
選択No報酬XPミッション内容
選択No報酬XPミッション内容