bourse stock
You can not select more than 25 topics Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.

1701 lines
76 KiB

<?php
namespace app\admin\service\setting;
use app\admin\service\AdminBaseService;
use app\admin\validate\setting\StockValidate;
use app\model\PreBrlStockModel;
use app\model\PreEurStockModel;
use app\model\PreFurStockModel;
use app\model\PreGBXStockModel;
use app\model\PreHkdStockModel;
use app\model\PreIdnStockModel;
use app\model\PreInStockModel;
use app\model\PreJpStockModel;
use app\model\PreMysStockModel;
use app\model\PreSgdStockModel;
use app\model\PreThaStockModel;
use app\model\PreUsStockModel;
use app\model\StockBrlListModel;
use app\model\StockEurListModel;
use app\model\StockFurListModel;
use app\model\StockFurTradeModel;
use app\model\StockGBXListModel;
use app\model\StockHkdListModel;
use app\model\StockIdnListModel;
use app\model\StockInListModel;
use app\model\StockJpListModel;
use app\model\StockListModel;
use app\model\StockMarketModel;
use app\model\StockMysListModel;
use app\model\StockPricesSettingModel;
use app\model\StockSgdListModel;
use app\model\StockThaListModel;
use app\model\TradeFeeModel;
use app\model\UserArrearsModel;
use app\model\UserModel;
use think\exception\ValidateException;
use think\facade\Db;
use think\facade\Queue;
use function app\admin\service\getTreeMenu;
class IPOService extends AdminBaseService
{
/**
* IPO列表
*/
public function stockIPOList($market_type, $param, $adminId)
{
try {
$table_obj = $this->getStockModel($market_type);
if (empty($table_obj)) {
return $this->toData('1', '市场类型无效');
}
if (empty($param['page']) || !is_numeric($param['page']) || empty($param['limit']) || !is_numeric($param['limit'])) {
return $this->toData('1', '分页参数错误');
}
$userId = 0;
$where = [];
$stockTypeList = $this->getStockTape($market_type);
// 用户号精确搜索
if (!empty($param['user_no'])) {
$user = UserModel::where('user_no', $param['user_no'])->find();
if (empty($user)) {
return $this->toData('0', 'SUCCESS', ['total' => 0, 'list' => [], 'extent' => [
'tape_list' => $stockTypeList['tape'],
'stock_type_list' => $stockTypeList['type'],
'symbol' => $table_obj['stock_id']]]);
}
$userId = $user['user_id'];
}
// 判断是否是代理 如果是代理 只能看他自己管理的用户
$whereU = $this->getWhereByIsAgentAndUserId($adminId, $where, $userId);
if (!is_array($whereU)) {
return $this->toData('0', 'SUCCESS', ['total' => 0, 'list' => [], 'extent' => [
'tape_list' => $stockTypeList['tape'],
'stock_type_list' => $stockTypeList['type'],
'symbol' => $table_obj['stock_id']]]);
}
// 未删除
$where[] = [
'is_delete', '=', 1
];
// 股票号
if (!empty($param['stock_code']) && is_string($param['stock_code'])) {
$where[] = [
'stock_code', 'like', '%' . $param['stock_code']
];
}
// 状态
if (!empty($param['status']) && in_array($param['status'], [1, 2])) {
$where[] = [
'status', '=', $param['status']
];
}
// 上市状态 1 待申购 2 (申购中)待中签 3 (申购结束)待中签 4 待上市 5 已上市
$query = Db::table($table_obj['stock_table'])->where($where)->where($whereU);
$totalQuery = Db::table($table_obj['stock_table'])->where($where)->where($whereU);
if (!empty($param['open_status']) && in_array($param['open_status'], ['1', '2', '3', '4'])) {
switch ($param['open_status']) {
case '1':
$query = $query->whereTime('start_time', '>', date('Y-m-d H:i:s'));
$totalQuery = $totalQuery->whereTime('start_time', '>', date('Y-m-d H:i:s'));
break;
case '2':
$query = $query->whereTime('start_time', '<=', date('Y-m-d H:i:s'))->whereTime('end_time', '>=', date('Y-m-d H:i:s'));
$totalQuery = $totalQuery->whereTime('start_time', '<=', date('Y-m-d H:i:s'))->whereTime('end_time', '>=', date('Y-m-d H:i:s'));
break;
case '3':
$query = $query->whereTime('end_time', '<=', date('Y-m-d H:i:s'))->whereTime('get_time', '>', date('Y-m-d H:i:s'));
$totalQuery = $totalQuery->whereTime('end_time', '<=', date('Y-m-d H:i:s'))->whereTime('get_time', '>', date('Y-m-d H:i:s'));
break;
case '4':
$query = $query->where('open_status', 1)->whereTime('get_time', '<', date('Y-m-d H:i:s'));
$totalQuery = $totalQuery->where('open_status', 2);
break;
case '5':
$query = $query->where('open_status', 2);
$totalQuery = $totalQuery->where('open_status', 2);
break;
}
}
$list = $query->order('id', 'desc')->page($param['page'], $param['limit'])->select();
$total = $totalQuery->order('id', 'desc')->count();
$rows = [];
if (!$list->isEmpty()) {
$rows = $list->toArray();
foreach ($rows as $key => $item) {
$open_status_name = '-';
if (strtotime($item['start_time']) > time()) {
$open_status_name = '待申购';
$re_status = 1;
}
if (strtotime($item['start_time']) <= time() && strtotime($item['end_time']) >= time()) {
$open_status_name = '待中签(申购中)';
$re_status = 2;
}
if (strtotime($item['end_time']) < time()) {
$open_status_name = '待中签(申购结束)';
$re_status = 3;
}
if ($item['sign_status'] == 1) {
$open_status_name = '待上市(已中签)';
$re_status = 4;
}
if ($item['open_status'] == 2) {
$open_status_name = '已上市';
$re_status = 5;
}
$rows[$key]['open_status_name'] = $open_status_name;
$rows[$key]['re_status'] = $re_status;
if (strpos($item['stock_code'], ':') !== false) {
$rows[$key]['stock_code'] = explode(':', $item['stock_code'])[1];
}
}
}
return $this->toData('0', 'SUCCESS', ['list' => $rows, 'total' => $total, 'extend' => [
'tape_list' => $stockTypeList['tape'],
'stock_type_list' => $stockTypeList['type'],
'symbol' => $table_obj['stock_id'],
're_status_list' => ['1' => '待申购', '2' => '待中签(申购中)', '3' => '待中签(申购结束)', '4' => '待上市(已中签)', '5' => '已上市']
]]);
} catch (\Exception $exception) {
return $this->toData('1', '系统繁忙', [$exception->getMessage(), $exception->getTrace()]);
}
}
/**
* 添加IPO
*/
public function addStockIPO($market_type, $param)
{
try {
$table_obj = $this->getStockModel($market_type);
if (empty($table_obj)) {
return $this->toData('1', '市场类型无效');
}
// 股票代码
if (empty($param['stock_code']) || !is_string($param['stock_code']) || !preg_match('/^[a-zA-Z0-9]+$/', $param['stock_code'])) {
return $this->toData('1', '股票代码 无效');
}
// 股票名称
if (empty($param['stock_name']) || !is_string($param['stock_name'])) {
return $this->toData('1', '股票名称 无效');
}
if ($market_type == 5) {
if (empty($param['numeric_code']) || !preg_match('/^[a-zA-Z0-9]+$/', $param['numeric_code'])) {
return $this->toData('1', '数字编码 无效');
}
}
$stockTypeList = $this->getStockTape($market_type);
// 股票类型
if (empty($param['stock_type']) || !in_array($param['stock_type'], array_keys($stockTypeList['type']))) {
return $this->toData('1', '股票类型 无效');
}
// 交易所类型
if (empty($param['tape']) || !in_array($param['tape'], array_keys($stockTypeList['tape']))) {
return $this->toData('1', '交易所类型 无效');
}
// 发布状态
if (empty($param['status']) || !in_array($param['status'], [1, 2])) {
return $this->toData('1', '发布状态 无效');
}
// 单股价格
if (empty($param['price']) || !is_numeric($param['price']) || $param['price'] <= 0) {
return $this->toData('1', '单股价格 无效');
}
// 最小申购数量
if (empty($param['min']) || !is_numeric($param['min']) || $param['min'] <= 0 || ceil($param['min']) != $param['min']) {
return $this->toData('1', '最小申购数量 无效');
}
// 发行总数
if (empty($param['total']) || !is_numeric($param['total']) || $param['total'] <= 0 || ceil($param['total']) != $param['total']) {
return $this->toData('1', '发行总数 无效');
}
// 中签率 两位小数
if (empty($param['rate']) || !is_numeric($param['rate']) || is_float($param['rate']) || $param['rate'] < 0 || $param['rate'] > 100) {
return $this->toData('1', '中签率无效;范围 0 - 100 , 必须是整数');
}
// 开始认购时间
if (empty($param['start_time']) || !is_string($param['start_time'])) {
return $this->toData('1', '开始认购时间 无效');
}
// 认购结束时间
if (empty($param['end_time']) || !is_string($param['end_time'])) {
return $this->toData('1', '认购结束时间 无效');
}
// 中签时间
if (empty($param['get_time']) || !is_string($param['get_time'])) {
return $this->toData('1', '中签时间 无效');
}
// 上市时间
if (empty($param['open_time']) || !is_string($param['open_time'])) {
return $this->toData('1', '上市时间 无效');
}
// 公司注册资本
$companyRegAmount = "";
if (!empty($param['company_reg_amount']) && is_string($param['company_reg_amount'])) {
$companyRegAmount = $param['company_reg_amount'];
}
// 公司上市时间
if (empty($param['company_open_time']) || !is_string($param['company_open_time'])) {
return $this->toData('1', '公司上市时间 无效');
}
// 公司简介
if (empty($param['company_info']) || !is_string($param['company_info'])) {
return $this->toData('1', '公司简介 无效');
}
// 股票logo
if (empty($param['logo']) || !is_string($param['logo'])) {
return $this->toData('1', '股票logo 无效');
}
// 上市时间 要大于 中签时间 中签时间要大于 认购结结束时间
if (strtotime($param['open_time']) <= strtotime($param['get_time']) || strtotime($param['get_time']) <= strtotime($param['end_time'])) {
return $this->toData('1', '上市时间 要大于 中签时间 中签时间要大于 认购结结束时间');
}
// 是否后支付
if (empty($param['is_post_pay']) || !in_array($param['is_post_pay'], [1, 2])) {
return $this->toData('1', '交易所类型 无效');
}
// 后支付截止时间 > 中签时间 && 后支付截止时间 < 上市时间
// if ($param['is_post_pay'] == 2 && (empty($param['pay_deadline_time']) || strtotime($param['pay_deadline_time']) <= strtotime($param['get_time']) || strtotime($param['pay_deadline_time']) >= strtotime($param['open_time']))) {
// return $this->toData('1', '后支付截止时间 要大于 中签时间 且 后支付截止时间 要小于 上市时间');
// }
if (strpos($param['stock_code'], ':') !== false) {
$param['stock_code'] = explode(':', $param['stock_code'])[1];
}
//除了美股 其他的 code前拼交易所
if ($market_type != 3) {
$param['stock_code'] = $this->getStockTape($market_type)['tape'][$param['tape']] . ":" . $param['stock_code'];
}
// 1.0 判断股票号是否已经存在
$preStock = Db::table($table_obj['stock_table'])->where('stock_code', $param['stock_code'])->where('is_delete', 1)->find();
if (!empty($preStock)) {
return $this->toData('1', '股票号已经存在');
}
$stock = Db::table($table_obj['list_table'])->where('stock_code', $param['stock_code'])->find();
if (!empty($stock)) {
return $this->toData('1', '股票号已经上市');
}
// 新增数据
$preHkStock['stock_code'] = $param['stock_code'];
$preHkStock['stock_name'] = $param['stock_name'];
$preHkStock['stock_type'] = $param['stock_type'];
$preHkStock['tape'] = $param['tape'];
$preHkStock['status'] = $param['status'];
$preHkStock['price'] = $param['price'];
$preHkStock['min'] = $param['min'];
$preHkStock['max'] = $param['max'] ?? 0;
$preHkStock['total'] = $param['total'];
$preHkStock['rate'] = $param['rate'];
$preHkStock['start_time'] = $param['start_time'];
$preHkStock['end_time'] = $param['end_time'];
$preHkStock['get_time'] = $param['get_time'];
$preHkStock['open_time'] = $param['open_time'];
$preHkStock['is_post_pay'] = $param['is_post_pay'];
if (!empty($param['pay_deadline_time'])) $preHkStock['pay_deadline_time'] = $param['pay_deadline_time'];
$preHkStock['limit_get_num'] = $param['limit_get_num'] ?? 100;
$preHkStock['is_delete'] = 1;
$preHkStock['open_status'] = 1;
$preHkStock['create_time'] = date('Y-m-d H:i:s');
$preHkStock['update_time'] = date('Y-m-d H:i:s');
$preHkStock['company_reg_amount'] = $companyRegAmount;
$preHkStock['company_open_time'] = $param['company_open_time'];
$preHkStock['company_info'] = $param['company_info'];
$preHkStock['logo'] = $param['logo'];
if ($market_type == 5) $preHkStock['numeric_code'] = $param['numeric_code'] ?? '0';
$bool = Db::table($table_obj['stock_table'])->insert($preHkStock);
if ($bool) {
return $this->toData('0', 'SUCCESS');
} else {
return $this->toData('1', 'FAIL');
}
} catch (\Exception $exception) {
return $this->toData('0', '系统繁忙', [$exception->getMessage()]);
}
}
/**
* 编辑IPO
*/
public function editStockIPO($market_type, $param)
{
try {
$table_obj = $this->getStockModel($market_type);
if (empty($table_obj)) {
return $this->toData('1', '数据异常');
}
if (empty($param['id']) || !is_numeric($param['id'])) {
return $this->toData('1', '主键 无效');
}
$preHkStock = Db::table($table_obj['stock_table'])->where('id', $param['id'])->where('is_delete', 1)->find();
if (empty($preHkStock)) {
return $this->toData('1', '主键 无效');
}
$stockTypeList = $this->getStockTape($market_type);
// 股票类型
if (empty($param['stock_type']) || !in_array($param['stock_type'], array_keys($stockTypeList['type']))) {
return $this->toData('1', '股票类型 无效');
}
// 股票代码
if (empty($param['stock_code']) || !is_string($param['stock_code']) || !preg_match('/^[a-zA-Z0-9]+$/', $param['stock_code'])) {
return $this->toData('1', '股票代码 无效');
}
// 股票名称
if (empty($param['stock_name']) || !is_string($param['stock_name'])) {
return $this->toData('1', '股票代码 无效');
}
if ($market_type == 5) {
if (empty($param['numeric_code']) || !preg_match('/^[a-zA-Z0-9]+$/', $param['numeric_code'])) {
return $this->toData('1', '数字编码 无效');
}
}
// 交易所类型
if (empty($param['tape']) || !in_array($param['tape'], array_keys($stockTypeList['tape']))) {
return $this->toData('1', '交易所类型 无效');
}
// 发布状态
if (empty($param['status']) || !in_array($param['status'], [1, 2])) {
return $this->toData('1', '发布状态 无效');
}
// 单股价格
if (empty($param['price']) || !is_numeric($param['price']) || $param['price'] <= 0) {
return $this->toData('1', '单股价格 无效');
}
// 开始认购时间
if (empty($param['start_time']) || !is_string($param['start_time'])) {
return $this->toData('1', '开始认购时间 无效');
}
// 最小申购数量
if (empty($param['min']) || !is_numeric($param['min']) || $param['min'] <= 0 || ceil($param['min']) != $param['min']) {
return $this->toData('1', '最小申购数量 无效');
}
// 发行总数
if (empty($param['total']) || !is_numeric($param['total']) || $param['total'] <= 0 || ceil($param['total']) != $param['total']) {
return $this->toData('1', '发行总数 无效');
}
// 中签率 两位小数
if (empty($param['rate']) || !is_numeric($param['rate']) || is_float($param['rate']) || $param['rate'] < 0 || $param['rate'] > 100) {
return $this->toData('1', '中签率无效;范围 0 - 100 , 必须是整数');
}
// 认购结束时间
if (empty($param['end_time']) || !is_string($param['end_time'])) {
return $this->toData('1', '认购结束时间 无效');
}
// 中签时间
if (empty($param['get_time']) || !is_string($param['get_time'])) {
return $this->toData('1', '中签时间 无效');
}
// 上市时间
if (empty($param['open_time']) || !is_string($param['open_time'])) {
return $this->toData('1', '上市时间 无效');
}
// 公司注册资本
$companyRegAmount = "";
if (!empty($param['company_reg_amount']) && is_string($param['company_reg_amount'])) {
$companyRegAmount = $param['company_reg_amount'];
}
// 公司上市时间
if (empty($param['company_open_time']) || !is_string($param['company_open_time'])) {
return $this->toData('1', '公司上市时间 无效');
}
// 公司简介
if (empty($param['company_info']) || !is_string($param['company_info'])) {
return $this->toData('1', '公司简介 无效');
}
// 股票logo
if (empty($param['logo']) || !is_string($param['logo'])) {
return $this->toData('1', '股票logo 无效');
}
// 上市时间 要大于 中签时间 中签时间要大于 认购结结束时间
if (strtotime($param['open_time']) <= strtotime($param['get_time']) || strtotime($param['get_time']) <= strtotime($param['end_time'])) {
return $this->toData('1', '上市时间 要大于 中签时间 中签时间要大于 认购结结束时间');
}
// 是否后支付
if (empty($param['is_post_pay']) || !in_array($param['is_post_pay'], [1, 2])) {
return $this->toData('1', '交易所类型 无效');
}
// 后支付截止时间 > 中签时间 && 后支付截止时间 < 上市时间
// if ($param['is_post_pay'] == 2 && (empty($param['pay_deadline_time']) || strtotime($param['pay_deadline_time']) <= strtotime($param['get_time']) || strtotime($param['pay_deadline_time']) >= strtotime($param['open_time']))) {
// return $this->toData('1', '后支付截止时间 要大于 中签时间 且 后支付截止时间 要小于 上市时间');
// }
if (strpos($param['stock_code'], ':') !== false) {
$param['stock_code'] = explode(':', $param['stock_code'])[1];
}
//除了美股 其他的 code前拼交易所
if ($market_type != 3) {
$param['stock_code'] = $this->getStockTape($market_type)['tape'][$param['tape']] . ":" . $param['stock_code'];
}
//code变更进行通知
if ($preHkStock['stock_code'] != $param['stock_code'] && $preHkStock['open_status'] == 2) {
$source = 0;
if ($market_type == 7) $source = 1;
// 通知行情
$bool = $this->sendNewStockToGo($table_obj['country'], $param['stock_code'], $preHkStock['stock_code'], $param['stock_name'], $stockTypeList['tape'][$preHkStock['tape']], $preHkStock['price'], 1, $preHkStock['company_info'], $source, $param['numeric_code'] ?? 0);
if (!$bool) {
return $this->toData('1', '给行情推送数据异常', []);
}
// 通知交易
$bool = $this->sendUpdateCodeGo($param['stock_code'], $preHkStock['stock_code'], $market_type);
if (!$bool) {
return $this->toData('1', '给交易推送数据异常', []);
}
//修改股票code
$stock = Db::table($table_obj['list_table'])->where('stock_code', $preHkStock['stock_code'])->find();
$stock_update['stock_code'] = $param['stock_code'];
$stock_update['update_time'] = date('Y-m-d H:i:m');
$updateCodeBool = Db::table($table_obj['list_table'])->where('id', $stock['id'])->update($stock_update);
if (!$updateCodeBool) return $this->toData('1', '修改股票code失败');
$oldKey = $table_obj['redis_key'] . $preHkStock['stock_code'];
$redis = $this->getRedis();
$redis->del($oldKey);
$newKey = $table_obj['redis_key'] . $param['stock_code'];
$cacheArr = [
'stock_name' => $stock['stock_name'],
'stock_code' => $param['stock_code'],
'status' => $stock['status'],
'keep_decimal' => $stock['keep_decimal'],
'forced_closure' => $stock['forced_closure'],
'up_limit' => $stock['up_limit'],
'down_limit' => $stock['down_limit'],
'info' => $stock['info'],
'tape' => $stock['tape'],
];
if ($market_type == 5) $cacheArr['numeric_code'] = $param['numeric_code'] ?? '0';
$redis->hMset($newKey, $cacheArr);
}
$preHkStock['stock_code'] = $param['stock_code'];
$preHkStock['stock_name'] = $param['stock_name'];
$preHkStock['tape'] = $param['tape'];
$preHkStock['status'] = $param['status'];
$preHkStock['price'] = $param['price'];
$preHkStock['start_time'] = $param['start_time'];
// 新增数据
$preHkStock['min'] = $param['min'];
$preHkStock['max'] = $param['max'] ?? 0;
$preHkStock['total'] = $param['total'];
$preHkStock['rate'] = $param['rate'];
$preHkStock['end_time'] = $param['end_time'];
$preHkStock['get_time'] = $param['get_time'];
$preHkStock['open_time'] = $param['open_time'];
$preHkStock['is_post_pay'] = $param['is_post_pay'];
if (!empty($param['pay_deadline_time'])) $preHkStock['pay_deadline_time'] = $param['pay_deadline_time'];
$preHkStock['limit_get_num'] = $param['limit_get_num'] ?? 100;
$preHkStock['is_delete'] = 1;
$preHkStock['update_time'] = date('Y-m-d H:i:s');
$preHkStock['company_reg_amount'] = $companyRegAmount;
$preHkStock['company_open_time'] = $param['company_open_time'];
$preHkStock['company_info'] = $param['company_info'];
$preHkStock['logo'] = $param['logo'];
if ($market_type == 5) $preHkStock['numeric_code'] = $param['numeric_code'] ?? '0';
$bool = Db::table($table_obj['stock_table'])->where('id', $param['id'])->update($preHkStock);
if ($bool) {
return $this->toData('0', 'SUCCESS');
} else {
return $this->toData('1', 'FAIL');
}
} catch (\Exception $exception) {
return $this->toData('0', '系统繁忙', [$exception->getMessage()]);
}
}
/**
* 删除IPO
*/
public function delStockIPO($market_type, $param)
{
try {
$table_obj = $this->getStockModel($market_type);
if (empty($table_obj)) {
return $this->toData('1', '数据异常');
}
if (empty($param['id']) || !is_numeric($param['id'])) {
return $this->toData('1', '主键 无效');
}
$preHkStock = Db::table($table_obj['stock_table'])->where('id', $param['id'])->where('is_delete', 1)->find();
if (empty($preHkStock)) {
return $this->toData('1', '主键 无效');
}
// 删除
$list_key = $table_obj['redis_key'] . $preHkStock['stock_code'];
$redis = $this->getRedis();
$redis->del($list_key);
//删除 修改状态
$preHkStock['is_delete'] = 2;
$preHkStock['update_time'] = date('Y-m-d H:i:s');
$bool = Db::table($table_obj['stock_table'])->where('id', $param['id'])->update($preHkStock);
if ($bool) {
return $this->toData('0', 'SUCCESS');
} else {
return $this->toData('1', 'FAIL');
}
} catch (\Exception $exception) {
return $this->toData('1', '系统繁忙', [$exception->getMessage()]);
}
}
/**
* IPO上市
*/
public function stockIPO($market_type, $param)
{
try {
$table_obj = $this->getStockModel($market_type);
if (empty($table_obj)) {
return $this->toData('1', '市场类型无效');
}
if (empty($param['id']) || !is_numeric($param['id'])) {
return $this->toData('1', '主键 无效');
}
$isReal = 1;
if (isset($param['is_real']) && is_numeric($param['is_real']) && $param['is_real'] == '2') {
$isReal = 2;
}
$preInStock = Db::table($table_obj['stock_table'])->where('id', $param['id'])->where('is_delete', 1)->find();
if (empty($preInStock)) {
return $this->toData('1', '主键 无效');
}
// 判断是否签名
if ($preInStock['sign_status'] != 1) {
return $this->toData('1', '还未签名');
}
// 未签名 上市
if ($preInStock['open_status'] != 1 || strtotime($preInStock['get_time']) < date('Y-m-d H:i:s')) {
return $this->toData('1', '无法操作');
}
Db::startTrans();
// 修改股票状态
$num = Db::table($table_obj['stock_table'])->where('id', $preInStock['id'])->update(['open_status' => 2,
'open_time' => date('Y-m-d H:i:s'),
'update_time' => date('Y-m-d H:i:s')]);
if ($num <= 0) {
Db::rollback();
return $this->toData('1', '股票状态修改失败');
}
$tape_list = $this->getStockTape($market_type);
if (Db::table($table_obj['list_table'])->where('stock_code', $preInStock['stock_code'])->find()) {
Db::rollback();
return $this->toData('1', '股票列表已存在该股票');
}
// 将新股加入股票
$inStock['stock_name'] = $preInStock['stock_name'];
$inStock['stock_code'] = $preInStock['stock_code'];
$inStock['status'] = 1;
$inStock['tape'] = $preInStock['tape'];
$inStock['keep_decimal'] = 4;
$inStock['info'] = '';
$inStock['forced_closure'] = 30;
$inStock['up_limit'] = 30;
$inStock['down_limit'] = 30;
$inStock['create_time'] = date('Y-m-d H:i:s');
$inStock['update_time'] = date('Y-m-d H:i:s');
if ($market_type == 5) $inStock['numeric_code'] = $preInStock['numeric_code'];
$bool = Db::table($table_obj['list_table'])->insert($inStock);
if (!$bool) {
Db::rollback();
return $this->toData('1', '股票转移失败');
}
// 加入缓存
$list_key = $table_obj['redis_key'] . $preInStock['stock_code'];
$redis = $this->getRedis();
$redis->del($list_key);
$cacheArr = [
'stock_name' => $inStock['stock_name'],
'stock_code' => $inStock['stock_code'],
'status' => $inStock['status'],
'keep_decimal' => $inStock['keep_decimal'],
'forced_closure' => $inStock['forced_closure'],
'up_limit' => $inStock['up_limit'],
'down_limit' => $inStock['down_limit'],
'info' => $inStock['info'],
'tape' => $inStock['tape'],
];
if ($market_type == 5) $cacheArr['numeric_code'] = $preInStock['numeric_code'];
$redis->hMset($list_key, $cacheArr);
$hqArr = [
'type' => 'hq',
'stock_code' => $inStock['stock_code'],
'stock_name' => $inStock['stock_name'],
'tape' => $tape_list['tape'][$inStock['tape']],
'price' => $preInStock['price'],
'isReal' => $isReal,
'company_info' => $preInStock['company_info'],
'country' => $table_obj['country'],
'id' => $preInStock['id'],
'market_type' => $market_type,
'source' => 0
];
if ($market_type == 7) $hqArr['source'] = 2;
if ($market_type == 5) $hqArr['numeric_code'] = $preInStock['numeric_code'];
Db::commit();
return $this->toData('0', 'SUCCESS');
} catch (\Exception $exception) {
Db::rollback();
trace('预售股上市失败' . $exception->getMessage(), 'error');
return $this->toData('1', '系统繁忙', [$exception->getMessage(), $exception->getTrace()]);
}
}
public function updateIPOStatus($market_type, $id, $type, $status, $order_no = '')
{
$table_obj = $this->getStockModel($market_type);
if (empty($table_obj)) {
return false;
}
switch ($type) {
case 'trade':
$bool = Db::table($table_obj['stock_table'])->where('id', $id)->update([
'update_time' => date('Y-m-d H:i:s'),
'trade_status' => $status
]);
if ($bool && $status == 1) {
Db::table($table_obj['order_table'])->where('pre_stock_id', $id)->where('status', 3)->update([
'update_time' => date('Y-m-d H:i:s'),
'trade_status' => 1
]);
}
break;
case 'last_trade':
$bool = Db::table($table_obj['order_table'])->where('pre_stock_id', $id)->where('order_no', $order_no)->update([
'update_time' => date('Y-m-d H:i:s'),
'trade_status' => 1
]);
break;
case 'hq':
$bool = Db::table($table_obj['stock_table'])->where('id', $id)->update([
'update_time' => date('Y-m-d H:i:s'),
'hq_status' => $status
]);
break;
}
if (!$bool) {
trace('预售股上市修改通知状态失败-' . $id, 'error');
}
}
public function repeatNoteGo($market_type, $param)
{
$table_obj = $this->getStockModel($market_type);
if (empty($table_obj)) {
return $this->toData('1', '市场类型无效');
}
if (empty($param['id']) || !is_numeric($param['id'])) {
return $this->toData('1', '主键 无效');
}
if (empty($param['type'])) {
return $this->toData('1', '缺少参数');
}
$tape_list = $this->getStockTape($market_type);
$preInStock = Db::table($table_obj['stock_table'])->where('id', $param['id'])->where('open_status', 2)->where('is_delete', 1)->find();
if (empty($preInStock)) {
return $this->toData('1', '股票未上市');
}
if ($preInStock['hq_status'] == 2 && $param['type'] == 'hq') {
// 给行情发送数据
Queue::push('app\admin\job\SendGo', [
'type' => 'hq',
'stock_code' => $preInStock['stock_code'],
'stock_name' => $preInStock['stock_name'],
'tape' => $tape_list['tape'][$preInStock['tape']],
'price' => $preInStock['price'],
'isReal' => 1,
'company_info' => $preInStock['company_info'],
'country' => $table_obj['country'],
'id' => $preInStock['id'],
], 'sendGo');
}
if ($preInStock['trade_status'] == 2 && $param['type'] == 'trade') {
Queue::push('app\admin\job\SendGo', [
'type' => 'trade',
'id' => $preInStock['id'],
'stock_code' => $preInStock['stock_code'],
'market_type' => $market_type
], 'sendGo');
}
return $this->toData('0', 'SUCCESS');
}
/**
* 处理股票IPO中签
*/
public function signStockIPO($market_type)
{
try {
$table_obj = $this->getStockModel($market_type);
if (empty($table_obj)) {
trace('数据异常,股票市场:' . $market_type, 'info');
return json(["数据异常"]);
}
$now = date('Y-m-d H:i:s');
$preStockList = Db::table($table_obj['stock_table'])->where('is_delete', 1)
->where('status', 1)
// 签名状态
->where('sign_status', 2)
// 中签时间已过
->whereTime('get_time', '<=', $now)
->select();
if ($preStockList->isEmpty()) {
trace('没有需要处理的新股,股票市场:' . $market_type, 'info');
return json(["没有需要处理的新股"]);
}
foreach ($preStockList as $preStock) {
try {
// 单个股票 开始事务
Db::startTrans();
// 中签率
$rate = bcdiv($preStock['rate'], 100, 6);
$rate = number_format($rate, '6', '.', '');
// 申购的订单列表
$orderList = Db::table($table_obj['order_table'])->where('pre_stock_id', $preStock['id'])->whereIn('status', [1, 5])->select();
if (!$orderList->isEmpty()) {
foreach ($orderList as $order) {
$status = ($order['status'] == 5) ? 5 : 2; // 中签
$get_num = $order['get_num'] > 0 ? $order['get_num'] : ceil($order['num'] * $rate); // 计算中签 数量 * 中签率 向上取整
$orderPrice = number_format($order['price'], '6', '.', '');
$get_amount = bcmul($get_num, $orderPrice, 6);
$orderAmount = number_format($order['amount'], '6', '.', '');
$diffAmount = bcsub($orderAmount, $get_amount, 6);
$feeRate = number_format($order['fee_rate'], '6', '.', '');
$get_fee = bcmul($get_amount, $feeRate, 6);
$orderFee = number_format($order['fee'], '6', '.', ''); // 总手续费
$diff_fee = bcsub($orderFee, $get_fee, 6); // 手续费差值
// 修改订单数据
$num = Db::table($table_obj['order_table'])->where('id', $order['id'])
->update([
'status' => $status,
'get_num' => $get_num,
'get_amount' => $get_amount,
'get_fee' => $get_fee,
'get_time' => $now,
'update_time' => $now]);
if ($num <= 0) {
Db::rollback();
trace('股票签名失败01,股票市场:' . $market_type . "股票名称:" . $preStock['stock_code'], 'info');
return json(["股票签名失败00"]);
}
//已退款订单 直接跳过
if ($order['status'] == 7) continue;
//后支付-未支付 直接跳过
if ($order['pay_type'] == 2 && $order['status'] == 5) continue;
// 回退本金
if ($diffAmount > 0) {
// 新增金额
$beforeAmount = Db::table($table_obj['user_table'])->where('user_id', $order['user_id'])->where('stock_id', $table_obj['stock_id'])->value('usable_num');
$num = Db::table($table_obj['user_table'])->where('user_id', $order['user_id'])->where('stock_id', $table_obj['stock_id'])
->inc('usable_num', $diffAmount)
->dec('frozen_num', $diffAmount)
->update(['update_time' => $now]);
if ($num <= 0) {
Db::rollback();
trace('股票签名失败02,股票市场:' . $market_type . "股票名称:" . $preStock['stock_code'], 'info');
return json(["股票签名失败02"]);
}
// 生成日志
$userStockLog['user_id'] = $order['user_id'];
$userStockLog['change_type'] = 17;
$userStockLog['stock_id'] = $table_obj['stock_id'];
$userStockLog['before_num'] = $beforeAmount;
$userStockLog['change_num'] = $diffAmount;
$userStockLog['order_id'] = $order['order_no'];
$userStockLog['update_time'] = $now;
$userStockLog['create_time'] = $now;
$bool = Db::table($table_obj['log_table'])->insert($userStockLog);
if (!$bool) {
Db::rollback();
trace('股票签名失败03,股票市场:' . $market_type . "股票名称:" . $preStock['stock_code'], 'info');
return json(["股票签名失败03"]);
}
}
// 退回手续费
if ($diff_fee > 0) {
// 新增金额
$beforeFee = Db::table($table_obj['user_table'])->where('user_id', $order['user_id'])->where('stock_id', $table_obj['stock_id'])->value('usable_num');
$num = Db::table($table_obj['user_table'])->where('user_id', $order['user_id'])->where('stock_id', $table_obj['stock_id'])
->inc('usable_num', $diff_fee)
->dec('frozen_num', $diff_fee)
->update(['update_time' => $now]);
if ($num <= 0) {
Db::rollback();
trace('股票签名失败04,股票市场:' . $market_type . "股票名称:" . $preStock['stock_code'], 'info');
return json(["股票签名失败04"]);
}
// 生成日志
$userStockLogFee['user_id'] = $order['user_id'];
$userStockLogFee['change_type'] = 18;
$userStockLogFee['stock_id'] = $table_obj['stock_id'];
$userStockLogFee['before_num'] = $beforeFee;
$userStockLogFee['change_num'] = $diff_fee;
$userStockLogFee['order_id'] = $order['order_no'];
$userStockLogFee['update_time'] = $now;
$userStockLogFee['create_time'] = $now;
$bool = Db::table($table_obj['log_table'])->insert($userStockLogFee);
if (!$bool) {
Db::rollback();
trace('股票签名失败05,股票市场:' . $market_type . "股票名称:" . $preStock['stock_code'], 'info');
return json(["股票签名失败05"]);
}
}
}
}
// 更新股票数据
$bool = Db::table($table_obj['stock_table'])->where('id', $preStock['id'])->update(['sign_status' => 1, 'update_time' => $now]);
if (!$bool) {
Db::rollback();
trace('股票签名失败07,股票市场:' . $market_type . "股票名称:" . $preStock['stock_code'], 'info');
return json(["股票签名失败07"]);
}
// 提交事务
Db::commit();
} catch (\Exception $exception) {
Db::rollback();
trace("股票签名失败-exception 股票市场:" . $market_type . $exception->getMessage(), 'error');
return json([$exception->getMessage()]);
}
}
return json(["SUCCESS"]);
} catch (\Exception $exception) {
trace("股票签名失败-exception 股票市场:" . $market_type . $exception->getMessage(), 'error');
return json([$exception->getMessage()]);
}
}
/**
* 股票列表
*/
public function stockList($market_type, $param)
{
try {
$table_obj = $this->getStockModel($market_type);
if (empty($table_obj)) {
return $this->toData('1', '数据异常');
}
validate(StockValidate::class)->scene($table_obj['check'] . 'index')->check($param);
$tapeList = $this->getStockTape($market_type);
$stockCode = $param['stock_code'] ?? '';
$where = [];
$whereOr = [];
if (!empty($stockCode)) {
if ($market_type == 5) {
$whereOr[] = ['stock_code', 'like', '%' . $stockCode];
$whereOr[] = ['numeric_code', 'like', '%' . $stockCode];
} else {
$where[] = ['stock_code', 'like', '%' . $stockCode];
}
}
$list = Db::table($table_obj['list_table'])->order('id', 'desc');
$total = Db::table($table_obj['list_table'])->order('id', 'desc');
if (!empty($whereOr)) {
$list = $list->whereOr($whereOr);
$total = $total->whereOr($whereOr);
}
if (!empty($where)) {
$list = $list->where($where);
$total = $total->where($where);
}
$list = $list->page($param['page'], $param['limit'])->select();
$total = $total->count();
return $this->toData('0', 'SUCCESS', ['list' => $list, 'total' => $total, 'extend' => [
'tape_list' => $tapeList['tape'],
'source_list' => $tapeList['source'] ?? [],
]]);
} catch (ValidateException $validateException) {
// 参数校验失败
$message = $validateException->getError();
return $this->toData('1', $message);
} catch (\Exception $exception) {
return $this->toData('1', '系统繁忙', [$exception->getMessage(), $exception->getTrace()]);
}
}
/**
* 添加股票
*/
public function addStock($market_type, $param)
{
try {
$table_obj = $this->getStockModel($market_type);
if (empty($table_obj)) {
return $this->toData('1', '数据异常');
}
validate(StockValidate::class)->scene($table_obj['check'] . 'add')->check($param);
$info = '';
if (isset($param['info']) && is_string($param['info'])) {
$info = $param['info'];
}
$tapeList = $this->getStockTape($market_type);
// 判断股票交易所
$tape = '0';
if (isset($param['tape']) && in_array($param['tape'], array_keys($tapeList['tape']))) {
$tape = $param['tape'];
}
if (empty($param['yesterday_close']) || !is_numeric($param['yesterday_close']) || $param['yesterday_close'] <= 0) {
return $this->toData('1', '昨日收盘价错误');
}
if (strpos($param['stock_code'], ':') !== false) {
$param['stock_code'] = explode(':', $param['stock_code'])[1];
}
if ($market_type != 3) {
$stock_code = $tapeList['tape'][$tape] . ":" . $param['stock_code'];
} else {
$stock_code = $param['stock_code'];
}
// 判断股票代码是否已经存在
$count = Db::table($table_obj['list_table'])->where('stock_code', $stock_code)->count();
if ($count > 0) {
return $this->toData('1', '股票代码已经存在');
}
$source = 0;
if ($market_type == 7) {
$stockList['source'] = $source = $param['source'] ?? 1;
}
// 给行情推送
$bool = $this->sendNewStockToGo($table_obj['country'], $stock_code, $stock_code, $param['stock_name'], $tapeList['tape'][$tape], $param['yesterday_close'], 1, '', $source, $param['numeric_code'] ?? '0');
if (!$bool) {
return $this->toData('1', '数据设置成功 但给行情推送数据异常', []);
}
// 新增数据
$stockList['stock_name'] = $param['stock_name'];
$stockList['stock_code'] = $stock_code;
$stockList['status'] = $param['status'];
$stockList['keep_decimal'] = $param['keep_decimal'];
$stockList['forced_closure'] = $param['forced_closure'];
$stockList['up_limit'] = $param['up_limit'];
$stockList['down_limit'] = $param['down_limit'];
$stockList['tape'] = $tape; // 交易所类型
$stockList['info'] = $info;
$stockList['yesterday_close'] = $param['yesterday_close'];
$stockList['create_time'] = date('Y-m-d H:i:s');
$stockList['update_time'] = date('Y-m-d H:i:s');
if ($market_type == 5) $stockList['numeric_code'] = $param['numeric_code'] ?? '0';
$bool = Db::table($table_obj['list_table'])->insert($stockList);
if ($bool) {
// 新增缓存
$list_key = $table_obj['redis_key'] . $stock_code;
$redis = $this->getRedis();
$redis->del($list_key);
$redis_arr = [
'stock_name' => $param['stock_name'],
'stock_code' => $stock_code,
'status' => $param['status'],
'keep_decimal' => $param['keep_decimal'],
'forced_closure' => $param['forced_closure'],
'up_limit' => $param['up_limit'],
'down_limit' => $param['down_limit'],
'info' => $info,
'tape' => $tape,
];
if ($market_type == 5) $redis_arr['numeric_code'] = $param['numeric_code'] ?? '0';
$redis->hMset($list_key, $redis_arr);
}
return $this->toData('0', 'SUCCESS', []);
} catch (ValidateException $validateException) {
$message = $validateException->getError();
return $this->toData('1', $message);
} catch (\Exception $exception) {
return $this->toData('1', '系统繁忙', []);
}
}
/**
* 编辑股票
*/
public function editStock($market_type, $param)
{
try {
$table_obj = $this->getStockModel($market_type);
if (empty($table_obj)) {
return $this->toData('1', '数据异常');
}
validate(StockValidate::class)->scene($table_obj['check'] . 'edit')->check($param);
$stockList = Db::table($table_obj['list_table'])->where('id', $param['id'])->find();
if (empty($stockList)) {
return $this->toData('1', '目标不存在', []);
}
$info = '';
if (isset($param['info']) && is_string($param['info'])) {
$info = $param['info'];
}
$tapeList = $this->getStockTape($market_type);
// 判断股票交易所
$tape = '0';
if (isset($param['tape']) && in_array($param['tape'], array_keys($tapeList['tape']))) {
$tape = $param['tape'];
}
if (empty($param['yesterday_close']) || !is_numeric($param['yesterday_close']) || $param['yesterday_close'] <= 0) {
return $this->toData('1', '昨日收盘价错误');
}
if (strpos($param['stock_code'], ':') !== false) {
$param['stock_code'] = explode(':', $param['stock_code'])[1];
}
if ($market_type != 3) {
$stock_code = $tapeList['tape'][$param['tape']] . ":" . $param['stock_code'];
} else {
$stock_code = $param['stock_code'];
}
$old_code = $stockList['stock_code'];
// 判断股票代码是否已经存在
$count = Db::table($table_obj['list_table'])->where('stock_code', $stock_code)->where('id', '<>', $param['id'])->count();
if ($count > 0) {
return $this->toData('1', '股票代码已经存在');
}
$source = 0;
if ($stock_code != $old_code || ($market_type == 7 && $param['source'] != $stockList['source'])) {
if ($market_type == 7) {
$stockList['source'] = $source = $param['source'] ?? 1;
}
// 给行情推送
$bool = $this->sendNewStockToGo($table_obj['country'], $stock_code, $old_code, $param['stock_name'], $tapeList['tape'][$tape], $param['yesterday_close'], 1, '', $source, $param['numeric_code'] ?? '0');
if (!$bool) {
return $this->toData('1', '数据设置成功 但给行情推送数据异常', []);
}
}
if ($stock_code != $old_code) {
// 通知交易
$bool = $this->sendUpdateCodeGo($stock_code, $old_code, $market_type);
if (!$bool) {
return $this->toData('1', '数据设置成功 但给交易推送数据异常', []);
}
//插针
$stockPrices = StockPricesSettingModel::where('market_type', $market_type)->where('stock_id', $param['id'])->find();
if (!empty($stockPrices)) {
// 添加缓存
$old_key = 'STOCK_PRICES:' . $stockPrices->market_type . ':' . $old_code;
$new_key = 'STOCK_PRICES:' . $stockPrices->market_type . ':' . $stock_code;
$redis = $this->getRedis();
$redis->del($old_key);
$redis->hMSet($new_key, [
'market_type' => $stockPrices->market_type,
'stock_id' => $stockPrices->stock_id,
'stock_code' => $stock_code,
'status' => $stockPrices->status,
'price' => $stockPrices->price,
]);
}
//IPO
$stockIPO = Db::table($table_obj['stock_table'])->where('stock_code', $old_code)->find();
if (!empty($stockIPO)) {
Db::table($table_obj['stock_table'])->where('stock_code', $old_code)->update(['stock_code' => $stock_code, 'update_time' => date('Y-m-d H:i:s')]);
}
}
// 修改数据
$stockList['stock_name'] = $param['stock_name'];
$stockList['stock_code'] = $stock_code;
$stockList['status'] = $param['status'];
$stockList['keep_decimal'] = $param['keep_decimal'];
$stockList['forced_closure'] = $param['forced_closure'];
$stockList['up_limit'] = $param['up_limit'];
$stockList['down_limit'] = $param['down_limit'];
$stockList['info'] = $info;
$stockList['tape'] = $tape;
$stockList['update_time'] = date('Y-m-d H:i:s');
$stockList['yesterday_close'] = $param['yesterday_close'];
if ($market_type == 5) $stockList['numeric_code'] = $param['numeric_code'] ?? '0';
$bool = Db::table($table_obj['list_table'])->where('id', $param['id'])->update($stockList);
if ($bool) {
// 新增缓存
$old_key = $table_obj['redis_key'] . $old_code;
$new_key = $table_obj['redis_key'] . $stock_code;
$redis = $this->getRedis();
$redis->del($old_key);
$redis_arr = [
'stock_name' => $param['stock_name'],
'stock_code' => $stock_code,
'status' => $param['status'],
'keep_decimal' => $param['keep_decimal'],
'forced_closure' => $param['forced_closure'],
'up_limit' => $param['up_limit'],
'down_limit' => $param['down_limit'],
'info' => $info,
'tape' => $tape,
];
if ($market_type == 5) $redis_arr['numeric_code'] = $param['numeric_code'] ?? '0';
$redis->hMset($new_key, $redis_arr);
}
return $this->toData('0', 'SUCCESS', []);
} catch (ValidateException $validateException) {
$message = $validateException->getError();
return $this->toData('1', $message);
} catch (\Exception $exception) {
return $this->toData('1', '系统繁忙', [$exception->getMessage(), $exception->getTrace()]);
}
}
/**
* 自动添加股票
*/
public function autoAddStock($param)
{
try {
$market_type = intval($param['country']);
$table_obj = $this->getStockModel($market_type);
if (empty($table_obj)) {
return $this->toData('1', '数据异常');
}
validate(StockValidate::class)->scene('stock_auto_add')->check($param);
$tapeList = $this->getStockTape($market_type);
$tape_arr = array_flip($tapeList['tape']);
// 判断股票交易所
$tape = '0';
if (isset($param['tape']) && in_array($param['tape'], array_keys($tape_arr))) {
$tape = $tape_arr[$param['tape']];
}
$stock_code = $param['stock_code'];
// 判断股票代码是否已经存在
$count = Db::table($table_obj['list_table'])->where('stock_code', $stock_code)->count();
if ($count > 0) {
return $this->toData('1', '股票代码已经存在');
}
// 新增数据
$stockList['stock_name'] = $param['stock_name'];
$stockList['stock_code'] = $stock_code;
$stockList['status'] = 1;
$stockList['keep_decimal'] = 4;
$stockList['forced_closure'] = 30;
$stockList['up_limit'] = 30;
$stockList['down_limit'] = 30;
$stockList['tape'] = $tape; // 交易所类型
$stockList['info'] = '';
$stockList['yesterday_close'] = 0;
$stockList['create_time'] = date('Y-m-d H:i:s');
$stockList['update_time'] = date('Y-m-d H:i:s');
$bool = Db::table($table_obj['list_table'])->insert($stockList);
if ($bool) {
// 新增缓存
$list_key = $table_obj['redis_key'] . $stock_code;
$redis = $this->getRedis();
$redis->del($list_key);
$redis->hMset($list_key, [
'stock_name' => $stockList['stock_name'],
'stock_code' => $stock_code,
'status' => $stockList['status'],
'keep_decimal' => $stockList['keep_decimal'],
'forced_closure' => $stockList['forced_closure'],
'up_limit' => $stockList['up_limit'],
'down_limit' => $stockList['down_limit'],
'info' => '',
'tape' => $tape,
]);
}
return $this->toData('0', 'SUCCESS', []);
} catch (ValidateException $validateException) {
$message = $validateException->getError();
return $this->toData('1', $message);
} catch (\Exception $exception) {
return $this->toData('1', '系统繁忙', [$exception->getMessage(), $exception->getTrace()]);
}
}
/**
* 取消上市
*/
public function cancelIPO($market_type,$param){
$table_obj = $this->getStockModel($market_type);
$redis = $this->getRedis();
if (empty($table_obj)) {
return false;
}
$preStock = Db::table($table_obj['stock_table'])->where('is_delete', 1)
->where('status', 1)
->where('id', $param['pre_id'])
// 签名状态
->where('sign_status', 1)
->where('open_status', 1)
->find();
if(empty($preStock)){
return $this->toData('1', '数据异常');
}
//1、2已支付,5、6未支付可能存在借款
$order_list = Db::table($table_obj['order_table'])->where('pre_stock_id', $param['pre_id'])
->whereIn('status',[1,2,5,6])
->select();
$now = date('Y-m-d H:i:s');
foreach ($order_list as $order){
Db::startTrans();
$total_num=$order['amount']+$order['fee'];
//查询订单有没有欠款
$user_arrears=UserArrearsModel::where('order_no', $order['order_no'])->where('status',0)->where('user_id', $order['user_id'])->find();
if($user_arrears){
$user_arrears=$user_arrears->toArray();
if($user_arrears['is_add']==1){
//扣除冻结,不加可用
$updateNum = Db::table($table_obj['user_table'])->where('stock_id', $table_obj['stock_id'])->where('user_id', $order['user_id'])
->where('frozen_num', '>=', $total_num)
->dec('frozen_num',$total_num)
->update(['update_time' => $now]);
if(!$updateNum){
Db::rollback();
trace('给用户ID:' . $order['user_id'] . "解冻资金异常" . $order['order_no'], 'error');
continue;
}
}
$update_bool=UserArrearsModel::where('order_no', $order['order_no'])->where('user_id', $order['user_id'])
->update([
'update_time'=>$now,
'status'=>1
]);
if(!$update_bool){
Db::rollback();
trace('给用户ID:' . $order['user_id'] . "更新贷款订单异常" . $order['order_no'], 'error');
continue;
}
$status=8;
}else{
//扣除冻结 加可用
$updateNum = Db::table($table_obj['user_table'])->where('stock_id', $table_obj['stock_id'])->where('user_id', $order['user_id'])
->where('frozen_num', '>=', $total_num)
->inc('usable_num', $total_num)
->dec('frozen_num',$total_num)
->update(['update_time' => $now]);
if(!$updateNum){
Db::rollback();
trace('给用户ID:' . $order['user_id'] . "解冻资金异常" . $order['order_no'], 'error');
continue;
}
$status=7;
}
//更新状态
$bool_status = Db::table($table_obj['order_table'])->where('id', $order['id'])->update([
'status' => $status,
'update_time' => $now
]);
if (!$bool_status) {
Db::rollback();
trace('更新订单状态异常' . $order['order_no'], 'error');
continue;
}
//删除缓存订单
$key = "USER:ARREAR:ORDER:" . $order['order_no'];
$redis->del($key);
Db::commit();
}
$bool = Db::table($table_obj['stock_table'])->where('id', $param['pre_id'])->update([
'is_delete'=>2,
'update_time' => $now
]);
if($bool){
return $this->toData('0', 'SUCCESS');
}else{
return $this->toData('1', '数据异常');
}
}
// 美股列表
public function getTradeNameList($market_type)
{
try {
$table_obj = $this->getStockModel($market_type);
if (empty($table_obj)) {
return $this->toData('1', '数据异常');
}
$list = Db::table($table_obj['list_table'])->where('status', 1)->order('id', 'desc')->column('stock_name', 'id');
return $this->toData('0', 'SUCCESS', ['list' => $list]);
} catch (\Exception $exception) {
return $this->toData('1', '系统繁忙', []);
}
}
public function getStockModel($market_type)
{
//3美股、4印尼股、5马股、6泰股、7印度股、9新加坡股、12港股、14英股
$prefix = env('database.prefix');
switch ($market_type) {
case 3:
$result = [
'stock_table' => $prefix . 'pre_us_stock',
'order_table' => $prefix . 'user_us_pre_stock_order',
'user_table' => $prefix . 'user_stock',
'log_table' => $prefix . 'user_stock_log',
'list_table' => $prefix . 'stock_list',
'trade_table' => $prefix . 'stock_trade',
'give_order_table' => $prefix . 'user_us_give_stock_order',
'redis_key' => 'US:STOCK:LIST:',
'stock_id' => 'USD',
'country' => 'US',
'check' => 'us_stock_',
];
break;
case 4:
$result = [
'stock_table' => $prefix . 'pre_idn_stock',
'order_table' => $prefix . 'user_idn_pre_stock_order',
'user_table' => $prefix . 'user_stock_idn',
'log_table' => $prefix . 'user_stock_idn_log',
'list_table' => $prefix . 'stock_idn_list',
'trade_table' => $prefix . 'stock_idn_trade',
'give_order_table' => $prefix . 'user_idn_give_stock_order',
'redis_key' => 'IDN:STOCK:LIST:',
'stock_id' => 'IDR',
'country' => 'Indonesia',
'check' => 'idn_stock_',
];
break;
case 5:
$result = [
'stock_table' => $prefix . 'pre_mys_stock',
'order_table' => $prefix . 'user_mys_pre_stock_order',
'user_table' => $prefix . 'user_stock_mys',
'log_table' => $prefix . 'user_stock_mys_log',
'list_table' => $prefix . 'stock_mys_list',
'trade_table' => $prefix . 'stock_mys_trade',
'give_order_table' => $prefix . 'user_mys_give_stock_order',
'redis_key' => 'MYS:STOCK:LIST:',
'stock_id' => 'MYR',
'country' => 'Malaysia',
'check' => 'mys_stock_',
];
break;
case 6:
$result = [
'stock_table' => $prefix . 'pre_tha_stock',
'order_table' => $prefix . 'user_tha_pre_stock_order',
'user_table' => $prefix . 'user_stock_tha',
'log_table' => $prefix . 'user_stock_tha_log',
'list_table' => $prefix . 'stock_tha_list',
'trade_table' => $prefix . 'stock_tha_trade',
'give_order_table' => $prefix . 'user_tha_give_stock_order',
'redis_key' => 'THA:STOCK:LIST:',
'stock_id' => 'THB',
'country' => 'Thailand',
'check' => 'tha_stock_',
];
break;
case 7:
$result = [
'stock_table' => $prefix . 'pre_in_stock',
'order_table' => $prefix . 'user_in_pre_stock_order',
'user_table' => $prefix . 'user_stock_in',
'log_table' => $prefix . 'user_stock_in_log',
'list_table' => $prefix . 'stock_in_list',
'trade_table' => $prefix . 'stock_in_trade',
'give_order_table' => $prefix . 'user_in_give_stock_order',
'redis_key' => 'IN:STOCK:LIST:',
'stock_id' => 'INR',
'country' => 'India',
'check' => 'idn_stock_',
];
break;
case 9:
$result = [
'stock_table' => $prefix . 'pre_sgd_stock',
'order_table' => $prefix . 'user_sgd_pre_stock_order',
'user_table' => $prefix . 'user_stock_sgd',
'log_table' => $prefix . 'user_stock_sgd_log',
'list_table' => $prefix . 'stock_sgd_list',
'trade_table' => $prefix . 'stock_sgd_trade',
'give_order_table' => $prefix . 'user_sgd_give_stock_order',
'redis_key' => 'SGD:STOCK:LIST:',
'stock_id' => 'SGD',
'country' => 'Singapore',
'check' => 'sgd_stock_',
];
break;
case 12:
$result = [
'stock_table' => $prefix . 'pre_hkd_stock',
'order_table' => $prefix . 'user_hkd_pre_stock_order',
'user_table' => $prefix . 'user_stock_hkd',
'log_table' => $prefix . 'user_stock_hkd_log',
'list_table' => $prefix . 'stock_hkd_list',
'trade_table' => $prefix . 'stock_hkd_trade',
'give_order_table' => $prefix . 'user_hkd_give_stock_order',
'redis_key' => 'HKD:STOCK:LIST:',
'stock_id' => 'HKD',
'country' => 'HongKong',
'check' => 'hk_stock_',
];
break;
case 14:
$result = [
'stock_table' => $prefix . 'pre_gbx_stock',
'order_table' => $prefix . 'user_gbx_pre_stock_order',
'user_table' => $prefix . 'user_stock_gbx',
'log_table' => $prefix . 'user_stock_gbx_log',
'list_table' => $prefix . 'stock_gbx_list',
'trade_table' => $prefix . 'stock_gbx_trade',
'give_order_table' => $prefix . 'user_gbx_give_stock_order',
'redis_key' => 'UK:STOCK:LIST:',
'stock_id' => 'GBX',
'country' => 'UK',
'check' => 'gbx_stock_',
];
break;
case 15:
$result = [
'stock_table' => $prefix . 'pre_fur_stock',
'order_table' => $prefix . 'user_fur_pre_stock_order',
'user_table' => $prefix . 'user_stock_fur',
'log_table' => $prefix . 'user_stock_fur_log',
'list_table' => $prefix . 'stock_fur_list',
'trade_table' => $prefix . 'stock_fur_trade',
'give_order_table' => $prefix . 'user_fur_give_stock_order',
'redis_key' => 'FUR:STOCK:LIST:',
'stock_id' => 'EUR',
'country' => 'FUR',
'check' => 'fur_stock_',
];
break;
case 16:
$result = [
'stock_table' => $prefix . 'pre_eur_stock',
'order_table' => $prefix . 'user_eur_pre_stock_order',
'user_table' => $prefix . 'user_stock_eur',
'log_table' => $prefix . 'user_stock_eur_log',
'list_table' => $prefix . 'stock_eur_list',
'trade_table' => $prefix . 'stock_eur_trade',
'give_order_table' => $prefix . 'user_eur_give_stock_order',
'redis_key' => 'EUR:STOCK:LIST:',
'stock_id' => 'EUR',
'country' => 'EUR',
'check' => 'eur_stock_',
];
break;
case 17:
$result = [
'stock_table' => $prefix . 'pre_brl_stock',
'order_table' => $prefix . 'user_brl_pre_stock_order',
'user_table' => $prefix . 'user_stock_brl',
'log_table' => $prefix . 'user_stock_brl_log',
'list_table' => $prefix . 'stock_brl_list',
'trade_table' => $prefix . 'stock_brl_trade',
'give_order_table' => $prefix . 'user_brl_give_stock_order',
'redis_key' => 'BR:STOCK:LIST:',
'stock_id' => 'BRL',
'country' => 'BRL',
'check' => 'brl_stock_',
];
break;
case 18:
$result = [
'stock_table' => $prefix . 'pre_jp_stock',
'order_table' => $prefix . 'user_jp_pre_stock_order',
'user_table' => $prefix . 'user_stock_jp',
'log_table' => $prefix . 'user_stock_jp_log',
'list_table' => $prefix . 'stock_jp_list',
'trade_table' => $prefix . 'stock_jp_trade',
'give_order_table' => $prefix . 'user_jp_give_stock_order',
'redis_key' => 'JP:STOCK:LIST:',
'stock_id' => 'JPY',
'country' => 'Japan',
'check' => 'jp_stock_',
];
break;
default:
$result = [];
break;
}
return $result;
}
public function getStockTape($market_type)
{
//3美股、4印尼股、5马股、6泰股、7印度股、9新加坡股、12港股
$result = [];
switch ($market_type) {
case 3:
$result = [
'tape' => StockListModel::$tapeList,
'type' => PreUsStockModel::$stockTypeList,
];
break;
case 4:
$result = [
'tape' => StockIdnListModel::$tapeList,
'type' => PreIdnStockModel::$stockTypeList,
];
break;
case 5:
$result = [
'tape' => StockMysListModel::$tapeList,
'type' => PreMysStockModel::$stockTypeList,
];
break;
case 6:
$result = [
'tape' => StockThaListModel::$tapeList,
'type' => PreThaStockModel::$stockTypeList,
];
break;
case 7:
$result = [
'tape' => StockInListModel::$tapeList,
'type' => PreInStockModel::$stockTypeList,
'source' => StockInListModel::SOURCE_LIST,
];
break;
case 9:
$result = [
'tape' => StockSgdListModel::$tapeList,
'type' => PreSgdStockModel::$stockTypeList,
];
break;
case 12:
$result = [
'tape' => StockHkdListModel::$tapeList,
'type' => PreHkdStockModel::$stockTypeList,
];
break;
case 14:
$result = [
'tape' => StockGBXListModel::$tapeList,
'type' => PreGBXStockModel::$stockTypeList,
];
break;
case 15:
$result = [
'tape' => StockFurListModel::$tapeList,
'type' => PreFurStockModel::$stockTypeList,
];
break;
case 16:
$result = [
'tape' => StockEurListModel::$tapeList,
'type' => PreEurStockModel::$stockTypeList,
];
break;
case 17:
$result = [
'tape' => StockBrlListModel::$tapeList,
'type' => PreBrlStockModel::$stockTypeList,
];
break;
case 18:
$result = [
'tape' => StockJpListModel::$tapeList,
'type' => PreJpStockModel::$stockTypeList,
];
break;
}
return $result;
}
}