作者 karlet

feat:优化交易对转换

... ... @@ -73,6 +73,7 @@ class CmBroker
$exBroker = new BybitBroker($apiInfo);
}
$this->exBroker = $exBroker;
$this->init();
}
public function setWsHost($host)
{
... ... @@ -224,6 +225,11 @@ class CmBroker
{
$symbol = str_replace('-USDT-SWAP', 'USDT', $symbol);
if (preg_match('/^[A-Z0-9]+USDT$/', $symbol)) {
if ($this->plat == self::PLAT_BINANCE || $this->plat == self::PLAT_BYBIT) {
$num = SymbolInfo::extractNumber($symbol);
$symbol = str_replace($num, '', $symbol);
return $symbol;
}
return $symbol;
} else {
throw new Exception('转换标准交易对错误' . $symbol . ' to ', $symbol);
... ... @@ -263,19 +269,14 @@ class CmBroker
}
//转换为原始交易对
public function getSymbolOri($symbol, $platTarget)
public function getSymbolOri($symbol): string
{
$symbolSt = $this->getSymbolSt($symbol);
if ($platTarget == self::PLAT_BINANCE) {
return $symbolSt;
}
if ($platTarget == self::PLAT_OKX) {
return str_replace('USDT', '-USDT-SWAP', $symbolSt);
}
if ($platTarget == self::PLAT_BYBIT) {
return $symbolSt;
/** @var SymbolInfo $symbolInfo */
$symbolInfo = $this->symbolInfos[$symbol] ?? false;
if ($symbolInfo) {
return $symbolInfo->symbolOri;
}
throw new Exception('平台错误' . $platTarget);
return "";
}
public function placeOrder(Order $order)
... ... @@ -284,7 +285,7 @@ class CmBroker
$symbolInfo = $this->symbolInfos[$order->symbol];
if ($this->plat == self::PLAT_OKX) {
$orderOri = $order->toOkxOrder($this->symbolInfos, function ($symbol) {
return $this->getSymbolOri($symbol, $this->plat);
return $this->getSymbolOri($symbol);
});
$this->msg("下单", $orderOri);
if ($orderOri['sz'] == 0) {
... ... @@ -335,8 +336,11 @@ class CmBroker
$pos = $this->positions[$key];
return abs($pos->qty);
}
private function initSymbolInfos()
private function initSymbolInfos($count = 1)
{
if ($count > 3) {
new Exception("broker初始化交易对信息失败");
}
if ($this->plat == self::PLAT_OKX) {
//获取所有USDT SWAP 交易对
$res = $this->exBroker->getSymbolInfos();
... ... @@ -364,6 +368,10 @@ class CmBroker
}
$this->symbolInfos = $infos;
}
if (count($this->symbolInfos) == 0) {
$this->initSymbolInfos($count + 1);
return;
}
//定时10m刷新
swoole_timer_after(1000 * 60 * 10, function () {
$this->initSymbolInfos();
... ... @@ -416,7 +424,7 @@ class CmBroker
//设置杠杆
public function setLever($symbol, $lever)
{
$symbol = $this->getSymbolOri($symbol, $this->plat);
$symbol = $this->getSymbolOri($symbol);
$res = $this->exBroker->setLever($symbol, $lever);
if ($res) {
$this->levers[$symbol] = $lever;
... ... @@ -446,7 +454,7 @@ class CmBroker
//获取某个品种的某个方向仓位
public function getPos($symbol, $posSide)
{
$symbolOri = $this->getSymbolOri($symbol, $this->plat);
$symbolOri = $this->getSymbolOri($symbol);
if ($this->plat == self::PLAT_OKX) {
$posSide = strtolower($posSide);
$symbolInfo = $this->symbolInfos[$symbol];
... ... @@ -465,7 +473,7 @@ class CmBroker
*/
public function getKlines($symbol, $peroid, $limit = 100)
{
$symbolOri = $this->getSymbolOri($symbol, $this->plat);
$symbolOri = $this->getSymbolOri($symbol);
if ($this->plat == self::PLAT_OKX) {
$res = $this->exBroker->getKlines($symbolOri, $peroid, $limit);
if ($res['code'] != '0') {
... ...
... ... @@ -16,8 +16,9 @@ class SymbolInfo
public string $lotPrec;
public string $minLot; // 最小下单张数
public string $minQty; // 最小下单数量
public int $mul; // 合约乘数//放大倍数,比如币安 1000CATUSDT,乘数为1000
public function __construct($symbolOri, $symbol, $ctVal, $pricePrec, $qtyPrec, $lotPrec, $minLot, $minQty)
public function __construct($symbolOri, $symbol, $ctVal, $pricePrec, $qtyPrec, $lotPrec, $minLot, $minQty, $mul = 1)
{
$this->symbolOri = $symbolOri;
$this->symbol = $symbol;
... ... @@ -27,6 +28,7 @@ class SymbolInfo
$this->lotPrec = $lotPrec;
$this->minLot = $minLot;
$this->minQty = $minQty;
$this->mul = $mul;
}
public function toArray()
{
... ... @@ -39,6 +41,7 @@ class SymbolInfo
'lotPrec' => $this->lotPrec,
'minLot' => $this->minLot,
'minQty' => $this->minQty,
'mul' => $this->mul,
];
}
public static function transferOkx($data, callable $getSymbolSt): SymbolInfo
... ... @@ -73,7 +76,19 @@ class SymbolInfo
$lotPrec = getPrecision($minLot);
}
}
$info = new SymbolInfo($symbolOri, $symbolSt, $ctVal, $pricePrec, $qtyPrec, $lotPrec, $minLot, $minQty);
$mul = self::extractNumber($symbolOri);
$info = new SymbolInfo($symbolOri, $symbolSt, $ctVal, $pricePrec, $qtyPrec, $lotPrec, $minLot, $minQty, $mul);
return $info;
}
public static function extractNumber($str)
{
// 示例
// echo extractNumber("1000CATUSDT") . PHP_EOL; // 输出:1000
// echo extractNumber("1000PEPEUSDT") . PHP_EOL; // 输出:1000
// echo extractNumber("1000000MOGUSDT") . PHP_EOL; // 输出:1000000
if (preg_match('/^\d+/', $str, $matches)) {
return (int)$matches[0]; // 返回整数
}
return 1;
}
}
... ...