website/hub/services/templates/calculator/csp_roi_calculator.html

553 lines
34 KiB
HTML
Raw Blame History

This file contains ambiguous Unicode characters

This file contains Unicode characters that might be confused with other characters. If you think that this is intentional, you can safely ignore this warning. Use the Escape button to reveal them.

{% extends 'base.html' %}
{% load static %}
{% block title %}CSP ROI Calculator{% endblock %}
{% block extra_css %}
<link rel="stylesheet" type="text/css" href='{% static "css/roi-calculator.css" %}'>
{% endblock %}
{% block extra_js %}
<script src="{% static "js/chart.umd.min.js" %}"></script>
<script src="{% static "js/jspdf.umd.min.js" %}"></script>
<script src="{% static "js/roi-calculator.js" %}"></script>
{% endblock %}
{% block content %}
<div class="container-fluid my-4">
<div class="row">
<!-- Header -->
<div class="col-12 mb-4">
<div class="d-flex justify-content-between align-items-center">
<div>
<h1 class="h2 mb-1">CSP ROI Calculator</h1>
<p class="text-muted">Calculate potential returns from investing in Servala platform</p>
</div>
<div>
<!-- Export Buttons -->
<button type="button" class="btn btn-outline-primary btn-sm me-2" onclick="exportToPDF()">
<i class="bi bi-file-pdf"></i> PDF
</button>
<button type="button" class="btn btn-outline-success btn-sm me-2" onclick="exportToCSV()">
<i class="bi bi-file-csv"></i> CSV
</button>
<button type="button" class="btn btn-outline-secondary me-2" onclick="resetCalculator()">
<i class="bi bi-arrow-clockwise"></i> Reset
</button>
<button type="button" class="btn btn-danger" onclick="logout()">
<i class="bi bi-box-arrow-right"></i> Logout
</button>
</div>
</div>
</div>
</div>
<div class="row">
<!-- Input Panel -->
<div class="col-lg-4">
<!-- Help Section -->
<div class="collapsible-section mb-3">
<div class="collapsible-header" onclick="toggleCollapsible('help-section')">
<h5 class="mb-0">
<i class="bi bi-question-circle"></i> How the Calculator Works
<i class="bi bi-chevron-down float-end"></i>
</h5>
</div>
<div class="collapsible-content" id="help-section">
<div class="help-content">
<h6 class="text-primary mb-2"><i class="bi bi-lightbulb"></i> Calculator Overview</h6>
<p class="small">This ROI calculator models your investment in the Servala platform by simulating cloud service provider (CSP) business growth over time. It calculates potential returns based on instance growth, churn rates, and revenue sharing with Servala.</p>
<h6 class="text-primary mb-2 mt-3"><i class="bi bi-gear"></i> Key Parameters</h6>
<div class="small">
<p><strong>Investment Amount:</strong> Your initial capital investment in the Servala platform and infrastructure.</p>
<p><strong>Monthly Revenue per Instance:</strong> The recurring revenue generated from each managed service instance (excl. compute).</p>
<p><strong>Servala Revenue Share:</strong> Percentage of revenue shared with Servala after the grace period. This is Servala's platform fee.</p>
<p><strong>Grace Period:</strong> Initial months where you keep 100% of revenue before sharing begins with Servala.</p>
</div>
<h6 class="text-primary mb-2 mt-3"><i class="bi bi-graph-up"></i> Growth Scenarios</h6>
<div class="small">
<p><strong>Conservative:</strong> Steady growth with low churn (2%), suitable for established markets.</p>
<p><strong>Moderate:</strong> Balanced growth with moderate churn (3%), typical for competitive markets.</p>
<p><strong>Aggressive:</strong> Rapid expansion with higher churn (5%), for high-growth strategies.</p>
<p>Each scenario has 4 growth phases with customizable instance acquisition rates in Advanced Parameters.</p>
</div>
<h6 class="text-primary mb-2 mt-3"><i class="bi bi-bullseye"></i> Understanding Results</h6>
<div class="small">
<p><strong>ROI:</strong> Return on Investment as a percentage of your initial investment.</p>
<p><strong>Break-even:</strong> Month when cumulative revenue equals your initial investment.</p>
<p><strong>Churn:</strong> Monthly percentage of instances that stop generating revenue (customer loss).</p>
</div>
</div>
</div>
</div>
<!-- Investment Settings -->
<div class="calculator-section">
<h4><i class="bi bi-cash-coin"></i> Investment Settings</h4>
<div class="input-group-custom">
<label for="investment-amount">
Investment Amount
<i class="bi bi-question-circle-fill text-muted ms-1"
data-bs-toggle="tooltip"
data-bs-placement="top"
title="Higher investments enable better growth through increased marketing, infrastructure, and customer success capabilities."
style="cursor: help; font-size: 0.8rem;"></i>
</label>
<div class="input-group">
<span class="input-group-text currency-symbol">CHF</span>
<input type="text" class="form-control" id="investment-amount"
data-value="500000" value="500,000"
oninput="handleInvestmentAmountInput(this)"
onchange="updateCalculations()">
</div>
<div class="slider-container">
<input type="range" class="slider" id="investment-slider"
min="100000" max="2000000" step="10000" value="500000"
onchange="updateInvestmentAmount(this.value)">
</div>
<small class="text-muted">CHF 100,000 - CHF 2,000,000</small>
<!-- Investment Impact Details -->
<div class="collapsible-section mt-2">
<div class="collapsible-header" onclick="toggleCollapsible('investment-impact')" style="padding: 0.5rem; font-size: 0.9rem;">
<h6 class="mb-0">
<i class="bi bi-info-circle"></i> Investment Impact
<i class="bi bi-chevron-down float-end"></i>
</h6>
</div>
<div class="collapsible-content" id="investment-impact" style="padding: 0.75rem; font-size: 0.85rem;">
<p class="mb-2"><strong>How Investment Amount Affects Growth</strong></p>
<p class="mb-2">Higher investments enable better growth through increased marketing, infrastructure, and customer success capabilities. This affects instance acquisition rates and reduces churn.</p>
<p class="mb-2"><strong>Mathematical Impact</strong></p>
<ul class="mb-2" style="font-size: 0.8rem;">
<li><strong>Instance Scaling Factor</strong> = √(Investment Amount / CHF 500,000)</li>
<li><strong>Churn Reduction Factor</strong> = max(0.7, 1 - (Investment - CHF 500,000) / CHF 2,000,000 × 0.3)</li>
<li><strong>New Instances per Month</strong> = Base Rate × Scaling Factor</li>
<li><strong>Adjusted Churn Rate</strong> = Base Churn × Reduction Factor</li>
</ul>
<p class="mb-0 text-info" style="font-size: 0.8rem;"><strong>Example:</strong> CHF 1M investment = 1.41× more instances + 25% lower churn than CHF 500K base.</p>
</div>
</div>
</div>
<div class="input-group-custom">
<label for="timeframe">Investment Timeframe (Years)</label>
<select class="form-select" id="timeframe" onchange="updateCalculations()">
<option value="1">1 Year</option>
<option value="2">2 Years</option>
<option value="3" selected>3 Years</option>
<option value="4">4 Years</option>
<option value="5">5 Years</option>
</select>
</div>
<div class="input-group-custom">
<label for="revenue-per-instance">Monthly Revenue per Instance</label>
<div class="input-group">
<span class="input-group-text currency-symbol">CHF</span>
<input type="number" class="form-control" id="revenue-per-instance"
min="20" max="200" step="5" value="50"
onchange="updateCalculations()">
</div>
<div class="slider-container">
<input type="range" class="slider" id="revenue-slider"
min="20" max="200" step="5" value="50"
onchange="updateRevenuePerInstance(this.value)">
</div>
<small class="text-muted">CHF 20 - CHF 200</small>
</div>
<div class="input-group-custom">
<label for="servala-share">Servala Revenue Share (%)</label>
<input type="number" class="form-control" id="servala-share"
min="10" max="40" step="1" value="25"
onchange="updateCalculations()">
<div class="slider-container">
<input type="range" class="slider" id="share-slider"
min="10" max="40" step="1" value="25"
onchange="updateServalaShare(this.value)">
</div>
<small class="text-muted">10% - 40%</small>
</div>
<div class="input-group-custom">
<label for="grace-period">Grace Period (Months)</label>
<input type="number" class="form-control" id="grace-period"
min="0" max="24" step="1" value="6"
onchange="updateCalculations()">
<div class="slider-container">
<input type="range" class="slider" id="grace-slider"
min="0" max="24" step="1" value="6"
onchange="updateGracePeriod(this.value)">
</div>
<small class="text-muted">0 - 24 months (100% revenue to CSP)</small>
</div>
</div>
<!-- Growth Scenarios -->
<div class="calculator-section">
<h4><i class="bi bi-speedometer2"></i> Growth Scenarios</h4>
<div class="scenario-card active" id="conservative-card">
<div class="form-check">
<input class="form-check-input" type="checkbox" id="conservative-enabled" checked onchange="toggleScenario('conservative')">
<label class="form-check-label fw-bold" for="conservative-enabled">
Conservative Growth
</label>
</div>
<p class="small text-muted mb-2">Steady, predictable growth with minimal risk</p>
<small class="text-info">Churn: 2% | New instances: 50-150/month (customizable below)</small>
</div>
<div class="scenario-card active" id="moderate-card">
<div class="form-check">
<input class="form-check-input" type="checkbox" id="moderate-enabled" checked onchange="toggleScenario('moderate')">
<label class="form-check-label fw-bold" for="moderate-enabled">
Moderate Growth
</label>
</div>
<p class="small text-muted mb-2">Balanced approach with moderate risk/reward</p>
<small class="text-info">Churn: 3% | New instances: 100-400/month (customizable below)</small>
</div>
<div class="scenario-card active" id="aggressive-card">
<div class="form-check">
<input class="form-check-input" type="checkbox" id="aggressive-enabled" checked onchange="toggleScenario('aggressive')">
<label class="form-check-label fw-bold" for="aggressive-enabled">
Aggressive Growth
</label>
</div>
<p class="small text-muted mb-2">Rapid expansion with higher risk/reward</p>
<small class="text-info">Churn: 5% | New instances: 200-800/month (customizable below)</small>
</div>
<!-- Advanced Parameters -->
<div class="collapsible-section">
<div class="collapsible-header" onclick="toggleCollapsible('advanced-params')">
<h6 class="mb-0">
<i class="bi bi-gear"></i> Advanced Parameters
<i class="bi bi-chevron-down float-end"></i>
</h6>
</div>
<div class="collapsible-content" id="advanced-params">
<div id="scenario-customization">
<p class="text-muted small mb-3">Customize growth phases and churn rates for each scenario. Changes apply immediately to calculations.</p>
<!-- Conservative Scenario Customization -->
<div class="phase-settings" id="conservative-advanced" style="display: block;">
<h6 class="text-success mb-3"><i class="bi bi-sliders"></i> Conservative Scenario Parameters</h6>
<div class="row mb-2">
<div class="col-6">
<label class="form-label small">Monthly Churn Rate (%)</label>
<input type="number" class="form-control form-control-sm" id="conservative-churn"
min="0" max="10" step="0.1" value="2.0"
onchange="updateScenarioChurn('conservative', this.value)">
</div>
</div>
<div class="row mb-2">
<div class="col-6">
<label class="form-label small">Phase 1 (Mo 1-6)</label>
<input type="number" class="form-control form-control-sm" id="conservative-phase-0"
min="10" max="500" step="5" value="50"
onchange="updateScenarioPhase('conservative', 0, this.value)">
<small class="text-muted">instances/month</small>
</div>
<div class="col-6">
<label class="form-label small">Phase 2 (Mo 7-12)</label>
<input type="number" class="form-control form-control-sm" id="conservative-phase-1"
min="10" max="500" step="5" value="75"
onchange="updateScenarioPhase('conservative', 1, this.value)">
<small class="text-muted">instances/month</small>
</div>
</div>
<div class="row">
<div class="col-6">
<label class="form-label small">Phase 3 (Mo 13-24)</label>
<input type="number" class="form-control form-control-sm" id="conservative-phase-2"
min="10" max="500" step="5" value="100"
onchange="updateScenarioPhase('conservative', 2, this.value)">
<small class="text-muted">instances/month</small>
</div>
<div class="col-6">
<label class="form-label small">Phase 4 (Mo 25+)</label>
<input type="number" class="form-control form-control-sm" id="conservative-phase-3"
min="10" max="500" step="5" value="150"
onchange="updateScenarioPhase('conservative', 3, this.value)">
<small class="text-muted">instances/month</small>
</div>
</div>
</div>
<!-- Moderate Scenario Customization -->
<div class="phase-settings" id="moderate-advanced" style="display: block;">
<h6 class="text-warning mb-3"><i class="bi bi-sliders"></i> Moderate Scenario Parameters</h6>
<div class="row mb-2">
<div class="col-6">
<label class="form-label small">Monthly Churn Rate (%)</label>
<input type="number" class="form-control form-control-sm" id="moderate-churn"
min="0" max="10" step="0.1" value="3.0"
onchange="updateScenarioChurn('moderate', this.value)">
</div>
</div>
<div class="row mb-2">
<div class="col-6">
<label class="form-label small">Phase 1 (Mo 1-6)</label>
<input type="number" class="form-control form-control-sm" id="moderate-phase-0"
min="10" max="1000" step="10" value="100"
onchange="updateScenarioPhase('moderate', 0, this.value)">
<small class="text-muted">instances/month</small>
</div>
<div class="col-6">
<label class="form-label small">Phase 2 (Mo 7-12)</label>
<input type="number" class="form-control form-control-sm" id="moderate-phase-1"
min="10" max="1000" step="10" value="200"
onchange="updateScenarioPhase('moderate', 1, this.value)">
<small class="text-muted">instances/month</small>
</div>
</div>
<div class="row">
<div class="col-6">
<label class="form-label small">Phase 3 (Mo 13-24)</label>
<input type="number" class="form-control form-control-sm" id="moderate-phase-2"
min="10" max="1000" step="10" value="300"
onchange="updateScenarioPhase('moderate', 2, this.value)">
<small class="text-muted">instances/month</small>
</div>
<div class="col-6">
<label class="form-label small">Phase 4 (Mo 25+)</label>
<input type="number" class="form-control form-control-sm" id="moderate-phase-3"
min="10" max="1000" step="10" value="400"
onchange="updateScenarioPhase('moderate', 3, this.value)">
<small class="text-muted">instances/month</small>
</div>
</div>
</div>
<!-- Aggressive Scenario Customization -->
<div class="phase-settings" id="aggressive-advanced" style="display: block;">
<h6 class="text-danger mb-3"><i class="bi bi-sliders"></i> Aggressive Scenario Parameters</h6>
<div class="row mb-2">
<div class="col-6">
<label class="form-label small">Monthly Churn Rate (%)</label>
<input type="number" class="form-control form-control-sm" id="aggressive-churn"
min="0" max="15" step="0.1" value="5.0"
onchange="updateScenarioChurn('aggressive', this.value)">
</div>
</div>
<div class="row mb-2">
<div class="col-6">
<label class="form-label small">Phase 1 (Mo 1-6)</label>
<input type="number" class="form-control form-control-sm" id="aggressive-phase-0"
min="50" max="2000" step="25" value="200"
onchange="updateScenarioPhase('aggressive', 0, this.value)">
<small class="text-muted">instances/month</small>
</div>
<div class="col-6">
<label class="form-label small">Phase 2 (Mo 7-12)</label>
<input type="number" class="form-control form-control-sm" id="aggressive-phase-1"
min="50" max="2000" step="25" value="400"
onchange="updateScenarioPhase('aggressive', 1, this.value)">
<small class="text-muted">instances/month</small>
</div>
</div>
<div class="row">
<div class="col-6">
<label class="form-label small">Phase 3 (Mo 13-24)</label>
<input type="number" class="form-control form-control-sm" id="aggressive-phase-2"
min="50" max="2000" step="25" value="600"
onchange="updateScenarioPhase('aggressive', 2, this.value)">
<small class="text-muted">instances/month</small>
</div>
<div class="col-6">
<label class="form-label small">Phase 4 (Mo 25+)</label>
<input type="number" class="form-control form-control-sm" id="aggressive-phase-3"
min="50" max="2000" step="25" value="800"
onchange="updateScenarioPhase('aggressive', 3, this.value)">
<small class="text-muted">instances/month</small>
</div>
</div>
</div>
<div class="mt-3">
<button type="button" class="btn btn-outline-secondary btn-sm" onclick="resetAdvancedParameters()">
<i class="bi bi-arrow-clockwise"></i> Reset to Defaults
</button>
</div>
</div>
</div>
</div>
</div>
</div>
<!-- Results Display -->
<div class="col-lg-8">
<!-- Loading Spinner -->
<div class="loading-spinner" id="loading-spinner">
<div class="spinner-border text-primary" role="status">
<span class="visually-hidden">Calculating...</span>
</div>
<p class="mt-2">Calculating scenarios...</p>
</div>
<!-- Summary Metrics -->
<div class="row" id="summary-metrics">
<div class="col-md-3 col-sm-6">
<div class="metric-card text-center">
<div class="metric-value" id="total-instances">0</div>
<div class="metric-label">
Total Instances
<i class="bi bi-question-circle-fill text-muted ms-1"
data-bs-toggle="tooltip"
data-bs-placement="top"
title="Average final number of cloud instances across all enabled scenarios at the end of your investment timeframe. This represents the scale of your cloud infrastructure business."
style="cursor: help; font-size: 0.8rem;"></i>
</div>
</div>
</div>
<div class="col-md-3 col-sm-6">
<div class="metric-card text-center">
<div class="metric-value" id="total-revenue">CHF 0</div>
<div class="metric-label">
Total Revenue
<i class="bi bi-question-circle-fill text-muted ms-1"
data-bs-toggle="tooltip"
data-bs-placement="top"
title="Average total revenue generated across all enabled scenarios over your investment timeframe. This includes both CSP revenue (what you keep) and Servala revenue (platform fees)."
style="cursor: help; font-size: 0.8rem;"></i>
</div>
</div>
</div>
<div class="col-md-3 col-sm-6">
<div class="metric-card text-center">
<div class="metric-value" id="roi-percentage">0%</div>
<div class="metric-label">
Average ROI
<i class="bi bi-question-circle-fill text-muted ms-1"
data-bs-toggle="tooltip"
data-bs-placement="top"
title="Return on Investment: Average percentage return across all enabled scenarios. Calculated as (CSP Revenue - Initial Investment) / Initial Investment × 100%. Shows how much profit you make relative to your initial investment."
style="cursor: help; font-size: 0.8rem;"></i>
</div>
</div>
</div>
<div class="col-md-3 col-sm-6">
<div class="metric-card text-center">
<div class="metric-value" id="breakeven-time">N/A</div>
<div class="metric-label">
Avg Break-even
<i class="bi bi-question-circle-fill text-muted ms-1"
data-bs-toggle="tooltip"
data-bs-placement="top"
title="Average time in months across all scenarios when your cumulative CSP revenue equals your initial investment. This is when you've recovered your upfront costs and start making pure profit."
style="cursor: help; font-size: 0.8rem;"></i>
</div>
</div>
</div>
</div>
<!-- Charts -->
<div class="row">
<div class="col-12">
<div class="chart-container">
<h5><i class="bi bi-graph-up-arrow"></i> Instance Growth Over Time</h5>
<canvas id="instanceGrowthChart"></canvas>
</div>
</div>
</div>
<div class="row">
<div class="col-md-6">
<div class="chart-container">
<h5><i class="bi bi-cash-stack"></i> Cumulative Revenue</h5>
<canvas id="revenueChart"></canvas>
</div>
</div>
<div class="col-md-6">
<div class="chart-container">
<h5><i class="bi bi-bar-chart"></i> Monthly Cash Flow</h5>
<canvas id="cashFlowChart"></canvas>
</div>
</div>
</div>
<!-- Scenario Comparison Table -->
<div class="row">
<div class="col-12">
<div class="chart-container">
<h5><i class="bi bi-table"></i> Scenario Comparison</h5>
<div class="table-responsive">
<table class="table table-striped" id="comparison-table">
<thead class="table-dark">
<tr>
<th>Scenario</th>
<th>Final Instances</th>
<th>Total Revenue</th>
<th>CSP Revenue</th>
<th>Servala Revenue</th>
<th>ROI</th>
<th>Break-even</th>
</tr>
</thead>
<tbody id="comparison-tbody">
<!-- Dynamic content -->
</tbody>
</table>
</div>
</div>
</div>
</div>
<!-- Monthly Breakdown -->
<div class="row">
<div class="col-12">
<div class="collapsible-section">
<div class="collapsible-header" onclick="toggleCollapsible('monthly-breakdown')">
<h5 class="mb-0">
<i class="bi bi-calendar3"></i> Monthly Breakdown
<i class="bi bi-chevron-down float-end"></i>
</h5>
</div>
<div class="collapsible-content" id="monthly-breakdown">
<div class="chart-container">
<div class="table-responsive" style="max-height: 400px; overflow-y: auto;">
<table class="table table-sm table-striped" id="monthly-table">
<thead class="table-dark sticky-top">
<tr>
<th>Month</th>
<th>Scenario</th>
<th>New Instances</th>
<th>Churned</th>
<th>Total Instances</th>
<th>Monthly Revenue</th>
<th>CSP Revenue</th>
<th>Servala Revenue</th>
<th>Cumulative CSP</th>
</tr>
</thead>
<tbody id="monthly-tbody">
<!-- Dynamic content -->
</tbody>
</table>
</div>
</div>
</div>
</div>
</div>
</div>
</div>
</div>
</div>
{% endblock %}