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

Can't save meta with factory builder/seeder #27

Open
tmaly1980 opened this issue Jan 26, 2017 · 1 comment
Open

Can't save meta with factory builder/seeder #27

tmaly1980 opened this issue Jan 26, 2017 · 1 comment

Comments

@tmaly1980
Copy link

If I create a table seeder for a table that uses metable, the meta columns don't get translated into key/value pairs on the related table. For example:

In database/factories/ModelFactory.php:

$factory->define(App\Models\Business::class, function (Faker\Generator $faker) {
    return [
        'name' => $faker->company,
        'short_description' => $faker->text(rand(15,60)),
        'description' => $faker->text,
        // Meta
        'address' => $faker->streetAddress, 
        'city' => $faker->city, 
        'state' => $faker->stateAbbr, 
        'zip_code' => $faker->postcode, 

        'facebook_url' => $faker->url,
        'youtube_url' => $faker->url,
        'google_plus_url' => $faker->url,
        'twitter_url' => $faker->url,
    ];
});

If I were to call (via artisan tinker): factory(App\Models\Business::class,10)->create(), I get this error:

Illuminate\Database\QueryException with message 'SQLSTATE[42S22]: Column not found: 1054 Unknown column 'address' in 'field list' (SQL: insert into businesses (name, short_description, description, address, city, state, zip_code, facebook_url, youtube_url, google_plus_url, twitter_url, slug, updated_at, created_at) values (Donnelly Inc, Maxime et et sunt pariatur., Impedit autem voluptas necessitatibus blanditiis aut dolores. Est fugiat sunt quisquam. Cumque aut velit ut inventore., 9658 Hane Crest, Elmorestad, AR, 33942, http://www.wilderman.biz/ea-ullam-molestias-aut-quisquam-aspernatur, http://www.wuckert.org/, http://www.quitzon.net/, http://www.reilly.biz/assumenda-nam-iste-in-ea-laboriosam-dolorem-sapiente-fuga, donnelly-inc, 2017-01-26 16:59:25, 2017-01-26 16:59:25))'

What I have to do instead as a workaround, is setting the meta data into a separate factory definition:

$factory->define(App\Models\BusinessMeta::class, function (Faker\Generator $faker) {
    return [
        // Meta
        'address' => $faker->streetAddress, 
        'city' => $faker->city, 
        'state' => $faker->stateAbbr, 
        'zip_code' => $faker->postcode, 

        'facebook_url' => $faker->url,
        'youtube_url' => $faker->url,
        'google_plus_url' => $faker->url,
        'twitter_url' => $faker->url,
    ];
});

And then calling:

factory(App\Models\Business::class,10)->create()->each(function ($business) { $business->setMeta(factory(App\Models\BusinessMeta::class)->make()->toArray()); $business->save(); });

If there's a way to make a direct call to factory()->create() work without the each(), it would make things simpler.

@eithed
Copy link

eithed commented Oct 11, 2017

While I've had the same issue, I don't have separate *Meta classes - I've gotten around doing it this way:

SupplierFactory.php

<?php

use Faker\Generator as Faker;

$factory->define(App\Supplier::class, function (Faker $faker) {
	return [
    	'first_name' => $faker->firstName,
        'last_name' => $faker->lastName,
        'email' => $faker->safeEmail,
        'password' => $faker->password,
        'telephone' => $faker->optional(0.5)->phoneNumber,
        'postcode' => $faker->optional(0.5)->postcode,
        'is_active' => 1,
    ];
});

SuppliersTableSeeder.php

<?php

use Illuminate\Database\Seeder;

class SuppliersTableSeeder extends Seeder
{
    /**
     * Run the database seeds.
     *
     * @return void
     */
    public function run()
    {
    	factory(App\Supplier::class, 50)->create()->each(function ($supplier) { 
    		$faker = Faker\Factory::create();

    		$company = $faker->company;

    		$supplier->setMeta([
		    	'short_name' => $company,
		        'long_name' => $company.' '.$faker->companySuffix
		    ]);

    		$supplier->save(); 
    	});
    }
}

As you can see, saving of metadata can't be done in the same step as creating given Model, but instead we have to utilize setMeta function and update the Model we have created.

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

2 participants