یک مثال کاربردی آپلود فایل
حالا نوبت این است که با یک مثال کاربردی نحوه آپلود فایل در لاراول رو کار کنیم. فرض کنید می خواهیم در جدول posts یک مطلب جدید را اضافه کنیم که این مطلب دارای یک تصویر هم می باشد که قرار است آن را در مسیر public/uploads ذخیره کنیم. فرض میکنیم در جدول posts ستونهای (id, title, body, pic_name) وجود دارد.
یک فایل view به نام form.blade.php در مسیر resources/views ایجاد کنید و کدهای زیر را داخل آن قرار دهید :
کد HTML:
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8">
<title>form validation</title>
<style type="text/css">
.error {
color: red;
font-weight: bold;
}
.success {
color: green;
font-weight: bold;
}
</style>
</head>
<body>
<form action="{{ url('add-post') }}" method="post" enctype="multipart/form-data">
<input type="hidden" name="_token" value="{{ csrf_token() }}">
<label for="title">Title</label>
<input type="text" name="title" id="title" value="{{ old('title') }}">
<span class="error">{{ $errors->first('title') }}</span><br>
<label for="post">Post</label>
<textarea name="post" id="post">{{ old('post') }}</textarea>
<span class="error">{{ $errors->first('post') }}</span><br>
<label for="photo">Select an Image:</label>
<input type="file" name="photo" id="photo">
<span class="error">{{ $errors->first('photo') }}</span><br>
<input type="submit" value="Submit">
</form>
<p class="success">{{ session('message') }}</p>
<p class="error">{{ session('error') }}</p>
</body>
</html>
اکنون مسیر های زیر را در فایل routes.php تعریف میکنیم :
Route::get('add-post', 'PostController@getAddPost');
Route::post('add-post', 'PostController@postAddPost');
همانطور که می بینید باید یک کنترلر به نام PostController داشته باشیم و متدهای getAddPost و postAddPost را داخل آن تعریف کنیم.
ابتدا برای رندر کردن فایل ویو متد getAddPost را به صورت زیر بنویسید :
public function getAddPost()
{
return view('form');
}
کد های زیر را هم در متد postAddPost قرار دهید :
public function postAddPost(Request $request)
{
$rules = [
'title' => 'required|max:255|unique:posts',
'post' => 'required',
'photo' => 'required|image|max:1024',
];
$v = Validator::make($request->all(), $rules);
if($v->fails()){
return redirect()->back()->withErrors($v->errors())->withInput($request->except('photo'));
} else {
$file = $request->file('photo');
if($file->isValid()){
$fileName = time().'_'.$file->getClientOriginalName();
$destinationPath = public_path().'/uploads';
$file->move($destinationPath, $fileName);
$post = new Post;
$post->title = $request->input('title');
$post->body = $request->input('post');
$post->pic_name = $fileName;
$post->save();
return redirect()->back()->with('message', 'The post successfully inserted.');
} else {
return redirect()->back()->with('error', 'uploaded file is not valid.');
}
}
}
همانطور که که می بینید ابتدا مقادیر فرم را اعتبارسنجی کردیم. برای فایل هم با قانون max مشخص کردم که فایل فقط می تواند ۱۰۲۴ کیلوبایت سایز داشته باشد و همچنین با قانون image مشخص میکنیم که فایل از نوع تصویر باشد فقط mime type های (jpeg, png, bmp, gif, or svg) را قبول میکند. در صورتی که می خواهید محدودیت بیشتری برای mime type فایل در نظر بگیرید یا اصلا فایل شما تصویر نیست می توانید با استفاده از قانون mime نوع فایل را مشخص کنید. در صورتی که اعتبارسنجی دارای خطا باشد به فرم برگشته و خطاها نمایش داده می شوند.
سپس اطلاعات فایل رو در متغیر file$ قرار دادم و با استفاده از متدهای کلاس UploadedFile می توانیم به اطلاعات فایل دسترسی داشته باشیم. نام فایل را تلفیقی از timestamp جاری و نام اصلی فایل تعیین کردم تا احتمال اینکه نام فایل تکراری باشد وجود نداشته باشد و داخل متغیر fileName$ قرار دادم. مسیر آپلود فایل را در destinationPath$ قرار دادم و با استفاده از متد move فایل را آپلود میکنیم. این متد مسیر آپلود و نام فایل را به عنوان پارامتر میگیرد.
در نهایت سایر مقادیر فرم به همراه نام فایل را در جدول posts درج میکنیم. در صورت موفقیت یا عدم موفقیت نیز پیغام های خطایی را ست و در ویو چاپ میکنیم.
اکنون هرقسمت از وبسایت که می خواهیم پست ها را نمایش دهیم به راحتی می توانیم تصویر را هم با استفاده از نام آن نمایش دهیم:
<img src="{{ asset('uploads/'.$post->pic_name) }}" alt="{{ $post->pic_name }}" >