در حال بارگذاری ...

Introducing Closure Commands0:00

Okay, next up with Laravel 5.3 is closure-based commands. So let me show you what I mean. If we go to our new routes file, yes, we have web for the web routes, yes, we have api, but now what the heck is this console file? And it looks a lot like our routes file, doesn't it? artisan command, and this is sort of like the route, or really what you would call from the command line. And then we have a closure that handles it. Now your first question is probably, well, does this replace the old class-based commands? And the answer is no, you will still find those within app/Console right here.

Class Commands Still Exist0:27

Now your first question is probably, well, does this replace the old class-based commands? And the answer is no, you will still find those within app/Console right here. Now notice the commands directory is not there, but once again, like your listeners, like your policies, it will be created on demand. So I can still say php artisan make:command, and maybe we have some kind of pivot table generator command or something like that, where you call the command and it whips up a migration for pivot table. I don't know, just a quick example. Anyways, yes, you will still see this file just like you saw in the past. However, what you may find is that often you have commands that don't really warrant this.

Anyways, yes, you will still see this file just like you saw in the past. However, what you may find is that often you have commands that don't really warrant this big class. Sometimes, yeah, if we come back to our console file, something very simple like this will do the job nicely. And also notice, by the way, any command you define here does not need to be registered with the kernel like you have to do traditionally. OK, so let's see. php artisan inspire. OK, it works, and I assume we get a different one each time.

php artisan inspire. OK, it works, and I assume we get a different one each time. Cool. So let's get rid of that, or if you want to take a look at what it's doing, and this is kind of a good practice. So for your commands, as much as you can, obviously sometimes it doesn't matter, but in general, think of your command sort of like the entry point from the console. So just like it sometimes makes sense for a controller to defer to a model or to a service class or something like that, the same is going to be true for your command. So for basic stuff, don't worry about it.

Creating a Closure Command1:55

class or something like that, the same is going to be true for your command. So for basic stuff, don't worry about it. Otherwise, you can defer to a separate class to perform the logic. And in this case, it's literally just a collection of quotes, and it grabs a random one. OK, let's get rid of that entirely, and we're going to make our own command. So let's just say php artisan command, and why don't we have, just to start, we're going to stick with this generator idea. Laravel already has a make command for a model, but maybe you have a special thing that it should do, or something like that. You're building on it.

that it should do, or something like that. You're building on it. OK, so you pass your closure here, and to start, simply by defining it here, well let me show you. If I run php artisan, you will immediately see it show up, if I come back up, right there. So already this is nice. In the past, you had to create the class, you had to set the name, you would then have to go and register the command with a service provider, but now you don't have to do that. However, notice that there's no description here. You can set that here.

Adding Descriptions and Arguments2:53

However, notice that there's no description here. You can set that here. So we can say describe generate a special model. OK, so if I run it again, now if we come back to the generate, yeah, there's our description. But if I say php artisan help generate:model, OK, so we have the usage, but what if it accepts an argument, like the name of the model? OK, well we can define that right here, just like with regular console commands. So we could do name, and again, notice how this is sort of like your routes file. With your routes file, you might say get post /post, and the fact that these are similar is not a coincidence.

With your routes file, you might say get /post, and the fact that these are similar is not a coincidence. So that's pretty neat. Anyways, if we run it again, now we can see that this accepts an argument. And of course, you can still do things like this, where you say the name is the name of the model to generate. And now you'll see that referenced here, or you can leave it off. Once again, for more complex commands, I think it's still useful to create a full class. But just for the small things where maybe your scheduler is hitting it, and you don't want to worry about any of this junk, this is good to know.

Generating Files from Command4:00

But just for the small things where maybe your scheduler is hitting it, and you don't want to worry about any of this junk, this is good to know. So now here, yeah, we could just very quickly exec touch, and then the name argument that would be passed in. OK, so if we run it, php artisan generate:model, it's failing because I didn't give it a name. We'll call it post. And now if we come back, it did create a post file, but we forgot the extension. You know, this is a very, very simplistic example. Anyways, we run it again, and now we get our Post model that's empty in this case. But you can generate it, you can add a template, or of course, just use Laravel's make:model.

Anyways, we run it again, and now we get our Post model that's empty in this case. But you can generate it, you can add a template, or of course, just use php artisan make:model command. But maybe you want to generate or make a file that Laravel doesn't include. Well, you could define your own here. And by the way, you can always use Laravel's File facade or the FileSystem class. So we could say like the model will be this argument name. And then we'll just say file_put_contents to app/name.php. And then, you know, whatever it needs to be. And I named that model, didn't I?

And then, you know, whatever it needs to be. And I named that model, didn't I? Anyways, we run that again. And once again, we get our Post model. And this can be any template you want. You could even have a stubs file. So you'd have like app templates for a model, class, the name of the model, something like that. Maybe you want to override the save method or something like that. So you're going to include that with your template.

Maybe you want to override the save method or something like that. So you're going to include that with your template. Okay, so you have your template, we can actually rename that to model.txt. And then you could say $template equals file_get_contents('templates/model.txt'). And then str_replace, look for the 'name', this is very simplistic, but replace it with the $model using the $template. That will be the compiled version. And then we will save or put the compiled version to the file they want to generate. Okay, so one more time, delete that. We run it again, file does not exist.

Okay, so one more time, delete that. We run it again, file does not exist. And that's because we need app. Run it again. Now we get Post and we have compiled our little model template down. Now, like I said, for little simple things like this, yeah, it just doesn't matter. You don't always have to extract extract if you're never going to edit this again. Just five or 10 lines of code there is exactly what the doctor ordered. But if you're going to have more than one generator, yeah, this is when you might want to use the automatic resolution.

Refactoring to Generator Class6:28

But if you're going to have more than one generator, yeah, this is when you might want to use the automatic resolution. So you might have a app generator, or maybe a model generator. And then yeah, you would do something like generator build for the argument, given the name. And then yeah, that would be responsible for this stuff. And then you can just do something like that. And then finally, when you're done, you can still use any of the methods that you could do traditionally, info, all done. And then get rid of this because the file doesn't exist.

do traditionally, info, all done. And then get rid of this because the file doesn't exist. Run it again, and you get the basic idea. So yeah, that's all you need to know. This is a simple entry point for defining artisan commands. If it's very simplistic, this is a cool way to go about it. If you do need more flexibility, or you're just adding lots of descriptions and options and it's starting to get clunky, yeah, that's the point when you would defer to make commands like you did in Laravel 5.2 and below.

دوست دارید گاهی خبرهای Laracasts را ایمیل کنیم؟