Files
sam-api/routes/api/v1/finance.php
김보곤 3b116c980b feat: [tax-invoice] 바로빌 SOAP 연동 및 공급자 설정 API 추가
- BarobillService HTTP→SOAP 전환 (MNG EtaxController 포팅)
- TI SOAP 클라이언트, callSoap(), buildTaxInvoiceData MNG 형식 적용
- issueTaxInvoice/cancelTaxInvoice/checkNtsSendStatus SOAP 방식
- 공급자 설정 조회/저장 API (GET/PUT /supplier-settings)
- 생성+즉시발행 통합 API (POST /issue-direct)
- SaveSupplierSettingsRequest FormRequest 추가
2026-02-21 17:19:18 +09:00

326 lines
23 KiB
PHP

<?php
/**
* 재무 관리 API 라우트 (v1)
*
* - 카드/계좌 관리
* - 입출금 관리
* - 급여/급료 관리
* - 채권/채무 관리
* - 세금계산서
* - 어음 관리
* - 대시보드/보고서
*/
use App\Http\Controllers\Api\V1\BadDebtController;
use App\Http\Controllers\Api\V1\BankAccountController;
use App\Http\Controllers\Api\V1\BankTransactionController;
use App\Http\Controllers\Api\V1\BarobillController;
use App\Http\Controllers\Api\V1\BarobillSettingController;
use App\Http\Controllers\Api\V1\BillController;
use App\Http\Controllers\Api\V1\CalendarController;
use App\Http\Controllers\Api\V1\CardController;
use App\Http\Controllers\Api\V1\CardTransactionController;
use App\Http\Controllers\Api\V1\ComprehensiveAnalysisController;
use App\Http\Controllers\Api\V1\CorporateCardController;
use App\Http\Controllers\Api\V1\DailyReportController;
use App\Http\Controllers\Api\V1\DepositController;
use App\Http\Controllers\Api\V1\EntertainmentController;
use App\Http\Controllers\Api\V1\ExpectedExpenseController;
use App\Http\Controllers\Api\V1\LoanController;
use App\Http\Controllers\Api\V1\PaymentController;
use App\Http\Controllers\Api\V1\PayrollController;
use App\Http\Controllers\Api\V1\PlanController;
use App\Http\Controllers\Api\V1\ReceivablesController;
use App\Http\Controllers\Api\V1\SalaryController;
use App\Http\Controllers\Api\V1\StatusBoardController;
use App\Http\Controllers\Api\V1\SubscriptionController;
use App\Http\Controllers\Api\V1\TaxInvoiceController;
use App\Http\Controllers\Api\V1\TodayIssueController;
use App\Http\Controllers\Api\V1\VatController;
use App\Http\Controllers\Api\V1\VendorLedgerController;
use App\Http\Controllers\Api\V1\WelfareController;
use App\Http\Controllers\Api\V1\WithdrawalController;
use Illuminate\Support\Facades\Route;
// Card API (카드 관리)
Route::prefix('cards')->group(function () {
Route::get('', [CardController::class, 'index'])->name('v1.cards.index');
Route::post('', [CardController::class, 'store'])->name('v1.cards.store');
Route::get('/active', [CardController::class, 'active'])->name('v1.cards.active');
Route::get('/{id}', [CardController::class, 'show'])->whereNumber('id')->name('v1.cards.show');
Route::put('/{id}', [CardController::class, 'update'])->whereNumber('id')->name('v1.cards.update');
Route::delete('/{id}', [CardController::class, 'destroy'])->whereNumber('id')->name('v1.cards.destroy');
Route::patch('/{id}/toggle', [CardController::class, 'toggle'])->whereNumber('id')->name('v1.cards.toggle');
});
// BankAccount API (계좌 관리)
Route::prefix('bank-accounts')->group(function () {
Route::get('', [BankAccountController::class, 'index'])->name('v1.bank-accounts.index');
Route::post('', [BankAccountController::class, 'store'])->name('v1.bank-accounts.store');
Route::get('/active', [BankAccountController::class, 'active'])->name('v1.bank-accounts.active');
Route::get('/{id}', [BankAccountController::class, 'show'])->whereNumber('id')->name('v1.bank-accounts.show');
Route::put('/{id}', [BankAccountController::class, 'update'])->whereNumber('id')->name('v1.bank-accounts.update');
Route::delete('/{id}', [BankAccountController::class, 'destroy'])->whereNumber('id')->name('v1.bank-accounts.destroy');
Route::patch('/{id}/toggle', [BankAccountController::class, 'toggle'])->whereNumber('id')->name('v1.bank-accounts.toggle');
Route::patch('/{id}/set-primary', [BankAccountController::class, 'setPrimary'])->whereNumber('id')->name('v1.bank-accounts.set-primary');
});
// CorporateCard API (법인카드 관리)
Route::prefix('corporate-cards')->group(function () {
Route::get('', [CorporateCardController::class, 'index'])->name('v1.corporate-cards.index');
Route::post('', [CorporateCardController::class, 'store'])->name('v1.corporate-cards.store');
Route::get('/active', [CorporateCardController::class, 'active'])->name('v1.corporate-cards.active');
Route::get('/{id}', [CorporateCardController::class, 'show'])->whereNumber('id')->name('v1.corporate-cards.show');
Route::put('/{id}', [CorporateCardController::class, 'update'])->whereNumber('id')->name('v1.corporate-cards.update');
Route::delete('/{id}', [CorporateCardController::class, 'destroy'])->whereNumber('id')->name('v1.corporate-cards.destroy');
Route::patch('/{id}/toggle', [CorporateCardController::class, 'toggle'])->whereNumber('id')->name('v1.corporate-cards.toggle');
});
// Deposit API (입금 관리)
Route::prefix('deposits')->group(function () {
Route::get('', [DepositController::class, 'index'])->name('v1.deposits.index');
Route::post('', [DepositController::class, 'store'])->name('v1.deposits.store');
Route::get('/summary', [DepositController::class, 'summary'])->name('v1.deposits.summary');
Route::post('/bulk-update-account-code', [DepositController::class, 'bulkUpdateAccountCode'])->name('v1.deposits.bulk-update-account-code');
Route::get('/{id}', [DepositController::class, 'show'])->whereNumber('id')->name('v1.deposits.show');
Route::put('/{id}', [DepositController::class, 'update'])->whereNumber('id')->name('v1.deposits.update');
Route::delete('/{id}', [DepositController::class, 'destroy'])->whereNumber('id')->name('v1.deposits.destroy');
});
// Withdrawal API (출금 관리)
Route::prefix('withdrawals')->group(function () {
Route::get('', [WithdrawalController::class, 'index'])->name('v1.withdrawals.index');
Route::post('', [WithdrawalController::class, 'store'])->name('v1.withdrawals.store');
Route::get('/summary', [WithdrawalController::class, 'summary'])->name('v1.withdrawals.summary');
Route::post('/bulk-update-account-code', [WithdrawalController::class, 'bulkUpdateAccountCode'])->name('v1.withdrawals.bulk-update-account-code');
Route::get('/{id}', [WithdrawalController::class, 'show'])->whereNumber('id')->name('v1.withdrawals.show');
Route::put('/{id}', [WithdrawalController::class, 'update'])->whereNumber('id')->name('v1.withdrawals.update');
Route::delete('/{id}', [WithdrawalController::class, 'destroy'])->whereNumber('id')->name('v1.withdrawals.destroy');
});
// Payroll API (급여 관리)
Route::prefix('payrolls')->group(function () {
Route::get('', [PayrollController::class, 'index'])->name('v1.payrolls.index');
Route::post('', [PayrollController::class, 'store'])->name('v1.payrolls.store');
Route::get('/summary', [PayrollController::class, 'summary'])->name('v1.payrolls.summary');
Route::post('/calculate', [PayrollController::class, 'calculate'])->name('v1.payrolls.calculate');
Route::post('/bulk-confirm', [PayrollController::class, 'bulkConfirm'])->name('v1.payrolls.bulk-confirm');
Route::get('/{id}', [PayrollController::class, 'show'])->whereNumber('id')->name('v1.payrolls.show');
Route::put('/{id}', [PayrollController::class, 'update'])->whereNumber('id')->name('v1.payrolls.update');
Route::delete('/{id}', [PayrollController::class, 'destroy'])->whereNumber('id')->name('v1.payrolls.destroy');
Route::post('/{id}/confirm', [PayrollController::class, 'confirm'])->whereNumber('id')->name('v1.payrolls.confirm');
Route::post('/{id}/pay', [PayrollController::class, 'pay'])->whereNumber('id')->name('v1.payrolls.pay');
Route::get('/{id}/payslip', [PayrollController::class, 'payslip'])->whereNumber('id')->name('v1.payrolls.payslip');
});
// Salary API (급여 관리 - React 연동)
Route::prefix('salaries')->group(function () {
Route::get('', [SalaryController::class, 'index'])->name('v1.salaries.index');
Route::post('', [SalaryController::class, 'store'])->name('v1.salaries.store');
Route::get('/statistics', [SalaryController::class, 'statistics'])->name('v1.salaries.statistics');
Route::get('/export', [SalaryController::class, 'export'])->name('v1.salaries.export');
Route::post('/bulk-update-status', [SalaryController::class, 'bulkUpdateStatus'])->name('v1.salaries.bulk-update-status');
Route::get('/{id}', [SalaryController::class, 'show'])->whereNumber('id')->name('v1.salaries.show');
Route::put('/{id}', [SalaryController::class, 'update'])->whereNumber('id')->name('v1.salaries.update');
Route::delete('/{id}', [SalaryController::class, 'destroy'])->whereNumber('id')->name('v1.salaries.destroy');
Route::patch('/{id}/status', [SalaryController::class, 'updateStatus'])->whereNumber('id')->name('v1.salaries.update-status');
});
// Expected Expense API (미지급비용 관리)
Route::prefix('expected-expenses')->group(function () {
Route::get('', [ExpectedExpenseController::class, 'index'])->name('v1.expected-expenses.index');
Route::post('', [ExpectedExpenseController::class, 'store'])->name('v1.expected-expenses.store');
Route::get('/summary', [ExpectedExpenseController::class, 'summary'])->name('v1.expected-expenses.summary');
Route::get('/dashboard-detail', [ExpectedExpenseController::class, 'dashboardDetail'])->name('v1.expected-expenses.dashboard-detail');
Route::delete('', [ExpectedExpenseController::class, 'destroyMany'])->name('v1.expected-expenses.destroy-many');
Route::put('/update-payment-date', [ExpectedExpenseController::class, 'updateExpectedPaymentDate'])->name('v1.expected-expenses.update-payment-date');
Route::get('/{id}', [ExpectedExpenseController::class, 'show'])->whereNumber('id')->name('v1.expected-expenses.show');
Route::put('/{id}', [ExpectedExpenseController::class, 'update'])->whereNumber('id')->name('v1.expected-expenses.update');
Route::delete('/{id}', [ExpectedExpenseController::class, 'destroy'])->whereNumber('id')->name('v1.expected-expenses.destroy');
});
// Loan API (가지급금 관리)
Route::prefix('loans')->group(function () {
Route::get('', [LoanController::class, 'index'])->name('v1.loans.index');
Route::post('', [LoanController::class, 'store'])->name('v1.loans.store');
Route::get('/summary', [LoanController::class, 'summary'])->name('v1.loans.summary');
Route::get('/dashboard', [LoanController::class, 'dashboard'])->name('v1.loans.dashboard');
Route::get('/tax-simulation', [LoanController::class, 'taxSimulation'])->name('v1.loans.tax-simulation');
Route::post('/calculate-interest', [LoanController::class, 'calculateInterest'])->name('v1.loans.calculate-interest');
Route::get('/interest-report/{year}', [LoanController::class, 'interestReport'])->whereNumber('year')->name('v1.loans.interest-report');
Route::get('/{id}', [LoanController::class, 'show'])->whereNumber('id')->name('v1.loans.show');
Route::put('/{id}', [LoanController::class, 'update'])->whereNumber('id')->name('v1.loans.update');
Route::delete('/{id}', [LoanController::class, 'destroy'])->whereNumber('id')->name('v1.loans.destroy');
Route::post('/{id}/settle', [LoanController::class, 'settle'])->whereNumber('id')->name('v1.loans.settle');
});
// Vendor Ledger API (거래처원장)
Route::prefix('vendor-ledger')->group(function () {
Route::get('', [VendorLedgerController::class, 'index'])->name('v1.vendor-ledger.index');
Route::get('/summary', [VendorLedgerController::class, 'summary'])->name('v1.vendor-ledger.summary');
Route::get('/{clientId}', [VendorLedgerController::class, 'show'])->whereNumber('clientId')->name('v1.vendor-ledger.show');
});
// Card Transaction API (카드 거래)
Route::prefix('card-transactions')->group(function () {
Route::get('', [CardTransactionController::class, 'index'])->name('v1.card-transactions.index');
Route::get('/summary', [CardTransactionController::class, 'summary'])->name('v1.card-transactions.summary');
Route::get('/dashboard', [CardTransactionController::class, 'dashboard'])->name('v1.card-transactions.dashboard');
Route::post('', [CardTransactionController::class, 'store'])->name('v1.card-transactions.store');
Route::put('/bulk-update-account', [CardTransactionController::class, 'bulkUpdateAccountCode'])->name('v1.card-transactions.bulk-update-account');
Route::get('/{id}', [CardTransactionController::class, 'show'])->whereNumber('id')->name('v1.card-transactions.show');
Route::put('/{id}', [CardTransactionController::class, 'update'])->whereNumber('id')->name('v1.card-transactions.update');
Route::delete('/{id}', [CardTransactionController::class, 'destroy'])->whereNumber('id')->name('v1.card-transactions.destroy');
});
// Bank Transaction API (은행 거래 조회)
Route::prefix('bank-transactions')->group(function () {
Route::get('', [BankTransactionController::class, 'index'])->name('v1.bank-transactions.index');
Route::get('/summary', [BankTransactionController::class, 'summary'])->name('v1.bank-transactions.summary');
Route::get('/accounts', [BankTransactionController::class, 'accounts'])->name('v1.bank-transactions.accounts');
});
// Receivables API (채권 현황)
Route::prefix('receivables')->group(function () {
Route::get('', [ReceivablesController::class, 'index'])->name('v1.receivables.index');
Route::get('/summary', [ReceivablesController::class, 'summary'])->name('v1.receivables.summary');
Route::put('/overdue-status', [ReceivablesController::class, 'updateOverdueStatus'])->name('v1.receivables.update-overdue-status');
Route::put('/memos', [ReceivablesController::class, 'updateMemos'])->name('v1.receivables.update-memos');
});
// Daily Report API (일일 보고서)
Route::prefix('daily-report')->group(function () {
Route::get('/note-receivables', [DailyReportController::class, 'noteReceivables'])->name('v1.daily-report.note-receivables');
Route::get('/daily-accounts', [DailyReportController::class, 'dailyAccounts'])->name('v1.daily-report.daily-accounts');
Route::get('/summary', [DailyReportController::class, 'summary'])->name('v1.daily-report.summary');
});
// Comprehensive Analysis API (종합 분석 보고서)
Route::get('/comprehensive-analysis', [ComprehensiveAnalysisController::class, 'index'])->name('v1.comprehensive-analysis.index');
// Status Board API (CEO 대시보드 현황판)
Route::get('/status-board/summary', [StatusBoardController::class, 'summary'])->name('v1.status-board.summary');
// Today Issue API (CEO 대시보드 오늘의 이슈 리스트)
Route::get('/today-issues/summary', [TodayIssueController::class, 'summary'])->name('v1.today-issues.summary');
Route::get('/today-issues/unread', [TodayIssueController::class, 'unread'])->name('v1.today-issues.unread');
Route::get('/today-issues/unread/count', [TodayIssueController::class, 'unreadCount'])->name('v1.today-issues.unread.count');
Route::post('/today-issues/{id}/read', [TodayIssueController::class, 'markAsRead'])->whereNumber('id')->name('v1.today-issues.read');
Route::post('/today-issues/read-all', [TodayIssueController::class, 'markAllAsRead'])->name('v1.today-issues.read-all');
// Calendar API (CEO 대시보드 캘린더)
Route::get('/calendar/schedules', [CalendarController::class, 'summary'])->name('v1.calendar.schedules');
// Vat API (CEO 대시보드 부가세 현황)
Route::get('/vat/summary', [VatController::class, 'summary'])->name('v1.vat.summary');
// Entertainment API (CEO 대시보드 접대비 현황)
Route::get('/entertainment/summary', [EntertainmentController::class, 'summary'])->name('v1.entertainment.summary');
// Welfare API (CEO 대시보드 복리후생비 현황)
Route::get('/welfare/summary', [WelfareController::class, 'summary'])->name('v1.welfare.summary');
Route::get('/welfare/detail', [WelfareController::class, 'detail'])->name('v1.welfare.detail');
// Plan API (요금제 관리)
Route::prefix('plans')->group(function () {
Route::get('', [PlanController::class, 'index'])->name('v1.plans.index');
Route::post('', [PlanController::class, 'store'])->name('v1.plans.store');
Route::get('/active', [PlanController::class, 'active'])->name('v1.plans.active');
Route::get('/{id}', [PlanController::class, 'show'])->whereNumber('id')->name('v1.plans.show');
Route::put('/{id}', [PlanController::class, 'update'])->whereNumber('id')->name('v1.plans.update');
Route::delete('/{id}', [PlanController::class, 'destroy'])->whereNumber('id')->name('v1.plans.destroy');
Route::patch('/{id}/toggle', [PlanController::class, 'toggle'])->whereNumber('id')->name('v1.plans.toggle');
});
// Subscription API (구독 관리)
Route::prefix('subscriptions')->group(function () {
Route::get('', [SubscriptionController::class, 'index'])->name('v1.subscriptions.index');
Route::post('', [SubscriptionController::class, 'store'])->name('v1.subscriptions.store');
Route::get('/current', [SubscriptionController::class, 'current'])->name('v1.subscriptions.current');
Route::get('/usage', [SubscriptionController::class, 'usage'])->name('v1.subscriptions.usage');
Route::post('/export', [SubscriptionController::class, 'export'])->name('v1.subscriptions.export');
Route::get('/export/{id}', [SubscriptionController::class, 'exportStatus'])->whereNumber('id')->name('v1.subscriptions.export.status');
Route::get('/{id}', [SubscriptionController::class, 'show'])->whereNumber('id')->name('v1.subscriptions.show');
Route::post('/{id}/cancel', [SubscriptionController::class, 'cancel'])->whereNumber('id')->name('v1.subscriptions.cancel');
Route::post('/{id}/renew', [SubscriptionController::class, 'renew'])->whereNumber('id')->name('v1.subscriptions.renew');
Route::post('/{id}/suspend', [SubscriptionController::class, 'suspend'])->whereNumber('id')->name('v1.subscriptions.suspend');
Route::post('/{id}/resume', [SubscriptionController::class, 'resume'])->whereNumber('id')->name('v1.subscriptions.resume');
});
// Payment API (결제 관리)
Route::prefix('payments')->group(function () {
Route::get('', [PaymentController::class, 'index'])->name('v1.payments.index');
Route::post('', [PaymentController::class, 'store'])->name('v1.payments.store');
Route::get('/summary', [PaymentController::class, 'summary'])->name('v1.payments.summary');
Route::get('/{id}', [PaymentController::class, 'show'])->whereNumber('id')->name('v1.payments.show');
Route::post('/{id}/complete', [PaymentController::class, 'complete'])->whereNumber('id')->name('v1.payments.complete');
Route::post('/{id}/cancel', [PaymentController::class, 'cancel'])->whereNumber('id')->name('v1.payments.cancel');
Route::post('/{id}/refund', [PaymentController::class, 'refund'])->whereNumber('id')->name('v1.payments.refund');
Route::get('/{id}/statement', [PaymentController::class, 'statement'])->whereNumber('id')->name('v1.payments.statement');
});
// Barobill Setting API (바로빌 설정)
Route::prefix('barobill-settings')->group(function () {
Route::get('', [BarobillSettingController::class, 'show'])->name('v1.barobill-settings.show');
Route::put('', [BarobillSettingController::class, 'save'])->name('v1.barobill-settings.save');
Route::post('/test-connection', [BarobillSettingController::class, 'testConnection'])->name('v1.barobill-settings.test-connection');
});
// Barobill Integration API (바로빌 연동 관리)
Route::prefix('barobill')->group(function () {
Route::post('/login', [BarobillController::class, 'login'])->name('v1.barobill.login');
Route::post('/signup', [BarobillController::class, 'signup'])->name('v1.barobill.signup');
Route::get('/bank-service-url', [BarobillController::class, 'bankServiceUrl'])->name('v1.barobill.bank-service-url');
Route::get('/status', [BarobillController::class, 'status'])->name('v1.barobill.status');
Route::get('/account-link-url', [BarobillController::class, 'accountLinkUrl'])->name('v1.barobill.account-link-url');
Route::get('/card-link-url', [BarobillController::class, 'cardLinkUrl'])->name('v1.barobill.card-link-url');
Route::get('/certificate-url', [BarobillController::class, 'certificateUrl'])->name('v1.barobill.certificate-url');
});
// Tax Invoice API (세금계산서)
Route::prefix('tax-invoices')->group(function () {
Route::get('', [TaxInvoiceController::class, 'index'])->name('v1.tax-invoices.index');
Route::post('', [TaxInvoiceController::class, 'store'])->name('v1.tax-invoices.store');
Route::get('/summary', [TaxInvoiceController::class, 'summary'])->name('v1.tax-invoices.summary');
Route::get('/supplier-settings', [TaxInvoiceController::class, 'supplierSettings'])->name('v1.tax-invoices.supplier-settings');
Route::put('/supplier-settings', [TaxInvoiceController::class, 'saveSupplierSettings'])->name('v1.tax-invoices.save-supplier-settings');
Route::post('/issue-direct', [TaxInvoiceController::class, 'storeAndIssue'])->name('v1.tax-invoices.issue-direct');
Route::post('/bulk-issue', [TaxInvoiceController::class, 'bulkIssue'])->name('v1.tax-invoices.bulk-issue');
Route::get('/{id}', [TaxInvoiceController::class, 'show'])->whereNumber('id')->name('v1.tax-invoices.show');
Route::put('/{id}', [TaxInvoiceController::class, 'update'])->whereNumber('id')->name('v1.tax-invoices.update');
Route::delete('/{id}', [TaxInvoiceController::class, 'destroy'])->whereNumber('id')->name('v1.tax-invoices.destroy');
Route::post('/{id}/issue', [TaxInvoiceController::class, 'issue'])->whereNumber('id')->name('v1.tax-invoices.issue');
Route::post('/{id}/cancel', [TaxInvoiceController::class, 'cancel'])->whereNumber('id')->name('v1.tax-invoices.cancel');
Route::get('/{id}/check-status', [TaxInvoiceController::class, 'checkStatus'])->whereNumber('id')->name('v1.tax-invoices.check-status');
});
// Bad Debt API (악성채권 추심관리)
Route::prefix('bad-debts')->group(function () {
Route::get('', [BadDebtController::class, 'index'])->name('v1.bad-debts.index');
Route::post('', [BadDebtController::class, 'store'])->name('v1.bad-debts.store');
Route::get('/summary', [BadDebtController::class, 'summary'])->name('v1.bad-debts.summary');
Route::get('/{id}', [BadDebtController::class, 'show'])->whereNumber('id')->name('v1.bad-debts.show');
Route::put('/{id}', [BadDebtController::class, 'update'])->whereNumber('id')->name('v1.bad-debts.update');
Route::delete('/{id}', [BadDebtController::class, 'destroy'])->whereNumber('id')->name('v1.bad-debts.destroy');
Route::patch('/{id}/toggle', [BadDebtController::class, 'toggle'])->whereNumber('id')->name('v1.bad-debts.toggle');
// 서류
Route::post('/{id}/documents', [BadDebtController::class, 'addDocument'])->whereNumber('id')->name('v1.bad-debts.documents.store');
Route::delete('/{id}/documents/{documentId}', [BadDebtController::class, 'removeDocument'])->whereNumber(['id', 'documentId'])->name('v1.bad-debts.documents.destroy');
// 메모
Route::post('/{id}/memos', [BadDebtController::class, 'addMemo'])->whereNumber('id')->name('v1.bad-debts.memos.store');
Route::delete('/{id}/memos/{memoId}', [BadDebtController::class, 'removeMemo'])->whereNumber(['id', 'memoId'])->name('v1.bad-debts.memos.destroy');
});
// Bill API (어음관리)
Route::prefix('bills')->group(function () {
Route::get('', [BillController::class, 'index'])->name('v1.bills.index');
Route::post('', [BillController::class, 'store'])->name('v1.bills.store');
Route::get('/summary', [BillController::class, 'summary'])->name('v1.bills.summary');
Route::get('/dashboard-detail', [BillController::class, 'dashboardDetail'])->name('v1.bills.dashboard-detail');
Route::get('/{id}', [BillController::class, 'show'])->whereNumber('id')->name('v1.bills.show');
Route::put('/{id}', [BillController::class, 'update'])->whereNumber('id')->name('v1.bills.update');
Route::delete('/{id}', [BillController::class, 'destroy'])->whereNumber('id')->name('v1.bills.destroy');
Route::patch('/{id}/status', [BillController::class, 'updateStatus'])->whereNumber('id')->name('v1.bills.update-status');
});