mirror of
https://github.com/tiennm99/coolify.git
synced 2026-10-15 08:17:02 +00:00
feat(ui): Shadow UI redesign, domain management, and DNS autoconfigure (#11119)
Co-authored-by: ShadowArcanist <162910371+ShadowArcanist@users.noreply.github.com>
This commit is contained in:
1 parent
0b843bb07c
commit
8ae56587d5
497 files changed
+44045
-22630
No files matched your search
@@ -1,139 +1,49 @@
|
||||
@php
|
||||
$serverPageItems = [
|
||||
[
|
||||
'label' => 'Configuration',
|
||||
'route' => 'server.show',
|
||||
'active' => request()->routeIs('server.show', 'server.advanced', 'server.private-key', 'server.cloud-provider-token', 'server.ca-certificate', 'server.cloudflare-tunnel', 'server.docker-cleanup', 'server.destinations', 'server.log-drains', 'server.metrics', 'server.swarm', 'server.delete'),
|
||||
],
|
||||
[
|
||||
'label' => 'Proxy',
|
||||
'route' => 'server.proxy',
|
||||
'active' => request()->routeIs('server.proxy', 'server.proxy.*'),
|
||||
'visible' => ! $server->isSwarmWorker() && ! $server->settings->is_build_server,
|
||||
],
|
||||
[
|
||||
'label' => 'Sentinel',
|
||||
'route' => 'server.sentinel',
|
||||
'active' => request()->routeIs('server.sentinel', 'server.sentinel.*'),
|
||||
'visible' => $server->isFunctional() && ! $server->isSwarm() && ! $server->settings->is_build_server && auth()->user()?->can('viewSentinel', $server),
|
||||
],
|
||||
[
|
||||
'label' => 'Resources',
|
||||
'route' => 'server.resources',
|
||||
'active' => request()->routeIs('server.resources'),
|
||||
],
|
||||
[
|
||||
'label' => 'Terminal',
|
||||
'route' => 'server.command',
|
||||
'active' => request()->routeIs('server.command'),
|
||||
'navigate' => false,
|
||||
'visible' => auth()->user()?->can('canAccessTerminal'),
|
||||
],
|
||||
[
|
||||
'label' => 'Security',
|
||||
'route' => 'server.security.patches',
|
||||
'active' => request()->routeIs('server.security.patches'),
|
||||
'visible' => auth()->user()?->can('update', $server),
|
||||
],
|
||||
];
|
||||
$proxyMenuItems = [
|
||||
[
|
||||
'label' => 'Configuration',
|
||||
'route' => 'server.proxy',
|
||||
'active' => request()->routeIs('server.proxy'),
|
||||
'icon' => 'settings',
|
||||
],
|
||||
[
|
||||
'label' => 'Dynamic Configurations',
|
||||
'route' => 'server.proxy.dynamic-confs',
|
||||
'active' => request()->routeIs('server.proxy.dynamic-confs'),
|
||||
'icon' => 'sliders',
|
||||
'visible' => $server->proxySet(),
|
||||
],
|
||||
[
|
||||
'label' => 'Logs',
|
||||
'route' => 'server.proxy.logs',
|
||||
'active' => request()->routeIs('server.proxy.logs'),
|
||||
'icon' => 'file-content',
|
||||
'visible' => $server->proxySet(),
|
||||
'navigate' => false,
|
||||
],
|
||||
];
|
||||
|
||||
$serverPageItems = array_values(array_filter(
|
||||
$serverPageItems,
|
||||
fn (array $item): bool => $item['visible'] ?? true,
|
||||
));
|
||||
$proxyMenuItems = array_values(array_filter(
|
||||
$proxyMenuItems,
|
||||
fn (array $item): bool => $item['visible'] ?? true,
|
||||
));
|
||||
$activeProxyMenuItem = collect($proxyMenuItems)->firstWhere('active', true) ?? $proxyMenuItems[0];
|
||||
$activeProxyMenuValue = (($activeProxyMenuItem['navigate'] ?? true) ? 'navigate' : 'location').'|proxy|'.route($activeProxyMenuItem['route'], $parameters);
|
||||
@endphp
|
||||
|
||||
<div class="w-full md:w-auto">
|
||||
<div class="mb-4 w-full border-b-2 border-solid border-neutral-200 pb-4 md:hidden dark:border-coolgray-200">
|
||||
<label id="server-mobile-section-label" for="server-mobile-section" class="mb-1 block text-xs font-semibold uppercase tracking-wide text-neutral-500 dark:text-neutral-400">Section</label>
|
||||
<select id="server-mobile-section" class="select w-full" aria-label="Proxy menu"
|
||||
data-current-value="{{ $activeProxyMenuValue }}"
|
||||
x-data="{
|
||||
init() {
|
||||
this.syncFromLocation();
|
||||
window.Livewire?.hook?.('morphed', ({ el }) => {
|
||||
if (el.contains(this.$el)) {
|
||||
queueMicrotask(() => this.syncFromLocation());
|
||||
}
|
||||
});
|
||||
},
|
||||
selected: $el.dataset.currentValue,
|
||||
syncFromLocation() {
|
||||
const currentUrl = new URL(window.location.href);
|
||||
const matchingOptions = Array.from(this.$el.options).filter((option) => {
|
||||
const optionUrl = new URL(option.value.split('|').slice(2).join('|'), window.location.origin);
|
||||
|
||||
return optionUrl.pathname === currentUrl.pathname;
|
||||
});
|
||||
const selectedOption = matchingOptions.find((option) => option.value.startsWith('navigate|proxy|') || option.value.startsWith('location|proxy|')) || matchingOptions[0];
|
||||
|
||||
if (selectedOption) {
|
||||
this.selected = selectedOption.value;
|
||||
}
|
||||
},
|
||||
}"
|
||||
x-on:livewire:navigated.window="syncFromLocation()"
|
||||
x-model="selected"
|
||||
x-on:change="
|
||||
const value = $event.target.value;
|
||||
const url = value.split('|').slice(2).join('|');
|
||||
|
||||
if (value.startsWith('navigate|')) {
|
||||
window.Livewire?.navigate ? window.Livewire.navigate(url) : window.location.href = url;
|
||||
return;
|
||||
}
|
||||
|
||||
window.location.href = url;
|
||||
">
|
||||
<optgroup label="Server">
|
||||
@foreach ($serverPageItems as $menuItem)
|
||||
<option value="{{ ($menuItem['navigate'] ?? true) ? 'navigate' : 'location' }}|server|{{ route($menuItem['route'], $parameters) }}">
|
||||
{{ $menuItem['label'] }}
|
||||
</option>
|
||||
@endforeach
|
||||
</optgroup>
|
||||
<optgroup label="Proxy">
|
||||
@foreach ($proxyMenuItems as $menuItem)
|
||||
<option value="{{ ($menuItem['navigate'] ?? true) ? 'navigate' : 'location' }}|proxy|{{ route($menuItem['route'], $parameters) }}">
|
||||
{{ $menuItem['label'] }}
|
||||
</option>
|
||||
@endforeach
|
||||
</optgroup>
|
||||
</select>
|
||||
</div>
|
||||
|
||||
<div class="sub-menu-wrapper hidden md:flex">
|
||||
<aside class="application-settings-navigation min-w-0 xl:sticky xl:top-26 xl:self-start">
|
||||
<nav aria-label="Proxy sections"
|
||||
class="grid grid-cols-2 gap-0.5 border-y border-neutral-200 py-3 sm:grid-cols-3 xl:grid-cols-1 xl:border-y-0 xl:py-0 dark:border-white/[0.06]">
|
||||
<div class="nav-section hidden xl:block">Proxy</div>
|
||||
@foreach ($proxyMenuItems as $menuItem)
|
||||
<a class="{{ $menuItem['active'] ? 'sub-menu-item menu-item-active' : 'sub-menu-item' }}" @if ($menuItem['navigate'] ?? true) {{ wireNavigate() }} @endif
|
||||
<a wire:key="server-proxy-link-{{ str($menuItem['label'])->slug() }}"
|
||||
@class([
|
||||
'menu-item',
|
||||
'menu-item-active' => $menuItem['active'],
|
||||
])
|
||||
@if ($menuItem['navigate'] ?? true) {{ wireNavigate() }} @endif
|
||||
href="{{ route($menuItem['route'], $parameters) }}">
|
||||
<x-reicon :name="$menuItem['icon']" class="menu-item-icon" />
|
||||
<span class="menu-item-label">{{ $menuItem['label'] }}</span>
|
||||
</a>
|
||||
@endforeach
|
||||
</div>
|
||||
</div>
|
||||
</nav>
|
||||
</aside>
|
||||
Reference in new issue
Block a user