solve dashboard indikator pertanian

This commit is contained in:
2026-08-13 13:07:03 +07:00
parent ba7520a23c
commit b855a857b2
3 changed files with 114 additions and 47 deletions
@@ -22,10 +22,13 @@ class ProfilPetaniController extends Controller
}
$title = 'Dashboard Profil Petani';
$komoditas = Komoditas::where('is_utama', true)->get();
$komoditas = Komoditas::select('id', 'nama')->where('is_utama', true)->get();
$komoditasIds = $komoditas->pluck('id');
$petani = Petani::pluck('id');
$lahan = Lahan::whereIn('petani_id', $petani)->get();
$petaniIds = fn () => Petani::query()->select('id');
$lahanIds = fn () => Lahan::query()
->whereIn('petani_id', $petaniIds())
->select('id');
$petaniSummary = Petani::select(
'komoditas_id',
@@ -38,14 +41,14 @@ class ProfilPetaniController extends Controller
DB::raw('COUNT(*) as total'),
DB::raw('SUM(luas_lahan) as luas_lahan')
)
->whereIn('petani_id', $petani)
->whereIn('petani_id', $petaniIds())
->groupBy('komoditas_id')
->get();
$tanamanSummary = Tanaman::select(
'komoditas_id',
DB::raw('COUNT(*) as total')
)
->whereIn('lahan_id', $lahan->pluck('id'))
->whereIn('lahan_id', $lahanIds())
->groupBy('komoditas_id')
->get();
@@ -59,7 +62,7 @@ class ProfilPetaniController extends Controller
END
";
$skorSummary = SkorPetani::selectRaw("$case AS segmen, COUNT(*) AS total")
->whereIn('petani_id', $petani)
->whereIn('petani_id', $petaniIds())
->groupByRaw($case)
->get();
@@ -70,15 +73,15 @@ class ProfilPetaniController extends Controller
$case AS segmen,
COUNT(petani.id) AS total
")
->whereIn('petani_skor.petani_id', $petani)
->whereIn('petani_skor.petani_id', $petaniIds())
->groupBy('petani.komoditas_id')
->groupByRaw($case)
->get();
$skorAverage = SkorPetani::query()
->join('petani', 'petani_skor.petani_id', '=', 'petani.id')
->whereIn('petani_id', $petani)
->whereIn('petani.komoditas_id', $komoditas->pluck('id'))
->whereIn('petani_id', $petaniIds())
->whereIn('petani.komoditas_id', $komoditasIds)
->avg('skor_kesiapan_adopsi');
if ($skorAverage >= 4.0) {
$segmenAverage = 'Penggerak';
@@ -94,8 +97,8 @@ class ProfilPetaniController extends Controller
$skorDimensi = SkorPetani::query()
->join('petani', 'petani_skor.petani_id', '=', 'petani.id')
->whereIn('petani_id', $petani)
->whereIn('petani.komoditas_id', $komoditas->pluck('id'))
->whereIn('petani_id', $petaniIds())
->whereIn('petani.komoditas_id', $komoditasIds)
->selectRaw("
avg(skor_d2_sistem_praktik_budidaya) as skor_d2_sistem_praktik_budidaya,
avg(skor_d4_sosial_ekonomi) as skor_d4_sosial_ekonomi,
@@ -104,8 +107,8 @@ class ProfilPetaniController extends Controller
$skorKomponen = SkorPetani::query()
->join('petani', 'petani_skor.petani_id', '=', 'petani.id')
->whereIn('petani_id', $petani)
->whereIn('petani.komoditas_id', $komoditas->pluck('id'))
->whereIn('petani_id', $petaniIds())
->whereIn('petani.komoditas_id', $komoditasIds)
->selectRaw("avg(skor_komp_1_d4_k3_motivasi_kapasitas_adopsi) as skor_komp_1_d4_k3_motivasi_kapasitas_adopsi,
avg(skor_komp_2_d4_k2_ekonomi_rumah_tangga) as skor_komp_2_d4_k2_ekonomi_rumah_tangga,
avg(skor_komp_3_d2_praktik_budidaya_gap) as skor_komp_3_d2_praktik_budidaya_gap,
@@ -116,8 +119,8 @@ class ProfilPetaniController extends Controller
$skorMultiDimensi = SkorPetani::query()
->join('petani', 'petani_skor.petani_id', '=', 'petani.id')
->whereIn('petani_id', $petani)
->whereIn('petani.komoditas_id', $komoditas->pluck('id'))
->whereIn('petani_id', $petaniIds())
->whereIn('petani.komoditas_id', $komoditasIds)
->selectRaw("$case AS segmen,
avg(skor_kesiapan_adopsi) as skor_kesiapan_adopsi,
avg(skor_d2_sistem_praktik_budidaya) as skor_d2_sistem_praktik_budidaya,
@@ -128,8 +131,8 @@ class ProfilPetaniController extends Controller
$skorMultiKomponen = SkorPetani::query()
->join('petani', 'petani_skor.petani_id', '=', 'petani.id')
->whereIn('petani_id', $petani)
->whereIn('petani.komoditas_id', $komoditas->pluck('id'))
->whereIn('petani_id', $petaniIds())
->whereIn('petani.komoditas_id', $komoditasIds)
->selectRaw("$case AS segmen,
avg(skor_kesiapan_adopsi) as skor_kesiapan_adopsi,
avg(skor_komp_1_d4_k3_motivasi_kapasitas_adopsi) as skor_komp_1_d4_k3_motivasi_kapasitas_adopsi,
@@ -141,9 +144,14 @@ class ProfilPetaniController extends Controller
->groupByRaw($case)
->get();
$petani = Petani::with(['skor'])
->whereIn('id', $petani)
->whereIn('komoditas_id', $komoditas->pluck('id'))
$petani = Petani::query()
->select('id', 'nama', 'jenis_kelamin', 'tanggal_lahir', 'komoditas_id')
->with([
'komoditas:id,nama',
'skor:id,petani_id,skor_kesiapan_adopsi,skor_d2_sistem_praktik_budidaya,skor_d4_sosial_ekonomi,skor_d6_rantai_nilai_akses_pasar,skor_komp_1_d4_k3_motivasi_kapasitas_adopsi,skor_komp_2_d4_k2_ekonomi_rumah_tangga,skor_komp_3_d2_praktik_budidaya_gap,skor_komp_4_d4_k4_keterlibatan_kelembagaan,skor_komp_5_d4_k5_k6_akses_kebebasan_keuangan,skor_komp_6_d6_k1_k4_k5_rantai_nilai_akses_pasar',
])
->whereIn('komoditas_id', $komoditasIds)
->orderBy('nama')
->get();
return view('dashboard.petani', compact('title',
@@ -55,19 +55,7 @@ class FormBasisDataController extends Controller
], 404);
}
$validated = $request->validate([
'parent_id' => ['nullable', 'exists:ekosistem_basis_data_form,id'],
'tipe' => ['required', Rule::enum(LayoutForm::class)],
'column_width' => [
Rule::requiredIf($request->tipe === LayoutForm::COLUMN->value),
'nullable', 'integer', 'min:1', 'max:12'],
'kolom_id' => [
Rule::requiredIf($request->tipe === LayoutForm::VALUE->value),
'nullable', 'exists:ekosistem_basis_data_kolom,id'],
'section_label' => [
Rule::requiredIf($request->tipe === LayoutForm::SECTION->value),
'nullable', 'string'],
]);
$validated = $this->validateFormPayload($request, $tabelId);
FormBasisData::create([...$validated,
'tabel_id' => $tabelId,
@@ -115,19 +103,7 @@ class FormBasisDataController extends Controller
], 404);
}
$validated = $request->validate([
'parent_id' => ['nullable', 'exists:ekosistem_basis_data_form,id'],
'tipe' => ['required', Rule::enum(LayoutForm::class)],
'column_width' => [
Rule::requiredIf($request->tipe === LayoutForm::COLUMN->value),
'nullable', 'integer', 'min:1', 'max:12'],
'kolom_id' => [
Rule::requiredIf($request->tipe === LayoutForm::VALUE->value),
'nullable', 'exists:ekosistem_basis_data_kolom,id'],
'section_label' => [
Rule::requiredIf($request->tipe === LayoutForm::SECTION->value),
'nullable', 'string'],
]);
$validated = $this->validateFormPayload($request, $tabelId, $form);
$form->update([...$validated,
'updated_by' => auth()->user()->id
@@ -293,4 +269,88 @@ class FormBasisDataController extends Controller
'message' => 'Formulir basis data berhasil diperbarui.'
], 200);
}
private function validateFormPayload(Request $request, string $tabelId, ?FormBasisData $form = null): array
{
$tipe = $request->input('tipe');
$needsParent = in_array($tipe, [LayoutForm::COLUMN->value, LayoutForm::VALUE->value], true);
$mustBeRoot = in_array($tipe, [LayoutForm::ROW->value, LayoutForm::SECTION->value, LayoutForm::HR_LINE->value], true);
$validator = Validator::make($request->all(), [
'parent_id' => [
Rule::requiredIf($needsParent),
Rule::prohibitedIf($mustBeRoot),
'nullable',
Rule::exists('ekosistem_basis_data_form', 'id')
->where(fn ($query) => $query
->where('tabel_id', $tabelId)
->whereNull('deleted_at')),
],
'tipe' => ['required', Rule::enum(LayoutForm::class)],
'column_width' => [
Rule::requiredIf($tipe === LayoutForm::COLUMN->value),
'nullable', 'integer', 'min:1', 'max:12'
],
'kolom_id' => [
Rule::requiredIf($tipe === LayoutForm::VALUE->value),
'nullable',
Rule::exists('ekosistem_basis_data_kolom', 'id')
->where(fn ($query) => $query
->where('tabel_id', $tabelId)
->whereNull('deleted_at')),
],
'section_label' => [
Rule::requiredIf($tipe === LayoutForm::SECTION->value),
'nullable', 'string'
],
]);
$validator->after(function ($validator) use ($request, $tabelId, $form) {
if ($validator->errors()->isNotEmpty() || !$request->filled('parent_id')) {
return;
}
if ($form && (int) $request->input('parent_id') === (int) $form->id) {
$validator->errors()->add('parent_id', 'Induk formulir tidak boleh menunjuk ke dirinya sendiri.');
return;
}
$layout = LayoutForm::from($request->input('tipe'));
$expectedParent = match ($layout) {
LayoutForm::COLUMN => LayoutForm::ROW,
LayoutForm::VALUE => LayoutForm::COLUMN,
default => null,
};
if (!$expectedParent) {
return;
}
$parent = FormBasisData::where('tabel_id', $tabelId)->find($request->input('parent_id'));
if (!$parent || $parent->tipe !== $expectedParent) {
$validator->errors()->add('parent_id', 'Induk formulir tidak sesuai dengan tipe formulir.');
}
});
$validated = $validator->validate();
$layout = LayoutForm::from($validated['tipe']);
if (in_array($layout, [LayoutForm::ROW, LayoutForm::SECTION, LayoutForm::HR_LINE], true)) {
$validated['parent_id'] = null;
}
if ($layout !== LayoutForm::COLUMN) {
$validated['column_width'] = null;
}
if ($layout !== LayoutForm::VALUE) {
$validated['kolom_id'] = null;
}
if ($layout !== LayoutForm::SECTION) {
$validated['section_label'] = null;
}
return $validated;
}
}