145 lines
8.3 KiB
HTML
145 lines
8.3 KiB
HTML
|
|
{{define "admin_storage_tests.html"}}{{template "base" .}}{{end}}
|
|||
|
|
|
|||
|
|
{{define "content"}}
|
|||
|
|
<section class="app-shell admin-shell" aria-labelledby="admin-storage-tests-title">
|
|||
|
|
<aside class="app-sidebar">
|
|||
|
|
<nav class="sidebar-nav">
|
|||
|
|
<a class="sidebar-link" href="/admin">{{template "icon-dashboard" .}}<span>Overview</span></a>
|
|||
|
|
<a class="sidebar-link" href="/admin/files">{{template "icon-folder" .}}<span>Files</span></a>
|
|||
|
|
<a class="sidebar-link" href="/admin/users">{{template "icon-user-circle" .}}<span>Users</span></a>
|
|||
|
|
<a class="sidebar-link" href="/admin/settings">{{template "icon-settings" .}}<span>Settings</span></a>
|
|||
|
|
<a class="sidebar-link is-active" href="/admin/storage">{{template "icon-database" .}}<span>Storage</span></a>
|
|||
|
|
</nav>
|
|||
|
|
<hr class="sidebar-sep">
|
|||
|
|
<nav class="sidebar-nav">
|
|||
|
|
<a class="sidebar-link" href="/app">{{template "icon-home-simple" .}}<span>My Files</span></a>
|
|||
|
|
</nav>
|
|||
|
|
<hr class="sidebar-sep">
|
|||
|
|
<form class="sidebar-logout" action="/admin/logout" method="post">
|
|||
|
|
<input type="hidden" name="csrf_token" value="{{.CSRFToken}}">
|
|||
|
|
<button class="button button-outline" type="submit">{{template "icon-log-out" .}}<span>Sign out</span></button>
|
|||
|
|
</form>
|
|||
|
|
</aside>
|
|||
|
|
|
|||
|
|
<div class="app-main">
|
|||
|
|
<div class="admin-header">
|
|||
|
|
<div>
|
|||
|
|
<p class="kicker">Storage testing</p>
|
|||
|
|
<h1 id="admin-storage-tests-title">{{.Data.PageTitle}}</h1>
|
|||
|
|
<p class="muted-copy">Connection status, speed-test history, and background benchmark runs for this backend.</p>
|
|||
|
|
</div>
|
|||
|
|
<div class="storage-tests-header-actions">
|
|||
|
|
<a class="button button-outline" href="/admin/storage">Back</a>
|
|||
|
|
{{if .Data.StorageTest.CanRun}}
|
|||
|
|
<button class="button button-primary" type="button" data-storage-speed-open>New Test</button>
|
|||
|
|
{{end}}
|
|||
|
|
</div>
|
|||
|
|
</div>
|
|||
|
|
|
|||
|
|
{{if .Data.Notice}}<p class="form-success">{{.Data.Notice}}</p>{{end}}
|
|||
|
|
{{if .Data.Error}}<p class="form-error">{{.Data.Error}}</p>{{end}}
|
|||
|
|
|
|||
|
|
<div class="storage-card">
|
|||
|
|
<div class="storage-card-header">
|
|||
|
|
<div class="storage-card-identity">
|
|||
|
|
<div class="storage-card-icon">
|
|||
|
|
{{if eq .Data.StorageTest.Config.Type "local"}}{{template "icon-hard-drive" .}}
|
|||
|
|
{{else if eq .Data.StorageTest.Config.Type "sftp"}}{{template "icon-database" .}}
|
|||
|
|
{{else if eq .Data.StorageTest.Config.Type "smb"}}{{template "icon-folder" .}}
|
|||
|
|
{{else if eq .Data.StorageTest.Config.Type "webdav"}}{{template "icon-cloud-sync" .}}
|
|||
|
|
{{else}}{{template "icon-cloud-upload" .}}{{end}}
|
|||
|
|
</div>
|
|||
|
|
<div>
|
|||
|
|
<strong class="storage-card-name">{{.Data.StorageTest.Config.Name}}</strong>
|
|||
|
|
<div class="storage-card-meta">
|
|||
|
|
<span class="badge">{{if eq .Data.StorageTest.Config.Provider "contabo"}}Contabo{{else if eq .Data.StorageTest.Config.Type "sftp"}}SFTP{{else if eq .Data.StorageTest.Config.Type "smb"}}Samba{{else if eq .Data.StorageTest.Config.Type "webdav"}}WebDAV{{else if eq .Data.StorageTest.Config.Type "s3"}}S3{{else if eq .Data.StorageTest.Config.Type "local"}}Local files{{else}}{{.Data.StorageTest.Config.Type}}{{end}}</span>
|
|||
|
|
{{if .Data.StorageTest.Config.LastTestSuccess}}<span class="badge badge-active">Connection OK</span>{{else}}<span class="badge badge-disabled">Needs connection test</span>{{end}}
|
|||
|
|
{{if .Data.StorageTest.UsageLabel}}<span class="storage-card-usage">{{.Data.StorageTest.UsageLabel}}</span>{{end}}
|
|||
|
|
</div>
|
|||
|
|
</div>
|
|||
|
|
</div>
|
|||
|
|
<form action="/admin/storage/{{.Data.StorageTest.Config.ID}}/test" method="post">
|
|||
|
|
<input type="hidden" name="csrf_token" value="{{.CSRFToken}}">
|
|||
|
|
<input type="hidden" name="next" value="tests">
|
|||
|
|
<button class="button button-outline button-sm" type="submit">Test Connection</button>
|
|||
|
|
</form>
|
|||
|
|
</div>
|
|||
|
|
{{if not (.Data.StorageTest.Config.LastTestedAt.IsZero)}}
|
|||
|
|
<div class="storage-card-summary">
|
|||
|
|
<div class="storage-detail storage-detail-test {{if .Data.StorageTest.Config.LastTestSuccess}}is-ok{{else}}is-err{{end}}">
|
|||
|
|
<span>Last test</span>
|
|||
|
|
<span>{{.Data.StorageTest.Config.LastTestedAt.Format "Jan 2, 15:04"}} · {{if .Data.StorageTest.Config.LastTestSuccess}}Passed{{else}}{{if .Data.StorageTest.Config.LastTestError}}{{.Data.StorageTest.Config.LastTestError}}{{else}}Failed{{end}}{{end}}</span>
|
|||
|
|
</div>
|
|||
|
|
</div>
|
|||
|
|
{{end}}
|
|||
|
|
</div>
|
|||
|
|
|
|||
|
|
{{if not .Data.StorageTest.CanRun}}
|
|||
|
|
<p class="form-error">Run a successful connection test before starting speed tests.</p>
|
|||
|
|
{{end}}
|
|||
|
|
|
|||
|
|
<div class="storage-results-list storage-results-page" data-storage-tests-page data-storage-tests-url="/admin/storage/{{.Data.StorageTest.Config.ID}}/tests.json">
|
|||
|
|
{{if .Data.StorageTest.Tests}}
|
|||
|
|
{{range .Data.StorageTest.Tests}}
|
|||
|
|
<details class="storage-result-row" data-storage-test-id="{{.ID}}">
|
|||
|
|
<summary>
|
|||
|
|
<span>{{.StartedLabel}}</span>
|
|||
|
|
<span>{{if eq .Mode "custom"}}{{.CustomFileCount}} files × {{.CustomFileSizeMB}} MB{{else}}{{.ModeLabel}}{{end}}</span>
|
|||
|
|
<span class="storage-result-status is-{{.Status}}">{{.Status}}</span>
|
|||
|
|
</summary>
|
|||
|
|
<div class="storage-test-progress" aria-label="Test progress">
|
|||
|
|
<div class="storage-test-progress-bar"><span style="width: {{.ProgressPercent}}%"></span></div>
|
|||
|
|
<small>{{.ProgressPercent}}%{{if .Stage}} · {{.Stage}}{{end}}</small>
|
|||
|
|
</div>
|
|||
|
|
<div class="storage-result-detail">
|
|||
|
|
<span><strong>Finished</strong>{{.FinishedLabel}}</span>
|
|||
|
|
<span><strong>Files</strong>{{.FilesWritten}}</span>
|
|||
|
|
<span><strong>Size</strong>{{.TotalSizeLabel}}</span>
|
|||
|
|
<span><strong>Write</strong>{{.WriteSpeedLabel}}</span>
|
|||
|
|
<span><strong>Read</strong>{{.ReadSpeedLabel}}</span>
|
|||
|
|
{{if .Error}}<span class="storage-result-error"><strong>Error</strong>{{.Error}}</span>{{end}}
|
|||
|
|
</div>
|
|||
|
|
</details>
|
|||
|
|
{{end}}
|
|||
|
|
{{else}}
|
|||
|
|
<p class="muted-copy">No speed tests have been run for this backend yet.</p>
|
|||
|
|
{{end}}
|
|||
|
|
</div>
|
|||
|
|
|
|||
|
|
<div class="storage-modal" data-storage-speed-modal hidden>
|
|||
|
|
<div class="storage-modal-backdrop" data-storage-modal-close></div>
|
|||
|
|
<div class="storage-modal-card" role="dialog" aria-modal="true" aria-label="Run storage speed test">
|
|||
|
|
<div class="storage-modal-header">
|
|||
|
|
<strong>New speed test</strong>
|
|||
|
|
<button type="button" class="button button-outline button-sm" data-storage-modal-close>Close</button>
|
|||
|
|
</div>
|
|||
|
|
<form action="/admin/storage/{{.Data.StorageTest.Config.ID}}/speed-test" method="post" class="storage-speed-form">
|
|||
|
|
<input type="hidden" name="csrf_token" value="{{.CSRFToken}}">
|
|||
|
|
<label class="storage-speed-option">
|
|||
|
|
<input type="radio" name="mode" value="small">
|
|||
|
|
<span><strong>Many small files test</strong><small>Writes, reads, and deletes many tiny objects.</small></span>
|
|||
|
|
</label>
|
|||
|
|
<label class="storage-speed-option">
|
|||
|
|
<input type="radio" name="mode" value="big">
|
|||
|
|
<span><strong>One big file test</strong><small>Uses one larger object for sequential throughput.</small></span>
|
|||
|
|
</label>
|
|||
|
|
<label class="storage-speed-option">
|
|||
|
|
<input type="radio" name="mode" value="mixed" checked>
|
|||
|
|
<span><strong>Average Test ( mix )</strong><small>Balances small object overhead and larger transfer speed.</small></span>
|
|||
|
|
</label>
|
|||
|
|
<label class="storage-speed-option">
|
|||
|
|
<input type="radio" name="mode" value="custom" data-storage-custom-radio>
|
|||
|
|
<span><strong>Custom</strong><small>Choose how many mock files to create and the size of each file.</small></span>
|
|||
|
|
</label>
|
|||
|
|
<div class="storage-custom-fields" data-storage-custom-fields hidden>
|
|||
|
|
<label><span>Files</span><input type="number" name="custom_file_count" min="1" max="500" value="10"></label>
|
|||
|
|
<label><span>Size per file (MB)</span><input type="number" name="custom_file_size_mb" min="0.001" step="0.001" value="1"></label>
|
|||
|
|
</div>
|
|||
|
|
<button class="button button-primary button-sm" type="submit">Run in background</button>
|
|||
|
|
</form>
|
|||
|
|
</div>
|
|||
|
|
</div>
|
|||
|
|
</div>
|
|||
|
|
</section>
|
|||
|
|
{{end}}
|