wip
This commit is contained in:
parent
57c64d0b86
commit
752c86d8f7
@ -2,8 +2,6 @@
|
||||
|
||||
namespace App\Http\Livewire\Destination;
|
||||
|
||||
use App\Models\StandaloneDocker;
|
||||
use App\Models\SwarmDocker;
|
||||
use Livewire\Component;
|
||||
|
||||
class Form extends Component
|
||||
@ -22,8 +20,18 @@ public function submit()
|
||||
}
|
||||
public function delete()
|
||||
{
|
||||
// instantRemoteProcess(['docker network rm -f ' . $this->destination->network], $this->destination->server);
|
||||
$this->destination->delete();
|
||||
return redirect()->route('dashboard');
|
||||
try {
|
||||
if ($this->destination->getMorphClass() === 'App\Models\StandaloneDocker') {
|
||||
if ($this->destination->attachedTo()) {
|
||||
return $this->emit('error', 'You must delete all resources before deleting this destination.');
|
||||
}
|
||||
instantRemoteProcess(["docker network disconnect {$this->destination->network} coolify-proxy"], $this->destination->server, throwError: false);
|
||||
instantRemoteProcess(['docker network rm -f ' . $this->destination->network], $this->destination->server);
|
||||
}
|
||||
$this->destination->delete();
|
||||
return redirect()->route('dashboard');
|
||||
} catch (\Exception $e) {
|
||||
return generalErrorHandler($e);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
@ -44,6 +44,10 @@ public function submit()
|
||||
$this->addError('network', 'Network already added to this server.');
|
||||
return;
|
||||
}
|
||||
$server = Server::find($this->server_id);
|
||||
instantRemoteProcess(['docker network create --attachable ' . $this->network], $server, throwError: false);
|
||||
instantRemoteProcess(["docker network connect $this->network coolify-proxy"], $server, throwError: false);
|
||||
|
||||
$docker = ModelsStandaloneDocker::create([
|
||||
'name' => $this->name,
|
||||
'network' => $this->network,
|
||||
@ -51,9 +55,7 @@ public function submit()
|
||||
'team_id' => session('currentTeam')->id
|
||||
]);
|
||||
|
||||
$server = Server::find($this->server_id);
|
||||
|
||||
instantRemoteProcess(['docker network create --attachable ' . $this->network], $server, throwError: false);
|
||||
return redirect()->route('destination.show', $docker->uuid);
|
||||
}
|
||||
}
|
||||
|
@ -20,7 +20,8 @@ class Form extends Component
|
||||
'server.ip' => 'required',
|
||||
'server.user' => 'required',
|
||||
'server.port' => 'required',
|
||||
'server.settings.is_validated' => 'required'
|
||||
'server.settings.is_validated' => 'required',
|
||||
'server.settings.is_part_of_swarm' => 'required'
|
||||
];
|
||||
public function mount()
|
||||
{
|
||||
|
@ -19,24 +19,28 @@ class ByIp extends Component
|
||||
public string $ip;
|
||||
public string $user = 'root';
|
||||
public int $port = 22;
|
||||
public bool $is_part_of_swarm = false;
|
||||
|
||||
protected $rules = [
|
||||
'name' => 'required',
|
||||
'ip' => 'required',
|
||||
'user' => 'required',
|
||||
'port' => 'required|integer',
|
||||
'is_part_of_swarm' => 'required|boolean',
|
||||
];
|
||||
public function mount()
|
||||
{
|
||||
$this->name = generateRandomName();
|
||||
if ($this->private_keys->count() > 0) {
|
||||
$this->private_key_id = $this->private_keys->first()->id;
|
||||
}
|
||||
$this->private_key_id = $this->private_keys->first()->id;
|
||||
}
|
||||
public function setPrivateKey(string $private_key_id)
|
||||
{
|
||||
$this->private_key_id = $private_key_id;
|
||||
}
|
||||
public function instantSave()
|
||||
{
|
||||
$this->emit('saved', 'Application settings updated!');
|
||||
}
|
||||
public function submit()
|
||||
{
|
||||
try {
|
||||
@ -51,8 +55,10 @@ public function submit()
|
||||
'user' => $this->user,
|
||||
'port' => $this->port,
|
||||
'team_id' => session('currentTeam')->id,
|
||||
'private_key_id' => $this->private_key_id
|
||||
'private_key_id' => $this->private_key_id,
|
||||
]);
|
||||
$server->settings->is_part_of_swarm = $this->is_part_of_swarm;
|
||||
$server->settings->save();
|
||||
return redirect()->route('server.show', $server->uuid);
|
||||
} catch (\Exception $e) {
|
||||
return generalErrorHandler($e);
|
||||
|
@ -13,8 +13,16 @@ public function applications()
|
||||
{
|
||||
return $this->morphMany(Application::class, 'destination');
|
||||
}
|
||||
public function databases()
|
||||
{
|
||||
return $this->morphMany(Database::class, 'destination');
|
||||
}
|
||||
public function server()
|
||||
{
|
||||
return $this->belongsTo(Server::class);
|
||||
}
|
||||
public function attachedTo()
|
||||
{
|
||||
return $this->applications->count() > 0 || $this->databases->count() > 0;
|
||||
}
|
||||
}
|
||||
|
@ -14,6 +14,8 @@ public function up(): void
|
||||
Schema::create('server_settings', function (Blueprint $table) {
|
||||
$table->id();
|
||||
$table->string('uuid')->unique();
|
||||
|
||||
$table->boolean('is_part_of_swarm')->default(false);
|
||||
$table->boolean('is_jump_server')->default(false);
|
||||
$table->boolean('is_build_server')->default(false);
|
||||
$table->boolean('is_validated')->default(false);
|
||||
|
@ -26,7 +26,7 @@ public function run(): void
|
||||
'team_id' => $root_team->id,
|
||||
'private_key_id' => $private_key_1->id,
|
||||
'extra_attributes' => ServerMetadata::from([
|
||||
'proxy' => ProxyTypes::TRAEFIK_V2->value
|
||||
'proxy_type' => ProxyTypes::TRAEFIK_V2->value
|
||||
]),
|
||||
]);
|
||||
Server::create([
|
||||
|
@ -19,7 +19,7 @@ public function run(): void
|
||||
$server_2->settings->save();
|
||||
|
||||
$server_3 = Server::find(2)->load(['settings']);
|
||||
$server_3->settings->is_build_server = false;
|
||||
$server_3->settings->is_part_of_swarm = true;
|
||||
$server_3->settings->is_validated = false;
|
||||
$server_3->settings->save();
|
||||
}
|
||||
|
@ -7,8 +7,8 @@
|
||||
<x-inputs.input id="destination.network" label="Docker Network" readonly />
|
||||
@endif
|
||||
<div>
|
||||
<x-inputs.button>
|
||||
Submit
|
||||
<x-inputs.button isBold type="submit">
|
||||
Save
|
||||
</x-inputs.button>
|
||||
<x-inputs.button isWarning x-on:click.prevent="deleteDestination = true">
|
||||
Delete
|
||||
|
@ -4,10 +4,11 @@
|
||||
<x-inputs.input id="network" label="Network" required />
|
||||
<x-inputs.select id="server_id" label="Select a server" required>
|
||||
@foreach ($servers as $server)
|
||||
<option disabled>Select a server</option>
|
||||
<option value="{{ $server->id }}">{{ $server->name }}</option>
|
||||
@endforeach
|
||||
</x-inputs.select>
|
||||
<x-inputs.button type="submit">
|
||||
<x-inputs.button isBold type="submit">
|
||||
Submit
|
||||
</x-inputs.button>
|
||||
</form>
|
||||
|
@ -1,14 +1,16 @@
|
||||
<div x-data="{ deletePrivateKey: false }">
|
||||
<x-naked-modal show="deletePrivateKey" message='Are you sure you would like to delete this private key?' />
|
||||
<form class="flex flex-col gap-2 w-96" wire:submit.prevent='changePrivateKey'>
|
||||
<form class="flex flex-col gap-2" wire:submit.prevent='changePrivateKey'>
|
||||
<x-inputs.input id="private_key.name" label="Name" required />
|
||||
<x-inputs.input id="private_key.description" label="Description" />
|
||||
<x-inputs.input type="textarea" id="private_key.private_key" label="Private Key" required />
|
||||
<x-inputs.button type="submit">
|
||||
Submit
|
||||
</x-inputs.button>
|
||||
<x-inputs.button isWarning x-on:click.prevent="deletePrivateKey = true">
|
||||
Delete
|
||||
</x-inputs.button>
|
||||
<x-inputs.input type="textarea" rows="10" id="private_key.private_key" label="Private Key" required />
|
||||
<div>
|
||||
<x-inputs.button isBold type="submit">
|
||||
Save
|
||||
</x-inputs.button>
|
||||
<x-inputs.button isWarning x-on:click.prevent="deletePrivateKey = true">
|
||||
Delete
|
||||
</x-inputs.button>
|
||||
</div>
|
||||
</form>
|
||||
</div>
|
||||
|
@ -1,27 +1,12 @@
|
||||
<div x-data="{ deleteServer: false }">
|
||||
<x-naked-modal show="deleteServer" message='Are you sure you would like to delete this server?' />
|
||||
<form wire:submit.prevent='submit' class="flex flex-col">
|
||||
<div class="flex flex-col pb-4">
|
||||
<div class="flex items-center gap-2">
|
||||
<div class="text-3xl font-bold">Server</div>
|
||||
<x-inputs.button isBold type="submit">Submit</x-inputs.button>
|
||||
<x-inputs.button isWarning x-on:click.prevent="deleteServer = true">
|
||||
Delete
|
||||
</x-inputs.button>
|
||||
</div>
|
||||
<div>
|
||||
@if ($server->settings->is_validated)
|
||||
<div class="text-green-400/90">Validated</div>
|
||||
@else
|
||||
<div class="text-red-400/90">Not validated</div>
|
||||
@endif
|
||||
</div>
|
||||
</div>
|
||||
|
||||
<div class="flex flex-col gap-2 xl:flex-row">
|
||||
<div class="flex flex-col w-96">
|
||||
<x-inputs.input id="server.name" label="Name" required />
|
||||
<x-inputs.input id="server.description" label="Description" />
|
||||
<x-inputs.input disabled type="checkbox" id="server.settings.is_part_of_swarm"
|
||||
label="Is it part of a Swarm cluster?" />
|
||||
</div>
|
||||
<div class="flex flex-col w-96">
|
||||
@if ($server->id === 0)
|
||||
@ -35,19 +20,34 @@
|
||||
@endif
|
||||
</div>
|
||||
</div>
|
||||
<div class="flex gap-2">
|
||||
<x-inputs.button isBold wire:click.prevent='validateServer'>Validate Server</x-inputs.button>
|
||||
<x-inputs.button isBold wire:click.prevent='installDocker'>Install Docker</x-inputs.button>
|
||||
|
||||
<div class="flex items-center gap-2">
|
||||
<x-inputs.button isBold type="submit">Save</x-inputs.button>
|
||||
|
||||
<x-inputs.button isBold wire:click.prevent='validateServer'>
|
||||
@if ($server->settings->is_validated)
|
||||
Check Connection
|
||||
@else
|
||||
Validate Server
|
||||
@endif
|
||||
</x-inputs.button>
|
||||
|
||||
{{-- <x-inputs.button isBold wire:click.prevent='installDocker'>Install Docker</x-inputs.button> --}}
|
||||
<x-inputs.button isWarning x-on:click.prevent="deleteServer = true">
|
||||
Delete
|
||||
</x-inputs.button>
|
||||
</div>
|
||||
<div class="pt-3">
|
||||
@isset($uptime)
|
||||
<p>Connection: OK</p>
|
||||
<p>Uptime: {{ $uptime }}</p>
|
||||
@endisset
|
||||
@isset($dockerVersion)
|
||||
<p>Docker Engine {{ $dockerVersion }}</p>
|
||||
@endisset
|
||||
@isset($dockerComposeVersion)
|
||||
<p>{{ $dockerComposeVersion }}</p>
|
||||
@endisset
|
||||
</div>
|
||||
</form>
|
||||
|
||||
@isset($uptime)
|
||||
<p>Uptime: {{ $uptime }}</p>
|
||||
@endisset
|
||||
@isset($dockerVersion)
|
||||
<p>Docker Engine: {{ $dockerVersion }}</p>
|
||||
@endisset
|
||||
@isset($dockerComposeVersion)
|
||||
<p>Docker Compose: {{ $dockerComposeVersion }}</p>
|
||||
@endisset
|
||||
</div>
|
||||
|
@ -7,7 +7,7 @@
|
||||
<x-inputs.input id="user" label="User" />
|
||||
<x-inputs.input type="number" id="port" label="Port" />
|
||||
<label>Private Key</label>
|
||||
<select wire:model.defer="private_key_id">
|
||||
<x-inputs.select wire:model.defer="private_key_id">
|
||||
<option disabled>Select a private key</option>
|
||||
@foreach ($private_keys as $key)
|
||||
@if ($loop->first)
|
||||
@ -16,7 +16,9 @@
|
||||
<option value="{{ $key->id }}">{{ $key->name }}</option>
|
||||
@endif
|
||||
@endforeach
|
||||
</select>
|
||||
</x-inputs.select>
|
||||
<x-inputs.input instantSave noDirty type="checkbox" id="is_part_of_swarm"
|
||||
label="Is it part of a Swarm cluster?" />
|
||||
<x-inputs.button isBold type="submit">
|
||||
Save
|
||||
</x-inputs.button>
|
||||
|
@ -1,9 +1,8 @@
|
||||
<div x-data="{ deleteSource: false }">
|
||||
<x-naked-modal show="deleteSource" message='Are you sure you would like to delete this source?' />
|
||||
<h3>Change Github App</h3>
|
||||
<form wire:submit.prevent='submit'>
|
||||
<x-inputs.input id="github_app.name" label="App Name" required />
|
||||
<x-inputs.input noDirty type="checkbox" label="System Wide?" instantSave id="is_system_wide" />
|
||||
|
||||
@if ($github_app->app_id)
|
||||
<x-inputs.input id="github_app.organization" label="Organization" disabled
|
||||
placeholder="Personal user if empty" />
|
||||
@ -14,19 +13,24 @@
|
||||
<x-inputs.input id="github_app.html_url" label="HTML Url" disabled />
|
||||
<x-inputs.input id="github_app.custom_user" label="User" required />
|
||||
<x-inputs.input type="number" id="github_app.custom_port" label="Port" required />
|
||||
|
||||
@if ($github_app->app_id)
|
||||
<x-inputs.input type="number" id="github_app.app_id" label="App Id" disabled />
|
||||
<x-inputs.input type="number" id="github_app.installation_id" label="Installation Id" disabled />
|
||||
<x-inputs.input id="github_app.client_id" label="Client Id" type="password" disabled />
|
||||
<x-inputs.input id="github_app.client_secret" label="Client Secret" type="password" disabled />
|
||||
<x-inputs.input id="github_app.webhook_secret" label="Webhook Secret" type="password" disabled />
|
||||
<x-inputs.button type="submit">Save</x-inputs.button>
|
||||
<x-inputs.button isWarning x-on:click.prevent="deleteSource = true">
|
||||
Delete
|
||||
</x-inputs.button>
|
||||
@else
|
||||
<x-inputs.input noDirty type="checkbox" label="System Wide?" instantSave id="is_system_wide" />
|
||||
<div class="py-2">
|
||||
<x-inputs.button type="submit">Save</x-inputs.button>
|
||||
<x-inputs.button isBold type="submit">Save</x-inputs.button>
|
||||
<x-inputs.button isWarning x-on:click.prevent="deleteSource = true">
|
||||
Delete
|
||||
</x-inputs.button>
|
||||
</div>
|
||||
@else
|
||||
<x-inputs.input noDirty type="checkbox" label="System Wide?" instantSave id="is_system_wide" />
|
||||
<div class="py-2">
|
||||
<x-inputs.button isBold type="submit">Save</x-inputs.button>
|
||||
<x-inputs.button isWarning x-on:click.prevent="deleteSource = true">
|
||||
Delete
|
||||
</x-inputs.button>
|
||||
|
@ -1,30 +1,67 @@
|
||||
<x-layout>
|
||||
<livewire:server.form :server_id="$server->id" />
|
||||
<div class="flex items-center gap-2">
|
||||
<h2>Private Key</h2>
|
||||
<a href="{{ route('server.private-key', ['server_uuid' => $server->uuid]) }}">
|
||||
<x-inputs.button isBold>Change</x-inputs.button>
|
||||
</a>
|
||||
</div>
|
||||
<p>{{ $server->privateKey->name }}</p>
|
||||
<div class="flex items-center gap-2">
|
||||
<h2>Destinations</h2>
|
||||
<a href="{{ route('destination.new', ['server_id' => $server->id]) }}">
|
||||
<x-inputs.button isBold>New</x-inputs.button>
|
||||
</a>
|
||||
</div>
|
||||
@if ($server->standaloneDockers->count() > 0)
|
||||
@foreach ($server->standaloneDockers as $docker)
|
||||
<p>Network: {{ data_get($docker, 'network') }}</p>
|
||||
@endforeach
|
||||
@else
|
||||
<p>No destinations found</p>
|
||||
@endif
|
||||
<div class="flex items-center gap-2">
|
||||
<h2>Proxy</h2>
|
||||
<div class="text-3xl font-bold">Server</div>
|
||||
<div class="flex flex-col pb-4">
|
||||
@if ($server->settings->is_validated)
|
||||
<div>{{ $server->extra_attributes->proxy_status }}</div>
|
||||
<div class="text-green-400">Validated</div>
|
||||
@else
|
||||
<div class="text-red-400">Not validated</div>
|
||||
@endif
|
||||
</div>
|
||||
<livewire:server.proxy :server="$server" />
|
||||
<div x-data="{ activeTab: window.location.hash ? window.location.hash.substring(1) : 'general' }">
|
||||
<div class="flex gap-4">
|
||||
<a :class="activeTab === 'general' && 'text-purple-500'"
|
||||
@click.prevent="activeTab = 'general'; window.location.hash = 'general'" href="#">General</a>
|
||||
<a :class="activeTab === 'private-key' && 'text-purple-500'"
|
||||
@click.prevent="activeTab = 'private-key'; window.location.hash = 'private-key'" href="#">Private
|
||||
Key</a>
|
||||
<a :class="activeTab === 'destinations' && 'text-purple-500'"
|
||||
@click.prevent="activeTab = 'destinations'; window.location.hash = 'destinations'"
|
||||
href="#">Destinations
|
||||
</a>
|
||||
<a :class="activeTab === 'proxy' && 'text-purple-500'"
|
||||
@click.prevent="activeTab = 'proxy'; window.location.hash = 'proxy'" href="#">Proxy
|
||||
</a>
|
||||
</div>
|
||||
<div x-cloak x-show="activeTab === 'general'">
|
||||
<h3>General Configurations</h3>
|
||||
<livewire:server.form :server_id="$server->id" />
|
||||
</div>
|
||||
<div x-cloak x-show="activeTab === 'private-key'">
|
||||
<div class="flex items-center gap-2">
|
||||
<h3>Private Keys</h3>
|
||||
<a href="{{ route('server.private-key', ['server_uuid' => $server->uuid]) }}">
|
||||
<x-inputs.button>Change</x-inputs.button>
|
||||
</a>
|
||||
</div>
|
||||
<p>{{ $server->privateKey->name }}</p>
|
||||
</div>
|
||||
<div x-cloak x-show="activeTab === 'destinations'">
|
||||
<div class="flex items-center gap-2">
|
||||
<h3>Destinations</h3>
|
||||
<a href="{{ route('destination.new', ['server_id' => $server->id]) }}">
|
||||
<x-inputs.button isBold>New</x-inputs.button>
|
||||
</a>
|
||||
</div>
|
||||
@if ($server->standaloneDockers->count() > 0)
|
||||
@foreach ($server->standaloneDockers as $docker)
|
||||
<p>Network: {{ data_get($docker, 'network') }}</p>
|
||||
@endforeach
|
||||
@else
|
||||
<p>No destinations found</p>
|
||||
@endif
|
||||
</div>
|
||||
<div x-cloak x-show="activeTab === 'proxy'">
|
||||
<div class="flex items-center gap-2">
|
||||
<h3>Proxy</h3>
|
||||
@if ($server->settings->is_validated)
|
||||
<div>{{ $server->extra_attributes->proxy_status }}</div>
|
||||
@endif
|
||||
</div>
|
||||
<livewire:server.proxy :server="$server" />
|
||||
</div>
|
||||
|
||||
</div>
|
||||
|
||||
|
||||
|
||||
</x-layout>
|
||||
|
@ -57,11 +57,11 @@ function createGithubApp() {
|
||||
</script>
|
||||
@elseif($github_app->app_id && !$github_app->installation_id)
|
||||
<a href="{{ $installation_url }}">
|
||||
<x-inputs.button>Install Repositories</x-inputs.button>
|
||||
<x-inputs.button isBold>Install Repositories</x-inputs.button>
|
||||
</a>
|
||||
@elseif($github_app->app_id && $github_app->installation_id)
|
||||
<a href="{{ $installation_url }}">
|
||||
<x-inputs.button>Update Repositories</x-inputs.button>
|
||||
<x-inputs.button isBold>Update Repositories</x-inputs.button>
|
||||
</a>
|
||||
@endif
|
||||
</x-layout>
|
||||
|
Loading…
Reference in New Issue
Block a user