Introducing Model Factories0:00
Whenever we talk about tasks, especially model tasks or tasks that involve a model, we also talk about model factories. Model factories provide a convenient way to generate fake data for tasks or for seeders as well, but mostly for tasks. Again, just like tasks, there are a few strategies you can use for model factories, and we're going to talk about them. For this Product model, for example, I've already created a ProductFactory like this. So we have a name, we have a price in cents, and we have the number of items in stock. The default location for factories is under database/factories. So we have a ProductFactory we just created,
Creating Records via Factory0:35
The default location for factories is under database, factories. So we have a ProductFactory we just created, and we also have the UserFactory which ships with Laravel. If we go back to our task, this one, I am going to run it. Okay, we have the test passing. If we were to replace this with a factory, we could do something like product. Now, we can either do productFactory like this. We got imported, obviously. Call the new method, and for example, call create. It's going to create a record on the database.
Fixing Model Namespace1:01
Call the new method, and for example, call create. It's going to create a record on the database. So let's dump and die this. As you can see, it failed. Class App\Product not found. And the reason is factories look by default for the model within App\Models. The first thing we can do is add a model property right here and specify the fully qualified namespace for our model. Cool. Let's rerun this. Still failing.
Cool. Let's rerun this. Still failing. No switch table products. That's because we're not migrating anything on this task. So let's use a database migration straight to run this. Okay, cool. Now, we are seeing the model. We see the Product model. We see the database. We see the connection, all of that. And we also see its properties.
Using Factory from Model1:46
We see the connection, all of that. And we also see its properties. That's the first way to use a factory. The second way is you can call it from within the model. So we can say Product, and this is the model. I'm going to import it. I can say factory, and this is going to return an instance of ProductFactory. And then I call create. So let's run this. As you can see, it failed.
So let's run this. As you can see, it failed. What happens is Laravel automatically tries to find the factory for you. For example, this is the Product model. It usually lives within the app/models directory. We have moved it to modules/product/models. So it's in a different namespace. And Laravel is trying to find it within database/factories and the namespace we added it to. And it's not going to find it.
Overriding newFactory Method2:33
and the namespace we added it to. And it's not going to find it unless we were to move this ProductFactory to this weird namespace. The first way we can solve this is we can go here. Let's jump into our model. And we can add a method called newFactory. If we go to the base method, you can see it tries to find a factory for the model. So if we have the method, it is going to use the method. If we do not have the method,
So if we have the method, it is going to use the method. If we do not have the method, it is going to guess where the factory for that model lives. And that's not what we want. So let's be explicit and return this right here. So we can say new, oops, ProductFactory. And let's add the return type, which is ProductFactory as well. Now, if we rerun this, now we're getting the factory back. And it's working. That's pretty much all we need to do. Now, let's look at the other strategy,
Moving Factories into Module3:25
And it's working. That's pretty much all we need to do. Now, let's look at the other strategy, which is having the factory within the module. If we go to our product module, remember that when we created this database folder, I said put the migrations in its own folder. And that's because we can have other things within database, for example, factories. Let's start by creating a new directory. Let's call it factories.
Let's start by creating a new directory. Let's call it factories. And now I'm going to drag and drop this here. As you can see, PHPStorm already updated the namespace for me. If I go to the task, it should have updated as well. Well, it looks like it didn't. Maybe it's because it's commented out. So let's get rid of this. Let's uncomment this. Let's import this namespace, or rather this class.
Let's uncomment this. Let's import this namespace, or rather this class. Okay, and let's run this. Still working. Let's try to create the factory from the model. So we can say Product, factory, create. Also working. So basically, the gist of it is, if you have your model in a different namespace, you just have to tell Laravel where it is.
if you have your model in a different namespace, you just have to tell Laravel where it is. And that's it. On the factory itself, just make sure to pass the model. And then you can choose. You can either store it within the database folder, or you can store it within the module. In my opinion, if you already went so far as to split your application modules, you might as well put your factories where they belong,
as to split your application modules, you might as well put your factories where they belong, which is within this folder, along with the migrations, close to models, and inside the actual module. And my friends, this is how you can use factories within your modular application. No tricks, pretty simple. You just need to instruct Laravel where to look for things. All right, I hope you enjoyed this lesson,
You just need to instruct Laravel where to look for things. All right, I hope you enjoyed this lesson, and I'll see you guys on the next one. Bye-bye.
