Merge origin/Abshode_Khanegi and resolve WalletController conflict.

Keep unified charge API from remote while preserving main-wallet metal detection for deposits and transaction labels via BalanceReportService.

Co-authored-by: Cursor <cursoragent@cursor.com>
This commit is contained in:
2026-06-24 01:22:56 +03:30
co-authored by Cursor
24 changed files with 1762 additions and 375 deletions
+125 -15
View File
@@ -73,6 +73,26 @@ class Controller extends BaseController
return $formatted !== '' ? $formatted : '0';
}
/**
* گزینه‌های Guzzle/cURL — فقط وقتی افزونه curl و ثابت‌ها موجود باشند.
*
* @param array<int, mixed> $curlOptions
* @return array<string, array<int, mixed>>
*/
public static function httpClientOptions(array $curlOptions = []): array
{
$curl = $curlOptions;
if (defined('CURLOPT_IPRESOLVE') && defined('CURL_IPRESOLVE_V4')) {
$resolveOpt = (int) constant('CURLOPT_IPRESOLVE');
if (! array_key_exists($resolveOpt, $curl)) {
$curl[$resolveOpt] = (int) constant('CURL_IPRESOLVE_V4');
}
}
return $curl === [] ? [] : ['curl' => $curl];
}
public static function Send($to , $msg, $is_customer = true)
{
$r = self::SendMessage($to , $msg, $is_customer);
@@ -139,26 +159,32 @@ class Controller extends BaseController
]);
$platforms[] = "0098:{$to}";*/
$response = Http::timeout(15)
->withHeaders([
'Content-Type' => 'application/json',
'secret_key' => 'f21debfb-83ac-4624-a2f4-f08375043181',
])
->withOptions([
'curl' => [
\CURLOPT_IPRESOLVE => \CURL_IPRESOLVE_V4,
]
])
->post('http://185.231.112.101/api/createsms', [
try {
$http = Http::timeout(15)
->withHeaders([
'Content-Type' => 'application/json',
'secret_key' => 'f21debfb-83ac-4624-a2f4-f08375043181',
]);
$curlOptions = self::httpClientOptions();
if ($curlOptions !== []) {
$http = $http->withOptions($curlOptions);
}
$response = $http->post('http://185.231.112.101/api/createsms', [
'phone' => $to,
'host' => $config->Config('name_fa') ?? gethostname(),
'text' => trim($msg),
'platform' => 'rayegansms',
]);
$platforms[] = $response->successful()
? "rayegansms:{$to}"
: "rayegansms_failed:{$to}:{$response->status()}";
$platforms[] = $response->successful()
? "rayegansms:{$to}"
: "rayegansms_failed:{$to}:{$response->status()}";
} catch (\Throwable $e) {
report($e);
$platforms[] = "rayegansms_error:{$to}";
}
}
@@ -435,6 +461,10 @@ class Controller extends BaseController
return false;
}
if (self::usesQuantityTrade($product)) {
return false;
}
if (self::isWeightBasedProductUnit($product['unit'] ?? null)) {
return false;
}
@@ -451,6 +481,86 @@ class Controller extends BaseController
return in_array($group, ['سکه', 'گوی', 'مکعب', 'شمش', 'سکه پارسیان'], true);
}
public static function productUnitPayload($product): array
{
if (!$product) {
return [];
}
if (is_array($product)) {
return $product;
}
return [
'unit' => $product->unit ?? null,
'direct_price' => $product->direct_price ?? null,
'group_type' => $product->group_type ?? null,
'amount' => $product->amount ?? null,
'trade_by_quantity' => $product->trade_by_quantity ?? null,
];
}
public static function convertWeight(float $value, ?string $fromUnit, ?string $toUnit): float
{
$from = trim((string) ($fromUnit ?? ''));
$to = trim((string) ($toUnit ?? ''));
if ($from === '' || $to === '' || $from === $to) {
return $value;
}
$grams = self::weightToGrams($value, $from);
return $to === 'کیلوگرم' ? $grams / 1000 : $grams;
}
/**
* مقدار و واحد نمایشی تراکنش — منبع حقیقت: unit محصول در ادمین.
* معامله مقداری + وزن دارد: تعداد ذخیره‌شده × وزن هر واحد.
*/
public static function resolveTransactionDisplayGoldAndUnit(?array $payload, float $gold, bool $onMainWallet = false): array
{
if ($payload === []) {
return [$gold, self::tradeWeightUnit()];
}
$sign = $gold < 0 ? -1 : 1;
$absGold = abs($gold);
if (
self::usesQuantityTrade($payload)
&& self::hasProductUnitWeight($payload)
&& self::isWeightBasedProductUnit($payload['unit'] ?? null)
) {
$factor = (float) ($payload['amount'] ?? 1);
return [
round($absGold * $factor, 3) * $sign,
trim((string) $payload['unit']),
];
}
$unit = self::productQuantityUnit($payload);
$productWeightUnit = self::isWeightBasedProductUnit($payload['unit'] ?? null)
? trim((string) $payload['unit'])
: null;
if ($onMainWallet && $productWeightUnit) {
$tradeUnit = self::tradeWeightUnit();
if ($productWeightUnit !== $tradeUnit) {
return [
round(self::convertWeight($absGold, $tradeUnit, $productWeightUnit), 3) * $sign,
$productWeightUnit,
];
}
return [$gold, $productWeightUnit];
}
return [$gold, $unit];
}
public static function productQuantityUnit(?array $product): string
{
$unit = trim((string) ($product['unit'] ?? ''));
@@ -462,7 +572,7 @@ class Controller extends BaseController
return 'عدد';
}
return 'گرم';
return self::tradeWeightUnit();
}
/** مطابق ادمین: وزن «دارد» => amount > 0 ؛ «ندارد» => amount = 0 */