In my laravel 5.4 app, i have a crud module. for the edit bit, the data is rendered in a bootstrap modal. the data is pulled successfully but on hitting the update button, the error shown is returned.
here's my blade form that's rendered in the modal:
<form id="formEdit" class="form-horizontal" role="form" method="put">
//form elements
</form>
here's the ajax that handles it:
//edit_id is defined globally
$('#updateClass').click(function(){
var name = $("#formEdit #name").val();
var status = ($('#formEdit #status').prop("checked") == true) ? 1 : 0;
var token = $('meta[name="csrf-token"]').attr('content');
var id = edit_id;
var url = "classes/update/"+id;
var formdata = {
'name' : name,
'status' : status,
'_token' : token
};
$.ajax({
method: "PUT",
url: url,
data: formdata,
dataType: "json"
})
.done(function(data) {
//
})
.fail(function(data) {
//
});
});
});
updateClass is the button that displays the edit form on the modal..
here's my routes in web.php:
Route::resource('classes', 'ClassesController');
Route::group(['prefix' => 'admin'], function () {
Route::get('classes', 'ClassesController#index');
Route::get('classes/edit/{id}', 'ClassesController#edit');
Route::put('classes/update/{id}', 'ClassesController#update');
});
and finally, my update function in the classes controller:
public function update(Request $request, $id)
{
$validator = $this->validator($request->all());
$errors = $validator->errors();
$errors = json_decode($errors);
if ($validator->passes())
{
Dl_class::find($id)->update($request->all());
return response()->json();
}
else
{
return response()->json($errors, 422);
}
}
what i'm i missing?
To send PUT request from form you need to send a hiddne input element named as method. Something like this:
<input type='hidden' name='_method' value='PUT'>
there is a helper method to do the same like:
{{ method_field('PUT') }}
Only then Laravel can recognize your PUT request.
Or alternatively, you can enclose this value to your ajax call also Something like:
var formdata = {
'name' : name,
'status' : status,
'_token' : token,
'_method' : 'PUT'
};
Related
I've Signup form in my website. It was properly submitting before. Now I wanted to submit my form using ajax and wanted to return a variable from controller into JSON that I will use into blade file.
The form is submitting and values are showing into database but after redirection, it returns error.
Undefined variable: seller in report blade
I tried to decode my variable to make it work but still the same error.
How would I make it work?
Report-Blade
#foreach(json_decode($seller, true) as $row)
<a href="{{route('Report', $row->id) }}" >
{{ __('Show Report of ')}} {{$row->car_title}}
</a>
#endforeach
Controller
$seller = Sellers::take(1)->latest()->get();
return response(view('report',array('seller'=>$seller)),200, ['Content-Type' =>
'application/json']);
JavaScript
$("#submit-all").click(function(e){
e.preventDefault();
var _token = $('input[name="_token"]').val();
$.ajax({
type: "post",
url: "{{ route('form_for_private_sellers') }}",
data : $('#msform').serialize() + "&_token=" + _token,
dataType: 'JSON',
beforeSend: function(){
// Show loading image
$("#se-pre-con").show();
},
success: function(data) {
window.location = "http://127.0.0.1:8000/report/";
},
complete:function(data){
// Hide loading image
$("#se-pre-con").hide();
}
});
});
As understood from your comments,
window.location = "http://127.0.0.1:8000/report/";
will hit the route
Route::get('/report', function () {
return view('report');
})->name('private_seller_report');
Report blade expects a variable named $seller, and it is not being sent from the route. You would need to change the route to something similar to this:
Route::get('/report', function () {
$sellers = Seller::get(); //your logic
return view('report', ['seller' => $sellers]);
})->name('private_seller_report');
Alternatively you can point the route to a method in a controller if you want to avoid bulking up your routes.
you need two route for this
first for rendering blade
return view('report');
and the second for fetch seller
$seller = Sellers::latest()->take(1)->get();
return $seller
I have a grid in which all users are shown. the grid is created and shown by ajax , it has 3 buttons: add, edit, remove. I can add and delete, but since in the update.blade.php I have the user image ( which is shown by a route and controller like : <img src="{{ route('userimage',['id' => $pass_the_id ])}}"/>, the problem now is how do I pass variable like $pass_the_id that I'm about to use in the view blade?
This is the code that brings up the modal ( when edit button which is right in front of user name and id is clicked. I can get user name, family and so on and show it in the modal, but how do I pass the $id to the image route that I mentioned above?
$('body').delegate('#student-info #edit','click',function (e) {
var id = $(this).data('id');
$.get("{{ URL::to('student/edit') }}",{id:id},function (data) {
$('#frm-update').find('#id').val(data.id);
$('#frm-update').find('#name').val(data.name);
$('#frm-update').find('#family').val(data.family);
$('#frm-update').find('#username').val(data.username);
$('#frm-update').find('#birth_date').val(data.birth_date);
$('#frm-update').find('#phone').val(data.cell_phone);
$('#frm-update').find('#email').val(data.email);
$('#frm-update').find('#gender').val(data.gender);
$('#student-update').modal('show');
})
})
here is the Laravel Controller function that is called on URL::to('student/edit') which I have mentioned in the above $.get code :
public function edit(Request $request) {
if($request->ajax()) {
$contact = User::find($request->id);
return response($contact);
}
}
the responsibility of above controller function which is called during $.get is to get the information based on the id that I have passed. ( my grid already shows each user id in the the grid table I've created. but I don't know how to pass it to the src="{{ route('userimage',['id' => $pass_the_id ])}}"
here is what userimage route is doing: below is the route:
Route::get('userimage/{id}','ImageController#showimage')->name('userimage');
and this is its code:
public function showimage($id) {
if(UserImages::selectuserimage($id) !== null) {
$imageData = UserImages::selectuserimage($id);
$info = $info = base64_decode($imageData);
$img = Imgs::make($info);
$img->encode('jpg',80);
return $img;
}
else return public_path('images/Atehran.jpg');
}
On Ajax Success call to pass data to view with return response() in laravel this is the simple way with an example -
js function
$(document).on('change', '[name="abc_field"]', getCitiesByState);
function yourAjaxCall() {
var data_to_pass = $(`[name='get_data_selector']`).val();
var $selector = $(`[name='selector']`);
$.ajax({
url: route('your_route'),
type: 'GET',
data: {
data: data_to_pass
},
dataType: "json",
success: function success(data) {
$selector.empty().append(data);
},
});
}
call to controller from ajax call
public function your_route_function()
{
$result = Abc::where('column',request('data'))->get();
return response()->json([
'result' => view('viewfilename.fields._option', ['options' => $result])->render(),
]);
}
view path "resources\viwes\viewfilename\fields_option.blade" to render
<option value="">{{ $defaultText or 'Select' }}</option>
#foreach($options as $value => $name)
<option value="{{ $value }}">{{ $name }}</option>
#endforeach
Hope this will help you to render view through ajax call.
I am trying to save to a database in yii2 using ajax but I am getting errors. I just want to insert the value or rate which is "up" into the database and I don't want to use a form, just on-click of a button.
This is my controller
public function actionThumbs()
{
$thumbs = new Thumbs;
$thumbs->user = Yii::$app->user->identity->email;
$thumbs->topic_id = Yii::$app->getRequest()->getQueryParam('id');
$thumbs->rate = $_POST["rate"];
if ($thumbs->load(Yii::$app->request->post()) ) {
$thumbs->load($_POST);
$thumbs->save();
return $this->redirect(['blog', 'id' => Yii::$app->getRequest()->getQueryParam('id')]);
}
return $this->redirect(['blog','id' => Yii::$app->getRequest()->getQueryParam('id')]);
}
This is my this is my ajax file
$("#mys").click(function() {
var rate = "up";
$.ajax({
type: 'POST',
url: 'vot/frontend/web/index.php?r=site%2Fthumbs',
data: 'rate='+rate,
success: function (rate) {
alert("test");
},
error: function (exception) {
alert(exception);
}
});
});
the view
<div>
<?= Html::Button('ups', ['class' => 'btn btn-primary', 'name' => 'mys' ,'id'=>'mys']) ?>
</div>
I get this alert error
The page at localhost says":
"[object Object]"
By default Yii2 controller doesn't accept POST request without _csrf protection, so there are 2 ways here:
1 - disable csrf:
public function actionThumbs() {
$this->enableCsrfValidation = false;
//your code here
}
2 - Send post request via ajax with _csrf token:
In your layout/main.php file, put this: <?= Html::csrfMetaTags() ?>
Before your "ajax" code, call this:
$.ajaxSetup({
headers: {
'X-CSRF-TOKEN': $('meta[name="_token"]').attr('content')
}
});
//Your ajax code here
The function below is called through a POST request. I need to retrieve URL from my database and open the link in a new tab. I'm using the Redirect::away() function for this. But it gives a MethodNotAllowedHttpException. I have tried calling this function in a GET request and it works perfectly fine.
public function generateURL(Request $request) {
$screenRow = \App\ScreenshotRow::find($request->input('row_ID'));
$baseURL = $screenRow->BaseURL;
$screenshot = \App\Screenshot::where('Setname', '=', $screenRow->Setname)->get();
$pageURL = $screenshot[0]['PageURL'];
if ($baseURL == "") {
return Redirect::away($PageURL);
}
else
return Redirect::away($baseURL);
}
Is there any way to calling this function in response to a POST request?
I would simply use an Ajax Form and redirect the User with Javascript.
Make sure to give your Form an ID
<form id="myForm" method="POST" action="{{ route('your.route') }}">
...
...
<button type="submit">Submit the Form</button>
And make this Form working with Ajax
<script>
$('#myForm [type="submit]').click(function(e){
e.preventDefault();
var form = jQuery(this).parents("form:first");
var dataString = form.serialize();
var formAction = form.attr('action');
$.ajax({
type: "POST",
url : formAction,
data : dataString,
success : function(data){
var url = $.parseJSON(data.responseText);
console.log(data);
// Redirect to a new tab with the given url
window.open(url.success, '_blank');
},
error : function(data){
var error = $.parseJSON(data.responseText);
console.log(error);
// Do what ever you want with an Error Message
alert(error)
}
},"json");
});
</script>
Okay - So if the Form receives a success Message, the success function is executed, otherwise the error function.
Lets go to the Backend Controller which handles the Request
public function generateURL(Request $request) {
$screenRow = \App\ScreenshotRow::find($request->input('row_ID'));
$baseURL = $screenRow->BaseURL;
$screenshot = \App\Screenshot::where('Setname', '=', $screenRow->Setname)->get();
$pageURL = $screenshot[0]['PageURL'];
// Return a JSON Success Message with a Success HTTP Status Code
if ($baseURL == "") {
return response()->json(['success' => $PageURL], 200);
}
// Return a JSON Error Message with a Error HTTP Status Code
else
return response()->json(['error' => $baseURL], 400);
}
Now if your Backend throws a Success Message the success function of the Ajax Form is called which redirects to a new tab based on the given url which you passed in your Backend Controller Success Response.
NOTE
To avoid the tokenmismatchexception on an Ajax Request, you should add the csrf_token to your meta Section in your <head>.
<meta name="csrf-token" content="{{ csrf_token() }}">
And fetch this csrf_token on every Form Request
$.ajaxSetup({
headers: {
'X-CSRF-TOKEN': $('meta[name="csrf-token"]').attr('content')
}
});
I'm to trying to store a sort order to each article within a help centre for my new site using Laravel 5 and having a bit of trouble getting it to work. I'm using jQuery UI's .sortable for arranging the elements on the page, and since there are going to be multiple sections throughout the site where areas are sortable, my jQuery script is built in a way for a 'one script for all' purposes. Hence the use of data-* attributes and route name references.
Here is the code I've got so far:
routes.php
Route::post('admin/help-centre/category/{category_id}/section/{section_id}/article/sort-order', 'AdminHelpCentreArticleController#sortOrder');
AdminHelpCentreArticleController.php
public function sortOrder($category_id, $section_id)
{
/* Return ------------------------------------- */
return [
'category_id' => $category_id,
'section_id' => $section_id
];
}
show.blade.php (Admin Article Listing)
<ul id="help-center-articles-sort" class="sortable">
#foreach ($helpCentreArticles as $helpCentreArticle)
<li class="sortable-element" data-sortable-element-id="{{ $helpCentreArticle->id }}">
{{ $helpCentreArticle->title }}
</li>
#endforeach
</ul>
Save Order
scripts.js (includes CSRF Token _token)
var csrfToken = $('meta[name="csrf-token"]').attr('content');
$.ajaxPrefilter(function(options, originalOptions, jqXHR) {
if (options.type.toLowerCase() === 'post')
{
options.data += options.data?'&':''; // add leading ampersand if `data` is non-empty
options.data += '_token=' + csrfToken; // add _token entry
}
});
$(document).ready(function() {
$('.sortable').sortable();
$('.sortable-save').on('click', function(e) {
e.preventDefault();
var route = $(this).attr('href'),
sortableID = $(this).attr('data-sortable-id');
var data = $('#' + sortableID + ' .sortable-element').map(function() {
return $(this).attr('data-sortable-element-id');
}).get();
$.ajax({
type: 'POST',
url: route,
dataType: 'json',
data: { id_array: data },
success: function(data) {
console.log(data);
}, error: function(data) {
console.log(data);
},
});
});
});
Everything so far is working in terms of the return response in the console, which is Object {category_id: "1", section_id: "1"}. But no matter what I try, I cannot seem to pass through the data map to the controller to use it.
I've tried a bunch of guesswork since I cannot find a single decent tutorial on AJAX in Laravel 5 anywhere, and I've tried things such as adding a $data parameter to the sortOrder() method, I've tried Input::all() and Request::all but it all returns errors (I'm guessing cause it's not an actual form?).
Once I've got the data to be passed through to the controller I'll be able to save the sort order to the database easily enough. But I can't quite get to that stage, any ideas?
EDIT
I should probably note that I do have a HelpCentreArticle model and a HelpCentreArticleRequest request too, here's some of the code from each file in case they are also needed:
HelpCentreArticle.php
class HelpCentreArticle extends Model {
protected $fillable = [
'category_id',
'section_id',
'title',
'content',
'excerpt',
'is_visible',
'sort_order',
'created_by',
'updated_by',
];
}
HelpCentreArticleRequest.php
class HelpCentreArticleRequest extends Request {
/* Authorization ------------------------------ */
public function authorize()
{
return true;
}
/* Validation rules --------------------------- */
public function rules()
{
$rules = [
'title' => 'required|min:3',
'content' => 'required|min:10',
];
return $rules;
}
}
I wasn't sure if I needed to add HelpCentreSectionRequest $request as the last parameter of the sortOrder() method, so I could use $request->all() but it just returns a 422 (Unprocessable Entity) in the console log.
So it appears that the correct way was to use Input::get('id_array'); instead of $_POST['id_array'];, which I tried, but when I originally tried this I wasn't including use Input; at the top of my controller, as I thought this was already accessible, but it wasn't.
Adding use Input;, and using Input::get(); is now working as expected.
Here is the updated code:
AdminHelpCentreArticleController.php
public function sortOrder($category_id, $section_id)
{
/* Query Select ------------------------------- */
$helpCentreCategory = HelpCentreCategory::findOrFail($category_id);
$helpCentreSection = HelpCentreSection::findOrFail($section_id);
/* Variables ---------------------------------- */
$id_array = Input::get('id_array');
$sort_order = 1;
/* Query Update ------------------------------- */
foreach($id_array as $id) {
$helpCentreArticle = HelpCentreArticle::where('id', $id)->first();
$helpCentreArticle->sort_order = $sort_order;
$helpCentreArticle->save();
$sort_order++;
}
/* Return ------------------------------------- */
return ['success' => true];
}
Then you can obviously access success for an if else statement in your jQuery to manipulate the page.
My implementation of UI sortable with Laravel
index.blade.php
...
#foreach($photos as $photo)
<tr data-sortable="{{ $photo->pivot->position }}" data-id="{{ $restaurant->id }}" data-photo-id="{{ $photo->pivot->photo_id }}">
<td>
<i class="fa fa-sort" aria-hidden="true"></i>
</td>
...
</tr>
#endforeach
<script type="text/javascript">
$("#sortable-ui tbody").sortable({
helper: fixHelper,
update: function(event, ui) {
$("#sortable-ui tbody tr").each(function(index){
console.log($(this).data('id')+', '+(index+1));
$.ajax({
url: '{{ route('owner.photo.update.position') }}',
type: 'POST',
data: 'restaurant_id='+$(this).data('id')+'&photo_id='+$(this).data('photo-id')+'&position='+(index+1)
})
.done(function (response) {
console.log(response);
})
.fail(function (jqXhr) {
console.log(jqXhr);
});
});
}
}).disableSelection();
</script>
scripts.js
$.ajaxSetup({
headers: {
'X-CSRF-TOKEN': $('meta[name="csrf-token"]').attr('content')
}
});
AjaxController.php
public function updatePhotoPosition(Request $request)
{
$restaurant = $this->restaurantRepository->getById($request->get('restaurant_id'));
$photoId = $request->get('photo_id');
$photo = $restaurant
->photos()
->wherePivot('photo_id', $photoId)
->first();
$photo->pivot->position = $request->get('position');
$photo->pivot->save();
}