Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Use with Laravel's schema:dump command #28

Closed
binotaliu opened this issue Feb 1, 2021 · 8 comments
Closed

Use with Laravel's schema:dump command #28

binotaliu opened this issue Feb 1, 2021 · 8 comments

Comments

@binotaliu
Copy link

Currently, Laravel's schema:dump artisan command only dumps database structure (except migrations table). If there are any settings migration, it won't be included in the dump file.

How to reproduce:

  1. Create a settings migration using make:settings-migration
  2. Run schema:dump
  3. Run migrate:fresh
  4. Check the output of migrate:status. The settings migration we created in step 1 is marked as ran, but the data it created will not be included in the database.
@rubenvanassche
Copy link
Member

Hi @binotaliu,

This is indeed a bug, the problem is that Laravel dumps the schema of your database + the data in your migrations table. In this case we'll also want the data within the settings table dumped.

There are a few solutions to this problem, though I'm not sure what's the right one

  1. Pr to Laravel the ability to dump the data of other tables then the migrations table
  2. Listen to the SchemaDumped event and remove all the settings migrations in the migrations table sql dump
  3. Listen to the SchemaDumped event and add the current data of the settings table at the end of the sql dump
    -> this one is quite difficult since we need to write our own dumpers for each database type(mysql, sqlite, ...)

I'm not quite sure what could be the best solution ....

@brendt
Copy link

brendt commented Feb 3, 2021

I would first try to discuss adding this functionality in Laravel before looking into workarounds in the package.

@rubenvanassche
Copy link
Member

Looks like someone already tried this:

laravel/framework#32352

The SchemaLoaded is interesting though, if we can run our migrations again at that point.

@binotaliu
Copy link
Author

Maybe we can just delete them from migrations table on SchemaLoaded event? There is a delete method on DatabaseMigrationRepository:

https://github.com/laravel/framework/blob/7fd4510377ae7a7aa9806d1e9190abbe522246c3/src/Illuminate/Database/Migrations/DatabaseMigrationRepository.php#L116-L119

@rubenvanassche
Copy link
Member

This was a funny problem, normally v1.0.6 should fix the problem!

@plakhin
Copy link

plakhin commented Sep 2, 2022

@rubenvanassche
I'm still experiencing this problem on v2.4.3.
Laravel v9.26.1
I'm using archtechx/tenancy package, multi-database tenancy.
Once I run php artisan tenants:run schema:dump the database/schema/tenant-schema.dump file is being generated, but then I have to manually remove all settings-related migrations this file.
What may be the reason?

The rest works pretty well, but I had to adjust configs (tenancy package and settings package) regarding file paths, don't exactly remember since that was might be a year ago, however I only put some values there, didn't change anything and didn't make any patches/workarounds/extensions.

@rubenvanassche
Copy link
Member

This is probably due to something the tenancy package, you probably should trigger this code:

$files = Finder::create()
->files()
->ignoreDotFiles(true)
->in($this->resolveMigrationPaths())
->depth(0);
$migrations = collect(iterator_to_array($files))
->mapWithKeys(function (SplFileInfo $file) {
preg_match('/class\s*(\w*)\s*extends/', file_get_contents($file->getRealPath()), $found);
if (empty($found)) {
return null;
}
require_once $file->getRealPath();
return [$file->getBasename('.php') => $found[1]];
})
->filter(fn (string $migrationClass) => is_subclass_of($migrationClass, SettingsMigration::class))
->keys();
$event->connection
->table(config()->get('database.migrations'))
->useWritePdo()
->whereIn('migration', $migrations)
->delete();

somehow for every tenant.

@plakhin
Copy link

plakhin commented Sep 29, 2022

This is probably due to something the tenancy package, you probably should trigger this code:

$files = Finder::create()
->files()
->ignoreDotFiles(true)
->in($this->resolveMigrationPaths())
->depth(0);
$migrations = collect(iterator_to_array($files))
->mapWithKeys(function (SplFileInfo $file) {
preg_match('/class\s*(\w*)\s*extends/', file_get_contents($file->getRealPath()), $found);
if (empty($found)) {
return null;
}
require_once $file->getRealPath();
return [$file->getBasename('.php') => $found[1]];
})
->filter(fn (string $migrationClass) => is_subclass_of($migrationClass, SettingsMigration::class))
->keys();
$event->connection
->table(config()->get('database.migrations'))
->useWritePdo()
->whereIn('migration', $migrations)
->delete();

somehow for every tenant.

Thanks for the response!
There's no need to trigger the code for every tenant since all the tenants has the same migrations, so this should be triggered only once per central context and once per tenant context. And I'm doing exactly this.
I will try to figure out if the code is being triggered. I think the problem may be in paths/filenames as after running schema:dump in central context I'm getting mysql-schema.dump and after running in tenant context, I'm getting tenant-schema.dump files.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

No branches or pull requests

4 participants