I have a table with unique column, it consists of 8 characters of random English letters and numbers.
I need to be able to seed the table by adding more data to the existing data. I am supposed to enter a given amount of rows. I tried using Factories and Seeders but then realized it's not working as expected:
<?php
namespace App\Models;
use Illuminate\Database\Eloquent\Model;
class Code extends Model
{
protected $table = 'codes';
}
protected $fillable = [
'code',
'is_valid'
];
Factory:
public function definition()
{
return [
'code' => $this->faker->regexify('[A-Z0-9]{8}')
];
}
Then I am supposed to add data by running:
$codes = Code::factory()->count(10000)->create();
and after that, if I run it multiple times I might end up with constraint violation:
// add some more data
$codes = Code::factory()->count(10000)->create();
$codes = Code::factory()->count(10000)->create();
What is an efficient way to be able to add given amount of rows and make sure they're unique?
All other questions I've seen here are similar, but not working for my case.
CodePudding user response:
Change in your factory definition this line from this: 'code' => $this->faker->regexify('[A-Z0-9]{8}')
to: $faker->unique()->regexify('[A-Z0-9]{8}');
.
CodePudding user response:
In your factory you can use the unique() faker modifier : https://fakerphp.github.io/#modifiers
public function definition()
{
return [
'code' => $this->faker->unique()->regexify('[A-Z0-9]{8}')
];
}
Edit: when running the factory with existing data, you can check if the faked data already exists in the database like:
public function definition()
{
do {
$fakeCode = $this->faker->unique()->regexify('[A-Z0-9]{8}');
} while (DB::table('codes')->where('code', $fakeCode)->exists());
return [
'code' => $fakeCode
];
}