Skip to content

Commit 771768a

Browse files
update
1 parent 4a4a718 commit 771768a

File tree

2 files changed

+55
-15
lines changed

2 files changed

+55
-15
lines changed

src/Console/Commands/MigrationCommand.php

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -67,7 +67,7 @@ public function refresh()
6767
*/
6868
public function status()
6969
{
70-
echo "[demo] Seeding database...\n";
70+
echo "[demo] status database...\n";
7171
// TODO: call your seeder pipeline here
7272
return 0;
7373
}

src/Migrations/Traits/MigrationTrait.php

Lines changed: 54 additions & 14 deletions
Original file line numberDiff line numberDiff line change
@@ -182,35 +182,75 @@ private static function scanDirectoryFiles($directory)
182182
array_walk($files, function(&$value, $index) use($directory) {
183183
$value = rtrim($directory, '/') . "/{$value}";
184184
});
185+
186+
dd(
187+
self::sortParentFiles($files)
188+
);
185189

186190
return self::sortParentFiles($files);
187191
}
188192

189193
/**
190194
* Sort parent files according to their names
191195
*
196+
* Ensures that base tables (e.g., "ads", "users") are migrated
197+
* before their derivative/child tables (e.g., "ads_data", "users_address", "ads_info").
198+
*
192199
* @param array $files
193-
* @return void
200+
* @return array
194201
*/
195202
private static function sortParentFiles(array $files)
196203
{
197-
// Custom sort: parent tables before child tables
198-
usort($files, function ($a, $b) {
199-
$aName = basename($a);
200-
$bName = basename($b);
201-
202-
// ensure "ads_table" comes before "ads_data_table"
203-
if (preg_match('/create_(\w+)_data_table/', $aName, $am) &&
204-
preg_match('/create_' . $am[1] . '_table/', $bName)) {
205-
return 1; // b before a
204+
// Robust sort: parent tables before child tables of the same base
205+
$parse = function (string $path): array {
206+
$name = basename($path);
207+
// extract between "create_" and "_table"
208+
if (preg_match('/create_(.+)_table\.php$/', $name, $m)) {
209+
$full = $m[1]; // e.g., "ads", "ads_data", "users_address"
210+
$parts = explode('_', $full); // split by underscore
211+
$base = $parts[0]; // the base entity
212+
return [
213+
'name' => $name,
214+
'full' => $full,
215+
'base' => $base,
216+
'parts' => $parts,
217+
'is_parent' => count($parts) === 1,
218+
];
206219
}
220+
// Non-standard name: treat as parent so it runs early
221+
return [
222+
'name' => $name,
223+
'full' => $name,
224+
'base' => $name,
225+
'parts' => [$name],
226+
'is_parent' => true,
227+
];
228+
};
207229

208-
if (preg_match('/create_(\w+)_data_table/', $bName, $bm) &&
209-
preg_match('/create_' . $bm[1] . '_table/', $aName)) {
210-
return -1; // a before b
230+
usort($files, function (string $a, string $b) use ($parse) {
231+
$ai = $parse($a);
232+
$bi = $parse($b);
233+
234+
// Same base entity (e.g., "ads" vs "ads_data", "users" vs "users_address")
235+
if ($ai['base'] === $bi['base']) {
236+
// Parent must come before children
237+
if ($ai['is_parent'] !== $bi['is_parent']) {
238+
return $ai['is_parent'] ? -1 : 1;
239+
}
240+
241+
// Both children or both parents:
242+
// fewer segments first (e.g., users_address before users_address_history)
243+
$cmpParts = count($ai['parts']) <=> count($bi['parts']);
244+
if ($cmpParts !== 0) {
245+
return $cmpParts;
246+
}
247+
248+
// then alphabetical by the entity part for stability
249+
return strcmp($ai['full'], $bi['full']);
211250
}
212251

213-
return strcmp($aName, $bName); // fallback alphabetical
252+
// Different bases: keep natural alphabetical (includes timestamp prefix)
253+
return strcmp($ai['name'], $bi['name']);
214254
});
215255

216256
return $files;

0 commit comments

Comments
 (0)