Skip to content
Open
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
88 changes: 88 additions & 0 deletions src/Commands/ChangeDisk.php
Original file line number Diff line number Diff line change
@@ -0,0 +1,88 @@
<?php

namespace Inovector\Mixpost\Commands;

use Illuminate\Console\Command;
use Illuminate\Database\Eloquent\Collection;
use Illuminate\Support\Facades\DB;
use Inovector\Mixpost\Models\Account;
use Inovector\Mixpost\Models\Media;

class ChangeDisk extends Command
{
public $signature = 'mixpost:change-disk {from} {to} {--force}';

public $description = 'Create new mastodon application for a server';

public function handle(): int
{
if (app()->isProduction() && !$this->option('force')) {
$this->fail('The app is in production. Use --force if you are sure.');
}

$from = $this->argument('from');
$to = $this->argument('to');

if (!$from || !$to) {
$this->fail('Please provide both source and target disk names.');
}

try {
DB::transaction(function () use ($from, $to) {
$bar = $this->output->createProgressBar(Media::count() + Account::count());
$bar->start();

Media::chunk(100, function (Collection $medias) use ($bar, $from, $to) {

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

100 is a magic number here. It should be provided as an argument in the command or named explicitly as a parameter.

foreach ($medias as $media) {
//the "disk" in mixpost_media table.,
if ($media->disk == $from) {
$media->disk = $to;
}
//conversions column of mixpost_media table has json stored disks too,
foreach ($media->conversions as $conversion) {
if (isset($conversion['disk']) && $conversion['disk'] == $from) {
$conversion['disk'] = $to;
}
}

if($media->isDirty())
{
$media->save();
}
}

// Advance the bar by the size of the chunked collection
$bar->advance($medias->count());
});

Account::chunk(100, function (Collection $accounts) use ($bar, $from, $to) {
foreach ($accounts as $account) {
//the disk in the media json of the mixpost_accounts table,
if ($account->media['disk'] == $from) {
$account->media['disk'] = $to;
}

if($account->isDirty())
{
$account->save();
}
}

// Advance the bar by the size of the chunked collection
$bar->advance($accounts->count());
});


$bar->finish();
});

$this->info("All media disks updated.");
$this->info("Remember to re-upload your site icons.");
return self::SUCCESS;
} catch (\Throwable $e) {
$this->error($e->getMessage());
return self::FAILURE;
}

}
}
2 changes: 2 additions & 0 deletions src/MixpostServiceProvider.php
Original file line number Diff line number Diff line change
Expand Up @@ -5,6 +5,7 @@
use Illuminate\Contracts\Debug\ExceptionHandler;
use Illuminate\Support\Facades\Event;
use Illuminate\Support\Facades\Gate;
use Inovector\Mixpost\Commands\ChangeDisk;
use Inovector\Mixpost\Commands\ClearServicesCache;
use Inovector\Mixpost\Commands\ClearSettingsCache;
use Inovector\Mixpost\Commands\CreateMastodonApp;
Expand Down Expand Up @@ -52,6 +53,7 @@ public function configurePackage(Package $package): void
ProcessMetrics::class,
DeleteOldData::class,
PruneTemporaryDirectory::class,
ChangeDisk::class,
])->hasInstallCommand(function (InstallCommand $command) {
$command
->startWith(function (InstallCommand $command) {
Expand Down
16 changes: 16 additions & 0 deletions tests/Commands/ChangeDiskTest.php
Original file line number Diff line number Diff line change
@@ -0,0 +1,16 @@
<?php


use Inovector\Mixpost\Models\Media;

it('changes disks', function () {
Media::factory()->count(10)->create();

$this->artisan(\Inovector\Mixpost\Commands\ChangeDisk::class, [
'from' => 'public',
'to' => 's3',
])->assertExitCode(0);

expect(Media::where('disk', 'public')->count())->toBe(0);
expect(Media::where('disk', 's3')->count())->toBe(10);
});