Skip to content

Commit

Permalink
Merge pull request #194 from OpenSynergic/192-upgrade-commands
Browse files Browse the repository at this point in the history
192 upgrade commands
  • Loading branch information
rahmanramsi authored Jan 20, 2024
2 parents 1afbbca + aefd3dc commit 3134bcf
Show file tree
Hide file tree
Showing 27 changed files with 1,031 additions and 278 deletions.
43 changes: 18 additions & 25 deletions .env.example
Original file line number Diff line number Diff line change
@@ -1,46 +1,39 @@
APP_ENV=local
APP_KEY=
APP_DEBUG=true
APP_URL=http://localhost

# Application
APP_ENV=production
APP_KEY=base64:yv7ba7W38mH8WC06OAWcokwKhfyaiNR4ranj0gWS7aw=
APP_DEBUG=false
APP_URL=http://leconfe.com
APP_TIMEZONE=Asia/Makassar

# Log
LOG_CHANNEL=stack
LOG_DEPRECATIONS_CHANNEL=null
LOG_LEVEL=debug

# Database
DB_CONNECTION=mysql
DB_HOST=127.0.0.1
DB_PORT=3306
DB_DATABASE=conf
DB_USERNAME=root
DB_PASSWORD=
DB_DATABASE=leconfe
DB_USERNAME=leconfe
DB_PASSWORD=leconfe

# Driver
BROADCAST_DRIVER=log
CACHE_DRIVER=file
FILESYSTEM_DISK=local
QUEUE_CONNECTION=sync
SESSION_DRIVER=file
SESSION_LIFETIME=120

MEMCACHED_HOST=127.0.0.1

# Redis
REDIS_HOST=127.0.0.1
REDIS_PASSWORD=null
REDIS_PORT=6379

MAIL_MAILER=smtp
MAIL_HOST=mailpit
MAIL_PORT=1025
MAIL_USERNAME=null
MAIL_PASSWORD=null
MAIL_ENCRYPTION=null
MAIL_FROM_ADDRESS="[email protected]"
MAIL_FROM_NAME="${APP_NAME}"





# Files
MAX_FILE_UPLOAD_SIZE = 5
ACCEPTED_FILE_TYPES = 'image/*,.pdf,.doc,.docx,.zip,.xls,xlsx,.odt,.txt,.xml'
MAX_FILE_UPLOAD_SIZE=5
ACCEPTED_FILE_TYPES='image/*,.pdf,.doc,.docx,.zip,.xls,xlsx,.odt,.txt,.xml'

# Scheduler
CLEANER_SCHEDULER=30
31 changes: 31 additions & 0 deletions app/Actions/Leconfe/CheckVersionAction.php
Original file line number Diff line number Diff line change
@@ -0,0 +1,31 @@
<?php

namespace App\Actions\Leconfe;

use Illuminate\Console\Command;
use Lorisleiva\Actions\Concerns\AsAction;

class CheckVersionAction
{
use AsAction;

public function handle()
{
return app()->getInstalledVersion();
}

public function asCommand(Command $command): void
{
$command->info('Leconfe version: ' . $this->handle());
}

public function getCommandSignature(): string
{
return 'leconfe:check';
}

public function getCommandDescription(): string
{
return 'Check leconfe version';
}
}
58 changes: 58 additions & 0 deletions app/Actions/Leconfe/GetUpgradeActionHistory.php
Original file line number Diff line number Diff line change
@@ -0,0 +1,58 @@
<?php

namespace App\Actions\Leconfe;

use Carbon\CarbonInterval;
use Illuminate\Console\Command;
use Illuminate\Database\Eloquent\Collection;
use Lorisleiva\Actions\Concerns\AsAction;
use Lorisleiva\Actions\Concerns\AsCommand;
use Spatie\Activitylog\Models\Activity;

use function Laravel\Prompts\spin;

class GetUpgradeActionHistory
{
use AsAction;

public function handle() : Collection
{
return Activity::where('log_name', 'leconfe')
->where('event', 'upgrade')
->orderBy('created_at', 'desc')
->get();
}

public function asCommand(Command $command): void
{
$upgradeHistories = spin(fn () => $this->handle(), 'Getting upgrade history');

if($upgradeHistories->isEmpty()) {
$command->info('No upgrade history found');
return;
}

$command->table(
['From', 'To', 'Duration', 'Status', 'Run at'],
$upgradeHistories->map(function ($history) {
return [
$history->getExtraProperty('from'),
$history->getExtraProperty('to'),
CarbonInterval::seconds($history->getExtraProperty('duration')),
$history->getExtraProperty('status'),
$history->created_at,
];
})
);
}

public function getCommandSignature(): string
{
return 'leconfe:upgrade-history';
}

public function getCommandDescription(): string
{
return 'Check leconfe upgrade history';
}
}
189 changes: 189 additions & 0 deletions app/Actions/Leconfe/InstallAction.php
Original file line number Diff line number Diff line change
@@ -0,0 +1,189 @@
<?php

namespace App\Actions\Leconfe;

use App\Utils\PermissionChecker;
use Illuminate\Console\Command;
use Illuminate\Support\Facades\Artisan;
use Illuminate\Support\Facades\Config;
use Illuminate\Support\Facades\DB;
use Jackiedo\Timezonelist\Facades\Timezonelist;
use Lorisleiva\Actions\Concerns\AsAction;

use function Laravel\Prompts\confirm;
use function Laravel\Prompts\error;
use function Laravel\Prompts\info;
use function Laravel\Prompts\password;
use function Laravel\Prompts\search;
use function Laravel\Prompts\select;
use function Laravel\Prompts\spin;
use function Laravel\Prompts\table;
use function Laravel\Prompts\text;

class InstallAction
{
use AsAction;

public function handle(array $params)
{
$upgrade = new \App\Utils\Installer($params);
$upgrade->run();
}

public function asCommand(Command $command): void
{
info('Welcome to leconfe installer.');

$permissionChecker = app(PermissionChecker::class);

$folderPermission = collect($permissionChecker->checkFolders([
'storage/framework/' => 'storage/framework/',
'storage/logs/' => 'storage/logs/',
'storage/app/public/' => 'storage/app/public/',
'bootstrap/cache/' => 'bootstrap/cache/',
]));

info('Checking folder permissions...');

table(
['folder', 'permission'],
$folderPermission->map(fn ($permission, $folder) => [$folder, $permission ? '' : ''])->values()->toArray()
);

// check if folder is not writable
if ($folderPermission->contains(false)) {
error('Some folders are not writable or not exist. Please fix it before continue.');

return;
}

info('Account information');

$data['given_name'] = text('What is your given name?', required: true);
$data['family_name'] = text('What is your family name?', required: true);
$data['email'] = text(
label: 'What is your email?',
required: true,
validate: fn (string $value) => filter_var($value, FILTER_VALIDATE_EMAIL) ? null : 'Please enter a valid email address.'
);

// Keep prompting password until a valid match is entered
while (true) {
$password = password('What is your password?');
if(!$password){
break;
}

$password_confirmation = password('Please confirm your password?', required: true);
// Compare password
if ($password === $password_confirmation) {
// Passwords match, break out of the loop
$data['password'] = $password;
break;
} else {
error('Password confirmation does not match.');
}
}

info('Timezone information');
info('The timezone that application gonna use.');
$timezones = collect(Timezonelist::splitGroup(false)->toArray(false));
$data['timezone'] = search(
label: 'Select timezone',
options: fn (string $value) => strlen($value) > 0
? $timezones->filter(fn ($timezone) => str_contains(strtolower($timezone), strtolower($value)))->toArray()
: $timezones->toArray(),
placeholder: 'Asia/Makassar',
required: true
);

info('Database information');

while (true) {
$data['db_connection'] = 'mysql';
$data['db_username'] = text('What is your database username?', required: true);
$data['db_password'] = password('What is your database password?', required: true);
$data['db_name'] = text('What is your database name?', default: 'leconfe', required: true);
$data['db_host'] = text('What is your database host?', default: '127.0.0.1', required: true);
$data['db_port'] = text('What is your database port?', default: '3306', required: true);

try {
spin(fn() => $this->reconnectDbWithNewData($data),'Testing database connection...');

info('Database connection success.');

break;
} catch (\Throwable $th) {
error('Cannot connect to database with provided information. Please check again.');
error($th->getMessage());
}
}

info('Create your first conference.');
$data['conference_name'] = text('What is your conference name?', required: true);
$data['conference_type'] = select('What is your conference type?', \App\Models\Enums\ConferenceType::array(), default: 'Offline', required: true);
$data['conference_description'] = text('What is your conference description?', required: false);


info('Please review your information before continue.');
table(
['key', 'value'],
collect($data)->map(fn ($value, $key) => [$key, $value])->toArray()
);

if (!confirm('Are you sure to continue?')) {
return;
}

try {

spin(
fn () => (new \App\Utils\Installer($data, $command))->run(),
'Installing application...'
);
} catch (\Throwable $th) {
throw $th;
}


info('Application installed.');
}

private function prepareDatabaseConnection($data): array
{
$connectionArray = config("database.connections.mysql", []);

return array_merge($connectionArray, [
'driver' => $data['db_connection'],
'database' => $data['db_name'],
'host' => $data['db_host'],
'port' => $data['db_port'],
'username' => $data['db_username'],
'password' => $data['db_password'],
]);
}

protected function reconnectDbWithNewData($data)
{
$connectionArray = $this->prepareDatabaseConnection($data);

Config::set("database.connections.mysql", $connectionArray);

DB::purge();

// reconnect to database with new settings
DB::reconnect();

DB::connection()->getPdo();
}

public function getCommandSignature(): string
{
return 'leconfe:install';
}

public function getCommandDescription(): string
{
return 'Install leconfe application';
}
}
Loading

0 comments on commit 3134bcf

Please sign in to comment.