API後端框架Godtail2-路由元件

weixin_34253539發表於2016-11-04

來自部落格:神的尾巴,原文連結

已提交到github,路由元件程式碼,程式碼質量一般,大家將就著看 : )

元件思路

現在都是單入口,通過index.php配置元件,然後通過元件dispatch,來呼叫指定的控制器。

另外這個框架作為後端純Api框架。沒有PHP模板引擎,所有與前端的資料互動都通過json(推薦)或xml。所以要支援跨域,也要支援RESTFul風格的請求。

當前實現了的一些特性

  1. 自動呼叫控制器,處理請求。

  2. 專門解析引數的Param工具類。

  3. PHP不處理PUT請求過來的引數,新增Parser工具類,有解析器FormData,Json,用來處理前端發過來的資料。包含上傳檔案的解析(設定到臨時檔案,對於比較小的檔案直接獲取檔案內容,可以自己配置)。

當前部落格就是用這個元件寫的,程式碼也在github上。

還需完善的一些地方(近幾天抽空解決下)

  1. 自定義路由:新增正則匹配。

    例如`/article/:id`,自動配置整數,並設定到引數id。
    [
        'url' => '/article/:id',
        'filter' => [
            'id' => '/\d+/'
         ]
         #'controller' => 'Article@detail'
         'real' => '/article/detail/:id'
    ]

實現過程

composer.json配置

{
    "name": "godtail/router",
    "description": "Easy router, no config, support RESTFul.",
    "license": "MIT",
    "require": {
        "php": ">=5.3.3"
    },
    "autoload": {
        "psr-4": {"Godtail\\Router\\": "./src"}
    }
}

需要的配置

'deep' => 2, #控制器層數 
'default' => ['Index', 'index'], #預設,自動補全
'namespacePre' => 'Service\\', #控制器名稱空間字首
'classSuffix' => 'Service', #控制器類名字尾
'crossDomain' => [ #跨域設定
    'allowOrigin' => 'http://test.net',
    'maxAge' => '86400',
    'headers' => 'Content-Type',
    'methods' => 'OPTIONS, GET, PUT, POST, DELETE',
]

如何獲得比較好的URL風格

通過nginx rewrite,把匹配不到的urlrewriteindex.php?/$uri

location / {
    try_files $uri $uri/ /index.php?/$uri;
}

這樣godtail.cn/index.php?/article/tag,就可以寫成godtail.cn/article/tag

路由分層和URL引數解析

config的deep引數,用來配置路由多少層,如果功能比較簡單可以只分為2層,如果分module,則可以分成3層。

獲取URL,根據/拆分。
例如`deep=2`, `godtail.cn/article/tag/page/2`,把page設定到Params。

Params: 儲存著一個靜態變數$data,用來存放請求過來的引數。
提供get,set,parse方法。

FormData的解析

如果通過POST過來的請求,PHP能夠處理,設定到$_POST或者$_FILES,但是如果是PUT請求,則需要自己處理php://input資料流

FormData的格式

------boundary--------['--'+boundary]
name=1
content-type=xxxx
[換行]
資料內容1
------boundary--------['--'+boundary]
name=2
content-type=xxxx
[換行]
資料內容2
------boundary---------[最後一個'--'+boundary+'-']

目前是通過正則來解析處理的,如果設定了saveFile。使用tempnam生成臨時檔案。

啟用

#設定配置
Router::config($config['router']);

#dispatch
Router::dispatch();

相關文章