140 lines
4.7 KiB
PHP
140 lines
4.7 KiB
PHP
<?php
|
|
|
|
namespace App\Http\Controllers;
|
|
|
|
use Illuminate\Http\Request;
|
|
use App\Models\Product;
|
|
use Illuminate\Support\Facades\Storage;
|
|
use Illuminate\Validation\Rule;
|
|
|
|
class ProductController extends Controller
|
|
{
|
|
public function index()
|
|
{
|
|
$title = '상품목록';
|
|
$products = Product::searchkeyword();
|
|
return view('product.list', compact('title', 'products'));
|
|
}
|
|
public function input()
|
|
{
|
|
$title = '상품추가';
|
|
return view('product.input', compact('title'));
|
|
}
|
|
|
|
public function edit(Product $product)
|
|
{
|
|
$title = '상품수정';
|
|
return view('product.edit', compact('product', 'title'));
|
|
}
|
|
|
|
public function update(Request $request, Product $product)
|
|
{
|
|
// 1) 입력 값 검증
|
|
$data = $request->validate([
|
|
'name' => ['required', 'string'],
|
|
'sku' => [
|
|
'required',
|
|
'string',
|
|
Rule::unique('products', 'sku')->ignore($product->id), // 현재 상품은 예외
|
|
],
|
|
'price' => ['required', 'numeric', 'min:0'],
|
|
'image' => ['nullable', 'image', 'mimes:jpg,jpeg,png,webp', 'max:2048'],
|
|
]);
|
|
|
|
// 2) 텍스트 데이터 업데이트
|
|
$product->name = $data['name'];
|
|
$product->sku = $data['sku'];
|
|
$product->price = $data['price'];
|
|
|
|
// 3) 이미지 처리
|
|
if ($request->hasFile('image')) {
|
|
|
|
// 기존 이미지가 있으면 삭제
|
|
if ($product->image && Storage::disk('public')->exists($product->image)) {
|
|
Storage::disk('public')->delete($product->image);
|
|
// Storage 파사드를 이용하면, 저장소 드라이버가 바뀌어도 코드 수정 최소화
|
|
}
|
|
|
|
// 새 이미지 저장
|
|
$path = $request->file('image')->store('uploads', 'public');
|
|
$product->image = $path;
|
|
}
|
|
|
|
// 4) 저장
|
|
$product->save();
|
|
|
|
// 5) 결과 응답
|
|
return redirect()
|
|
->route('product')
|
|
->with('success', '상품정보가 수정되었습니다.');
|
|
}
|
|
|
|
public function destroy($id)
|
|
{
|
|
// 1. 모델을 먼저 가져온다
|
|
$product = Product::findOrFail($id);
|
|
|
|
// 2. 이미지가 있는 경우만 삭제
|
|
if (!empty($product->image)) {
|
|
Storage::disk('public')->delete($product->image);
|
|
}
|
|
|
|
// 3. DB 레코드 삭제
|
|
$product->delete();
|
|
|
|
// 4. 목록으로 이동
|
|
return redirect()
|
|
->route('product')
|
|
->with('success', '상품이 삭제되었습니다.');
|
|
}
|
|
|
|
public function store(Request $request)
|
|
{
|
|
// 1) 검증 + 중복 검사 + 사용자 정의 메시지
|
|
$data = $request->validate([
|
|
'name' => ['required', 'string', 'max:100'],
|
|
'sku' => ['required', 'string', 'max:255', 'unique:products,sku'],
|
|
'quantity' => ['required', 'numeric', 'min:0'],
|
|
'price' => ['required', 'numeric', 'min:0'],
|
|
'image' => ['nullable', 'image', 'max:2048'],
|
|
], [
|
|
// name
|
|
'name.required' => '상품명은 필수 입력 항목입니다.',
|
|
'name.unique' => '이미 등록된 상품명입니다.',
|
|
|
|
// sku
|
|
'sku.required' => 'SKU는 필수 입력 항목입니다.',
|
|
'sku.string' => 'SKU는 문자열이어야 합니다.',
|
|
'sku.unique' => '이미 등록된 SKU입니다.',
|
|
|
|
// quantity
|
|
'quantity.required' => '수량은 필수 입력 항목입니다.',
|
|
'quantity.numeric' => '수량은 숫자여야 합니다.',
|
|
'quantity.min' => '수량은 0 이상이어야 합니다.',
|
|
|
|
// price
|
|
'price.required' => '가격은 필수 입력 항목입니다.',
|
|
'price.numeric' => '가격은 숫자여야 합니다.',
|
|
'price.min' => '가격은 0 이상이어야 합니다.',
|
|
|
|
// image
|
|
'image.image' => '업로드된 파일은 이미지여야 합니다.',
|
|
'image.max' => '이미지 파일 크기는 2MB 이하만 가능합니다.',
|
|
]);
|
|
|
|
// 2) 이미지 업로드 처리
|
|
if ($request->hasFile('image')) {
|
|
$data['image'] = $request->file('image')->store('products', 'public');
|
|
// 저장 경로 예: storage/app/public/products/파일명.jpg
|
|
}
|
|
|
|
// 3) DB 저장
|
|
Product::create($data);
|
|
|
|
// 4) 등록 후 리다이렉트
|
|
return redirect()
|
|
->route('product.input')
|
|
->with('success', '상품이 등록되었습니다.');
|
|
}
|
|
}
|