added some feature for accounting and price 2

This commit is contained in:
2026-06-28 16:02:15 +03:30
parent 3801e5ee88
commit 89807696d6
3 changed files with 134 additions and 149 deletions
@@ -3,18 +3,8 @@
namespace App\Http\Controllers\Finance;
use App\Http\Controllers\Controller;
use App\Http\Controllers\Admin\TahesabController;
use App\Models\Customer;
use App\Models\Order;
use App\Models\Price;
use App\Models\Product;
use App\Models\TransactionsAdmin;
use App\Models\User;
use App\Models\Withdraw;
use App\Models\Tahesab;
use App\Services\TahesabSyncService;
use App\DB\Te\TableEngine;
use Symfony\Component\HttpKernel\Exception\UnprocessableEntityHttpException;
use Illuminate\Http\Request;
use Illuminate\Support\Facades\DB;
@@ -25,151 +15,21 @@ use Rooyesh\Wallet\models\Wallet;
class FinanceController extends Controller
{
/**
* دفترکل داخلی: همه رویدادهای مالی (معامله / شارژ / پاداش و …).
* مستقل از اتصال به حسابداری بیرونی — برای همه اپ‌ها نمایان است.
*/
public function fall(Request $request)
{
$transactions_admins = TransactionsAdmin::with(['withdraw','order',"user",'customerTo','customer']);
$transactions_admins = TransactionsAdmin::with(['withdraw', 'order', 'user', 'customerTo', 'customer']);
TableEngine::create($transactions_admins, $request)
->initSearch(['price'])
->select(['*'])
->export($transactions_admins);
if (isset($transactions_admins['rows']) && is_array($transactions_admins['rows']) && $this->Config('send_to_tahesab') === 'true') {
$this->enrichRowsWithTahesab($transactions_admins['rows']);
}
return response()->json($transactions_admins);
}
/**
* هر ردیف دفترکل را با وضعیت سند ته‌حساب مرتبط غنی می‌کند.
* لینک: ابتدا از طریق withdraw_id (کیف‌پول/پاداش) و سپس order_id (معامله).
*
* @param array<int, array<string, mixed>> $rows با ارجاع تغییر می‌کند
*/
private function enrichRowsWithTahesab(array &$rows): void
{
$withdrawIds = collect($rows)->pluck('withdraw_id')->filter()->unique()->values()->all();
$orderIds = collect($rows)->pluck('order_id')->filter()->unique()->values()->all();
if ($withdrawIds === [] && $orderIds === []) {
return;
}
$tahesabByWithdraw = $withdrawIds === []
? collect()
: Tahesab::query()->whereIn('withdraw_id', $withdrawIds)
->orderByDesc('id')->get()->unique('withdraw_id')->keyBy('withdraw_id');
$tahesabByOrder = $orderIds === []
? collect()
: Tahesab::query()->whereIn('order_id', $orderIds)
->orderByDesc('id')->get()->unique('order_id')->keyBy('order_id');
foreach ($rows as &$row) {
$tahesab = $tahesabByWithdraw->get($row['withdraw_id'] ?? null)
?? $tahesabByOrder->get($row['order_id'] ?? null);
if (! $tahesab) {
// ردیف دفترکل بدون سند ته‌حساب — یعنی هنوز به حسابداری ارسال نشده
$row['tahesab_record_id'] = null;
$row['tahesab_sync_status'] = TahesabSyncService::STATUS_PENDING;
$row['tahesab_failed_id'] = null;
continue;
}
$row['tahesab_record_id'] = $tahesab->id;
$row['tahesab_sync_status'] = $tahesab->sync_status
?? (empty($tahesab->tahesab_id) ? TahesabSyncService::STATUS_PENDING : TahesabSyncService::STATUS_SUCCESS);
if (empty($tahesab->tahesab_id) || $row['tahesab_sync_status'] === TahesabSyncService::STATUS_FAILED) {
$row['tahesab_failed_id'] = $tahesab->id;
}
}
unset($row);
}
/**
* سینک یک ردیف دفترکل با حسابداری (فعلاً ته‌حساب).
* اگر سند ته‌حساب مرتبط موجود باشد → retry؛ وگرنه از روی منبع (معامله) ساخته و ارسال می‌شود.
*/
public function sync(int $id)
{
if ($this->Config('send_to_tahesab') !== 'true') {
throw new UnprocessableEntityHttpException('حسابداری ته‌حساب فعال نیست');
}
$row = TransactionsAdmin::find($id);
if (! $row) {
throw new UnprocessableEntityHttpException('سند دفترکل یافت نشد');
}
$tahesab = $this->findLinkedTahesab($row);
if ($tahesab) {
$result = app(TahesabSyncService::class)->retry($tahesab);
$status = ($result['ok'] ?? false) ? 200 : 422;
return response()->json($result, $status);
}
// سند ته‌حساب وجود ندارد — اگر معامله است، از روی سفارش بساز و ارسال کن
if ($row->order_id) {
return $this->syncTradeFromOrder((int) $row->order_id);
}
throw new UnprocessableEntityHttpException(
'برای این ردیف سند ته‌حسابی یافت نشد و امکان ساخت خودکار آن وجود ندارد'
);
}
private function findLinkedTahesab(TransactionsAdmin $row): ?Tahesab
{
if ($row->withdraw_id) {
$byWithdraw = Tahesab::where('withdraw_id', $row->withdraw_id)->orderByDesc('id')->first();
if ($byWithdraw) {
return $byWithdraw;
}
}
if ($row->order_id) {
return Tahesab::where('order_id', $row->order_id)->orderByDesc('id')->first();
}
return null;
}
private function syncTradeFromOrder(int $orderId)
{
$order = Order::find($orderId);
if (! $order) {
throw new UnprocessableEntityHttpException('سفارش مرتبط یافت نشد');
}
$product = Product::find($order->product_id);
if (! $product) {
throw new UnprocessableEntityHttpException('محصول سفارش یافت نشد — امکان ساخت سند ته‌حساب نیست');
}
$data = [
'customer_id' => $order->customer_id,
'direction' => (int) $order->direction,
'price' => $order->price,
'total_price' => $order->total_price,
'amount' => $order->amount,
'pay_at' => $order->pay_at ?? $order->created_at,
'product' => $product,
'order' => ['id' => $order->id],
];
$result = app(TahesabController::class)->storeTrade($data);
$ok = $result !== false && ! is_string($result);
return response()->json([
'ok' => $ok,
'message' => $ok ? 'سند معامله در ته‌حساب ثبت شد' : (is_string($result) ? $result : 'ارسال به ته‌حساب ناموفق بود'),
], $ok ? 200 : 422);
}
public function index()
{
$tallaPrice = Price::latest()->first();