fix(db): null-safe unique keys on rollup tables, workspace slug unique, link slug scoping
Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>main
parent
23fd5a5e30
commit
3b19bbe88f
|
|
@ -12,7 +12,7 @@ return new class extends Migration
|
|||
$table->id();
|
||||
$table->string('ulid', 26)->unique();
|
||||
$table->string('name');
|
||||
$table->string('slug', 64);
|
||||
$table->string('slug', 64)->unique();
|
||||
$table->foreignId('owner_id')->constrained('users')->cascadeOnDelete();
|
||||
$table->foreignId('plan_id')->nullable()->constrained('plans')->nullOnDelete();
|
||||
$table->timestamp('trial_ends_at')->nullable();
|
||||
|
|
|
|||
|
|
@ -18,6 +18,7 @@ return new class extends Migration
|
|||
$table->timestamp('expires_at');
|
||||
$table->timestamp('accepted_at')->nullable();
|
||||
$table->timestamps();
|
||||
$table->index(['workspace_id', 'email']);
|
||||
});
|
||||
}
|
||||
|
||||
|
|
|
|||
|
|
@ -29,7 +29,7 @@ return new class extends Migration
|
|||
$table->foreignId('updated_by')->nullable()->constrained('users')->nullOnDelete();
|
||||
$table->softDeletes();
|
||||
$table->timestamps();
|
||||
$table->unique(['domain_id', 'slug']);
|
||||
$table->unique(['workspace_id', 'domain_id', 'slug'], 'links_workspace_domain_slug_unique');
|
||||
$table->index('workspace_id');
|
||||
$table->index('status');
|
||||
});
|
||||
|
|
|
|||
|
|
@ -21,7 +21,7 @@ return new class extends Migration
|
|||
$table->boolean('is_published')->default(false);
|
||||
$table->softDeletes();
|
||||
$table->timestamps();
|
||||
$table->unique(['domain_id', 'slug']);
|
||||
$table->unique(['workspace_id', 'domain_id', 'slug'], 'bio_pages_workspace_domain_slug_unique');
|
||||
$table->index('workspace_id');
|
||||
});
|
||||
}
|
||||
|
|
|
|||
|
|
@ -12,8 +12,8 @@ return new class extends Migration
|
|||
$table->id();
|
||||
$table->foreignId('link_id')->constrained()->cascadeOnDelete();
|
||||
$table->timestamp('hour');
|
||||
$table->string('country', 2)->nullable();
|
||||
$table->enum('device', ['desktop', 'mobile', 'tablet', 'bot', 'unknown'])->nullable();
|
||||
$table->string('country', 2)->default('');
|
||||
$table->enum('device', ['desktop', 'mobile', 'tablet', 'bot', 'unknown'])->default('unknown');
|
||||
$table->unsignedBigInteger('count')->default(0);
|
||||
$table->unsignedBigInteger('unique_visitors')->default(0);
|
||||
$table->unique(['link_id', 'hour', 'country', 'device']);
|
||||
|
|
|
|||
|
|
@ -12,8 +12,8 @@ return new class extends Migration
|
|||
$table->id();
|
||||
$table->foreignId('link_id')->constrained()->cascadeOnDelete();
|
||||
$table->date('day');
|
||||
$table->string('country', 2)->nullable();
|
||||
$table->enum('device', ['desktop', 'mobile', 'tablet', 'bot', 'unknown'])->nullable();
|
||||
$table->string('country', 2)->default('');
|
||||
$table->enum('device', ['desktop', 'mobile', 'tablet', 'bot', 'unknown'])->default('unknown');
|
||||
$table->unsignedBigInteger('count')->default(0);
|
||||
$table->unsignedBigInteger('unique_visitors')->default(0);
|
||||
$table->unique(['link_id', 'day', 'country', 'device']);
|
||||
|
|
|
|||
|
|
@ -12,7 +12,7 @@ return new class extends Migration
|
|||
$table->id();
|
||||
$table->foreignId('link_id')->constrained()->cascadeOnDelete();
|
||||
$table->date('day');
|
||||
$table->string('referrer_host', 253)->nullable();
|
||||
$table->string('referrer_host', 191)->default('');
|
||||
$table->unsignedBigInteger('count')->default(0);
|
||||
$table->unique(['link_id', 'day', 'referrer_host']);
|
||||
$table->index(['link_id', 'day']);
|
||||
|
|
|
|||
|
|
@ -12,9 +12,9 @@ return new class extends Migration
|
|||
$table->id();
|
||||
$table->foreignId('link_id')->constrained()->cascadeOnDelete();
|
||||
$table->date('day');
|
||||
$table->string('utm_source', 128)->nullable();
|
||||
$table->string('utm_medium', 128)->nullable();
|
||||
$table->string('utm_campaign', 128)->nullable();
|
||||
$table->string('utm_source', 128)->default('');
|
||||
$table->string('utm_medium', 128)->default('');
|
||||
$table->string('utm_campaign', 128)->default('');
|
||||
$table->unsignedBigInteger('count')->default(0);
|
||||
$table->unique(['link_id', 'day', 'utm_source', 'utm_medium', 'utm_campaign'], 'clicks_by_utm_unique');
|
||||
$table->index(['link_id', 'day']);
|
||||
|
|
|
|||
|
|
@ -12,7 +12,7 @@ return new class extends Migration
|
|||
$table->id();
|
||||
$table->foreignId('webhook_id')->constrained()->cascadeOnDelete();
|
||||
$table->string('event', 64);
|
||||
$table->text('payload');
|
||||
$table->json('payload');
|
||||
$table->enum('status', ['success', 'failed', 'pending'])->default('pending');
|
||||
$table->unsignedSmallInteger('response_code')->nullable();
|
||||
$table->unsignedTinyInteger('attempts')->default(1);
|
||||
|
|
|
|||
Loading…
Reference in New Issue