Am having the form which I want to upload file but i got null on the fileUpload field when I submit to the controller
here is my Form
<form action="{{route('manager.expense.store')}}" method="POST" id="manager_add_new_expense" enctype="multipart/form-data">
enter code here
<div class="mb-3">
<label for="example-input-palaceholder">Add Supporting Document</label><small class="ml-auto align-self-end"><b>
Doc Such as: Receipt, Mpawe, Orders, Etc ...</b></small>
<input type="file" class="form-control #error('Uploadfile') is-invalid #enderror" id="Uploadfile" name="Uploadfile" value="">
Also my controller content bellow
//
$user = User::findOrFail(Auth::id());
$validator = Validator::make($request->all(), [
'Uploadfile' => 'required|mimes:doc,docx,pdf,txt,png,jpg|max:500000'
]);
if ($validator->fails()){
// return back()->withErrors($validator)->withInput();
return response()->json(["error"=>true, "message"=>$validator->errors()->first()]);
}
$filename = $request->file('Uploadfile');
$filen = date('YmdHis')."-".$filename->getClientOriginalName();
$request->file('Uploadfile')->move(storage_path('expensefile'), $filen);
I don't know why I am getting the Null value, only Am failing on the the validation like I have no file found.
try adding #csrf and make sure your route is a post route
I have found that the Error was i was submitting the form using AJAX yet there was no code to enable the upload
Just I added this and it works
data: new FormData(this),
contentType: false,
cache: false,
processData:false,
Related
When I make an AJAX call from view and pass form data to the controller. I get a couple of problems. First, the code inside success is never executed, and second, the page is being refreshed even though it is an AJAX call. Can anyone tell me where am I doing wrong?
I have seen a lot of questions since yesterday but none of them were able to solve my problem.
Model code
public function insert_user($name, $email) {
$data = array();
$data['name'] = $name;
$data['email'] = $email;
$data['created_at'] = date('y-m-d');
$this->db->insert('all_users', $data);
return true;
}
Controller code
public function insert_user () {
$data = $this->input->post();
$name = $data['name'];
$email = $data['email'];
$this->User_model->insert_user($name, $email);
$this->load->view('view');
}
Ajax request code
const insertBtn = $(".insert-btn");
insertBtn.on("click", function () {
const name = $(".insert-form input[type=name]");
const email = $(".insert-form input[type=email]");
$.ajax({
url: "<?php echo base_url() ?>index.php/Users/insert_user",
type: "post",
data: {name, email},
dataType: "json",
success: function () {
$("body").append("Request made successfully");
}
})
});
My form looks something like this:
<form class="insert-form" action="<?php echo base_url() ?>index.php/Users/insert_user" method="post">
<input type="text" name="name" placeholder="Enter name">
<input type="email" name="email" placeholder="Enter email">
<button class="insert-btn">Insert Data</button>
</form>
NOTE: I am able to successfully insert data into the database.
The browser is submitting the form before your AJAX code gets a chance to run/finish.
Instead of binding an event to the click event of the button, you want to bind to the submit event of the form. Then you want to cancel the browser's default action. This is done via the e.preventDefault(); method.
Also, dataType: "json" is not needed here. dataType tells jQuery what kind of data your AJAX call is returning. You generally don't need it as jQuery can automatically detect it. Plus, if you are not returning a JSON document, then this may cause a problem.
const insertForm = $(".insert-form");
insertForm.on("submit", function (e) {
const name = insertForm.find("input[type=name]");
const email = insertForm.find("input[type=email]");
e.preventDefault();
$.ajax({
url: "<?php echo base_url() ?>index.php/Users/insert_user",
type: "post",
data: {name, email},
success: function () {
$("body").append("Request made successfully");
}
})
});
Controller code
public function insert_user () {
$data = $this->input->post();
$name = $data['name'];
$email = $data['email'];
$data = $this->User_model->insert_user($name, $email);
$this->output
->set_content_type('application/json')
->set_output(json_encode($data));
}
Ajax request code
const insertBtn = $(".insert-btn");
insertBtn.on("click", function () {
const name = $(".insert-form input[type=name]");
const email = $(".insert-form input[type=email]");
$.ajax({
url: "<?php echo base_url() ?>Users/insert_user", // <?php echo base_url() ?>controller_name/function_name
type: "post",
data: {name, email},
dataType: "json",
success: function () {
$("body").append("Request made successfully");
}
})
});
form looks something like this:
<form class="insert-form" method="post">
<input type="text" name="name" placeholder="Enter name">
<input type="email" name="email" placeholder="Enter email">
<button class="insert-btn">Insert Data</button>
</form>
The page was being refreshed because I had a button that was acting as submit button on changing it to the input of the type button it does not submits the form and we don't see the page being refreshed. And also the AJAX request made also runs successfully.
<form class="insert-form" action="<?php echo base_url() ?>index.php/Users/insert_user" method="post">
<input type="text" name="name" placeholder="Enter name">
<input type="email" name="email" placeholder="Enter email">
<input type="button" class="insert-btn" value="Insert Data">
</form>
I am currently having issues saving in Laravel from my Nuxt Application. I tried to perform the creating data from my postman and it works. I don't know what I missing here.
Controller
$book = Book::create([
'name' => $request->name,
'about' => $request->about,
// dd($request->file('image')),
'image' => $request->file('image')->store('images'),
]);
In my Nuxt template I have this
<form method="POST" enctype="multipart/form-data" #submit.prevent="save">
<div class="form-group">
<label for="name">Book Name</label>
<input
id="name"
v-model="editedItem.name"
type="text"
class="form-control"
placeholder="Book Name"
>
</div>
<div class="form-group">
<label for="image">Upload Book Cover</label>
<input
id="image"
name="image"
type="file"
accept="image/*"
class="form-control-file"
#change="onUpload"
>
</div>
<button type="submit" class="btn btn-primary">
Create Book
</button>
</form>
My nuxt methods
async save () {
try {
const formData = new FormData()
formData.append('name', this.editedItem.name)
formData.append('image', this.editedItem.imageurl.name)
await this.$axios.post('http://127.0.0.1:8000/api/createbookapi',
formData,
{
headers: {
enctype: 'multipart/form-data'
}
}
)
},
onUpload (e) {
this.editedItem.imageurl = e.target.files[0]
},
data: () => ({
editedItem: {
name: '',
imageurl: ''
}),
When I tried to save using postman, it works.
I don't know what I am missing here.
Call to a member function store() on null
becouse your file is null to avoid this add validation or make it optional
example of optional image
make sure database field is nullable
$book = Book::create([
'name' => $request->name,
'about' => $request->about,
'image' => $request->hasFile('image')
? $request->file('image')->store('images')
: null,
]);
for validation example
'image' => 'required|file', // it should check for file because file have class have store method
I've upgraded my app from Laravel 4.2 to Laravel 5.3. On an index page listing citations, I have an AJAX modal form to edit or view the login credentials for the citation. This was working fine in Laravel 4.2, but I cannot for the life of me get it to work in 5.3. After about 5 hours Googling and trying different things, I thought I would post it here so that someone way more experienced than me can point me in the right direction.
Here's the link on the index page:
<a style="cursor: pointer; " title= "Login Credentials" data-loopback="cit-pg-1" data-citationid="1079" class="getCitationdetails"><span class="glyphicon glyphicon-lock " title="Login Credentials"></span></a>
And here's the JavaScript:
<script type="text/javascript">
$(document).on('click','.getCitationdetails',function(){
var citationid = $(this).data('citationid');
var loopback = $(this).data('loopback');
$.ajax({
url : '/citation-password',
type:'post',
data : {citationid :citationid, loopback :loopback},
success:function(resp){
$('#AppendLoginDetails').html(resp);
$('#LoginCredentialsModal').modal('show');
$('.loadingDiv').hide();
},
error:function(){
alert('Error');
}
})
})
Here's my route:
Route::match(['get', 'post'], '/citation-password', 'CitationsController#citationpassword');
And here's the Controller method that generates the form on get and saves the data on post:
public function citationpassword()
{
if (Request::ajax()) {
$data = Request::all();
if (!$data['citationid']) {
return redirect('/citations')
->with('flash-danger', 'Missing citation id for Login credentials form!!');
}
// Save loopback variable if we have it in order to return user to the page where they came from; default return location is citations
$loopback = 'citations';
if (array_key_exists("loopback", $data)) {
$loopback = $data['loopback'];
}
$getcitationdetails = Citation::where('id', $data['citationid'])->select('id', 'site_id', 'username', 'password', 'login_email', 'login_notes')->first();
$getcitationdetails = json_decode(json_encode($getcitationdetails), true);
$getsitedetails = Site::where('id', $getcitationdetails['site_id'])->select(
'id',
'directory_username',
'directory_password',
'security_questions',
'email_account',
'email_account_password',
'email_account_name',
'google_user',
'google_pwd',
'name_of_google_account'
)->first();
$getsitedetails = json_decode(json_encode($getsitedetails), true);
$response ="";
$response .= '<form action="'.url('/citation-password').'" method="post">
<div class="modal-body">';
if (!empty($getsitedetails['directory_username'])) {
$response .= '<div class="form-group">
<label for="recipient-name" class="col-form-label">Default login credentials for this site:</label>
<p>Username: '.$getsitedetails['directory_username'].'
<br />Password: '.$getsitedetails['directory_password'].'
<br />Email account: '.$getsitedetails['email_account'].'
<br />Email password: '.$getsitedetails['email_account_password'].'
<br />Name on email account: '.$getsitedetails['email_account_name'].'
<br />Default security questions: '.$getsitedetails['security_questions'].'</p>
<p>Gmail account: '.$getsitedetails['google_user'].'
<br />Gmail password: '.$getsitedetails['google_pwd'].'
<br />Name on Gmail account: '.$getsitedetails['name_of_google_account'].'</p>
</div>';
}
$response .= '
<input type="hidden" name="_token" value="'.csrf_token() .'" />
<input type="hidden" name="citation_id" value="'.$data['citationid'].'" />
<input type="hidden" name="loopback" value="'.$loopback.'" />
<div class="form-group">
<label for="recipient-name" class="col-form-label">Username:</label>
<input type="text" class="form-control" name="username" value="'.$getcitationdetails['username'].'" autocomplete="off">
</div>
<div class="form-group">
<label for="message-text" class="col-form-label">Password:</label>
<input type="text" class="form-control" name="password" value="'.$getcitationdetails['password'].'" autocomplete="off">
</div>
<div class="form-group">
<label for="message-text" class="col-form-label">Login email used:</label>
<input type="text" class="form-control" name="login_email" value="'.$getcitationdetails['login_email'].'" autocomplete="off">
</div>
<div class="form-group">
<label for="message-text" class="col-form-label">Login notes:</label>
<textarea class="form-control" style="height:130px;" name="login_notes">'.$getcitationdetails['login_notes'].'</textarea>
</div>
</div>
<div class="modal-footer">
<button type="submit" class="btn btn-success" id="success">Save</button>
<button type="button" class="btn btn-danger" data-dismiss="modal" aria-hidden="true">Cancel</button>
</div>
</form>';
return $response;
} else {
// The popup modal has posted back here; process the data
$data = Request::all();
// Handle & translate loopback; returning user to the page where they came from
$loopback = 'citations';
if ($data['loopback']) {
$loopback = $data['loopback'];
// Translate pages it came from
$trackLoopback = new trackLoopback();
$loopback = $trackLoopback->translate($loopback);
}
$updatecitation = Citation::find($data['citation_id']);
$updatecitation->username = $data['username'];
$updatecitation->password = $data['password'];
$updatecitation->save();
return redirect($loopback)
->with('flash-success', 'Login credentials have been updated successfully!');
}
}
In an effort to isolate the error, I even simplified the form in the controller like this:
public function citationpassword()
{
if (Request::ajax()) {
return '<p>This is the modal form!</p>';
} else {
// The popup modal has posted back here; process the data
$data = Request::all();
// Handle & translate loopback; returning user to the page where they came from
$loopback = 'citations';
if ($data['loopback']) {
$loopback = $data['loopback'];
// Translate pages it came from
$trackLoopback = new trackLoopback();
$loopback = $trackLoopback->translate($loopback);
}
$updatecitation = Citation::find($data['citation_id']);
$updatecitation->username = $data['username'];
$updatecitation->password = $data['password'];
$updatecitation->save();
return redirect($loopback)
->with('flash-success', 'Login credentials have been updated successfully!');
}
}
and also simplified the route to this:
Route::get('/citation-password', 'CitationsController#citationpassword');
but all I get when I click the link is a popup notice, "Error."
I'm not experienced with AJAX. How do I get the form to display in Laravel 5.3?
And/or, how can I change the JavaScript function so that it shows the actual error instead of the "Error" notice? (I tried a number of methods I found on StackOverflow to display errors but all of them resulted in NO error notice; just a blank page. And, I've not been successful at getting my Firefox debugger to show the errors either.)
Thanks!
The correct way to debug the JavaScript is to post the errors this way:
<script type="text/javascript">
$(document).on('click','.getCitationdetails',function(){
var citationid = $(this).data('citationid');
var loopback = $(this).data('loopback');
$.ajax({
url : '/citation-password',
type:'post',
data : {citationid :citationid, loopback :loopback},
success:function(resp){
$('#AppendLoginDetails').html(resp);
$('#LoginCredentialsModal').modal('show');
$('.loadingDiv').hide();
},
error: function(xhr, ajaxOptions, thrownError) {
alert(thrownError + "\r\n" + xhr.statusText + "\r\n" + xhr.responseText);
}
})
})
Once you do so, you will see that the error has to do with missing CsrfToken for the form. [The actual error message is from the Laravel framework: Illuminate\Session\TokenMismatchException: in file /home/reviewsites/moxy53/vendor/laravel/framework/src/Illuminate/Foundation/Http/Middleware/VerifyCsrfToken.php on line 6] Since both the get and post verbs use the same route, Laravel is requiring the CsrfToken before the form with the Csrf field gets generated.
It is possible (but NOT recommended!) to exclude this route from CSRF protection by editing App\Http\Middleware\VerifyCsrfToken.php with the following exception:
/**
* The URIs that should be excluded from CSRF verification.
*
* #var array
*/
protected $except = [
'/citation-password',
];
However, a much better approach is to add the token. It is correct that since you are using a post method to send the data values to the controller, you cannot use the controller to generate the token field in the form. Hence, the solution is to take the html out of the controller and put it in the blade. These lines:
$response .= '<form action="'.url('/citation-password').'" method="post">
<div class="modal-body">';
...
</div>
</form>';
should not be in the $response generated by the controller, but should instead be in the modal div in the blade itself. THEN, you can add the CSRF field in the blade thus:
<form action="{{url('/citation-password')}}" method="post">
{{ csrf_field() }}
<div class="modal-body" id="AppendLoginDetails">
</div>
</form>
I get "CLI stopped working" error when i press the upload button.I used the sample code from one of the website to upload file into the database column. I use Laravel 5.2.39. command used: php artisan serve
Code:(Only test version)
Form.blade.php
<form method="post" enctype="multipart/form-data" action="/upload_file">
{{ csrf_field() }}
<input type="file" name="file" />
<input type="submit" name="submit" value="upload" />
</form>
Routes.php
(Not an ideal place to code this but it is only for file upload test purpose)
Route::get('/upload_form', function()
{
$data['files'] = Attachment::get();
return View::make('form', $data);
});
Route::post('/upload_file', function()
{
$rules = array(
'file' => 'required|mimes:doc,docx,pdf',
);
$validator = Validator::make(Request::all(), $rules);
if(Request::hasFile('file'))
{
$f = Request::file('file');
$att = new Attachment;
$att->name = $f->getClientOriginalName();
$att->file = base64_encode(file_get_contents($f->getRealPath()));
$att->mime = $f->getMimeType();
$att->size = $f->getSize();
$att->save();
return Redirect::to('/upload_form');
}
});
Has anyone encountered this issue? Need help.
I have one form which contains one file upload.
Form Id is "upload_form"
<input type="file" id="image" name="image"/>
Using javascript onclick function and ajax to pass the image to the controller.
Ajax fn:
$.ajax({
url: 'UploadImage',
data:new FormData($("#upload_form")[0]),
type: "post",
dataType:"JSON",
async:false,
success: function (data) {
console.log(data);
}
});
}
Routes:
Routes::post('UploadImage','UploadController#Upload');
UploadController:
public function Upload()
{
$file = Input::file('image');
$tmpFilePath = '/temp/uploads/';
$tmpFileName = time() . '-' . $file->getClientOriginalName();
$path = $tmpFilePath.$tmpFileName;
$data_file = $file->move(public_path() . $tmpFilePath, $tmpFileName);
// Error for move() and getClientOriginalName() functions.
}
use this and it should work for you ... :)
<form action="" method="post" enctype="multipart/form-data">
{{ csrf_field() }}
<input type="file" id="image" name="image"/>
<input type="submit" value="Upload" name="submit">
</form>
Thanks #GONG.
Changed my form to this. Worked.
<form enctype="multipart/form-data" id="upload_form" role="form" method="POST" action="" >