本篇概要:
1. Laravel 路由简介;
1.1 路由介绍;
- Laravel 的路由就是将用户的请求转发给对应的处理函数。它的作用建立 URL 与处理函数之间的映射。
- Laravel 与普通的 PHP 应用不同,普通的 PHP 应用处理用户的请求的基本单位是一个文件,而 Laravel 当中,只需要一个处理函数就能处理一个用户的请求。因此就需要一种机制,将用户的请求与对应的处理函数建立起一个联系,而这种机制就是 Laravel 的路由。
- 路由还可以是实现其它的一些功能,比如参数的传递,或者可以通过路由在请求上绑定中间键进行处理。
1.2 单一请求路由和多请求路由使用;
# **单一请求路由**
# 使用 Route 类的静态方法(get、post 等)
# 此方法有两个参数:第一个参数是 URL,第二个参数是处理函数
# 其它请求类型:get、post、put、patch、delete、options
Route::get('foo', function () {
return 'Hello World';
});
Route::post('foo', function () {
return 'Hello World';
});
# **多请求路由**
# 使用三个参数,后两个参数和单请求路由一样。
# 第一个参数,把要请求的类型以数组的形式传入。
Route::match(['get', 'post'], '/', function () {
//request processing code
});
# 处理所有类型的请求
Route::any('foo', function () {
//request processing code
});
- Laravel 5.3 之前,路由文件的路径是
app/Http/routes.php
- Laravel 5.3 开始,
app/Http/routes.php
文件被移动到routes
目录下,并且被分割成两个文件:web.php 和api.php。 - web.php 中的路由应用了 web 中间件组,而 api.php 中的路由应用了 api 中间件组。
- 实例:打开
routes/web.php
<?php
/*
|--------------------------------------------------------------------------
| Web Routes
|--------------------------------------------------------------------------
|
| Here is where you can register web routes for your application. These
| routes are loaded by the RouteServiceProvider within a group which
| contains the "web" middleware group. Now create something great!
|
*/
// 单一请求路由,处理请求函数返回了一个 view
// view 对应的视图文件路径是 resources/views/welcome.blade.php
Route::get('/', function () {
return view('welcome');
});
// 如果需要传参给 view
// welcome.blade.php 页面添加 {{ msg }} 接收变量
// Route 可以有以下两种写法传参
Route::post('/', function () {
// return view('welcome')->with("msg", "Hello world");
// return view('welcome', ["msg" => "hello world"]);
});
2. 方法欺骗和命名路由;
2.1 方法欺骗;
- 方法欺骗就是通过在 HTML 表单中增加一个字段,填写对应的请求类型(put、delete 等),来通过一个 post 请求模拟这些请求。
- 为什么要进行方法欺骗?在 HTML 当中(在 HTML5 以前), FORM 只支持 GET 和 POST 两种请求,如果要使用 RESTful 的话,就要进行方法欺骗。
- 实例:创建视图文件
resources/views/hello.blade.php
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="utf-8" >
<title>Hello</title>
</head>
<body>
<form method="POST" action="/">
<input type="text" name="msg">
<!-- 在 Laravel 模板里,两个大括号之间可以直接调用 PHP 函数 -->
<!-- 调用 Laravel 自带的方法,参数填写方法欺骗的方法的名称 -->
{{ method_field('PUT')}}
<input type="submit">
</form>
</body>
</html>
- 方法欺骗的基本原理,在 HTML 表单中新加了一个名称为 “_method” 的这样的一个字段,value 填写为想欺骗成为的那个方法名称。
- 修改
routes/web.php
<?php
Route::match(['get', 'post', 'put'], '/', function(){
return view('welcome')->with("msg", "Hello world");
});
Route::get('/hello',function(){
return view('hello');
});
2.2 命名路由介绍;
- 给路由起一个名字。
# 举例:给路由取一个名字叫 “main”
# 方法 1:
Route::get('/hello',['as' => 'main', function(){
return view('hello');
}]);
# 方法 2:
Route::get('/hello',function(){
return view('hello');
}) -> name('main');
- 在什么情况下会用到?在编写 WEB 应用的时候,可能会使用非常多的超链接,超链接都有连接 URL,这些 URL 都在对应的路由当中。如果每一个都手动写的话,会非常的麻烦,还可能出现各种各样的问题。
- 修改
routes/web.php
<?php
Route::match(['get','post','put'], '/', function () {
$url = route('main');
return view('welcome')->with("msg", $url);
});
Route::get('/hello', function(){
return view('hello');
}) -> name('main');
-
welcome.blade.php 页面添加 {{ msg }} 接收变量
-
访问:
设置的 ip 或域名:端口号(可选)/
-
还有在做重定向的时候,在处理完成一个请求之后,要做一个重定向,跳转到一个新的页面。这时候也可以用命名路由。
-
修改
routes/web.php
<?php
Route::match(['get','post','put'], '/', function () {
return redirect()->route('main');
});
Route::get('/hello', function(){
return view('hello');
}) -> name('main');
- 当访问 “
设置的 ip 或域名:端口号(可选)/
” 的时候就会跳到 “设置的 ip 或域名:端口号(可选)/hello
” 页面,完成重定向。
3. 带参数的路由;
3.1 基本参数路由;
# 在路由当中,所有被“{}” 包围起来的,都是路由参数
# 可以在路由请求函数中,可以把它参数传进函数中,在函数内部使用
# 例子 1:
Route::get('user/{id}', function ($id) {
return 'User '. $id;
});
# 例子 2(在一个 url 中使用多个参数):
# 在下面的例子中,虽然 post 和postId 取名不一样,只要顺序相同,就能对应起来
Route::get('posts/{post}/comments/{comment}',
function ($postId, $commentId) {
//request processing code
});
- 修改
routes/web.php
<?php
Route::any('/hello/{id}/comments/{comment}', function($id, $commentId){
return view('welcome')->with('msg','ID:' . $id . ' commentId:' . $commentId);
});
- welcome.blade.php 页面添加 {{ msg }} 接收变量
- 访问:
设置的 ip 或域名:端口号(可选)/hello/123/comments/abc
3.2 可选参数路由;
- 如果在路由中没有指定参数,会有默认值传给处理请求函数让它进行相应处理
# 举例
Route::get('user/{name?}', function ($name = null) {
return $name;
});
Route::get('user/{name?}', function ($name = 'John') {
return $name;
});
- 修改
routes/web.php
<?php
Route::any('/hello/{id}/comments/{comment?}', function($id, $commentId = 'aaa'){
return view('welcome')->with('msg','ID:' . $id . ' commentId:' . $commentId);
});
- welcome.blade.php 页面添加 {{ msg }} 接收变量
- 访问:
设置的 ip 或域名:端口号(可选)/hello/123/comments
3.3 在参数中使用正则表达式;
- 在很多的请求中要限定用户的输入。比如要传进来一个 “id” 的话,必须是数字组成的一个字符串,不能含有字母等内容。
- 在传统的处理过程中,可以读取用户传进的 id 参数后进行判断是不是满足全是数字的要求,如果不是的话就报错。
- 在 Laravel 中可以通过正则表达式来限制用户的参数。
# 举例
Route::get('user/{name}', function ($name) {
//
}) -> where('name', '[A-Za-z]+');
Route::get('user/{id}', function ($id) {
//
}) -> where('id', '[0-9]+');
Route::get('user/{id}/{name}', function ($id, $name) {
//
}) -> where(['id' => '[0-9]+', 'name' => '[a-z]+']);
- 修改
routes/web.php
<?php
Route::any('/hello/{id}/comments/{comment}', function($id, $commentId){
return view('welcome')->with('msg','ID:' . $id . ' commentId:' . $commentId);
}) -> where(['id' => '[0-9]+', 'comment' => '[a-z]+']);
- welcome.blade.php 页面添加 {{ msg }} 接收变量
- 访问:
设置的 ip 或域名:端口号(可选)/hello/123/comments/ab
- 访问:
设置的 ip 或域名:端口号(可选)/hello/123ab/comments/12ab
4. 路由群组;
4.1 路由群组前缀;
- 将本群组里面所有路由的前面都加上一个统一的前缀
- 比如说,在一个简单的管理系统中,有普通用户也有管理员用户,对于管理员用户和普通用户的请求要分来进行处理。在所有管理员用户的请求前面加上 “admin” 前缀。但是如果在所有请求前面都手动添加 “admin” 的话会非常麻烦,这时候就可以使用路由群组。
- 路由群组实现对一类路由的统一配置和处理。前缀就是其中的一种应用。
- 路由群组的前缀是可以嵌套的。
# 举例:
Route::group(['prefix' => 'admin'], function () {
Route::get('users', function () {
// Matches The "/admin/users" URL
});
});
Route::group(['prefix' => 'accounts/{account_id}'], function () {
Route::get('detail', function ($accountId) {
// Matches The "/accounts/{account_id}/detail" URL
});
});
- 修改
routes/web.php
<?php
Route::group(['prefix' => 'admin'], function(){
Route::get('/user/{id}', function($id){
return view('welcome') -> with('msg', $id);
});
});
- welcome.blade.php 页面添加 {{ msg }} 接收变量
- 访问:
设置的 ip 或域名:端口号(可选)/admin/user/123
4.2 路由群组命名空间;
# 举例:
Route::group(['namespace' => 'Admin'], function(){
// Controllers Within The "App\Http\Controllers\Admin" Namespace
Route::group(['namespace' => 'User'], function() {
// Controllers Within The "App\Http\Controllers\Admin\User" Namespace
});
});
4.3 子域名路由。
- 需要制定一个域名,域名也可以带参数。
- 这个群组里所有的路由,都必须通过制指定的子域名进行访问。
- 其它的域名就算指向该服务器,也无法访问。
# 举例:
Route::group(['domain' => '{account}.myapp.com'], function () {
Route::get('user/{id}', function ($account, $id) {
//
});
});