Refactor code structure for improved readability and maintainability
This commit is contained in:
File diff suppressed because it is too large
Load Diff
@@ -0,0 +1,92 @@
|
||||
Copyright 2018 The Manrope Project Authors (https://github.com/googlefonts/manrope)
|
||||
|
||||
This Font Software is licensed under the SIL Open Font License, Version 1.1.
|
||||
This license is copied below, and is also available with a FAQ at:
|
||||
http://scripts.sil.org/OFL
|
||||
|
||||
-----------------------------------------------------------
|
||||
SIL OPEN FONT LICENSE Version 1.1 - 26 February 2007
|
||||
-----------------------------------------------------------
|
||||
|
||||
PREAMBLE
|
||||
The goals of the Open Font License (OFL) are to stimulate worldwide
|
||||
development of collaborative font projects, to support the font creation
|
||||
efforts of academic and linguistic communities, and to provide a free and
|
||||
open framework in which fonts may be shared and improved in partnership
|
||||
with others.
|
||||
|
||||
The OFL allows the licensed fonts to be used, studied, modified and
|
||||
redistributed freely as long as they are not sold by themselves. The
|
||||
fonts, including any derivative works, can be bundled, embedded,
|
||||
redistributed and/or sold with any software provided that any reserved
|
||||
names are not used by derivative works. The fonts and derivatives,
|
||||
however, cannot be released under any other type of license. The
|
||||
requirement for fonts to remain under this license does not apply
|
||||
to any document created using the fonts or their derivatives.
|
||||
|
||||
DEFINITIONS
|
||||
"Font Software" refers to the set of files released by the Copyright
|
||||
Holder(s) under this license and clearly marked as such. This may
|
||||
include source files, build scripts and documentation.
|
||||
|
||||
"Reserved Font Name" refers to any names specified as such after the
|
||||
copyright statement(s).
|
||||
|
||||
"Original Version" refers to the collection of Font Software components as
|
||||
distributed by the Copyright Holder(s).
|
||||
|
||||
"Modified Version" refers to any derivative made by adding to, deleting,
|
||||
or substituting -- in part or in whole -- any of the components of the
|
||||
Original Version, by changing formats or by porting the Font Software to a
|
||||
new environment.
|
||||
|
||||
"Author" refers to any designer, engineer, programmer, technical
|
||||
writer or other person who contributed to the Font Software.
|
||||
|
||||
PERMISSION & CONDITIONS
|
||||
Permission is hereby granted, free of charge, to any person obtaining
|
||||
a copy of the Font Software, to use, study, copy, merge, embed, modify,
|
||||
redistribute, and sell modified and unmodified copies of the Font
|
||||
Software, subject to the following conditions:
|
||||
|
||||
1) Neither the Font Software nor any of its individual components,
|
||||
in Original or Modified Versions, may be sold by itself.
|
||||
|
||||
2) Original or Modified Versions of the Font Software may be bundled,
|
||||
redistributed and/or sold with any software, provided that each copy
|
||||
contains the above copyright notice and this license. These can be
|
||||
included either as stand-alone text files, human-readable headers or
|
||||
in the appropriate machine-readable metadata fields within text or
|
||||
binary files as long as those fields can be easily viewed by the user.
|
||||
|
||||
3) No Modified Version of the Font Software may use the Reserved Font
|
||||
Name(s) unless explicit written permission is granted by the corresponding
|
||||
Copyright Holder. This restriction only applies to the primary font name as
|
||||
presented to the users.
|
||||
|
||||
4) The name(s) of the Copyright Holder(s) or the Author(s) of the Font
|
||||
Software shall not be used to promote, endorse or advertise any
|
||||
Modified Version, except to acknowledge the contribution(s) of the
|
||||
Copyright Holder(s) and the Author(s) or with their explicit written
|
||||
permission.
|
||||
|
||||
5) The Font Software, modified or unmodified, in part or in whole,
|
||||
must be distributed entirely under this license, and must not be
|
||||
distributed under any other license. The requirement for fonts to
|
||||
remain under this license does not apply to any document created
|
||||
using the Font Software.
|
||||
|
||||
TERMINATION
|
||||
This license becomes null and void if any of the above conditions are
|
||||
not met.
|
||||
|
||||
DISCLAIMER
|
||||
THE FONT SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
|
||||
EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO ANY WARRANTIES OF
|
||||
MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT
|
||||
OF COPYRIGHT, PATENT, TRADEMARK, OR OTHER RIGHT. IN NO EVENT SHALL THE
|
||||
COPYRIGHT HOLDER BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY,
|
||||
INCLUDING ANY GENERAL, SPECIAL, INDIRECT, INCIDENTAL, OR CONSEQUENTIAL
|
||||
DAMAGES, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING
|
||||
FROM, OUT OF THE USE OR INABILITY TO USE THE FONT SOFTWARE OR FROM
|
||||
OTHER DEALINGS IN THE FONT SOFTWARE.
|
||||
Binary file not shown.
+189
-363
@@ -1,379 +1,205 @@
|
||||
<!DOCTYPE html>
|
||||
<!doctype html>
|
||||
<html lang="en">
|
||||
<head>
|
||||
<meta charset="UTF-8" />
|
||||
<meta name="viewport" content="width=device-width, initial-scale=1.0" />
|
||||
<title>UVM Dashboard</title>
|
||||
<link rel="stylesheet" href="/dashboard/static/css/dashboard.css" />
|
||||
<meta name="viewport" content="width=device-width, initial-scale=1" />
|
||||
<meta name="theme-color" content="#e8e7ed" />
|
||||
<meta name="color-scheme" content="light" />
|
||||
<title>UVM Control</title>
|
||||
<link rel="icon" href="data:image/svg+xml,%3Csvg xmlns='http://www.w3.org/2000/svg' viewBox='0 0 32 32'%3E%3Crect width='32' height='32' rx='10' fill='%23eee7ac'/%3E%3Cpath d='M9 11v7a7 7 0 0 0 14 0v-7' fill='none' stroke='%234b4854' stroke-width='3' stroke-linecap='round'/%3E%3C/svg%3E" />
|
||||
<link rel="preload" href="/dashboard/static/fonts/manrope-latin.woff2" as="font" type="font/woff2" crossorigin />
|
||||
<link rel="stylesheet" href="/dashboard/static/css/dashboard.css?v=2" />
|
||||
<script src="/dashboard/static/js/dashboard.js?v=2" defer></script>
|
||||
</head>
|
||||
<body>
|
||||
<div id="app">
|
||||
<!-- Auth Screen -->
|
||||
<div id="auth-screen" class="screen active">
|
||||
<div class="auth-card">
|
||||
<div class="auth-header">
|
||||
<div class="logo">
|
||||
<svg width="32" height="32" viewBox="0 0 32 32" fill="none">
|
||||
<rect width="32" height="32" rx="8" fill="currentColor" />
|
||||
<path d="M9 11h14M9 16h10M9 21h6" stroke="#0b0b0f" stroke-width="2" stroke-linecap="round"/>
|
||||
</svg>
|
||||
<span>UVM</span>
|
||||
</div>
|
||||
<h1>Welcome back</h1>
|
||||
<p>Enter your management API token to access the dashboard.</p>
|
||||
</div>
|
||||
<div class="auth-form">
|
||||
<div class="field">
|
||||
<label for="token-input">API Token</label>
|
||||
<input id="token-input" type="password" placeholder="Paste your UVM_API_TOKEN here" autocomplete="off" />
|
||||
</div>
|
||||
<button id="auth-btn" class="btn btn-primary btn-lg">Connect</button>
|
||||
<p id="auth-error" class="error-text"></p>
|
||||
<svg class="icon-sprite" xmlns="http://www.w3.org/2000/svg" aria-hidden="true">
|
||||
<symbol id="i-grid" viewBox="0 0 24 24"><rect x="3.5" y="3.5" width="6" height="6" rx="1.7"/><rect x="14.5" y="3.5" width="6" height="6" rx="1.7"/><rect x="3.5" y="14.5" width="6" height="6" rx="1.7"/><rect x="14.5" y="14.5" width="6" height="6" rx="1.7"/></symbol>
|
||||
<symbol id="i-server" viewBox="0 0 24 24"><rect x="3" y="4" width="18" height="6" rx="2"/><rect x="3" y="14" width="18" height="6" rx="2"/><path d="M7 7h.01M7 17h.01M15 7h3M15 17h3"/></symbol>
|
||||
<symbol id="i-network" viewBox="0 0 24 24"><rect x="9" y="3" width="6" height="5" rx="1.5"/><rect x="2" y="16" width="6" height="5" rx="1.5"/><rect x="16" y="16" width="6" height="5" rx="1.5"/><path d="M12 8v4M5 16v-4h14v4"/></symbol>
|
||||
<symbol id="i-heart" viewBox="0 0 24 24"><path d="M20.8 5.8a5.2 5.2 0 0 0-7.4 0L12 7.2l-1.4-1.4a5.2 5.2 0 0 0-7.4 7.4L12 22l8.8-8.8a5.2 5.2 0 0 0 0-7.4Z" transform="translate(0 -2) scale(1 0.95)"/><path d="M5 11h3l2-3 3 7 2-4h4"/></symbol>
|
||||
<symbol id="i-plus" viewBox="0 0 24 24"><path d="M12 5v14M5 12h14"/></symbol>
|
||||
<symbol id="i-arrow" viewBox="0 0 24 24"><path d="M5 12h14m-5-5 5 5-5 5"/></symbol>
|
||||
<symbol id="i-back" viewBox="0 0 24 24"><path d="M19 12H5m5-5-5 5 5 5"/></symbol>
|
||||
<symbol id="i-chevron" viewBox="0 0 24 24"><path d="m9 5 7 7-7 7"/></symbol>
|
||||
<symbol id="i-search" viewBox="0 0 24 24"><circle cx="10.5" cy="10.5" r="6.5"/><path d="m16 16 4.5 4.5"/></symbol>
|
||||
<symbol id="i-refresh" viewBox="0 0 24 24"><path d="M20 10a8 8 0 0 0-14-4L3 9m0-6v6h6M4 14a8 8 0 0 0 14 4l3-3m-6 0h6v6"/></symbol>
|
||||
<symbol id="i-book" viewBox="0 0 24 24"><path d="M12 5v15M12 5C8 2 3 4 3 4v15s5-2 9 1c4-3 9-1 9-1V4s-5-2-9 1Z"/></symbol>
|
||||
<symbol id="i-logout" viewBox="0 0 24 24"><path d="M10 4H5a2 2 0 0 0-2 2v12a2 2 0 0 0 2 2h5M8 12h13m-5-5 5 5-5 5"/></symbol>
|
||||
<symbol id="i-lock" viewBox="0 0 24 24"><rect x="5" y="10" width="14" height="11" rx="3"/><path d="M8 10V7a4 4 0 0 1 8 0v3M12 14v3"/></symbol>
|
||||
<symbol id="i-spark" viewBox="0 0 24 24"><path d="m12 3 2.7 6.3L21 12l-6.3 2.7L12 21l-2.7-6.3L3 12l6.3-2.7L12 3Z"/></symbol>
|
||||
<symbol id="i-shield" viewBox="0 0 24 24"><path d="m12 3 8 3v6c0 5-8 9-8 9s-8-4-8-9V6l8-3Z"/><path d="m8 12 3 3 5-6"/></symbol>
|
||||
<symbol id="i-cpu" viewBox="0 0 24 24"><rect x="6" y="6" width="12" height="12" rx="3"/><rect x="9" y="9" width="6" height="6" rx="1"/><path d="M9 3v3m6-3v3M9 18v3m6-3v3M3 9h3m-3 6h3m12-6h3m-3 6h3"/></symbol>
|
||||
<symbol id="i-memory" viewBox="0 0 24 24"><rect x="3" y="6" width="18" height="12" rx="2"/><path d="M7 10h3v4H7zm7 0h3v4h-3zM7 18v3m5-3v3m5-3v3"/></symbol>
|
||||
<symbol id="i-play" viewBox="0 0 24 24"><path d="m8 4 12 8-12 8V4Z"/></symbol>
|
||||
<symbol id="i-stop" viewBox="0 0 24 24"><rect x="6" y="6" width="12" height="12" rx="2"/></symbol>
|
||||
<symbol id="i-more" viewBox="0 0 24 24"><circle cx="5" cy="12" r="1"/><circle cx="12" cy="12" r="1"/><circle cx="19" cy="12" r="1"/></symbol>
|
||||
<symbol id="i-trash" viewBox="0 0 24 24"><path d="M3 6h18M9 6V3h6v3M5 6l1 15h12l1-15M10 10v7m4-7v7"/></symbol>
|
||||
<symbol id="i-copy" viewBox="0 0 24 24"><rect x="8" y="8" width="12" height="13" rx="2"/><path d="M16 8V5a2 2 0 0 0-2-2H5a2 2 0 0 0-2 2v9a2 2 0 0 0 2 2h3"/></symbol>
|
||||
<symbol id="i-terminal" viewBox="0 0 24 24"><rect x="3" y="4" width="18" height="16" rx="3"/><path d="m7 9 3 3-3 3m6 0h4"/></symbol>
|
||||
<symbol id="i-check" viewBox="0 0 24 24"><path d="m5 12 4 4L19 6"/></symbol>
|
||||
<symbol id="i-close" viewBox="0 0 24 24"><path d="m6 6 12 12M6 18 18 6"/></symbol>
|
||||
<symbol id="i-info" viewBox="0 0 24 24"><circle cx="12" cy="12" r="9"/><path d="M12 11v6M12 7h.01"/></symbol>
|
||||
<symbol id="i-menu" viewBox="0 0 24 24"><path d="M4 6h16M4 12h16M4 18h16"/></symbol>
|
||||
<symbol id="i-eye" viewBox="0 0 24 24"><path d="M2 12s4-7 10-7 10 7 10 7-4 7-10 7S2 12 2 12Z"/><circle cx="12" cy="12" r="3"/></symbol>
|
||||
<symbol id="i-download" viewBox="0 0 24 24"><path d="M12 3v12m-5-5 5 5 5-5M4 16v4h16v-4"/></symbol>
|
||||
</svg>
|
||||
|
||||
<section id="auth-screen" class="auth-screen">
|
||||
<div class="auth-window">
|
||||
<div class="auth-story">
|
||||
<a href="#overview" class="brand" aria-label="UVM Control"><span class="brand-flower" aria-hidden="true"><i></i><i></i><i></i><i></i></span><span>uvm<span class="brand-period">.</span></span><span class="brand-tag">workspace</span></a>
|
||||
<div class="auth-story-copy"><span class="subtle-label">A little space for big ideas</span><h1>Your compute.<br />A little calmer.</h1><p>A considered workspace for your machines,<br />your network, and everything in between.</p></div>
|
||||
<div class="auth-sculpture" aria-hidden="true">
|
||||
<div class="sculpture-orbit orbit-outer"></div><div class="sculpture-orbit orbit-inner"></div>
|
||||
<div class="sculpture-card sculpture-back"><span></span><i></i><i></i><i></i></div>
|
||||
<div class="sculpture-card sculpture-middle"><span></span><i></i><i></i><i></i></div>
|
||||
<div class="sculpture-card sculpture-front"><svg class="icon"><use href="#i-server"/></svg><span>Room to create.</span><div class="sculpture-lights"><i></i><i></i><i></i></div></div>
|
||||
<div class="sculpture-caption"><span class="dot dot-yellow"></span>Small footprint. Your possibilities.</div>
|
||||
</div>
|
||||
<span class="auth-story-footer">MicroVMs, thoughtfully managed.</span>
|
||||
</div>
|
||||
</div>
|
||||
|
||||
<!-- Main App -->
|
||||
<div id="main-app" class="screen">
|
||||
<aside class="sidebar">
|
||||
<div class="sidebar-brand">
|
||||
<div class="logo">
|
||||
<svg width="28" height="28" viewBox="0 0 32 32" fill="none">
|
||||
<rect width="32" height="32" rx="8" fill="currentColor" />
|
||||
<path d="M9 11h14M9 16h10M9 21h6" stroke="#0b0b0f" stroke-width="2" stroke-linecap="round"/>
|
||||
</svg>
|
||||
<span>UVM</span>
|
||||
</div>
|
||||
</div>
|
||||
<nav class="sidebar-nav">
|
||||
<a href="#overview" class="nav-item active" data-page="overview">
|
||||
<svg width="20" height="20" viewBox="0 0 24 24" fill="none" stroke="currentColor" stroke-width="2" stroke-linecap="round" stroke-linejoin="round"><rect x="3" y="3" width="7" height="7"/><rect x="14" y="3" width="7" height="7"/><rect x="14" y="14" width="7" height="7"/><rect x="3" y="14" width="7" height="7"/></svg>
|
||||
<span>Overview</span>
|
||||
</a>
|
||||
<a href="#vms" class="nav-item" data-page="vms">
|
||||
<svg width="20" height="20" viewBox="0 0 24 24" fill="none" stroke="currentColor" stroke-width="2" stroke-linecap="round" stroke-linejoin="round"><rect x="2" y="2" width="20" height="8" rx="2"/><rect x="2" y="14" width="20" height="8" rx="2"/><line x1="6" y1="6" x2="6.01" y2="6"/><line x1="6" y1="18" x2="6.01" y2="18"/></svg>
|
||||
<span>Virtual Machines</span>
|
||||
</a>
|
||||
<a href="#system" class="nav-item" data-page="system">
|
||||
<svg width="20" height="20" viewBox="0 0 24 24" fill="none" stroke="currentColor" stroke-width="2" stroke-linecap="round" stroke-linejoin="round"><path d="M12 2L2 7l10 5 10-5-10-5z"/><path d="M2 17l10 5 10-5"/><path d="M2 12l10 5 10-5"/></svg>
|
||||
<span>System</span>
|
||||
</a>
|
||||
</nav>
|
||||
<div class="sidebar-footer">
|
||||
<div class="connection-status">
|
||||
<span class="status-dot" id="conn-dot"></span>
|
||||
<span class="status-label" id="conn-label">Connected</span>
|
||||
</div>
|
||||
<button id="logout-btn" class="btn btn-ghost btn-sm">Disconnect</button>
|
||||
</div>
|
||||
</aside>
|
||||
|
||||
<main class="main">
|
||||
<header class="topbar">
|
||||
<div class="topbar-left">
|
||||
<h2 id="page-title">Overview</h2>
|
||||
</div>
|
||||
<div class="topbar-right">
|
||||
<button id="refresh-btn" class="btn btn-ghost btn-icon" title="Refresh">
|
||||
<svg width="18" height="18" viewBox="0 0 24 24" fill="none" stroke="currentColor" stroke-width="2" stroke-linecap="round" stroke-linejoin="round"><path d="M21.5 2v6h-6M2.5 22v-6h6M2 11.5a10 10 0 0118.8-4.3M22 12.5a10 10 0 01-18.8 4.3"/></svg>
|
||||
</button>
|
||||
<button id="create-vm-btn" class="btn btn-primary">+ New VM</button>
|
||||
</div>
|
||||
</header>
|
||||
|
||||
<div class="content">
|
||||
<!-- Overview Page -->
|
||||
<section id="page-overview" class="page active">
|
||||
<div class="stats-grid">
|
||||
<div class="stat-card">
|
||||
<div class="stat-header">
|
||||
<span class="stat-label">Total VMs</span>
|
||||
<div class="stat-icon icon-blue">
|
||||
<svg width="18" height="18" viewBox="0 0 24 24" fill="none" stroke="currentColor" stroke-width="2" stroke-linecap="round" stroke-linejoin="round"><rect x="2" y="2" width="20" height="8" rx="2"/><rect x="2" y="14" width="20" height="8" rx="2"/><line x1="6" y1="6" x2="6.01" y2="6"/><line x1="6" y1="18" x2="6.01" y2="18"/></svg>
|
||||
</div>
|
||||
</div>
|
||||
<div class="stat-value" id="stat-total">—</div>
|
||||
<div class="stat-meta">registered VMs</div>
|
||||
</div>
|
||||
<div class="stat-card">
|
||||
<div class="stat-header">
|
||||
<span class="stat-label">Running</span>
|
||||
<div class="stat-icon icon-green">
|
||||
<svg width="18" height="18" viewBox="0 0 24 24" fill="none" stroke="currentColor" stroke-width="2" stroke-linecap="round" stroke-linejoin="round"><path d="M22 11.08V12a10 10 0 11-5.93-9.14"/><polyline points="22 4 12 14.01 9 11.01"/></svg>
|
||||
</div>
|
||||
</div>
|
||||
<div class="stat-value text-green" id="stat-running">—</div>
|
||||
<div class="stat-meta">active microVMs</div>
|
||||
</div>
|
||||
<div class="stat-card">
|
||||
<div class="stat-header">
|
||||
<span class="stat-label">Stopped</span>
|
||||
<div class="stat-icon icon-amber">
|
||||
<svg width="18" height="18" viewBox="0 0 24 24" fill="none" stroke="currentColor" stroke-width="2" stroke-linecap="round" stroke-linejoin="round"><rect x="6" y="4" width="4" height="16"/><rect x="14" y="4" width="4" height="16"/></svg>
|
||||
</div>
|
||||
</div>
|
||||
<div class="stat-value text-amber" id="stat-stopped">—</div>
|
||||
<div class="stat-meta">inactive microVMs</div>
|
||||
</div>
|
||||
<div class="stat-card">
|
||||
<div class="stat-header">
|
||||
<span class="stat-label">API Health</span>
|
||||
<div class="stat-icon icon-purple">
|
||||
<svg width="18" height="18" viewBox="0 0 24 24" fill="none" stroke="currentColor" stroke-width="2" stroke-linecap="round" stroke-linejoin="round"><path d="M22 12h-4l-3 9L9 3l-3 9H2"/></svg>
|
||||
</div>
|
||||
</div>
|
||||
<div class="stat-value" id="stat-health">—</div>
|
||||
<div class="stat-meta">last check <span id="health-ago">—</span></div>
|
||||
</div>
|
||||
</div>
|
||||
|
||||
<div class="section-header">
|
||||
<h3>Recent Virtual Machines</h3>
|
||||
<a href="#vms" class="link">View all</a>
|
||||
</div>
|
||||
<div class="vm-grid" id="overview-vm-list">
|
||||
<div class="empty-state">
|
||||
<p>No virtual machines yet.</p>
|
||||
<button class="btn btn-primary btn-sm" onclick="location.hash='#create'">Create your first VM</button>
|
||||
</div>
|
||||
</div>
|
||||
</section>
|
||||
|
||||
<!-- VMs Page -->
|
||||
<section id="page-vms" class="page">
|
||||
<div class="card">
|
||||
<div class="card-toolbar">
|
||||
<div class="search-box">
|
||||
<svg width="16" height="16" viewBox="0 0 24 24" fill="none" stroke="currentColor" stroke-width="2" stroke-linecap="round" stroke-linejoin="round"><circle cx="11" cy="11" r="8"/><line x1="21" y1="21" x2="16.65" y2="16.65"/></svg>
|
||||
<input id="vm-search" type="text" placeholder="Search by name, ID, or IP..." />
|
||||
</div>
|
||||
<div class="toolbar-actions">
|
||||
<div id="bulk-controls" class="bulk-controls">
|
||||
<span id="bulk-selection-count">0 selected</span>
|
||||
<select id="bulk-action" class="select">
|
||||
<option value="start">Start</option>
|
||||
<option value="restart">Restart</option>
|
||||
<option value="stop">Stop</option>
|
||||
<option value="ports-sync">Sync ports</option>
|
||||
<option value="delete">Delete</option>
|
||||
</select>
|
||||
<button id="bulk-run-btn" class="btn btn-ghost btn-sm">Run</button>
|
||||
</div>
|
||||
<select id="vm-filter-status" class="select">
|
||||
<option value="all">All statuses</option>
|
||||
<option value="running">Running</option>
|
||||
<option value="stopped">Stopped</option>
|
||||
</select>
|
||||
</div>
|
||||
</div>
|
||||
<div class="table-wrap">
|
||||
<table class="data-table" id="vms-table">
|
||||
<thead>
|
||||
<tr>
|
||||
<th class="selection"><input id="vm-select-all" type="checkbox" aria-label="Select all visible VMs" /></th>
|
||||
<th>VM</th>
|
||||
<th>Status</th>
|
||||
<th>Guest IP</th>
|
||||
<th>Resources</th>
|
||||
<th>Ports</th>
|
||||
<th>Policy</th>
|
||||
<th class="actions">Actions</th>
|
||||
</tr>
|
||||
</thead>
|
||||
<tbody></tbody>
|
||||
</table>
|
||||
</div>
|
||||
<div class="table-empty" id="vms-empty">
|
||||
<div class="empty-state">
|
||||
<p>No virtual machines found.</p>
|
||||
<button class="btn btn-primary btn-sm" onclick="location.hash='#create'">Create VM</button>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
</section>
|
||||
|
||||
<!-- VM Detail Page -->
|
||||
<section id="page-vm-detail" class="page">
|
||||
<div class="vm-detail-header">
|
||||
<button class="btn btn-ghost btn-sm back-btn" onclick="history.back()">
|
||||
<svg width="16" height="16" viewBox="0 0 24 24" fill="none" stroke="currentColor" stroke-width="2" stroke-linecap="round" stroke-linejoin="round"><line x1="19" y1="12" x2="5" y2="12"/><polyline points="12 19 5 12 12 5"/></svg>
|
||||
Back
|
||||
</button>
|
||||
<div class="vm-detail-title">
|
||||
<h2 id="detail-name">—</h2>
|
||||
<span class="badge" id="detail-status">—</span>
|
||||
</div>
|
||||
</div>
|
||||
<div class="detail-grid">
|
||||
<div class="card detail-card">
|
||||
<h4 class="card-title">Configuration</h4>
|
||||
<div class="detail-rows" id="detail-config">
|
||||
</div>
|
||||
</div>
|
||||
<div class="card detail-card">
|
||||
<h4 class="card-title">Networking</h4>
|
||||
<div class="detail-rows" id="detail-network">
|
||||
</div>
|
||||
</div>
|
||||
<div class="card detail-card">
|
||||
<h4 class="card-title">SSH Access</h4>
|
||||
<code id="detail-ssh-command" class="ssh-command">ssh root@10.42.0.2</code>
|
||||
<button id="detail-ssh-copy-btn" class="btn btn-ghost btn-sm">Copy Command</button>
|
||||
<p id="detail-ssh-hint" class="hint">Run this from a trusted local terminal.</p>
|
||||
</div>
|
||||
<div class="card detail-card wide">
|
||||
<h4 class="card-title">Port Rules</h4>
|
||||
<div class="port-list" id="detail-ports">
|
||||
<p class="muted">No port rules configured.</p>
|
||||
</div>
|
||||
<div id="detail-ports-edit" class="port-editor">
|
||||
<input id="detail-ports-input" class="port-editor-input" type="text" placeholder="e.g. 22:TCP,80:HTTP,443:HTTPS" />
|
||||
<div class="port-editor-actions">
|
||||
<button id="detail-ports-set" class="btn btn-primary btn-sm">Set</button>
|
||||
<button id="detail-ports-open" class="btn btn-ghost btn-sm">Open</button>
|
||||
<button id="detail-ports-close" class="btn btn-ghost btn-sm">Close</button>
|
||||
<button id="detail-ports-cancel" class="btn btn-ghost btn-sm">Cancel</button>
|
||||
</div>
|
||||
</div>
|
||||
<div class="port-actions">
|
||||
<button id="detail-ports-edit-btn" class="btn btn-ghost btn-sm">Edit Ports</button>
|
||||
<button id="detail-ports-sync-btn" class="btn btn-ghost btn-sm">Sync Ports</button>
|
||||
</div>
|
||||
</div>
|
||||
<div class="card detail-card wide">
|
||||
<div class="card-title-row">
|
||||
<h4 class="card-title">Firecracker Log</h4>
|
||||
<button id="detail-log-refresh-btn" class="btn btn-ghost btn-sm">Refresh Log</button>
|
||||
</div>
|
||||
<pre id="detail-log-output" class="log-output">Loading recent log entries…</pre>
|
||||
<p id="detail-log-meta" class="hint">Showing up to 100 recent lines.</p>
|
||||
</div>
|
||||
<div class="card detail-card wide">
|
||||
<h4 class="card-title">Actions</h4>
|
||||
<div class="action-bar">
|
||||
<button id="detail-start-btn" class="btn btn-primary">Start VM</button>
|
||||
<button id="detail-restart-btn" class="btn btn-warning">Restart VM</button>
|
||||
<button id="detail-stop-btn" class="btn btn-warning">Stop VM</button>
|
||||
<button id="detail-delete-btn" class="btn btn-danger">Delete VM</button>
|
||||
</div>
|
||||
<p class="hint">Use the copied SSH command from a trusted local terminal.</p>
|
||||
</div>
|
||||
</div>
|
||||
</section>
|
||||
|
||||
<!-- Create VM Page -->
|
||||
<section id="page-create" class="page">
|
||||
<div class="card create-card">
|
||||
<h3 class="card-heading">Create Virtual Machine</h3>
|
||||
<div class="form-grid">
|
||||
<div class="field">
|
||||
<label for="create-name">Name</label>
|
||||
<input id="create-name" type="text" placeholder="e.g. web-server" />
|
||||
</div>
|
||||
<div class="field">
|
||||
<label for="create-cpu">vCPUs</label>
|
||||
<input id="create-cpu" type="number" min="1" value="1" />
|
||||
</div>
|
||||
<div class="field">
|
||||
<label for="create-ram">RAM</label>
|
||||
<input id="create-ram" type="text" placeholder="e.g. 512M or 1G" value="512M" />
|
||||
</div>
|
||||
<div class="field">
|
||||
<label for="create-guest-ip">Guest IP <span class="hint-inline">(optional)</span></label>
|
||||
<input id="create-guest-ip" type="text" placeholder="10.42.0.10" />
|
||||
</div>
|
||||
<div class="field">
|
||||
<label for="create-username">Username</label>
|
||||
<input id="create-username" type="text" placeholder="root" value="root" />
|
||||
</div>
|
||||
<div class="field">
|
||||
<label for="create-password">Password</label>
|
||||
<input id="create-password" type="password" placeholder="root" value="root" />
|
||||
</div>
|
||||
<div class="field full">
|
||||
<label for="create-ports">Ports <span class="hint-inline">comma-separated, e.g. 22,80:HTTP,443:HTTPS</span></label>
|
||||
<input id="create-ports" type="text" placeholder="22:TCP,80:HTTP,443:HTTPS" value="22:TCP" />
|
||||
</div>
|
||||
<div class="field full checkbox-field">
|
||||
<label class="checkbox">
|
||||
<input id="create-no-default-ports" type="checkbox" />
|
||||
<span class="checkmark"></span>
|
||||
<span class="checkbox-label">Do not add default SSH port (22)</span>
|
||||
</label>
|
||||
</div>
|
||||
</div>
|
||||
<div class="form-actions">
|
||||
<button id="create-submit" class="btn btn-primary btn-lg">Create VM</button>
|
||||
<button id="create-cancel" class="btn btn-ghost">Cancel</button>
|
||||
</div>
|
||||
<pre id="create-error" class="error-block"></pre>
|
||||
</div>
|
||||
</section>
|
||||
|
||||
<!-- System Page -->
|
||||
<section id="page-system" class="page">
|
||||
<div class="stats-grid two">
|
||||
<div class="card system-card">
|
||||
<h4 class="card-title">API Health</h4>
|
||||
<div class="system-status" id="system-health">
|
||||
<span class="status-badge badge-loading">Checking…</span>
|
||||
<p class="muted">Send a test request to the management API.</p>
|
||||
</div>
|
||||
</div>
|
||||
<div class="card system-card">
|
||||
<h4 class="card-title">Installation</h4>
|
||||
<p class="muted">Install or refresh host assets (Firecracker, kernel, rootfs). This is a privileged operation.</p>
|
||||
<div class="system-actions">
|
||||
<button id="install-btn" class="btn btn-primary">Install / Refresh</button>
|
||||
<label class="checkbox inline">
|
||||
<input id="install-force" type="checkbox" />
|
||||
<span class="checkmark"></span>
|
||||
<span class="checkbox-label">Force redownload</span>
|
||||
</label>
|
||||
</div>
|
||||
<pre id="install-result" class="code-block hidden"></pre>
|
||||
</div>
|
||||
</div>
|
||||
|
||||
<div class="card wide">
|
||||
<h4 class="card-title">Server Information</h4>
|
||||
<div class="detail-rows" id="server-info">
|
||||
<div class="detail-row"><span class="detail-key">Dashboard Version</span><span class="detail-value">1.0.0</span></div>
|
||||
<div class="detail-row"><span class="detail-key">API URL</span><span class="detail-value" id="info-api-url">—</span></div>
|
||||
<div class="detail-row"><span class="detail-key">Observed At</span><span class="detail-value" id="info-observed">—</span></div>
|
||||
</div>
|
||||
</div>
|
||||
<div class="card wide">
|
||||
<div class="card-title-row">
|
||||
<h4 class="card-title">Host Diagnostics</h4>
|
||||
<button id="diagnostics-refresh-btn" class="btn btn-ghost btn-sm">Run Checks</button>
|
||||
</div>
|
||||
<div id="diagnostics-list" class="diagnostics-list">
|
||||
<p class="muted">Open System to run host readiness checks.</p>
|
||||
</div>
|
||||
</div>
|
||||
</section>
|
||||
<main class="auth-panel">
|
||||
<div class="auth-panel-inner">
|
||||
<span class="round-icon auth-lock"><svg class="icon"><use href="#i-lock"/></svg></span>
|
||||
<span class="subtle-label">Your local workspace</span>
|
||||
<h2>Welcome to UVM</h2>
|
||||
<p>Bring your machines into view.<br />Connect with your management token to begin.</p>
|
||||
<form id="auth-form">
|
||||
<label class="field" for="token-input"><span>Management token</span><input id="token-input" name="token" type="password" placeholder="Enter your API token" autocomplete="off" spellcheck="false" required aria-describedby="auth-error" /></label>
|
||||
<p id="auth-error" class="form-error" role="alert"></p>
|
||||
<button id="auth-btn" class="button button-primary button-wide" type="submit"><span>Open workspace</span><svg class="icon"><use href="#i-arrow"/></svg></button>
|
||||
</form>
|
||||
<p class="auth-note"><svg class="icon"><use href="#i-shield"/></svg>Saved only for this browser session.</p>
|
||||
</div>
|
||||
<a class="quiet-link auth-help" href="/docs" target="_blank" rel="noopener">Explore the API <svg class="icon"><use href="#i-arrow"/></svg></a>
|
||||
</main>
|
||||
</div>
|
||||
</section>
|
||||
|
||||
<!-- Toast Container -->
|
||||
<div id="toast-container"></div>
|
||||
|
||||
<!-- Confirm Modal -->
|
||||
<div id="confirm-modal" class="modal">
|
||||
<div class="modal-overlay"></div>
|
||||
<div class="modal-card">
|
||||
<h3 id="confirm-title">Are you sure?</h3>
|
||||
<p id="confirm-body">This action cannot be undone.</p>
|
||||
<div class="modal-actions">
|
||||
<button id="confirm-cancel" class="btn btn-ghost">Cancel</button>
|
||||
<button id="confirm-ok" class="btn btn-danger">Confirm</button>
|
||||
<section id="main-app" class="app-shell" hidden>
|
||||
<button id="nav-scrim" class="nav-scrim" aria-label="Close navigation" hidden></button>
|
||||
<aside id="workspace-nav" class="workspace-drawer" aria-label="Workspace navigation">
|
||||
<div class="sidebar">
|
||||
<a class="brand" href="#overview" aria-label="UVM Control overview"><span class="brand-flower" aria-hidden="true"><i></i><i></i><i></i><i></i></span><span>uvm<span class="brand-period">.</span></span><span class="brand-tag">workspace</span></a>
|
||||
<div class="sidebar-heading"><span class="sidebar-heading-mark" aria-hidden="true">↳</span><h2><span id="sidebar-title">Management</span><span id="sidebar-subtitle">Overview</span></h2></div>
|
||||
<button class="sidebar-search" type="button" data-action="search"><svg class="icon"><use href="#i-search"/></svg><span>Find in workspace</span><kbd>/</kbd></button>
|
||||
<nav class="primary-nav" aria-label="Primary">
|
||||
<a class="nav-item" href="#overview" data-nav="overview"><svg class="icon"><use href="#i-grid"/></svg><span>Overview</span><span class="nav-indicator"></span></a>
|
||||
<a class="nav-item" href="#vms" data-nav="vms"><svg class="icon"><use href="#i-server"/></svg><span>Machines</span><span class="nav-count" id="nav-vm-count">—</span></a>
|
||||
<a class="nav-item" href="#network" data-nav="network"><svg class="icon"><use href="#i-network"/></svg><span>Network & ports</span><span class="nav-indicator"></span></a>
|
||||
<a class="nav-item" href="#system" data-nav="system"><svg class="icon"><use href="#i-heart"/></svg><span>Host health</span><span class="nav-health-dot" id="nav-health-dot"></span></a>
|
||||
<a class="nav-item nav-create" href="#create" data-nav="create"><svg class="icon"><use href="#i-plus"/></svg><span>New machine</span><svg class="icon nav-end-icon"><use href="#i-plus"/></svg></a>
|
||||
</nav>
|
||||
<div class="sidebar-secondary"><a class="nav-item" href="/docs" target="_blank" rel="noopener"><svg class="icon"><use href="#i-book"/></svg><span>API reference</span><svg class="icon nav-end-icon"><use href="#i-arrow"/></svg></a></div>
|
||||
<div class="sidebar-bottom">
|
||||
<div class="workspace-identity"><span class="workspace-avatar">u</span><div><strong>Local workspace</strong><span><i id="connection-dot" class="dot"></i><span id="connection-label">Connecting</span></span></div></div>
|
||||
<button id="logout-btn" class="quiet-link" type="button"><svg class="icon"><use href="#i-logout"/></svg>End session</button>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
|
||||
<script src="/dashboard/static/js/dashboard.js"></script>
|
||||
<div class="context-rail" aria-label="Workspace at a glance">
|
||||
<a href="#system" class="insight-card">
|
||||
<div class="card-caption"><span>Workspace insights</span><svg class="icon"><use href="#i-spark"/></svg></div>
|
||||
<p id="insight-copy">A fresh perspective on your local compute.</p>
|
||||
<div class="insight-matrix" aria-hidden="true"><span></span></div>
|
||||
<span class="insight-footer"><span class="dot dot-yellow"></span><span id="insight-footer">Looking at the details</span></span>
|
||||
</a>
|
||||
<a href="#vms" class="collection collection-machines">
|
||||
<div class="collection-art machine-art" aria-hidden="true"><div class="paper-machine back-paper"><span></span><i></i><i></i></div><div class="paper-machine front-paper"><svg class="icon"><use href="#i-server"/></svg><i></i><i></i><span></span></div></div>
|
||||
<div class="collection-label"><div><strong>Machines</strong><span id="rail-machines">Your private fleet</span></div><svg class="icon"><use href="#i-chevron"/></svg></div>
|
||||
</a>
|
||||
<a href="#network" class="collection collection-network">
|
||||
<div class="collection-art network-art" aria-hidden="true"><div class="network-paper"><span class="network-line"></span><i></i><i></i><i></i><svg class="icon"><use href="#i-network"/></svg></div></div>
|
||||
<div class="collection-label"><div><strong>Network</strong><span id="rail-network">Connections, considered</span></div><svg class="icon"><use href="#i-chevron"/></svg></div>
|
||||
</a>
|
||||
<a href="#system" class="collection collection-simple"><div class="collection-label"><div><strong>Host health</strong><span id="rail-health">Checking the essentials</span></div><svg class="icon"><use href="#i-chevron"/></svg></div></a>
|
||||
<a href="#create" class="collection collection-simple collection-new"><div class="collection-label"><div><strong>Something new?</strong><span>Make room for an idea</span></div><svg class="icon"><use href="#i-plus"/></svg></div></a>
|
||||
<span class="rail-footnote">A small cloud.<br />Entirely yours.</span>
|
||||
</div>
|
||||
</aside>
|
||||
|
||||
<div class="workspace">
|
||||
<header class="topbar">
|
||||
<button id="nav-toggle" class="icon-button mobile-menu" type="button" aria-label="Open navigation" aria-expanded="false" aria-controls="workspace-nav"><svg class="icon"><use href="#i-menu"/></svg></button>
|
||||
<div class="workspace-crumb"><span class="dot dot-yellow"></span><span>Workspace</span><span class="crumb-divider">/</span><span id="breadcrumb">Overview</span></div>
|
||||
<button id="refresh-btn" class="icon-button refresh-button" type="button" aria-label="Refresh workspace" title="Refresh workspace"><svg class="icon"><use href="#i-refresh"/></svg></button>
|
||||
<div class="global-search">
|
||||
<svg class="icon"><use href="#i-search"/></svg><input id="global-search" type="search" placeholder="Find a machine or a page" autocomplete="off" role="combobox" aria-label="Search workspace" aria-autocomplete="list" aria-expanded="false" aria-controls="search-results" /><kbd>⌘ K</kbd>
|
||||
<div id="search-results" class="search-results" role="listbox" aria-label="Search results" hidden></div>
|
||||
</div>
|
||||
<a href="#create" class="icon-button topbar-create" aria-label="Create a new machine" title="Create a new machine"><svg class="icon"><use href="#i-plus"/></svg></a>
|
||||
</header>
|
||||
|
||||
<main id="main-content" class="page-content">
|
||||
<div id="connection-banner" class="notice notice-error" role="status" hidden><svg class="icon"><use href="#i-info"/></svg><span id="connection-message"></span><button class="quiet-link" type="button" data-action="refresh">Try again</button></div>
|
||||
|
||||
<section id="page-overview" class="page" aria-labelledby="overview-heading" hidden>
|
||||
<div class="page-heading"><div><span class="subtle-label">The bigger picture</span><h1 id="overview-heading" tabindex="-1">Workspace overview<span class="heading-period">.</span></h1></div><span id="today-label" class="date-label"></span></div>
|
||||
<div class="overview-metrics">
|
||||
<article class="metric-card fleet-metric"><div class="card-caption"><h2>Your machine fleet</h2><a href="#vms" class="mini-link" aria-label="View all machines"><svg class="icon"><use href="#i-chevron"/></svg></a></div><div class="fleet-number"><strong id="metric-total">—</strong><span>little machines,<br />endless possibilities</span></div><div class="metric-bottom"><span class="status-inline"><i class="dot dot-yellow"></i><span id="metric-running">Waiting for the fleet</span></span><span id="metric-stopped" class="muted">—</span></div></article>
|
||||
<article class="metric-card"><div class="card-caption"><h2>Host signals</h2><a href="#system" class="mini-link" aria-label="View host signals"><svg class="icon"><use href="#i-chevron"/></svg></a></div><div class="signal-readouts"><div><span class="dot dot-sage"></span><strong id="checks-ready">—</strong><small>Ready</small></div><div><span class="dot dot-peach"></span><strong id="checks-attention">—</strong><small>Attention</small></div><div><span class="dot dot-lilac"></span><strong id="checks-total">—</strong><small>Checks</small></div></div><div class="segmented-track" aria-hidden="true"><span id="checks-ready-bar"></span><span id="checks-attention-bar"></span></div><div class="range-labels"><span>Host readiness</span><span id="checks-summary">Taking a look</span></div></article>
|
||||
<article class="metric-card resources-metric"><div class="card-caption"><h2>Resource allocation</h2><svg class="icon caption-icon"><use href="#i-cpu"/></svg></div><div class="resource-line"><span id="metric-cpu">— vCPU</span><small id="cpu-active-label">Allocated</small></div><div class="resource-track"><span id="cpu-allocation-bar"></span></div><div class="resource-line second-resource"><span id="metric-ram">— MiB</span><small id="ram-active-label">Allocated</small></div><div class="resource-track memory-track"><span id="ram-allocation-bar"></span></div></article>
|
||||
</div>
|
||||
|
||||
<section class="portfolio-section" aria-labelledby="portfolio-heading"><header class="section-heading"><div><h2 id="portfolio-heading">Machine portfolio</h2><span>A place for every workload.</span></div><a class="quiet-link" href="#vms">View all <svg class="icon"><use href="#i-arrow"/></svg></a></header><div id="overview-machines" class="portfolio-content"><div class="loading-state">Bringing your machines into view…</div></div></section>
|
||||
|
||||
<div class="overview-bottom">
|
||||
<article class="activity-panel soft-panel"><header class="section-heading"><div><h2>Fleet activity</h2><span>A snapshot of your machine states.</span></div><svg class="icon caption-icon"><use href="#i-grid"/></svg></header><div class="activity-body"><div class="fleet-ring" role="img" id="fleet-ring" aria-label="Waiting for machine activity"><svg viewBox="0 0 200 200" aria-hidden="true"><circle class="ring-track" cx="100" cy="100" r="82"/><circle id="ring-running" class="ring-segment ring-running" cx="100" cy="100" r="82" pathLength="100"/><circle id="ring-stopped" class="ring-segment ring-stopped" cx="100" cy="100" r="82" pathLength="100"/><circle id="ring-other" class="ring-segment ring-other" cx="100" cy="100" r="82" pathLength="100"/></svg><div class="ring-center"><span>Running now</span><strong id="ring-percent">—<small>%</small></strong><span id="ring-total">Your fleet, in balance</span></div></div><div class="ring-legend"><div><i class="dot dot-yellow"></i><span>Running<small>Doing their thing</small></span><strong id="legend-running">—</strong></div><div><i class="dot dot-peach"></i><span>Stopped<small>Taking a breather</small></span><strong id="legend-stopped">—</strong></div><div><i class="dot dot-lilac"></i><span>Other states<small>A closer look</small></span><strong id="legend-other">—</strong></div></div></div></article>
|
||||
<article class="notes-panel soft-panel"><header class="section-heading"><div><h2>Worth a little attention</h2><span>The useful details, together.</span></div><svg class="icon caption-icon"><use href="#i-spark"/></svg></header><div id="workspace-notes" class="workspace-notes"></div><a href="#system" class="notes-footer quiet-link">A closer look at your host <svg class="icon"><use href="#i-arrow"/></svg></a></article>
|
||||
</div>
|
||||
<footer class="page-footer"><span><i class="dot" id="footer-dot"></i>Live from your local control plane</span><span id="last-updated">Waiting for an update</span></footer>
|
||||
</section>
|
||||
|
||||
<section id="page-vms" class="page" aria-labelledby="machines-heading" hidden>
|
||||
<div class="page-heading"><div><span class="subtle-label">A collection of possibilities</span><h1 id="machines-heading" tabindex="-1">Your machines<span class="heading-period">.</span></h1></div><a class="button button-primary" href="#create"><svg class="icon"><use href="#i-plus"/></svg>New machine</a></div>
|
||||
<div id="fleet-summary" class="compact-metrics"></div>
|
||||
<div class="fleet-toolbar"><div class="filter-tabs" role="group" aria-label="Filter machines by state"><button type="button" class="filter-tab active" data-filter="all" aria-pressed="true">All machines</button><button type="button" class="filter-tab" data-filter="running" aria-pressed="false">Running</button><button type="button" class="filter-tab" data-filter="stopped" aria-pressed="false">Stopped</button><button type="button" class="filter-tab" data-filter="attention" aria-pressed="false">Attention</button></div><label class="select-wrap"><span class="sr-only">Sort machines</span><select id="vm-sort"><option value="recent">Newest first</option><option value="name">Name A–Z</option><option value="status">Machine state</option></select></label></div>
|
||||
<div class="fleet-list-panel"><div class="list-search-row"><label class="search-field"><svg class="icon"><use href="#i-search"/></svg><input id="vm-search" type="search" placeholder="Find by name, ID, or address" aria-label="Search machines" /></label><span id="visible-count" class="muted"></span></div><div id="bulk-controls" class="bulk-controls" hidden><span id="bulk-count"></span><label class="select-wrap"><span class="sr-only">Bulk action</span><select id="bulk-action"><option value="start">Start machines</option><option value="stop">Stop machines</option><option value="restart">Restart machines</option><option value="ports-sync">Sync port policies</option><option value="delete">Delete machines</option></select></label><button id="bulk-run-btn" class="button button-small button-primary" type="button">Apply</button><button class="icon-button" type="button" data-action="clear-selection" aria-label="Clear selection"><svg class="icon"><use href="#i-close"/></svg></button></div><div id="machine-table-wrap" class="table-scroll"><table class="machine-table"><thead><tr><th class="check-cell"><input id="vm-select-all" type="checkbox" aria-label="Select all visible machines" /></th><th>Machine</th><th>State</th><th>Allocation</th><th>Ingress</th><th>Policy</th><th class="row-controls-heading"><span class="sr-only">Actions</span></th></tr></thead><tbody id="machine-rows"></tbody></table></div><div id="machines-empty" hidden></div><div class="list-footer"><span id="fleet-list-caption">Your private machine registry.</span><span>Made for a small footprint.</span></div></div>
|
||||
<div id="bulk-results" class="operation-results" aria-live="polite" hidden></div>
|
||||
</section>
|
||||
|
||||
<section id="page-network" class="page" aria-labelledby="network-heading" hidden>
|
||||
<div class="page-heading"><div><span class="subtle-label">Good connections start here</span><h1 id="network-heading" tabindex="-1">Network & ports<span class="heading-period">.</span></h1></div><span class="tag"><svg class="icon"><use href="#i-network"/></svg>Private IPv4 · TCP</span></div>
|
||||
<div id="network-summary" class="compact-metrics"></div>
|
||||
<div class="network-layout"><article class="soft-panel network-map-panel"><header class="section-heading"><div><h2>Your private fabric</h2><span>One host. Room to connect.</span></div></header><div class="fabric-diagram"><div class="fabric-node"><span class="round-icon"><svg class="icon"><use href="#i-server"/></svg></span><strong>Local host</strong><small>UVM control plane</small></div><div class="fabric-connector"></div><div class="fabric-node fabric-gateway"><span class="round-icon"><svg class="icon"><use href="#i-network"/></svg></span><strong id="network-gateway">No gateway yet</strong><small>Private gateway</small></div><div class="fabric-branches" aria-hidden="true"><span></span><span></span><span></span></div><div class="fabric-guests" aria-hidden="true"><svg class="icon"><use href="#i-server"/></svg><svg class="icon"><use href="#i-server"/></svg><svg class="icon"><use href="#i-server"/></svg></div><span id="network-machine-count" class="muted">Waiting for your fleet</span></div><p class="panel-footnote">Port rules allow private guest TCP traffic. HTTP and HTTPS are descriptive labels for TCP services.</p></article><article class="soft-panel network-policies"><header class="section-heading"><div><h2>Ports, with purpose</h2><span>Choose a machine to manage its rules.</span></div><svg class="icon caption-icon"><use href="#i-shield"/></svg></header><div id="network-policies"></div></article></div>
|
||||
</section>
|
||||
|
||||
<section id="page-vm-detail" class="page" aria-labelledby="detail-heading" hidden>
|
||||
<a class="quiet-link back-link" href="#vms"><svg class="icon"><use href="#i-back"/></svg>Back to machines</a>
|
||||
<div id="detail-loading" class="loading-state">Getting to know this machine…</div>
|
||||
<div id="detail-content" hidden>
|
||||
<div class="page-heading detail-heading"><div><span class="subtle-label">A closer look</span><h1 id="detail-heading" tabindex="-1"></h1><span id="detail-id" class="mono muted"></span></div><div id="detail-actions" class="button-row"></div></div>
|
||||
<div id="detail-error" class="notice notice-error" hidden></div>
|
||||
<div class="detail-grid"><article class="soft-panel detail-card"><header class="section-heading"><h2>The essentials</h2><span id="detail-status"></span></header><dl id="detail-config" class="detail-list"></dl></article><article class="soft-panel detail-card"><header class="section-heading"><h2>A place in the network</h2><svg class="icon caption-icon"><use href="#i-network"/></svg></header><dl id="detail-network" class="detail-list"></dl></article></div>
|
||||
<article class="soft-panel ssh-panel"><div><span class="round-icon"><svg class="icon"><use href="#i-terminal"/></svg></span><div><h2>A direct connection</h2><p id="ssh-hint" class="muted"></p></div></div><div class="ssh-command"><code id="ssh-command"></code><button class="icon-button" data-action="copy-ssh" type="button" aria-label="Copy SSH command"><svg class="icon"><use href="#i-copy"/></svg></button></div></article>
|
||||
<article class="soft-panel ports-panel"><header class="section-heading"><div><h2>Private port policy</h2><span>Just the connections this machine needs.</span></div><div class="button-row"><button id="edit-ports-btn" class="button button-small" type="button" data-action="edit-ports">Edit rules</button><button id="sync-ports-btn" class="icon-button" type="button" data-action="sync-ports" aria-label="Sync port policy" title="Sync port policy"><svg class="icon"><use href="#i-refresh"/></svg></button></div></header><div id="detail-ports" class="port-list"></div><form id="port-editor" class="port-editor" hidden><label class="field" for="port-input"><span>Port rules <small>PORT:TCP, PORT:HTTP, or PORT:HTTPS</small></span><input id="port-input" type="text" placeholder="22:TCP, 80:HTTP, 443:HTTPS" spellcheck="false" /></label><p id="port-error" class="form-error" role="alert"></p><div class="button-row"><button class="button button-primary button-small" type="submit" value="set">Replace rules</button><button id="open-ports-btn" class="button button-small" type="submit" value="open">Open ports</button><button id="close-ports-btn" class="button button-small" type="submit" value="close">Close ports</button><button class="button button-quiet button-small" type="button" data-action="cancel-ports">Cancel</button></div><p class="panel-footnote">An empty replacement creates a managed policy with no inbound TCP ports.</p></form></article>
|
||||
<article class="soft-panel log-panel"><header class="section-heading"><div><h2>A window into the runtime</h2><span>Recent Firecracker log entries.</span></div><div class="button-row"><label class="select-wrap"><span class="sr-only">Log tail length</span><select id="log-tail"><option value="100">100 lines</option><option value="250">250 lines</option><option value="500">500 lines</option><option value="1000">1,000 lines</option></select></label><button id="log-refresh-btn" class="icon-button" type="button" data-action="refresh-logs" aria-label="Refresh logs"><svg class="icon"><use href="#i-refresh"/></svg></button></div></header><pre id="log-output" class="log-output" tabindex="0"></pre><p id="log-meta" class="panel-footnote"></p></article>
|
||||
<div class="detail-delete-row"><span>Every machine has its own private disk.</span><button class="quiet-link danger-text" type="button" data-action="delete-current"><svg class="icon"><use href="#i-trash"/></svg>Delete machine</button></div>
|
||||
</div>
|
||||
</section>
|
||||
|
||||
<section id="page-create" class="page" aria-labelledby="create-heading" hidden>
|
||||
<div class="page-heading"><div><span class="subtle-label">Every idea starts somewhere</span><h1 id="create-heading" tabindex="-1">Make something new<span class="heading-period">.</span></h1></div><a class="quiet-link" href="#vms">Back to machines <svg class="icon"><use href="#i-arrow"/></svg></a></div>
|
||||
<form id="create-form" class="create-layout">
|
||||
<div class="create-fields"><section class="soft-panel form-section"><header class="section-heading"><div><h2><span class="step-number">01</span>A name and a little space</h2><span>Give your new machine a shape.</span></div></header><label class="field" for="create-name"><span>Machine name <small>Optional</small></span><input id="create-name" type="text" name="name" placeholder="e.g. my-little-server" pattern="[a-z][a-z0-9\-]{0,62}" maxlength="63" autocomplete="off" /></label><fieldset class="preset-fieldset"><legend>Start with a size</legend><div class="size-presets"><button class="size-preset active" type="button" data-preset="small" aria-pressed="true"><svg class="icon"><use href="#i-server"/></svg><strong>Small</strong><span>1 vCPU · 512 MiB</span></button><button class="size-preset" type="button" data-preset="balanced" aria-pressed="false"><svg class="icon"><use href="#i-server"/></svg><strong>Balanced</strong><span>2 vCPU · 1 GiB</span></button><button class="size-preset" type="button" data-preset="roomy" aria-pressed="false"><svg class="icon"><use href="#i-server"/></svg><strong>Roomy</strong><span>4 vCPU · 2 GiB</span></button></div></fieldset><div class="form-grid"><label class="field" for="create-cpu"><span>CPU capacity</span><input id="create-cpu" name="cpu" type="number" value="1" min="0.01" step="any" required /><small>Fractional requests round up to whole vCPUs.</small></label><label class="field" for="create-ram"><span>Memory</span><input id="create-ram" name="ram" type="text" value="512M" required /><small>At least 128 MiB. Try 512M, 1G, or 2G.</small></label></div></section>
|
||||
<section class="soft-panel form-section"><header class="section-heading"><div><h2><span class="step-number">02</span>A way to connect</h2><span>Private networking and guest access.</span></div></header><label class="field" for="create-guest-ip"><span>Guest IPv4 address <small>Optional</small></span><input id="create-guest-ip" name="guest_ip" type="text" placeholder="Automatically assigned" autocomplete="off" /></label><div class="form-grid"><label class="field" for="create-username"><span>Guest user</span><input id="create-username" name="username" type="text" value="root" autocomplete="username" required /></label><label class="field" for="create-password"><span>Guest password</span><span class="password-field"><input id="create-password" name="password" type="password" value="root" autocomplete="new-password" maxlength="128" required /><button class="icon-button" type="button" data-action="toggle-password" aria-label="Show password" aria-pressed="false"><svg class="icon"><use href="#i-eye"/></svg></button></span></label></div><p class="panel-footnote">Use an account that exists in your guest image. Credentials are applied to the machine’s private disk.</p></section>
|
||||
<section class="soft-panel form-section"><header class="section-heading"><div><h2><span class="step-number">03</span>Open the right doors</h2><span>Choose which private TCP services are allowed.</span></div></header><label class="toggle-field"><span><strong>Include the default SSH rule</strong><small>Allow TCP port 22 for terminal access.</small></span><input id="create-default-ssh" name="default_ssh" type="checkbox" checked /><span class="toggle-track" aria-hidden="true"></span></label><label class="field" for="create-ports"><span>Additional port rules <small>Optional</small></span><input id="create-ports" name="ports" type="text" placeholder="80:HTTP, 443:HTTPS" spellcheck="false" /><small>Separate rules with commas. HTTP and HTTPS both use TCP.</small></label></section></div>
|
||||
<aside class="create-summary soft-panel"><div class="summary-art" aria-hidden="true"><div></div><div></div><span><svg class="icon"><use href="#i-server"/></svg></span></div><span class="subtle-label">Your next little machine</span><h2 id="create-summary-name">Room for an idea.</h2><p>A private disk, a network identity,<br />and a fresh start.</p><dl id="create-summary-details" class="detail-list"></dl><p id="create-error" class="form-error" role="alert"></p><button id="create-submit" class="button button-primary button-wide" type="submit"><span>Create machine</span><svg class="icon"><use href="#i-arrow"/></svg></button><a href="#vms" class="quiet-link summary-cancel">Maybe later</a><span class="summary-note"><svg class="icon"><use href="#i-spark"/></svg>Built on Firecracker</span></aside>
|
||||
</form>
|
||||
</section>
|
||||
|
||||
<section id="page-system" class="page" aria-labelledby="system-heading" hidden>
|
||||
<div class="page-heading"><div><span class="subtle-label">Behind every little machine</span><h1 id="system-heading" tabindex="-1">A look at your host<span class="heading-period">.</span></h1></div><button id="diagnostics-refresh-btn" class="button" type="button" data-action="diagnostics"><svg class="icon"><use href="#i-refresh"/></svg>Run checks</button></div>
|
||||
<div id="health-summary" class="compact-metrics"></div>
|
||||
<div class="health-layout"><article class="soft-panel diagnostics-panel"><header class="section-heading"><div><h2>The essentials, checked</h2><span>Readiness checks from your local host.</span></div><span id="diagnostics-count" class="tag">Checking</span></header><div id="diagnostics-list" class="diagnostics-list"><div class="loading-state">Checking in with your host…</div></div></article><div class="health-side"><article class="soft-panel install-panel"><span class="round-icon"><svg class="icon"><use href="#i-download"/></svg></span><h2>A foundation for your fleet</h2><p>Install the Firecracker binary, guest kernel, and root filesystem, ready for your next machine.</p><div class="install-assets"><span><svg class="icon"><use href="#i-cpu"/></svg>Firecracker</span><span><svg class="icon"><use href="#i-terminal"/></svg>Guest kernel</span><span><svg class="icon"><use href="#i-server"/></svg>Root filesystem</span></div><label class="toggle-field"><span><strong>Refresh existing assets</strong><small>Reinstall with force enabled.</small></span><input id="install-force" type="checkbox" /><span class="toggle-track" aria-hidden="true"></span></label><button id="install-btn" class="button button-primary button-wide" type="button" data-action="install"><span>Install assets</span><svg class="icon"><use href="#i-arrow"/></svg></button><pre id="install-result" class="install-result" role="status" hidden></pre></article><article class="soft-panel server-info"><header class="section-heading"><h2>Close to home</h2><svg class="icon caption-icon"><use href="#i-network"/></svg></header><dl class="detail-list"><div><dt>API origin</dt><dd id="info-api-url"></dd></div><div><dt>Last host check</dt><dd id="info-observed">Not checked yet</dd></div><div><dt>Connection</dt><dd>Session token</dd></div></dl><a href="/docs" target="_blank" rel="noopener" class="quiet-link">Open API reference <svg class="icon"><use href="#i-arrow"/></svg></a></article></div></div>
|
||||
</section>
|
||||
</main>
|
||||
</div>
|
||||
</section>
|
||||
|
||||
<div id="action-menu" class="action-menu" role="menu" aria-label="Machine actions" hidden></div>
|
||||
<div id="toast-container" class="toast-container" aria-live="polite" aria-atomic="false"></div>
|
||||
<dialog id="confirm-dialog" class="confirm-dialog" aria-labelledby="confirm-title" aria-describedby="confirm-body"><form method="dialog"><span class="round-icon" id="confirm-icon"><svg class="icon"><use href="#i-info"/></svg></span><span class="subtle-label">A moment before we continue</span><h2 id="confirm-title"></h2><p id="confirm-body"></p><div class="dialog-actions"><button class="button button-quiet" value="cancel" autofocus>Cancel</button><button id="confirm-ok" class="button button-primary" value="confirm">Confirm</button></div></form></dialog>
|
||||
<noscript><p class="noscript-message">Enable JavaScript to connect to your UVM workspace.</p></noscript>
|
||||
</body>
|
||||
</html>
|
||||
|
||||
+1281
-680
File diff suppressed because it is too large
Load Diff
Reference in New Issue
Block a user