Call to a member function getClientOriginalExtension() on null what should do? - laravel

public function store(Request $request)
{
$data = new product1();
$file = $request->file;
$filename= time().'.'.$file->getClientOriginalExtension();
$request->file->move('assets', $filename);
$data->file = $filename;
$data->name = $request->name;
$data->description = $request->description;
$data->author = $request->author;
$data->comment = $request->comment;
$data->save();
return redirect()->back();
}
View:
<form action="{{ url('uploadproduct') }}" method="post" enctype="multipart/form-data">
#csrf
<div class="form-group">
<input class="form-control" name="comment" placeholder="Write comment" type="text" style=" width: 50%;">
<input class="btn btn-primary" type="submit" value="Done" style=" width: 20%;">
</div>
</form>

$file is null when trying to get its properties.
You can either condition the process to the existence of $file (in case that the 'file' input is not required), or simply check what is happening that input value is null when requesting it.
Maybe there's no <input type="file" name="file"> in your form...
Or maybe your form has no enctype="multipart/form-data" property that allows you to submit files.
I DO also recommend you to validate your request before processing the data: https://laravel.com/docs/8.x/validation
public function store(Request $request)
{
$validator = Validator::make($request->all(), [
'file' => 'required'
]);
if ($validator->fails()) {
return Redirect::back()->withErrors($validator)->withInput();
}
// Here you start processing your inputs
}

Related

Get product id to store attachments accordingly

I currently have the add attachment button for each product on the product list page. After clicking the button, will proceed to add attachment form. How do I get the current product ID from the product table in order to store the attachment data into the attachment table?
Route
Route::post('/store/{product}', 'AttachmentController#store')->name('attachment.store');
Product Model
public function attachment()
{
return $this->hasMany(Attachment::class, 'product_id', 'id');
}
Attachment Model
public function product()
{
return $this->belongsTo(Product::class, 'product_id');
}
Controller
public function create()
{
return view('document.create', ['prod' => Product::select('id', 'name')->get()]);
}
public function store(Request $request, Product $product) {
$data['product_id'] = $product->id;
$data = $request->validate([
'file' => 'required',
'file.*' => 'mimes:csv,xlsx,pdf,docx',
]);
$attachmentData = [];
if($request->hasFile('file'))
{
foreach($request->file('file') as $file) {
$path = public_path('storage/attachments/'.$request->product_id);
$fileName = time().'-'.$file->getClientOriginalName();
$file->move($path, $fileName);
$attachmentData[] = $fileName;
}
$data['file'] = json_encode($attachmentData);
}
$attachment = Attachment::create($data);
return redirect()->route('product.index')->with('success','Attachment added successfully');
}
Blade View
<form method="POST" action="{{route('attachment.store')}}" enctype="multipart/form-data">
#csrf
<h3><b>Add Attachment</b></h3>
<input type="submit" class="btn btn-primary mr-2" value="Save">
<div class="row">
<h4 class="card-title">General</h4>
<input type="text" name="product_id" value="{{ $product->id ?? '' }}" hidden>
<div class="form-group">
<label for="name">Name</label>
<input type="text" id="name" class="form-control" name="name" required>
</div>
<div class="form-group">
<label>Attachment </label>
<div class="input-group-append">
<label for="attachment" class="btn btn-info">Upload</label>
<input id="attachment" type="file" name="file[]" multiple required>
</div>
</div>
</div>
</form>
You have to use form action like below
<form method="POST" action="{{route('attachment.store',['product'=>$product->id])}}" enctype="multipart/form-data">

Laravel Image Upload not saving to public folder

I am struggling with this image upload system.
It is supposed to upload an image that will be attached to a post (each post has 1 image).
Everything seems to be working fine, the problem is that when I check the database for the image path, I see a path to a random temporary file and the image doesn't even get uploaded to the right folder inside the app public folder.
Check the logic below:
PostController.php
public function store(Request $request)
{
$post = new Post;
$request->validate([
'title' => 'required',
'description' => 'required',
'slug' => 'required',
'message' => 'required',
'user' => 'required',
'post_image' => 'image|mimes:jpeg,png,jpg,gif|max:2048'
]);
if ($request->has('post_image')) {
$image = $request->file('post_image');
$name = Str::slug($request->input('title')).'_'.time();
$folder = '/uploads/images/';
$filePath = $folder . $name. '.' . $image->getClientOriginalExtension();
$this->uploadOne($image, $folder, 'public', $name);
$post->post_image = Storage::url($filePath);;
}
Post::create($request->all());
return \Redirect::to('admin')->with('success','Great! Post created successfully.');
}
UploadTrait.php
trait UploadTrait
{
public function uploadOne(UploadedFile $uploadedFile, $folder = null, $disk = 'public', $filename = null)
{
$name = !is_null($filename) ? $filename : Str::random(25);
$file = $uploadedFile->storeAs($folder, $name.'.'.$uploadedFile->getClientOriginalExtension(), $disk);
return $file;
}
}
Post.php (model)
class Post extends Model
{
protected $fillable = [
'title',
'description',
'slug',
'message',
'user',
'post_image'
];
public function getImageAttribute(){
return $this->post_image;
}
}
Create.blade.php
<form action="{{ route('blog.store') }}" method="POST" name="add_post" role="form" enctype="multipart/form-data">
{{ csrf_field() }}
<h1>New Post</h1>
<div role="separator" class="dropdown-divider"></div>
<div class="form-row">
<div class="form-group col-12 col-md-6">
<label for="title">Post Title</label>
<input type="text" autocomplete="off" class="form-control" id="title" name="title" placeholder="Your post title" required>
<span class="text-danger">{{ $errors->first('title') }}</span>
</div>
<div class="form-group col-12 col-md-6">
<label for="slug">Slug</label>
<input type="text" autocomplete="off" class="form-control" id="slug" name="slug" placeholder="Write post slug" required>
<span class="text-danger">{{ $errors->first('slug') }}</span>
</div>
</div>
<div class="form-row">
<div class="form-group col-12 col-md-12">
<label for="description">Post Description</label>
<textarea class="form-control" id="description" name="description" placeholder="Enter a small description for your post" required></textarea>
<span class="text-danger">{{ $errors->first('description') }}</span>
</div>
</div>
<div class="badge badge-warning badge-pill">Message</div>
<div role="separator" class="dropdown-divider"></div>
<div class="form-row">
<div class="form-group col-md-12">
<textarea class="form-control" col="4" id="message" name="message"></textarea>
<span class="text-danger">{{ $errors->first('message') }}</span>
</div>
</div>
<input type="hidden" value="{{ Auth::user()->name }}" name="user">
<input id="post_image" type="file" class="form-control" name="post_image">
<button type="submit" class="btn btn-warning btn-block">Create Post</button>
</form>
Thank you for your help!
Regards,
Tiago
You can use directly the functions provided by Laravel itself
$image_path = Storage::disk('public')->putFile('folders/inside/public', $request->file('post_image'));
Notice Storage::disk('public') that specifies the public folder.
Then you can update your request array with $request['image_path'] = $image_path and save it like you're currently doing or you cant still use your $post = new Post; and set every input data like $post->title = $request->title; then save like $post->save();
You did not save the image path in the database on the created post
$post = new Post; //here you have created an empty Post object
...
$post->post_image = Storage::url($filePath); //here you assigned the post_image to the empty object.
Post::create($request->all());// here you create a new POST object with the request data, which does not contain the post_image
Thank you David! I managed to correct the path that gets saved to the database, but the files are not getting uploaded (even though the path in database says /uploads/images/something.png, when i check the folder, the image is not there.. there is not even an uploads folder. This is the method I have now with your suggestions:
public function store(Request $request)
{
$request->validate([
'title' => 'required',
'description' => 'required',
'slug' => 'required',
'message' => 'required',
'user' => 'required',
'post_image' => 'image|mimes:jpeg,png,jpg,gif|max:2048'
]);
if ($request->has('post_image')) {
$image = $request->file('post_image');
$name = Str::slug($request->input('title')).'_'.time();
$folder = '/uploads/images';
$filePath = $folder . $name. '.' . $image->getClientOriginalExtension();
$this->uploadOne($image, $folder, 'public', $name);
$image_path = Storage::disk('public')->putFile('uploads/images', $request->file('post_image'));
$request['image_path'] = $image_path;
}
$post = new Post;
$post->title = $request->title;
$post->description = $request->description;
$post->slug = $request->slug;
$post->message = $request->message;
$post->user = $request->user;
$post->post_image = $request->image_path;
$post->save();
return \Redirect::to('admin')->with('success','Great! Post created successfully.');
}
Input in form
<form method="POST" enctype="multipart/form-data" action="/url">
<input id="category_logo" type="file" class="form-control" name="category_logo">...
Code in controller
$category = Category::find($id);
if($request->has('category_logo')) {
$image = $request->file('category_logo');
$category->category_logo = $image->getClientOriginalName();
$image->move(public_path('img/logo'), $image->getClientOriginalName());
}
$category->save();
Works for me!

File uploader gives null when i want to sent it to my database

I was trying to make a file uploader in laravel. But when i want to send it to database it have a null value when i send it to the controller. I don't know where I have to go to with this problem to fix it.
My view:
<div class="container">
<form method="POST" action="/admin/add-album/add">
#csrf
<label>Album name</label>
<input type="text" name="album_name" class="form-control">
<br>
<input id="file-upload" type="file" name="album_picture" accept="image/*">
<br>
<input type="submit" name="submit" class="form-control">
</form>
</div>
My controller:
public function addAlbumDatabase(Request $request)
{
request()->validate([
'album_name' => ['required'],
]);
$slug = $this->slugify(request('album_name'));
$user = \Auth::user();
dd($request->file('album_picture'));
if ($files = $request->album_picture) {
$destinationPath = 'public/images/';
$profileImage = date('YmdHis') . "." . $files->getClientOriginalExtension();
$files->move($destinationPath, $profileImage);
} else {
dd("mislukt om de image up te loaden");
}
Albums::create([
'user_id' => $user->id,
'album_name' => request('album_name'),
'album_profile_picture' => $profileImage,
'album_slug'=> $slug
]);
return redirect('admin/add-album');
}
my model:
class Albums extends Model {
protected $fillable = [
'user_id', 'album_name', 'album_profile_picture', 'album_slug'
];
}
Add enctype="multipart/form-data" in your form rule. So:
<form method="POST" action="/admin/add-album/add" enctype="multipart/form-data">

Summernote WYSIWYG editor not rendering data correctly with Laravel 5.8

I have a problem when I want to rendering data and Images from database, I'm using Summernote and Laravel, I will paste my Code of the controller and views, thanks in advance.
I get summer note show correctly with all his options, but when I try to add some things in my text like make it bold or something like that he did not work.
Controller:
public function createPost(Request $request){
$this->validate($request, [
'title' => 'required',
'description' => 'required',
]);
$title = $request->input('title');
$description = $request->input('description');
$writer = Auth::user()->id;
$dom = new \DomDocument();
$dom->loadHtml($description, LIBXML_HTML_NOIMPLIED | LIBXML_HTML_NODEFDTD);
$images = $dom->getElementsByTagName('img');
foreach($images as $k => $img){
$data = $img->getAttribute('src');
list($type, $data) = explode(';', $data);
list(, $data) = explode(',', $data);
$data = base64_decode($data);
$image_name= "/upload/" . time().$k.'.png';
$path = public_path() . $image_name;
file_put_contents($path, $data);
$img->removeAttribute('src');
$img->setAttribute('src', $image_name);
}
$description = $dom->saveHTML();
$post = new Post;
$post->title= $title;
$post->description = $description;
$post->writer = $writer;
$post->save();
return redirect()->route('home')->with('success', 'Post has been successfully added!');
}
Add view:
#if(Auth::check())
<div class="col-md-12">
<form method="post" action="{{ route('post.form') }}">
{{ csrf_field() }}
<div class="form-group">
<label for="name">Title</label>
<input type="text" class="form-control" id="id_title" name="title"
aria-describedby="title" placeholder="Enter title">
</div>
<div class="form-group">
<label for="description">Description</label>
<textarea class="form-control" id="content" rows="3" name="description" placeholder="Description"></textarea>
</div>
<button type="submit" class="btn btn-primary">Publish <i class="fas fa-paper-plane"></i></button>
</form>
</div>
#endif
Call of the summernote:
<script>
$(document).ready(function() {
$('#content').summernote({
height:300,
});
});
</script>
Example of the result, title plus content :
You should use {!! $description !!} to print as html.
Inspect the output in the browser, maybe the summernote plugin is not called properly,
In head tag, check the javascript plugin, and the css as well. Put them is proper order.

data is not submitting into db

I’m trying to signup user, initially it was working but now its not , when i enter data and click on signup then nothing happens, any solution to resolve this issue?
this is UsersController:
public function register(Request $request){
if($request->isMethod('post')){
$data = $request->all();
/*echo "<pre>"; print_r($data); die;*/
// Check if User already exists
$usersCount = User::where('email',$data['email'])->count();
if($usersCount>0){
return redirect()->back()->with('flash_message_error','Email already exists!');
}else{
$user = new User;
$user->name = $data['name'];
$user->email = $data['email'];
$user->password = bcrypt($data['password']);
$user->save();
// Send Confirmation Email
$email = $data['email'];
$messageData = ['email'=>$data['email'],'name'=>$data['name'],'code'=>base64_encode($data['email'])];
Mail::send('emails.confirmation',$messageData,function($message) use($email){
$message->to($email)->subject('Confirm your E-com Account');
});
return redirect()->back()->with('flash_message_success','Please confirm your email to activate your account!');
if(Auth::attempt(['email'=>$data['email'],'password'=>$data['password']])){
Session::put('frontSession',$data['email']);
if(!empty(Session::get('session_id'))){
$session_id = Session::get('session_id');
DB::table('cart')->where('session_id',$session_id)->update(['user_email' => $data['email']]);
}
return redirect('/cart');
}
}
}
}
this is registeration form:
<form id="registerForm" name="registerForm" action="{{ url('/user-register') }}" method="POST">{{ csrf_field() }}
<input id="name" name="name" type="text" placeholder="Name"/>
<input id="email" name="email" type="email" placeholder="Email Address"/>
<input id="myPassword" name="password" type="password" placeholder="Password"/>
<button type="submit" class="btn btn-default">Signup</button>
</form>
and this is route:
Route::post('/user-register','UsersController#register');
The basic registration method in laravel with validation and auto login
public function register(Request $request)
{
$this->validate($request, [
'name' => 'required',
'email' => 'required|email|unique:users,email',
'password' => 'required|min:6',
]);
$input = $request->all();
$input['password'] = Hash::make($input['password']);
$user = User::create($input);
Auth::login($user);
return redirect()->route('dashboard')
->with('success','Congratulation !!! You are registered successfully. Now you can login');
}
What is the error you will see in the blade template by adding this before form
#if($errors->all())
#foreach ($errors->all() as $error)
<div class="alert alert-danger">{{ $error }}</div>
#endforeach
#endif

Resources