百度云 api php,百度云API鉴权总结

最近在研究百度云的一些服务,处理api接口鉴权时花了不少时间,总结一下,方便大家对接:

废话不说,直接上代码

Signer.php:签名工具类,鉴权签名的核心方法都在这里

Utils.php:封装的工具类,鉴权,返回json数据等都在这里

Account.php:示例Controller,请求百度云接口

使用的tp5框架,代码仅供参考,思路可以供大家借鉴,如有不当之处,欢迎指正

签名工具类

Signer.php

class SignerException extends Exception

{

function __construct($message)

{

parent::__construct($message, 999);

}

}

class Signer

{

private $ak;

private $sk;

private $version = "1";

private $timestamp;

private $expiration = 1800;

private $method;

private $uri;

private $params = array();

private $headers = array();

private $needLog = false;

function __construct($accessKey, $secretKey)

{

$this->ak = $accessKey;

$this->sk = $secretKey;

$date = new DateTime('now');

$date->setTimezone(new DateTimeZone('UTC'));

$this->timestamp = $date->format('Y-m-d\TH:i:s\Z');

}

public function setVersion($version)

{

$this->version = $version;

}

public function setExpiration($expiration)

{

$this->expiration = $expiration;

}

public function setMethod($method)

{

if (!empty($method)) {

$this->method = strtoupper($method);

}

}

public function setTimestamp($timestamp)

{

$this->timestamp = $timestamp;

}

public function setUri($uri)

{

$this->uri = $uri;

}

public function setParams($params)

{

$this->params = $this->normalizeParam($params);

}

public function setSignHeaders($headers)

{

$this->headers = $this->normalizeHeaders($headers);

}

public function beLog($needLog)

{

$this->needLog = $needLog;

}

public function genAuthorization()

{

$signature = $this->genSignature();

$authStr = "bce-auth-v" . $this->version . "/" .

$this->ak . "/" . $this->timestamp . "/" .

$this->expiration . "/" . $this->getSignedHeaderNames() . "/" . $signature;

return $authStr;

}

public function genSignature()

{

if (empty($this->method)) {

throw new SignerException("method is null or empty");

}

$signingKey = $this->genSigningKey();

$this->signerLog("signingKey:" . $signingKey, __LINE__, __FILE__);

$authStr = $this->method . "\n" .

$this->getCanonicalURI() . "\n" .

$this->getCanonicalParam() . "\n" .

$this->getCanonicalHeaders();

$this->signerLog("auth str:" . $authStr, __LINE__, __FILE__);

return $this->sha256($signingKey, $authStr);

}

public function genSigningKey()

{

if (empty($this->ak)) {

throw new SignerException("access key is null or empty");

}

if (empty($this->sk)) {

throw new SignerException("secret key is null or empty");

}

if (empty($this->version)) {

throw new SignerException("version is null or empty");

}

if (empty($this->timestamp)) {

throw new SignerException("timestamp is null or empty");

}

if (empty($this->expiration)) {

throw new SignerException("expiration is null or empty");

}

$authStr = "bce-auth-v" . $this->version . "/" . $this->ak . "/" .

$this->timestamp . "/" . $this->expiration;

return $this->sha256($this->sk, $authStr);

}

public function getCanonicalParam()

{

if (empty($this->params)) {

return "";

}

$arryLen = count($this->params);

$canonicalParams = "";

foreach ($this->params as $key => $value) {

if (is_array($value)) {

$num = count($value);

if (count($value) == 0) {

$canonicalParams = $canonicalParams . $key . "=";

} else {

foreach ($value as $item) {

$canonicalParams = $canonicalParams . $key . "=" . $item;

if ($num > 1) {

$canonicalParams = $canonicalParams . "&";

$num--;

}

}

}

} else {

$canonicalParams = $canonicalParams . $key . "=" . $value;

}

if ($arryLen > 1) {

$canonicalParams = $canonicalParams . "&";

$arryLen--;

}

}

return $canonicalParams;

}

public function getCanonicalURI()

{

if (empty($this->uri)) {

throw new SignerException("uri is null or empty");

}

$newUri = $this->dataEncode($this->uri, true);

if (strpos($newUri, "/") === 0) {

return $newUri;

}

return "/" . $newUri;

}

public function getCanonicalHeaders()

{

if (empty($this->headers) || !array_key_exists("host", $this->headers)) {

throw new SignerException("host not in headers");

}

$canonicalHeaders = "";

$strArry = array();

foreach ($this->headers as $key => $value) {

if (empty($value)) {

continue;

}

$strArry[] = $this->dataEncode($key, false) . ":" . $value;

}

$arryLen = count($strArry);

for ($i = 0; $i < $arryLen; $i++) {

if ($i < $arryLen - 1) {

$canonicalHeaders = $canonicalHeaders . $strArry[$i] . "\n";

continue;

}

$canonicalHeaders = $canonicalHeaders . $strArry[$i];

}

return $canonicalHeaders;

}

private function sha256($key, $data)

{

return hash_hmac('sha256', $data, $key);

}

private function dataEncode($data, $isPath)

{

if (empty($data)) {

return "";

}

$encode = mb_detect_encoding($data, array("ASCII", "UTF-8", "GB2312", "GBK", "BIG5"));

if ($encode != "UTF-8") {

$data = $code1 = mb_convert_encoding($data, 'utf-8', $encode);

}

$encodeStr = rawurlencode($data);

if ($isPath) {

$encodeStr = str_replace("%2F", "/", $encodeStr);

}

return $encodeStr;

}

private function normalizeHeaders($headers)

{

$newArray = array();

if (empty($headers)) {

return $newArray;

}

foreach ($headers as $key => $value) {

$newKey = strtolower($key);

if (empty($newKey)) {

continue;

}

$newArray[$newKey] = $this->dataEncode(trim($value), false);

}

ksort($newArray);

return $newArray;

}

private function normalizeParam($params)

{

$newArray = array();

if (empty($params)) {

return $newArray;

}

foreach ($params as $key => $value) {

if (empty($key) || strtolower($key) == "authorization") {

continue;

}

if (is_array($value)) {

$newSubArray = array();

foreach ($value as $item) {

$newSubArray[] = $this->dataEncode($item, false);

}

sort($newSubArray);

$newArray[$this->dataEncode($key, false)] = $newSubArray;

} else {

$newArray[$this->dataEncode($key, false)] = $this->dataEncode($value, false);

}

}

ksort($newArray);

return $newArray;

}

private function getSignedHeaderNames()

{

$arryLen = count($this->headers);

$headerNames = "";

foreach ($this->headers as $key => $value) {

$headerNames = $headerNames . $key;

if ($arryLen > 1) {

$headerNames = $headerNames . ";";

$arryLen--;

}

}

return $headerNames;

}

private function signerLog($content, $line, $file)

{

if ($this->needLog) {

error_log($file . ":" . $line . ":[" . $content . "]\n", 3, "./signer_log");

}

}

}

?>

封装的工具类,集成了常用的方法

Utils.php

/**

* Created by PhpStorm.

* User: 王中阳

* Date: 2019/7/24

* Time: 9:45

*/

require 'Signer.php';

define('AK', "your ak");

define('SK', "your sk");

define('HOST', "sem.baidubce.com"); //按百度要求换内容

define('BASE_URL', "http://sem.baidubce.com/");//按百度要求换内容

define('HTTP_Method', "POST");//按百度要求换内容

class Utils

{

//公共header 注意:我对接的是百度信息流推广api,header应根据百度云各服务的要求进行修改

static function Header()

{

return [

'opUsername' => 'xxxxxxx',

'opPassword' => 'xxxxxxx',

'tgUsername' => 'xxxxxxx',

'tgPassword' => 'xxxxxxx',

'bceUser' => 'xxxxxxx',

];

}

//请求百度

static function curl_post($url, $body, $auth)

{

//处理请求体

$files = [

'header' => self::Header(),

'body' => $body

];

$files = json_encode($files, JSON_UNESCAPED_UNICODE | JSON_UNESCAPED_SLASHES);

$ch = curl_init();

curl_setopt($ch, CURLOPT_POST, 1);

curl_setopt($ch, CURLOPT_URL, $url);

curl_setopt($ch, CURLOPT_POSTFIELDS, $files);

curl_setopt($ch, CURLOPT_RETURNTRANSFER, 1);

curl_setopt($ch, CURLOPT_HTTPHEADER, array(

'Content-Type: application/json',

'host:sem.baidubce.com', //改成你的数据

'authorization:' . $auth,

'accept-encoding:gzip, deflate',

'accept:*/*'

)

);

$response = curl_exec($ch);

$request = curl_getinfo($ch, CURLINFO_HEADER_OUT);

$httpCode = curl_getinfo($ch, CURLINFO_HTTP_CODE);

self::result($httpCode, $response);

}

//校验权限

static function gen_auth($uri = "")

{

$headers = array();

$headers['host'] = HOST;

$signer = new \Signer(AK, SK);

$signer->setMethod(HTTP_Method);

$signer->setUri($uri);

$signer->setSignHeaders($headers);

try {

$signature = $signer->genAuthorization();

return $signature;

} catch (SignerException $e) {

echo $e->getMessage();

return;

}

}

//返回结果

static public function result($errno = 0, $data = '')

{

header("Content-type: application/json;charset=utf-8");

$errno = intval($errno);

//注意:这里可能不满足你的项目 根据百度返回结果做修改 或者不用我这种处理方式

//json转数组

$data = json_decode($data, true);

if (isset($data['header']['failures'][0])) {

$message = $data['header']['failures'][0]['message'];

} else {

$message = 'success';

}

$json = json_encode($data['body']['data'][0]);

$result = array(

'errno' => 1,

'message' => $message,

'data' => json_encode($data['body']['data'][0]),//处理百度 返回结果

);

echo json_encode($result, JSON_UNESCAPED_UNICODE | JSON_UNESCAPED_SLASHES);

exit;

}

/**

* 时间 日期

*/

static public function ymd($time)

{

return date("Y-m-d", $time);

}

}

业务层controller:百度api在请求接口的同时做权限校验

Account.php

namespace app\index\controller;

require 'Utils.php';

class Account

{

/**

* 获得账号信息

*/

public function info()

{

$uri = "v1/feed/cloud/AccountFeedService/getAccountFeed";

$auth = \Utils::gen_auth($uri);

$url = BASE_URL . $uri;

$body = [

'accountFeedFields' => [

'userId',

'balance',

'budget',

'balancePackage',

'userStat',

'uaStatus',

'validFlows',

],

];

//返回数据集成在Utils中

\Utils::curl_post($url, $body, $auth);

}

思路仅供参考。如有更好的处理方式,欢迎赐教。

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值