user()->id; // Ambil customer_id dari user yang login // Ambil data booking berdasarkan customer_id, lalu ambil data token untuk masing-masing booking $bookings = Booking::where('customer_id', $customer_id) ->with('photos') // Mengambil relasi dengan tabel photos ->get() ->map(function($booking) { // Menggabungkan token dari photos terkait dengan booking $booking->photos = $booking->photos->unique('token'); // Mengambil hanya token yang unik return $booking; }); return view('customer.photos', compact('bookings')); } public function verifyToken(Request $request) { $request->validate([ 'token' => 'required|string|size:10' // Sesuaikan ukuran token jika perlu ]); // Cari semua foto berdasarkan token $photos = Photo::where('token', $request->token)->get(); if ($photos->isEmpty()) { return redirect()->back()->with('error', 'Token tidak valid atau foto tidak ditemukan.'); } // Kirimkan data foto yang ditemukan ke view return view('customer.photos', compact('photos')); } public function download($token) { // Cari foto berdasarkan token $photo = Photo::where('token', $token)->first(); // Jika tidak ditemukan, kembalikan error if (!$photo) { return redirect()->back()->with('error', 'Foto tidak ditemukan atau token salah.'); } // Path file $filePath = storage_path('app/public/' . $photo->file_path); // Cek apakah file ada di storage if (!file_exists($filePath)) { return redirect()->back()->with('error', 'File tidak tersedia.'); } // Download file return response()->download($filePath); } public function create() { $customers = User::where('role', 'customer')->get(); $photos = Photo::with(['customer', 'booking']) ->orderByDesc('created_at') ->get(); // Ambil semua booking yang belum memiliki entri di tabel photos $bookingsWithPhotoIds = Photo::distinct()->pluck('booking_id')->toArray(); $bookingsWithoutPhotoToken = Booking::whereNotIn('id', $bookingsWithPhotoIds) ->with('customer') // pastikan relasi customer() tersedia di model Booking ->orderBy('tanggal_pemotretan', 'desc') ->get(); return view('user.upload', compact('customers', 'photos', 'bookingsWithoutPhotoToken')); } public function store(Request $request) { $request->validate([ 'customer_id' => 'required|exists:users,id', 'booking_id' => 'required|exists:bookings,id', 'photos' => 'required|array', 'photos.*' => 'required|image|mimes:jpg,jpeg,png,gif|max:102400', ]); $customerId = $request->customer_id; $bookingId = $request->booking_id; // Cek apakah token sudah ada untuk booking & customer ini $existingToken = Photo::where('customer_id', $customerId) ->where('booking_id', $bookingId) ->pluck('token') ->first(); if (!$existingToken) { do { $token = Str::random(10); } while (Photo::where('token', $token)->exists()); } else { $token = $existingToken; } // Path folder tujuan di server hosting $destinationPath = public_path('images/photos'); // Buat folder jika belum ada if (!file_exists($destinationPath)) { mkdir($destinationPath, 0755, true); } if ($request->hasFile('photos')) { foreach ($request->file('photos') as $photo) { $filename = time() . '_' . $photo->getClientOriginalName(); $photo->move($destinationPath, $filename); // Simpan path relatif untuk diakses lewat browser Photo::create([ 'user_id' => auth()->id(), 'customer_id' => $customerId, 'booking_id' => $bookingId, 'file_path' => 'images/photos/' . $filename, 'token' => $token, ]); } } else { return redirect()->back()->with('error', 'Tidak ada foto yang diupload.'); } return redirect()->back()->with([ 'success' => "Foto berhasil diupload!", 'token' => $token, ]); } public function downloadAll(Request $request) { $token = $request->query('token'); $photos = Photo::where('token', $token)->get(); if ($photos->isEmpty()) { return redirect()->back()->with('error', 'Token tidak ditemukan atau foto belum tersedia.'); } $zipFileName = 'foto_' . $token . '.zip'; $zipPath = storage_path('app/public/zips/' . $zipFileName); if (!file_exists(dirname($zipPath))) { mkdir(dirname($zipPath), 0755, true); } $zip = new ZipArchive; if ($zip->open($zipPath, ZipArchive::CREATE | ZipArchive::OVERWRITE) === true) { foreach ($photos as $photo) { $filePath = public_path($photo->file_path); if (file_exists($filePath)) { $zip->addFile($filePath, basename($filePath)); } } $zip->close(); return response()->download($zipPath)->deleteFileAfterSend(true); } else { return redirect()->back()->with('error', 'Gagal membuat file ZIP.'); } } }