fix
This commit is contained in:
parent
97d79b4a84
commit
54c237d211
@ -11,8 +11,8 @@ class ReviewController extends Controller
|
||||
// Ambil semua ulasan
|
||||
public function index()
|
||||
{
|
||||
$reviews = Review::all();
|
||||
return response()->json($reviews, 200);
|
||||
$reviews = Review::latest()->paginate(10);
|
||||
return view('admin.reviews.index', compact('reviews'));
|
||||
}
|
||||
|
||||
|
||||
|
||||
@ -4,6 +4,7 @@ namespace App\Http\Controllers;
|
||||
|
||||
use App\Models\Template;
|
||||
use Illuminate\Http\Request;
|
||||
use Illuminate\Support\Facades\Storage;
|
||||
|
||||
class TemplateController extends Controller
|
||||
{
|
||||
@ -20,15 +21,28 @@ class TemplateController extends Controller
|
||||
return view('admin.template.edit', compact('template'));
|
||||
}
|
||||
|
||||
// Update template (nama, harga, paket)
|
||||
// Update template (nama, harga, paket, foto)
|
||||
public function update(Request $request, Template $template)
|
||||
{
|
||||
$validated = $request->validate([
|
||||
'nama_template' => 'required|string|max:255',
|
||||
'harga' => 'required|numeric|min:0',
|
||||
'paket' => 'required|in:starter,basic,premium',
|
||||
'foto' => 'nullable|image|mimes:jpg,jpeg,png|max:5120 ',
|
||||
]);
|
||||
|
||||
// kalau ada upload foto baru
|
||||
if ($request->hasFile('foto')) {
|
||||
// hapus foto lama kalau ada
|
||||
if ($template->foto && Storage::exists('public/' . $template->foto)) {
|
||||
Storage::delete('public/' . $template->foto);
|
||||
}
|
||||
|
||||
// simpan foto baru
|
||||
$path = $request->file('foto')->store('templates', 'public');
|
||||
$validated['foto'] = $path;
|
||||
}
|
||||
|
||||
$template->update($validated);
|
||||
|
||||
return redirect()->route('admin.template.index')
|
||||
|
||||
@ -24,7 +24,7 @@
|
||||
<table class="w-full border border-gray-200 text-left border-collapse">
|
||||
<thead class="bg-gray-100">
|
||||
<tr>
|
||||
<th class="px-3 py-2 border border-gray-200 w-[50px] text-center">#</th>
|
||||
<th class="px-3 py-2 border border-gray-200 w-[50px] text-center">No.</th>
|
||||
<th class="px-3 py-2 border border-gray-200">Nama</th>
|
||||
<th class="px-3 py-2 border border-gray-200">Deskripsi</th>
|
||||
<th class="px-3 py-2 border border-gray-200 text-center w-[100px]">Foto</th>
|
||||
|
||||
@ -0,0 +1,92 @@
|
||||
@extends('layouts.app')
|
||||
|
||||
@section('title', 'Daftar Pesanan Pelanggan')
|
||||
|
||||
@section('content')
|
||||
<div class="container mx-auto py-6">
|
||||
<div class="flex justify-between items-center mb-6">
|
||||
<h2 class="text-2xl font-bold">Daftar Pesanan</h2>
|
||||
</div>
|
||||
|
||||
<!-- Flash Message -->
|
||||
@if(session('success'))
|
||||
<div class="mb-4 p-3 rounded bg-green-100 text-green-800 border border-green-300 shadow">
|
||||
{{ session('success') }}
|
||||
</div>
|
||||
@endif
|
||||
|
||||
<!-- Tabel -->
|
||||
<div class="bg-white rounded-lg shadow overflow-x-auto">
|
||||
<table class="w-full border border-gray-200 text-left border-collapse">
|
||||
<thead class="bg-gray-100">
|
||||
<tr>
|
||||
<th class="px-3 py-2 border border-gray-200 w-[50px] text-center">No.</th>
|
||||
<th class="px-3 py-2 border border-gray-200">Nama Pemesan</th>
|
||||
<th class="px-3 py-2 border border-gray-200">Email</th>
|
||||
<th class="px-3 py-2 border border-gray-200">Template</th>
|
||||
<th class="px-3 py-2 border border-gray-200">Status</th>
|
||||
<th class="px-3 py-2 border border-gray-200">Harga</th>
|
||||
<th class="px-3 py-2 border border-gray-200 text-center w-[180px]">Aksi</th>
|
||||
</tr>
|
||||
</thead>
|
||||
<tbody>
|
||||
@forelse($pelanggans as $index => $pelanggan)
|
||||
<tr class="hover:bg-gray-50">
|
||||
<td class="px-3 py-2 border border-gray-200 text-center">{{ $index + 1 }}</td>
|
||||
<td class="px-3 py-2 border border-gray-200">{{ $pelanggan->nama_pemesan }}</td>
|
||||
<td class="px-3 py-2 border border-gray-200">{{ $pelanggan->email }}</td>
|
||||
<td class="px-3 py-2 border border-gray-200">{{ $pelanggan->template->nama_template ?? '-' }}</td>
|
||||
<td class="px-3 py-2 border border-gray-200">
|
||||
<span class="px-2 py-1 rounded text-sm
|
||||
{{ $pelanggan->status == 'diterima' ? 'bg-green-100 text-green-700' : ($pelanggan->status == 'ditolak' ? 'bg-red-100 text-red-700' : 'bg-yellow-100 text-yellow-700') }}">
|
||||
{{ ucfirst($pelanggan->status) }}
|
||||
</span>
|
||||
</td>
|
||||
<td class="px-3 py-2 border border-gray-200">Rp {{ number_format($pelanggan->harga, 0, ',', '.') }}</td>
|
||||
<td class="px-3 py-2 border border-gray-200 text-center">
|
||||
<div class="flex justify-center gap-2">
|
||||
<!-- Detail -->
|
||||
<a href="{{ route('admin.pelanggan.show', $pelanggan->id) }}"
|
||||
class="px-3 py-1 rounded bg-blue-500 text-white text-sm hover:bg-blue-600 flex items-center">
|
||||
<i class="bi bi-eye mr-1"></i> Detail
|
||||
</a>
|
||||
|
||||
<!-- Form Update Status -->
|
||||
<form action="{{ route('admin.pelanggan.update', $pelanggan->id) }}" method="POST" class="d-inline">
|
||||
@csrf
|
||||
@method('PUT')
|
||||
<select name="status" onchange="this.form.submit()"
|
||||
class="text-sm border rounded px-2 py-1">
|
||||
<option value="menunggu" {{ $pelanggan->status == 'menunggu' ? 'selected' : '' }}>Menunggu</option>
|
||||
<option value="diterima" {{ $pelanggan->status == 'diterima' ? 'selected' : '' }}>Diterima</option>
|
||||
<option value="ditolak" {{ $pelanggan->status == 'ditolak' ? 'selected' : '' }}>Ditolak</option>
|
||||
</select>
|
||||
</form>
|
||||
|
||||
<!-- Hapus -->
|
||||
<form action="{{ route('admin.pelanggan.destroy', $pelanggan->id) }}" method="POST" class="d-inline" onsubmit="return confirm('Yakin hapus pesanan?')">
|
||||
@csrf
|
||||
@method('DELETE')
|
||||
<button class="px-3 py-1 rounded bg-red-500 text-white text-sm hover:bg-red-600 flex items-center">
|
||||
<i class="bi bi-trash mr-1"></i> Hapus
|
||||
</button>
|
||||
</form>
|
||||
</div>
|
||||
</td>
|
||||
</tr>
|
||||
@empty
|
||||
<tr>
|
||||
<td colspan="7" class="px-3 py-4 text-center text-gray-500 border border-gray-200">
|
||||
Belum ada pesanan.
|
||||
</td>
|
||||
</tr>
|
||||
@endforelse
|
||||
</tbody>
|
||||
</table>
|
||||
</div>
|
||||
|
||||
<div class="mt-4">
|
||||
{{ $pelanggans->links() }}
|
||||
</div>
|
||||
</div>
|
||||
@endsection
|
||||
94
backend-baru/resources/views/admin/reviews/index.blade.php
Normal file
94
backend-baru/resources/views/admin/reviews/index.blade.php
Normal file
@ -0,0 +1,94 @@
|
||||
@extends('layouts.app')
|
||||
|
||||
@section('title', 'Manajemen Ulasan')
|
||||
|
||||
@section('content')
|
||||
<div class="container mx-auto py-6">
|
||||
<div class="flex justify-between items-center mb-6">
|
||||
<h2 class="text-2xl font-bold">Daftar Ulasan</h2>
|
||||
</div>
|
||||
|
||||
<!-- Flash Message -->
|
||||
@if(session('success'))
|
||||
<div class="mb-4 p-3 rounded bg-green-100 text-green-800 border border-green-300 shadow">
|
||||
{{ session('success') }}
|
||||
</div>
|
||||
@endif
|
||||
|
||||
<!-- Tabel -->
|
||||
<div class="bg-white rounded-lg shadow overflow-x-auto">
|
||||
<table class="w-full border border-gray-200 text-left border-collapse">
|
||||
<thead class="bg-gray-100">
|
||||
<tr>
|
||||
<th class="px-3 py-2 border border-gray-200 w-[50px] text-center">No.</th>
|
||||
<th class="px-3 py-2 border border-gray-200">Nama</th>
|
||||
<th class="px-3 py-2 border border-gray-200">Kota</th>
|
||||
<th class="px-3 py-2 border border-gray-200 text-center">Penilaian</th>
|
||||
<th class="px-3 py-2 border border-gray-200">Pesan</th>
|
||||
<th class="px-3 py-2 border border-gray-200 text-center w-[120px]">Aksi</th>
|
||||
</tr>
|
||||
</thead>
|
||||
<tbody>
|
||||
@forelse($reviews as $index => $review)
|
||||
<tr class="hover:bg-gray-50">
|
||||
<td class="px-3 py-2 border border-gray-200 text-center">{{ $index + 1 }}</td>
|
||||
<td class="px-3 py-2 border border-gray-200">{{ $review->name }}</td>
|
||||
<td class="px-3 py-2 border border-gray-200">{{ $review->city }}</td>
|
||||
<td class="px-3 py-2 border border-gray-200 text-center">
|
||||
@for ($s = 1; $s <= 5; $s++)
|
||||
<i class="bi {{ $s <= $review->rating ? 'bi-star-fill text-yellow-500' : 'bi-star text-gray-400' }}"></i>
|
||||
@endfor
|
||||
</td>
|
||||
<td class="px-3 py-2 border border-gray-200">{{ $review->message }}</td>
|
||||
<td class="px-3 py-2 border border-gray-200 text-center">
|
||||
<div class="flex justify-center gap-2">
|
||||
<form action="{{ route('admin.reviews.destroy', $review->id) }}" method="POST" onsubmit="return confirm('Hapus ulasan dari {{ $review->name }}?')">
|
||||
@csrf
|
||||
@method('DELETE')
|
||||
<button type="submit" class="px-3 py-1 rounded bg-red-600 text-white text-sm hover:bg-red-700 flex items-center">
|
||||
<i class="bi bi-trash mr-1"></i> Hapus
|
||||
</button>
|
||||
</form>
|
||||
</div>
|
||||
</td>
|
||||
</tr>
|
||||
@empty
|
||||
<tr>
|
||||
<td colspan="6" class="px-3 py-4 text-center text-gray-500 border border-gray-200">
|
||||
Belum ada ulasan.
|
||||
</td>
|
||||
</tr>
|
||||
@endforelse
|
||||
</tbody>
|
||||
</table>
|
||||
</div>
|
||||
</div>
|
||||
|
||||
|
||||
<script>
|
||||
document.addEventListener('DOMContentLoaded', () => {
|
||||
const modal = document.getElementById('modalDelete');
|
||||
const overlay = document.getElementById('modalDeleteOverlay');
|
||||
const closeBtn = document.getElementById('closeDeleteModal');
|
||||
const deleteForm = document.getElementById('deleteForm');
|
||||
const deleteName = document.getElementById('deleteName');
|
||||
|
||||
document.querySelectorAll('.btn-delete').forEach(btn => {
|
||||
btn.addEventListener('click', () => {
|
||||
deleteForm.action = btn.dataset.action;
|
||||
deleteName.textContent = btn.dataset.name || 'pengguna ini';
|
||||
modal.classList.remove('hidden');
|
||||
modal.classList.add('flex');
|
||||
});
|
||||
});
|
||||
|
||||
const closeModal = () => {
|
||||
modal.classList.add('hidden');
|
||||
modal.classList.remove('flex');
|
||||
}
|
||||
|
||||
closeBtn.addEventListener('click', closeModal);
|
||||
overlay.addEventListener('click', closeModal);
|
||||
});
|
||||
</script>
|
||||
@endsection
|
||||
@ -20,7 +20,8 @@
|
||||
</div>
|
||||
@endif
|
||||
|
||||
<form action="{{ route('admin.template.update', $template->id) }}" method="POST">
|
||||
<form action="{{ route('admin.template.update', $template->id) }}"
|
||||
method="POST" enctype="multipart/form-data">
|
||||
@csrf
|
||||
@method('PUT')
|
||||
|
||||
@ -59,6 +60,26 @@
|
||||
@enderror
|
||||
</div>
|
||||
|
||||
{{-- Foto / Gambar --}}
|
||||
<div class="mb-3">
|
||||
<label for="foto" class="form-label">Gambar Template</label>
|
||||
<div class="mb-2">
|
||||
@if($template->foto)
|
||||
<img src="{{ asset('storage/' . $template->foto) }}"
|
||||
alt="{{ $template->nama_template }}"
|
||||
class="rounded border" style="max-height: 120px">
|
||||
@else
|
||||
<p class="text-muted">Belum ada gambar</p>
|
||||
@endif
|
||||
</div>
|
||||
<input type="file" name="foto" id="foto"
|
||||
class="form-control @error('foto') is-invalid @enderror">
|
||||
<small class="text-muted">Kosongkan jika tidak ingin mengganti gambar.</small>
|
||||
@error('foto')
|
||||
<div class="invalid-feedback">{{ $message }}</div>
|
||||
@enderror
|
||||
</div>
|
||||
|
||||
{{-- Tombol --}}
|
||||
<button type="submit" class="btn btn-primary">Simpan Perubahan</button>
|
||||
<a href="{{ route('admin.template.index') }}" class="btn btn-secondary">Batal</a>
|
||||
|
||||
@ -20,7 +20,8 @@
|
||||
<table class="w-full border border-gray-200 text-left border-collapse">
|
||||
<thead class="bg-gray-100">
|
||||
<tr>
|
||||
<th class="px-3 py-2 border border-gray-200 w-[50px] text-center">#</th>
|
||||
<th class="px-3 py-2 border border-gray-200 w-[50px] text-center">No.</th>
|
||||
<th class="px-3 py-2 border border-gray-200">Gambar</th>
|
||||
<th class="px-3 py-2 border border-gray-200">Nama</th>
|
||||
<th class="px-3 py-2 border border-gray-200">Kategori</th>
|
||||
<th class="px-3 py-2 border border-gray-200">Paket</th>
|
||||
@ -32,6 +33,18 @@
|
||||
@forelse($templates as $index => $t)
|
||||
<tr class="hover:bg-gray-50">
|
||||
<td class="px-3 py-2 border border-gray-200 text-center">{{ $index + 1 }}</td>
|
||||
|
||||
<!-- Kolom gambar -->
|
||||
<td class="px-3 py-2 border border-gray-200 text-center">
|
||||
@if($t->foto)
|
||||
<img src="{{ asset('storage/' . $t->foto) }}"
|
||||
alt="{{ $t->nama_template }}"
|
||||
class="w-16 h-16 object-cover rounded">
|
||||
@else
|
||||
<span class="text-gray-400">-</span>
|
||||
@endif
|
||||
</td>
|
||||
|
||||
<td class="px-3 py-2 border border-gray-200">{{ $t->nama_template }}</td>
|
||||
<td class="px-3 py-2 border border-gray-200">{{ $t->kategori->nama ?? '-' }}</td>
|
||||
<td class="px-3 py-2 border border-gray-200">{{ ucfirst($t->paket) }}</td>
|
||||
@ -47,7 +60,7 @@
|
||||
</tr>
|
||||
@empty
|
||||
<tr>
|
||||
<td colspan="6"
|
||||
<td colspan="7"
|
||||
class="px-3 py-4 text-center text-gray-500 border border-gray-200">
|
||||
Belum ada template.
|
||||
</td>
|
||||
|
||||
@ -12,6 +12,7 @@
|
||||
background-color: #f1f5f9;
|
||||
font-family: 'Poppins', sans-serif;
|
||||
}
|
||||
|
||||
.sidebar {
|
||||
width: 250px;
|
||||
height: 100vh;
|
||||
@ -54,19 +55,23 @@
|
||||
<li>
|
||||
<a href="{{ route('admin.template.index') }}"
|
||||
class="flex items-center py-2 px-3 rounded hover:bg-blue-50 {{ request()->routeIs('admin.template.*') ? 'bg-blue-100 text-blue-600' : 'text-gray-700' }}">
|
||||
<i class="bi bi-diagram-3 me-2"></i> Template
|
||||
<i class="bi bi-layout-text-window me-2"></i> Template
|
||||
</a>
|
||||
</li>
|
||||
<li>
|
||||
<a href="#" class="flex items-center py-2 px-3 rounded hover:bg-blue-50 text-gray-700">
|
||||
<a href="{{ route('admin.pelanggan.index') }}"
|
||||
class="flex items-center py-2 px-3 rounded hover:bg-blue-50 {{ request()->routeIs('admin.pelanggan.*') ? 'bg-blue-100 text-blue-600' : 'text-gray-700' }}">
|
||||
<i class="bi bi-people me-2"></i> Pelanggan
|
||||
</a>
|
||||
</li>
|
||||
<li>
|
||||
<a href="#" class="flex items-center py-2 px-3 rounded hover:bg-blue-50 text-gray-700">
|
||||
<i class="bi bi-chat-dots me-2"></i> Ulasan
|
||||
<a href="{{ route('admin.reviews.index') }}"
|
||||
class="flex items-center py-2 px-3 rounded hover:bg-blue-50 {{ request()->routeIs('admin.reviews.*') ? 'bg-blue-100 text-blue-600' : 'text-gray-700' }}">
|
||||
<i class="bi bi-people me-2"></i> Ulasan
|
||||
</a>
|
||||
</li>
|
||||
|
||||
|
||||
</ul>
|
||||
|
||||
<p class="text-gray-500 uppercase text-xs font-semibold px-3 mt-4 mb-2">Akun</p>
|
||||
@ -89,4 +94,5 @@
|
||||
@yield('content')
|
||||
</div>
|
||||
</body>
|
||||
|
||||
</html>
|
||||
|
||||
@ -1,58 +0,0 @@
|
||||
@extends('layouts.app')
|
||||
|
||||
@section('title', 'Daftar Pesanan Pelanggan')
|
||||
|
||||
@section('content')
|
||||
<div class="container mt-4">
|
||||
<h2 class="mb-3">Daftar Pesanan</h2>
|
||||
|
||||
<a href="{{ route('pelanggans.create') }}" class="btn btn-primary mb-3">+ Buat Pesanan</a>
|
||||
|
||||
@if(session('success'))
|
||||
<div class="alert alert-success">{{ session('success') }}</div>
|
||||
@endif
|
||||
|
||||
<table class="table table-bordered">
|
||||
<thead>
|
||||
<tr>
|
||||
<th>#</th>
|
||||
<th>Nama Pemesan</th>
|
||||
<th>Email</th>
|
||||
<th>Template</th>
|
||||
<th>Status</th>
|
||||
<th>Harga</th>
|
||||
<th>Aksi</th>
|
||||
</tr>
|
||||
</thead>
|
||||
<tbody>
|
||||
@forelse($pelanggans as $index => $pelanggan)
|
||||
<tr>
|
||||
<td>{{ $index + 1 }}</td>
|
||||
<td>{{ $pelanggan->nama_pemesan }}</td>
|
||||
<td>{{ $pelanggan->email }}</td>
|
||||
<td>{{ $pelanggan->template->nama_template ?? '-' }}</td>
|
||||
<td>
|
||||
<span class="badge bg-{{ $pelanggan->status == 'diterima' ? 'success' : ($pelanggan->status == 'ditolak' ? 'danger' : 'warning') }}">
|
||||
{{ ucfirst($pelanggan->status) }}
|
||||
</span>
|
||||
</td>
|
||||
<td>Rp {{ number_format($pelanggan->harga, 0, ',', '.') }}</td>
|
||||
<td>
|
||||
<a href="{{ route('pelanggans.show', $pelanggan->id) }}" class="btn btn-sm btn-info">Detail</a>
|
||||
<a href="{{ route('pelanggans.edit', $pelanggan->id) }}" class="btn btn-sm btn-warning">Edit</a>
|
||||
<form action="{{ route('pelanggans.destroy', $pelanggan->id) }}" method="POST" class="d-inline" onsubmit="return confirm('Yakin hapus pesanan?')">
|
||||
@csrf
|
||||
@method('DELETE')
|
||||
<button class="btn btn-sm btn-danger">Hapus</button>
|
||||
</form>
|
||||
</td>
|
||||
</tr>
|
||||
@empty
|
||||
<tr><td colspan="7" class="text-center">Belum ada pesanan.</td></tr>
|
||||
@endforelse
|
||||
</tbody>
|
||||
</table>
|
||||
|
||||
{{ $pelanggans->links() }}
|
||||
</div>
|
||||
@endsection
|
||||
@ -5,7 +5,9 @@ use App\Http\Controllers\AdminAuthController;
|
||||
use App\Http\Controllers\DashboardController;
|
||||
use App\Http\Controllers\KategoriController;
|
||||
use App\Http\Controllers\TemplateController;
|
||||
use App\Http\Controllers\PelangganController;
|
||||
use Illuminate\Support\Facades\Auth;
|
||||
use App\Http\Controllers\Api\ReviewController;
|
||||
|
||||
// logout umum
|
||||
Route::post('/logout', function () {
|
||||
@ -42,5 +44,11 @@ Route::prefix('admin')->name('admin.')->group(function () {
|
||||
Route::get('/template', [TemplateController::class, 'index'])->name('template.index');
|
||||
Route::get('/template/{template}/edit', [TemplateController::class, 'edit'])->name('template.edit');
|
||||
Route::put('/template/{template}', [TemplateController::class, 'update'])->name('template.update');
|
||||
|
||||
// Pelanggan routes
|
||||
Route::resource('pelanggan', PelangganController::class)->except(['create', 'edit']);
|
||||
|
||||
// Ulasan routes
|
||||
Route::resource('reviews', ReviewController::class)->except(['create', 'edit', 'update', 'show', 'store']);
|
||||
});
|
||||
});
|
||||
|
||||
Loading…
Reference in New Issue
Block a user