Files
dashcaddy/status/help-errors.html
Sami f61e85d9a7 Initial commit: DashCaddy v1.0
Full codebase including API server (32 modules + routes), dashboard frontend,
DashCA certificate distribution, installer script, and deployment skills.
2026-03-05 02:26:12 -08:00

488 lines
16 KiB
HTML

<!doctype html>
<html lang="en">
<head>
<meta charset="utf-8" />
<title>DashCaddy - Troubleshooting</title>
<meta name="viewport" content="width=device-width,initial-scale=1" />
<link rel="icon" href="/assets/dashcaddy-favicon.ico" sizes="any">
<style>
:root {
--bg: #0b0f1a;
--fg: #e8ecf5;
--muted: #9aa6bf;
--card-base: #121826;
--border: #263552;
--accent: #8FD6FF;
--accent-strong: #1F7BFF;
--ok-bg: #0c2430;
--ok-fg: #7ef2ff;
--bad-bg: #2a121a;
--bad-fg: #ff9aa3;
--radius: 12px;
}
* { box-sizing: border-box; margin: 0; padding: 0; }
body {
font-family: -apple-system, BlinkMacSystemFont, 'Segoe UI', Roboto, sans-serif;
background: var(--bg);
color: var(--fg);
line-height: 1.6;
padding: 24px;
max-width: 900px;
margin: 0 auto;
}
header {
display: flex;
align-items: center;
gap: 16px;
margin-bottom: 32px;
flex-wrap: wrap;
}
header h1 {
font-size: 1.8rem;
font-weight: 700;
color: var(--accent);
}
header a {
color: var(--muted);
text-decoration: none;
font-size: 0.9rem;
margin-left: auto;
}
header a:hover { color: var(--accent); }
.search-box {
width: 100%;
padding: 12px 16px;
border-radius: var(--radius);
border: 1px solid var(--border);
background: var(--card-base);
color: var(--fg);
font-size: 1rem;
outline: none;
margin-bottom: 24px;
}
.search-box:focus { border-color: var(--accent); }
.search-box::placeholder { color: var(--muted); }
.category {
margin-bottom: 32px;
}
.category h2 {
font-size: 1.1rem;
font-weight: 600;
color: var(--accent);
margin-bottom: 12px;
padding-bottom: 8px;
border-bottom: 1px solid var(--border);
}
.error-card {
background: var(--card-base);
border: 1px solid var(--border);
border-radius: var(--radius);
padding: 16px 20px;
margin-bottom: 10px;
transition: border-color 0.2s;
}
.error-card.highlight {
border-color: var(--accent);
box-shadow: 0 0 12px rgba(143, 214, 255, 0.15);
}
.error-header {
display: flex;
align-items: baseline;
gap: 12px;
margin-bottom: 8px;
}
.error-code {
font-family: 'Courier New', monospace;
font-weight: 700;
font-size: 0.95rem;
color: var(--bad-fg);
background: var(--bad-bg);
padding: 2px 8px;
border-radius: 6px;
white-space: nowrap;
}
.error-message {
font-weight: 500;
color: var(--fg);
}
.error-details {
display: grid;
grid-template-columns: auto 1fr;
gap: 4px 12px;
font-size: 0.9rem;
margin-top: 8px;
}
.error-details dt {
color: var(--muted);
font-weight: 500;
}
.error-details dd {
color: var(--fg);
}
.fix {
color: var(--ok-fg);
background: var(--ok-bg);
padding: 2px 6px;
border-radius: 4px;
font-size: 0.85rem;
}
.no-results {
text-align: center;
color: var(--muted);
padding: 40px 0;
display: none;
}
footer {
text-align: center;
color: var(--muted);
font-size: 0.8rem;
margin-top: 40px;
padding-top: 20px;
border-top: 1px solid var(--border);
}
</style>
</head>
<body>
<header>
<h1>Troubleshooting</h1>
<a href="/">&larr; Back to Dashboard</a>
</header>
<input type="text" class="search-box" id="search" placeholder="Search by error code (e.g. DC-200) or keyword..." autofocus />
<div id="no-results" class="no-results">No matching errors found.</div>
<div id="error-list">
<!-- Authentication & CSRF -->
<div class="category" data-category="auth">
<h2>Authentication & CSRF (DC-1xx)</h2>
<div class="error-card" data-code="DC-100">
<div class="error-header">
<span class="error-code">DC-100</span>
<span class="error-message">CSRF token missing</span>
</div>
<dl class="error-details">
<dt>Cause</dt>
<dd>Your browser cookie expired or was blocked. This often happens after the browser has been idle for a long time.</dd>
<dt>Fix</dt>
<dd><span class="fix">Hard refresh the page with Ctrl+Shift+R (or Cmd+Shift+R on Mac), then try again.</span></dd>
</dl>
</div>
<div class="error-card" data-code="DC-101">
<div class="error-header">
<span class="error-code">DC-101</span>
<span class="error-message">CSRF token invalid</span>
</div>
<dl class="error-details">
<dt>Cause</dt>
<dd>The security token in your browser doesn't match the one the server expects. This can happen after long idle periods or if you have multiple tabs open.</dd>
<dt>Fix</dt>
<dd><span class="fix">Refresh the page and try the action again.</span></dd>
</dl>
</div>
<div class="error-card" data-code="DC-110">
<div class="error-header">
<span class="error-code">DC-110</span>
<span class="error-message">Authentication required</span>
</div>
<dl class="error-details">
<dt>Cause</dt>
<dd>Your TOTP session has expired. Sessions last for the duration configured in your TOTP settings (default: 24 hours).</dd>
<dt>Fix</dt>
<dd><span class="fix">Enter your TOTP code from your authenticator app to re-authenticate.</span></dd>
</dl>
</div>
<div class="error-card" data-code="DC-111">
<div class="error-header">
<span class="error-code">DC-111</span>
<span class="error-message">Invalid code</span>
</div>
<dl class="error-details">
<dt>Cause</dt>
<dd>The TOTP code you entered is incorrect or has already expired. Codes refresh every 30 seconds.</dd>
<dt>Fix</dt>
<dd><span class="fix">Check your authenticator app for the current code. Wait for a fresh code if the current one is about to expire.</span></dd>
</dl>
</div>
<div class="error-card" data-code="DC-120">
<div class="error-header">
<span class="error-code">DC-120</span>
<span class="error-message">Access denied - Tailscale required</span>
</div>
<dl class="error-details">
<dt>Cause</dt>
<dd>The dashboard is configured to require a Tailscale VPN connection, and you're not currently connected.</dd>
<dt>Fix</dt>
<dd><span class="fix">Connect to Tailscale VPN first, then try accessing the dashboard again.</span></dd>
</dl>
</div>
</div>
<!-- Deployment & Containers -->
<div class="category" data-category="deploy">
<h2>Deployment & Containers (DC-2xx)</h2>
<div class="error-card" data-code="DC-200">
<div class="error-header">
<span class="error-code">DC-200</span>
<span class="error-message">Port is already in use</span>
</div>
<dl class="error-details">
<dt>Cause</dt>
<dd>Another container or process on the host is already using the port you selected. This sometimes happens after a failed deploy leaves a stale container behind.</dd>
<dt>Fix</dt>
<dd><span class="fix">Use a different port in Advanced Options, or stop the conflicting service first. Check the Monitor panel to see which container is using the port.</span></dd>
</dl>
</div>
<div class="error-card" data-code="DC-201">
<div class="error-header">
<span class="error-code">DC-201</span>
<span class="error-message">Failed to pull image</span>
</div>
<dl class="error-details">
<dt>Cause</dt>
<dd>Docker couldn't download the container image. This is usually a network issue, or the image name/tag doesn't exist on Docker Hub.</dd>
<dt>Fix</dt>
<dd><span class="fix">Check your internet connection. If using a custom image, verify the image name and tag are correct.</span></dd>
</dl>
</div>
<div class="error-card" data-code="DC-202">
<div class="error-header">
<span class="error-code">DC-202</span>
<span class="error-message">Container failed to start</span>
</div>
<dl class="error-details">
<dt>Cause</dt>
<dd>The container was created but couldn't start or become healthy. Common reasons include misconfigured environment variables, missing volume mounts, or insufficient resources.</dd>
<dt>Fix</dt>
<dd><span class="fix">Check the Logs panel for container-specific error messages. Try redeploying with default settings.</span></dd>
</dl>
</div>
<div class="error-card" data-code="DC-203">
<div class="error-header">
<span class="error-code">DC-203</span>
<span class="error-message">Port conflict with another service</span>
</div>
<dl class="error-details">
<dt>Cause</dt>
<dd>Another DashCaddy-managed service is already using the port you specified. DashCaddy checks for this before deploying to prevent conflicts.</dd>
<dt>Fix</dt>
<dd><span class="fix">Choose a different port in Advanced Options, or remove the conflicting service first.</span></dd>
</dl>
</div>
<div class="error-card" data-code="DC-210">
<div class="error-header">
<span class="error-code">DC-210</span>
<span class="error-message">Invalid IP address</span>
</div>
<dl class="error-details">
<dt>Cause</dt>
<dd>The IP address field contains an invalid value. It must be a valid IPv4 or IPv6 address, or one of the allowed hostnames.</dd>
<dt>Fix</dt>
<dd><span class="fix">Use a valid IP address (e.g., 192.168.1.100) or "localhost". Leave blank to use the default.</span></dd>
</dl>
</div>
</div>
<!-- DNS & Caddy Configuration -->
<div class="category" data-category="caddy">
<h2>DNS & Caddy Configuration (DC-3xx)</h2>
<div class="error-card" data-code="DC-300">
<div class="error-header">
<span class="error-code">DC-300</span>
<span class="error-message">DNS token unavailable</span>
</div>
<dl class="error-details">
<dt>Cause</dt>
<dd>The DNS server credentials have expired or are missing. DashCaddy needs valid DNS credentials to create and manage DNS records.</dd>
<dt>Fix</dt>
<dd><span class="fix">Go to Tokens in the toolbar, select DNS, and re-enter your DNS server credentials.</span></dd>
</dl>
</div>
<div class="error-card" data-code="DC-301">
<div class="error-header">
<span class="error-code">DC-301</span>
<span class="error-message">Invalid domain/subdomain format</span>
</div>
<dl class="error-details">
<dt>Cause</dt>
<dd>The domain or subdomain name contains invalid characters. Domain names can only contain lowercase letters, numbers, hyphens, and dots.</dd>
<dt>Fix</dt>
<dd><span class="fix">Use only letters (a-z), numbers (0-9), hyphens (-), and dots (.) in your domain name.</span></dd>
</dl>
</div>
<div class="error-card" data-code="DC-302">
<div class="error-header">
<span class="error-code">DC-302</span>
<span class="error-message">Site already exists in Caddyfile</span>
</div>
<dl class="error-details">
<dt>Cause</dt>
<dd>A site block for this domain is already present in the Caddy configuration file. You can't create a duplicate entry.</dd>
<dt>Fix</dt>
<dd><span class="fix">Edit the existing site configuration, or remove it first before creating a new one.</span></dd>
</dl>
</div>
<div class="error-card" data-code="DC-303">
<div class="error-header">
<span class="error-code">DC-303</span>
<span class="error-message">Caddy reload failed</span>
</div>
<dl class="error-details">
<dt>Cause</dt>
<dd>Caddy couldn't reload its configuration. This usually means there's a syntax error in the Caddyfile, or Caddy's admin API is unreachable.</dd>
<dt>Fix</dt>
<dd><span class="fix">Check the Logs panel for the specific Caddy error. The Caddyfile change was automatically rolled back. If the problem persists, verify Caddy is running.</span></dd>
</dl>
</div>
</div>
<!-- Service Management -->
<div class="category" data-category="services">
<h2>Service Management (DC-4xx)</h2>
<div class="error-card" data-code="DC-400">
<div class="error-header">
<span class="error-code">DC-400</span>
<span class="error-message">Container not found</span>
</div>
<dl class="error-details">
<dt>Cause</dt>
<dd>The Docker container was removed outside of DashCaddy (e.g., via Docker Desktop or the CLI). DashCaddy still has it registered but can't find it.</dd>
<dt>Fix</dt>
<dd><span class="fix">Delete the service card from DashCaddy, then redeploy the app from the App Selector.</span></dd>
</dl>
</div>
<div class="error-card" data-code="DC-401">
<div class="error-header">
<span class="error-code">DC-401</span>
<span class="error-message">Update failed</span>
</div>
<dl class="error-details">
<dt>Cause</dt>
<dd>The container update process failed during image pull, container recreation, or startup. The old container may have been removed but the new one couldn't start.</dd>
<dt>Fix</dt>
<dd><span class="fix">Check the Logs panel for details. If the container is gone, redeploy the app from the App Selector.</span></dd>
</dl>
</div>
</div>
<!-- Credentials & Auto-Login -->
<div class="category" data-category="creds">
<h2>Credentials & Auto-Login (DC-5xx)</h2>
<div class="error-card" data-code="DC-500">
<div class="error-header">
<span class="error-code">DC-500</span>
<span class="error-message">No credentials stored</span>
</div>
<dl class="error-details">
<dt>Cause</dt>
<dd>Auto-login was attempted but no username/password is saved for this service. DashCaddy needs stored credentials to log you in automatically.</dd>
<dt>Fix</dt>
<dd><span class="fix">Click the key icon (&#x1f511;) on the service card to add your credentials for auto-login.</span></dd>
</dl>
</div>
<div class="error-card" data-code="DC-501">
<div class="error-header">
<span class="error-code">DC-501</span>
<span class="error-message">Login failed</span>
</div>
<dl class="error-details">
<dt>Cause</dt>
<dd>The stored credentials were rejected by the service. The username or password may be incorrect, or the service's auth endpoint may have changed.</dd>
<dt>Fix</dt>
<dd><span class="fix">Click the key icon (&#x1f511;) on the service card to update your credentials. Verify the username and password are correct by logging into the service directly first.</span></dd>
</dl>
</div>
</div>
</div>
<footer>
DashCaddy v0.95 &middot; Error codes help you quickly find solutions. Search by code or keyword above.
</footer>
<script>
(function() {
const search = document.getElementById('search');
const cards = document.querySelectorAll('.error-card');
const categories = document.querySelectorAll('.category');
const noResults = document.getElementById('no-results');
search.addEventListener('input', function() {
const q = this.value.trim().toLowerCase();
if (!q) {
cards.forEach(c => { c.style.display = ''; c.classList.remove('highlight'); });
categories.forEach(c => c.style.display = '');
noResults.style.display = 'none';
return;
}
let found = 0;
cards.forEach(card => {
const text = card.textContent.toLowerCase();
const code = card.dataset.code.toLowerCase();
const match = text.includes(q) || code.includes(q);
card.style.display = match ? '' : 'none';
card.classList.toggle('highlight', match && q.startsWith('dc-'));
if (match) found++;
});
// Hide categories with no visible cards
categories.forEach(cat => {
const visible = cat.querySelectorAll('.error-card:not([style*="display: none"])');
cat.style.display = visible.length ? '' : 'none';
});
noResults.style.display = found === 0 ? '' : 'none';
});
// Auto-search if URL has hash (e.g., help-errors.html#DC-200)
if (location.hash) {
const code = decodeURIComponent(location.hash.slice(1));
search.value = code;
search.dispatchEvent(new Event('input'));
}
})();
</script>
</body>
</html>