TIFNJK_E41222887/database/seeders/PayrollSeeder.php

325 lines
16 KiB
PHP

<?php
namespace Database\Seeders;
use App\Models\Employee;
use App\Models\Payroll;
use Illuminate\Database\Seeder;
/**
* PayrollSeeder
*
* Membuat data payroll dummy yang realistis dan terhubung ke employee.
* Seeder ini HARUS dijalankan setelah EmployeeSeeder.
*
* Variasi kasus yang di-cover:
* - Status 'paid' (bulan lalu) dan 'pending' (bulan ini)
* - Karyawan dengan bonus lembur, tunjangan jabatan, tunjangan transport
* - Karyawan dengan potongan (BPJS, absen, pinjaman, keterlambatan)
* - Karyawan magang (gaji pokok rendah, komponen minimal)
* - Karyawan senior dengan tunjangan lengkap
*/
class PayrollSeeder extends Seeder
{
public function run(): void
{
// Helper: hitung net_salary otomatis (sama dengan logika Controller)
$net = function (int $basic, array $details): int {
$total = $basic;
foreach ($details as $item) {
$total += $item['type'] === 'bonus' ? $item['amount'] : -$item['amount'];
}
return max(0, $total);
};
// Resolve semua employee sekaligus (1 query, bukan N query)
$emp = Employee::pluck('id', 'name');
// Periode referensi
$bulanLalu = now()->subMonth()->format('Y-m');
$bulanIni = now()->format('Y-m');
// ──────────────────────────────────────────────────────────────
// DATASET PAYROLL
// ──────────────────────────────────────────────────────────────
$records = [];
// ── 1. JONO JONI — Senior Developer (IT) ─────────────────────
// Kasus: Karyawan senior, ada bonus proyek + tunjangan lengkap.
// Bulan lalu: sudah dibayar. Bulan ini: masih pending.
if (isset($emp['Jono Joni'])) {
$basicJono = 9_000_000;
$detailLalu = [
['name' => 'Tunjangan Transport', 'type' => 'bonus', 'amount' => 600_000],
['name' => 'Tunjangan Makan', 'type' => 'bonus', 'amount' => 450_000],
['name' => 'Potongan BPJS Kesehatan','type' => 'deduction', 'amount' => 180_000],
['name' => 'Potongan BPJS TK', 'type' => 'deduction', 'amount' => 90_000],
];
$records[] = [
'employee_id' => $emp['Jono Joni'],
'period' => $bulanLalu,
'basic_salary' => $basicJono,
'details' => $detailLalu,
'net_salary' => $net($basicJono, $detailLalu),
'status' => 'paid',
];
$detailIni = [
['name' => 'Tunjangan Transport', 'type' => 'bonus', 'amount' => 600_000],
['name' => 'Tunjangan Makan', 'type' => 'bonus', 'amount' => 450_000],
['name' => 'Bonus Proyek Klien', 'type' => 'bonus', 'amount' => 1_500_000],
['name' => 'Potongan BPJS Kesehatan','type' => 'deduction', 'amount' => 180_000],
['name' => 'Potongan BPJS TK', 'type' => 'deduction', 'amount' => 90_000],
];
$records[] = [
'employee_id' => $emp['Jono Joni'],
'period' => $bulanIni,
'basic_salary' => $basicJono,
'details' => $detailIni,
'net_salary' => $net($basicJono, $detailIni),
'status' => 'pending',
];
}
// ── 2. BUDI SANTOSO — Junior Developer (IT) ──────────────────
// Kasus: Karyawan kontrak, ada potongan keterlambatan.
if (isset($emp['Budi Santoso'])) {
$basicBudi = 5_500_000;
$detailLalu = [
['name' => 'Tunjangan Transport', 'type' => 'bonus', 'amount' => 400_000],
['name' => 'Tunjangan Makan', 'type' => 'bonus', 'amount' => 350_000],
['name' => 'Potongan BPJS TK', 'type' => 'deduction', 'amount' => 55_000],
['name' => 'Potongan Keterlambatan', 'type' => 'deduction', 'amount' => 100_000],
];
$records[] = [
'employee_id' => $emp['Budi Santoso'],
'period' => $bulanLalu,
'basic_salary' => $basicBudi,
'details' => $detailLalu,
'net_salary' => $net($basicBudi, $detailLalu),
'status' => 'paid',
];
$detailIni = [
['name' => 'Tunjangan Transport', 'type' => 'bonus', 'amount' => 400_000],
['name' => 'Tunjangan Makan', 'type' => 'bonus', 'amount' => 350_000],
['name' => 'Potongan BPJS TK', 'type' => 'deduction', 'amount' => 55_000],
];
$records[] = [
'employee_id' => $emp['Budi Santoso'],
'period' => $bulanIni,
'basic_salary' => $basicBudi,
'details' => $detailIni,
'net_salary' => $net($basicBudi, $detailIni),
'status' => 'pending',
];
}
// ── 3. RIZKY FIRMANSYAH — Junior Developer Magang (IT) ───────
// Kasus: Karyawan magang, komponen sangat minimal, tidak ada BPJS penuh.
if (isset($emp['Rizky Firmansyah'])) {
$basicRizky = 5_500_000; // gaji pokok jabatan "Junior Developer"
$detailIni = [
['name' => 'Uang Transport Magang', 'type' => 'bonus', 'amount' => 200_000],
['name' => 'Potongan Tidak Hadir', 'type' => 'deduction', 'amount' => 250_000],
];
$records[] = [
'employee_id' => $emp['Rizky Firmansyah'],
'period' => $bulanIni,
'basic_salary' => $basicRizky,
'details' => $detailIni,
'net_salary' => $net($basicRizky, $detailIni),
'status' => 'pending',
];
}
// ── 4. DEWI RAHAYU — Manager HR ──────────────────────────────
// Kasus: Manajer dengan tunjangan jabatan besar + BPJS penuh.
if (isset($emp['Dewi Rahayu'])) {
$basicDewi = 12_000_000;
$detailLalu = [
['name' => 'Tunjangan Jabatan', 'type' => 'bonus', 'amount' => 2_000_000],
['name' => 'Tunjangan Transport', 'type' => 'bonus', 'amount' => 700_000],
['name' => 'Tunjangan Makan', 'type' => 'bonus', 'amount' => 500_000],
['name' => 'Potongan BPJS Kesehatan', 'type' => 'deduction', 'amount' => 240_000],
['name' => 'Potongan BPJS TK', 'type' => 'deduction', 'amount' => 120_000],
['name' => 'Potongan PPh 21', 'type' => 'deduction', 'amount' => 500_000],
];
$records[] = [
'employee_id' => $emp['Dewi Rahayu'],
'period' => $bulanLalu,
'basic_salary' => $basicDewi,
'details' => $detailLalu,
'net_salary' => $net($basicDewi, $detailLalu),
'status' => 'paid',
];
$detailIni = [
['name' => 'Tunjangan Jabatan', 'type' => 'bonus', 'amount' => 2_000_000],
['name' => 'Tunjangan Transport', 'type' => 'bonus', 'amount' => 700_000],
['name' => 'Tunjangan Makan', 'type' => 'bonus', 'amount' => 500_000],
['name' => 'Bonus Kinerja Triwulan', 'type' => 'bonus', 'amount' => 1_000_000],
['name' => 'Potongan BPJS Kesehatan', 'type' => 'deduction', 'amount' => 240_000],
['name' => 'Potongan BPJS TK', 'type' => 'deduction', 'amount' => 120_000],
['name' => 'Potongan PPh 21', 'type' => 'deduction', 'amount' => 600_000],
];
$records[] = [
'employee_id' => $emp['Dewi Rahayu'],
'period' => $bulanIni,
'basic_salary' => $basicDewi,
'details' => $detailIni,
'net_salary' => $net($basicDewi, $detailIni),
'status' => 'pending',
];
}
// ── 5. ANISA PUTRI — HR Specialist ───────────────────────────
// Kasus: Karyawan tetap biasa, komponen standard.
if (isset($emp['Anisa Putri'])) {
$basicAnisa = 5_800_000;
$detailLalu = [
['name' => 'Tunjangan Transport', 'type' => 'bonus', 'amount' => 400_000],
['name' => 'Tunjangan Makan', 'type' => 'bonus', 'amount' => 350_000],
['name' => 'Potongan BPJS Kesehatan', 'type' => 'deduction', 'amount' => 116_000],
['name' => 'Potongan BPJS TK', 'type' => 'deduction', 'amount' => 58_000],
];
$records[] = [
'employee_id' => $emp['Anisa Putri'],
'period' => $bulanLalu,
'basic_salary' => $basicAnisa,
'details' => $detailLalu,
'net_salary' => $net($basicAnisa, $detailLalu),
'status' => 'paid',
];
}
// ── 6. HENDRA KURNIAWAN — Finance Analyst ────────────────────
// Kasus: Karyawan lama, ada potongan cicilan pinjaman perusahaan.
if (isset($emp['Hendra Kurniawan'])) {
$basicHendra = 7_000_000;
$detailLalu = [
['name' => 'Tunjangan Transport', 'type' => 'bonus', 'amount' => 500_000],
['name' => 'Tunjangan Makan', 'type' => 'bonus', 'amount' => 450_000],
['name' => 'Potongan BPJS Kesehatan', 'type' => 'deduction', 'amount' => 140_000],
['name' => 'Potongan BPJS TK', 'type' => 'deduction', 'amount' => 70_000],
['name' => 'Cicilan Pinjaman', 'type' => 'deduction', 'amount' => 500_000],
];
$records[] = [
'employee_id' => $emp['Hendra Kurniawan'],
'period' => $bulanLalu,
'basic_salary' => $basicHendra,
'details' => $detailLalu,
'net_salary' => $net($basicHendra, $detailLalu),
'status' => 'paid',
];
$detailIni = [
['name' => 'Tunjangan Transport', 'type' => 'bonus', 'amount' => 500_000],
['name' => 'Tunjangan Makan', 'type' => 'bonus', 'amount' => 450_000],
['name' => 'Potongan BPJS Kesehatan', 'type' => 'deduction', 'amount' => 140_000],
['name' => 'Potongan BPJS TK', 'type' => 'deduction', 'amount' => 70_000],
['name' => 'Cicilan Pinjaman', 'type' => 'deduction', 'amount' => 500_000],
];
$records[] = [
'employee_id' => $emp['Hendra Kurniawan'],
'period' => $bulanIni,
'basic_salary' => $basicHendra,
'details' => $detailIni,
'net_salary' => $net($basicHendra, $detailIni),
'status' => 'pending',
];
}
// ── 7. SARI WULANDARI — Staff Admin Finance (PKWT) ───────────
// Kasus: Kontrak, ada potongan absen, tidak ada bonus.
if (isset($emp['Sari Wulandari'])) {
$basicSari = 4_000_000;
$detailIni = [
['name' => 'Tunjangan Transport', 'type' => 'bonus', 'amount' => 300_000],
['name' => 'Potongan Absen', 'type' => 'deduction', 'amount' => 200_000],
['name' => 'Potongan BPJS TK', 'type' => 'deduction', 'amount' => 40_000],
];
$records[] = [
'employee_id' => $emp['Sari Wulandari'],
'period' => $bulanIni,
'basic_salary' => $basicSari,
'details' => $detailIni,
'net_salary' => $net($basicSari, $detailIni),
'status' => 'pending',
];
}
// ── 8. FAJAR NUGROHO — Marketing Staff ───────────────────────
// Kasus: Marketing, ada bonus komisi penjualan bulan lalu.
if (isset($emp['Fajar Nugroho'])) {
$basicFajar = 4_500_000;
$detailLalu = [
['name' => 'Tunjangan Transport', 'type' => 'bonus', 'amount' => 350_000],
['name' => 'Komisi Penjualan', 'type' => 'bonus', 'amount' => 2_000_000],
['name' => 'Potongan BPJS TK', 'type' => 'deduction', 'amount' => 45_000],
];
$records[] = [
'employee_id' => $emp['Fajar Nugroho'],
'period' => $bulanLalu,
'basic_salary' => $basicFajar,
'details' => $detailLalu,
'net_salary' => $net($basicFajar, $detailLalu),
'status' => 'paid',
];
$detailIni = [
['name' => 'Tunjangan Transport', 'type' => 'bonus', 'amount' => 350_000],
['name' => 'Potongan BPJS TK', 'type' => 'deduction', 'amount' => 45_000],
];
$records[] = [
'employee_id' => $emp['Fajar Nugroho'],
'period' => $bulanIni,
'basic_salary' => $basicFajar,
'details' => $detailIni,
'net_salary' => $net($basicFajar, $detailIni),
'status' => 'pending',
];
}
// ── 9. AGUS PRASETYO — Manager Operations ────────────────────
// Kasus: Manager senior dengan PPh 21 dan semua tunjangan.
if (isset($emp['Agus Prasetyo'])) {
$basicAgus = 12_000_000;
$detailLalu = [
['name' => 'Tunjangan Jabatan', 'type' => 'bonus', 'amount' => 2_500_000],
['name' => 'Tunjangan Transport', 'type' => 'bonus', 'amount' => 700_000],
['name' => 'Tunjangan Makan', 'type' => 'bonus', 'amount' => 500_000],
['name' => 'Potongan BPJS Kesehatan', 'type' => 'deduction', 'amount' => 240_000],
['name' => 'Potongan BPJS TK', 'type' => 'deduction', 'amount' => 120_000],
['name' => 'Potongan PPh 21', 'type' => 'deduction', 'amount' => 650_000],
];
$records[] = [
'employee_id' => $emp['Agus Prasetyo'],
'period' => $bulanLalu,
'basic_salary' => $basicAgus,
'details' => $detailLalu,
'net_salary' => $net($basicAgus, $detailLalu),
'status' => 'paid',
];
}
// ──────────────────────────────────────────────────────────────
// Insert semua record
// ──────────────────────────────────────────────────────────────
foreach ($records as $data) {
Payroll::create($data);
}
$this->command->info('PayrollSeeder: ' . count($records) . ' slip gaji berhasil dibuat.');
}
}