<?phpnamespaceDatabase\Factories;useApp\Models\User;useIlluminate\Database\Eloquent\Factories\Factory;useIlluminate\Support\Str;classUserFactoryextendsFactory{/**
* The name of the factory's corresponding model.
*
* @var string
*/protected$model=User::class;/**
* Define the model's default state.
*
* @return array
*/publicfunctiondefinition(){return['name'=>$this->faker->name,'email'=>$this->faker->unique()->safeEmail,'email_verified_at'=>now(),'password'=>'$2y$10$92IXUNpkjO0rOQ5byMi.Ye4oKoEa3Ro9llC/.og/at2.uheWG/igi',// password
'remember_token'=>Str::random(10),];}}
Empiezo a crealos.
1
2
3
4
5
6
7
8
enrique@enrique-server:/var/www/laravel/blog_laravel$ php artisan make:factory CategoryFactory
Factory created successfully.
enrique@enrique-server:/var/www/laravel/blog_laravel$ php artisan make:factory PostFactory
Factory created successfully.
enrique@enrique-server:/var/www/laravel/blog_laravel$ php artisan make:factory TagFactory
Factory created successfully.
enrique@enrique-server:/var/www/laravel/blog_laravel$ php artisan make:factory ImageFactory
Factory created successfully.
Ahora abro cada uno de los factories creados y los edito. Debo de indicar en cada uno de ellos que campos de la tabla quiero que se llenen y con que tipo de datos.
namespaceDatabase\Factories;useApp\Models\Category;useIlluminate\Database\Eloquent\Factories\Factory;useIlluminate\Support\Str;classCategoryFactoryextendsFactory{/**
* The name of the factory's corresponding model.
*
* @var string
*/protected$model=Category::class;/**
* Define the model's default state.
*
* @return array
*/publicfunctiondefinition(){$name=$this->faker->unique()->word(20);//genera una palabra aleatorioa y única
return['name'=>$name,'slug'=>Str::slug($name)// Uso Str para que me genere el slug de $name
];}}
<?phpnamespaceDatabase\Factories;useApp\Models\Category;useApp\Models\Post;useApp\Models\User;useIlluminate\Database\Eloquent\Factories\Factory;useIlluminate\Support\Str;classPostFactoryextendsFactory{/**
* The name of the factory's corresponding model.
*
* @var string
*/protected$model=Post::class;/**
* Define the model's default state.
*
* @return array
*/publicfunctiondefinition(){$name=$this->faker->unique()->sentence();// Para el titulo del post
return['name'=>$name,'slug'=>Str::slug($name),'extract'=>$this->faker->text(250),//Expecifico que el texto sea de 250 caracteres
'body'=>$this->faker->text(2000),//Expecifico que el texto sea de 250 caracteres
'category_id'=>Category::all()->random()->id,// Llamo al modelo Category, traigo todos los registros, elijo uno al azar y pido su id.
'user_id'=>User::all()->random()->id// Llamo al modelo User, traigo todos los registros, elijo uno al azar y pido su id.
];
namespaceDatabase\Factories;useApp\Models\Tag;useIlluminate\Database\Eloquent\Factories\Factory;useIlluminate\Support\Str;classTagFactoryextendsFactory{/**
* The name of the factory's corresponding model.
*
* @var string
*/protected$model=Tag::class;/**
* Define the model's default state.
*
* @return array
*/publicfunctiondefinition(){$name=$this->faker->unique()->word(20);return['name'=>$name,'slug'=>Str::slug($name),'color'=>$this->faker->randomElement(['red','yellow','green','blue','indigo','purple','pink'])];}}
cuando subimos una imagen al servidor esta se almacena en la carpeta var/www/laravel/blog_laravel/storage/app
1
2
3
4
5
6
enrique@enrique-server:/var/www/laravel/blog_laravel$ ls -la storage/app/
total 16drwxrwsr-x 3 enrique www-data 4096 Dec 8 15:51 .
drwxrwsr-x 5 enrique www-data 4096 Dec 8 15:51 ..
-rw-rw-r-- 1 enrique www-data 23 Dec 8 15:51 .gitignore
drwxrwsr-x 2 enrique www-data 4096 Dec 8 15:51 public
Pero a la única carpeta a la que podemos acceder desde el navegador es a la carpeta public
1
2
3
4
5
6
7
8
9
10
11
12
13
enrique@enrique-server:/var/www/laravel/blog_laravel$ ls -la public/
total 36drwxrwsr-x 4 enrique www-data 4096 Dec 9 22:58 .
drwxrwsr-x 13 enrique www-data 4096 Dec 9 22:57 ..
-rw-rw-r-- 1 enrique www-data 603 Dec 8 15:51 .htaccess
drwxr-sr-x 2 enrique www-data 4096 Dec 9 22:30 css
-rw-rw-r-- 1 enrique www-data 0 Dec 8 15:51 favicon.ico
-rw-rw-r-- 1 enrique www-data 1731 Dec 8 15:51 index.php
drwxrwsr-x 2 enrique www-data 4096 Dec 9 22:58 js
-rw-rw-r-- 1 enrique www-data 71 Dec 9 22:58 mix-manifest.json
-rw-rw-r-- 1 enrique www-data 24 Dec 8 15:51 robots.txt
lrwxrwxrwx 1 enrique www-data 48 Dec 9 22:30 storage -> /var/www/laravel/blog_laravel/storage/app/public
-rw-rw-r-- 1 enrique www-data 1194 Dec 8 15:51 web.config
En esta carpeta public hay un acceso directo a una carpeta llamada storage, pero esta carpeta storage no es la misma que var/www/laravel/blog_laravel/storage/app, sino a /var/www/laravel/blog_laravel/storage/app/public.
Entonces lo que debo lograr es que las imágenes se suban a la carpeta /var/www/laravel/blog_laravel/storage/app/public para conseguirlo voy a la carpeta config y abro el archivo /var/www/laravel/blog_laravel/config/filesystems.php donde cambio el valor de la variable FILESYSTEM_DRIVER de local a public.
filesystems.php
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
<?phpreturn[/*
|--------------------------------------------------------------------------
| Default Filesystem Disk
|--------------------------------------------------------------------------
|
| Here you may specify the default filesystem disk that should be used
| by the framework. The "local" disk, as well as a variety of cloud
| based disks are available to your application. Just store away!
|
*///'default' => env('FILESYSTEM_DRIVER', 'local'),
'default'=>env('FILESYSTEM_DRIVER','public'),
<?phpnamespaceDatabase\Factories;useApp\Models\Image;useIlluminate\Database\Eloquent\Factories\Factory;classImageFactoryextendsFactory{/**
* The name of the factory's corresponding model.
*
* @var string
*/protected$model=Image::class;/**
* Define the model's default state.
*
* @return array
*/publicfunctiondefinition(){return['url'=>'posts/'.$this->faker->image('public/storage/posts',640,480,null,false)//lo almacena en posts/imagen.jpg
];}}
Para que estos factories puedan rellenar la base de datos con valores falsos debo de llamarlos desde databaseSeeders.php
Creo un seeder para meter mis usuarios junto con datos aleatorios creados por el UserFactory.php
1
2
enrique@enrique-server:/var/www/laravel/blog_laravel$ php artisan make:seeder UserSeeder
Seeder created successfully.
<?phpnamespaceDatabase\Seeders;useIlluminate\Database\Seeder;classDatabaseSeederextendsSeeder{/**
* Seed the application's database.
*
* @return void
*/publicfunctionrun(){$this->call(UserSeeder::class);// Llamo al UserSeeder
Category::factory(4)->create();// Para que me cree 4 categorias
Tag::factory(8)->create();// me crea 8 etiquetas
}}
Para crear los posts falsos necesito que me cree a la vez una imagen con cada uno por lo que los voy a crear con u seeder a parte que incluiré después en DaabaseSeeder.php
enrique@enrique-server:/var/www/laravel/blog_laravel$ php artisan make:seeder PostSeeder
Seeder created successfully.
<?phpnamespaceDatabase\Seeders;useApp\Models\Image;useApp\Models\Post;useIlluminate\Database\Seeder;classPostSeederextendsSeeder{/**
* Run the database seeds.
*
* @return void
*/publicfunctionrun(){$posts=Post::factory(100)->create();foreach($postsas$post){// añado una imagen a cada post (como el ImageFactory solo añade la url el resto lo añado aqui)
Image::factory(1)->create(['imageable_id'=>$post->id,'imageable_type'=>Post::class]);// Añado 2 etiquetas a cada post
$post->tags()->attach([// attach() rellena la tabla post_tag
rand(1,4),rand(5,8)]);}}}
<?phpnamespaceDatabase\Seeders;useApp\Models\Category;useApp\Models\Tag;useIlluminate\Database\Seeder;useIlluminate\Support\Facades\Storage;classDatabaseSeederextendsSeeder{/**
* Seed the application's database.
*
* @return void
*/publicfunctionrun(){// \App\Models\User::factory(10)->create();
Storage::deleteDirectory('posts');// Elimina el directorio cada vez que hago un seed
Storage::makeDirectory('posts');$this->call(UserSeeder::class);Category::factory(4)->create();Tag::factory(8)->create();$this->call(PostSeeder::class);}}