本文主要是介绍筋斗云接口编程 / 对象型接口(四),希望对大家解决编程问题提供一定的参考价值,需要的开发者们随着小编来一起学习吧!
定制可访问数据
除了限制用户可以访问哪些表和字段,还常会遇到一类需求是限制用户只能访问自己的数据。
[任务]
用户登录后,可以添加订单、查看自己的订单。
我们在设计文档中设计接口如下:
添加订单
Ordr.add()(amount) -> id查看订单
Ordr.query() -> tbl(id, userId, status, amount)
Ordr.get(id) -> { 同query接口字段...}应用逻辑- 权限:AUTH_USER
- 用户只能添加(add)、查看(get/query)订单,不可修改(set)、删除(del)订单
- 用户只能查看(get/query)属于自己的订单。
- 用户在添加订单时,必须设置amount字段,不可设置userId, status这些字段。后端将userId字段自动设置为该用户编号,status字段自动设置为"CR"(已创建)
上面接口原型描述中,get接口用”…”省略了详细的返回字段,因为返回对象的字段与query接口是一样的,两者写清楚一个即可。
实现对象型接口,我们一般写到文件php/api_objects.php中:
class AC1_Ordr extends AccessControl
{protected $allowedAc = ["get", "query", "add"];protected $requiredFields = ["amount"];protected $readonlyFields = ["status", "userId"];// get/query接口会回调protected function onQuery(){$userId = $_SESSION["uid"];$this->addCond("t0.userId={$userId}");}// add/set接口会回调protected function onValidate(){if ($this->ac == "add") {$userId = $_SESSION["uid"];$_POST["userId"] = $userId;$_POST["status"] = "CR";}}
}
在get/query操作中,会回调
onQuery
函数,在这里我们用addCond
添加了一条限制:用户只能查看到自己的订单。
addCond
的参数可理解为SQL语句中WHERE子句的片段;字段用”t0.userId”来表示,其中”t0”表示当前操作表”Ordr”的别名(alias)。后面会讲到联合查询(join)其它表,就可能使用其它表的别名。add/set操作会回调
onValidate
函数(本例中$allowedAc
中未定义”set”,因而不会有”set”操作过来)。在这个回调中常常设置$_POST[字段名]
来自动完成一些字段。注意
$_SESSION["uid"]
变量是在用户登录成功后设置的,由于”AC1”类是用户登录后使用的,所以必能取到该变量。
[任务]
我们把需求稍扩展一下,现在允许set/del操作,即用户可以更改和删除自己的订单。
可以这样实现:
class AC1_Ordr extends AccessControl
{protected $allowedAc = ["get", "query", "add", "set", "del"];...// get/set/del接口会回调protected function onValidateId(){$uid = $_SESSION["uid"];$id = mparam("id");$rv = queryOne("SELECT id FROM Ordr WHERE id={$id} AND userId={$uid}");if ($rv === false)throw new MyException(E_FORBIDDEN, "not your order");}
}
可通过onValidateId
回调来限制get/set/del操作时,只允许访问自己的订单。
函数mparam
用来取必传参数(m表示mandatory)。
函数queryOne
用来查询首行数据,如果查询只有一列,则返回首行首列数据,但如果查询不到数据,就返回false.
这里如果返回false,既可能是订单id不存在,也可能是虽然存在但是是别人的订单,简单处理,我们都返回一个E_FORBIDDEN异常。
框架对异常会自动处理,一般不用特别再检查数据库操作失败之类的异常。如果返回错误对象,可抛出MyException
异常:
throw new MyException(E_FORBIDDEN);
错误码”E_FORBIDDEN”表示没有权限,不允许操作;常用的其它错误码还有”E_PARAM”,表示参数错误。
MyException的第二个参数是内部调试信息,第三个参数是对用户友好的报错信息,比如:
throw new MyException(E_FORBIDDEN, "order id {$id} does not belong to user {$uid}", "不是你的订单,不可操作");
这篇关于筋斗云接口编程 / 对象型接口(四)的文章就介绍到这儿,希望我们推荐的文章对编程师们有所帮助!