mirror of
https://github.com/vitodeploy/vito.git
synced 2025-04-15 07:51:37 +00:00
init
This commit is contained in:
commit
5c72f12490
18
.editorconfig
Normal file
18
.editorconfig
Normal file
@ -0,0 +1,18 @@
|
||||
root = true
|
||||
|
||||
[*]
|
||||
charset = utf-8
|
||||
end_of_line = lf
|
||||
indent_size = 4
|
||||
indent_style = space
|
||||
insert_final_newline = true
|
||||
trim_trailing_whitespace = true
|
||||
|
||||
[*.md]
|
||||
trim_trailing_whitespace = false
|
||||
|
||||
[*.{yml,yaml}]
|
||||
indent_size = 2
|
||||
|
||||
[docker-compose.yml]
|
||||
indent_size = 4
|
75
.env.example
Executable file
75
.env.example
Executable file
@ -0,0 +1,75 @@
|
||||
APP_NAME=Vito
|
||||
APP_ENV=local
|
||||
APP_KEY=
|
||||
APP_DEBUG=true
|
||||
APP_URL=http://localhost:2080
|
||||
|
||||
LOG_CHANNEL=stack
|
||||
LOG_LEVEL=debug
|
||||
|
||||
DB_CONNECTION=mysql
|
||||
DB_HOST=127.0.0.1
|
||||
DB_PORT=3306
|
||||
DB_DATABASE=vito
|
||||
DB_USERNAME=root
|
||||
DB_PASSWORD=
|
||||
|
||||
BROADCAST_DRIVER=log
|
||||
CACHE_DRIVER=file
|
||||
FILESYSTEM_DRIVER=local
|
||||
QUEUE_CONNECTION=sync
|
||||
SESSION_DRIVER=database
|
||||
SESSION_LIFETIME=120
|
||||
|
||||
MEMCACHED_HOST=127.0.0.1
|
||||
|
||||
REDIS_HOST=127.0.0.1
|
||||
REDIS_PASSWORD=null
|
||||
REDIS_PORT=6379
|
||||
|
||||
MAIL_MAILER=smtp
|
||||
MAIL_HOST=mailhog
|
||||
MAIL_PORT=1025
|
||||
MAIL_USERNAME=null
|
||||
MAIL_PASSWORD=null
|
||||
MAIL_ENCRYPTION=null
|
||||
MAIL_FROM_ADDRESS=null
|
||||
MAIL_FROM_NAME="${APP_NAME}"
|
||||
|
||||
AWS_ACCESS_KEY_ID=
|
||||
AWS_SECRET_ACCESS_KEY=
|
||||
AWS_DEFAULT_REGION=us-east-1
|
||||
AWS_BUCKET=
|
||||
AWS_USE_PATH_STYLE_ENDPOINT=false
|
||||
|
||||
PUSHER_APP_ID=
|
||||
PUSHER_APP_KEY=
|
||||
PUSHER_APP_SECRET=
|
||||
PUSHER_APP_CLUSTER=mt1
|
||||
|
||||
MIX_PUSHER_APP_KEY="${PUSHER_APP_KEY}"
|
||||
MIX_PUSHER_APP_CLUSTER="${PUSHER_APP_CLUSTER}"
|
||||
|
||||
FORWARD_REDIS_PORT=2060
|
||||
FORWARD_DB_PORT=2070
|
||||
APP_PORT=2080
|
||||
HMR_PORT=2090
|
||||
|
||||
SENTRY_LARAVEL_DSN=
|
||||
|
||||
APP_SERVICE=vito
|
||||
|
||||
GITHUB_CLIENT_ID=
|
||||
GITHUB_CLIENT_SECRET=
|
||||
|
||||
ABLY_KEY=
|
||||
ABLY_PUBLIC_KEY=
|
||||
|
||||
STRIPE_KEY=pk_test_NndNPdqsaU772F7rGf9VwMBZ00QTxVOAZI
|
||||
STRIPE_SECRET=sk_test_nXrcZWPhxtzVLDWo3qzk5O2e00ygZPvrAJ
|
||||
STRIPE_STANDARD_MONTHLY=price_1KJelHLZWr04YoNXo85HB9L6
|
||||
STRIPE_STANDARD_ANNUALLY=price_1KJelHLZWr04YoNX5JzxilBB
|
||||
STRIPE_BUSINESS_MONTHLY=price_1KJelHLZWr04YoNX6rdAxIEA
|
||||
STRIPE_BUSINESS_ANNUALLY=price_1KJelHLZWr04YoNXAoBOSLs9
|
||||
#STRIPE_UNLIMITED_MONTHLY=price_1KJelHLZWr04YoNXDRvMP511
|
||||
#STRIPE_UNLIMITED_ANNUALLY=price_1KJelHLZWr04YoNXG4Ad4Bjp
|
41
.env.testing
Executable file
41
.env.testing
Executable file
@ -0,0 +1,41 @@
|
||||
APP_NAME=Vito
|
||||
APP_ENV=local
|
||||
APP_KEY=base64:d9kZW60V4lFEw2SPn6UiJ0cfi04v80EWP0GZ6kzoxNg=
|
||||
APP_DEBUG=true
|
||||
APP_URL=http://localhost:2080
|
||||
|
||||
LOG_CHANNEL=stack
|
||||
LOG_LEVEL=debug
|
||||
|
||||
DB_CONNECTION=mysql
|
||||
DB_HOST=mysql
|
||||
DB_PORT=3306
|
||||
DB_DATABASE=testing
|
||||
DB_USERNAME=root
|
||||
DB_PASSWORD=password
|
||||
|
||||
BROADCAST_DRIVER=pusher
|
||||
CACHE_DRIVER=array
|
||||
FILESYSTEM_DRIVER=local
|
||||
QUEUE_CONNECTION=database
|
||||
SESSION_DRIVER=array
|
||||
SESSION_LIFETIME=120
|
||||
|
||||
MAIL_MAILER=array
|
||||
|
||||
PUSHER_APP_ID=app-id
|
||||
PUSHER_APP_KEY=app-key
|
||||
PUSHER_APP_SECRET=app-secret
|
||||
PUSHER_HOST=soketi
|
||||
PUSHER_PORT=6001
|
||||
PUSHER_SCHEME=http
|
||||
PUSHER_APP_CLUSTER=mt1
|
||||
|
||||
VITE_PUSHER_APP_KEY="${PUSHER_APP_KEY}"
|
||||
VITE_PUSHER_HOST="${PUSHER_HOST}"
|
||||
VITE_PUSHER_PORT="${PUSHER_PORT}"
|
||||
VITE_PUSHER_SCHEME="${PUSHER_SCHEME}"
|
||||
VITE_PUSHER_APP_CLUSTER="${PUSHER_APP_CLUSTER}"
|
||||
|
||||
SSH_PUBLIC_KEY_NAME=ssh-public.key
|
||||
SSH_PRIVATE_KEY_NAME=ssh-private.pem
|
11
.gitattributes
vendored
Normal file
11
.gitattributes
vendored
Normal file
@ -0,0 +1,11 @@
|
||||
* text=auto eol=lf
|
||||
|
||||
*.blade.php diff=html
|
||||
*.css diff=css
|
||||
*.html diff=html
|
||||
*.md diff=markdown
|
||||
*.php diff=php
|
||||
|
||||
/.github export-ignore
|
||||
CHANGELOG.md export-ignore
|
||||
.styleci.yml export-ignore
|
20
.gitignore
vendored
Normal file
20
.gitignore
vendored
Normal file
@ -0,0 +1,20 @@
|
||||
/.phpunit.cache
|
||||
/node_modules
|
||||
/public/build
|
||||
/public/hot
|
||||
/public/storage
|
||||
/storage/*.key
|
||||
/storage/*.pem
|
||||
/vendor
|
||||
.env
|
||||
.env.backup
|
||||
.env.production
|
||||
.phpunit.result.cache
|
||||
Homestead.json
|
||||
Homestead.yaml
|
||||
auth.json
|
||||
npm-debug.log
|
||||
yarn-error.log
|
||||
/.fleet
|
||||
/.idea
|
||||
/.vscode
|
85
app/Actions/Backup/CreateBackup.php
Normal file
85
app/Actions/Backup/CreateBackup.php
Normal file
@ -0,0 +1,85 @@
|
||||
<?php
|
||||
|
||||
namespace App\Actions\Backup;
|
||||
|
||||
use App\Enums\DatabaseStatus;
|
||||
use App\Models\Backup;
|
||||
use App\Models\Database;
|
||||
use App\Models\Server;
|
||||
use App\Models\User;
|
||||
use Illuminate\Auth\Access\AuthorizationException;
|
||||
use Illuminate\Support\Facades\Gate;
|
||||
use Illuminate\Support\Facades\Validator;
|
||||
use Illuminate\Validation\Rule;
|
||||
use Illuminate\Validation\ValidationException;
|
||||
|
||||
class CreateBackup
|
||||
{
|
||||
/**
|
||||
* @throws AuthorizationException
|
||||
* @throws ValidationException
|
||||
*/
|
||||
public function create($type, Server $server, User $user, array $input): Backup
|
||||
{
|
||||
$this->validate($type, $server, $user, $input);
|
||||
|
||||
if ($type == 'database') {
|
||||
Gate::forUser($user)->authorize('viewAny', [Database::class, $server]);
|
||||
}
|
||||
|
||||
$backup = new Backup([
|
||||
'name' => $input['name'],
|
||||
'type' => $type,
|
||||
'server_id' => $server->id,
|
||||
'database_id' => $input['database'] ?? null,
|
||||
'storage_id' => $input['storage'],
|
||||
'interval' => $input['interval'],
|
||||
'keep_backups' => $input['keep_backups'],
|
||||
'status' => 'running',
|
||||
]);
|
||||
$backup->save();
|
||||
|
||||
$backup->run();
|
||||
|
||||
return $backup;
|
||||
}
|
||||
|
||||
/**
|
||||
* @throws ValidationException
|
||||
*/
|
||||
private function validate($type, Server $server, User $user, array $input): void
|
||||
{
|
||||
$rules = [
|
||||
'name' => 'required',
|
||||
'storage' => [
|
||||
'required',
|
||||
Rule::exists('storage_providers', 'id')
|
||||
->where('user_id', $user->id)
|
||||
->where('connected', 1),
|
||||
],
|
||||
'keep_backups' => [
|
||||
'required',
|
||||
'numeric',
|
||||
'min:1',
|
||||
],
|
||||
'interval' => [
|
||||
'required',
|
||||
Rule::in([
|
||||
'0 * * * *',
|
||||
'0 0 * * *',
|
||||
'0 0 * * 0',
|
||||
'0 0 1 * *',
|
||||
]),
|
||||
],
|
||||
];
|
||||
if ($type === 'database') {
|
||||
$rules['database'] = [
|
||||
'required',
|
||||
Rule::exists('databases', 'id')
|
||||
->where('server_id', $server->id)
|
||||
->where('status', DatabaseStatus::READY),
|
||||
];
|
||||
}
|
||||
Validator::make($input, $rules)->validateWithBag('createBackup');
|
||||
}
|
||||
}
|
48
app/Actions/CronJob/CreateCronJob.php
Executable file
48
app/Actions/CronJob/CreateCronJob.php
Executable file
@ -0,0 +1,48 @@
|
||||
<?php
|
||||
|
||||
namespace App\Actions\CronJob;
|
||||
|
||||
use App\Enums\CronjobStatus;
|
||||
use App\Models\CronJob;
|
||||
use App\Models\Server;
|
||||
use App\ValidationRules\CronRule;
|
||||
use Illuminate\Support\Facades\Validator;
|
||||
use Illuminate\Validation\ValidationException;
|
||||
|
||||
class CreateCronJob
|
||||
{
|
||||
public function create(Server $server, array $input): void
|
||||
{
|
||||
$this->validate($input);
|
||||
|
||||
$cronJob = new CronJob([
|
||||
'server_id' => $server->id,
|
||||
'user' => $input['user'],
|
||||
'command' => $input['command'],
|
||||
'frequency' => $input['frequency'],
|
||||
'status' => CronjobStatus::CREATING,
|
||||
]);
|
||||
$cronJob->save();
|
||||
$cronJob->addToServer();
|
||||
}
|
||||
|
||||
/**
|
||||
* @throws ValidationException
|
||||
*/
|
||||
private function validate(array $input): void
|
||||
{
|
||||
Validator::make($input, [
|
||||
'command' => [
|
||||
'required',
|
||||
],
|
||||
'user' => [
|
||||
'required',
|
||||
'in:root,'.config('core.ssh_user'),
|
||||
],
|
||||
'frequency' => [
|
||||
'required',
|
||||
new CronRule(),
|
||||
],
|
||||
])->validateWithBag('createCronJob');
|
||||
}
|
||||
}
|
58
app/Actions/Database/CreateDatabase.php
Executable file
58
app/Actions/Database/CreateDatabase.php
Executable file
@ -0,0 +1,58 @@
|
||||
<?php
|
||||
|
||||
namespace App\Actions\Database;
|
||||
|
||||
use App\Models\Database;
|
||||
use App\Models\Server;
|
||||
use Illuminate\Support\Facades\Validator;
|
||||
use Illuminate\Validation\Rule;
|
||||
use Illuminate\Validation\ValidationException;
|
||||
|
||||
class CreateDatabase
|
||||
{
|
||||
/**
|
||||
* @throws ValidationException
|
||||
*/
|
||||
public function create(Server $server, array $input): Database
|
||||
{
|
||||
$this->validate($server, $input);
|
||||
|
||||
$database = new Database([
|
||||
'server_id' => $server->id,
|
||||
'name' => $input['name'],
|
||||
]);
|
||||
$database->save();
|
||||
$database->createOnServer();
|
||||
|
||||
return $database;
|
||||
}
|
||||
|
||||
/**
|
||||
* @throws ValidationException
|
||||
*/
|
||||
private function validate(Server $server, array $input): void
|
||||
{
|
||||
$rules = [
|
||||
'name' => [
|
||||
'required',
|
||||
'alpha_dash',
|
||||
Rule::unique('databases', 'name')->where('server_id', $server->id),
|
||||
],
|
||||
];
|
||||
if (isset($input['user']) && $input['user']) {
|
||||
$rules['username'] = [
|
||||
'required',
|
||||
'alpha_dash',
|
||||
Rule::unique('database_users', 'username')->where('server_id', $server->id),
|
||||
];
|
||||
$rules['password'] = [
|
||||
'required',
|
||||
'min:6',
|
||||
];
|
||||
}
|
||||
if (isset($input['remote']) && $input['remote']) {
|
||||
$rules['host'] = 'required';
|
||||
}
|
||||
Validator::make($input, $rules)->validate();
|
||||
}
|
||||
}
|
53
app/Actions/Database/CreateDatabaseUser.php
Executable file
53
app/Actions/Database/CreateDatabaseUser.php
Executable file
@ -0,0 +1,53 @@
|
||||
<?php
|
||||
|
||||
namespace App\Actions\Database;
|
||||
|
||||
use App\Models\DatabaseUser;
|
||||
use App\Models\Server;
|
||||
use Illuminate\Support\Facades\Validator;
|
||||
use Illuminate\Validation\Rule;
|
||||
use Illuminate\Validation\ValidationException;
|
||||
|
||||
class CreateDatabaseUser
|
||||
{
|
||||
/**
|
||||
* @throws ValidationException
|
||||
*/
|
||||
public function create(Server $server, array $input): DatabaseUser
|
||||
{
|
||||
$this->validate($server, $input);
|
||||
|
||||
$databaseUser = new DatabaseUser([
|
||||
'server_id' => $server->id,
|
||||
'username' => $input['username'],
|
||||
'password' => $input['password'],
|
||||
'host' => isset($input['remote']) && $input['remote'] ? $input['host'] : 'localhost',
|
||||
]);
|
||||
$databaseUser->save();
|
||||
$databaseUser->createOnServer();
|
||||
|
||||
return $databaseUser;
|
||||
}
|
||||
|
||||
/**
|
||||
* @throws ValidationException
|
||||
*/
|
||||
private function validate(Server $server, array $input): void
|
||||
{
|
||||
$rules = [
|
||||
'username' => [
|
||||
'required',
|
||||
'alpha_dash',
|
||||
Rule::unique('database_users', 'username')->where('server_id', $server->id),
|
||||
],
|
||||
'password' => [
|
||||
'required',
|
||||
'min:6',
|
||||
],
|
||||
];
|
||||
if (isset($input['remote']) && $input['remote']) {
|
||||
$rules['host'] = 'required';
|
||||
}
|
||||
Validator::make($input, $rules)->validate();
|
||||
}
|
||||
}
|
55
app/Actions/Database/InstallPHPMyAdmin.php
Normal file
55
app/Actions/Database/InstallPHPMyAdmin.php
Normal file
@ -0,0 +1,55 @@
|
||||
<?php
|
||||
|
||||
namespace App\Actions\Database;
|
||||
|
||||
use App\Models\Server;
|
||||
use App\Models\Service;
|
||||
use Illuminate\Support\Facades\Validator;
|
||||
use Illuminate\Validation\ValidationException;
|
||||
|
||||
class InstallPHPMyAdmin
|
||||
{
|
||||
/**
|
||||
* @throws ValidationException
|
||||
*/
|
||||
public function install(Server $server, array $input): Service
|
||||
{
|
||||
$this->validate($input);
|
||||
|
||||
$phpMyAdmin = $server->defaultService('phpmyadmin');
|
||||
if ($phpMyAdmin) {
|
||||
if ($phpMyAdmin->status === 'ready') {
|
||||
throw ValidationException::withMessages([
|
||||
'install' => __('Already installed'),
|
||||
])->errorBag('installPHPMyAdmin');
|
||||
}
|
||||
$phpMyAdmin->delete();
|
||||
}
|
||||
$phpMyAdmin = new Service([
|
||||
'server_id' => $server->id,
|
||||
'type' => 'phpmyadmin',
|
||||
'type_data' => [
|
||||
'allowed_ip' => $input['allowed_ip'],
|
||||
'php' => $server->defaultService('php')->version,
|
||||
],
|
||||
'name' => 'phpmyadmin',
|
||||
'version' => '5.1.2',
|
||||
'status' => 'installing',
|
||||
'is_default' => 1,
|
||||
]);
|
||||
$phpMyAdmin->save();
|
||||
$phpMyAdmin->install();
|
||||
|
||||
return $phpMyAdmin;
|
||||
}
|
||||
|
||||
/**
|
||||
* @throws ValidationException
|
||||
*/
|
||||
private function validate(array $input): void
|
||||
{
|
||||
Validator::make($input, [
|
||||
'allowed_ip' => 'required',
|
||||
])->validateWithBag('installPHPMyAdmin');
|
||||
}
|
||||
}
|
30
app/Actions/Database/LinkUser.php
Executable file
30
app/Actions/Database/LinkUser.php
Executable file
@ -0,0 +1,30 @@
|
||||
<?php
|
||||
|
||||
namespace App\Actions\Database;
|
||||
|
||||
use App\Models\Database;
|
||||
use App\Models\DatabaseUser;
|
||||
use Illuminate\Validation\ValidationException;
|
||||
|
||||
class LinkUser
|
||||
{
|
||||
/**
|
||||
* @throws ValidationException
|
||||
*/
|
||||
public function link(DatabaseUser $databaseUser, array $databases): void
|
||||
{
|
||||
$dbs = Database::query()
|
||||
->where('server_id', $databaseUser->server_id)
|
||||
->whereIn('name', $databases)
|
||||
->count();
|
||||
if (count($databases) !== $dbs) {
|
||||
throw ValidationException::withMessages(['databases' => __('Databases not found!')])
|
||||
->errorBag('linkUser');
|
||||
}
|
||||
|
||||
$databaseUser->databases = $databases;
|
||||
$databaseUser->unlinkUser();
|
||||
$databaseUser->linkUser();
|
||||
$databaseUser->save();
|
||||
}
|
||||
}
|
64
app/Actions/FirewallRule/CreateRule.php
Executable file
64
app/Actions/FirewallRule/CreateRule.php
Executable file
@ -0,0 +1,64 @@
|
||||
<?php
|
||||
|
||||
namespace App\Actions\FirewallRule;
|
||||
|
||||
use App\Enums\FirewallRuleStatus;
|
||||
use App\Models\FirewallRule;
|
||||
use App\Models\Server;
|
||||
use Illuminate\Support\Facades\Validator;
|
||||
use Illuminate\Validation\Rule;
|
||||
use Illuminate\Validation\ValidationException;
|
||||
|
||||
class CreateRule
|
||||
{
|
||||
public function create(Server $server, array $input): FirewallRule
|
||||
{
|
||||
$this->validate($server, $input);
|
||||
|
||||
$rule = new FirewallRule([
|
||||
'server_id' => $server->id,
|
||||
'type' => $input['type'],
|
||||
'protocol' => $input['protocol'],
|
||||
'port' => $input['port'],
|
||||
'source' => $input['source'],
|
||||
'mask' => $input['mask'],
|
||||
'status' => FirewallRuleStatus::CREATING,
|
||||
]);
|
||||
$rule->save();
|
||||
$rule->addToServer();
|
||||
|
||||
return $rule;
|
||||
}
|
||||
|
||||
/**
|
||||
* @throws ValidationException
|
||||
*/
|
||||
private function validate(Server $server, array $input): void
|
||||
{
|
||||
Validator::make($input, [
|
||||
'type' => [
|
||||
'required',
|
||||
'in:allow,deny',
|
||||
],
|
||||
'protocol' => [
|
||||
'required',
|
||||
'in:'.implode(',', array_keys(config('core.firewall_protocols_port'))),
|
||||
],
|
||||
'port' => [
|
||||
'required',
|
||||
'numeric',
|
||||
'min:1',
|
||||
'max:65535',
|
||||
Rule::unique('firewall_rules', 'port')->where('server_id', $server->id),
|
||||
],
|
||||
'source' => [
|
||||
'required',
|
||||
'ip',
|
||||
],
|
||||
'mask' => [
|
||||
'required',
|
||||
'numeric',
|
||||
],
|
||||
])->validateWithBag('createRule');
|
||||
}
|
||||
}
|
55
app/Actions/NotificationChannels/AddChannel.php
Normal file
55
app/Actions/NotificationChannels/AddChannel.php
Normal file
@ -0,0 +1,55 @@
|
||||
<?php
|
||||
|
||||
namespace App\Actions\NotificationChannels;
|
||||
|
||||
use App\Models\NotificationChannel;
|
||||
use App\Models\User;
|
||||
use Illuminate\Support\Facades\Validator;
|
||||
use Illuminate\Validation\ValidationException;
|
||||
|
||||
class AddChannel
|
||||
{
|
||||
/**
|
||||
* @throws ValidationException
|
||||
*/
|
||||
public function add(User $user, array $input): void
|
||||
{
|
||||
$this->validate($input);
|
||||
$channel = new NotificationChannel([
|
||||
'user_id' => $user->id,
|
||||
'provider' => $input['provider'],
|
||||
'label' => $input['label'],
|
||||
]);
|
||||
$this->validateType($channel, $input);
|
||||
$channel->data = $channel->provider()->data($input);
|
||||
$channel->save();
|
||||
|
||||
if (! $channel->provider()->connect()) {
|
||||
$channel->delete();
|
||||
|
||||
throw ValidationException::withMessages([
|
||||
'provider' => __('Could not connect'),
|
||||
]);
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* @throws ValidationException
|
||||
*/
|
||||
protected function validate(array $input): void
|
||||
{
|
||||
Validator::make($input, [
|
||||
'provider' => 'required|in:'.implode(',', config('core.notification_channels_providers')),
|
||||
'label' => 'required',
|
||||
])->validate();
|
||||
}
|
||||
|
||||
/**
|
||||
* @throws ValidationException
|
||||
*/
|
||||
protected function validateType(NotificationChannel $channel, array $input): void
|
||||
{
|
||||
Validator::make($input, $channel->provider()->validationRules())
|
||||
->validate();
|
||||
}
|
||||
}
|
52
app/Actions/PHP/InstallNewPHP.php
Executable file
52
app/Actions/PHP/InstallNewPHP.php
Executable file
@ -0,0 +1,52 @@
|
||||
<?php
|
||||
|
||||
namespace App\Actions\PHP;
|
||||
|
||||
use App\Enums\ServiceStatus;
|
||||
use App\Models\Server;
|
||||
use App\Models\Service;
|
||||
use Illuminate\Support\Facades\Validator;
|
||||
use Illuminate\Validation\Rule;
|
||||
use Illuminate\Validation\ValidationException;
|
||||
|
||||
class InstallNewPHP
|
||||
{
|
||||
public function install(Server $server, array $input): void
|
||||
{
|
||||
$this->validate($server, $input);
|
||||
|
||||
$php = new Service([
|
||||
'server_id' => $server->id,
|
||||
'type' => 'php',
|
||||
'type_data' => [
|
||||
'extensions' => [],
|
||||
'settings' => config('core.php_settings'),
|
||||
],
|
||||
'name' => 'php',
|
||||
'version' => $input['version'],
|
||||
'status' => ServiceStatus::INSTALLING,
|
||||
'is_default' => false,
|
||||
]);
|
||||
$php->save();
|
||||
$php->install();
|
||||
}
|
||||
|
||||
/**
|
||||
* @throws ValidationException
|
||||
*/
|
||||
private function validate(Server $server, array $input): void
|
||||
{
|
||||
Validator::make($input, [
|
||||
'version' => [
|
||||
'required',
|
||||
Rule::in(config('core.php_versions')),
|
||||
],
|
||||
])->validateWithBag('installPHP');
|
||||
|
||||
if (in_array($input['version'], $server->installedPHPVersions())) {
|
||||
throw ValidationException::withMessages(
|
||||
['version' => __('This version is already installed')]
|
||||
)->errorBag('installPHP');
|
||||
}
|
||||
}
|
||||
}
|
46
app/Actions/PHP/InstallPHPExtension.php
Executable file
46
app/Actions/PHP/InstallPHPExtension.php
Executable file
@ -0,0 +1,46 @@
|
||||
<?php
|
||||
|
||||
namespace App\Actions\PHP;
|
||||
|
||||
use App\Models\Service;
|
||||
use Illuminate\Support\Facades\Validator;
|
||||
use Illuminate\Validation\ValidationException;
|
||||
|
||||
class InstallPHPExtension
|
||||
{
|
||||
/**
|
||||
* @throws ValidationException
|
||||
*/
|
||||
public function handle(Service $service, array $input): Service
|
||||
{
|
||||
$typeData = $service->type_data;
|
||||
$typeData['extensions'] = $typeData['extensions'] ?? [];
|
||||
$service->type_data = $typeData;
|
||||
$service->save();
|
||||
|
||||
$this->validate($service, $input);
|
||||
|
||||
$service->handler()->installExtension($input['name']);
|
||||
|
||||
return $service;
|
||||
}
|
||||
|
||||
/**
|
||||
* @throws ValidationException
|
||||
*/
|
||||
private function validate(Service $service, array $input): void
|
||||
{
|
||||
Validator::make($input, [
|
||||
'name' => [
|
||||
'required',
|
||||
'in:'.implode(',', config('core.php_extensions')),
|
||||
],
|
||||
])->validateWithBag('installPHPExtension');
|
||||
|
||||
if (in_array($input['name'], $service->type_data['extensions'])) {
|
||||
throw ValidationException::withMessages(
|
||||
['name' => __('This extension already installed')]
|
||||
)->errorBag('installPHPExtension');
|
||||
}
|
||||
}
|
||||
}
|
39
app/Actions/PHP/UninstallPHP.php
Executable file
39
app/Actions/PHP/UninstallPHP.php
Executable file
@ -0,0 +1,39 @@
|
||||
<?php
|
||||
|
||||
namespace App\Actions\PHP;
|
||||
|
||||
use App\Models\Server;
|
||||
use Illuminate\Validation\ValidationException;
|
||||
|
||||
class UninstallPHP
|
||||
{
|
||||
public function uninstall(Server $server, string $version): void
|
||||
{
|
||||
$this->validate($server, $version);
|
||||
|
||||
$php = $server->services()->where('type', 'php')->where('version', $version)->first();
|
||||
|
||||
$php->uninstall();
|
||||
}
|
||||
|
||||
/**
|
||||
* @throws ValidationException
|
||||
*/
|
||||
private function validate(Server $server, string $version): void
|
||||
{
|
||||
$php = $server->services()->where('type', 'php')->where('version', $version)->first();
|
||||
|
||||
if (! $php) {
|
||||
throw ValidationException::withMessages(
|
||||
['version' => __('This version has not been installed yet!')]
|
||||
);
|
||||
}
|
||||
|
||||
$hasSite = $server->sites()->where('php_version', $version)->first();
|
||||
if ($hasSite) {
|
||||
throw ValidationException::withMessages(
|
||||
['version' => __('Cannot uninstall this version because some sites are using it!')]
|
||||
);
|
||||
}
|
||||
}
|
||||
}
|
40
app/Actions/PHP/UpdatePHPIni.php
Executable file
40
app/Actions/PHP/UpdatePHPIni.php
Executable file
@ -0,0 +1,40 @@
|
||||
<?php
|
||||
|
||||
namespace App\Actions\PHP;
|
||||
|
||||
use App\Models\Service;
|
||||
use Illuminate\Support\Facades\Storage;
|
||||
use Illuminate\Support\Str;
|
||||
use Illuminate\Validation\ValidationException;
|
||||
use Throwable;
|
||||
|
||||
class UpdatePHPIni
|
||||
{
|
||||
/**
|
||||
* @throws ValidationException
|
||||
*/
|
||||
public function update(Service $service, string $ini): void
|
||||
{
|
||||
$tmpName = Str::random(10).strtotime('now');
|
||||
try {
|
||||
Storage::disk('local')->put($tmpName, $ini);
|
||||
$service->server->ssh('root')->upload(
|
||||
Storage::disk('local')->path($tmpName),
|
||||
"/etc/php/$service->version/cli/php.ini"
|
||||
);
|
||||
$this->deleteTempFile($tmpName);
|
||||
} catch (Throwable) {
|
||||
$this->deleteTempFile($tmpName);
|
||||
throw ValidationException::withMessages([
|
||||
'ini' => __("Couldn't update php.ini file!"),
|
||||
]);
|
||||
}
|
||||
}
|
||||
|
||||
private function deleteTempFile(string $name): void
|
||||
{
|
||||
if (Storage::disk('local')->exists($name)) {
|
||||
Storage::disk('local')->delete($name);
|
||||
}
|
||||
}
|
||||
}
|
65
app/Actions/Queue/CreateQueue.php
Normal file
65
app/Actions/Queue/CreateQueue.php
Normal file
@ -0,0 +1,65 @@
|
||||
<?php
|
||||
|
||||
namespace App\Actions\Queue;
|
||||
|
||||
use App\Enums\QueueStatus;
|
||||
use App\Models\Queue;
|
||||
use App\Models\Server;
|
||||
use App\Models\Site;
|
||||
use Illuminate\Support\Facades\Validator;
|
||||
use Illuminate\Validation\ValidationException;
|
||||
|
||||
class CreateQueue
|
||||
{
|
||||
/**
|
||||
* @throws ValidationException
|
||||
*/
|
||||
public function create(mixed $queueable, array $input): void
|
||||
{
|
||||
$this->validate($input);
|
||||
|
||||
$queue = new Queue([
|
||||
'server_id' => $queueable instanceof Server ? $queueable->id : $queueable->server_id,
|
||||
'site_id' => $queueable instanceof Site ? $queueable->id : null,
|
||||
'command' => $input['command'],
|
||||
'user' => $input['user'],
|
||||
'auto_start' => $input['auto_start'],
|
||||
'auto_restart' => $input['auto_restart'],
|
||||
'numprocs' => $input['numprocs'],
|
||||
'status' => QueueStatus::CREATING,
|
||||
]);
|
||||
$queue->save();
|
||||
$queue->deploy();
|
||||
}
|
||||
|
||||
/**
|
||||
* @throws ValidationException
|
||||
*/
|
||||
protected function validate(array $input): void
|
||||
{
|
||||
$rules = [
|
||||
'command' => [
|
||||
'required',
|
||||
],
|
||||
'user' => [
|
||||
'required',
|
||||
'in:root,'.config('core.ssh_user'),
|
||||
],
|
||||
'auto_start' => [
|
||||
'required',
|
||||
'in:0,1',
|
||||
],
|
||||
'auto_restart' => [
|
||||
'required',
|
||||
'in:0,1',
|
||||
],
|
||||
'numprocs' => [
|
||||
'required',
|
||||
'numeric',
|
||||
'min:1',
|
||||
],
|
||||
];
|
||||
|
||||
Validator::make($input, $rules)->validateWithBag('createQueue');
|
||||
}
|
||||
}
|
47
app/Actions/SSL/CreateSSL.php
Normal file
47
app/Actions/SSL/CreateSSL.php
Normal file
@ -0,0 +1,47 @@
|
||||
<?php
|
||||
|
||||
namespace App\Actions\SSL;
|
||||
|
||||
use App\Enums\SslType;
|
||||
use App\Models\Site;
|
||||
use Illuminate\Support\Facades\Validator;
|
||||
use Illuminate\Validation\Rule;
|
||||
use Illuminate\Validation\ValidationException;
|
||||
|
||||
class CreateSSL
|
||||
{
|
||||
/**
|
||||
* @throws ValidationException
|
||||
*/
|
||||
public function create(Site $site, array $input): void
|
||||
{
|
||||
$this->validate($input);
|
||||
|
||||
if ($input['type'] == SslType::LETSENCRYPT) {
|
||||
$site->createFreeSsl();
|
||||
}
|
||||
|
||||
if ($input['type'] == SslType::CUSTOM) {
|
||||
$site->createCustomSsl($input['certificate'], $input['private']);
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* @throws ValidationException
|
||||
*/
|
||||
protected function validate(array $input): void
|
||||
{
|
||||
$rules = [
|
||||
'type' => [
|
||||
'required',
|
||||
Rule::in(SslType::getValues()),
|
||||
],
|
||||
];
|
||||
if (isset($input['type']) && $input['type'] == SslType::CUSTOM) {
|
||||
$rules['certificate'] = 'required';
|
||||
$rules['private'] = 'required';
|
||||
}
|
||||
|
||||
Validator::make($input, $rules)->validateWithBag('createSSL');
|
||||
}
|
||||
}
|
41
app/Actions/Script/CreateScript.php
Normal file
41
app/Actions/Script/CreateScript.php
Normal file
@ -0,0 +1,41 @@
|
||||
<?php
|
||||
|
||||
namespace App\Actions\Script;
|
||||
|
||||
use App\Models\Script;
|
||||
use App\Models\User;
|
||||
use Illuminate\Support\Facades\Validator;
|
||||
use Illuminate\Validation\ValidationException;
|
||||
|
||||
class CreateScript
|
||||
{
|
||||
/**
|
||||
* @throws ValidationException
|
||||
*/
|
||||
public function handle(User $creator, array $input): Script
|
||||
{
|
||||
$this->validateInputs($input);
|
||||
|
||||
$script = new Script([
|
||||
'user_id' => $creator->id,
|
||||
'name' => $input['name'],
|
||||
'content' => $input['content'],
|
||||
]);
|
||||
$script->save();
|
||||
|
||||
return $script;
|
||||
}
|
||||
|
||||
/**
|
||||
* @throws ValidationException
|
||||
*/
|
||||
private function validateInputs(array $input): void
|
||||
{
|
||||
$rules = [
|
||||
'name' => 'required',
|
||||
'content' => 'required',
|
||||
];
|
||||
|
||||
Validator::make($input, $rules)->validateWithBag('createScript');
|
||||
}
|
||||
}
|
17
app/Actions/Script/GetScripts.php
Executable file
17
app/Actions/Script/GetScripts.php
Executable file
@ -0,0 +1,17 @@
|
||||
<?php
|
||||
|
||||
namespace App\Actions\Script;
|
||||
|
||||
use App\Models\User;
|
||||
use Illuminate\Contracts\Pagination\LengthAwarePaginator;
|
||||
|
||||
class GetScripts
|
||||
{
|
||||
public function handle(User $user): LengthAwarePaginator
|
||||
{
|
||||
return $user->scripts()
|
||||
->orderBy('id', 'desc')
|
||||
->paginate(6)
|
||||
->onEachSide(1);
|
||||
}
|
||||
}
|
37
app/Actions/Script/UpdateScript.php
Normal file
37
app/Actions/Script/UpdateScript.php
Normal file
@ -0,0 +1,37 @@
|
||||
<?php
|
||||
|
||||
namespace App\Actions\Script;
|
||||
|
||||
use App\Models\Script;
|
||||
use Illuminate\Support\Facades\Validator;
|
||||
use Illuminate\Validation\ValidationException;
|
||||
|
||||
class UpdateScript
|
||||
{
|
||||
/**
|
||||
* @throws ValidationException
|
||||
*/
|
||||
public function handle(Script $script, array $input): Script
|
||||
{
|
||||
$this->validateInputs($input);
|
||||
|
||||
$script->name = $input['name'];
|
||||
$script->content = $input['content'];
|
||||
$script->save();
|
||||
|
||||
return $script;
|
||||
}
|
||||
|
||||
/**
|
||||
* @throws ValidationException
|
||||
*/
|
||||
private function validateInputs(array $input): void
|
||||
{
|
||||
$rules = [
|
||||
'name' => 'required',
|
||||
'content' => 'required',
|
||||
];
|
||||
|
||||
Validator::make($input, $rules)->validateWithBag('updateScript');
|
||||
}
|
||||
}
|
183
app/Actions/Server/CreateServer.php
Executable file
183
app/Actions/Server/CreateServer.php
Executable file
@ -0,0 +1,183 @@
|
||||
<?php
|
||||
|
||||
namespace App\Actions\Server;
|
||||
|
||||
use App\Enums\FirewallRuleStatus;
|
||||
use App\Exceptions\ServerProviderError;
|
||||
use App\Jobs\Installation\ContinueInstallation;
|
||||
use App\Models\Server;
|
||||
use App\Models\User;
|
||||
use App\ValidationRules\RestrictedIPAddressesRule;
|
||||
use Exception;
|
||||
use Illuminate\Support\Facades\DB;
|
||||
use Illuminate\Support\Facades\Validator;
|
||||
use Illuminate\Support\Str;
|
||||
use Illuminate\Validation\Rule;
|
||||
use Illuminate\Validation\ValidationException;
|
||||
use Throwable;
|
||||
|
||||
class CreateServer
|
||||
{
|
||||
/**
|
||||
* @throws Throwable
|
||||
*/
|
||||
public function create(User $creator, array $input): Server
|
||||
{
|
||||
$this->validateInputs($input);
|
||||
|
||||
$server = new Server([
|
||||
'user_id' => $creator->id,
|
||||
'name' => $input['name'],
|
||||
'ssh_user' => config('core.server_providers_default_user')[$input['provider']][$input['os']],
|
||||
'ip' => $input['ip'],
|
||||
'port' => $input['port'] ?? 22,
|
||||
'os' => $input['os'],
|
||||
'type' => $input['type'],
|
||||
'provider' => $input['provider'],
|
||||
'authentication' => [
|
||||
'user' => config('core.ssh_user'),
|
||||
'pass' => Str::random(10),
|
||||
'root_pass' => Str::random(10),
|
||||
],
|
||||
'progress' => 0,
|
||||
'progress_step' => 'Initializing',
|
||||
]);
|
||||
|
||||
try {
|
||||
DB::beginTransaction();
|
||||
|
||||
if ($server->provider != 'custom') {
|
||||
$server->provider_id = $input['server_provider'];
|
||||
}
|
||||
|
||||
// validate type
|
||||
$this->validateType($server, $input);
|
||||
$server->type_data = $server->type()->data($input);
|
||||
|
||||
// validate provider
|
||||
$this->validateProvider($server, $input);
|
||||
$server->provider_data = $server->provider()->data($input);
|
||||
|
||||
// save
|
||||
$server->save();
|
||||
|
||||
// create firewall rules
|
||||
$this->createFirewallRules($server);
|
||||
|
||||
// create instance
|
||||
$server->provider()->create();
|
||||
|
||||
// add services
|
||||
$server->type()->createServices($input);
|
||||
|
||||
// install server
|
||||
if ($server->provider == 'custom') {
|
||||
$server->install();
|
||||
} else {
|
||||
$server->progress_step = __('Installation will begin in 3 minutes!');
|
||||
$server->save();
|
||||
dispatch(new ContinueInstallation($server))
|
||||
->delay(now()->addMinutes(3))
|
||||
->onQueue('default');
|
||||
}
|
||||
DB::commit();
|
||||
|
||||
return $server;
|
||||
} catch (Exception $e) {
|
||||
$server->provider()->delete();
|
||||
DB::rollBack();
|
||||
if ($e instanceof ServerProviderError) {
|
||||
throw ValidationException::withMessages([
|
||||
'provider' => __('Provider Error: ').$e->getMessage(),
|
||||
])->errorBag('createServer');
|
||||
}
|
||||
throw $e;
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* @throws ValidationException
|
||||
*/
|
||||
private function validateInputs(array $input): void
|
||||
{
|
||||
$rules = [
|
||||
'provider' => 'required|in:'.implode(',', config('core.server_providers')),
|
||||
'name' => 'required',
|
||||
'os' => 'required|in:'.implode(',', config('core.operating_systems')),
|
||||
'type' => [
|
||||
'required',
|
||||
Rule::in(config('core.server_types')),
|
||||
],
|
||||
];
|
||||
|
||||
Validator::make($input, $rules)->validate();
|
||||
|
||||
if ($input['provider'] != 'custom') {
|
||||
$rules['server_provider'] = 'required|exists:server_providers,id,user_id,'.auth()->user()->id;
|
||||
}
|
||||
|
||||
if ($input['provider'] == 'custom') {
|
||||
$rules['ip'] = [
|
||||
'required',
|
||||
'ip',
|
||||
new RestrictedIPAddressesRule(),
|
||||
];
|
||||
$rules['port'] = [
|
||||
'required',
|
||||
'numeric',
|
||||
'min:1',
|
||||
'max:65535',
|
||||
];
|
||||
}
|
||||
|
||||
Validator::make($input, $rules)->validate();
|
||||
}
|
||||
|
||||
/**
|
||||
* @throws ValidationException
|
||||
*/
|
||||
private function validateType(Server $server, array $input): void
|
||||
{
|
||||
Validator::make($input, $server->type()->createValidationRules($input))
|
||||
->validate();
|
||||
}
|
||||
|
||||
/**
|
||||
* @throws ValidationException
|
||||
*/
|
||||
private function validateProvider(Server $server, array $input): void
|
||||
{
|
||||
Validator::make($input, $server->provider()->createValidationRules($input))
|
||||
->validate();
|
||||
}
|
||||
|
||||
private function createFirewallRules(Server $server): void
|
||||
{
|
||||
$server->firewallRules()->createMany([
|
||||
[
|
||||
'type' => 'allow',
|
||||
'protocol' => 'ssh',
|
||||
'port' => 22,
|
||||
'source' => '0.0.0.0',
|
||||
'mask' => 0,
|
||||
'status' => FirewallRuleStatus::READY,
|
||||
],
|
||||
[
|
||||
'type' => 'allow',
|
||||
'protocol' => 'http',
|
||||
'port' => 80,
|
||||
'source' => '0.0.0.0',
|
||||
'mask' => 0,
|
||||
'status' => FirewallRuleStatus::READY,
|
||||
],
|
||||
[
|
||||
'type' => 'allow',
|
||||
'protocol' => 'https',
|
||||
'port' => 443,
|
||||
'source' => '0.0.0.0',
|
||||
'mask' => 0,
|
||||
'status' => FirewallRuleStatus::READY,
|
||||
],
|
||||
]);
|
||||
}
|
||||
}
|
33
app/Actions/Server/DeleteServer.php
Executable file
33
app/Actions/Server/DeleteServer.php
Executable file
@ -0,0 +1,33 @@
|
||||
<?php
|
||||
|
||||
namespace App\Actions\Server;
|
||||
|
||||
use App\Models\Server;
|
||||
use Illuminate\Support\Facades\DB;
|
||||
use Illuminate\Support\Facades\Validator;
|
||||
use Illuminate\Validation\ValidationException;
|
||||
|
||||
class DeleteServer
|
||||
{
|
||||
/**
|
||||
* @throws ValidationException
|
||||
*/
|
||||
public function delete(Server $server, array $input): void
|
||||
{
|
||||
$this->validateDelete($input);
|
||||
|
||||
DB::transaction(function () use ($server) {
|
||||
$server->cleanDelete();
|
||||
});
|
||||
}
|
||||
|
||||
/**
|
||||
* @throws ValidationException
|
||||
*/
|
||||
protected function validateDelete(array $input): void
|
||||
{
|
||||
Validator::make($input, [
|
||||
'confirm' => 'required|in:delete',
|
||||
])->validateWithBag('deleteServer');
|
||||
}
|
||||
}
|
55
app/Actions/Server/EditServer.php
Executable file
55
app/Actions/Server/EditServer.php
Executable file
@ -0,0 +1,55 @@
|
||||
<?php
|
||||
|
||||
namespace App\Actions\Server;
|
||||
|
||||
use App\Models\Server;
|
||||
use App\ValidationRules\RestrictedIPAddressesRule;
|
||||
use Illuminate\Support\Facades\Validator;
|
||||
use Illuminate\Validation\ValidationException;
|
||||
|
||||
class EditServer
|
||||
{
|
||||
/**
|
||||
* @throws ValidationException
|
||||
*/
|
||||
public function edit(Server $server, array $input): Server
|
||||
{
|
||||
$this->validate($input);
|
||||
|
||||
$checkConnection = false;
|
||||
if (isset($input['name'])) {
|
||||
$server->name = $input['name'];
|
||||
}
|
||||
if (isset($input['ip'])) {
|
||||
if ($server->ip !== $input['ip']) {
|
||||
$checkConnection = true;
|
||||
}
|
||||
$server->ip = $input['ip'];
|
||||
}
|
||||
if (isset($input['port'])) {
|
||||
if ($server->port !== $input['port']) {
|
||||
$checkConnection = true;
|
||||
}
|
||||
$server->port = $input['port'];
|
||||
}
|
||||
$server->save();
|
||||
|
||||
if ($checkConnection) {
|
||||
$server->checkConnection();
|
||||
}
|
||||
|
||||
return $server;
|
||||
}
|
||||
|
||||
/**
|
||||
* @throws ValidationException
|
||||
*/
|
||||
protected function validate(array $input): void
|
||||
{
|
||||
Validator::make($input, [
|
||||
'ip' => [
|
||||
new RestrictedIPAddressesRule(),
|
||||
],
|
||||
])->validateWithBag('editServer');
|
||||
}
|
||||
}
|
14
app/Actions/Server/GetServers.php
Executable file
14
app/Actions/Server/GetServers.php
Executable file
@ -0,0 +1,14 @@
|
||||
<?php
|
||||
|
||||
namespace App\Actions\Server;
|
||||
|
||||
use App\Models\Server;
|
||||
use Illuminate\Database\Eloquent\Collection;
|
||||
|
||||
class GetServers
|
||||
{
|
||||
public function handle(): Collection
|
||||
{
|
||||
return Server::query()->latest()->get();
|
||||
}
|
||||
}
|
77
app/Actions/ServerProvider/CreateServerProvider.php
Normal file
77
app/Actions/ServerProvider/CreateServerProvider.php
Normal file
@ -0,0 +1,77 @@
|
||||
<?php
|
||||
|
||||
namespace App\Actions\ServerProvider;
|
||||
|
||||
use App\Contracts\ServerProvider as ServerProviderContract;
|
||||
use App\Models\ServerProvider;
|
||||
use App\Models\User;
|
||||
use Exception;
|
||||
use Illuminate\Support\Facades\Validator;
|
||||
use Illuminate\Validation\Rule;
|
||||
use Illuminate\Validation\ValidationException;
|
||||
|
||||
class CreateServerProvider
|
||||
{
|
||||
/**
|
||||
* @throws ValidationException
|
||||
*/
|
||||
public function create(User $user, array $input): ServerProvider
|
||||
{
|
||||
$this->validateInput($input);
|
||||
|
||||
$provider = $this->getProvider($input['provider']);
|
||||
|
||||
$this->validateProvider($provider, $input);
|
||||
|
||||
try {
|
||||
$provider->connect($input);
|
||||
} catch (Exception) {
|
||||
throw ValidationException::withMessages([
|
||||
'provider' => [
|
||||
__("Couldn't connect to provider. Please check your credentials and try again later."),
|
||||
],
|
||||
]);
|
||||
}
|
||||
|
||||
$serverProvider = new ServerProvider();
|
||||
$serverProvider->user_id = $user->id;
|
||||
$serverProvider->profile = $input['name'];
|
||||
$serverProvider->provider = $input['provider'];
|
||||
$serverProvider->credentials = $provider->credentialData($input);
|
||||
$serverProvider->save();
|
||||
|
||||
return $serverProvider;
|
||||
}
|
||||
|
||||
private function getProvider($name): ServerProviderContract
|
||||
{
|
||||
$providerClass = config('core.server_providers_class.'.$name);
|
||||
|
||||
return new $providerClass();
|
||||
}
|
||||
|
||||
/**
|
||||
* @throws ValidationException
|
||||
*/
|
||||
private function validateInput(array $input): void
|
||||
{
|
||||
Validator::make($input, [
|
||||
'name' => [
|
||||
'required',
|
||||
],
|
||||
'provider' => [
|
||||
'required',
|
||||
Rule::in(config('core.server_providers')),
|
||||
Rule::notIn('custom'),
|
||||
],
|
||||
])->validate();
|
||||
}
|
||||
|
||||
/**
|
||||
* @throws ValidationException
|
||||
*/
|
||||
private function validateProvider(ServerProviderContract $provider, array $input): void
|
||||
{
|
||||
Validator::make($input, $provider->credentialValidationRules($input))->validate();
|
||||
}
|
||||
}
|
30
app/Actions/Site/ChangePHPVersion.php
Executable file
30
app/Actions/Site/ChangePHPVersion.php
Executable file
@ -0,0 +1,30 @@
|
||||
<?php
|
||||
|
||||
namespace App\Actions\Site;
|
||||
|
||||
use App\Models\Site;
|
||||
use Illuminate\Support\Facades\Validator;
|
||||
use Illuminate\Validation\ValidationException;
|
||||
|
||||
class ChangePHPVersion
|
||||
{
|
||||
/**
|
||||
* @throws ValidationException
|
||||
*/
|
||||
public function handle(Site $site, array $input): void
|
||||
{
|
||||
$this->validate($site, $input);
|
||||
|
||||
$site->changePHPVersion($input['php_version']);
|
||||
}
|
||||
|
||||
/**
|
||||
* @throws ValidationException
|
||||
*/
|
||||
protected function validate(Site $site, array $input): void
|
||||
{
|
||||
Validator::make($input, [
|
||||
'php_version' => 'required|in:'.implode(',', $site->server->installedPHPVersions()),
|
||||
])->validateWithBag('changePHPVersion');
|
||||
}
|
||||
}
|
51
app/Actions/Site/CreateRedirect.php
Normal file
51
app/Actions/Site/CreateRedirect.php
Normal file
@ -0,0 +1,51 @@
|
||||
<?php
|
||||
|
||||
namespace App\Actions\Site;
|
||||
|
||||
use App\Models\Redirect;
|
||||
use App\Models\Site;
|
||||
use Exception;
|
||||
use Illuminate\Support\Facades\Validator;
|
||||
use Illuminate\Validation\ValidationException;
|
||||
|
||||
class CreateRedirect
|
||||
{
|
||||
/**
|
||||
* @throws Exception
|
||||
*/
|
||||
public function handle(Site $site, array $input): void
|
||||
{
|
||||
$this->validate($input);
|
||||
|
||||
$redirect = new Redirect([
|
||||
'site_id' => $site->id,
|
||||
'mode' => $input['mode'],
|
||||
'from' => $input['from'],
|
||||
'to' => $input['to'],
|
||||
]);
|
||||
$redirect->save();
|
||||
$redirect->addToServer();
|
||||
}
|
||||
|
||||
/**
|
||||
* @throws ValidationException
|
||||
*/
|
||||
private function validate(array $input): void
|
||||
{
|
||||
$rules = [
|
||||
'mode' => [
|
||||
'required',
|
||||
'in:301,302',
|
||||
],
|
||||
'from' => [
|
||||
'required',
|
||||
],
|
||||
'to' => [
|
||||
'required',
|
||||
'url',
|
||||
],
|
||||
];
|
||||
|
||||
Validator::make($input, $rules)->validateWithBag('createRedirect');
|
||||
}
|
||||
}
|
118
app/Actions/Site/CreateSite.php
Executable file
118
app/Actions/Site/CreateSite.php
Executable file
@ -0,0 +1,118 @@
|
||||
<?php
|
||||
|
||||
namespace App\Actions\Site;
|
||||
|
||||
use App\Enums\SiteStatus;
|
||||
use App\Exceptions\SourceControlIsNotConnected;
|
||||
use App\Models\Server;
|
||||
use App\Models\Site;
|
||||
use App\ValidationRules\DomainRule;
|
||||
use Exception;
|
||||
use Illuminate\Support\Facades\DB;
|
||||
use Illuminate\Support\Facades\Validator;
|
||||
use Illuminate\Validation\Rule;
|
||||
use Illuminate\Validation\ValidationException;
|
||||
|
||||
class CreateSite
|
||||
{
|
||||
/**
|
||||
* @throws SourceControlIsNotConnected
|
||||
* @throws ValidationException
|
||||
*/
|
||||
public function create(Server $server, array $input): Site
|
||||
{
|
||||
$this->validateInputs($server, $input);
|
||||
|
||||
try {
|
||||
DB::beginTransaction();
|
||||
|
||||
$site = new Site([
|
||||
'server_id' => $server->id,
|
||||
'type' => $input['type'],
|
||||
'domain' => $input['domain'],
|
||||
'aliases' => isset($input['alias']) ? [$input['alias']] : [],
|
||||
'path' => '/home/'.$server->ssh_user.'/'.$input['domain'],
|
||||
'status' => SiteStatus::INSTALLING,
|
||||
]);
|
||||
|
||||
// fields based on type
|
||||
$site->fill($site->type()->createFields($input));
|
||||
|
||||
// check has access to repository
|
||||
try {
|
||||
if ($site->sourceControl()) {
|
||||
$site->sourceControl()->getRepo($site->repository);
|
||||
}
|
||||
} catch (SourceControlIsNotConnected) {
|
||||
throw ValidationException::withMessages([
|
||||
'source_control' => __('Source control is not connected'),
|
||||
]);
|
||||
}
|
||||
|
||||
// detect php version
|
||||
if ($site->type()->language() === 'php') {
|
||||
$site->php_version = $input['php_version'];
|
||||
}
|
||||
|
||||
// validate type
|
||||
$this->validateType($site, $input);
|
||||
|
||||
// set type data
|
||||
$site->type_data = $site->type()->data($input);
|
||||
|
||||
// save
|
||||
$site->save();
|
||||
|
||||
// create default deployment script
|
||||
$site->deploymentScript()->create([
|
||||
'name' => 'default',
|
||||
'content' => '',
|
||||
]);
|
||||
|
||||
// install server
|
||||
$site->install();
|
||||
|
||||
DB::commit();
|
||||
|
||||
return $site;
|
||||
} catch (Exception $e) {
|
||||
DB::rollBack();
|
||||
throw $e;
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* @throws ValidationException
|
||||
*/
|
||||
private function validateInputs(Server $server, array $input): void
|
||||
{
|
||||
$rules = [
|
||||
'type' => [
|
||||
'required',
|
||||
Rule::in(config('core.site_types')),
|
||||
],
|
||||
'domain' => [
|
||||
'required',
|
||||
new DomainRule(),
|
||||
Rule::unique('sites', 'domain')->where(function ($query) use ($server) {
|
||||
return $query->where('server_id', $server->id);
|
||||
}),
|
||||
],
|
||||
'alias' => [
|
||||
new DomainRule(),
|
||||
],
|
||||
];
|
||||
|
||||
Validator::make($input, $rules)->validate();
|
||||
}
|
||||
|
||||
/**
|
||||
* @throws ValidationException
|
||||
*/
|
||||
private function validateType(Site $site, array $input): void
|
||||
{
|
||||
$rules = $site->type()->createValidationRules($input);
|
||||
|
||||
Validator::make($input, $rules)->validate();
|
||||
}
|
||||
}
|
32
app/Actions/Site/DeleteSite.php
Executable file
32
app/Actions/Site/DeleteSite.php
Executable file
@ -0,0 +1,32 @@
|
||||
<?php
|
||||
|
||||
namespace App\Actions\Site;
|
||||
|
||||
use App\Models\Site;
|
||||
use Illuminate\Support\Facades\Validator;
|
||||
use Illuminate\Validation\ValidationException;
|
||||
|
||||
class DeleteSite
|
||||
{
|
||||
/**
|
||||
* @throws ValidationException
|
||||
*/
|
||||
public function handle(Site $site, array $input): void
|
||||
{
|
||||
$this->validateDelete($input);
|
||||
|
||||
$site->update(['status' => 'deleting']);
|
||||
|
||||
$site->remove();
|
||||
}
|
||||
|
||||
/**
|
||||
* @throws ValidationException
|
||||
*/
|
||||
protected function validateDelete(array $input): void
|
||||
{
|
||||
Validator::make($input, [
|
||||
'confirm' => 'required|in:delete',
|
||||
])->validateWithBag('deleteSite');
|
||||
}
|
||||
}
|
41
app/Actions/Site/EditSite.php
Executable file
41
app/Actions/Site/EditSite.php
Executable file
@ -0,0 +1,41 @@
|
||||
<?php
|
||||
|
||||
namespace App\Actions\Site;
|
||||
|
||||
use App\Models\Site;
|
||||
use Illuminate\Support\Facades\Validator;
|
||||
use Illuminate\Validation\ValidationException;
|
||||
|
||||
class EditSite
|
||||
{
|
||||
/**
|
||||
* @throws ValidationException
|
||||
*/
|
||||
public function handle(Site $site, array $input): Site
|
||||
{
|
||||
// validate type
|
||||
$this->validateType($site, $input);
|
||||
|
||||
// set type data
|
||||
$site->type_data = $site->type()->data($input);
|
||||
|
||||
// save
|
||||
$site->port = $input['port'] ?? null;
|
||||
$site->save();
|
||||
|
||||
// edit
|
||||
$site->type()->edit();
|
||||
|
||||
return $site;
|
||||
}
|
||||
|
||||
/**
|
||||
* @throws ValidationException
|
||||
*/
|
||||
private function validateType(Site $site, array $input): void
|
||||
{
|
||||
$rules = $site->type()->editValidationRules($input);
|
||||
|
||||
Validator::make($input, $rules)->validateWithBag('editSite');
|
||||
}
|
||||
}
|
14
app/Actions/Site/GetSites.php
Executable file
14
app/Actions/Site/GetSites.php
Executable file
@ -0,0 +1,14 @@
|
||||
<?php
|
||||
|
||||
namespace App\Actions\Site;
|
||||
|
||||
use App\Models\Server;
|
||||
use Illuminate\Database\Eloquent\Collection;
|
||||
|
||||
class GetSites
|
||||
{
|
||||
public function handle(Server $server): Collection
|
||||
{
|
||||
return $server->sites()->orderBy('id', 'desc')->get();
|
||||
}
|
||||
}
|
30
app/Actions/Site/UpdateBranch.php
Executable file
30
app/Actions/Site/UpdateBranch.php
Executable file
@ -0,0 +1,30 @@
|
||||
<?php
|
||||
|
||||
namespace App\Actions\Site;
|
||||
|
||||
use App\Models\Site;
|
||||
use Illuminate\Support\Facades\Validator;
|
||||
use Illuminate\Validation\ValidationException;
|
||||
|
||||
class UpdateBranch
|
||||
{
|
||||
/**
|
||||
* @throws ValidationException
|
||||
*/
|
||||
public function update(Site $site, array $input): void
|
||||
{
|
||||
$this->validate($input);
|
||||
|
||||
$site->updateBranch($input['branch']);
|
||||
}
|
||||
|
||||
/**
|
||||
* @throws ValidationException
|
||||
*/
|
||||
protected function validate(array $input): void
|
||||
{
|
||||
Validator::make($input, [
|
||||
'branch' => 'required',
|
||||
])->validateWithBag('updateBranch');
|
||||
}
|
||||
}
|
32
app/Actions/Site/UpdateDeploymentScript.php
Executable file
32
app/Actions/Site/UpdateDeploymentScript.php
Executable file
@ -0,0 +1,32 @@
|
||||
<?php
|
||||
|
||||
namespace App\Actions\Site;
|
||||
|
||||
use App\Models\Site;
|
||||
use Illuminate\Support\Facades\Validator;
|
||||
use Illuminate\Validation\ValidationException;
|
||||
|
||||
class UpdateDeploymentScript
|
||||
{
|
||||
/**
|
||||
* @throws ValidationException
|
||||
*/
|
||||
public function update(Site $site, array $input): void
|
||||
{
|
||||
$this->validate($input);
|
||||
|
||||
$site->deploymentScript()->update([
|
||||
'content' => $input['script'],
|
||||
]);
|
||||
}
|
||||
|
||||
/**
|
||||
* @throws ValidationException
|
||||
*/
|
||||
protected function validate(array $input): void
|
||||
{
|
||||
Validator::make($input, [
|
||||
'script' => 'required',
|
||||
])->validateWithBag('updateDeploymentScript');
|
||||
}
|
||||
}
|
18
app/Actions/Site/UpdateEnv.php
Executable file
18
app/Actions/Site/UpdateEnv.php
Executable file
@ -0,0 +1,18 @@
|
||||
<?php
|
||||
|
||||
namespace App\Actions\Site;
|
||||
|
||||
use App\Models\Site;
|
||||
|
||||
class UpdateEnv
|
||||
{
|
||||
public function handle(Site $site, array $input): void
|
||||
{
|
||||
$typeData = $site->type_data;
|
||||
$typeData['env'] = $input['env'];
|
||||
$site->type_data = $typeData;
|
||||
$site->save();
|
||||
|
||||
$site->deployEnv();
|
||||
}
|
||||
}
|
35
app/Actions/SourceControl/ConnectSourceControl.php
Normal file
35
app/Actions/SourceControl/ConnectSourceControl.php
Normal file
@ -0,0 +1,35 @@
|
||||
<?php
|
||||
|
||||
namespace App\Actions\SourceControl;
|
||||
|
||||
use App\Models\SourceControl;
|
||||
use Illuminate\Validation\ValidationException;
|
||||
|
||||
class ConnectSourceControl
|
||||
{
|
||||
public function connect(string $provider, array $input): void
|
||||
{
|
||||
$sourceControl = SourceControl::query()
|
||||
->where('provider', $provider)
|
||||
->first();
|
||||
if (! $sourceControl) {
|
||||
$sourceControl = new SourceControl([
|
||||
'provider' => $provider,
|
||||
]);
|
||||
}
|
||||
|
||||
if (! $input['token']) {
|
||||
$sourceControl->delete();
|
||||
|
||||
return;
|
||||
}
|
||||
|
||||
$sourceControl->access_token = $input['token'];
|
||||
if (! $sourceControl->provider()->connect()) {
|
||||
throw ValidationException::withMessages([
|
||||
'token' => __('Cannot connect to :provider or invalid token!', ['provider' => $provider]),
|
||||
]);
|
||||
}
|
||||
$sourceControl->save();
|
||||
}
|
||||
}
|
43
app/Actions/SshKey/CreateSshKey.php
Normal file
43
app/Actions/SshKey/CreateSshKey.php
Normal file
@ -0,0 +1,43 @@
|
||||
<?php
|
||||
|
||||
namespace App\Actions\SshKey;
|
||||
|
||||
use App\Models\SshKey;
|
||||
use App\Models\User;
|
||||
use App\ValidationRules\SshKeyRule;
|
||||
use Illuminate\Support\Facades\Validator;
|
||||
use Illuminate\Validation\ValidationException;
|
||||
|
||||
class CreateSshKey
|
||||
{
|
||||
/**
|
||||
* @throws ValidationException
|
||||
*/
|
||||
public function create(User $user, array $input): SshKey
|
||||
{
|
||||
$this->validate($input);
|
||||
|
||||
$key = new SshKey([
|
||||
'user_id' => $user->id,
|
||||
'name' => $input['name'],
|
||||
'public_key' => $input['public_key'],
|
||||
]);
|
||||
$key->save();
|
||||
|
||||
return $key;
|
||||
}
|
||||
|
||||
/**
|
||||
* @throws ValidationException
|
||||
*/
|
||||
private function validate(array $input): void
|
||||
{
|
||||
Validator::make($input, [
|
||||
'name' => 'required',
|
||||
'public_key' => [
|
||||
'required',
|
||||
new SshKeyRule(),
|
||||
],
|
||||
])->validate();
|
||||
}
|
||||
}
|
30
app/Actions/StorageProvider/AddStorageProvider.php
Normal file
30
app/Actions/StorageProvider/AddStorageProvider.php
Normal file
@ -0,0 +1,30 @@
|
||||
<?php
|
||||
|
||||
namespace App\Actions\StorageProvider;
|
||||
|
||||
use App\Models\StorageProvider;
|
||||
use App\Models\User;
|
||||
use Illuminate\Validation\ValidationException;
|
||||
|
||||
class AddStorageProvider
|
||||
{
|
||||
use ValidateProvider;
|
||||
|
||||
/**
|
||||
* @throws ValidationException
|
||||
*/
|
||||
public function add(User $user, array $input): mixed
|
||||
{
|
||||
$this->validate($user, $input);
|
||||
|
||||
$storageProvider = new StorageProvider([
|
||||
'user_id' => $user->id,
|
||||
'provider' => $input['provider'],
|
||||
'label' => $input['label'],
|
||||
'connected' => false,
|
||||
]);
|
||||
$storageProvider->save();
|
||||
|
||||
return $storageProvider->provider()->connect();
|
||||
}
|
||||
}
|
34
app/Actions/StorageProvider/HandleProviderCallback.php
Executable file
34
app/Actions/StorageProvider/HandleProviderCallback.php
Executable file
@ -0,0 +1,34 @@
|
||||
<?php
|
||||
|
||||
namespace App\Actions\StorageProvider;
|
||||
|
||||
use App\Models\StorageProvider;
|
||||
use Illuminate\Http\RedirectResponse;
|
||||
use Illuminate\Http\Request;
|
||||
use Laravel\Socialite\Facades\Socialite;
|
||||
use Laravel\Socialite\Two\User;
|
||||
use Throwable;
|
||||
|
||||
class HandleProviderCallback
|
||||
{
|
||||
public function callback(Request $request, string $provider): string|RedirectResponse
|
||||
{
|
||||
try {
|
||||
$providerId = $request->session()->get('storage_provider_id');
|
||||
/** @var StorageProvider $storageProvider */
|
||||
$storageProvider = StorageProvider::query()->findOrFail($providerId);
|
||||
/** @var User $oauthUser */
|
||||
$oauthUser = Socialite::driver($provider)->user();
|
||||
$storageProvider->token = $oauthUser->token;
|
||||
$storageProvider->refresh_token = $oauthUser->refreshToken;
|
||||
$storageProvider->token_expires_at = now()->addSeconds($oauthUser->expiresIn);
|
||||
$storageProvider->connected = true;
|
||||
$storageProvider->save();
|
||||
/** @TODO toast success message */
|
||||
} catch (Throwable) {
|
||||
/** @TODO toast failed message */
|
||||
}
|
||||
|
||||
return redirect()->route('storage-providers');
|
||||
}
|
||||
}
|
28
app/Actions/StorageProvider/ValidateProvider.php
Executable file
28
app/Actions/StorageProvider/ValidateProvider.php
Executable file
@ -0,0 +1,28 @@
|
||||
<?php
|
||||
|
||||
namespace App\Actions\StorageProvider;
|
||||
|
||||
use App\Models\User;
|
||||
use Illuminate\Support\Facades\Validator;
|
||||
use Illuminate\Validation\Rule;
|
||||
use Illuminate\Validation\ValidationException;
|
||||
|
||||
trait ValidateProvider
|
||||
{
|
||||
/**
|
||||
* @throws ValidationException
|
||||
*/
|
||||
private function validate(User $user, array $input): void
|
||||
{
|
||||
Validator::make($input, [
|
||||
'label' => [
|
||||
'required',
|
||||
Rule::unique('storage_providers', 'label')->where('user_id', $user->id),
|
||||
],
|
||||
'provider' => [
|
||||
'required',
|
||||
Rule::in(config('core.storage_providers')),
|
||||
],
|
||||
])->validateWithBag('addStorageProvider');
|
||||
}
|
||||
}
|
25
app/Actions/User/UpdateUserPassword.php
Executable file
25
app/Actions/User/UpdateUserPassword.php
Executable file
@ -0,0 +1,25 @@
|
||||
<?php
|
||||
|
||||
namespace App\Actions\User;
|
||||
|
||||
use Illuminate\Support\Facades\Hash;
|
||||
use Illuminate\Support\Facades\Validator;
|
||||
|
||||
class UpdateUserPassword
|
||||
{
|
||||
/**
|
||||
* Validate and update the user's password.
|
||||
*/
|
||||
public function update($user, array $input): void
|
||||
{
|
||||
Validator::make($input, [
|
||||
'current_password' => ['required', 'string', 'current-password'],
|
||||
'password' => ['required', 'string'],
|
||||
'password_confirmation' => ['required', 'same:password'],
|
||||
])->validate();
|
||||
|
||||
$user->forceFill([
|
||||
'password' => Hash::make($input['password']),
|
||||
])->save();
|
||||
}
|
||||
}
|
44
app/Actions/User/UpdateUserProfileInformation.php
Executable file
44
app/Actions/User/UpdateUserProfileInformation.php
Executable file
@ -0,0 +1,44 @@
|
||||
<?php
|
||||
|
||||
namespace App\Actions\User;
|
||||
|
||||
use App\Models\User;
|
||||
use Exception;
|
||||
use Illuminate\Support\Facades\Validator;
|
||||
use Illuminate\Validation\Rule;
|
||||
|
||||
class UpdateUserProfileInformation
|
||||
{
|
||||
/**
|
||||
* Validate and update the given user's profile information.
|
||||
*
|
||||
* @throws Exception
|
||||
*/
|
||||
public function update(User $user, array $input): void
|
||||
{
|
||||
Validator::make($input, [
|
||||
'name' => ['required', 'string', 'max:255'],
|
||||
'email' => ['required', 'email', 'max:255', Rule::unique('users')->ignore($user->id)],
|
||||
])->validateWithBag('updateProfileInformation');
|
||||
|
||||
if ($input['email'] !== $user->email) {
|
||||
$this->updateVerifiedUser($user, $input);
|
||||
} else {
|
||||
$user->forceFill([
|
||||
'name' => $input['name'],
|
||||
'email' => $input['email'],
|
||||
])->save();
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* Update the given verified user's profile information.
|
||||
*/
|
||||
protected function updateVerifiedUser(User $user, array $input): void
|
||||
{
|
||||
$user->forceFill([
|
||||
'name' => $input['name'],
|
||||
'email' => $input['email'],
|
||||
])->save();
|
||||
}
|
||||
}
|
28
app/Console/Commands/CreateDatabaseCommand.php
Normal file
28
app/Console/Commands/CreateDatabaseCommand.php
Normal file
@ -0,0 +1,28 @@
|
||||
<?php
|
||||
|
||||
namespace App\Console\Commands;
|
||||
|
||||
use Illuminate\Console\Command;
|
||||
use Illuminate\Support\Facades\DB;
|
||||
|
||||
class CreateDatabaseCommand extends Command
|
||||
{
|
||||
protected $signature = 'database:create';
|
||||
|
||||
protected $description = 'Create the database if it does not exist.';
|
||||
|
||||
public function handle(): void
|
||||
{
|
||||
$schemaName = config("database.connections.mysql.database");
|
||||
|
||||
config(["database.connections.mysql.database" => null]);
|
||||
|
||||
$query = "CREATE DATABASE IF NOT EXISTS $schemaName";
|
||||
|
||||
DB::statement($query);
|
||||
|
||||
config(["database.connections.mysql.database" => $schemaName]);
|
||||
|
||||
$this->info(sprintf("Database `%s` created successfully.", $schemaName));
|
||||
}
|
||||
}
|
26
app/Console/Commands/CreateUserCommand.php
Normal file
26
app/Console/Commands/CreateUserCommand.php
Normal file
@ -0,0 +1,26 @@
|
||||
<?php
|
||||
|
||||
namespace App\Console\Commands;
|
||||
|
||||
use App\Models\User;
|
||||
use Illuminate\Console\Command;
|
||||
use Illuminate\Support\Str;
|
||||
|
||||
class CreateUserCommand extends Command
|
||||
{
|
||||
protected $signature = 'user:create {name} {email}';
|
||||
|
||||
protected $description = 'Create a new user';
|
||||
|
||||
public function handle(): void
|
||||
{
|
||||
$password = Str::random(20);
|
||||
User::create([
|
||||
'name' => $this->argument('name'),
|
||||
'email' => $this->argument('email'),
|
||||
'password' => bcrypt($password),
|
||||
]);
|
||||
|
||||
$this->info("User created with password: {$password}");
|
||||
}
|
||||
}
|
27
app/Console/Kernel.php
Normal file
27
app/Console/Kernel.php
Normal file
@ -0,0 +1,27 @@
|
||||
<?php
|
||||
|
||||
namespace App\Console;
|
||||
|
||||
use Illuminate\Console\Scheduling\Schedule;
|
||||
use Illuminate\Foundation\Console\Kernel as ConsoleKernel;
|
||||
|
||||
class Kernel extends ConsoleKernel
|
||||
{
|
||||
/**
|
||||
* Define the application's command schedule.
|
||||
*/
|
||||
protected function schedule(Schedule $schedule): void
|
||||
{
|
||||
// $schedule->command('inspire')->hourly();
|
||||
}
|
||||
|
||||
/**
|
||||
* Register the commands for the application.
|
||||
*/
|
||||
protected function commands(): void
|
||||
{
|
||||
$this->load(__DIR__.'/Commands');
|
||||
|
||||
require base_path('routes/console.php');
|
||||
}
|
||||
}
|
24
app/Contracts/Database.php
Executable file
24
app/Contracts/Database.php
Executable file
@ -0,0 +1,24 @@
|
||||
<?php
|
||||
|
||||
namespace App\Contracts;
|
||||
|
||||
use App\Models\BackupFile;
|
||||
|
||||
interface Database
|
||||
{
|
||||
public function create(string $name): void;
|
||||
|
||||
public function delete(string $name): void;
|
||||
|
||||
public function createUser(string $username, string $password, string $host): void;
|
||||
|
||||
public function deleteUser(string $username, string $host): void;
|
||||
|
||||
public function link(string $username, string $host, array $databases): void;
|
||||
|
||||
public function unlink(string $username, string $host): void;
|
||||
|
||||
public function runBackup(BackupFile $backupFile): void;
|
||||
|
||||
public function restoreBackup(BackupFile $backupFile, string $database): void;
|
||||
}
|
10
app/Contracts/Firewall.php
Executable file
10
app/Contracts/Firewall.php
Executable file
@ -0,0 +1,10 @@
|
||||
<?php
|
||||
|
||||
namespace App\Contracts;
|
||||
|
||||
interface Firewall
|
||||
{
|
||||
public function addRule(string $type, string $protocol, int $port, string $source, string $mask): void;
|
||||
|
||||
public function removeRule(string $type, string $protocol, int $port, string $source, string $mask): void;
|
||||
}
|
10
app/Contracts/Notification.php
Normal file
10
app/Contracts/Notification.php
Normal file
@ -0,0 +1,10 @@
|
||||
<?php
|
||||
|
||||
namespace App\Contracts;
|
||||
|
||||
interface Notification
|
||||
{
|
||||
public function subject(): string;
|
||||
|
||||
public function message(bool $mail = false): mixed;
|
||||
}
|
14
app/Contracts/NotificationChannel.php
Normal file
14
app/Contracts/NotificationChannel.php
Normal file
@ -0,0 +1,14 @@
|
||||
<?php
|
||||
|
||||
namespace App\Contracts;
|
||||
|
||||
interface NotificationChannel
|
||||
{
|
||||
public function validationRules(): array;
|
||||
|
||||
public function data(array $input): array;
|
||||
|
||||
public function connect(): bool;
|
||||
|
||||
public function sendMessage(string $subject, string $text): void;
|
||||
}
|
27
app/Contracts/ProcessManager.php
Executable file
27
app/Contracts/ProcessManager.php
Executable file
@ -0,0 +1,27 @@
|
||||
<?php
|
||||
|
||||
namespace App\Contracts;
|
||||
|
||||
interface ProcessManager
|
||||
{
|
||||
public function create(
|
||||
int $id,
|
||||
string $command,
|
||||
string $user,
|
||||
bool $autoStart,
|
||||
bool $autoRestart,
|
||||
int $numprocs,
|
||||
string $logFile,
|
||||
?int $siteId = null
|
||||
): void;
|
||||
|
||||
public function delete(int $id, int $siteId = null): void;
|
||||
|
||||
public function restart(int $id, int $siteId = null): void;
|
||||
|
||||
public function stop(int $id, int $siteId = null): void;
|
||||
|
||||
public function start(int $id, int $siteId = null): void;
|
||||
|
||||
public function getLogs(string $logPath): string;
|
||||
}
|
10
app/Contracts/SSHCommand.php
Executable file
10
app/Contracts/SSHCommand.php
Executable file
@ -0,0 +1,10 @@
|
||||
<?php
|
||||
|
||||
namespace App\Contracts;
|
||||
|
||||
interface SSHCommand
|
||||
{
|
||||
public function file(string $os): string;
|
||||
|
||||
public function content(string $os): string;
|
||||
}
|
26
app/Contracts/ServerProvider.php
Executable file
26
app/Contracts/ServerProvider.php
Executable file
@ -0,0 +1,26 @@
|
||||
<?php
|
||||
|
||||
namespace App\Contracts;
|
||||
|
||||
interface ServerProvider
|
||||
{
|
||||
public function createValidationRules(array $input): array;
|
||||
|
||||
public function credentialValidationRules(array $input): array;
|
||||
|
||||
public function credentialData(array $input): array;
|
||||
|
||||
public function data(array $input): array;
|
||||
|
||||
public function connect(array $credentials = null): bool;
|
||||
|
||||
public function plans(): array;
|
||||
|
||||
public function regions(): array;
|
||||
|
||||
public function create(): void;
|
||||
|
||||
public function isRunning(): bool;
|
||||
|
||||
public function delete(): void;
|
||||
}
|
14
app/Contracts/ServerType.php
Executable file
14
app/Contracts/ServerType.php
Executable file
@ -0,0 +1,14 @@
|
||||
<?php
|
||||
|
||||
namespace App\Contracts;
|
||||
|
||||
interface ServerType
|
||||
{
|
||||
public function createValidationRules(array $input): array;
|
||||
|
||||
public function data(array $input): array;
|
||||
|
||||
public function createServices(array $input): void;
|
||||
|
||||
public function install(): void;
|
||||
}
|
22
app/Contracts/SiteType.php
Executable file
22
app/Contracts/SiteType.php
Executable file
@ -0,0 +1,22 @@
|
||||
<?php
|
||||
|
||||
namespace App\Contracts;
|
||||
|
||||
interface SiteType
|
||||
{
|
||||
public function language(): string;
|
||||
|
||||
public function createValidationRules(array $input): array;
|
||||
|
||||
public function createFields(array $input): array;
|
||||
|
||||
public function data(array $input): array;
|
||||
|
||||
public function install(): void;
|
||||
|
||||
public function delete(): void;
|
||||
|
||||
public function editValidationRules(array $input): array;
|
||||
|
||||
public function edit(): void;
|
||||
}
|
18
app/Contracts/SourceControlProvider.php
Executable file
18
app/Contracts/SourceControlProvider.php
Executable file
@ -0,0 +1,18 @@
|
||||
<?php
|
||||
|
||||
namespace App\Contracts;
|
||||
|
||||
interface SourceControlProvider
|
||||
{
|
||||
public function connect(): bool;
|
||||
|
||||
public function getRepo(string $repo = null): mixed;
|
||||
|
||||
public function fullRepoUrl(string $repo): string;
|
||||
|
||||
public function deployHook(string $repo, array $events, string $secret): array;
|
||||
|
||||
public function destroyHook(string $repo, string $hookId): void;
|
||||
|
||||
public function getLastCommit(string $repo, string $branch): ?array;
|
||||
}
|
17
app/Contracts/StorageProvider.php
Normal file
17
app/Contracts/StorageProvider.php
Normal file
@ -0,0 +1,17 @@
|
||||
<?php
|
||||
|
||||
namespace App\Contracts;
|
||||
|
||||
use App\Models\Server;
|
||||
use Symfony\Component\HttpFoundation\RedirectResponse;
|
||||
|
||||
interface StorageProvider
|
||||
{
|
||||
public function connect(): RedirectResponse;
|
||||
|
||||
public function upload(Server $server, string $src, string $dest): array;
|
||||
|
||||
public function download(Server $server, string $src, string $dest): void;
|
||||
|
||||
public function delete(array $paths): void;
|
||||
}
|
23
app/Contracts/Webserver.php
Executable file
23
app/Contracts/Webserver.php
Executable file
@ -0,0 +1,23 @@
|
||||
<?php
|
||||
|
||||
namespace App\Contracts;
|
||||
|
||||
use App\Models\Site;
|
||||
use App\Models\Ssl;
|
||||
|
||||
interface Webserver
|
||||
{
|
||||
public function createVHost(Site $site): void;
|
||||
|
||||
public function updateVHost(Site $site): void;
|
||||
|
||||
public function deleteSite(Site $site): void;
|
||||
|
||||
public function changePHPVersion(Site $site, string $version): void;
|
||||
|
||||
public function setupSSL(Ssl $ssl): void;
|
||||
|
||||
public function removeSSL(Ssl $ssl): void;
|
||||
|
||||
public function updateRedirects(Site $site, array $redirects): void;
|
||||
}
|
14
app/Enums/CronjobStatus.php
Normal file
14
app/Enums/CronjobStatus.php
Normal file
@ -0,0 +1,14 @@
|
||||
<?php
|
||||
|
||||
namespace App\Enums;
|
||||
|
||||
use BenSampo\Enum\Enum;
|
||||
|
||||
final class CronjobStatus extends Enum
|
||||
{
|
||||
const CREATING = 'creating';
|
||||
|
||||
const READY = 'ready';
|
||||
|
||||
const DELETING = 'deleting';
|
||||
}
|
16
app/Enums/Database.php
Normal file
16
app/Enums/Database.php
Normal file
@ -0,0 +1,16 @@
|
||||
<?php
|
||||
|
||||
namespace App\Enums;
|
||||
|
||||
use BenSampo\Enum\Enum;
|
||||
|
||||
final class Database extends Enum
|
||||
{
|
||||
const NONE = 'none';
|
||||
|
||||
const MYSQL57 = 'mysql57';
|
||||
|
||||
const MYSQL80 = 'mysql80';
|
||||
|
||||
const MARIADB = 'mariadb';
|
||||
}
|
16
app/Enums/DatabaseStatus.php
Normal file
16
app/Enums/DatabaseStatus.php
Normal file
@ -0,0 +1,16 @@
|
||||
<?php
|
||||
|
||||
namespace App\Enums;
|
||||
|
||||
use BenSampo\Enum\Enum;
|
||||
|
||||
final class DatabaseStatus extends Enum
|
||||
{
|
||||
const READY = 'ready';
|
||||
|
||||
const CREATING = 'creating';
|
||||
|
||||
const FAILED = 'failed';
|
||||
|
||||
const DELETING = 'deleting';
|
||||
}
|
16
app/Enums/DatabaseUserStatus.php
Normal file
16
app/Enums/DatabaseUserStatus.php
Normal file
@ -0,0 +1,16 @@
|
||||
<?php
|
||||
|
||||
namespace App\Enums;
|
||||
|
||||
use BenSampo\Enum\Enum;
|
||||
|
||||
final class DatabaseUserStatus extends Enum
|
||||
{
|
||||
const READY = 'ready';
|
||||
|
||||
const CREATING = 'creating';
|
||||
|
||||
const FAILED = 'failed';
|
||||
|
||||
const DELETING = 'deleting';
|
||||
}
|
14
app/Enums/DeploymentStatus.php
Normal file
14
app/Enums/DeploymentStatus.php
Normal file
@ -0,0 +1,14 @@
|
||||
<?php
|
||||
|
||||
namespace App\Enums;
|
||||
|
||||
use BenSampo\Enum\Enum;
|
||||
|
||||
final class DeploymentStatus extends Enum
|
||||
{
|
||||
const DEPLOYING = 'deploying';
|
||||
|
||||
const FINISHED = 'finished';
|
||||
|
||||
const FAILED = 'failed';
|
||||
}
|
14
app/Enums/FirewallRuleStatus.php
Normal file
14
app/Enums/FirewallRuleStatus.php
Normal file
@ -0,0 +1,14 @@
|
||||
<?php
|
||||
|
||||
namespace App\Enums;
|
||||
|
||||
use BenSampo\Enum\Enum;
|
||||
|
||||
final class FirewallRuleStatus extends Enum
|
||||
{
|
||||
const CREATING = 'creating';
|
||||
|
||||
const READY = 'ready';
|
||||
|
||||
const DELETING = 'deleting';
|
||||
}
|
12
app/Enums/LogType.php
Normal file
12
app/Enums/LogType.php
Normal file
@ -0,0 +1,12 @@
|
||||
<?php
|
||||
|
||||
namespace App\Enums;
|
||||
|
||||
use BenSampo\Enum\Enum;
|
||||
|
||||
final class LogType extends Enum
|
||||
{
|
||||
const SERVER = 'server';
|
||||
|
||||
const SITE = 'site';
|
||||
}
|
14
app/Enums/NotificationChannel.php
Normal file
14
app/Enums/NotificationChannel.php
Normal file
@ -0,0 +1,14 @@
|
||||
<?php
|
||||
|
||||
namespace App\Enums;
|
||||
|
||||
use BenSampo\Enum\Enum;
|
||||
|
||||
final class NotificationChannel extends Enum
|
||||
{
|
||||
const EMAIL = 'email';
|
||||
|
||||
const SLACK = 'slack';
|
||||
|
||||
const DISCORD = 'discord';
|
||||
}
|
14
app/Enums/OperatingSystem.php
Normal file
14
app/Enums/OperatingSystem.php
Normal file
@ -0,0 +1,14 @@
|
||||
<?php
|
||||
|
||||
namespace App\Enums;
|
||||
|
||||
use BenSampo\Enum\Enum;
|
||||
|
||||
final class OperatingSystem extends Enum
|
||||
{
|
||||
const UBUNTU18 = 'ubuntu_18';
|
||||
|
||||
const UBUNTU20 = 'ubuntu_20';
|
||||
|
||||
const UBUNTU22 = 'ubuntu_22';
|
||||
}
|
24
app/Enums/QueueStatus.php
Normal file
24
app/Enums/QueueStatus.php
Normal file
@ -0,0 +1,24 @@
|
||||
<?php
|
||||
|
||||
namespace App\Enums;
|
||||
|
||||
use BenSampo\Enum\Enum;
|
||||
|
||||
final class QueueStatus extends Enum
|
||||
{
|
||||
const RUNNING = 'running';
|
||||
|
||||
const CREATING = 'creating';
|
||||
|
||||
const DELETING = 'deleting';
|
||||
|
||||
const FAILED = 'failed';
|
||||
|
||||
const STARTING = 'starting';
|
||||
|
||||
const STOPPING = 'stopping';
|
||||
|
||||
const RESTARTING = 'restarting';
|
||||
|
||||
const STOPPED = 'stopped';
|
||||
}
|
20
app/Enums/ServerProvider.php
Normal file
20
app/Enums/ServerProvider.php
Normal file
@ -0,0 +1,20 @@
|
||||
<?php
|
||||
|
||||
namespace App\Enums;
|
||||
|
||||
use BenSampo\Enum\Enum;
|
||||
|
||||
final class ServerProvider extends Enum
|
||||
{
|
||||
const CUSTOM = 'custom';
|
||||
|
||||
const AWS = 'aws';
|
||||
|
||||
const LINODE = 'linode';
|
||||
|
||||
const DIGITALOCEAN = 'digitalocean';
|
||||
|
||||
const VULTR = 'vultr';
|
||||
|
||||
const HETZNER = 'hetzner';
|
||||
}
|
16
app/Enums/ServerStatus.php
Normal file
16
app/Enums/ServerStatus.php
Normal file
@ -0,0 +1,16 @@
|
||||
<?php
|
||||
|
||||
namespace App\Enums;
|
||||
|
||||
use BenSampo\Enum\Enum;
|
||||
|
||||
final class ServerStatus extends Enum
|
||||
{
|
||||
const READY = 'ready';
|
||||
|
||||
const INSTALLING = 'installing';
|
||||
|
||||
const INSTALLATION_FAILED = 'installation_failed';
|
||||
|
||||
const DISCONNECTED = 'disconnected';
|
||||
}
|
10
app/Enums/ServerType.php
Normal file
10
app/Enums/ServerType.php
Normal file
@ -0,0 +1,10 @@
|
||||
<?php
|
||||
|
||||
namespace App\Enums;
|
||||
|
||||
use BenSampo\Enum\Enum;
|
||||
|
||||
final class ServerType extends Enum
|
||||
{
|
||||
const REGULAR = 'regular';
|
||||
}
|
26
app/Enums/ServiceStatus.php
Normal file
26
app/Enums/ServiceStatus.php
Normal file
@ -0,0 +1,26 @@
|
||||
<?php
|
||||
|
||||
namespace App\Enums;
|
||||
|
||||
use BenSampo\Enum\Enum;
|
||||
|
||||
final class ServiceStatus extends Enum
|
||||
{
|
||||
const READY = 'ready';
|
||||
|
||||
const INSTALLING = 'installing';
|
||||
|
||||
const INSTALLATION_FAILED = 'installation_failed';
|
||||
|
||||
const UNINSTALLING = 'uninstalling';
|
||||
|
||||
const FAILED = 'failed';
|
||||
|
||||
const STARTING = 'starting';
|
||||
|
||||
const STOPPING = 'stopping';
|
||||
|
||||
const RESTARTING = 'restarting';
|
||||
|
||||
const STOPPED = 'stopped';
|
||||
}
|
16
app/Enums/SiteStatus.php
Normal file
16
app/Enums/SiteStatus.php
Normal file
@ -0,0 +1,16 @@
|
||||
<?php
|
||||
|
||||
namespace App\Enums;
|
||||
|
||||
use BenSampo\Enum\Enum;
|
||||
|
||||
final class SiteStatus extends Enum
|
||||
{
|
||||
const READY = 'ready';
|
||||
|
||||
const INSTALLING = 'installing';
|
||||
|
||||
const INSTALLATION_FAILED = 'installation_failed';
|
||||
|
||||
const DELETING = 'deleting';
|
||||
}
|
14
app/Enums/SiteType.php
Normal file
14
app/Enums/SiteType.php
Normal file
@ -0,0 +1,14 @@
|
||||
<?php
|
||||
|
||||
namespace App\Enums;
|
||||
|
||||
use BenSampo\Enum\Enum;
|
||||
|
||||
final class SiteType extends Enum
|
||||
{
|
||||
const PHP = 'php';
|
||||
|
||||
const LARAVEL = 'laravel';
|
||||
|
||||
const WORDPRESS = 'wordpress';
|
||||
}
|
16
app/Enums/SourceControl.php
Normal file
16
app/Enums/SourceControl.php
Normal file
@ -0,0 +1,16 @@
|
||||
<?php
|
||||
|
||||
namespace App\Enums;
|
||||
|
||||
use BenSampo\Enum\Enum;
|
||||
|
||||
final class SourceControl extends Enum
|
||||
{
|
||||
const GITHUB = 'github';
|
||||
|
||||
const GITLAB = 'gitlab';
|
||||
|
||||
const BITBUCKET = 'bitbucket';
|
||||
|
||||
const CUSTOM = 'custom';
|
||||
}
|
14
app/Enums/SshKeyStatus.php
Normal file
14
app/Enums/SshKeyStatus.php
Normal file
@ -0,0 +1,14 @@
|
||||
<?php
|
||||
|
||||
namespace App\Enums;
|
||||
|
||||
use BenSampo\Enum\Enum;
|
||||
|
||||
final class SshKeyStatus extends Enum
|
||||
{
|
||||
const ADDING = 'adding';
|
||||
|
||||
const ADDED = 'added';
|
||||
|
||||
const DELETING = 'deleting';
|
||||
}
|
16
app/Enums/SslStatus.php
Normal file
16
app/Enums/SslStatus.php
Normal file
@ -0,0 +1,16 @@
|
||||
<?php
|
||||
|
||||
namespace App\Enums;
|
||||
|
||||
use BenSampo\Enum\Enum;
|
||||
|
||||
final class SslStatus extends Enum
|
||||
{
|
||||
const CREATED = 'created';
|
||||
|
||||
const CREATING = 'creating';
|
||||
|
||||
const DELETING = 'deleting';
|
||||
|
||||
const FAILED = 'failed';
|
||||
}
|
12
app/Enums/SslType.php
Normal file
12
app/Enums/SslType.php
Normal file
@ -0,0 +1,12 @@
|
||||
<?php
|
||||
|
||||
namespace App\Enums;
|
||||
|
||||
use BenSampo\Enum\Enum;
|
||||
|
||||
final class SslType extends Enum
|
||||
{
|
||||
const LETSENCRYPT = 'letsencrypt';
|
||||
|
||||
const CUSTOM = 'custom';
|
||||
}
|
12
app/Enums/StorageProvider.php
Normal file
12
app/Enums/StorageProvider.php
Normal file
@ -0,0 +1,12 @@
|
||||
<?php
|
||||
|
||||
namespace App\Enums;
|
||||
|
||||
use BenSampo\Enum\Enum;
|
||||
|
||||
final class StorageProvider extends Enum
|
||||
{
|
||||
const GOOGLE = 'google';
|
||||
|
||||
const DROPBOX = 'dropbox';
|
||||
}
|
10
app/Enums/Webserver.php
Normal file
10
app/Enums/Webserver.php
Normal file
@ -0,0 +1,10 @@
|
||||
<?php
|
||||
|
||||
namespace App\Enums;
|
||||
|
||||
use BenSampo\Enum\Enum;
|
||||
|
||||
final class Webserver extends Enum
|
||||
{
|
||||
const NGINX = 'nginx';
|
||||
}
|
25
app/Events/Broadcast.php
Normal file
25
app/Events/Broadcast.php
Normal file
@ -0,0 +1,25 @@
|
||||
<?php
|
||||
|
||||
namespace App\Events;
|
||||
|
||||
use Illuminate\Broadcasting\InteractsWithSockets;
|
||||
use Illuminate\Broadcasting\PrivateChannel;
|
||||
use Illuminate\Contracts\Broadcasting\ShouldBroadcast;
|
||||
use Illuminate\Foundation\Events\Dispatchable;
|
||||
use Illuminate\Queue\SerializesModels;
|
||||
|
||||
class Broadcast implements ShouldBroadcast
|
||||
{
|
||||
use Dispatchable, InteractsWithSockets, SerializesModels;
|
||||
|
||||
public function __construct(public string $type, public array $data)
|
||||
{
|
||||
}
|
||||
|
||||
public function broadcastOn(): array
|
||||
{
|
||||
return [
|
||||
new PrivateChannel('app'),
|
||||
];
|
||||
}
|
||||
}
|
10
app/Exceptions/CannotDeployKey.php
Executable file
10
app/Exceptions/CannotDeployKey.php
Executable file
@ -0,0 +1,10 @@
|
||||
<?php
|
||||
|
||||
namespace App\Exceptions;
|
||||
|
||||
use Exception;
|
||||
|
||||
class CannotDeployKey extends Exception
|
||||
{
|
||||
//
|
||||
}
|
10
app/Exceptions/ComposerInstallFailed.php
Normal file
10
app/Exceptions/ComposerInstallFailed.php
Normal file
@ -0,0 +1,10 @@
|
||||
<?php
|
||||
|
||||
namespace App\Exceptions;
|
||||
|
||||
use Exception;
|
||||
|
||||
class ComposerInstallFailed extends Exception
|
||||
{
|
||||
//
|
||||
}
|
10
app/Exceptions/CouldNotConnectToProvider.php
Normal file
10
app/Exceptions/CouldNotConnectToProvider.php
Normal file
@ -0,0 +1,10 @@
|
||||
<?php
|
||||
|
||||
namespace App\Exceptions;
|
||||
|
||||
use Exception;
|
||||
|
||||
class CouldNotConnectToProvider extends Exception
|
||||
{
|
||||
//
|
||||
}
|
10
app/Exceptions/ErrorUpdatingRedirects.php
Normal file
10
app/Exceptions/ErrorUpdatingRedirects.php
Normal file
@ -0,0 +1,10 @@
|
||||
<?php
|
||||
|
||||
namespace App\Exceptions;
|
||||
|
||||
use Exception;
|
||||
|
||||
class ErrorUpdatingRedirects extends Exception
|
||||
{
|
||||
//
|
||||
}
|
10
app/Exceptions/FailedToDeleteServer.php
Normal file
10
app/Exceptions/FailedToDeleteServer.php
Normal file
@ -0,0 +1,10 @@
|
||||
<?php
|
||||
|
||||
namespace App\Exceptions;
|
||||
|
||||
use Exception;
|
||||
|
||||
class FailedToDeleteServer extends Exception
|
||||
{
|
||||
//
|
||||
}
|
10
app/Exceptions/FailedToDeployGitHook.php
Normal file
10
app/Exceptions/FailedToDeployGitHook.php
Normal file
@ -0,0 +1,10 @@
|
||||
<?php
|
||||
|
||||
namespace App\Exceptions;
|
||||
|
||||
use Exception;
|
||||
|
||||
class FailedToDeployGitHook extends Exception
|
||||
{
|
||||
//
|
||||
}
|
10
app/Exceptions/FailedToDestroyGitHook.php
Normal file
10
app/Exceptions/FailedToDestroyGitHook.php
Normal file
@ -0,0 +1,10 @@
|
||||
<?php
|
||||
|
||||
namespace App\Exceptions;
|
||||
|
||||
use Exception;
|
||||
|
||||
class FailedToDestroyGitHook extends Exception
|
||||
{
|
||||
//
|
||||
}
|
10
app/Exceptions/FailedToInstallWordpress.php
Normal file
10
app/Exceptions/FailedToInstallWordpress.php
Normal file
@ -0,0 +1,10 @@
|
||||
<?php
|
||||
|
||||
namespace App\Exceptions;
|
||||
|
||||
use Exception;
|
||||
|
||||
class FailedToInstallWordpress extends Exception
|
||||
{
|
||||
//
|
||||
}
|
10
app/Exceptions/GitRepositoryNotFound.php
Executable file
10
app/Exceptions/GitRepositoryNotFound.php
Executable file
@ -0,0 +1,10 @@
|
||||
<?php
|
||||
|
||||
namespace App\Exceptions;
|
||||
|
||||
use Exception;
|
||||
|
||||
class GitRepositoryNotFound extends Exception
|
||||
{
|
||||
//
|
||||
}
|
48
app/Exceptions/Handler.php
Normal file
48
app/Exceptions/Handler.php
Normal file
@ -0,0 +1,48 @@
|
||||
<?php
|
||||
|
||||
namespace App\Exceptions;
|
||||
|
||||
use Illuminate\Foundation\Exceptions\Handler as ExceptionHandler;
|
||||
use Throwable;
|
||||
|
||||
class Handler extends ExceptionHandler
|
||||
{
|
||||
/**
|
||||
* A list of exception types with their corresponding custom log levels.
|
||||
*
|
||||
* @var array<class-string<\Throwable>, \Psr\Log\LogLevel::*>
|
||||
*/
|
||||
protected $levels = [
|
||||
//
|
||||
];
|
||||
|
||||
/**
|
||||
* A list of the exception types that are not reported.
|
||||
*
|
||||
* @var array<int, class-string<\Throwable>>
|
||||
*/
|
||||
protected $dontReport = [
|
||||
//
|
||||
];
|
||||
|
||||
/**
|
||||
* A list of the inputs that are never flashed to the session on validation exceptions.
|
||||
*
|
||||
* @var array<int, string>
|
||||
*/
|
||||
protected $dontFlash = [
|
||||
'current_password',
|
||||
'password',
|
||||
'password_confirmation',
|
||||
];
|
||||
|
||||
/**
|
||||
* Register the exception handling callbacks for the application.
|
||||
*/
|
||||
public function register(): void
|
||||
{
|
||||
$this->reportable(function (Throwable $e) {
|
||||
//
|
||||
});
|
||||
}
|
||||
}
|
10
app/Exceptions/InstallationFailed.php
Normal file
10
app/Exceptions/InstallationFailed.php
Normal file
@ -0,0 +1,10 @@
|
||||
<?php
|
||||
|
||||
namespace App\Exceptions;
|
||||
|
||||
use Exception;
|
||||
|
||||
class InstallationFailed extends Exception
|
||||
{
|
||||
//
|
||||
}
|
10
app/Exceptions/ProcessFailed.php
Normal file
10
app/Exceptions/ProcessFailed.php
Normal file
@ -0,0 +1,10 @@
|
||||
<?php
|
||||
|
||||
namespace App\Exceptions;
|
||||
|
||||
use Exception;
|
||||
|
||||
class ProcessFailed extends Exception
|
||||
{
|
||||
//
|
||||
}
|
10
app/Exceptions/RepositoryNotFound.php
Normal file
10
app/Exceptions/RepositoryNotFound.php
Normal file
@ -0,0 +1,10 @@
|
||||
<?php
|
||||
|
||||
namespace App\Exceptions;
|
||||
|
||||
use Exception;
|
||||
|
||||
class RepositoryNotFound extends Exception
|
||||
{
|
||||
//
|
||||
}
|
10
app/Exceptions/RepositoryPermissionDenied.php
Normal file
10
app/Exceptions/RepositoryPermissionDenied.php
Normal file
@ -0,0 +1,10 @@
|
||||
<?php
|
||||
|
||||
namespace App\Exceptions;
|
||||
|
||||
use Exception;
|
||||
|
||||
class RepositoryPermissionDenied extends Exception
|
||||
{
|
||||
//
|
||||
}
|
10
app/Exceptions/SSHAuthenticationError.php
Executable file
10
app/Exceptions/SSHAuthenticationError.php
Executable file
@ -0,0 +1,10 @@
|
||||
<?php
|
||||
|
||||
namespace App\Exceptions;
|
||||
|
||||
use Exception;
|
||||
|
||||
class SSHAuthenticationError extends Exception
|
||||
{
|
||||
//
|
||||
}
|
10
app/Exceptions/SSHConnectionError.php
Executable file
10
app/Exceptions/SSHConnectionError.php
Executable file
@ -0,0 +1,10 @@
|
||||
<?php
|
||||
|
||||
namespace App\Exceptions;
|
||||
|
||||
use Exception;
|
||||
|
||||
class SSHConnectionError extends Exception
|
||||
{
|
||||
//
|
||||
}
|
10
app/Exceptions/SSLCreationException.php
Normal file
10
app/Exceptions/SSLCreationException.php
Normal file
@ -0,0 +1,10 @@
|
||||
<?php
|
||||
|
||||
namespace App\Exceptions;
|
||||
|
||||
use Exception;
|
||||
|
||||
class SSLCreationException extends Exception
|
||||
{
|
||||
//
|
||||
}
|
Some files were not shown because too many files have changed in this diff Show More
Loading…
x
Reference in New Issue
Block a user