概要

項目内容
案件 IDMAS-059
案件名1 人コンサルタント 非連続成長シミュレーター(4 レバー成長戦略)
カテゴリシミュレーション・成長戦略・FP&A
優先度P2 ★★★(一人法人 SMB の天井突破支援・MAS-057 cockpit の上位レイヤー)
所要時間約 1.5 ヶ月(週 10h 前提・Phase 1-3 計)
実装ステータス📝 仕様書段階・実装未着手(v2.0 = 2026-05-01 全面 scope reset)
対象ファイル(新規)400_domain/446_growth_strategy_engine.js(純粋関数 4 レバーシミュレーター・約 500 行)/ webapp_client/src/cockpit/GrowthStrategyPanel.tsx(左 4 スライダー + 右 2 チャート UI・約 700 行)
対象ファイル(変更)webapp_client/scripts/sync-engines.mjsENGINES_TO_SYNC に 446 追加)/ webapp_client/src/cockpit-main.tsx(副作用 import 追加)/ webapp_client/src/cockpit/calc.tscalcGrowthStrategy 公開)/ 300_ui/302_spa_bridge.js(bootstrap に sys_params 配信追加)/ 100_config/101_sys_config.js03_sys_params 12 キーシード)/ 000_infra/002_constants.jsMENU_DEFINITION に「🚀 成長戦略シミュレーター」追加)
新規シートなし(panel-local 入力 + 既存 03_sys_params 拡張のみ)
新規 03_sys_params キーF59_HOURS_PER_MONTH_SOFT_LIMIT(default 160 h)/ F59_HOURS_PER_MONTH_HARD_LIMIT(default 200 h)/ F59_PRICING_ELASTICITY(default 0.7・価格弾力性)/ F59_PRODUCTIZATION_BOOST_MULTIPLIER(default 1.5・最大生産性倍率)/ F59_HUMAN_LEVERAGE_OVERHEAD_RATIO(default 0.30・人員追加時の管理コスト比率)/ F59_CAPITAL_REINVEST_ROIC_HURDLE(default 0.15・再投資 ROIC 閾値)/ F59_CAPITAL_MNA_PREMIUM_DEFAULT(default 5・M&A EBITDA 倍率)/ F59_CAPITAL_DIVIDEND_HURDLE_RATE(default 0.05・配当機会費用)/ F59_BUDGET_OVER_THRESHOLD_RATIO(default 0.95・予算超過警告閾値)/ F59_LIMIT_PROFIT_STACKED_BAR_BASE_LABEL(default "Y0 ベースライン")/ F59_HOURS_LINE_BASELINE(default "現状稼働")/ F59_FORECAST_HORIZON_YEARS(default 5)の計 12 キー
前提案件MAS-057 Phase 3 cockpit ✅ 完了 (PR #379/#394/#454/#459) = SPA 基盤 + 副作用 import 規約 + sync-engines.mjs / MAS-058 必要年商ソルバー ✅ Step 4 完了 (PR #401) = RequiredRevenueSolver.solveRequiredRevenue / MAS-067 マルチイヤー ✅ v1.8 完了 (PR #418/#423/.../#454) = MultiyearPlanner.runFiveYearPL / MAS-066 配当ミックス ✅ 完了 (PR #402) = 配当連携基盤 / MAS-071 4 アプローチ役員報酬 ✅ 完了 (PR #457/#459) = CompensationStrategyEngine.simulateFourApproaches
後続連携MAS-072 企業価値スコアボード(4 レバー → EV スコア連動)/ MAS-060 組織構成シミュレーター(Human レバー Tool 化)/ MAS-061 Cash ETR(節税で Capital レバー貢献度化)/ MAS-144 規程ジェネレーター(Human レバー業務委託 / 採用 → 規程整備の前段)
scope reset 経緯(v1.x → v2.0)v1.0-v1.1(2026-04-27/28)は「統合意思決定ツリー UI + LangGraph + Postgres checkpointer」スコープで起草していたが、2026-05-01 のユーザー要望「1 人社長コンサル業の非連続成長 = 4 レバー(価格・生産物・人・資本)の組合せシミュレーター」を受けスコープ全面リセット。旧 v1.x スコープ(Decision Tree Orchestrator + LangGraph + Cloud SQL Postgres)は §A アーカイブとして末尾に保存し、必要なら別案件 MAS-XXX としてカーブアウト可能(MAS-361 候補・本 PR ではキャリーオーバー扱い)。

目的

1 人コンサルタントの事業が順調なのに、年収 1500-2000 万円台で頭打ちになる」課題に対し、4 つの成長レバー(Pricing / Product / Human / Capital)の組合せシミュレーターを提供する。

一人法人成長の天井 = 4 レバーの未活用

順調な 1 人コンサルは Y3-Y5 で以下の天井に到達:

天井数値的特徴既存案件で扱える?
時間天井月稼働 160h × 単価 5-8 万円 = 年商 1,600-1,920 万円× (MAS-057 は静的試算のみ)
市場天井同単価帯顧客の需要量 = 単一サービスでは不可避×
思考天井「もっと働くしかない」モードに固定化×
資本天井余剰 CF の使い道が銀行口座放置のみ× (MAS-066 配当ミックス、MAS-072 EV だけでは不十分)

これらの天井を非連続的に突破する 4 レバーを組合せ可視化し、「次に何のレバーを引くか」を意思決定可能にする。

4 レバー成長戦略フレーム(Deep Research 由来)

Gemini Deep Research(2026-04-30 実施)+ Claude 内部調査の突合により以下 4 レバーが世界の SMB 成長理論で共通項として確立されている:

レバー中核戦略数値効果(年商換算)主要施策
① Pricing 価格価値ベース価格設定 / 単価非連続上昇 / リテイナー化 / 成果報酬+30-100%顧客選別 / パッケージ化 / 段階的単価アップ
② Product 生産物デリバラブル化 / 製品化 / AI 補完 / 知識資産化(コース・著作・SaaS)+50-200%テンプレート化 / 反復販売 / 1 時間あたり収入の非線形化
③ Human 人的レバレッジ業務委託 / 配偶者役員化 / 採用 / マイクロ M&A+50-300%フリーランス活用 / 採用 BEP / 同業小規模事業者の買収
④ Capital 資本配分Buffett-Munger 階層(再投資 → M&A → 配当 → 自社株買い)CF 投下効率 +50-200%ROIC > WACC で再投資 / 5 年 NPV 比較

重要原則: 4 レバーは独立ではなく相互作用する(例: Product レバー [製品化] が成立すると Pricing レバー [単価アップ] が容易になる、Capital レバー [M&A] は Human レバー [人員拡張] に直結)。本シミュレーターは 4 レバーの組合せ効果を「限界利益スタックド棒グラフ」と「月間稼働時間ラインチャート」で同時可視化し、時間制約(物理上限 200h/月)と予算制約(固定費 + Capital 投下総額)を超えない範囲での最適組合せを探索可能にする。

MAS-072 / MAS-071 / MAS-067 / MAS-058 cockpit との関係

  • MAS-058 必要年商: 単年「希望年収 → 必要年商」逆算(1 シナリオ
  • MAS-067 マルチイヤー: 静的 5 年計画(B/S 引継ぎ + ステージ準備度
  • MAS-071 役員報酬 4 アプローチ: 報酬最適化(4 アプローチ比較
  • MAS-072 企業価値スコアボード: 経営の通信簿(3 評価手法
  • MAS-059 本案件: ⬆️ これらの上位レイヤー = 成長戦略 4 レバーの組合せ意思決定1 cockpit の中で動的に 4 軸を引いて天井突破

現在のコード(前提案件・利用関数)

MAS-058 必要年商ソルバー(✅ Step 4 完了 / PR #401)

関数定義ファイルシグネチャ用途
RequiredRevenueSolver.solveRequiredRevenue(input)400_domain/445_required_revenue_solver.js(input) → {min, healthy, buffered}希望年収から必要年商を逆算(Pricing レバー検証用)
RequiredRevenueSolver.evaluateScenarioHealth(input)400_domain/445_required_revenue_solver.js(input) → {feasible, riskLevel, runwayMonths}4 レバー組合せ後の年商シナリオを健全性評価

MAS-067 マルチイヤー計画(✅ v1.8 完了 / PR #454)

関数定義ファイルシグネチャ用途
MultiyearPlanner.runFiveYearPL(input)400_domain/451_multiyear_planner.js(input) → {pl[5], bs[5], cf[5], stageReadiness}Y1-Y5 P/L · B/S · CF · ステージ準備度(4 レバー適用後の 5 年シミュレーション基盤)

MAS-071 役員報酬 4 アプローチ(✅ v1.1 完了 / PR #457/#459)

関数定義ファイルシグネチャ用途
CompensationStrategyEngine.simulateFourApproaches(input)400_domain/454_compensation_strategy_engine.js(input) → {A, B, C, D}4 アプローチ役員報酬最適化(Capital レバー [配当 vs 報酬] 比較で活用)
CompensationStrategyEngine.calcLimitProfit(input)400_domain/454_compensation_strategy_engine.js:~120({revenue, cogs, fixedCost}) → number限界利益(Limit Profit)= 売上 − 変動費 − 固定費(4 レバー貢献度の積上げ基底値)

MAS-066 配当ミックス(✅ 完了 / PR #402)

関数定義ファイルシグネチャ用途
DividendMixOptimizer.simulateScan(input)400_domain/449_dividend_mix_optimizer.js(input) → {bestRatio, scenarios[]}Capital レバー [配当] の最適化(手残り最大化 vs 内部留保のトレードオフ)

MAS-057 SPA cockpit 基盤(✅ Phase 3 + Step 7 完了 / PR #379/#394/#454/#459)

部品パス役割
webapp_client/src/cockpit-main.tsxSPA エントリ副作用 import 規約(failure_patterns #33)で各 panel をマウント
webapp_client/src/cockpit/calc.tsclient-side 計算 hub各 panel の計算は calc.ts 経由で engine 呼出
webapp_client/scripts/sync-engines.mjsengine syncENGINES_TO_SYNC 配列で SPA bundle に GAS 純粋関数を取込
webapp_client/src/cockpit/CompensationDropdowns.tsxUI 規約離散単位ドロップダウン優先ai_agent_tips.md §7

_scrubInfinityForJSON_ 汎用ヘルパ(MAS-066 PR #402 で確立)

関数定義ファイル用途
_scrubInfinityForJSON_(value)300_ui/302_spa_bridge.js 末尾failure_patterns #29 対策(Infinity / NaN を null に変換)

修正方針

Step 1 — 400_domain/446_growth_strategy_engine.js 新設(純粋関数・約 500 行)

⚠️ ID 採番衝突回避(failure_patterns #31): ユーザー初期提案ファイル名は 400_domain/448_growth_strategy_engine.js だったが、448 は MAS-061 (448_cash_etr_simulator.js) で予約済で衝突発覚。次空き番号として MAS-059 v1.x で予約していた 446 slot を v2.0 で再利用(v1.x の 446_decision_tree_orchestrator.js は §A にアーカイブ・実体ファイル未作成のため slot 競合なし)。新規ドメインエンジン番号予約前に必ず grep -nE '400_domain/44[6-9]_' docs/dev/*.md で全使用状況を確認すること(dev_spec_prompt_template v1.10 Phase 1-A-pre 適用)。

// 400_domain/446_growth_strategy_engine.js (純粋関数 + IIFE 名前空間)

var GrowthStrategyEngine = (function () {

  // ─────────────────────────────────────────────────────────
  // ① Pricing レバー: 価格 × 顧客数 × 単価アップ
  // ─────────────────────────────────────────────────────────
  /**
   * @param {Object} input
   * @param {number} input.baseRevenue       Y0 ベース年商
   * @param {number} input.priceUpRatio      単価アップ率 (0-1, 例 0.30 = 30% 引上げ)
   * @param {number} input.elasticity        価格弾力性 (default 0.7)
   * @param {number} input.churnRiskRatio    顧客流出率 (single-elasticity モデル)
   * @returns {{deltaRevenue, deltaProfit, churnedClients, hoursDelta}}
   */
  function simulatePricingLever(input) {
    var elasticity = input.elasticity || 0.7;
    var churnRatio = elasticity * input.priceUpRatio;
    var newRevenue = input.baseRevenue * (1 + input.priceUpRatio) * (1 - churnRatio);
    var deltaRevenue = newRevenue - input.baseRevenue;
    return {
      deltaRevenue: deltaRevenue,
      deltaProfit: deltaRevenue,  // Pricing レバーは追加コストなし
      churnedClients: churnRatio,
      hoursDelta: 0,  // 時間は不変
    };
  }

  // ─────────────────────────────────────────────────────────
  // ② Product レバー: 製品化 / AI 補完 / 知識資産化
  // ─────────────────────────────────────────────────────────
  /**
   * @param {Object} input
   * @param {number} input.baseHourlyRevenue   Y0 1 時間あたり収入
   * @param {number} input.productizationLevel 0-5 (0=完全カスタム, 5=完全 SaaS)
   * @param {number} input.boostMultiplier     最大生産性倍率 (default 1.5)
   * @returns {{newHourlyRevenue, deltaProfit, hoursDelta, knowledgeAssetValue}}
   */
  function simulateProductLever(input) {
    var levelRatio = input.productizationLevel / 5;  // 0-1 normalize
    var boost = 1 + (input.boostMultiplier - 1) * levelRatio;
    var newHourlyRevenue = input.baseHourlyRevenue * boost;
    var deltaHourly = newHourlyRevenue - input.baseHourlyRevenue;
    return {
      newHourlyRevenue: newHourlyRevenue,
      deltaProfit: deltaHourly * (input.baseHours || 0),  // 同じ時間で多く稼ぐ
      hoursDelta: -input.baseHours * (1 - 1 / boost),  // 同売上を維持なら時間削減
      knowledgeAssetValue: input.baseRevenue * levelRatio * 0.20,  // 知識資産簿外価値
    };
  }

  // ─────────────────────────────────────────────────────────
  // ③ Human レバー: 業務委託 / 採用 / マイクロ M&A
  // ─────────────────────────────────────────────────────────
  /**
   * @param {Object} input
   * @param {number} input.contractorHours       業務委託時間 (月)
   * @param {number} input.contractorRate        業務委託単価
   * @param {number} input.employeeCount         採用人員 (整数)
   * @param {number} input.employeeAvgCost       採用人員単価 (年額・社保込)
   * @param {number} input.mnaTargetRevenue      マイクロ M&A 対象年商
   * @param {number} input.mnaPremiumMultiple    買収 EBITDA 倍率 (default 5)
   * @param {number} input.overheadRatio         管理コスト比率 (default 0.30)
   * @returns {{capacityDelta, costDelta, mnaInvestment, hoursDelta, requiresHitl}}
   */
  function simulateHumanLever(input) {
    var contractorAnnual = (input.contractorHours || 0) * 12 * (input.contractorRate || 0);
    var employeeAnnual = (input.employeeCount || 0) * (input.employeeAvgCost || 0)
      * (1 + (input.overheadRatio || 0.30));
    var mnaInvestment = (input.mnaTargetRevenue || 0) * (input.mnaPremiumMultiple || 5);
    var capacityDelta = (input.contractorHours || 0) * 12
      + (input.employeeCount || 0) * 2000;  // 正社員年間稼働 2000h
    return {
      capacityDelta: capacityDelta,  // 追加可能稼働時間 (年)
      costDelta: contractorAnnual + employeeAnnual,
      mnaInvestment: mnaInvestment,  // M&A 一時支出 (B/S 計上)
      hoursDelta: -capacityDelta * 0.6,  // CEO 自身の時間は委譲分削減 (60% 効率)
      requiresHitl: (input.employeeCount > 0) || (input.mnaTargetRevenue > 0),
    };
  }

  // ─────────────────────────────────────────────────────────
  // ④ Capital レバー: Buffett-Munger 階層 (再投資 → M&A → 配当 → 自社株買い)
  // ─────────────────────────────────────────────────────────
  /**
   * @param {Object} input
   * @param {number} input.surplusCf          余剰 CF
   * @param {number} input.reinvestRatio      再投資比率 (0-1)
   * @param {number} input.reinvestRoic       再投資 ROIC 想定
   * @param {number} input.mnaRatio           M&A 比率
   * @param {number} input.dividendRatio      配当比率 (MAS-066 連携)
   * @param {number} input.buybackRatio       自社株買い比率 (1 人法人では通常 0)
   * @param {number} input.roicHurdle         ROIC 閾値 (default 0.15)
   * @param {number} input.dividendHurdle     配当機会費用 (default 0.05)
   * @returns {{npvByOption, recommendedAllocation, totalNpv5y, warnings[]}}
   */
  function simulateCapitalLever(input) {
    var hurdle = input.roicHurdle || 0.15;
    var dividendHurdle = input.dividendHurdle || 0.05;
    var npvReinvest = (input.reinvestRoic >= hurdle)
      ? input.surplusCf * input.reinvestRatio * _annuityFactor_(5, input.reinvestRoic)
      : 0;
    var npvMna = input.surplusCf * input.mnaRatio * _annuityFactor_(5, hurdle);
    var npvDividend = input.surplusCf * input.dividendRatio * _annuityFactor_(5, dividendHurdle);
    var npvBuyback = input.surplusCf * (input.buybackRatio || 0) * _annuityFactor_(5, hurdle);
    var warnings = [];
    if (input.reinvestRoic < hurdle && input.reinvestRatio > 0) {
      warnings.push("再投資 ROIC " + (input.reinvestRoic * 100).toFixed(1)
        + "% が閾値 " + (hurdle * 100).toFixed(0) + "% を下回る — 配当 / M&A を検討");
    }
    return {
      npvByOption: {
        reinvest: npvReinvest,
        mna: npvMna,
        dividend: npvDividend,
        buyback: npvBuyback,
      },
      recommendedAllocation: _rankByNpv_(npvReinvest, npvMna, npvDividend, npvBuyback),
      totalNpv5y: npvReinvest + npvMna + npvDividend + npvBuyback,
      warnings: warnings,
    };
  }

  // ─────────────────────────────────────────────────────────
  // 統合 API: runGrowthStrategy(input) — 4 レバーを順次計算
  // ─────────────────────────────────────────────────────────
  /**
   * @param {Object} input
   * @param {number} input.baseRevenue
   * @param {number} input.baseHours       Y0 ベース月稼働時間
   * @param {Object} input.pricingInput
   * @param {Object} input.productInput
   * @param {Object} input.humanInput
   * @param {Object} input.capitalInput
   * @param {Object} input.constraints     {hoursSoftLimit, hoursHardLimit, budgetTotal}
   * @returns {{
   *   levers: {pricing, product, human, capital},
   *   stackedBarData: Array<{year, pricing, product, human, capital, base}>,
   *   hoursLineData: Array<{year, hours, softLimit, hardLimit}>,
   *   budgetOverWarning: {flag, message, amount} | null,
   *   requiresHitl: boolean,
   *   limitProfitTotal: number,
   *   feasibility: 'feasible' | 'tight' | 'infeasible'
   * }}
   */
  function runGrowthStrategy(input) {
    var pricing = simulatePricingLever(input.pricingInput);
    var product = simulateProductLever(input.productInput);
    var human = simulateHumanLever(input.humanInput);
    var capital = simulateCapitalLever(input.capitalInput);

    // 5 年スタックドバー組立 (Y0-Y5)
    var horizon = input.constraints.forecastHorizonYears || 5;
    var stackedBarData = _buildStackedBarData_(input.baseRevenue, pricing, product, human, capital, horizon);

    // 月間稼働時間ラインチャート組立
    var hoursLineData = _buildHoursLineData_(input.baseHours, pricing, product, human,
      input.constraints.hoursSoftLimit || 160, input.constraints.hoursHardLimit || 200, horizon);

    // 予算オーバー警告
    var totalCost = (human.costDelta || 0) + (human.mnaInvestment || 0)
      + (capital.npvByOption.reinvest > 0 ? input.capitalInput.surplusCf * input.capitalInput.reinvestRatio : 0);
    var budgetThreshold = (input.constraints.budgetTotal || 0)
      * (input.constraints.budgetOverThresholdRatio || 0.95);
    var budgetOverWarning = (totalCost > budgetThreshold) ? {
      flag: true,
      message: "総支出 " + _formatJpy_(totalCost) + " が予算枠 "
        + _formatJpy_(input.constraints.budgetTotal) + " の 95% を超過",
      amount: totalCost,
    } : null;

    // feasibility 判定
    var maxHours = Math.max.apply(null, hoursLineData.map(function (d) { return d.hours; }));
    var feasibility = (maxHours > (input.constraints.hoursHardLimit || 200))
      ? 'infeasible'
      : (maxHours > (input.constraints.hoursSoftLimit || 160) ? 'tight' : 'feasible');

    return {
      levers: { pricing: pricing, product: product, human: human, capital: capital },
      stackedBarData: stackedBarData,
      hoursLineData: hoursLineData,
      budgetOverWarning: budgetOverWarning,
      requiresHitl: human.requiresHitl,
      limitProfitTotal: pricing.deltaProfit + product.deltaProfit + (capital.totalNpv5y / horizon),
      feasibility: feasibility,
    };
  }

  // ─────────────────────────────────────────────────────────
  // 内部ヘルパ
  // ─────────────────────────────────────────────────────────
  function _annuityFactor_(years, rate) {
    if (rate === 0) return years;
    return (1 - Math.pow(1 + rate, -years)) / rate;
  }

  function _rankByNpv_(reinvest, mna, dividend, buyback) {
    var options = [
      { key: 'reinvest', npv: reinvest },
      { key: 'mna', npv: mna },
      { key: 'dividend', npv: dividend },
      { key: 'buyback', npv: buyback },
    ];
    options.sort(function (a, b) { return b.npv - a.npv; });
    return options;
  }

  function _buildStackedBarData_(baseRevenue, pricing, product, human, capital, horizon) {
    var data = [];
    for (var y = 0; y <= horizon; y++) {
      var growthFactor = y / horizon;  // 線形ランプアップ
      data.push({
        year: 'Y' + y,
        base: baseRevenue,
        pricing: pricing.deltaProfit * growthFactor,
        product: product.deltaProfit * growthFactor,
        human: (human.capacityDelta * 0.5) * growthFactor,  // 容量増 → 売上換算
        capital: (capital.totalNpv5y / horizon) * (y > 0 ? 1 : 0),  // Y1 以降に発現
      });
    }
    return data;
  }

  function _buildHoursLineData_(baseHours, pricing, product, human, softLimit, hardLimit, horizon) {
    var data = [];
    for (var y = 0; y <= horizon; y++) {
      var growthFactor = y / horizon;
      var hours = baseHours
        + pricing.hoursDelta * growthFactor
        + product.hoursDelta * growthFactor
        + human.hoursDelta * growthFactor;
      data.push({
        year: 'Y' + y,
        hours: Math.max(0, hours),
        softLimit: softLimit,
        hardLimit: hardLimit,
      });
    }
    return data;
  }

  function _formatJpy_(amount) {
    return Math.round(amount).toLocaleString('ja-JP') + ' 円';
  }

  return {
    simulatePricingLever: simulatePricingLever,
    simulateProductLever: simulateProductLever,
    simulateHumanLever: simulateHumanLever,
    simulateCapitalLever: simulateCapitalLever,
    runGrowthStrategy: runGrowthStrategy,
  };
})();

純粋性の維持: SpreadsheetApp / Repository / PropertiesService 一切呼ばず、全て input で完結。MAS-058 / MAS-066 / MAS-067 / MAS-071 と同型の Pure Function 規約(failure_patterns #25 対称性遵守)。

Step 2 — webapp_client/src/cockpit/GrowthStrategyPanel.tsx 新設(約 700 行)

// 左 4 スライダー + 右 2 チャート + 下部予算オーバー警告

import React, { useState, useMemo } from 'react';
import { calcGrowthStrategy } from './calc';

const GrowthStrategyPanel: React.FC<Props> = ({ baseRevenue, baseHours, sysParams }) => {
  const [pricingLevel, setPricingLevel] = useState(0);   // 0-5
  const [productLevel, setProductLevel] = useState(0);
  const [humanLevel, setHumanLevel] = useState(0);
  const [capitalLevel, setCapitalLevel] = useState(0);

  const result = useMemo(() => calcGrowthStrategy({
    baseRevenue, baseHours,
    pricingInput: { baseRevenue, priceUpRatio: pricingLevel * 0.10 /* 0-50% */ },
    productInput: { baseHourlyRevenue: baseRevenue / (baseHours * 12), productizationLevel: productLevel },
    humanInput: _mapHumanLevel(humanLevel),
    capitalInput: _mapCapitalLevel(capitalLevel),
    constraints: sysParams,
  }), [pricingLevel, productLevel, humanLevel, capitalLevel, baseRevenue, baseHours]);

  return (
    <div className="growth-strategy-panel">
      <div className="left-pane">
        <h3>🚀 4 成長レバー</h3>
        <SliderRow label="① Pricing 価格" value={pricingLevel} onChange={setPricingLevel}
          marks={['現状', '+10%', '+20%', '+30%', '+40%', '+50%']} />
        <SliderRow label="② Product 製品化" value={productLevel} onChange={setProductLevel}
          marks={['完全カスタム', '...', '...', '...', '...', '完全 SaaS']} />
        <SliderRow label="③ Human 人的レバレッジ" value={humanLevel} onChange={setHumanLevel}
          marks={['1 人', '+業委 80h', '+業委 160h', '+正社 1', '+正社 2', '+M&A']} />
        <SliderRow label="④ Capital 資本配分" value={capitalLevel} onChange={setCapitalLevel}
          marks={['全額留保', '配当 25%', '再投資 50%', 'M&A 50%', '再投資 80%', 'M&A 80%']} />

        {result.requiresHitl && <HitlBadge message="採用 / M&A は HITL 承認必須" />}
      </div>

      <div className="right-pane">
        <div className="chart-stacked-bar">
          <h4>限界利益スタックドバー (Y0-Y5)</h4>
          <LimitProfitStackedBar data={result.stackedBarData} />
        </div>
        <div className="chart-hours-line">
          <h4>月間稼働時間 (時間制約: 160h ソフト / 200h ハード)</h4>
          <MonthlyHoursLineChart data={result.hoursLineData} />
        </div>
      </div>

      {result.budgetOverWarning && (
        <BudgetOverWarningBanner warning={result.budgetOverWarning} />
      )}

      <FeasibilityIndicator level={result.feasibility} />
    </div>
  );
};

Step 3 — webapp_client/scripts/sync-engines.mjsENGINES_TO_SYNC 拡張

const ENGINES_TO_SYNC = [
  // ... 既存
  '400_domain/446_growth_strategy_engine.js',  // ← 追加
];

Step 4 — webapp_client/src/cockpit-main.tsx 副作用 import 追加

// failure_patterns #33 対策: panel-level の useEffect ベースエントリは
// import 副作用で必ず登録する
import './cockpit/GrowthStrategyPanel';

Step 5 — webapp_client/src/cockpit/calc.ts への calcGrowthStrategy 公開

export function calcGrowthStrategy(input) {
  // GAS 純粋関数を direct call (sync-engines.mjs で bundle 済)
  const result = GrowthStrategyEngine.runGrowthStrategy(input);
  // failure_patterns #29: Infinity / NaN を null に変換
  return scrubInfinityForJSON(result);
}

Step 6 — 300_ui/302_spa_bridge.js bootstrap に F59_* sys_params 配信追加

function _buildF59CockpitBootstrap_() {
  return {
    f59Params: {
      hoursPerMonthSoftLimit: Constants.getParam('F59_HOURS_PER_MONTH_SOFT_LIMIT', 160),
      hoursPerMonthHardLimit: Constants.getParam('F59_HOURS_PER_MONTH_HARD_LIMIT', 200),
      pricingElasticity: Constants.getParam('F59_PRICING_ELASTICITY', 0.7),
      productizationBoostMultiplier: Constants.getParam('F59_PRODUCTIZATION_BOOST_MULTIPLIER', 1.5),
      humanLeverageOverheadRatio: Constants.getParam('F59_HUMAN_LEVERAGE_OVERHEAD_RATIO', 0.30),
      capitalReinvestRoicHurdle: Constants.getParam('F59_CAPITAL_REINVEST_ROIC_HURDLE', 0.15),
      capitalMnaPremiumDefault: Constants.getParam('F59_CAPITAL_MNA_PREMIUM_DEFAULT', 5),
      capitalDividendHurdleRate: Constants.getParam('F59_CAPITAL_DIVIDEND_HURDLE_RATE', 0.05),
      budgetOverThresholdRatio: Constants.getParam('F59_BUDGET_OVER_THRESHOLD_RATIO', 0.95),
      forecastHorizonYears: Constants.getParam('F59_FORECAST_HORIZON_YEARS', 5),
    }
  };
}

Step 7 — 100_config/101_sys_config.jsF59_* 12 キーシード追加

confSheet.appendRow パターン(MAS-066 / MAS-067 と同型)で 12 キーを 03_sys_params に投入。default 値は注意事項 #4 の運用調整余地を残し Constants.getParam の第 2 引数 fallback を併用。

影響範囲

対象種別変更内容リスク
400_domain/446_growth_strategy_engine.js追加GrowthStrategyEngine 名前空間 (4 レバー pure function + runGrowthStrategy + 内部ヘルパ・約 500 行)既存ロジックへの影響なし
webapp_client/src/cockpit/GrowthStrategyPanel.tsx追加左 4 スライダー + 右 2 チャート + 予算超過警告 + feasibility indicator (約 700 行)MAS-057 cockpit-main.tsx の追加 panel として独立
webapp_client/scripts/sync-engines.mjs変更ENGINES_TO_SYNC に 446 追加bundle サイズ +500 行・既存 engine sync に影響なし
webapp_client/src/cockpit-main.tsx変更import './cockpit/GrowthStrategyPanel' 副作用 import 追加failure_patterns #33 対策
webapp_client/src/cockpit/calc.ts変更calcGrowthStrategy 公開関数追加・scrubInfinityForJSON 流用既存計算 hub に影響なし
300_ui/302_spa_bridge.js変更_buildF59CockpitBootstrap_ 追加 + doGet の bootstrap mergefailure_patterns #29 (_scrubInfinityForJSON_ は MAS-066 PR #402 で確立済)
100_config/101_sys_config.js変更confSheet.appendRow で 12 キー追加シード未実行でも Constants.getParam 第 2 引数 default で動作
000_infra/002_constants.js変更MENU_DEFINITION に「🚀 成長戦略シミュレーター」追加(cockpit から独立タブ起動)既存メニューに影響なし
900_test/901_test_runner.js変更F059-01〜F059-18 単体テスト追加既存テストへの影響なし
MAS-057 cockpit連携拡張パネル並び: 健全性診断 → 4 アプローチ → EV → 🚀 成長戦略(最下部追加・MAS-072 直下)既存 cockpit に影響なし
appsscript.json変更なしOAuth スコープは v1 で変更なし(Postgres 移行は §A 旧スコープ保留・本案件 v2.0 ではスコープ外)failure_patterns #26 遵守

注意事項

  1. 【failure_patterns #31】ID 採番衝突回避(v1.x → v2.0 の slot 継承): ユーザー初期提案 400_domain/448_growth_strategy_engine.jsMAS-061 (448_cash_etr_simulator.js) で予約済のため衝突。MAS-059 v1.x で予約していた 446 slot を v2.0 で再利用(v1.x の 446_decision_tree_orchestrator.js は §A アーカイブで実体未作成のため slot 競合なし)。grep -nE '400_domain/44[6-9]_' docs/dev/*.md 結果: 446 = MAS-059 v1.x(旧)/ 447 = MAS-060 (workforce_mix_optimizer 予約) / 448 = MAS-061 (cash_etr_simulator 予約) / 449 = MAS-066 (dividend_mix ✅ 完了)。新規 slot 予約前に必ず全使用状況を grep 確認

  2. 【failure_patterns #18-#20】命名造語の禁止(必読): simulatePricingLever / simulateProductLever / simulateHumanLever / simulateCapitalLever / runGrowthStrategy は MAS-058 (solveRequiredRevenue) / MAS-067 (runFiveYearPL) / MAS-071 (simulateFourApproaches) と命名対称(動詞 + 目的語)。runGrowthStrategy は造語ではなく業界標準(McKinsey 4 Levers / BCG Growth-Share Matrix の延長)。実装着手前に必ず 400_domain/445_required_revenue_solver.js / 400_domain/451_multiyear_planner.js / 400_domain/454_compensation_strategy_engine.js を Read で確認し、関数シグネチャの整合性を裏取り。

  3. 【failure_patterns #25】並列実装対称性: MAS-058 / MAS-066 / MAS-067 / MAS-071 と純粋関数 + IIFE 名前空間 + Repository 注入なし(panel-local 入力モード)パターンで対称。runGrowthStrategy(input)MultiyearPlanner.runFiveYearPL(input)CompensationStrategyEngine.simulateFourApproaches(input) の API シグネチャ整合(input 全 plain object / output 全 plain object)。

  4. 【failure_patterns #26】appsscript.json は v1 段階で変更なし: 4 レバー全て純粋関数 + 既存 sys_params 配信パターンで完結。Cloud SQL Postgres 移行 / LangGraph 統合は §A 旧 v1.x スコープに保留しており、本 v2.0 ではスコープ外。OAuth スコープ追加は v2 以降の別 PR で実施。

  5. 【failure_patterns #29】Infinity / NaN の JSON 配信: simulateCapitalLever_annuityFactor_rate=0 時の特例処理を実装済。さらに 300_ui/302_spa_bridge.js_scrubInfinityForJSON_f59Params 配信前に必ず通す(MAS-066 PR #402 で確立した汎用ヘルパ)。

  6. 【failure_patterns #33】副作用 import の必須化: webapp_client/src/cockpit-main.tsximport './cockpit/GrowthStrategyPanel' を追加しないと、本番ビルドで panel が tree-shaking で消える。MAS-066 実装中に発覚した bug pattern(commit 41305ea で fix 済)の再発防止。

  7. 時間制約(物理上限)の硬性ガード: F59_HOURS_PER_MONTH_HARD_LIMIT (default 200h) を超える組合せは feasibility: 'infeasible' で警告表示し、ユーザーに「Human レバーを引かないと達成不可」と明示。1 人法人 CEO の自身稼働時間は週 50h × 4 週 = 200h を物理上限とし、それ以上は Human レバー(業務委託 / 採用 / M&A)を必須化。

  8. Pricing 弾力性の前提: F59_PRICING_ELASTICITY (default 0.7) は経済学の標準弾力性レンジ(0.5-1.0)で、コンサル業種特性として「単価 +30% → 顧客流出 21%」を意味する保守値。実運用ではユーザー業種(IT コンサル / 戦略コンサル / 業務コンサル)で調整余地あり、03_sys_params で運用調整可能。

  9. Product レバーの製品化レベル定義: productizationLevel 0-5 は離散単位(dropdown 推奨・ai_agent_tips.md §7 準拠)。0 = 完全カスタム / 5 = 完全 SaaS / 1-4 = 段階的(テンプレート化 → ガイドブック → コース → 半自動 SaaS)。boost multiplier F59_PRODUCTIZATION_BOOST_MULTIPLIER (default 1.5) は最大生産性倍率で、レベル 5 で 1.5 倍(同じ時間で 1.5 倍稼ぐ)。

  10. Human レバーの HITL 強制: simulateHumanLeveremployeeCount > 0 または mnaTargetRevenue > 0 の組合せは requiresHitl: true を返し、UI 側で必ず承認モーダルを挟む(PRD プロダクトポリシー Human-in-the-Loop 原則準拠)。Pricing / Product レバーは数値変更のみで HITL 不要、Capital レバーは閾値超過時のみ HITL(注意事項 #11)。

  11. Capital レバー Buffett-Munger 階層の優先順位: 4 オプション(再投資 / M&A / 配当 / 自社株買い)の NPV ランキングを表示。1 人法人で自社株買いは通常 0(株主 = 代表者 1 名のため自社株買いの意味なし)。default では buybackRatio: 0、UI でも非表示推奨。再投資 ROIC が F59_CAPITAL_REINVEST_ROIC_HURDLE (default 15%) を下回る場合、warnings に「配当 / M&A を検討」が出る(バフェット第 1 原則: ROIC > WACC でなければ再投資せず配当を選ぶ)。

  12. 限界利益(Limit Profit)の積上げ規約: LimitProfitStackedBar の Y 軸 = 限界利益(売上 − 変動費 − 固定費)。各レバーの寄与は deltaProfit で積上げる(base = Y0 限界利益、各色 = 4 レバーの追加寄与)。MAS-071 calcLimitProfit と整合(変動費 = 原価率 × 売上、固定費 = 月額固定費 × 12)。

  13. マイクロ M&A の B/S 影響: simulateHumanLevermnaInvestment は M&A 一時支出(B/S のれん計上 + キャッシュアウト)。Y0 で B/S 計上 + Y1 以降に統合効果(capacityDelta として年次反映)。詳細な PMI(Post-Merger Integration)コストは v1 で簡易扱い(買収プレミアム × 5 = EBITDA × 5 倍数で一括)。実運用では税務 DD・労務 DD コストを別途検討(人間検討事項 #6)。

  14. 予算オーバー警告のしきい値: F59_BUDGET_OVER_THRESHOLD_RATIO (default 0.95) で「予算枠の 95% 到達で警告」を default。100% を超えると feasibility: 'infeasible' に降格。ユーザーが Capital レバー [再投資 80%] + Human レバー [採用 + M&A] を同時最大化した場合の「夢追いシナリオ警告」として機能。

  15. シナリオ保存 (v2 拡張余地): v1 では panel-local 入力 + URL クエリパラメータ保存(?growthStrategy=p3,p2,h4,c2)を default。シナリオ永続化(40_scenario_registry 連携)は v2 拡張として留保(MAS-067 / MAS-066 同型・必要時に Spreadsheet 保存追加)。

エッジケース

#条件期待される挙動理由・ログ出力
1全レバー = 0(現状維持)base のみ stacked bar / 現状稼働時間 lineY0 ベースライン表示
2全レバー最大(Pricing+50% / Product=5 / Human=+M&A / Capital 80% 再投資)feasibility = 'infeasible' + 予算オーバー警告 + HITL 強制物理時間 + 予算超過 + 採用 / M&A 重複
3Pricing +50% 単独引上げpricing.churnedClients 35% 表示 + 売上 +30%(弾力性 0.7 反映)高単価少数顧客戦略の前提確認
4Product レベル 5 + Pricing 0productLever.knowledgeAssetValue > 0 + hours -40% (productivity 1.5x)製品化で時間圧縮
5Human レバー [業務委託のみ]requiresHitl: false(フリーランスは契約のため HITL 不要)+ capacityDelta 増業務委託 vs 採用の責任範囲差
6Human レバー [採用 1 名]requiresHitl: true + 雇用契約 / 社保 / 規程整備の前提MAS-144 規程ジェネレーター連携を促す警告
7Human レバー [マイクロ M&A]mnaInvestment > 0 + B/S のれん計上 + 税務 DD 警告買収プレミアム 5 倍 + 簿外債務 20% を gross-up(注意事項 #13)
8Capital レバー再投資 ROIC < 15%warnings: ["再投資 ROIC が閾値を下回る - 配当 / M&A を検討"]バフェット第 1 原則違反警告
9Capital レバー全配当 100%npvByOption.dividend のみ + 再投資 ゼロMAS-066 配当ミックス連携で税効率最適化を促す
10余剰 CF = 0(赤字期)全 Capital レバー npv = 0 + 「Capital レバー前に Pricing/Product/Human を先行検討」UI ヒント赤字フェーズで Capital を引いても無意味
11baseHours = 200h(既に物理上限)Human レバーなしで他のレバーだけ引くと feasibility = 'tight' or 'infeasible'1 人で天井到達済の警告
12弾力性 = 0(顧客流出ゼロ前提)Pricing +50% で売上 +50% 全反映独占的サービスの仮定(楽観値・実運用では default 0.7 推奨)
13弾力性 = 1.0(完全弾力的)Pricing +50% で売上 ±0コモディティサービスの警告
14productizationLevel = 5 でも baseHours = 0knowledgeAssetValue 計算可・hoursDelta = 0既に時間ゼロなら時間圧縮効果なし
15M&A 対象年商 = 0(買収先未定)mnaInvestment = 0 + 「対象先を入力してください」ヒントUI 側で入力ガイド
16予算枠 = 0(無入力)予算オーバー警告は出ず、feasibility のみ判定制約なしでの理論値表示モード
17Infinity / NaN(不正入力)_scrubInfinityForJSON_ で null 化 + UI 「入力エラー」failure_patterns #29 対策
18forecastHorizonYears = 1(短期)stackedBar 1 年分のみ + Capital レバーは Y0 全反映短期シナリオ表示

実データ検証 / テスト

F059-01〜F059-18 単体テスト(901_test_runner.js

#テスト名入力期待値失敗時の影響
F059-01Pricing +30% 単独baseRevenue 1500万 / 弾力性 0.7deltaRevenue ≈ +85万、churnedClients 21%価格弾力性ロジック検証
F059-02Pricing +50% 単独baseRevenue 1500万 / 弾力性 0.7deltaRevenue ≈ +97万、churnedClients 35%高引上げ時の流出反映
F059-03Product レベル 5 単独baseRevenue 1500万 / boost 1.5newHourlyRevenue × 1.5、hoursDelta -33%製品化生産性検証
F059-04Human 業務委託 80hcontractorHours 80 / rate 1万円costDelta = 96万、capacityDelta 960h、HITL false業務委託 = HITL 不要
F059-05Human 採用 1 名employeeCount 1 / avgCost 580万costDelta = 754万 (+30% overhead)、HITL true採用 = HITL 必須
F059-06Human M&A 1500万mnaTargetRevenue 1500万 / multiple 5mnaInvestment = 7500万、HITL trueM&A 倍数 5 反映
F059-07Capital 再投資 ROIC 20%surplusCf 1000万 / reinvestRatio 0.5 / roic 0.2 / hurdle 0.15npvReinvest > 0、warnings なしROIC > 閾値で warn なし
F059-08Capital 再投資 ROIC 10%surplusCf 1000万 / reinvestRatio 0.5 / roic 0.10 / hurdle 0.15npvReinvest = 0、warnings 1 件ROIC < 閾値 warn 発動
F059-09Capital 全配当surplusCf 1000万 / dividendRatio 1.0npvDividend > 0、recommendedAllocation[0] = dividend配当ランキング検証
F059-104 レバー組合せ最大Pricing 0.5 / Product 5 / Human +M&A / Capital 全再投資feasibility 'infeasible' + budgetOverWarning + HITL過剰組合せ警告
F059-11全レバー 0全 input 0base のみ + warnings 0ベースライン
F059-12時間ハード上限超過baseHours 200 + Pricing+50% で hoursDelta 微増feasibility 'tight' or 'infeasible'物理時間ガード
F059-13予算枠 95% 超過totalCost 950万 / budget 1000万budgetOverWarning.flag = true予算オーバー警告
F059-14Infinity 注入reinvestRoic = Infinitynpv = null、warnings に「不正入力」failure_patterns #29
F059-15NaN 注入priceUpRatio = NaNdeltaRevenue = nullfailure_patterns #29
F059-16annuityFactor rate=0rate 0 / years 5factor = 5(特例処理)数学エッジケース
F059-17stackedBar Y5 線形ランプhorizon 5 / pricing.deltaProfit 100万Y5 で 100万、Y2 で 40万線形ランプ検証
F059-18hours line baseHours 160baseHours 160 / human.hoursDelta -50Y5 で 110h時間削減反映

齋藤 Baseline 多年検証(手動)

シナリオ入力期待観察
A (現状維持)全レバー 0Y0 = Y5 = 限界利益 1,200万、稼働 160h
B (Pricing+30% のみ)Pricing slider 3Y5 限界利益 +85万、顧客流出 21% 警告
C (Product 5 + Pricing+30%)Product 5 + Pricing 3Y5 限界利益 +250万、稼働 -33%、知識資産 300万
D (フル拡張)全レバー maxfeasibility 'infeasible' + 「Human 必須」警告

Limit Profit Stacked Bar の整合性

webapp_client/src/cockpit/calc.tscalcGrowthStrategy の output stackedBarData が以下を満たすか単体テスト:

  • Y0 row: pricing/product/human/capital 全て 0、base のみ
  • Y5 row: 各色の合計 = limitProfitTotal
  • 中間年: 線形ランプ(growthFactor = y / horizon)

Monthly Hours Line Chart の整合性

hoursLineData が以下を満たすか単体テスト:

  • 全 row で softLimit / hardLimit 一定
  • hours が baseHours から線形に変化
  • Human レバー引いた場合に hours が減少

関連ドキュメント

カテゴリドキュメント関係
MAS-058 必要年商ソルバーdev_mas-058_required_revenue_solver.mdPricing レバー検証用 (solveRequiredRevenueevaluateScenarioHealth 経由で呼出)
MAS-067 マルチイヤー計画dev_mas-067_multiyear_planning_workspace.md5 年 P/L · B/S · CF 基盤(4 レバー適用後の年次反映)
MAS-071 役員報酬 4 アプローチdev_mas-071_compensation_strategy_simulator.mdCapital レバー [報酬 vs 配当] 比較・限界利益計算式
MAS-066 配当ミックスdev_mas-066_dividend_mix_optimizer.mdCapital レバー [配当] の手残り最大化
MAS-072 企業価値スコアボードdev_mas-072_valuation_scoreboard.md4 レバー → EV スコア連動(後続案件)
MAS-057 Solo-CEO Cockpitdev_mas-057_solo_ceo_cockpit.mdSPA 基盤 + 副作用 import 規約 + sync-engines.mjs
MAS-060 組織構成シミュレーターdev_mas-060_workforce_mix_optimizer.mdHuman レバー Tool 化(業務委託 / 採用ミックス最適化)
MAS-061 Cash ETRdev_mas-061_cash_etr_tracking.md節税 → Capital レバー貢献度化(合法節税範囲)
MAS-144 規程ジェネレーターdev_mas-144_regulation_generator.mdHuman レバー(採用 / 業務委託)→ 規程整備の前段
PRD プロダクトポリシーprd.mdHuman-in-the-Loop 原則(採用 / M&A 強制 HITL)
failure_patternsfailure_patterns.md特に #18-#20(命名造語)/ #25(並列実装対称性)/ #26(OAuth スコープ)/ #29(Infinity/NaN)/ #31(ID 採番衝突)/ #33(副作用 import)
ai_agent_tips.md §7ai_agent_tips.mdUI: スライダー禁止 → 離散単位ドロップダウン優先
CLAUDE.mdCLAUDE.mdプロジェクトルール・GAS ファイル番号体系・推奨実行モデル
BRD Solo-CEO Financial Navigatorbrd_solo_ceo_financial_navigator.md「天井突破 = 4 レバー」フレームの戦略的位置付け

人間が検討すべき事項

  1. 4 レバーの相互作用モデル: v1 は各レバー独立計算(足し算)。実運用では Product レバー成立 → Pricing レバー容易、Capital レバー [M&A] → Human レバー [採用] 自動連動など相互増幅がある。v2 で相関係数モデルに拡張するか。

  2. 価格弾力性の業種別カスタマイズ: F59_PRICING_ELASTICITY (default 0.7) は IT コンサル想定。戦略コンサル(弾力性 0.5・希少性高)/ 業務コンサル(弾力性 0.9・代替容易)で大きく異なる。業種別 default を Constants.BUSINESS_TYPE_ELASTICITY_MAP に追加するか。

  3. 製品化レベル 0-5 の境界定義: レベル 1-4 の中間段階(テンプレート / ガイド / コース / 半自動)を離散ドロップダウンで表現するか、連続スライダーにするか。ai_agent_tips.md §7 準拠なら離散だが、4 レバー UI で他 3 レバーが連続だと不揃い。

  4. マイクロ M&A の対象先入力 UX: 「対象年商 1500 万 + プレミアム 5 倍」だけでは粗い。実運用では業種・PMI コスト・税務 DD コスト・労務 DD コスト・買収後の文化統合リスクが必要。v2 で MnaTargetInput panel を別 panel として分離するか。

  5. Buffett-Munger 階層の 1 人法人特化: 自社株買いは 1 人法人で意味なし → default 非表示の判断は妥当か。配当 vs 内部留保のトレードオフは MAS-066 配当ミックスに委譲、再投資 vs M&A は本案件で扱う、自社株買いは商用化期に解禁、で OK か。

  6. PMI コストの簡易扱い: 注意事項 #13 で「v1 で簡易扱い」としたが、買収プレミアム × 5(EBITDA 5 倍)だけでは過小評価リスクあり。日本中小 M&A 平均 PMI コスト = 買収額の 10-20%(経済産業省調査)を簡易加算するか。

  7. 時間ハード上限 200h の医療学的根拠: 週 50h × 4 週は労基法 36 協定上限超え(45h × 12 月)。1 人法人 CEO は労基法対象外だが、健康面では週 60h を超えると過労リスク。F59_HOURS_PER_MONTH_HARD_LIMIT default を 240(週 60h)に上げるか、180(週 45h)に下げるか。

  8. シナリオ保存方式: v1 = URL クエリパラメータ、v2 = 40_scenario_registry 永続化。マルチイヤー(MAS-067)と同型でシナリオ DB 統合するか、独立 spreadsheet シートにするか。

  9. HITL 承認モーダルの UX: 採用 / M&A の HITL は「承認ボタン押下」だけでは弱い。承認文言の自動生成(採用 1 名 → 「年間 754万のキャッシュアウト + 雇用契約 / 規程整備が必要 → 承認しますか?」)と承認履歴ログ(誰がいつ承認したか)を実装するか。

  10. 多通貨対応: 海外 M&A / 海外採用 / 海外配当の場合、現状 JPY hardcoding。商用化時に通貨切替(USD / JPY / EUR)を支援するか。

  11. Capital レバー [M&A] の機会費用計算: M&A NPV は買収後 5 年シナジーを _annuityFactor_(5, hurdle) で割引。実運用では PMI 失敗リスク(IRR ベース 30% 失敗確率)を反映する確率調整 NPV に拡張するか。

  12. シミュレーション履歴の AI レビュー: 4 レバー組合せの「過去 X 回試行で何を選んだか」を記録し、Gemini Deep Think で「あなたは Pricing レバーを過大評価する傾向があります」等のメタ分析を提供するか(v3 拡張)。

  13. 限界利益スタックドバーの色彩設計: 4 レバー(Pricing 青 / Product 緑 / Human 橙 / Capital 紫)+ base 灰の 5 色。色覚多様性対応で模様 / パターン併用するか。

  14. 月間稼働時間ラインチャートの軸: 縦軸 = h/月、横軸 = Y0-Y5。Soft 160 / Hard 200 のしきい値ラインは赤 / 黄の 2 本。月次粒度(Y3M6 等)に粒度を細かくするかは v2 拡張余地(短期は縮退)。

実装プロンプト(Claude Code 用)

Claude Opus 4.7(1M context)推奨。4 純粋関数レバー + UI 統合 + sync-engines + bootstrap + sys_params の複合実装。

## 案件
MAS-059 v2.0 — 1 人コンサルタント 非連続成長シミュレーター(4 レバー成長戦略)

## 事前調査(必ず Read する)
1. `docs/dev/dev_mas-059_growth_planning_workspace.md` 全文(本仕様書 v2.0)
2. `400_domain/445_required_revenue_solver.js` 全文(純粋関数 IIFE 名前空間 / `evaluateScenarioHealth`)
3. `400_domain/451_multiyear_planner.js` 全文(同型・5 年シミュ基盤)
4. `400_domain/454_compensation_strategy_engine.js` 全文(同型・`calcLimitProfit` を流用)
5. `400_domain/449_dividend_mix_optimizer.js` 全文(`_scrubInfinityForJSON_` の参照例)
6. `300_ui/302_spa_bridge.js` 全文(特に末尾の `_scrubInfinityForJSON_` 汎用ヘルパ)
7. `webapp_client/src/cockpit-main.tsx`(副作用 import 規約)
8. `webapp_client/src/cockpit/calc.ts`(client-side 計算 hub)
9. `webapp_client/src/cockpit/CompensationDropdowns.tsx`(離散単位ドロップダウン UI 規約)
10. `webapp_client/scripts/sync-engines.mjs`(`ENGINES_TO_SYNC` 配列規約)
11. `100_config/101_sys_config.js`(`confSheet.appendRow` パターン)
12. `docs/_internal/failure_patterns.md` #18-#20 / #25 / #26 / #29 / #31 / #33

## 実装対象(Phase 1-3 段階実装)

Phase 1 (0.5 ヶ月): 純粋関数エンジン
    1. `400_domain/446_growth_strategy_engine.js` 新規(IIFE 名前空間 GrowthStrategyEngine):
       - simulatePricingLever(input)
       - simulateProductLever(input)
       - simulateHumanLever(input)
       - simulateCapitalLever(input)
       - runGrowthStrategy(input) — 統合 API
       - 内部ヘルパ: _annuityFactor_ / _rankByNpv_ / _buildStackedBarData_ / _buildHoursLineData_ / _formatJpy_
    2. `webapp_client/scripts/sync-engines.mjs` の ENGINES_TO_SYNC に 446 追加

Phase 2 (0.5 ヶ月): React UI Panel
    3. `webapp_client/src/cockpit/GrowthStrategyPanel.tsx` 新規:
       - 左: 4 sliders (Pricing / Product / Human / Capital・各 0-5 離散)
       - 右上: LimitProfitStackedBar (Y0-Y5)
       - 右下: MonthlyHoursLineChart (Y0-Y5 + soft/hard limit)
       - 下部: BudgetOverWarningBanner + FeasibilityIndicator + HitlBadge
    4. `webapp_client/src/cockpit/calc.ts` の calcGrowthStrategy 公開
    5. `webapp_client/src/cockpit-main.tsx` に副作用 import 追加

Phase 3 (0.5 ヶ月): 設定 / メニュー / テスト
    6. `300_ui/302_spa_bridge.js` の _buildF59CockpitBootstrap_ 追加 + bootstrap merge
    7. `100_config/101_sys_config.js` に F59_* 12 キー seed 追加
    8. `000_infra/002_constants.js` の MENU_DEFINITION に「🚀 成長戦略シミュレーター」追加
    9. `900_test/901_test_runner.js` に F059-01〜F059-18 単体テスト追加

## 動作確認
1. dev で push:dev → cockpit を開く → GrowthStrategyPanel が表示される
2. 全レバー = 0 で base のみ表示・warnings なし
3. Pricing+30% で deltaProfit ≈ +85万・churn 21% 警告
4. Human レバー [採用 1 名] で HITL モーダル発動
5. Capital レバー再投資 ROIC 10% で「閾値割れ」warning
6. 全レバー max で feasibility 'infeasible' + 予算オーバー
7. F059-01〜F059-18 全 PASS
8. URL クエリパラメータ ?growthStrategy=p3,p2,h1,c2 でレベル復元

## デプロイ(Phase 1-3 統合)
1. dev で push:dev → メニュー「🚀 成長戦略シミュレーター」or cockpit から表示
2. Go なら push:prod
3. コミット: feat(MAS-059 v2.0): 1 人コンサル 非連続成長シミュレーター (4 レバー: Pricing/Product/Human/Capital)

## failure_patterns チェック
- #18-#20: simulatePricingLever / simulateProductLever / simulateHumanLever / simulateCapitalLever / runGrowthStrategy を Read で裏取り(既存 simulate* と整合)
- #25: 445/449/451/454 と純粋関数 + IIFE パターン対称
- #26: appsscript.json は v2.0 で変更なし
- #29: _scrubInfinityForJSON_ を bootstrap 配信前に通す
- #31: 446 slot は v1.x で予約済(v2.0 で再利用)・448 は MAS-061 で予約済
- #33: cockpit-main.tsx に副作用 import 必須

推奨実行モデル

工程推奨モデル根拠
Phase 1 GrowthStrategyEngine 純粋関数(4 レバー + 統合 API + 内部ヘルパ)Claude Opus 4.7 (1M context)4 レバー独立純粋関数の設計 + Buffett-Munger 階層 NPV ロジック + Infinity 防御
Phase 2 React UI Panel(4 sliders + 2 charts + warning banners)Claude Opus 4.7 (1M context)大規模 UI 設計 + recharts/d3 ライブラリ選定 + レスポンシブ
Phase 3 sys_params seed + メニュー + 単体テストClaude Sonnet 4.6パターン化された seed + テスト追加
マイグレーション 8XX_migration_f59_*(任意・v2 でシナリオ DB 化時のみ)Claude Haiku 4.5800_ops 既存パターン流用
仕様書レビューGemini 3 Pro Preview + Deep Think第三者視点での 4 レバー妥当性 + 物理時間ガード + バフェット階層検証

§A 旧 v1.x スコープ(アーカイブ・参考)

⚠️ 注意: 以下は v1.0-v1.1(2026-04-27/28)の「統合意思決定ツリー UI + LangGraph + Cloud SQL Postgres checkpointer」スコープのアーカイブ。v2.0(2026-05-01 全面 scope reset)では本案件 MAS-059 から切り離され、必要に応じて別案件 MAS-361 候補(仮) としてカーブアウト可能。

A.1 旧 v1.x の核となるスコープ

  • 400_domain/446_decision_tree_orchestrator.js(純粋関数オーケストレーター・約 400 行)= MAS-058/MAS-012/MAS-048/MAS-017/MAS-056 の連鎖 API
  • webapp_client/src/panels/GrowthPlanningWorkspace.tsx(左右分割 SPA UI = 左ツリー / 右入力)
  • runDecisionLoop(input) = 必要年商 → 必要 HC → 採用 TCO → CF 制約違反 → Next Actions → HITL 制御
  • HITL 強制条件 + Autonomy Slider(Conservative / Balanced / Autonomous)
  • シナリオ分岐管理40_scenario_registry に「親シナリオ ID」列追加 + 5 階層上限)
  • LangGraph + Cloud SQL Postgres checkpointer(Phase 4 拡張・月 $56-95)
  • Causal AI(do-calculus エンジン)は不採用(DAG 思考フレームのみ採用 / arXiv 2506.00844 等)
  • LLM に計算結果を復唱させない(Air Canada v. Moffatt 2024 BCCRT 149 型責任回避)
  • 真のツリー UI は不採用Runway 型カード並列 UI + Progressive Disclosure)

A.2 v2.0 で切り離した理由

  • v1.x は「統合意思決定ループ全体を駆動するオーケストレーター」として大規模(5 既存エンジン結合 + LangGraph 移行ロードマップ)
  • v2.0 ユーザー要望は「1 人コンサルが順調なのに天井で頭打ちになる課題に 4 レバーで突破するツール」というシンプルな成長戦略可視化(既存 cockpit の上位レイヤーとして 1 panel 追加)
  • 両者はスコープ・実装規模・前提案件が大きく異なるため別案件として分離するのが筋
  • v1.x は MAS-058 / MAS-067 / MAS-066 / MAS-071 が完了した今、「自動オーケストレーション」案件として独立起票が可能(MAS-361 候補)

A.3 v1.x キャリーオーバー先候補

候補案件内容
MAS-361(仮)旧 v1.x 全スコープを「意思決定ツリー オーケストレーター + LangGraph 統合」として独立起票。MAS-058/067/066/071 完了後の 第 5 cockpit として位置付け(MAS-057 単年 / MAS-067 マルチイヤー / MAS-072 EV / MAS-059 4 レバー / MAS-361 AI オーケストレーター)
MAS-059 v3 (将来)本 v2.0 の 4 レバー UI を v1.x のオーケストレーターでラップする統合形(1 人法人 GROWTH OS

A.4 v1.x の保存リソース

  • 旧 spec 全文 (462 行 v1.1) は本ファイルの git 履歴 (commit 直前バージョン) で復元可能
  • RQ-035 synthesis(LangGraph + Postgres / Causal AI 不採用 / Autonomy Slider)は docs/_internal/research_prompts/RQ-035_*.md で別途保存済み
  • tasks/prompts/task_F-59.md(手動骨格・PR #350 起票時版)は tasks/prompts/ で保存済み

変更履歴

日時バージョン変更内容
2026-04-27v0.1 (骨組み)初版骨組み作成。全セクション見出し + 概要テーブルのみ。ai_agent_tips.md §6 の章単位生成方針を準用。
2026-04-27v0.2 (本体)現在のコード(MAS-058/MAS-012/MAS-048/MAS-017/MAS-056/MAS-232 利用関数 6 個)+ 修正方針 6 Step 本文。JavaScript 疑似コードで runDecisionLoop を提示。
2026-04-27v0.3 (堅牢化)影響範囲 + 注意事項 14 項目 + エッジケース 13 + 実データ検証 5 本(齋藤 Baseline 連鎖 / HITL 発動 / LLM 数値整合性 / 5 階層上限 / F59-01〜F59-13)。
2026-04-27v1.0 (仕様書完了)関連ドキュメント 17 件 + 人間検討事項 14 + 実装プロンプト + 推奨実行モデル。前提案件 5 件のうち MAS-017 以外は仕様書完了済
2026-04-28v1.1 (前提案件ステータス訂正)MAS-012 ステータスを「📝 仕様書段階・未着手」に修正 + ⚠️ 警告コメント追加。
2026-05-01v2.0 (scope reset・4 レバー成長戦略へ全面書換)ユーザー要望「1 人コンサルが順調なのに 1500-2000 万円台で頭打ち = 4 レバー(Pricing/Product/Human/Capital)の組合せで非連続成長を可視化」を受けスコープ全面リセット。Gemini Deep Research(2026-04-30)+ Claude 内部調査の突合により 4 レバー成長戦略フレーム(Pricing 弾力性 / Product 製品化 / Human 人的レバレッジ / Capital Buffett-Munger 階層)を採用。新規ファイル: 400_domain/446_growth_strategy_engine.js(純粋関数 IIFE 名前空間 / 4 レバー独立 + 統合 API・約 500 行)+ webapp_client/src/cockpit/GrowthStrategyPanel.tsx(左 4 スライダー + 右 限界利益スタックドバー / 月間稼働時間ライン + 予算オーバー警告・約 700 行)。ID 採番衝突回避(failure_patterns #31): ユーザー初期提案 448_growth_strategy_engine.jsMAS-061 で予約済で衝突発覚 → MAS-059 v1.x で予約していた 446 slot を v2.0 で再利用(v1.x の 446_decision_tree_orchestrator.js は §A アーカイブで実体未作成)。14 セクション全網羅: 概要 + 目的(4 レバーフレーム + 4 cockpit 関係)+ 現在のコード(前提案件 5 + 副作用 import 規約)+ 修正方針 7 Step(Engine / Panel / sync-engines / 副作用 import / calc.ts / spa_bridge bootstrap / 12 sys_params seed)+ 影響範囲(新規 2 / 変更 7)+ 注意事項 15 件(#31 ID 採番 / #18-#20 命名造語 / #25 並列対称性 / #26 OAuth / #29 Infinity / #33 副作用 import / 時間ハード上限 / Pricing 弾力性 / Product レベル定義 / Human HITL / Capital バフェット階層 / 限界利益積上げ / マイクロ M&A B/S / 予算しきい値 / シナリオ保存)+ エッジケース 18 件 + テスト F059-01〜F059-18 + 関連ドキュメント 14 件 + 人間検討事項 14 件 + 実装プロンプト(Claude Opus 4.7 向け・事前調査 12 / Phase 1-3)+ 推奨実行モデル + §A 旧 v1.x スコープのアーカイブ(LangGraph + Postgres + Decision Tree Orchestrator は MAS-361 候補としてキャリーオーバー)。docs-only PR で prod 自動デプロイへの影響なし。