fix bug
This commit is contained in:
@@ -207,9 +207,7 @@ class ProductController extends SuperController
|
||||
$displayPriceService->warmLivePriceCache();
|
||||
$displayPriceService->enrichForApi($products);
|
||||
$products->each(function (Product $product) use ($displayPriceService) {
|
||||
if (! $displayPriceService->hasCustomerDisplayPrice($product)) {
|
||||
$product->setAttribute('show', false);
|
||||
}
|
||||
$product->setAttribute('show', $displayPriceService->resolveCustomerShow($product));
|
||||
});
|
||||
}
|
||||
|
||||
@@ -257,12 +255,11 @@ class ProductController extends SuperController
|
||||
|
||||
public function auto_close_open()
|
||||
{
|
||||
$config = app(ConfigService::class);
|
||||
$products = Product::with([])->get();
|
||||
$current_time = now()->format('H:i:s');
|
||||
foreach ($products as $product) {
|
||||
$show = ($current_time >= $product->auto_open_at && $current_time <= $product->auto_close_at);
|
||||
Product::where('id', $product->id)->update([
|
||||
'show' => $show,
|
||||
'show' => $config->isProductWithinTradingHours($product),
|
||||
]);
|
||||
}
|
||||
|
||||
@@ -358,13 +355,17 @@ class ProductController extends SuperController
|
||||
|
||||
}
|
||||
|
||||
/** فروشگاه — نمایش در اپ کاربر: فعال + قیمت ذخیرهشده یا محصول وزنی */
|
||||
/** فروشگاه — نمایش در اپ کاربر: فعال + ساعات + قیمت ذخیرهشده یا محصول وزنی */
|
||||
private function storeProductShowForCustomer(Product $product): bool
|
||||
{
|
||||
if (! $product->active) {
|
||||
return false;
|
||||
}
|
||||
|
||||
if (! app(ConfigService::class)->isProductWithinTradingHours($product)) {
|
||||
return false;
|
||||
}
|
||||
|
||||
$storedPrice = (int) ($product->price ?? 0) + (int) ($product->price_profit ?? 0);
|
||||
if ($storedPrice > 0) {
|
||||
return true;
|
||||
|
||||
@@ -364,6 +364,8 @@ class CartController extends Controller
|
||||
throw new UnprocessableEntityHttpException("خرید {$product->title} در این لحظه مقدور نیست.");
|
||||
}
|
||||
|
||||
app(ConfigService::class)->assertProductTradingOpen($product);
|
||||
|
||||
$line = $requestLines->get($item->product_id);
|
||||
$qty = (int) $item->quantity;
|
||||
|
||||
|
||||
@@ -42,6 +42,8 @@ class SingleOrderController extends Controller
|
||||
return filter_var($value, FILTER_VALIDATE_BOOLEAN);
|
||||
};
|
||||
|
||||
$config->assertTradingOpen();
|
||||
|
||||
if ($config->usesMontzarPricing()) {
|
||||
$montzar_closed = $toBool($config->Config('montzar_closed'));
|
||||
$montzar_buy = !$toBool($config->Config('montzar_open_buy')) && (int) $data['direction'] === 1;
|
||||
@@ -52,10 +54,6 @@ class SingleOrderController extends Controller
|
||||
}
|
||||
}
|
||||
|
||||
if ($toBool($config->Config('close_price'))) {
|
||||
$config->assertTradingOpen();
|
||||
}
|
||||
|
||||
// throw new UnprocessableEntityHttpException('به دلیل نوسانات سفارشات بسته میباشد.');
|
||||
$transactionType = $data['direction'] == 1 ? "خرید" : "فروش";
|
||||
$customer = Customer::find(auth('customer')->id() ?? ($data['customer_id'] ?? null));
|
||||
@@ -76,6 +74,9 @@ class SingleOrderController extends Controller
|
||||
$latestPrice = Price::latest()->first();
|
||||
|
||||
if (!$latestPrice || $latestPrice->price == 0) {
|
||||
if ($config->isOutsideTradingHours()) {
|
||||
throw new UnprocessableEntityHttpException($config->tradingClosedMessage());
|
||||
}
|
||||
throw new UnprocessableEntityHttpException('عدم ارائه سرویس.');
|
||||
}
|
||||
$data['all_price'] = $latestPrice;
|
||||
@@ -120,6 +121,8 @@ class SingleOrderController extends Controller
|
||||
|
||||
// Check if the user wants to transact with a product or non-product (gold)
|
||||
if (isset($data['product_id']) and $data['product'] = Product::find($data['product_id'])) {
|
||||
$config->assertProductTradingOpen($data['product']);
|
||||
|
||||
// Check if the user wants to buy
|
||||
if ($data['direction'] == 1) {
|
||||
|
||||
@@ -166,6 +169,7 @@ class SingleOrderController extends Controller
|
||||
if (!$data['product']) {
|
||||
throw new UnprocessableEntityHttpException('محصول آبشده یافت نشد.');
|
||||
}
|
||||
$config->assertProductTradingOpen($data['product']);
|
||||
if ($data['direction'] == 1) {
|
||||
$data['difference'] = $this->resolveCashSpread($config, $data['product'], 1);
|
||||
$data['service_charge_percentage'] = $data['product']['percent_fee_buy'];
|
||||
|
||||
@@ -457,10 +457,103 @@ class ConfigService
|
||||
return $closed;
|
||||
}
|
||||
|
||||
public function formatTradingTimeForDisplay(string $time): string
|
||||
{
|
||||
$normalized = $this->normalizeTradingTime($time, '00:00');
|
||||
|
||||
return $normalized . ':00';
|
||||
}
|
||||
|
||||
public function tradingClosedMessage(?Carbon $now = null): string
|
||||
{
|
||||
$bounds = $this->tradingHourBounds();
|
||||
$start = $this->formatTradingTimeForDisplay($bounds['start']);
|
||||
$end = $this->formatTradingTimeForDisplay($bounds['end']);
|
||||
|
||||
return "فروشگاه در حال حاضر بسته است. ساعت کاری از {$start} تا {$end} میباشد.";
|
||||
}
|
||||
|
||||
public function assertTradingOpen(?Carbon $now = null): void
|
||||
{
|
||||
if ($this->isOutsideTradingHours($now)) {
|
||||
throw new UnprocessableEntityHttpException('فروشگاه در حال حاضر بسته است.');
|
||||
throw new UnprocessableEntityHttpException($this->tradingClosedMessage($now));
|
||||
}
|
||||
}
|
||||
|
||||
public function hasProductTradingWindow(?string $open, ?string $close): bool
|
||||
{
|
||||
if ($open === null || $close === null || trim($open) === '' || trim($close) === '') {
|
||||
return false;
|
||||
}
|
||||
|
||||
return $this->formatProductTime($open) !== $this->formatProductTime($close);
|
||||
}
|
||||
|
||||
public function formatProductTime(?string $time): string
|
||||
{
|
||||
if ($time === null || trim($time) === '') {
|
||||
return '00:00:00';
|
||||
}
|
||||
|
||||
$time = trim($time);
|
||||
if (preg_match('/(\d{1,2}:\d{2}(?::\d{2})?)/', $time, $matches)) {
|
||||
$parts = explode(':', $matches[1]);
|
||||
|
||||
return sprintf(
|
||||
'%02d:%02d:%02d',
|
||||
(int) ($parts[0] ?? 0),
|
||||
(int) ($parts[1] ?? 0),
|
||||
(int) ($parts[2] ?? 0)
|
||||
);
|
||||
}
|
||||
|
||||
return '00:00:00';
|
||||
}
|
||||
|
||||
public function isWithinTimeWindow(?string $open, ?string $close, ?Carbon $now = null): bool
|
||||
{
|
||||
if (!$this->hasProductTradingWindow($open, $close)) {
|
||||
return true;
|
||||
}
|
||||
|
||||
$now = $now ?? Carbon::now();
|
||||
$current = $now->format('H:i:s');
|
||||
$openStr = $this->formatProductTime($open);
|
||||
$closeStr = $this->formatProductTime($close);
|
||||
|
||||
return $current >= $openStr && $current <= $closeStr;
|
||||
}
|
||||
|
||||
/** ساعت کاری سراسری (close_price) + بازه auto_open_at/auto_close_at هر محصول */
|
||||
public function isProductWithinTradingHours(Product $product, ?Carbon $now = null): bool
|
||||
{
|
||||
if ($this->isClosePriceEnabled() && $this->isOutsideTradingHours($now)) {
|
||||
return false;
|
||||
}
|
||||
|
||||
return $this->isWithinTimeWindow($product->auto_open_at, $product->auto_close_at, $now);
|
||||
}
|
||||
|
||||
public function productTradingClosedMessage(Product $product): string
|
||||
{
|
||||
$title = trim((string) ($product->title ?? 'محصول'));
|
||||
|
||||
if ($this->hasProductTradingWindow($product->auto_open_at, $product->auto_close_at)) {
|
||||
$open = $this->formatProductTime($product->auto_open_at);
|
||||
$close = $this->formatProductTime($product->auto_close_at);
|
||||
|
||||
return "محصول «{$title}» در حال حاضر بسته است. ساعت فعالسازی از {$open} تا {$close} میباشد.";
|
||||
}
|
||||
|
||||
return $this->tradingClosedMessage();
|
||||
}
|
||||
|
||||
public function assertProductTradingOpen(Product $product, ?Carbon $now = null): void
|
||||
{
|
||||
$this->assertTradingOpen($now);
|
||||
|
||||
if (!$this->isProductWithinTradingHours($product, $now)) {
|
||||
throw new UnprocessableEntityHttpException($this->productTradingClosedMessage($product));
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
@@ -462,7 +462,11 @@ class ProductDisplayPriceService
|
||||
*/
|
||||
public function resolveCustomerShow(Product $product): bool
|
||||
{
|
||||
if (! (bool) ($product->show ?? true)) {
|
||||
if (! (bool) ($product->active ?? true)) {
|
||||
return false;
|
||||
}
|
||||
|
||||
if (! app(ConfigService::class)->isProductWithinTradingHours($product)) {
|
||||
return false;
|
||||
}
|
||||
|
||||
|
||||
@@ -178,7 +178,7 @@ class ProductPriceSyncService
|
||||
$synced = false;
|
||||
|
||||
foreach ($products as $product) {
|
||||
$show = ($currentTime >= $product->auto_open_at && $currentTime <= $product->auto_close_at);
|
||||
$show = app(ConfigService::class)->isProductWithinTradingHours($product);
|
||||
|
||||
foreach ($RPrices as $RPrice) {
|
||||
if ($product->reading_method == ($RPrice['name'] ?? null)) {
|
||||
|
||||
@@ -349,7 +349,7 @@ class ZaarboxPriceService
|
||||
$liquidGoldPrice = app(ProductDisplayPriceService::class)->resolveAppBasePrice();
|
||||
$p = Product::find($product->id);
|
||||
if ($p && $liquidGoldPrice > 0) {
|
||||
$show = ($currentTime >= $product->auto_open_at && $currentTime <= $product->auto_close_at);
|
||||
$show = app(ConfigService::class)->isProductWithinTradingHours($product);
|
||||
$p->amount = $row['price'] / $liquidGoldPrice;
|
||||
$p->show = $show;
|
||||
$p->save();
|
||||
|
||||
Reference in New Issue
Block a user