erp/app/Services/Business/KuaiTuanTuan/KuaiTuanTuan.php

168 lines
6.5 KiB
PHP
Raw Normal View History

<?php
namespace App\Services\Business\KuaiTuanTuan;
use App\Models\BusinessGoodsSku;
use App\Models\GoodsSku;
use App\Services\Business\BusinessClient;
use App\Models\Log;
use App\Utils\DateTimeUtils;
class KuaiTuanTuan extends BusinessClient
{
// 所有的请求和响应数据编码皆为utf-8格式url里的所有参数值请做urlencode编码。
// 如果请求的content-type是 application/x-www-form-urlencoded所有参数值也做urlencode编码
// 如果是multipart/form-data格式每个表单字段的参数值无需编码但每个表单字段的charset需要指定为utf-8
// 如果指定接口返回数据格式为JSON请指明header头content-type: application/json
protected $clientId = '8d7ca13bc27247b6a04e08404b51dfd8';
protected $clientSecret = '4478bc82dc1e1f68fe06c9f2bc683f1dcb3e6d83';
protected $publicParams = [
'type' => '',
'client_id' => '',
'access_token' => '', // 非必填,通过code获取的access_token
'timestamp' => '',
'data_type' => '', // 非必填,响应格式即返回数据的格式JSON或者XML二选一默认JSON注意是大写
'version' => '', // 非必填, API协议版本号默认为V1可不填
'sign' => ''
];
public function auth()
{
$accessToken = $this->getAccessTokenWithCode();
2022-08-08 16:00:47 +08:00
$accessToken['scope'] = json_encode($accessToken['scope'], 256);
$accessToken['pop_auth_token_create_response'] = json_encode($accessToken, 256);
2022-08-08 16:00:47 +08:00
$accessToken['status'] = 1;
$this->shop->update($accessToken);
return $this->shop;
}
2022-08-09 16:56:52 +08:00
public function downloadGoodsListAndBind($page = 1)
{
[$type, $appendParams] = Goods::downloadGoods($this->shop->owner_id, $page);
$log = Log::query()
->where('target_field', 'pdd.ktt.goods.query.list')
->where('target_id', $this->shop->id)
->orderBy('id', 'desc')
->first();
if ($log) {
$lastGetTime = DateTimeUtils::getMicroTime($log->created_at);
// 毫秒时间戳,往前算3分钟
$startTime = $lastGetTime - 30000;
$appendParams['update_time_start'] = $startTime;
$appendParams['update_time_end'] = DateTimeUtils::getMicroTime();
}
2022-08-08 15:05:17 +08:00
$res = $this->doRequest($type, $appendParams);
$goods = $res['ktt_goods_query_list_response']['goods_list'];
2022-08-06 16:38:04 +08:00
$this->bindGoods($goods);
$pageNum = ceil($res['ktt_goods_query_list_response']['total'] / $appendParams['size']);
if ($pageNum > $page && 30 >= $page) {
2022-08-17 13:40:51 +08:00
$this->downloadGoodsListAndBind($page + 1);
}
}
2022-08-06 16:38:04 +08:00
public function bindGoods($goods)
{
Goods::bindGoods($goods, $this->shop->id);
}
2022-08-16 21:02:31 +08:00
public function incrQuantity($businessGoodsSku, $num, $incremental)
{
2022-08-17 20:50:03 +08:00
[$type, $appendParams] = Goods::incrQuantity($businessGoodsSku['goods_id'], $businessGoodsSku['sku_id'], $num, $incremental ? 1 : 2);
2022-08-08 15:05:17 +08:00
$this->doRequest($type, $appendParams);
}
2022-08-09 10:34:36 +08:00
/**
2022-08-24 18:09:34 +08:00
* 下载订单
2022-08-09 10:34:36 +08:00
*
* @param $beginTime
* @param $endTime
2022-08-09 16:56:52 +08:00
* @param int $page
* @param string $downloadType
* @return void
2022-08-09 10:34:36 +08:00
*/
public function downloadOrdersAndSave($beginTime, $endTime, $downloadType = 'default', $page = 1)
{
if ('increment' === $downloadType) {
2022-08-09 16:56:52 +08:00
[$type, $appendParams] = Order::downloadIncrementOrders($beginTime, $endTime, $page);
2022-08-10 16:39:25 +08:00
$responseName = 'ktt_increment_order_query_response';
} else {
2022-08-09 16:56:52 +08:00
[$type, $appendParams] = Order::downloadOrders($beginTime, $endTime, $page);
2022-08-10 16:39:25 +08:00
$responseName = 'ktt_order_list_response';
}
2022-08-08 15:05:17 +08:00
$res = $this->doRequest($type, $appendParams);
2022-08-10 16:39:25 +08:00
$this->saveOrders($res[$responseName]['order_list']);
$pageNum = ceil($res[$responseName]['total_count'] / $appendParams['page_size']);
2022-08-24 18:09:34 +08:00
if ($pageNum > $page && 30 >= $page) {
$this->downloadOrdersAndSave($beginTime, $endTime, $downloadType, $page + 1);
2022-08-09 16:56:52 +08:00
}
}
2022-08-06 16:38:04 +08:00
protected function getAccessTokenWithCode()
{
$type = 'pdd.pop.auth.token.create';
$res = $this->doRequest($type, ['code' => $this->code]);
return $res['pop_auth_token_create_response'];
}
protected function getSign($params)
{
2022-08-08 13:59:44 +08:00
ksort($params);
2022-08-06 16:38:04 +08:00
$str = '';
foreach ($params as $key => $val) {
$str .= $key . $val;
}
$str = $this->clientSecret . $str . $this->clientSecret;
return strtoupper(md5($str));
}
2022-08-08 14:20:54 +08:00
public function doRequest($type, $appendParams = [], $url = 'https://gw-api.pinduoduo.com/api/router')
2022-08-06 16:38:04 +08:00
{
$publicParams = [
'type' => $type,
'client_id' => $this->clientId,
'timestamp' => time()
];
if ('pdd.pop.auth.token.create' !== $type) {
2022-08-08 16:00:47 +08:00
$publicParams['access_token'] = $this->getShop()->access_token;
2022-08-06 16:38:04 +08:00
}
$publicParams = array_merge($publicParams, $appendParams);
$publicParams['sign'] = $this->getSign($publicParams);
2022-09-01 09:56:08 +08:00
$res = $this->formDataPostRequest($url, $publicParams);
if (isset($res['error_response'])) {
// ToDo 重构异常处理
if ('业务服务错误' === $res['error_response']['error_msg'] && '该店铺下不存在该商品' === $res['error_response']['sub_msg']) {
BusinessGoodsSku::where('goods_id', $appendParams['goods_id'])->where('sku_id', $appendParams['sku_id'])->delete();
} else {
throw new \RuntimeException($res['error_response']['error_msg'] . ':' . $res['error_response']['error_msg']);
}
2022-09-01 09:56:08 +08:00
}
2022-08-06 16:38:04 +08:00
2022-09-01 09:56:08 +08:00
return $res;
2022-08-06 16:38:04 +08:00
}
public function downloadGoods($skuId)
{
$goodsSku = GoodsSku::query()
->with(['goods:id,goods_code'])
->find($skuId);
$code = $goodsSku->goods->goods_code . '_' . $goodsSku->sku_code;
$business = BusinessGoodsSku::query()->where('shop_id', $this->shop->id)->where('external_sku_id', $code)->first(['goods_id', 'sku_id']);
[$type, $appendParams] = Goods::downloadSingle($business->goods_id);
$res = $this->doRequest($type, $appendParams);
$goods = $res['response']['result'];
$this->bindGoods([$goods]);
}
public function getAuthUrl($shopId, $platId)
{
$state = $shopId . '_' . $platId;
return "https://oauth.pinduoduo.com/authorize/ktt?client_id={$this->clientId}&redirect_uri={$this->redirectUri}&state={$state}";
}
}