diff --git a/app/Http/Controllers/Customer/CartController.php b/app/Http/Controllers/Customer/CartController.php index b9c7a50..10fbc69 100644 --- a/app/Http/Controllers/Customer/CartController.php +++ b/app/Http/Controllers/Customer/CartController.php @@ -127,6 +127,8 @@ class CartController extends Controller { // return $request; + app(ConfigService::class)->assertTradingOpen(); + $data = $request->json()->all(); $user= auth()->user(); if ($user->is_legal == 0 || !$user) { diff --git a/app/Http/Controllers/Customer/OrderController.php b/app/Http/Controllers/Customer/OrderController.php index c0c9c59..a199a62 100644 --- a/app/Http/Controllers/Customer/OrderController.php +++ b/app/Http/Controllers/Customer/OrderController.php @@ -10,6 +10,7 @@ use App\Models\Order; use App\Models\Price; use App\Models\Setting; use App\Models\User; +use App\Services\ConfigService; use Carbon\Carbon; use Illuminate\Http\Request; use Rooyesh\Wallet\interfaces\TransactionInterface; @@ -40,6 +41,7 @@ class OrderController extends Controller if (!auth('customer')->user()->trade_active){ throw new UnprocessableEntityHttpException('امکان سفارش برای شما غیرفعال است.'); } + app(ConfigService::class)->assertTradingOpen(); $wallet = Wallet::where('owner',auth('customer')->id())->whereNull('fund_id') ->first(); $wallet_interface = new WalletInterface($data['customer_id'], 1); diff --git a/app/Http/Controllers/Single/SingleOrderController.php b/app/Http/Controllers/Single/SingleOrderController.php index ff860ca..00b3a68 100644 --- a/app/Http/Controllers/Single/SingleOrderController.php +++ b/app/Http/Controllers/Single/SingleOrderController.php @@ -53,9 +53,7 @@ class SingleOrderController extends Controller } if ($toBool($config->Config('close_price'))) { - if (Cnt::where('key', 'app_closed')->value('value') == "true") { - throw new UnprocessableEntityHttpException('عدم ارائه سرویس.'); - } + $config->assertTradingOpen(); } // throw new UnprocessableEntityHttpException('به دلیل نوسانات سفارشات بسته میباشد.'); diff --git a/app/Http/Controllers/Site/ReportController.php b/app/Http/Controllers/Site/ReportController.php index 50ae70f..7ad6c03 100644 --- a/app/Http/Controllers/Site/ReportController.php +++ b/app/Http/Controllers/Site/ReportController.php @@ -206,22 +206,8 @@ class ReportController extends Controller |-------------------------------------------------------------------------- */ if ($toBool($config->Config('close_price'))) { - $startDay = $config->Config('startDay') ?: '00:00'; - [$startHour, $startMinute] = explode(':', $startDay); - - $endDay = $config->Config('endDay') ?: '23:59'; - [$endHour, $endMinute] = explode(':', $endDay); - - $current = Carbon::now(); - $start = Carbon::today()->setTime((int) $startHour, (int) $startMinute); - $end = Carbon::today()->setTime((int) $endHour, (int) $endMinute); - - if (!$current->between($start, $end)) { - // عمومی: در Cnt بماند - Cnt::where('key', 'app_closed')->update(['value' => 'true']); - - // مربوط به منتزر: settings - $config->UpdateConfig('montzar_closed', 'true'); + if ($config->isOutsideTradingHours()) { + $config->syncAppClosedFlag(); return $zeroResponse(); } diff --git a/app/Services/ConfigService.php b/app/Services/ConfigService.php index 9c02725..534dd95 100644 --- a/app/Services/ConfigService.php +++ b/app/Services/ConfigService.php @@ -7,6 +7,8 @@ use App\Models\Price; use App\Models\PriceCandle; use App\Models\Product; use App\Models\Setting; +use Carbon\Carbon; +use Symfony\Component\HttpKernel\Exception\UnprocessableEntityHttpException; class ConfigService { @@ -397,4 +399,68 @@ class ConfigService 'max' => $max, ]; } + + public function isClosePriceEnabled(): bool + { + return $this->getBool('close_price', false); + } + + /** @return array{start: string, end: string} */ + public function tradingHourBounds(): array + { + return [ + 'start' => $this->normalizeTradingTime($this->getString('startDay', '00:00'), '00:00'), + 'end' => $this->normalizeTradingTime($this->getString('endDay', '23:59'), '23:59'), + ]; + } + + private function normalizeTradingTime(string $value, string $default): string + { + $value = trim($value); + if ($value === '') { + $value = $default; + } + + if (preg_match('/^(\d{1,2}):(\d{2})(?::(\d{2}))?$/', $value, $matches)) { + return sprintf('%02d:%02d', (int) $matches[1], (int) $matches[2]); + } + + return $default; + } + + public function isOutsideTradingHours(?Carbon $now = null): bool + { + if (!$this->isClosePriceEnabled()) { + return false; + } + + $now = $now ?? Carbon::now(); + $bounds = $this->tradingHourBounds(); + [$startHour, $startMinute] = array_map('intval', explode(':', $bounds['start'])); + [$endHour, $endMinute] = array_map('intval', explode(':', $bounds['end'])); + + $start = $now->copy()->startOfDay()->setTime($startHour, $startMinute); + $end = $now->copy()->startOfDay()->setTime($endHour, $endMinute); + + return !$now->between($start, $end); + } + + public function syncAppClosedFlag(?Carbon $now = null): bool + { + $closed = $this->isOutsideTradingHours($now); + Cnt::where('key', 'app_closed')->update(['value' => $closed ? 'true' : 'false']); + + if ($closed) { + $this->UpdateConfig('montzar_closed', 'true'); + } + + return $closed; + } + + public function assertTradingOpen(?Carbon $now = null): void + { + if ($this->isOutsideTradingHours($now)) { + throw new UnprocessableEntityHttpException('فروشگاه در حال حاضر بسته است.'); + } + } } diff --git a/database/sql/bazre_tala_settings_update.sql b/database/sql/bazre_tala_settings_update.sql index 4dbeb48..7a80dc7 100644 --- a/database/sql/bazre_tala_settings_update.sql +++ b/database/sql/bazre_tala_settings_update.sql @@ -432,7 +432,7 @@ UPDATE `settings` SET `title_fa` = 'کارمزد رایگان (تعداد)', `ty UPDATE `settings` SET `title_fa` = 'کارمزد درصدی (legacy)', `type` = 'number', `is_active` = COALESCE(`is_active`, 1) WHERE `key` = 'fee'; UPDATE `settings` SET `title_fa` = 'کارمزد درصدی', `type` = 'number', `is_active` = COALESCE(`is_active`, 1) WHERE `key` = 'fee_service_charge_percentage'; UPDATE `settings` SET `title_fa` = 'کارمزد درصدی (alias)', `type` = 'number', `is_active` = COALESCE(`is_active`, 1) WHERE `key` = 'service_charge_percentage'; -UPDATE `settings` SET `title_fa` = 'کارمزد ریالی', `type` = 'number', `is_active` = COALESCE(`is_active`, 1) WHERE `key` = 'fee_cash'; +UPDATE `settings` SET `title_fa` = 'کارمزد ریالی', `type` = 'number', `is_active` = COALESCE(`is_active`, 1), `can_edit` = 0 WHERE `key` = 'fee_cash'; UPDATE `settings` SET `title_fa` = 'اختلاف با قیمت واقعی', `type` = 'number', `is_active` = COALESCE(`is_active`, 1) WHERE `key` = 'fee_single'; UPDATE `settings` SET `title_fa` = 'سود خرید', `type` = 'number', `is_active` = COALESCE(`is_active`, 1) WHERE `key` = 'buy_fee'; UPDATE `settings` SET `title_fa` = 'سود فروش', `type` = 'number', `is_active` = COALESCE(`is_active`, 1) WHERE `key` = 'sell_fee'; diff --git a/database/sql/deploy_settings_const.sql b/database/sql/deploy_settings_const.sql index c0d218a..3442f87 100644 --- a/database/sql/deploy_settings_const.sql +++ b/database/sql/deploy_settings_const.sql @@ -387,7 +387,7 @@ SELECT 'sell_fee', '', 'سود فروش نمایش', 1, 1, NULL, 'number' WHERE NOT EXISTS (SELECT 1 FROM `settings` WHERE `key` = 'sell_fee' LIMIT 1); INSERT INTO `settings` (`key`, `value`, `title_fa`, `can_edit`, `is_active`, `description`, `type`) -SELECT 'fee_cash', '500000', 'کارمزد ریالی سفارش (legacy)', 1, 1, NULL, 'number' +SELECT 'fee_cash', '500000', 'کارمزد ریالی سفارش (legacy)', 0, 1, NULL, 'number' WHERE NOT EXISTS (SELECT 1 FROM `settings` WHERE `key` = 'fee_cash' LIMIT 1); INSERT INTO `settings` (`key`, `value`, `title_fa`, `can_edit`, `is_active`, `description`, `type`) @@ -816,6 +816,9 @@ WHERE `key` = 'send_to_tahesab' AND TRIM(COALESCE(`value`, '')) = ''; -- is_store فقط از دیتابیس/دیپلوی — در پنل قابل ویرایش نیست UPDATE `settings` SET `can_edit` = 0 WHERE `key` = 'is_store'; +-- fee_cash legacy — فقط از دیپلوی/SQL +UPDATE `settings` SET `can_edit` = 0 WHERE `key` = 'fee_cash'; + -- لوگو / PWA / favicon — فقط از دیپلوی؛ در پنل نمایش داده نمی‌شوند UPDATE `settings` SET `can_edit` = 0, `is_active` = 0 WHERE `key` IN ('logo_login', 'logo_register', 'title_pwa', 'title_fav'); diff --git a/database/sql/garoosi_gold_settings_update.sql b/database/sql/garoosi_gold_settings_update.sql index cdfa986..930a1aa 100644 --- a/database/sql/garoosi_gold_settings_update.sql +++ b/database/sql/garoosi_gold_settings_update.sql @@ -83,7 +83,7 @@ UPDATE `settings` SET `title_fa` = 'چت', `type` = 'switch', UPDATE `settings` SET `title_fa` = 'آدرس API', `type` = 'text', `is_active` = COALESCE(`is_active`, 1) WHERE `key` = 'server_url'; UPDATE `settings` SET `title_fa` = 'کلید اپ', `type` = 'text', `is_active` = COALESCE(`is_active`, 1) WHERE `key` = 'key'; UPDATE `settings` SET `title_fa` = 'توکن بات تلگرام', `type` = 'text', `is_active` = COALESCE(`is_active`, 1), `can_edit` = 0 WHERE `key` = 'telegram_bot_token'; -UPDATE `settings` SET `title_fa` = 'کارمزد ریالی', `type` = 'number', `is_active` = COALESCE(`is_active`, 1) WHERE `key` = 'fee_cash'; +UPDATE `settings` SET `title_fa` = 'کارمزد ریالی', `type` = 'number', `is_active` = COALESCE(`is_active`, 1), `can_edit` = 0 WHERE `key` = 'fee_cash'; UPDATE `settings` SET `title_fa` = 'اختلاف با قیمت واقعی', `type` = 'number', `is_active` = COALESCE(`is_active`, 1) WHERE `key` = 'fee_single'; UPDATE `settings` SET `title_fa` = 'ارسال اسناد به ته‌حساب', `type` = 'switch', `is_active` = COALESCE(`is_active`, 1) WHERE `key` = 'send_to_tahesab'; UPDATE `settings` SET `title_fa` = 'تعداد سفارش اول بدون کارمزد', `type` = 'number', `is_active` = COALESCE(`is_active`, 1) WHERE `key` = 'fee_free'; diff --git a/database/sql/goldali_settings_full_catalog.sql b/database/sql/goldali_settings_full_catalog.sql index bffd52f..ad9bcbb 100644 --- a/database/sql/goldali_settings_full_catalog.sql +++ b/database/sql/goldali_settings_full_catalog.sql @@ -277,7 +277,7 @@ WHERE `key` = 'buy_fee'; UPDATE `settings` SET `title_fa` = COALESCE(NULLIF(TRIM(`title_fa`), ''), 'سود فروش نمایش'), `can_edit` = 1 WHERE `key` = 'sell_fee'; -UPDATE `settings` SET `title_fa` = COALESCE(NULLIF(TRIM(`title_fa`), ''), 'کارمزد ریالی سفارش (legacy)'), `can_edit` = 1 +UPDATE `settings` SET `title_fa` = COALESCE(NULLIF(TRIM(`title_fa`), ''), 'کارمزد ریالی سفارش (legacy)'), `can_edit` = 0 WHERE `key` = 'fee_cash'; UPDATE `settings` SET `title_fa` = COALESCE(NULLIF(TRIM(`title_fa`), ''), 'درصد کارمزد سفارش'), `can_edit` = 1