我在ActiveRecord
类中有一个虚拟公共属性。当我在类中收到JSON
RawBody
时ActiveController
我正在尝试将解析的 JSON 分配给$model->attributes
。请求 JSON 如下所示:
{
"name": "test",
"address": "a place on earth",
"_id": 1
}
现在在上面的 JSON _id
是我在类中声明为public $_id;
ActiveRecord
键,我也为此属性使用了 setter getter,如下所示:
public function setId ($value)
{
$this->_id = $value;
}
public function getId ($value)
{
return $this->_id;
}
主动控制器方法:
public function actionPush()
{
$data = $this->getRequestData();
$model = new User();
$model->attributes = $data;
if($model->save())
return ['status' => 200, 'message' => 'Record added successfully', 'record' => $model];
return ['status' => 400, 'message' => 'Records not updated', 'errors' => $errors];
}
public function getRequestData()
{
$body = 'Yii::$app->request->getRawBody();
$parser = new JsonParser();
return $parser->parse($body, 'application/json');
}
现在我想要这样的回应:
{
"status": 200,
"message": "Record added successfully",
"record": {
"id": 10,
"name": "test",
"_id": 1
}
}
但是像这样:
{
"status": 200,
"message": "Record added successfully",
"record": {
"id": 10,
"name": "test"
}
}
我如何获得结果?
情况 1:您要用 _id
替换id
如果您的模型已经有一个名为 id
的属性,那么我不确定覆盖现有数据库属性是否是一种好的做法。我建议重写 yii''base''Model::fields((,因为它是在内置的 Yii RESTful API 中完成的(参见文档(。这样,你将保留模型的原始实例,以便在应用内在需要时使用,并将$model->fields()
绑定到用户终结点或输出。
我认为您在这里甚至不需要虚拟属性。 如果您打算手动设置或更新模型的主键,则 id
和 _id
之间的映射器属性可能就足够了。 这可以在 setter 方法中完成。将此添加到您的模型中:
// remember to add '_id' to safe attributes (model::rules)
public function set_id ($value)
{
$this->id = $value;
}
public function fields()
{
$fields = parent::fields();
unset($fields['id']);
$fields['_id'] = $this->id;
// or $fields['_id'] = $this->getPrimaryKey();
return $fields;
}
然后强制actionPush()
返回$model->fields()
而不是$model
:
public function actionPush()
{
$data = $this->getRequestData();
$model = new User();
$model->attributes = $data;
if($model->save())
return [
'status' => 200,
'message' => 'Record added successfully',
'record' => $model->fields();
];
return ['status' => 400, 'message' => 'Records not updated', 'errors' => $errors];
}
情况2:你想同时保持id
和_id
我添加第二种情况,因为我想我可能误解了你的问题。 如果要保留和维护属性id
和_id
:
"record": {
"id": 10,
"_id": 1
"name": "test",
}
然后这将解决问题:
private $_id;
public function get_id ()
{
return $this->_id;
}
public function set_id ($value)
{
$this->_id = $value;
}
public function fields()
{
$fields = parent::fields();
$fields['_id'] = '_id';
return $fields;
}
注意:如果 ''yii''web''Response 设置为 'yii'web'Response::FORMAT_JSON
,Yii 将使用 fields
来检索属性(可以在配置文件或 ContentNegotiator 中设置(。否则,如果您使用不同的格式化程序,则可以手动调用$model->fields()
而不是$model
来输出数据。