Channeldataapi.php 54 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416417418419420421422423424425426427428429430431432433434435436437438439440441442443444445446447448449450451452453454455456457458459460461462463464465466467468469470471472473474475476477478479480481482483484485486487488489490491492493494495496497498499500501502503504505506507508509510511512513514515516517518519520521522523524525526527528529530531532533534535536537538539540541542543544545546547548549550551552553554555556557558559560561562563564565566567568569570571572573574575576577578579580581582583584585586587588589590591592593594595596597598599600601602603604605606607608609610611612613614615616617618619620621622623624625626627628629630631632633634635636637638639640641642643644645646647648649650651652653654655656657658659660661662663664665666667668669670671672673674675676677678679680681682683684685686687688689690691692693694695696697698699700701702703704705706707708709710711712713714715716717718719720721722723724725726727728729730731732733734735736737738739740741742743744745746747748749750751752753754755756757758759760761762763764765766767768769770771772773774775776777778779780781782783784785786787788789790791792793794795796797798799800801802803804805806807808809810811812813814815816817818819820821822823824825826827828829830831832833834835836837838839840841842843844845846847848849850851852853854855856857858859860861862863864865866867868869870871872873874875876877878879880881882883884885886887888889890891892893894895896897898899900901902903904905906907908909910911912913914915916917918919920921922923924925926927928929930931932933934935936937938939940941942943944945946947948949950951952953954955956957958959960961962963964965966967968969970971972973974975976977978979980981982983984985986987988989990991992993994995996997998999100010011002100310041005100610071008100910101011101210131014101510161017101810191020102110221023102410251026102710281029103010311032103310341035103610371038103910401041104210431044104510461047104810491050105110521053105410551056105710581059106010611062106310641065106610671068106910701071107210731074107510761077107810791080108110821083108410851086108710881089109010911092109310941095109610971098109911001101110211031104110511061107110811091110111111121113111411151116111711181119112011211122112311241125112611271128112911301131113211331134113511361137113811391140114111421143114411451146114711481149115011511152115311541155115611571158115911601161116211631164116511661167116811691170117111721173117411751176117711781179118011811182118311841185118611871188118911901191119211931194119511961197119811991200120112021203120412051206120712081209121012111212121312141215121612171218121912201221122212231224122512261227122812291230
  1. <?php
  2. /**
  3. * Created by: PhpStorm
  4. * User: lytian
  5. * Date: 2020/3/11
  6. * Time: 14:44
  7. */
  8. namespace app\api\controller;
  9. use app\common\controller\Api;
  10. use app\common\library\Redis;
  11. use app\main\constants\AdminConstants;
  12. use app\main\constants\ApiConstants;
  13. use app\main\constants\CacheConstants;
  14. use app\main\constants\UserConstants;
  15. use app\main\helper\ArrayHelper;
  16. use app\main\service\AdminService;
  17. use app\main\service\ApiService;
  18. use app\main\service\LogService;
  19. use app\main\service\ReferralService;
  20. use app\main\service\UserDdFlushService;
  21. use app\main\service\UserService;
  22. use app\main\service\VisitLimitService;
  23. use think\Config;
  24. use think\Db;
  25. use think\Env;
  26. use think\Exception;
  27. use think\Log;
  28. class Channeldataapi extends Api
  29. {
  30. protected $clientConfig = [];
  31. protected $books = [];
  32. public function _initialize()
  33. {
  34. parent::_initialize(); // TODO: Change the autogenerated stub
  35. $this->checkSign();
  36. }
  37. /**
  38. * 指定日期的活跃用户信息
  39. */
  40. public function userinfo()
  41. {
  42. $result = [
  43. 'last_id' => 0,
  44. 'count' => 0,
  45. 'push_time' => time(),
  46. 'list' => []
  47. ];
  48. $channel_id = (int)$this->request->param('channel_id');
  49. $search_date = $this->request->param('search_date');
  50. $last_id = (int)$this->request->param('last_id', 0);
  51. $is_order = (int)$this->request->param('is_order', 0);
  52. if (empty($channel_id)) {
  53. $this->result([], 20001, 'channel_id参数必填', "json");
  54. }
  55. if (empty($search_date)) {
  56. $this->result([], 20001, 'search_date参数必填', "json");
  57. }
  58. $order = $is_order > 0 ? ' desc ' : ' asc ';
  59. $gt = $is_order > 0 ? ' < ' : ' > ';
  60. $idSql = " id {$gt} {$last_id} AND ";
  61. if ($is_order && !$last_id){
  62. $idSql = '';
  63. }
  64. try {
  65. $expandDbConfig = Config::get("expanddb");
  66. $expandDb = Db::connect($expandDbConfig);
  67. $sql = "SELECT * FROM channel_active_user WHERE {$idSql} channel_id = {$channel_id} AND active_date = '{$search_date}' ORDER BY id {$order} LIMIT 1000";
  68. $rows = $expandDb->query($sql);
  69. $list = [];
  70. //定位渠道和代理
  71. $mainSlaveDbConfig = $this->getMainSlaveDbConfig();
  72. $adminIdsRes = Db::connect($mainSlaveDbConfig)->query("select admin.id, ac.appid, JSON_EXTRACT(ac.json,'$.authorizer_info.nick_name') as app_nickname from admin left join admin_config ac on ac.admin_id = admin.id where admin.id = {$channel_id}");
  73. if ($rows) {
  74. $whereSql = "";
  75. if ($this->clientConfig['is_all'] == '0') {
  76. //不包含扣量
  77. $whereSql = " AND is_black != 1 ";
  78. }
  79. $user_ids = array_column($rows, 'user_id');
  80. $groups = [];
  81. $mod = Config::get('db.user_num');
  82. foreach ($user_ids as $user_id) {
  83. $dbId = $user_id % $mod;
  84. if (isset($groups[$dbId])) {
  85. $groups[$dbId][] = $user_id;
  86. } else {
  87. $groups[$dbId] = [$user_id];
  88. }
  89. }
  90. foreach ($groups as $dbId => $user_id_arr) {
  91. $user_id_str = implode(',', $user_id_arr);
  92. $userDbConfig = $this->getDbDeploy($dbId, 'user');
  93. $userTable = $userDbConfig['table'] . '.user';
  94. unset($userDbConfig['table']);
  95. $user_rows = Db::connect($userDbConfig)->query("SELECT id as user_id, nickname, openid, mobile, province, city, sex, is_subscribe,subscribe_time, operate_time as operatetime, createtime as registertime, channel_id,register_ip FROM {$userTable} WHERE id IN ({$user_id_str}) $whereSql");
  96. foreach ($user_rows as $user_row) {
  97. $item = array_merge($user_row, [
  98. 'authorizer_nickname' => str_replace(['"'], [''], $adminIdsRes[0]['app_nickname']),
  99. 'authorizer_appid' => $adminIdsRes[0]['appid']
  100. ]);
  101. //转换一下数据类型为string
  102. $this->toString($item);
  103. $list[] = $item;
  104. unset($item);
  105. }
  106. }
  107. $result['last_id'] = end($rows)['id'];
  108. $result['count'] = count($list);
  109. $result['push_time'] = time();
  110. $result['list'] = $list;
  111. }
  112. } catch (\Exception $e) {
  113. Log::error("接口错误: API: userinfo params:" . json_encode($this->request->param()) . " error" . $e->getMessage());
  114. }
  115. $action = $this->request->action();
  116. $this->setLimit($action);
  117. $this->result($result);
  118. }
  119. /**
  120. * 订单记录
  121. */
  122. public function orders()
  123. {
  124. $result = [
  125. 'last_id' => 0,
  126. 'count' => 0,
  127. 'push_time' => time(),
  128. 'list' => []
  129. ];
  130. $channel_id = (int)$this->request->param('channel_id');
  131. $search_date = $this->request->param('search_date');
  132. $last_id = (int)$this->request->param('last_id', 0);
  133. $is_order = (int)$this->request->param('is_order', 0);
  134. if (empty($channel_id)) {
  135. $this->result([], 20001, 'channel_id参数必填', "json");
  136. }
  137. if (empty($search_date)) {
  138. $this->result([], 20001, 'search_date参数必填', "json");
  139. }
  140. $list = [];
  141. $order = $is_order > 0 ? ' desc ' : ' asc ';
  142. $gt = $is_order > 0 ? ' < ' : ' > ';
  143. $idSql = " id {$gt} {$last_id} AND ";
  144. if ($is_order && !$last_id){
  145. $idSql = '';
  146. }
  147. $userlist = [];
  148. //$channelInfo = model('adminConfig')->field('appid,json')->where('admin_id','=',$channel_id)->find();
  149. try {
  150. $selectBegin = strtotime($search_date);
  151. $selectEnd = $selectBegin + 86400;
  152. $whereSql = "";
  153. if ($this->clientConfig['is_all'] == '0') {
  154. //不包含扣量
  155. $whereSql = " AND deduct = 0 ";
  156. }
  157. $sql = "SELECT id, user_id, out_trade_no as merchant_id, transaction_id, type, money, state, business_line as `from`, createtime as create_time, finishtime as finish_time, book_id, referral_id, referral_id_permanent, admin_id as channel_id FROM orders FORCE INDEX(createtime) WHERE {$idSql} admin_id in({$channel_id}) AND createtime >= {$selectBegin} AND createtime < {$selectEnd} {$whereSql} ORDER BY createtime {$order} LIMIT 1000";
  158. if (Config::get('polardb.orders_apply_polardb')) {
  159. $rows = Db::connect(Config::get('polardb'))->query($sql);
  160. } else {
  161. $mainSlaveDbConfig = $this->getMainSlaveDbConfig();
  162. $rows = Db::connect($mainSlaveDbConfig)->query($sql);
  163. }
  164. if ($rows) {
  165. $userIds = array_unique(array_column($rows,'user_id'));
  166. $userlist = $this->getUserList($userIds);
  167. foreach ($rows as $row) {
  168. $last_id = $row['id'];
  169. $bookId = $row['book_id'];
  170. $referralId = $row['referral_id'] ?: ($row['referral_id_permanent'] ?: 0);
  171. unset($row['id']);
  172. unset($row['book_id']);
  173. unset($row['referral_id_permanent']);
  174. $bookName = $bookTags = $referralUrl = '';
  175. if ($bookId) {
  176. list($bookName, $bookTags) = $this->getBook($bookId);
  177. }
  178. if ($referralId) {
  179. $referralUrl = '/t/' . $referralId;
  180. }
  181. $row['referral_id'] = $referralId;
  182. $item = array_merge($row, ['book_name' => $bookName, 'book_tags' => $bookTags, 'referral_url' => $referralUrl]);
  183. $item['subscribe_time'] = isset($userlist[$row['user_id']]) ? $userlist[$row['user_id']]['subscribe_time'] : 0;
  184. $item['user_createtime'] = isset($userlist[$row['user_id']]) ? $userlist[$row['user_id']]['createtime'] : '';
  185. $item['openid'] = isset($userlist[$row['user_id']]) ? $userlist[$row['user_id']]['openid'] : '';
  186. $item['register_ip'] = isset($userlist[$row['user_id']]) ? $userlist[$row['user_id']]['register_ip'] : '';
  187. //转换一下数据类型为string
  188. $this->toString($item);
  189. $list[] = $item;
  190. unset($item);
  191. }
  192. }
  193. // $result['appid'] = $channelInfo['appid'] ?? '';
  194. // $result['nick_name'] = $channelInfo['json']['authorizer_info']['nick_name'] ?? '';
  195. $result['last_id'] = $last_id;
  196. $result['list'] = $list;
  197. $result['count'] = count($list);
  198. $result['push_time'] = time();
  199. } catch (\Exception $e) {
  200. Log::error("接口错误: API: orders params:" . json_encode($this->request->param()) . " error" . $e->getMessage());
  201. }
  202. $action = $this->request->action();
  203. $this->setLimit($action);
  204. $this->result($result);
  205. }
  206. /**
  207. * 客服消息
  208. */
  209. public function custom()
  210. {
  211. $result = [
  212. 'last_id' => 0,
  213. 'count' => 0,
  214. 'push_time' => time(),
  215. 'list' => []
  216. ];
  217. $channel_id = (int)$this->request->param('channel_id');
  218. $search_date = $this->request->param('search_date');
  219. $last_id = (int)$this->request->param('last_id', 0);
  220. if (empty($channel_id)) {
  221. $this->result([], 20001, 'channel_id参数必填', "json");
  222. }
  223. if (empty($search_date)) {
  224. $this->result([], 20001, 'search_date参数必填', "json");
  225. }
  226. $list = [];
  227. try {
  228. $selectBegin = strtotime($search_date);
  229. $selectEnd = $selectBegin + 86400;
  230. $mainSlaveDbConfig = $this->getMainSlaveDbConfig();
  231. $sql = "SELECT id as custom_id, admin_id as channel_id, title, sendtime as send_time, send_num, createtime as create_time,user_json FROM custom WHERE id > {$last_id} AND admin_id in({$channel_id}) AND sendtime >= {$selectBegin} AND sendtime < {$selectEnd} ORDER BY id ASC LIMIT 1000";
  232. $rows = Db::connect($mainSlaveDbConfig)->query($sql);
  233. if ($rows) {
  234. $adminIdsRes = Db::connect($mainSlaveDbConfig)->query("select admin.id, ac.appid, JSON_EXTRACT(ac.json,'$.authorizer_info.nick_name') as app_nickname from admin left join admin_config ac on ac.admin_id = admin.id where admin.id = {$channel_id}");
  235. $customIds = array_column($rows, 'custom_id');
  236. $customIdStr = implode(',', $customIds);
  237. $sql = "SELECT custom_id, sum(uv) as uv, sum(recharge_money) as recharge_money FROM custom_url_collect WHERE custom_id in({$customIdStr}) GROUP BY custom_id";
  238. $collectRes = Db::connect($mainSlaveDbConfig)->query($sql);
  239. $collectResGroup = ArrayHelper::index($collectRes, 'custom_id');
  240. $ids = array_column($rows, 'custom_id');
  241. $collectList = [];
  242. if (VisitLimitService::instance()->checkMigrated()) {
  243. $apiResult = ApiService::instance()->getCollectFromApi(ApiConstants::API_CUSTOM, ['ids' => $ids])->data;
  244. if ($apiResult) {
  245. foreach ($apiResult as $index => $item) {
  246. if (array_key_exists($item['cuId'], $collectList)) {
  247. $collectList[$item['cuId']]['uv'] += $item['uv'];
  248. $collectList[$item['cuId']]['recharge_money'] += $item['money'];
  249. } else {
  250. $collectList[$item['cuId']] = [
  251. 'uv' => $item['uv'],
  252. 'recharge_money' => $item['money'],
  253. ];
  254. }
  255. }
  256. }
  257. }
  258. foreach ($rows as $row) {
  259. $last_id = $row['custom_id'];
  260. $userJson = json_decode($row['user_json'],true);
  261. $row['is_all_user'] = $userJson['all'] ?? 0;
  262. unset($row['user_json']);
  263. $item = array_merge($row, [
  264. 'authorizer_nickname' => str_replace(['"'], [''], $adminIdsRes[0]['app_nickname']),
  265. 'authorizer_appid' => $adminIdsRes[0]['appid']
  266. ]);
  267. if (VisitLimitService::instance()->checkMigrated()) {
  268. if (array_key_exists($row['custom_id'], $collectList)) {
  269. $item['recharge_money'] = $collectList[$row['custom_id']]['recharge_money'];
  270. $item['uv'] = $collectList[$row['custom_id']]['uv'];
  271. } else {
  272. $item['recharge_money'] = 0;
  273. $item['uv'] = 0;
  274. }
  275. } else {
  276. //拉取uv
  277. if (isset($collectResGroup[$row['custom_id']])) {
  278. $item['uv'] = $collectResGroup[$row['custom_id']]['uv'];
  279. } else {
  280. $item['uv'] = 0;
  281. }
  282. //拉取总充值金额
  283. if (isset($collectResGroup[$row['custom_id']])) {
  284. $item['recharge_money'] = $collectResGroup[$row['custom_id']]['recharge_money'];
  285. } else {
  286. $item['recharge_money'] = 0;
  287. }
  288. }
  289. //转换一下数据类型为string
  290. $this->toString($item);
  291. $list[] = $item;
  292. unset($item);
  293. }
  294. }
  295. $result['last_id'] = $last_id;
  296. $result['count'] = count($list);
  297. $result['push_time'] = time();
  298. $result['list'] = $list;
  299. } catch (\Exception $e) {
  300. Log::error("接口错误: API: userinfo params:" . json_encode($this->request->param()) . " error" . $e->getMessage());
  301. }
  302. $action = $this->request->action();
  303. $this->setLimit($action);
  304. $this->result($result);
  305. }
  306. public function customnew()
  307. {
  308. $result = [
  309. 'last_id' => 0,
  310. 'count' => 0,
  311. 'push_time' => time(),
  312. 'list' => []
  313. ];
  314. $channel_id = (int)$this->request->param('channel_id');
  315. $search_date = $this->request->param('search_date');
  316. $last_id = (int)$this->request->param('last_id', 0);
  317. if (empty($channel_id)) {
  318. $this->result([], 20001, 'channel_id参数必填', "json");
  319. }
  320. if (empty($search_date)) {
  321. $this->result([], 20001, 'search_date参数必填', "json");
  322. }
  323. $selectBegin = strtotime($search_date);
  324. $selectEnd = $selectBegin + 86400;
  325. $mainSlaveDbConfig = $this->getMainSlaveDbConfig();
  326. $sql = "SELECT
  327. cu.id last_id, c.id AS custom_id, c.title, cu.idx,admin_id AS channel_id, c.sendtime AS send_time, send_num, c.createtime AS create_time, book_id,
  328. book_name, push_type, uv, recharge_money,recharge_orders,c.user_json
  329. FROM
  330. custom c
  331. LEFT JOIN custom_url cu on c.id=cu.custom_id && cu.id >{$last_id}
  332. LEFT JOIN custom_url_collect cc on (cu.custom_id=cc.custom_id && cu.idx=cc.idx)
  333. where c.admin_id in({$channel_id}) AND c.sendtime >= {$selectBegin} AND c.sendtime < {$selectEnd} and cu.id is not null";
  334. $rows = Db::connect($mainSlaveDbConfig)->query($sql);
  335. if ($rows){
  336. $adminIdsRes = Db::connect($mainSlaveDbConfig)->query("select admin.id,admin.nickname, ac.appid, JSON_EXTRACT(ac.json,'$.authorizer_info.nick_name') as app_nickname from admin left join admin_config ac on ac.admin_id = admin.id where admin.id = {$channel_id}");
  337. $ids = array_column($rows, 'custom_id');
  338. $collectList = [];
  339. if (VisitLimitService::instance()->checkMigrated()) {
  340. $apiResult = ApiService::instance()->getCollectFromApi(ApiConstants::API_CUSTOM, ['ids' => $ids])->data;
  341. if ($apiResult) {
  342. foreach ($apiResult as $index => $item) {
  343. if (!array_key_exists($item['cuId'], $collectList)) {
  344. $collectList[$item['cuId']] = [];
  345. }
  346. $collectList[$item['cuId']][$item['idx']] = [
  347. 'uv' => $item['uv'],
  348. 'money' => $item['money'],
  349. 'orders' => $item['orders'],
  350. ];
  351. }
  352. }
  353. }
  354. foreach ($rows as &$row) {
  355. $userJson = json_decode($row['user_json'],true);
  356. $row['is_all_user'] = $userJson['is_all'] ?? 0;
  357. $row['channel_name'] = $adminIdsRes[0]['nickname'];
  358. $row['authorizer_nickname'] = str_replace(['"'], [''], $adminIdsRes[0]['app_nickname']);
  359. $row['authorizer_appid'] = $adminIdsRes[0]['appid'];
  360. if ($find = ArrayHelper::array_find($collectList, $row['custom_id'].'.'.$row['idx'])) {
  361. $row['uv'] = $collectList[$row['custom_id']][$row['idx']]['uv'];
  362. $row['recharge_money'] = $collectList[$row['custom_id']][$row['idx']]['money'];
  363. $row['recharge_orders'] = $collectList[$row['custom_id']][$row['idx']]['orders'];
  364. }
  365. unset($row['user_json']);
  366. }
  367. }
  368. $result['last_id'] = (int)end($rows)['last_id'];
  369. $result['count'] = count($rows);
  370. $result['push_time'] = time();
  371. $result['list'] = $rows;
  372. $this->result($result);
  373. }
  374. /**
  375. * 充值记录
  376. */
  377. public function recharge()
  378. {
  379. $result = [
  380. 'last_id' => 0,
  381. 'count' => 0,
  382. 'push_time' => time(),
  383. 'list' => []
  384. ];
  385. $user_id = (int)$this->request->param('user_id');
  386. $channel_id = (int)$this->request->param('channel_id');
  387. $search_date = $this->request->param('search_date');
  388. $last_id = (int)$this->request->param('last_id', 0);
  389. if (empty($user_id)) {
  390. $this->result(['error_code' => 20001, 'error_msg' => 'user_id参数必填'], 0, '', "json");
  391. $this->result([], 20001, 'user_id参数必填', "json");
  392. }
  393. if (empty($channel_id)) {
  394. $this->result([], 20001, 'channel_id参数必填', "json");
  395. }
  396. if (empty($search_date)) {
  397. $this->result([], 20001, 'search_date参数必填', "json");
  398. }
  399. $list = [];
  400. try {
  401. $selectBegin = strtotime($search_date);
  402. $selectEnd = $selectBegin + 86400;
  403. $userDbConfig = $this->getDbDeploy($user_id, 'user');
  404. $rechargeTable = $userDbConfig['table'] . '.recharge';
  405. $userTable = $userDbConfig['table'] . '.user';
  406. unset($userDbConfig['table']);
  407. $userRow = Db::connect($userDbConfig)->query("select id, is_black, flush_state from {$userTable} where id = {$user_id} and channel_id = {$channel_id}");
  408. if (empty($userRow)) {
  409. $action = $this->request->action();
  410. $this->setLimit($action);
  411. $this->result($result);
  412. } else {
  413. if ($this->clientConfig['is_all'] == '0') {
  414. if ($userRow[0]['is_black'] == AdminConstants::ADMIN_KL_BLACK_YES) {
  415. Log::info("匹配到黑名单用户:user_id: {$user_id} channel_id: {$channel_id}");
  416. $action = $this->request->action();
  417. $this->setLimit($action);
  418. $this->result($result);
  419. }
  420. }
  421. //是否有扣量订单
  422. $sql = "SELECT count(1) as total FROM orders WHERE user_id = {$user_id} AND state = '1' AND deduct = 1";
  423. if (Config::get('polardb.orders_apply_polardb')) {
  424. $countRes = Db::connect(Config::get('polardb'))->query($sql);
  425. } else {
  426. $mainSlaveDbConfig = $this->getMainSlaveDbConfig();
  427. $countRes = Db::connect($mainSlaveDbConfig)->query($sql);
  428. }
  429. if ($userRow[0]['flush_state'] != UserConstants::USER_FLUSH_STATE_ADMIN) {
  430. UserDdFlushService::instance()->checkUserFlushState($user_id);
  431. UserDdFlushService::instance()->flushVip($user_id);
  432. if ($countRes[0]['total'] > 0) {
  433. UserDdFlushService::instance()->flushUserConsume($user_id);
  434. }
  435. UserService::instance()->getUserModel()->setConnect($user_id)->update(['flush_state' => UserConstants::USER_FLUSH_STATE_ADMIN], ['id' => $user_id]);
  436. $cacheUser = CacheConstants::getUserCacheKey($user_id);
  437. Redis::instance()->del($cacheUser);
  438. }
  439. //拉取充值记录
  440. $whereSql = "";
  441. if ($this->clientConfig['is_all'] == '0') {
  442. //过滤dd
  443. $whereSql = " AND dd = 0 ";
  444. }
  445. $rechargeRows = Db::connect($userDbConfig)->query("SELECT id as recharge_id, user_id, type, kandian as shubi, free_kandian as free_shubi, free_endtime, day, hour, createtime as create_time, vip_starttime FROM {$rechargeTable} WHERE id > {$last_id} AND user_id in({$user_id}) AND createtime >= {$selectBegin} AND createtime < {$selectEnd} {$whereSql} ORDER BY id asc limit 1000");
  446. if ($rechargeRows) {
  447. foreach ($rechargeRows as $rechargeRow) {
  448. $last_id = $rechargeRow['recharge_id'];
  449. $vipEndtime = '';
  450. if ($rechargeRow['day'] || $rechargeRow['hour']) {
  451. $day = $rechargeRow['day'];
  452. $hour = $rechargeRow['hour'];
  453. $vipEndtime = $rechargeRow['vip_starttime'] + 86400 * $day + $hour * 3600;
  454. }
  455. $item = array_merge($rechargeRow, ['vip_endtime' => $vipEndtime]);
  456. $item['channel_id'] = $channel_id;
  457. $this->toString($item);
  458. $list[] = $item;
  459. unset($item);
  460. }
  461. }
  462. $result['last_id'] = $last_id;
  463. $result['count'] = count($list);
  464. $result['push_time'] = time();
  465. $result['list'] = $list;
  466. }
  467. } catch (\Exception $e) {
  468. Log::error("接口错误: API: recharge params:" . json_encode($this->request->param()) . " error" . $e->getMessage());
  469. }
  470. $action = $this->request->action();
  471. $this->setLimit($action);
  472. $this->result($result);
  473. }
  474. /**
  475. * 消费
  476. */
  477. public function consume()
  478. {
  479. $result = [
  480. 'last_id' => 0,
  481. 'count' => 0,
  482. 'push_time' => time(),
  483. 'list' => []
  484. ];
  485. $user_id = (int)$this->request->param('user_id');
  486. $channel_id = (int)$this->request->param('channel_id');
  487. $search_date = $this->request->param('search_date');
  488. $last_id = (int)$this->request->param('last_id', 0);
  489. if (empty($user_id)) {
  490. $this->result(['error_code' => 20001, 'error_msg' => 'user_id参数必填'], 0, '', "json");
  491. $this->result([], 20001, 'user_id参数必填', "json");
  492. }
  493. if (empty($channel_id)) {
  494. $this->result([], 20001, 'channel_id参数必填', "json");
  495. }
  496. if (empty($search_date)) {
  497. $this->result([], 20001, 'search_date参数必填', "json");
  498. }
  499. $list = [];
  500. try {
  501. $selectBegin = strtotime($search_date);
  502. $selectEnd = $selectBegin + 86400;
  503. $userDbConfig = $this->getDbDeploy($user_id, 'user');
  504. $shardDbConfig = $this->getDbDeploy($user_id, 'shard');
  505. $consumeTable = $shardDbConfig['table'] . '.consume';
  506. $userTable = $userDbConfig['table'] . '.user';
  507. unset($userDbConfig['table']);
  508. unset($shardDbConfig['table']);
  509. $userRow = Db::connect($userDbConfig)->query("select id, is_black, flush_state from {$userTable} where id = {$user_id} and channel_id = {$channel_id}");
  510. if (empty($userRow)) {
  511. $action = $this->request->action();
  512. $this->setLimit($action);
  513. $this->result($result);
  514. } else {
  515. if ($this->clientConfig['is_all'] == '0') {
  516. if ($userRow[0]['is_black'] == AdminConstants::ADMIN_KL_BLACK_YES) {
  517. Log::info("匹配到黑名单用户:user_id: {$user_id} channel_id: {$channel_id}");
  518. $action = $this->request->action();
  519. $this->setLimit($action);
  520. $this->result($result);
  521. }
  522. }
  523. //是否有扣量订单
  524. $sql = "SELECT count(1) as total FROM orders WHERE user_id = {$user_id} AND state = '1' AND deduct = 1";
  525. if (Config::get('polardb.orders_apply_polardb')) {
  526. $countRes = Db::connect(Config::get('polardb'))->query($sql);
  527. } else {
  528. $mainSlaveDbConfig = $this->getMainSlaveDbConfig();
  529. $countRes = Db::connect($mainSlaveDbConfig)->query($sql);
  530. }
  531. if ($userRow[0]['flush_state'] != UserConstants::USER_FLUSH_STATE_ADMIN) {
  532. UserDdFlushService::instance()->checkUserFlushState($user_id);
  533. UserDdFlushService::instance()->flushVip($user_id);
  534. if ($countRes[0]['total'] > 0) {
  535. UserDdFlushService::instance()->flushUserConsume($user_id);
  536. }
  537. UserService::instance()->getUserModel()->setConnect($user_id)->update(['flush_state' => UserConstants::USER_FLUSH_STATE_ADMIN], ['id' => $user_id]);
  538. $cacheUser = CacheConstants::getUserCacheKey($user_id);
  539. Redis::instance()->del($cacheUser);
  540. }
  541. //拉取充值记录
  542. $whereSql = "";
  543. if ($this->clientConfig['is_all'] == '0') {
  544. //过滤dd
  545. $whereSql = " AND free_kandian+kandian-dd_free_kandian-dd_kandian>0 ";
  546. }
  547. $consumeSql = "SELECT id as consume_id, user_id, createtime as consume_time, book_id, book_name, chapter_id, chapter_name, (kandian - dd_kandian) as shubi, (free_kandian - dd_free_kandian) as free_shubi FROM {$consumeTable} WHERE id > {$last_id} AND user_id in ({$user_id}) AND createtime >= {$selectBegin} AND createtime < {$selectEnd} {$whereSql} ORDER BY id asc LIMIT 1000";
  548. $consumeRows = Db::connect($shardDbConfig)->query($consumeSql);
  549. if ($consumeRows) {
  550. foreach ($consumeRows as $consumeRow) {
  551. $last_id = $consumeRow['consume_id'];
  552. $item = array_merge($consumeRow);
  553. $item['channel_id'] = $channel_id;
  554. $this->toString($item);
  555. $list[] = $item;
  556. unset($item);
  557. }
  558. }
  559. $result['last_id'] = $last_id;
  560. $result['count'] = count($list);
  561. $result['push_time'] = time();
  562. $result['list'] = $list;
  563. }
  564. } catch (\Exception $e) {
  565. Log::error("接口错误: API: consume params:" . json_encode($this->request->param()) . " error" . $e->getMessage());
  566. }
  567. $action = $this->request->action();
  568. $this->setLimit($action);
  569. $this->result($result);
  570. }
  571. /**
  572. * 最近阅读记录
  573. */
  574. public function recent()
  575. {
  576. $result = [
  577. 'last_id' => 0,
  578. 'count' => 0,
  579. 'push_time' => time(),
  580. 'list' => []
  581. ];
  582. $user_id = (int)$this->request->param('user_id');
  583. $channel_id = (int)$this->request->param('channel_id');
  584. $search_date = $this->request->param('search_date');
  585. $last_id = (int)$this->request->param('last_id', 0);
  586. if (empty($user_id)) {
  587. $this->result(['error_code' => 20001, 'error_msg' => 'user_id参数必填'], 0, '', "json");
  588. $this->result([], 20001, 'user_id参数必填', "json");
  589. }
  590. if (empty($channel_id)) {
  591. $this->result([], 20001, 'channel_id参数必填', "json");
  592. }
  593. if (empty($search_date)) {
  594. $this->result([], 20001, 'search_date参数必填', "json");
  595. }
  596. $list = [];
  597. try {
  598. $selectBegin = strtotime($search_date);
  599. $selectEnd = $selectBegin + 86400;
  600. $userDbConfig = $this->getDbDeploy($user_id, 'user');
  601. $shardDbConfig = $this->getDbDeploy($user_id, 'shard');
  602. $recentTable = $shardDbConfig['table'] . '.user_recently_read';
  603. $userTable = $userDbConfig['table'] . '.user';
  604. unset($userDbConfig['table']);
  605. unset($shardDbConfig['table']);
  606. $userRow = Db::connect($userDbConfig)->query("select id, is_black, flush_state from {$userTable} where id = {$user_id} and channel_id = {$channel_id}");
  607. if (empty($userRow)) {
  608. $action = $this->request->action();
  609. $this->setLimit($action);
  610. $this->result($result);
  611. } else {
  612. if ($this->clientConfig['is_all'] == '0') {
  613. if ($userRow[0]['is_black'] == AdminConstants::ADMIN_KL_BLACK_YES) {
  614. Log::info("匹配到黑名单用户:user_id: {$user_id} channel_id: {$channel_id}");
  615. $action = $this->request->action();
  616. $this->setLimit($action);
  617. $this->result($result);
  618. }
  619. }
  620. //拉取阅读记录
  621. $recentSql = "SELECT id as recent_id, user_id, book_id, chapter_id, chapter_name, flag, updatetime as update_time FROM {$recentTable} WHERE id > {$last_id} AND user_id in ({$user_id}) AND updatetime >= {$selectBegin} AND updatetime < {$selectEnd} ORDER BY id asc LIMIT 1000";
  622. $recentRows = Db::connect($shardDbConfig)->query($recentSql);
  623. if ($recentRows) {
  624. foreach ($recentRows as $recentRow) {
  625. $last_id = $recentRow['recent_id'];
  626. list($bookName, $bookTags) = $this->getBook($recentRow['book_id']);
  627. unset($bookTags);
  628. $item = array_merge($recentRow, ['book_name' => $bookName]);
  629. unset($bookName);
  630. $this->toString($item);
  631. $list[] = $item;
  632. unset($item);
  633. }
  634. }
  635. unset($recentRows);
  636. $result['last_id'] = $last_id;
  637. $result['count'] = count($list);
  638. $result['push_time'] = time();
  639. $result['list'] = $list;
  640. }
  641. } catch (\Exception $e) {
  642. Log::error("接口错误: API: recent params:" . json_encode($this->request->param()) . " error" . $e->getMessage());
  643. }
  644. $action = $this->request->action();
  645. $this->setLimit($action);
  646. $this->result($result);
  647. }
  648. /**
  649. * 验证签名
  650. */
  651. private function checkSign()
  652. {
  653. $params = $this->request->param();
  654. $signaure = $params['signaure'] ?? '';
  655. $client_id = $params['client_id'] ?? '';
  656. $timestamp = $params['timestamp'] ?? '';
  657. $nonce = $params['nonce'] ?? '';
  658. if (!$signaure || !$client_id || !$timestamp || !$nonce) {
  659. $this->result([], 11000, '缺少参数', 'json');
  660. }
  661. $this->clientConfig = $clientConfig = model("DataApiConfig")->getInfo($client_id);
  662. //限制访问频率
  663. $action = $this->request->action();
  664. $this->getLimit($action);
  665. //还需验证后台是否关闭接口
  666. if (empty($clientConfig)) {
  667. $this->result([], 10005, 'client_id不存在', 'json');
  668. }
  669. $token = $this->clientConfig['token'];
  670. if ($signaure === sha1($token . $timestamp . $client_id . $nonce)) {
  671. if ($clientConfig['status'] != '1') {
  672. $this->result([], 10003, '接口已禁用', 'json');
  673. }
  674. $configChannelIds = array_filter(array_unique(explode(',', $this->clientConfig['channel_ids'])));
  675. if (isset($this->clientConfig['vip_id']) && !empty($this->clientConfig['vip_id'])){//查看vip下的权限
  676. $vipChannelIds = $this->getChannelIdByVip($this->clientConfig['vip_id']);
  677. $configChannelIds = array_merge($vipChannelIds,$configChannelIds);
  678. }
  679. $channel_id = (int)$this->request->param('channel_id');
  680. $vip_id = (int)$this->request->param('vip_id');
  681. if( $vip_id && strstr($this->clientConfig['vip_id'],(string)$vip_id) !== false){
  682. return;
  683. }
  684. if ( !in_array($channel_id, $configChannelIds)) {
  685. $this->result([], 10006, '没有权限查询该渠道信息', "json");
  686. }
  687. } else {
  688. $this->result([], 10001, '签名验证失败', 'json');
  689. }
  690. }
  691. /**
  692. * 返回结果
  693. * @param mixed $data
  694. * @param int $code
  695. * @param string $msg
  696. */
  697. public function result($data, $code = 0, $msg = '', $type = '', array $header = [])
  698. {
  699. exit(json_encode(
  700. [
  701. 'error_code' => $code,
  702. 'error_msg' => $msg,
  703. 'data' => $data
  704. ],
  705. 320
  706. ));
  707. }
  708. /**
  709. * 从库配置
  710. * @param $param
  711. * @param string $deploy
  712. * @return array|mixed
  713. */
  714. private function getDbDeploy($param, $deploy = 'shard')
  715. {
  716. $db = Config::get('db');
  717. $mod = $param % $db[$deploy . '_num'];
  718. $mod = abs($mod);
  719. $list = explode(';', $db[$deploy . '_list']);
  720. foreach ($list as $item) {
  721. $con = explode(':', $item); // 0=0-191库编号 1=192.168.1.149主IP 2=3306主端口 3=192.168.1.150从IP 4=3306从端口
  722. if (count($con) >= 3) {
  723. $c = explode('-', $con[0]); //库编号 0开始 1结束
  724. if (count($c) >= 2) {
  725. if ($c[0] <= $mod && $mod <= $c[1]) {
  726. $database = Config::get('database');
  727. if (count($con) >= 5) { //开启主从 & 带主从配置
  728. $database['deploy'] = 1;
  729. $database['rw_separate'] = true;
  730. $database['hostname'] = $con[1] . ',' . $con[3]; //192.168.1.149,192.168.1.150
  731. $database['hostport'] = $con[2] . ',' . $con[4]; //3306,3306
  732. } else { //只有主库
  733. $database['hostname'] = $con[1];
  734. $database['hostport'] = $con[2];
  735. }
  736. $database['database'] = 'mysql';
  737. $database['table'] = str_replace('$mod', $mod, $db[$deploy . '_database']);
  738. return $database;
  739. }
  740. }
  741. }
  742. }
  743. return [];
  744. }
  745. /**
  746. * 获取主库的从库配置 从库不存在返回主库
  747. * @return array
  748. */
  749. private function getMainSlaveDbConfig()
  750. {
  751. $hostArr = explode(',', Env::get('database.admin_hostname'));
  752. $portArr = explode(',', Env::get('database.admin_hostport', '3306,3306'));
  753. //默认主库
  754. $mainDbConfig = array_merge(Config::get("database"), ['hostname' => $hostArr[0], 'hostport' => $portArr[0]]);
  755. if (count($hostArr) >= 2) {
  756. //从库
  757. $mainDbConfig = array_merge(Config::get("database"),
  758. ['hostname' => $hostArr[1], 'hostport' => $portArr[1]]);
  759. }
  760. return $mainDbConfig;
  761. }
  762. /**
  763. * 转换数据
  764. * @param $data
  765. */
  766. private function toString(&$data)
  767. {
  768. if (is_array($data)) {
  769. array_walk($data, function (&$val, $key) {
  770. $val = strval($val);
  771. });
  772. }
  773. }
  774. /**
  775. * 返回书籍
  776. * @param $bookId
  777. * @return mixed
  778. * @throws Exception
  779. * @throws \think\db\exception\BindParamException
  780. * @throws \think\exception\PDOException
  781. */
  782. private function getBook($bookId)
  783. {
  784. if (!isset($this->books[$bookId])) {
  785. //查询
  786. $mainSlaveDbConfig = $this->getMainSlaveDbConfig();
  787. $bookSql = "select book.name, bc.name as category_name from book left join book_category as bc on bc.id = book.book_category_id where book.id = {$bookId}";
  788. $bookRow = Db::connect($mainSlaveDbConfig)->query($bookSql);
  789. $this->books[$bookId] = array_values($bookRow[0]);
  790. }
  791. return $this->books[$bookId];
  792. }
  793. /**
  794. * 增加限频次数
  795. * @param $apiMethod
  796. * @return int
  797. */
  798. private function setLimit($apiMethod)
  799. {
  800. $key = "ADL:" . $this->clientConfig['client_id']. ":" . $apiMethod;
  801. if (Redis::instance()->incrBy($key, 1) == 1){
  802. Redis::instance()->expire($key, 60);
  803. }
  804. return true;
  805. }
  806. /**
  807. * 判断限频次数
  808. * @param $apiMethod
  809. * @return bool
  810. */
  811. private function getLimit($apiMethod)
  812. {
  813. //限频
  814. $key = "ADL:" . $this->clientConfig['client_id']. ":" . $apiMethod;
  815. $times = (int)Redis::instance()->get($key);
  816. if ($times >= $this->clientConfig['access_limit']) {
  817. $this->result([], 10004, "接口达到限频 每分钟/{$this->clientConfig['access_limit']}次", 'json');
  818. }
  819. return true;
  820. }
  821. private function getUserList($userIds)
  822. {
  823. $groups = [];
  824. $mod = Config::get('db.user_num');
  825. foreach ($userIds as $userId) {
  826. $dbId = $userId % $mod;
  827. if (isset($groups[$dbId])) {
  828. $groups[$dbId][] = $userId;
  829. } else {
  830. $groups[$dbId] = [$userId];
  831. }
  832. }
  833. $userList = [];
  834. foreach ($groups as $dbId => $userIdArr) {
  835. $userIdStr = implode(',', $userIdArr);
  836. $userDbConfig = $this->getDbDeploy($dbId, 'user');
  837. $userTable = $userDbConfig['table'] . '.user';
  838. unset($userDbConfig['table']);
  839. $userRows = Db::connect($userDbConfig)->query("SELECT id, openid,subscribe_time,createtime,register_ip FROM {$userTable} WHERE id IN ({$userIdStr})");
  840. foreach ($userRows as $userRow) {
  841. $userList[$userRow['id']] = $userRow;
  842. }
  843. unset($userRows);
  844. }
  845. unset($groups);
  846. return $userList;
  847. }
  848. //20200317==================================
  849. /**
  850. * @param $vipId
  851. * @return array
  852. */
  853. private function getChannelIdByVip($vipId)
  854. {
  855. $mainSlaveDbConfig = $this->getMainSlaveDbConfig();
  856. $channelIds = Db::connect($mainSlaveDbConfig)->table('vip_admin_bind')
  857. ->force('uk_admin_relationship_bind')
  858. ->field('admin_id_master,admin_id_slave')
  859. ->where(['flag'=>1])
  860. ->whereIn('admin_id_master',$vipId)
  861. ->select();
  862. if (!empty($channelIds)){
  863. $channelIds = array_column($channelIds,'admin_id_slave');
  864. }
  865. return (array)$channelIds;
  866. }
  867. /**
  868. * 书单统计
  869. */
  870. public function getBookList()
  871. {
  872. $channelId = $this->request->param('channel_id');
  873. $lastId = (int)$this->request->param('last_id',0);
  874. $num = (int)$this->request->param('num',200);
  875. $mainSlaveDbConfig = $this->getMainSlaveDbConfig();
  876. $data = Db::connect($mainSlaveDbConfig)->table('book_list')
  877. ->alias('bl')
  878. ->field('booklist_collect.id as last_id,bl.id,bl.title,bl.admin_id as channel_id,booklist_collect.idx as book_id,book.name book_name,booklist_collect.uv,booklist_collect.orders_num,booklist_collect.recharge_money,booklist_collect.createtime')
  879. ->join('booklist_collect','bl.admin_id=booklist_collect.admin_id','left')
  880. ->join('book','booklist_collect.idx=book.id','left')
  881. ->where('bl.admin_id',$channelId)
  882. ->where('booklist_collect.id','>',$lastId)
  883. ->order('booklist_collect.id','asc')
  884. ->limit($num)
  885. ->select();
  886. // $sql = Db::table('vip_admin_bind')->getLastSql();
  887. // print_r($sql);
  888. $action = $this->request->action();
  889. $this->setLimit($action);
  890. $this->result($data);
  891. }
  892. /**
  893. * 渠道公众号列表
  894. */
  895. public function channelList()
  896. {
  897. $vip = $this->request->param('vip_id');
  898. $lastId = (int)$this->request->param('last_id',0);
  899. $num = (int)$this->request->param('num',1000);
  900. $mainSlaveDbConfig = $this->getMainSlaveDbConfig();
  901. $channelList =Db::connect($mainSlaveDbConfig)->table('vip_admin_bind')
  902. ->field('admin.id as channel_id,username,nickname,admin_config.appid as app_id,json')
  903. ->alias('vab')
  904. ->join('admin','vab.admin_id_slave=admin.id')
  905. ->join('admin_config','vab.admin_id_slave=admin_config.admin_id','inner')
  906. ->where(['vab.admin_id_master'=>$vip,'flag'=>1])
  907. ->where('admin_config.admin_id','>',$lastId)
  908. ->order('admin.id','asc')
  909. ->limit($num)
  910. ->select();
  911. if (!empty($channelList)){
  912. foreach ($channelList as $k=>&$v){
  913. $wx_json = json_decode($v['json'],true);
  914. $v['wx_nickname'] = !empty($wx_json) && isset($wx_json['authorizer_info']['nick_name']) ? $wx_json['authorizer_info']['nick_name']: '';
  915. unset($v['json']);
  916. }
  917. }
  918. $result['count'] = count($channelList);
  919. $result['list'] = $channelList;
  920. $result['last_id'] = (int)end($channelList)['channel_id'];
  921. // $sql = Db::connect($mainSlaveDbConfig)->table('vip_admin_bind')->getLastSql();
  922. $action = $this->request->action();
  923. $this->setLimit($action);
  924. $this->result($result);
  925. }
  926. /**
  927. * 渠道的粉丝统计
  928. */
  929. public function userCollect()
  930. {
  931. $channelId = $this->request->param('channel_id');
  932. $beginDate = (int)$this->request->param('begin_date');
  933. $endDate = (int)$this->request->param('end_date');
  934. $type = (int)$this->request->param('type',0);
  935. $max = (strtotime($endDate) - strtotime($beginDate))/(3600*24) > 100 ? false : true;
  936. if ( !$max ){
  937. $this->error('时间跨度超过100天');
  938. }
  939. $where = ['admin_id'=>$channelId];
  940. if ($type){
  941. $where['type'] = $type;
  942. }
  943. $mainSlaveDbConfig = $this->getMainSlaveDbConfig();
  944. $data = Db::connect($mainSlaveDbConfig)->table('user_collect')->alias('uc')
  945. ->field('admin_id as channel_id,type,increase,increase_fllow,unfollow_num,createdate')
  946. ->where($where)
  947. ->whereBetween('createdate',$beginDate.','.$endDate)
  948. ->select();
  949. $result['count'] = count($data);
  950. $result['list'] = $data;
  951. $action = $this->request->action();
  952. $this->setLimit($action);
  953. $this->result($result);
  954. }
  955. /**
  956. *
  957. *获取书单链接的接口
  958. */
  959. public function bookUrlList()
  960. {
  961. $result = [
  962. 'last_id' => 0,
  963. 'count' => 0,
  964. 'push_time' => time(),
  965. 'list' => []
  966. ];
  967. $channelId = $this->request->param('channel_id');
  968. $lastId = (int)$this->request->param('last_id',0);
  969. $url = getCurrentDomain($channelId, "/index/index/booklistch");
  970. $mainSlaveDbConfig = $this->getMainSlaveDbConfig();
  971. $sql = "SELECT id,admin_id channel_id,title,name,status,createtime FROM `book_list_ch` WHERE `admin_id` ={$channelId} and id > {$lastId} ORDER BY `id` asc LIMIT 200";
  972. $con = Db::connect($mainSlaveDbConfig)->table('book_list_ch')->query($sql);
  973. if(!empty($con))foreach($con as $k=>&$v){
  974. $v['url'] = $url.'?id='.$v['id'];
  975. }
  976. $result['count'] = count($con);
  977. $result['list'] = $con;
  978. $result['last_id'] = (int)end($con)['id'];
  979. $action = $this->request->action();
  980. $this->setLimit($action);
  981. $this->success($result);
  982. }
  983. public function activityList()
  984. {
  985. $result = [
  986. 'last_id' => 0,
  987. 'count' => 0,
  988. 'push_time' => time(),
  989. 'list' => []
  990. ];
  991. $channelId = $this->request->param('channel_id');
  992. $lastId = (int)$this->request->param('last_id',0);
  993. $typeId = (int)$this->request->param('type_id',1);
  994. $today = date('Ymd',time());
  995. $mainSlaveDbConfig = $this->getMainSlaveDbConfig();
  996. $activity_config = Config::get('site.activity_config');
  997. $con = Db::connect($mainSlaveDbConfig)->table('activity')
  998. ->join('activity_collect c','activity.id=c.aid and c.createdate='.$today.' and c.admin_id='.$channelId,'left')
  999. ->join('activity_collect_all a','activity.id=a.aid and a.admin_id='.$channelId,'left')
  1000. ->join('activity_shortlink s','activity.id= s.aid and s.admin_id='.$channelId,'left')
  1001. ->where('activity.type',$typeId)
  1002. ->where('activity.id','>',$lastId)
  1003. ->field('activity.id,activity.name,activity.copywriting,activity.starttime,activity.endtime,activity.createtime,activity.admin_id channel_id,config_id,c.money,a.money as allmoney,s.qq as qq, s.sina as sina,c.recharge_count,a.recharge_count as arecharge_count,"" as url')
  1004. ->order('activity.id','asc')
  1005. ->limit(500)
  1006. ->select();
  1007. if(!empty($con))foreach($con as $k=>&$v){
  1008. if (isset($activity_config['config'][$v['config_id']]) && $activity_config['config'][$v['config_id']]['status'] == 1) {
  1009. $v['url'] = getCurrentDomain($channelId, '/s/' . $v['id'] . '/r/' . $activity_config['config'][$v['config_id']]['resource_id']);
  1010. }
  1011. }
  1012. $result['count'] = count($con);
  1013. $result['list'] = $con;
  1014. $result['last_id'] = (int)end($con)['id'];
  1015. $action = $this->request->action();
  1016. $this->setLimit($action);
  1017. $this->success($result);
  1018. }
  1019. /**
  1020. * 获取推广链接接口
  1021. */
  1022. public function getReferral()
  1023. {
  1024. $result = [
  1025. 'last_id' => 0,
  1026. 'count' => 0,
  1027. 'push_time' => time(),
  1028. 'list' => []
  1029. ];
  1030. $channelId = $this->request->param('channel_id');
  1031. $lastId = (int)$this->request->param('last_id',0);
  1032. $mainSlaveDbConfig = $this->getMainSlaveDbConfig();
  1033. if (VisitLimitService::instance()->checkMigratedV2()) {
  1034. $con = Db::connect($mainSlaveDbConfig)->table('referral')
  1035. ->join('admin','referral.admin_id=admin.id')
  1036. ->join('admin_config','admin.id=admin_config.admin_id')
  1037. ->join('book','referral.book_id=book.id')
  1038. ->field('referral.id,referral.type,referral.name,admin.id channel_id,admin.username,admin.nickname,admin_config.appid,`admin_config`.`json` AS `wx_json`,referral.source_url,book.name as book_name,referral.chapter_name,referral.guide_chapter_idx,referral.name,referral.createtime,referral.push')
  1039. ->where('admin.id',$channelId)
  1040. ->where('referral.id','>',$lastId)
  1041. ->select();
  1042. if ($con) {
  1043. $ids = array_column($con, 'id');
  1044. $data = ReferralService::instance()->getReferralCollectFromApi($ids)->data;
  1045. foreach ($con as $index=>$item) {
  1046. $con[$index]['uv'] = $data[$item['id']]['uv'];
  1047. $con[$index]['money'] = $data[$item['id']]['money'];
  1048. $con[$index]['orders_num'] = $data[$item['id']]['order_nums'];
  1049. $con[$index]['follow'] = $data[$item['id']]['follow'];
  1050. }
  1051. }
  1052. } else {
  1053. $con = Db::connect($mainSlaveDbConfig)->table('referral')
  1054. ->join('admin','referral.admin_id=admin.id')
  1055. ->join('admin_config','admin.id=admin_config.admin_id')
  1056. ->join('book','referral.book_id=book.id')
  1057. ->field('referral.id,referral.type,referral.name,admin.id channel_id,admin.username,admin.nickname,admin_config.appid,`admin_config`.`json` AS `wx_json`,referral.source_url,book.name as book_name,referral.chapter_name,referral.guide_chapter_idx,referral.name,referral.uv,referral.money,referral.orders_num,referral.createtime,referral.push,referral.follow')
  1058. ->where('admin.id',$channelId)
  1059. ->where('referral.id','>',$lastId)
  1060. ->select();
  1061. }
  1062. if (!empty($con))foreach ($con as $k =>&$v){
  1063. $wx_json = json_decode($v['wx_json'],true);
  1064. $v['wx_nick_name'] = !empty($wx_json) && isset($wx_json['authorizer_info']['nick_name']) ? $wx_json['authorizer_info']['nick_name']: '';
  1065. unset($v['wx_json']);
  1066. $type = (int)$v['type'];
  1067. switch ($type){
  1068. case 1:
  1069. $c = $v['guide_chapter_idx'] ? $v['guide_chapter_idx'] : '关注章节';
  1070. $v['entry_page'] = $v['book_name'].'-'.$v['chapter_name'].$c;
  1071. break;
  1072. case 2:
  1073. $v['entry_page'] = '书城首页推广';
  1074. break;
  1075. case 3:
  1076. $c = $v['guide_chapter_idx'] ? $v['guide_chapter_idx'] : '关注章节';
  1077. $v['entry_page'] = '落地推广页-'.$v['book_name'].'-'.$v['chapter_name'].$c;
  1078. break;
  1079. default:
  1080. $v['entry_page'] = '';
  1081. break;
  1082. }
  1083. }
  1084. $result['count'] = count($con);
  1085. $result['list'] = $con;
  1086. $result['last_id'] = (int)end($con)['id'];
  1087. $action = $this->request->action();
  1088. $this->setLimit($action);
  1089. $this->success($result);
  1090. }
  1091. /**
  1092. * 获取推广链接充值金额
  1093. * @return \think\response\Json
  1094. */
  1095. public function getReferralRecharge()
  1096. {
  1097. $ids = $this->request->param('ids');
  1098. $vip_id = $this->request->param('vip_id');
  1099. $channel_id = $this->request->param('channel_id');
  1100. if (!$ids) {
  1101. $this->error("ids参数缺失");
  1102. } else {
  1103. $ids = explode(',', $ids);
  1104. }
  1105. if (count($ids) == 1) {
  1106. $where = [
  1107. 'id' => $ids[0]
  1108. ];
  1109. } else {
  1110. $where = [
  1111. 'id' => ['in', $ids]
  1112. ];
  1113. }
  1114. if (!$channel_id && $vip_id) {
  1115. $channel_id = (array)AdminService::instance()->getAdminId($vip_id)->data;
  1116. if (count($channel_id) == 1) {
  1117. if ($channel_id[0] == -1) {
  1118. $this->error("未绑定渠道");
  1119. } else {
  1120. $where['admin_id'] = $channel_id[0];
  1121. }
  1122. } else {
  1123. $where['admin_id'] = ['in', $channel_id];
  1124. }
  1125. }
  1126. if (VisitLimitService::instance()->checkMigratedV2()) {
  1127. $referralCost = $data = model('Referral')->where($where)
  1128. ->column('id,cost');
  1129. $data = ReferralService::instance()->getReferralCollectFromApi(array_keys($referralCost))->data;
  1130. foreach ($data as $id => $item) {
  1131. $tmp = [
  1132. 'id' => $id,
  1133. 'money' => $item['money'],
  1134. 'day_money' => (int)$item['daymt'],
  1135. 'uv' => (int)$item['uv'],
  1136. 'day_uv' => (int)$item['dayuv'],
  1137. 'subscribe' => (int)$item['follow'],
  1138. 'day_subscribe' => (int)$item['dayut'],
  1139. 'cost' => $referralCost[$id],
  1140. ];
  1141. $return['list'][] = $tmp;
  1142. }
  1143. } else {
  1144. $data = model('Referral')->where($where)
  1145. ->field('id,money,uv,follow,cost')
  1146. ->select();
  1147. $return = [
  1148. 'list' => [],
  1149. 'total' => count($data),
  1150. ];
  1151. foreach ($data as $item) {
  1152. $dayMTkey = "M-T:".$item['id'].":".date("d");
  1153. $tmp = [
  1154. 'id' => $item['id'],
  1155. 'money' => $item['money'],
  1156. 'day_money' => (int)Redis::instance()->get($dayMTkey) ? round(Redis::instance()->get($dayMTkey) / 100, 2) : 0,
  1157. 'uv' => (int)$item['uv'],
  1158. 'day_uv' => (int)Redis::instance()->get(CacheConstants::getReadOfReferralIdKey($item['id'])),
  1159. 'subscribe' => (int)$item['follow'],
  1160. 'day_subscribe' => (int)Redis::instance()->get(CacheConstants::getSubscribeOfReferralIdKey($item['id'])),
  1161. 'cost' => (float)$item['cost'],
  1162. ];
  1163. if ($tmp['uv'] < $tmp['day_uv']) {
  1164. $tmp['uv'] = $tmp['day_uv'];
  1165. }
  1166. if ($tmp['subscribe'] < $tmp['day_subscribe']) {
  1167. $tmp['subscribe'] = $tmp['day_subscribe'];
  1168. }
  1169. $return['list'][] = $tmp;
  1170. }
  1171. }
  1172. $this->success("ok", $return);
  1173. }
  1174. }