feat(service): crud dan route model binding

This commit is contained in:
Yoga Pangestu 2024-11-24 17:28:37 +07:00
parent fc3f77af2f
commit 255a70a923
7 changed files with 312 additions and 0 deletions

View File

@ -0,0 +1,69 @@
<?php
namespace App\Http\Controllers\Admin\Master;
use App\Http\Controllers\Controller;
use App\Http\Requests\Admin\Master\ServiceRequest;
use App\Models\Service;
use Illuminate\Contracts\View\View;
use Illuminate\Http\RedirectResponse;
use Illuminate\Support\Facades\Auth;
class ServiceController extends Controller
{
public function index(): View
{
return view('pages.admin.master.service.index', [
'pageTitle' => 'Layanan',
'services' => Service::latest()->get(),
]);
}
public function create(): View
{
return view('pages.admin.master.service.create', [
'pageTitle' => 'Tambah Layanan',
]);
}
public function store(ServiceRequest $request): RedirectResponse
{
$validatedData = $request->validated();
Service::create(array_merge($validatedData, [
'user_id' => Auth::id(),
'barbershop_id' => Auth::user()->barbershop_id,
]));
notify()->success('Data berhasil ditambahkan', 'Berhasil');
return redirect('dashboard/master/services');
}
public function edit(Service $service): View
{
return view('pages.admin.master.service.edit', [
'pageTitle' => 'Edit Layanan',
'service' => $service,
]);
}
public function update(Service $service, ServiceRequest $request): RedirectResponse
{
$validatedData = $request->validated();
$service->update($validatedData);
notify()->success('Data berhasil diubah', 'Berhasil');
return redirect('dashboard/master/services');
}
public function delete(Service $service): RedirectResponse
{
$service->delete();
notify()->success('Data berhasil dihapus', 'Berhasil');
return back();
}
}

View File

@ -0,0 +1,39 @@
<?php
namespace App\Http\Requests\Admin\Master;
use App\Traits\NotificationTrait;
use Illuminate\Contracts\Validation\Validator;
use Illuminate\Foundation\Http\FormRequest;
use Illuminate\Support\Facades\Auth;
class ServiceRequest extends FormRequest
{
use NotificationTrait;
public function authorize(): bool
{
return Auth::check();
}
protected function prepareForValidation(): void
{
$this->merge([
'price' => removeRupiahFormatting($this->price),
]);
}
public function rules(): array
{
return [
'name' => ['required', 'string', 'max:100'],
'price' => ['required', 'numeric', 'min:0'],
'description' => ['required', 'string', 'max:65535'],
];
}
protected function failedValidation(Validator $validator): void
{
$this->handleValidationFailure($validator);
}
}

View File

@ -4,6 +4,7 @@
use App\Models\Barbershop;
use App\Models\Customer;
use App\Models\Service;
use App\Models\User;
use Illuminate\Support\Facades\Route;
use Illuminate\Support\ServiceProvider;
@ -26,5 +27,6 @@ public function boot(): void
Route::bind('barbershop', fn (string $barbershop) => Barbershop::findOrFail(decryptId($barbershop)));
Route::bind('user', fn (string $user) => User::findOrFail(decryptId($user)));
Route::bind('customer', fn (string $customer) => Customer::findOrFail(decryptId($customer)));
Route::bind('service', fn (string $service) => Service::findOrFail(decryptId($service)));
}
}

View File

@ -0,0 +1,57 @@
@extends('layouts.admin')
@section('styles')
@endsection
@section('app')
<div class="container-fluid">
<div class="list-product-header">
<div>
<a class="btn btn-dark" href="{{ route('master.services') }}">Kembali</a>
</div>
</div>
<div class="card">
<div class="card-body">
<form class="row g-3 custom-input" action="{{ route('master.service.store') }}" method="post">
@csrf
<div class="col-lg-6 position-relative">
<label class="form-label" for="name">Nama</label>
<input name="name" class="form-control @error('name') is-invalid @enderror" id="name"
type="text" placeholder="Masukan Nama" value="{{ old('name') }}">
@error('name')
<div class="invalid-feedback">
{{ $message }}
</div>
@enderror
</div>
<div class="col-lg-6 position-relative">
<label class="form-label" for="price">Harga</label>
<input name="price" class="form-control rupiah-format @error('price') is-invalid @enderror"
id="price" type="text" placeholder="Masukan Harga" value="{{ old('price') }}"
inputmode="numeric">
@error('price')
<div class="invalid-feedback">
{{ $message }}
</div>
@enderror
</div>
<div class="col-lg-12 position-relative">
<label class="form-label" for="description">Deskripsi</label>
<textarea name="description" class="form-control @error('description') is-invalid @enderror" id="description"
rows="3" placeholder="Masukan Deskripsi">{{ old('description') }}</textarea>
@error('description')
<div class="invalid-feedback">
{{ $message }}
</div>
@enderror
</div>
<div class="col-12">
<button class="btn btn-primary button-disable" type="submit">Simpan</button>
</div>
</form>
</div>
</div>
</div>
@endsection
@section('afterScripts')
<script src="{{ asset('assets/js/forms/button-disable.js?ver=1.0.0') }}"></script>
<script src="{{ asset('assets/js/forms/rupiah-format.js?ver=1.0.0') }}"></script>
@endsection

View File

@ -0,0 +1,59 @@
@extends('layouts.admin')
@section('styles')
@endsection
@section('app')
<div class="container-fluid">
<div class="list-product-header">
<div>
<a class="btn btn-dark" href="{{ route('master.services') }}">Kembali</a>
</div>
</div>
<div class="card">
<div class="card-body">
<form class="row g-3 custom-input" action="{{ route('master.service.update', encryptId($service->id)) }}"
method="post">
@csrf
@method('put')
<div class="col-lg-6 position-relative">
<label class="form-label" for="name">Nama</label>
<input name="name" class="form-control @error('name') is-invalid @enderror" id="name"
type="text" placeholder="Masukan Nama" value="{{ old('name', $service->name) }}">
@error('name')
<div class="invalid-feedback">
{{ $message }}
</div>
@enderror
</div>
<div class="col-lg-6 position-relative">
<label class="form-label" for="price">Harga</label>
<input name="price" class="form-control rupiah-format @error('price') is-invalid @enderror"
id="price" type="text" placeholder="Masukan Harga"
value="{{ old('price', formatToRupiah($service->price)) }}" inputmode="numeric">
@error('price')
<div class="invalid-feedback">
{{ $message }}
</div>
@enderror
</div>
<div class="col-lg-12 position-relative">
<label class="form-label" for="description">Deskripsi</label>
<textarea name="description" class="form-control @error('description') is-invalid @enderror" id="description"
rows="3" placeholder="Masukan Deskripsi">{{ old('description', $service->description) }}</textarea>
@error('description')
<div class="invalid-feedback">
{{ $message }}
</div>
@enderror
</div>
<div class="col-12">
<button class="btn btn-primary button-disable" type="submit">Simpan</button>
</div>
</form>
</div>
</div>
</div>
@endsection
@section('afterScripts')
<script src="{{ asset('assets/js/forms/button-disable.js?ver=1.0.0') }}"></script>
<script src="{{ asset('assets/js/forms/rupiah-format.js?ver=1.0.0') }}"></script>
@endsection

View File

@ -0,0 +1,76 @@
@extends('layouts.admin')
@section('styles')
<link rel="stylesheet" type="text/css" href="{{ asset('assets/admin/css/vendors/datatables.css') }}">
@endsection
@section('app')
<div class="container-fluid">
<div class="row">
<div class="col-sm-12">
<div class="list-product-header">
<div>
<a class="btn btn-primary" href="{{ route('master.service.create') }}">Tambah</a>
</div>
</div>
<div class="card">
<div class="card-body">
<div class="table-responsive">
<table class="display" id="datatable">
<thead>
<tr>
<th>No</th>
<th>Nama</th>
<th>Harga</th>
<th>Deskripsi</th>
<th>Tanggal</th>
<th>Aksi</th>
</tr>
</thead>
<tbody>
@foreach ($services as $service)
<tr>
<td>{{ $loop->iteration }}</td>
<td>{{ $service->name }}</td>
<td>{{ formatToRupiah($service->price) }}</td>
<td>{{ $service->description }}</td>
<td>{{ formatDateIndo($service->created_at) }}</td>
<td>
<ul class="action">
<li class="edit">
<a href="{{ route('master.service.edit', encryptId($service->id)) }}"
data-bs-toggle="tooltip" data-bs-placement="left"
data-bs-title="Edit">
<i data-feather="edit"></i>
</a>
</li>
<li class="delete">
<form
action="{{ route('master.service.delete', encryptId($service->id)) }}"
method="post">
@csrf
@method('delete')
<a href="javascript:void(0)" class="delete-data"
data-bs-toggle="tooltip" data-bs-placement="left"
data-bs-title="Hapus">
<i data-feather="trash-2"></i>
</a>
</form>
</li>
</ul>
</td>
</tr>
@endforeach
</tbody>
</table>
</div>
</div>
</div>
</div>
</div>
</div>
@endsection
@section('afterScripts')
<script src="{{ asset('assets/admin/js/datatable/jquery.dataTables.min.js?ver=1.0.0') }}"></script>
<script src="{{ asset('assets/admin/js/datatable/client-side.js?ver=1.0.0') }}"></script>
<script src="{{ asset('assets/js/interactions/confirmation.js?ver=1.0.0') }}"></script>
<script src="https://cdn.jsdelivr.net/npm/sweetalert2@11"></script>
@endsection

View File

@ -4,6 +4,7 @@
use App\Http\Controllers\Admin\Dashboard\OverviewController;
use App\Http\Controllers\Admin\Master\BarbershopController;
use App\Http\Controllers\Admin\Master\CustomerController;
use App\Http\Controllers\Admin\Master\ServiceController;
use App\Http\Controllers\Admin\Master\UserController;
use Illuminate\Support\Facades\Route;
@ -48,5 +49,14 @@
Route::put('update/{customer}', [CustomerController::class, 'update'])->name('master.customer.update');
Route::delete('delete/{customer}', [CustomerController::class, 'delete'])->name('master.customer.delete');
});
Route::get('/services', [ServiceController::class, 'index'])->name('master.services');
Route::prefix('service')->group(function () {
Route::get('create', [ServiceController::class, 'create'])->name('master.service.create');
Route::post('store', [ServiceController::class, 'store'])->name('master.service.store');
Route::get('edit/{service}', [ServiceController::class, 'edit'])->name('master.service.edit');
Route::put('update/{service}', [ServiceController::class, 'update'])->name('master.service.update');
Route::delete('delete/{service}', [ServiceController::class, 'delete'])->name('master.service.delete');
});
});
});