亚洲香蕉成人av网站在线观看_欧美精品成人91久久久久久久_久久久久久久久久久亚洲_热久久视久久精品18亚洲精品_国产精自产拍久久久久久_亚洲色图国产精品_91精品国产网站_中文字幕欧美日韩精品_国产精品久久久久久亚洲调教_国产精品久久一区_性夜试看影院91社区_97在线观看视频国产_68精品久久久久久欧美_欧美精品在线观看_国产精品一区二区久久精品_欧美老女人bb

首頁 > 開發 > ThinkPHP > 正文

thinkphp5 URL和路由的功能詳解與實例

2024-09-09 15:20:22
字體:
來源:轉載
供稿:網友

前面的話:本文將詳細介紹thinkphp5URL和路由

URL訪問

ThinkPHP采用單一入口模式訪問應用,對應用的所有請求都定向到應用的入口文件,系統會從URL參數中解析當前請求的模塊、控制器和操作,下面是一個標準的URL訪問格式:

http://domainName/index.php/模塊/控制器/操作

其中index.php就稱之為應用的入口文件(注意入口文件可以被隱藏,后面會提到)

模塊在ThinkPHP中的概念其實就是應用目錄下面的子目錄,而官方的規范是目錄名小寫,因此模塊全部采用小寫命名,無論URL是否開啟大小寫轉換,模塊名都會強制小寫

應用的index模塊的Index控制器定義如下:

  1. namespace app/index/controller; 
  2. class Index 
  3.   public function index() 
  4.   { 
  5.     return 'index'
  6.   } 
  7.   public function hello($name = 'World'
  8.   { 
  9.     return 'Hello,' . $name . '!'
  10.   } 

如果直接訪問入口文件的話,由于URL中沒有模塊、控制器和操作,因此系統會訪問默認模塊(index)下面的默認控制器(Index)的默認操作(index),因此下面的訪問是等效的:

http://tp5.com/index.php

http://tp5.com/index.php/index/index/index

如果要訪問控制器的hello方法,則需要使用完整的URL地址

http://tp5.com/index.php/index/index/hello/name/thinkphp

訪問URL地址后頁面輸出結果為:

Hello,thinkphp!

由于name參數為可選參數,因此也可以使用

http://tp5.com/index.php/index/index/hello

訪問URL地址后頁面輸出結果為:

Hello,World!

默認情況下,URL地址中的控制器和操作名是不區分大小寫的,因此下面的訪問其實是等效的:

http://tp5.com/index.php/index/Index/Index

http://tp5.com/index.php/index/INDEX/INDEX

如果控制器是駝峰的,例如定義一個HelloWorld控制器(application/index/controller/HelloWorld.php):

  1. namespace app/index/controller; 
  2. class HelloWorld 
  3.   public function index($name = 'World'
  4.   { 
  5.     return 'Hello,' . $name . '!'
  6.   } 

正確的URL訪問地址(該地址可以使用url方法生成)應該是

http://tp5.com/index.php/index/hello_world/index

系統會自動定位到HelloWorld控制器類去操作

如果使用

http://tp5.com/index.php/index/HelloWorld/index

將會報錯,并提示Helloworld控制器類不存在

如果希望嚴格區分大小寫訪問(這樣就可以支持駝峰法進行控制器訪問),可以在應用配置文件中設置:

// 關閉URL自動轉換(支持駝峰訪問控制器)

'url_convert' => false,

關閉URL自動轉換之后,必須使用下面的URL地址訪問(控制器名稱必須嚴格使用控制器類的名稱,不包含控制器后綴):

http://tp5.com/index.php/index/Index/index

http://tp5.com/index.php/index/HelloWorld/index

如果服務器環境不支持pathinfo方式的URL訪問,可以使用兼容方式,例如:

http://tp5.com/index.php?s=/index/Index/index

其中變量s的名稱的可以配置的

5.0不再支持普通的URL訪問方式,所以下面的訪問是無效的,你會發現無論輸入什么,訪問的都是默認的控制器和操作

http://tp5.com/index.php?m=index&c=Index&a=hello

參數傳入

通過操作方法的參數綁定功能,可以實現自動獲取URL的參數,仍然以上面的控制器為例,控制器代碼如下:

  1. namespace app/index/controller; 
  2. class Index 
  3.   public function index() 
  4.   { 
  5.     return 'index'
  6.   } 
  7.   public function hello($name = 'World'
  8.   { 
  9.     return 'Hello,' . $name . '!'
  10.   } 

當我們訪問

http://tp5.com/index.php/index/index/hello

就是訪問appindexcontrollerIndex控制器類的hello方法,因為沒有傳入任何參數,name參數就使用默認值World。如果傳入name參數,則使用:

http://tp5.com/index.php/index/index/hello/name/thinkphp

頁面輸出結果為:

Hello,thinkphp!

現在給hello方法增加第二個參數:

  1. public function hello($name = 'World'$city = ''
  2.   { 
  3.     return 'Hello,' . $name . '! You come from ' . $city . '.'
  4.   } 

訪問地址為http://tp5.com/index.php/index/index/hello/name/thinkphp/city/shanghai

頁面輸出結果為:

Hello,thinkphp! You come from shanghai.

可以看到,hello方法會自動獲取URL地址中的同名參數值作為方法的參數值,而且這個參數的傳入順序不受URL參數順序的影響,例如下面的URL地址輸出的結果和上面是一樣的:

http://tp5.com/index.php/index/index/hello/city/shanghai/name/thinkphp

或者使用http://tp5.com/index.php/index/index/hello?city=shanghai&name=thinkphp

還可以進一步對URL地址做簡化,前提就是我們必須明確參數的順序代表的變量,我們更改下URL參數的獲取方式,把應用配置文件中的url_param_type參數的值修改如下:

// 按照參數順序獲取

'url_param_type' => 1,

現在,URL的參數傳值方式就變成了嚴格按照操作方法的變量定義順序來傳值了,也就是說我們必須使用下面的URL地址訪問才能正確傳入name和city參數到hello方法:http://tp5.com/index.php/index/index/hello/thinkphp/shanghai

頁面輸出結果為:

Hello,thinkphp! You come from shanghai.

如果改變參數順序為http://tp5.com/index.php/index/index/hello/shanghai/thinkphp

頁面輸出結果為:

Hello,shanghai! You come from thinkphp.

顯然不是我們預期的結果。

同樣,我們試圖通過http://tp5.com/index.php/index/index/hello/name/thinkphp/city/shanghai

訪問也不會得到正確的結果

[注意]按順序綁定參數的話,操作方法的參數只能使用URL pathinfo變量,而不能使用get或者post變量

隱藏入口

可以去掉URL地址里面的入口文件index.php,但是需要額外配置WEB服務器的重寫規則。

以Apache為例,需要在入口文件的同級添加.htaccess文件(官方默認自帶了該文件),內容如下:

  1. <IfModule mod_rewrite.c> 
  2. Options +FollowSymlinks -Multiviews 
  3. RewriteEngine on 
  4. RewriteCond %{REQUEST_FILENAME} !-d 
  5. RewriteCond %{REQUEST_FILENAME} !-f 
  6. RewriteRule ^(.*)$ index.php/$1 [QSA,PT,L] 
  7. </IfModule> 

如果用的phpstudy,規則如下:

  1. <IfModule mod_rewrite.c>  
  2. Options +FollowSymlinks -Multiviews  
  3. RewriteEngine on  
  4. RewriteCond %{REQUEST_FILENAME} !-d  
  5. RewriteCond %{REQUEST_FILENAME} !-f  
  6. RewriteRule ^(.*)$ index.php [L,E=PATH_INFO:$1]  
  7. </IfModule> 

接下來就可以使用下面的URL地址訪問了

http://tp5.com/index/index/index

http://tp5.com/index/index/hello

如果使用的apache版本使用上面的方式無法正常隱藏index.php,可以嘗試使用下面的方式配置.htaccess文件:

  1. <IfModule mod_rewrite.c> 
  2. Options +FollowSymlinks -Multiviews 
  3. RewriteEngine on 
  4. RewriteCond %{REQUEST_FILENAME} !-d 
  5. RewriteCond %{REQUEST_FILENAME} !-f 
  6. RewriteRule ^(.*)$ index.php?/$1 [QSA,PT,L] 
  7. </IfModule> 

如果是Nginx環境的話,可以在Nginx.conf中添加:

  1. location / { // …..省略部分代碼 
  2.   if (!-e $request_filename) { 
  3.     rewrite ^(.*)$ /index.php?s=/$1 last; 
  4.     break
  5.   } 

定義路由:

URL地址里面的index模塊怎么才能省略呢,默認的URL地址顯得有點長,下面就來說說如何通過路由簡化URL訪問。

我們在路由定義文件(application/route.php)里面添加一些路由規則,如下:

  1. return [ 
  2.   // 添加路由規則 路由到 index控制器的hello操作方法 
  3.   'hello/:name' => 'index/index/hello'
  4. ]; 

該路由規則表示所有hello開頭的并且帶參數的訪問都會路由到index控制器的hello操作方法。

路由之前的URL訪問地址為:http://tp5.com/index/index/hello/name/thinkphp

定義路由后就只能訪問下面的URL地址http://tp5.com/hello/thinkphp

[注意]定義路由規則后,原來的URL地址將會失效,變成非法請求。

但這里有一個小問題,如果我們只是訪問http://tp5.com/hello

將發生錯誤

事實上這是由于路由沒有正確匹配到,我們修改路由規則如下:

  1. return [ 
  2.   // 路由參數name為可選 
  3.   'hello/[:name]' => 'index/hello'
  4. ]; 

使用[]把路由規則中的變量包起來,就表示該變量為可選,接下來就可以正常訪問了http://tp5.com/hello

當name參數沒有傳入值的時候,hello方法的name參數有默認值World,所以輸出的內容為 Hello,World!

除了路由配置文件中定義之外,還可以采用動態定義路由規則的方式定義,例如在路由配置文件(application/route.php)的開頭直接添加下面的方法:

use think/Route;

Route::rule('hello/:name', 'index/hello');

完成的效果和使用配置方式定義是一樣的。

無論是配置方式還是通過Route類的方法定義路由,都統一放到路由配置文件application/route.php文件中

[注意]路由配置不支持在模塊配置文件中設置

【完整匹配】

前面定義的路由是只要以hello開頭就能進行匹配,如果需要完整匹配,可以使用下面的定義:

  1. return [ 
  2.   // 路由參數name為可選 
  3.   'hello/[:name]$' => 'index/hello'
  4. ]; 

當路由規則以$結尾的時候就表示當前路由規則需要完整匹配。

當我們訪問下面的URL地址的時候:

http://tp5.com/hello // 正確匹配

http://tp5.com/hello/thinkphp // 正確匹配

http://tp5.com/hello/thinkphp/val/value // 不會匹配

【閉包定義】

還支持通過定義閉包為某些特殊的場景定義路由規則,例如:

  1. return [ 
  2.   // 定義閉包 
  3.   'hello/[:name]' => function ($name) { 
  4.     return 'Hello,' . $name . '!'
  5.   }, 
  6. ]; 

或者

  1. use think/Route; 
  2. Route::rule('hello/:name'function ($name) { 
  3.   return 'Hello,' . $name . '!'
  4. }); 

[注意]閉包函數的參數就是路由規則中定義的變量

因此,當訪問下面的URL地址:http://tp5.com/hello/thinkphp

會輸出

Hello,thinkphp!

【設置URL分隔符】

如果需要改變URL地址中的pathinfo參數分隔符,只需要在應用配置文件(application/config.php)中設置:

// 設置pathinfo分隔符

'pathinfo_depr'     => '-',

路由規則定義無需做任何改變,我們就可以訪問下面的地址:http://tp5.com/hello-thinkphp

【路由參數】

還可以約束路由規則的請求類型或者URL后綴之類的條件,例如:

  1. return [ 
  2.   // 定義路由的請求類型和后綴 
  3.   'hello/[:name]' => ['index/hello', ['method' => 'get''ext' => 'html']], 
  4. ]; 

上面定義的路由規則限制了必須是get請求,而且后綴必須是html的,所以下面的訪問地址:

http://tp5.com/hello // 無效

http://tp5.com/hello.html // 有效

http://tp5.com/hello/thinkphp // 無效

http://tp5.com/hello/thinkphp.html // 有效

【變量規則】

接下來,嘗試一些復雜的路由規則定義滿足不同的路由變量。在此之前,首先增加一個控制器類如下:

  1. <?php 
  2. namespace app/index/controller; 
  3. class Blog 
  4.   public function get($id
  5.   { 
  6.     return '查看id=' . $id . '的內容'
  7.   } 
  8.   public function read($name
  9.   { 
  10.     return '查看name=' . $name . '的內容'
  11.   } 
  12.   public function archive($year$month
  13.   { 
  14.     return '查看' . $year . '/' . $month . '的歸檔內容'
  15.   } 

添加如下路由規則:

  1. return [ 
  2.   'blog/:year/:month' => ['blog/archive', ['method' => 'get'], ['year' => '/d{4}''month' => '/d{2}']], 
  3.   'blog/:id'     => ['blog/get', ['method' => 'get'], ['id' => '/d+']], 
  4.   'blog/:name'    => ['blog/read', ['method' => 'get'], ['name' => '/w+']], 
  5. ]; 

在上面的路由規則中,我們對變量進行的規則約束,變量規則使用正則表達式進行定義。

我們看下幾種URL訪問的情況

  1. // 訪問id為5的內容 
  2. http://tp5.com/blog/5  
  3. // 訪問name為thinkphp的內容 
  4. http://tp5.com/blog/thinkphp  
  5. // 訪問2015年5月的歸檔內容 
  6. http://tp5.com/blog/2015/05 

【路由分組】

上面的三個路由規則由于都是blog打頭,所以我們可以做如下的簡化:

  1. return [ 
  2.   '[blog]' => [ 
  3.     ':year/:month' => ['blog/archive', ['method' => 'get'], ['year' => '/d{4}''month' => '/d{2}']],   
  4.     ':id'     => ['blog/get', ['method' => 'get'], ['id' => '/d+']], 
  5.     ':name'    => ['blog/read', ['method' => 'get'], ['name' => '/w+']], 
  6.   ], 
  7. ]; 

對于這種定義方式,我們稱之為路由分組,路由分組一定程度上可以提高路由檢測的效率

【復雜路由】

有時候,還需要對URL做一些特殊的定制,例如如果要同時支持下面的訪問地址

http://tp5.com/blog/thinkphp

http://tp5.com/blog-2015-05

我們只要稍微改變路由定義規則即可:

  1. return [ 
  2.   'blog/:id'      => ['blog/get', ['method' => 'get'], ['id' => '/d+']], 
  3.   'blog/:name'     => ['blog/read', ['method' => 'get'], ['name' => '/w+']], 
  4.   'blog-<year>-<month>' => ['blog/archive', ['method' => 'get'], ['year' => '/d{4}''month' => '/d{2}']], 
  5. ]; 

對 blog-<year>-<month> 這樣的非正常規范,我們需要使用<變量名>這樣的變量定義方式,而不是 :變量名方式。

簡單起見,我們還可以把變量規則統一定義,例如:

  1. return [ 
  2.   // 全局變量規則定義 
  3.   '__pattern__'     => [ 
  4.     'name' => '/w+'
  5.     'id'  => '/d+'
  6.     'year' => '/d{4}'
  7.     'month' => '/d{2}'
  8.   ], 
  9.   // 路由規則定義 
  10.   'blog/:id'      => 'blog/get'
  11.   'blog/:name'     => 'blog/read'
  12.   'blog-<year>-<month>' => 'blog/archive'
  13. ]; 

在__pattern__中定義的變量規則我們稱之為全局變量規則,在路由規則里面定義的變量規則我們稱之為局部變量規則,如果一個變量同時定義了全局規則和局部規則的話,當前的局部規則會覆蓋全局規則的,例如:

  1. return [ 
  2.   // 全局變量規則 
  3.   '__pattern__'     => [ 
  4.     'name' => '/w+'
  5.     'id'  => '/d+'
  6.     'year' => '/d{4}'
  7.     'month' => '/d{2}'
  8.   ], 
  9.  
  10.   'blog/:id'      => 'blog/get'
  11.   // 定義了局部變量規則 
  12.   'blog/:name'     => ['blog/read', ['method' => 'get'], ['name' => '/w{5,}']], 
  13.   'blog-<year>-<month>' => 'blog/archive'
  14. ]; 

URL生成

定義路由規則之后,可以通過Url類來方便的生成實際的URL地址(路由地址),針對上面的路由規則,我們可以用下面的方式生成URL地址。

  1. // 輸出 blog/thinkphp 
  2. Url::build('blog/read''name=thinkphp'); 
  3. Url::build('blog/read', ['name' => 'thinkphp']); 
  4. // 輸出 blog/5 
  5. Url::build('blog/get''id=5'); 
  6. Url::build('blog/get', ['id' => 5]); 
  7. // 輸出 blog/2015/05 
  8. Url::build('blog/archive''year=2015&month=05'); 
  9. Url::build('blog/archive', ['year' => '2015''month' => '05']); 

[注意]build方法的第一個參數使用路由定義中的完整路由地址

還可以使用系統提供的助手函數url來簡化

url('blog/read', 'name=thinkphp');

// 等效于

Url::build('blog/read', 'name=thinkphp');

通常在模板文件中輸出的話,可以使用助手函數,例如:

{:url('blog/read', 'name=thinkphp')}

如果我們的路由規則發生調整,生成的URL地址會自動變化

如果你配置了url_html_suffix參數的話,生成的URL地址會帶上后綴,例如:

'url_html_suffix'  => 'html',

那么生成的URL地址 類似

blog/thinkphp.html

blog/2015/05.html

如果你的URL地址全部采用路由方式定義,也可以直接使用路由規則來定義URL生成,例如:

url('/blog/thinkphp');

Url::build('/blog/8');

Url::build('/blog/archive/2015/05');

生成方法的第一個參數一定要和路由定義的路由地址保持一致,如果你的路由地址比較特殊,例如使用閉包定義的話,則需要手動給路由指定標識,例如:

  1. // 添加hello路由標識 
  2. Route::rule(['hello','hello/:name'], function($name){ 
  3.   return 'Hello,'.$name
  4. }); 
  5. // 根據路由標識快速生成URL 
  6. Url::build('hello''name=thinkphp'); 
  7. // 或者使用 
  8. Url::build('hello', ['name' => 'thinkphp']); 

發表評論 共有條評論
用戶名: 密碼:
驗證碼: 匿名發表

圖片精選

亚洲香蕉成人av网站在线观看_欧美精品成人91久久久久久久_久久久久久久久久久亚洲_热久久视久久精品18亚洲精品_国产精自产拍久久久久久_亚洲色图国产精品_91精品国产网站_中文字幕欧美日韩精品_国产精品久久久久久亚洲调教_国产精品久久一区_性夜试看影院91社区_97在线观看视频国产_68精品久久久久久欧美_欧美精品在线观看_国产精品一区二区久久精品_欧美老女人bb
日韩av在线高清| 亚洲男人天堂网站| 中文字幕日韩精品在线| 亚洲人成自拍网站| 欧美激情乱人伦一区| 亚洲最大激情中文字幕| 亚洲一区二区自拍| 51视频国产精品一区二区| 午夜精品免费视频| 亚洲色图综合网| 91久久精品美女| 狠狠久久五月精品中文字幕| 97在线视频免费| 欧美丰满片xxx777| 日本高清不卡的在线| 黑人极品videos精品欧美裸| 亚洲男女性事视频| 自拍视频国产精品| 少妇高潮久久久久久潘金莲| 精品国产依人香蕉在线精品| 亚洲精品久久久久久久久久久久久| 亚洲人成绝费网站色www| 国产精品91久久| 亚洲人免费视频| 国产免费一区二区三区香蕉精| 美女撒尿一区二区三区| 日韩视频免费在线观看| 2021国产精品视频| 日韩中文字幕在线播放| 欧美性少妇18aaaa视频| 亚洲精品97久久| 亚洲男人天堂古典| 色偷偷91综合久久噜噜| 亚洲少妇激情视频| 97久久超碰福利国产精品…| 日韩一区在线视频| 亚洲午夜国产成人av电影男同| 红桃av永久久久| 国产成人精品综合| 欧美在线免费看| 一区二区三区四区视频| 亚洲18私人小影院| 国产成人av网址| 日韩av电影手机在线观看| 国模视频一区二区三区| 欧美多人乱p欧美4p久久| 久久69精品久久久久久久电影好| www.日韩免费| 国产成人一区二区| 国产精品久久久久久久久久久不卡| 欧美xxxx做受欧美| 欧美又大又硬又粗bbbbb| 国产精品久久久久免费a∨大胸| 亚洲成人久久一区| 欧美一级大片在线免费观看| 中文字幕在线看视频国产欧美在线看完整| 日韩电影免费在线观看中文字幕| 国产精品专区h在线观看| 国产欧美一区二区三区在线| 国自在线精品视频| 午夜欧美大片免费观看| 成人免费视频xnxx.com| 91wwwcom在线观看| 91tv亚洲精品香蕉国产一区7ujn| 91精品国产九九九久久久亚洲| 国产一区二区三区在线免费观看| 欧美精品电影免费在线观看| 亚洲欧洲日产国码av系列天堂| 亚洲精品视频播放| 性色av一区二区三区免费| 精品激情国产视频| 成人女保姆的销魂服务| 亚洲激情国产精品| 午夜精品久久久久久久久久久久| 欧美与黑人午夜性猛交久久久| 成人精品在线视频| 亚洲视频网站在线观看| 亚洲色图13p| 国产日产欧美精品| 日韩有码在线电影| 92版电视剧仙鹤神针在线观看| 国产一区二区三区视频| 欧美性一区二区三区| 欧美精品福利在线| 久久久精品网站| 国a精品视频大全| 97人人做人人爱| 美女视频久久黄| 国产午夜精品全部视频在线播放| 亚洲欧美另类国产| 欧美影院成年免费版| 欧美一级片免费在线| 国产精品视频免费观看www| 欧美精品少妇videofree| 国产午夜精品全部视频播放| 91在线观看免费观看| 国产精品99免视看9| 在线播放国产一区中文字幕剧情欧美| 91wwwcom在线观看| 97在线观看免费高清| 日韩在线观看电影| xxx成人少妇69| 欧美性色视频在线| 欧美激情一二区| 日韩经典第一页| 国产精品欧美风情| 92裸体在线视频网站| 精品偷拍各种wc美女嘘嘘| 91久久精品国产91久久性色| 日韩av中文字幕在线免费观看| 亚洲美女免费精品视频在线观看| 91视频8mav| 国产精品中文在线| 国产精品爽爽爽爽爽爽在线观看| 亚洲精品永久免费精品| 欧美在线视频一区| 日韩在线视频观看| 国产成人午夜视频网址| 国产91热爆ts人妖在线| 国产亚洲精品美女久久久久| 国产亚洲成av人片在线观看桃| www欧美xxxx| 国产日韩精品入口| 8x拔播拔播x8国产精品| 成人激情在线观看| 96精品视频在线| 国产噜噜噜噜噜久久久久久久久| 欧美精品激情视频| 欧美性20hd另类| 欧美一区二区三区免费观看| 国产精品美女久久久免费| 国产精品视频一| 国产女精品视频网站免费| 日韩av在线不卡| 欧美成人国产va精品日本一级| 欧美激情a∨在线视频播放| 57pao国产成人免费| 欧美日韩国产成人在线观看| 亚洲精品97久久| 欧美性videos高清精品| 欧美乱大交xxxxx另类电影| 伊人成人开心激情综合网| 伦理中文字幕亚洲| 国产又爽又黄的激情精品视频| 96精品久久久久中文字幕| 日韩在线观看你懂的| 国产福利精品av综合导导航| 国产区精品在线观看| 亚洲成人激情图| 亚洲福利影片在线| 伊人久久综合97精品| 浅井舞香一区二区| 久久成人免费视频| 国产成人综合一区二区三区| 国产中文字幕91| 97色在线观看免费视频| 欧美成人激情图片网| 欧美久久精品一级黑人c片| 精品国内亚洲在观看18黄| 91久久久在线| 岛国av一区二区三区| 亚洲国产成人爱av在线播放| 九九热精品视频在线播放| 亚洲全黄一级网站|