yii2-cookbook之定制response类型[翻译] [ 2.0 版本 ]
以后会看心情不定时翻译github上的yii-cookbook(url: https://github.com/samdark/yii2-cookbook/tree/master/book)
英文水平有限,有错误请一定指出来.
原文地址:https://github.com/samdark/yii2-cookbook/blob/master/book/response-formats.md
使用不同的response类型
现代的web和移动应用(对Server的要求)已经不仅仅满足于渲染HTML了.现代的软件架构已渐渐将UI看成是一个客户端,客户端负责直接和用户发生交互,整个前端由服务端API驱动.(这种情况下)JSON和XML就常常作为结构化数据的序列化和传输的载体在网络上传输,所以创建这种response的能力已经成为现代服务框架的必备要求.
response类型
你可能知道,yii2的action函数中需要(某种方法)"返回"结果,而不是直接echo:
// returning HTML result
return $this->render('index', [
'items' => $items,
]);
有个好消息是yii2现在可以return其他格式的数据,如:
- 数组
- 实现了Arrayable接口的对象
- 字符串
- 实现了__toString()方法的对象
只是不要忘了在return前设置\Yii::$app->response->format
来告诉YII你想要response的类型:
\Yii::$app->response->format = \yii\web\Response::FORMAT_JSON;
可选的类型有:
- FORMAT_RAW
- FORMAT_HTML
- FORMAT_JSON
- FORMAT_JSONP
- FORMAT_XML
默认是FORMAT_HTML
JSON response
现在我们返回一个数组:
public function actionIndex()
{
\Yii::$app->response->format = \yii\web\Response::FORMAT_JSON;
$items = ['some', 'array', 'of', 'data' => ['associative', 'array']];
return $items;
}
返回结果:
{
"0": "some",
"1": "array",
"2": "of",
"data": ["associative", "array"]
}
注: 如果没有设置response类型你会收到一个exception
同样地,我们还可以返回一个对象:
public function actionView($id)
{
\Yii::$app->response->format = \yii\web\Response::FORMAT_JSON;
$user = \app\models\User::find($id);
return $user;
}
这里的$user是一个ActiveRecord对象,而ActiveRecord类已实现了Arrayable接口,所以它可以很轻易地被转成json:
{
"id": 1,
"name": "John Doe",
"email": "john@example.com"
}
我们甚至可以返回一个对象数组:
public function actionIndex()
{
\Yii::$app->response->format = \yii\web\Response::FORMAT_JSON;
$users = \app\models\User::find()->all();
return $users;
}
这里的$users就是一个ActiveRecord对象数组,不过在底层yii是通过\yii\helpers\Json::encode()
来传输和转化数据的,所以返回的时候请小心确保数组中元素的类型:
[
{
"id": 1,
"name": "John Doe",
"email": "john@example.com"
},
{
"id": 2,
"name": "Jane Foo",
"email": "jane@example.com"
},
...
]
XML response
只要把response的format改成FORMAT_XML, 那么你就能得到XML类型的返回值:
public function actionIndex()
{
\Yii::$app->response->format = \yii\web\Response::FORMAT_XML;
$items = ['some', 'array', 'of', 'data' => ['associative', 'array']];
return $items;
}
//返回
<response>
<item>some</item>
<item>array</item>
<item>of</item>
<data>
<item>associative</item>
<item>array</item>
</data>
</response>
是的,我们同样可以把对象转成XML:
public function actionIndex()
{
\Yii::$app->response->format = \yii\web\Response::FORMAT_XML;
$users = \app\models\User::find()->all();
return $users;
}
//返回
<response>
<User>
<id>1</id>
<name>John Doe</name>
<email>john@example.com</email>
</User>
<User>
<id>2</id>
<name>Jane Foo</name>
<email>jane@example.com</email>
</User>
</response>
定制化自己的response类型
让我们搞一个自己的response类型玩玩吧.为了让例子有趣点,我们打算respond一个PHP数组格式的数据.
首先,我们需要先定制一个formatter. 创建文件components/PhpArrayFormatter.php:
<?php
namespace app\components;
use yii\helpers\VarDumper;
use yii\web\ResponseFormatterInterface;
class PhpArrayFormatter implements ResponseFormatterInterface
{
public function format($response)
{
$response->getHeaders()->set('Content-Type', 'text/php; charset=UTF-8');
if ($response->data !== null) {
$response->content = "<?php\nreturn " . VarDumper::export($response->data) . ";\n";
}
}
}
现在我们需要在配置文件中注册这个formatter:
return [
// ...
'components' => [
// ...
'response' => [
'formatters' => [
'php' => 'app\components\PhpArrayFormatter',
],
],
],
];
好了,万事俱备, 现在在controller里创建一个action:
public function actionTest()
{
Yii::$app->response->format = 'php';
return [
'hello' => 'world!',
];
}
执行之后的response是这样的:
<?php
return [
'hello' => 'world!',
];
yiissy001
最后登录:2017-09-25
在线时长:24小时55分
- 粉丝7
- 金钱2529
- 威望90
- 积分3669
共 2 条评论
代码不错哦, 还是有个问题问问大家, 数据库中的配置文件如何缓存为驻足格式数据到 params.php 文件中???
如何返回关联对象的json呀