As a web framework, the main work of Laravel is to accept a Request then to send a Response.
Take look at the public/index.php of a Laravel project:
The process is simple, they make a kernel, capture the request, then handle the request with the kernel so get a response, and send the response.
As you see, all miraculous magics are in the box of $kernel->handle(). But what is the $kernel? We can find where it from.
So, the $kernel is the singleton of class App\Http\Kernel.
Let's check the class. Aha, you will find that here is where we manage our middlewares.
But there is no handle(), we need search at the parent class Illuminate\Foundation\Http\Kernel.
Here we are:
Let's just skip noises and focus on the main line:
Let's jump to sendRequestThroughRouter() and focus on:
There is a magician named Pipeline.
Do not get acquaintance with her too deep at this time, just look on what she does:
sending the $request through the global middlewares then dispatching with router.
In router, we expectedly find that:
With the route we find, another pipeline is here.
In this pipeline, the request is sent through middlewares with the route to the controller. A response will be created with the result of controller.
But this is only half of effects of middlewares. A typical middleware is like this:
In a middleware, we can process not only request, but also response. The full process is like this:
This structure gives middleware ability to block the request into next level and respond directly. And the middlewares of upper levels will still work well.
Exception Handling
When a exception or error is thrown, the response cannot create successfully.
Let's go back where we've caught a sight of try-catch: Illuminate\Foundation\Http\Kernel::handle().
As we see, the exception or error will be caught at the top level, out of all middlewares.
And an Exception Handler will render it into a response.
That means, on the positive hand, exception or error from middlewares can be caught,
but on the negative hand, when an exception or error thrown, what we act on response in middlewares will not work anymore.
For example, your middleware cannot add Access-Control-Allow-Origin to your exception responses.
A good practice is add a global handler middleware between common middlewares and business middlewares to handle exceptions or errors.
So your exception response will not miss your global middlewares.
As the example, you can find file app/Http/Middleware/Handler.php in this repository. The main code is just like what in the kernel:
Don't forget to register it in the App\Http\Kernel:
Summing up
So far, we've learned how Laravel handle a HTTP request and respond a response. We've met several friends: HTTP Kernel, Pipeline, Router and Middleware. What I can do is just introducing.For digging deeper, you can read the source codes of Laravel. Good Luck!