174 lines
7.0 KiB
PHP
174 lines
7.0 KiB
PHP
<?php
|
|
require_once __DIR__ . '/../app/lib/auth.php';
|
|
require_once __DIR__ . '/../app/lib/db.php';
|
|
require_once __DIR__ . '/../app/lib/helpers.php';
|
|
require_once __DIR__ . '/../app/lib/card_billing_service.php';
|
|
|
|
check_auth();
|
|
|
|
$pdo = db();
|
|
$uid = user_id();
|
|
|
|
$ym = $_GET['ym'] ?? date('Y-m');
|
|
$nextYm = date('Y-m', strtotime($ym . '-01 +1 month'));
|
|
|
|
$stmt = $pdo->prepare("
|
|
SELECT *
|
|
FROM accounts
|
|
WHERE user_id = ?
|
|
ORDER BY FIELD(account_type, 'bank', 'card', 'cash', 'other'), id ASC
|
|
");
|
|
$stmt->execute([$uid]);
|
|
$accounts = $stmt->fetchAll();
|
|
|
|
$cardDueMap = [];
|
|
|
|
$stmt = $pdo->prepare("
|
|
SELECT
|
|
t.account_id,
|
|
t.billing_year_month,
|
|
COALESCE(SUM(t.amount),0) total_amount
|
|
FROM transactions t
|
|
JOIN accounts a ON a.id=t.account_id
|
|
WHERE t.user_id=?
|
|
AND t.transaction_type='expense'
|
|
AND a.account_type='card'
|
|
AND a.card_kind='credit'
|
|
AND COALESCE(t.is_installment,0)=0
|
|
AND t.billing_year_month IN (?,?)
|
|
GROUP BY t.account_id,t.billing_year_month
|
|
");
|
|
$stmt->execute([$uid,$ym,$nextYm]);
|
|
|
|
foreach ($stmt->fetchAll() as $row) {
|
|
$aid = (int)$row['account_id'];
|
|
$billYm = $row['billing_year_month'];
|
|
|
|
$cardDueMap[$aid][$billYm] =
|
|
($cardDueMap[$aid][$billYm] ?? 0) + (float)$row['total_amount'];
|
|
}
|
|
|
|
$stmt = $pdo->prepare("
|
|
SELECT
|
|
i.account_id AS account_id,
|
|
s.bill_year_month,
|
|
COALESCE(SUM(s.total_amount),0) total_amount
|
|
FROM installment_schedules s
|
|
JOIN installments i ON i.id=s.installment_id
|
|
WHERE i.user_id=?
|
|
AND s.is_billed=0
|
|
AND s.total_amount>0
|
|
AND s.bill_year_month IN (?,?)
|
|
GROUP BY i.account_id,s.bill_year_month
|
|
");
|
|
$stmt->execute([$uid,$ym,$nextYm]);
|
|
|
|
foreach ($stmt->fetchAll() as $row) {
|
|
$aid = (int)$row['account_id'];
|
|
$billYm = $row['bill_year_month'];
|
|
|
|
$cardDueMap[$aid][$billYm] =
|
|
($cardDueMap[$aid][$billYm] ?? 0) + (float)$row['total_amount'];
|
|
}
|
|
|
|
require __DIR__ . '/../app/views/header.php';
|
|
?>
|
|
|
|
<div class="page-head">
|
|
<h2>계좌 / 카드 현황</h2>
|
|
<div class="d-flex gap-2">
|
|
<form method="get" class="d-flex gap-2">
|
|
<input type="month" name="ym" class="form-control" value="<?= h($ym) ?>">
|
|
<button class="btn btn-outline-primary">조회</button>
|
|
</form>
|
|
<a href="/account_create.php" class="btn btn-primary">추가</a>
|
|
</div>
|
|
</div>
|
|
|
|
<div class="row g-3">
|
|
<?php foreach ($accounts as $account): ?>
|
|
<?php
|
|
$isCard = $account['account_type'] === 'card';
|
|
$cardKind = $account['card_kind'] ?? null;
|
|
$thisMonthDue = $cardDueMap[(int)$account['id']][$ym] ?? 0;
|
|
$nextMonthDue = $cardDueMap[(int)$account['id']][$nextYm] ?? 0;
|
|
?>
|
|
<div class="col-12 col-md-6 col-xl-4">
|
|
<div class="card finance-card h-100">
|
|
<div class="card-body">
|
|
<div class="d-flex justify-content-between align-items-start gap-3 mb-2">
|
|
<div>
|
|
<div class="eyebrow">
|
|
<?= h(blank_to_dash($account['institution_name'])) ?> / <?= h($account['account_type']) ?>
|
|
</div>
|
|
<div class="card-title-lg"><?= h($account['account_name']) ?></div>
|
|
</div>
|
|
|
|
<span class="badge <?= $account['is_active'] ? 'text-bg-success' : 'text-bg-secondary' ?>">
|
|
<?= $account['is_active'] ? 'active' : 'inactive' ?>
|
|
</span>
|
|
</div>
|
|
|
|
<?php if ($isCard): ?>
|
|
<div class="mb-3">
|
|
<span class="badge <?= $cardKind === 'credit' ? 'text-bg-warning' : 'text-bg-info' ?>">
|
|
<?= $cardKind === 'credit' ? '신용카드' : ($cardKind === 'check' ? '체크카드' : '카드') ?>
|
|
</span>
|
|
</div>
|
|
|
|
<?php if ($cardKind === 'credit'): ?>
|
|
<div class="row g-3">
|
|
<div class="col-6">
|
|
<div class="stat-label"><?= h($ym) ?> 청구예정</div>
|
|
<div class="stat-value text-danger"><?= won($thisMonthDue) ?></div>
|
|
</div>
|
|
<div class="col-6">
|
|
<div class="stat-label"><?= h($nextYm) ?> 이월예정</div>
|
|
<div class="stat-value"><?= won($nextMonthDue) ?></div>
|
|
</div>
|
|
|
|
<div class="col-6">
|
|
<div class="stat-label">결제기준일</div>
|
|
<div class="stat-value">
|
|
<?= !empty($account['billing_day']) ? intvalf($account['billing_day']) . '일' : '-' ?>
|
|
</div>
|
|
</div>
|
|
<div class="col-6">
|
|
<div class="stat-label">납부일</div>
|
|
<div class="stat-value">
|
|
<?= !empty($account['payment_day']) ? intvalf($account['payment_day']) . '일' : '-' ?>
|
|
</div>
|
|
</div>
|
|
</div>
|
|
|
|
<div class="small text-secondary mt-3">
|
|
<?= h(get_card_billing_label($account)) ?>
|
|
</div>
|
|
<?php else: ?>
|
|
<div class="stat-label">체크카드 잔액 기준</div>
|
|
<div class="stat-value text-primary"><?= won($account['current_balance']) ?></div>
|
|
<div class="small text-secondary mt-2">체크카드는 신용공여기간 없이 거래월 기준으로 반영됩니다.</div>
|
|
<?php endif; ?>
|
|
<?php else: ?>
|
|
<div class="stat-label">현재 잔액</div>
|
|
<div class="stat-value text-primary"><?= won($account['current_balance']) ?></div>
|
|
<?php endif; ?>
|
|
|
|
<div class="mt-3 d-flex gap-2">
|
|
<a href="/account_edit.php?id=<?= $account['id'] ?>" class="btn btn-sm btn-outline-primary">수정</a>
|
|
</div>
|
|
</div>
|
|
</div>
|
|
</div>
|
|
<?php endforeach; ?>
|
|
|
|
<?php if (!$accounts): ?>
|
|
<div class="col-12">
|
|
<div class="card finance-card">
|
|
<div class="card-body empty-state">등록된 계좌/카드가 없습니다.</div>
|
|
</div>
|
|
</div>
|
|
<?php endif; ?>
|
|
</div>
|
|
|
|
<?php require __DIR__ . '/../app/views/footer.php'; ?>
|