How to pass a data from Javascript to PHP Laravel? - javascript

what I'm trying to do is a function in javascript that sends a simple data to a laravel controller and then upload it to the database, the problem I have is that until now I have not been able to find a way to send this data, always I get error 500.
Laravel Controller:
public function crearRegistro(Request $request){
$registro = new Registro();
$registro->indicador = $request->indicador;
$registro->save();
}
Javasript Function:
$scope.calculoIndicador = function(){
$http.post("/calculoIndicador")
.then(function(response) {
});
$scope.indicador = 5 +5;
alert('Se ha guardado correctamente');
}
view:
<input class="btn btn-success" style="" ng-click="calculoIndicador()"
type="submit" value="Enviar"/>
Route:
Route::post('/calculoIndicador', 'TecnologiaController#crearRegistro');

(First, sorry with my bad english)
I assume that you use Laravel 5.6. On controller you have to use:
$request->all() method to get the data passed to controller via post on javascript. On your code i assume yout want the "indicador", so:
$requestData = $request->all();
$registro->indicador = $requestData['indicador'];
But on your javascript you have to pass "indicador" as parameter on post request data. So, on javascript (or typescript of Angular) post do something like this:
$http.post("/calculoIndicador", {indicador: 'your_data'}).then(
function(response) {
$scope.status = response.status;
$scope.data = response.data;
}, function(response) {
$scope.data = response.data || 'Request failed';
$scope.status = response.status;
}
)
Can you update this page with stack trace of this error?

Related

How to return a view from laravel controller function upon ajax call?

I am working on a bookstore project where books can be added to cart, a user can select many books for adding them to cart. when the user clicks on the Add to Cart button, I am adding the IDs of the selected books in a JS array called cart. When all the selected books are added to the cart then I want to link <a> tag with ajax call that will hit the url of a controller function and will send the JS cart array object to the controller function and then in the controller function, I want to return view to the browser, I do not want the controller function to return the response back to the ajax call but instead I want to return the view to the browser.
Here is the JS function that adds the ID of the selected books to the cart JS array:
function addToCart(id)
{
if(! cart.includes(id) ) cart.push(id);
cartLength.html(cart.length);
$('#successCart'+id).html('Book added to cart.');
}
Here is the <a> tag that calls the ajax function, the function name is showCart():
<a href="#" onclick="event.preventDefault(); showCart();">
<i class="fa fa-shopping-cart"></i>
<span id="cartLength"></span>
</a>
Here is the showCart() function that has ajax code:
function showCart()
{
$.ajaxSetup({
headers: {
'X-CSRF-TOKEN': $('meta[name="csrf-token"]').attr('content')
}
});
$.ajax({
url:"cart",
method:'post',
data:{cart:cart},
dataType: 'html'
})
.done(function(msg){
});
.fail(function(msg){
alert(msg.responseJSON.errors);
});
}
Here is the controller function - I want this function to directly return the view to the browser without sending it back to the ajax call:
public function showCart(Request $request)
{
return view('cart', ['cart' => $request->cart ]); // this should be returned to the browser and not to the ajax call
}
Here is the route for the controller function:
Route::post('/cart', 'HomeController#showCart')->name('home.cart');
EDIT:
I have temporarily solved the issue with the following tricks but that is not a permanent solution:
After calling the showCart() function from ajax for sending the cart array variable from js to laravel controller, I used the following logic to store the books in a session variable whose ids are stored in the cart array:
public function showCart(Request $request)
{
session()->put('cart_books', Book::whereIn('id', $request->cart)->get());
session()->save();
return "success";
}
After storing the result of the query in a session variable, I created another GET route for /cart as below:
Route::get('/cart', 'HomeController#viewCart');
Then upon success of the post ajax call, I called /cart with get method as below:
.done(function(msg){
console.log('calling cart');
location.href = "cart"; // Here I call the `/cart` with `get` method which will hit the `viewCart()` function of HomeController which will return the view back to the browser along with the results that were stored in the session variable.
})
And this is the viewCart() controller function that returns the view to the browser and sends the session variable's data to the view:
public function viewCart()
{
$random_books = Book::all()->random(4);
$categories = Category::all();
return view('cart', ['cart_books' => session()->get('cart_books'),
'random_books' => $random_books, 'categories' => $categories]);
}
I want the controller function to return the view to the browser without returning it to the ajax call, any help is appreciated in advance.
You can return Raw html from ajax call by rendering and returning the view inside your controller as,
return view('cart', ['cart' => $request->cart])->render();
This will return the raw HTML and you can further use it. However, returning HTML from ajax is not a good way, You can return JSON from the controller and render the view in frontend according to the JSON data.
As the others said you can use
return view('cart', ['cart' => $request->cart])->render();
and in you jQuery do
.done(function(response){
document.write(response);
});
Or you can return the link that its content should be shown to the user and redirect the user in your done method. So in your back-end you'll have
return route('cart', ['cart' => $request->cart]);
and in your front-end you'll have
.done(function(response){
location.href = response;
});
In the controller function just add render method like the following line
public function showCart(Request $request)
{
return view('cart', ['cart' => $request->cart ])->render();
}
For js:
$.ajax({
method: 'POST', // Type of response and matches what we said in the route
url: '{{ route('home.cart') }}', // This is the url we gave in the route
data: {'cart' : cart}, // <-- this is your POST data
success: function(response){ // What to do if we succeed
console.log(response);
},
error: function(jqXHR, textStatus, errorThrown) { // What to do if we fail
console.log(JSON.stringify(jqXHR));
console.log("AJAX error: " + textStatus + ' : ' + errorThrown);
}
});
You're doing a XHR, so you shouldn't return the whole HTML view from your controller unless you plan to replace your existing element with the returned HTML, like how you're doing with addToCart. What you need here is a redirection after your POST, and your temporary solution isn't actually a bad solution :) Here's a similar question as yours with the same answer. In fact, I highly recommend your temporary solution over the alternative solution below.
Since you wish to use the view returned from your controller without returning it to your ajax, a rather unorthodox approach would be to POST through a <form>. You can dynamically create a <form>, with the <input>s of your data, and submit.
function postData(actionUrl, method, data) {
var mapForm = $('<form id="mapform" action="' + actionUrl + '" method="' + method.toLowerCase() + '"></form>');
for (var key in data) {
if (data.hasOwnProperty(key)) {
mapForm.append('<input type="hidden" name="' + key + '" id="' + key + '" value="' + data[key] + '" />');
}
}
$('body').append(mapForm);
mapForm.submit();
}
function showCart()
{
postData('cart', 'post', cart);
}
I borrowed the above code from here. You can do the same with vanilla JS too.

Ajax returning empty string in Django view

I am developing a web application through Django and I want to get information from my javascript to a view of Django in order to access to the database.
I am using an ajax call as this post shows.
I am calling the js in html by an onclick event :
sortedTracks.html
...
<form action="{% url 'modelReco:sortVideo' video.id %}">
<input type="submit" value="Validate" onclick="ajaxPost()" />
</form>
...
clickDetection.js
//defined here
var tracksSelected = [];
//function that fill tracksSelected
function tagTrack(track_num){
if(tracksSelected.includes(track_num)){
var index = tracksSelected.indexOf(track_num);
tracksSelected.splice(index, 1);
}else{
tracksSelected.push(track_num);
}};
//ajax function
function ajaxPost(){
$.ajax({
method: 'POST',
url: '/modelReco/sortedTracks',
data: {'tracksSelected': tracksSelected},
success: function (data) {
//this gets called when server returns an OK response
alert("it worked! ");
},
error: function (data) {
alert("it didnt work");
}
});
};
So the information I want to transfer is tracksSelected and is an array of int like [21,150,80]
views.py
def sortedTracks(request):
if request.is_ajax():
#do something
print(request)
request_data = request.POST
print(request_data)
return HttpResponse("OK")
The ajax post works well but the answer I get is only an empty Query Dict like this :
<QueryDict: {}>
And if I print the request I get :
<WSGIRequest: GET '/modelReco/sortedTracks/?tracksSelected%5B%5D=25&tracksSelected%5B%5D=27&tracksSelected%5B%5D=29'>
I have also tried to change to request_data=request.GET but I get a weird result where data is now in tracksSelected[]
I've tried to know why if I was doing request_data=request.GET, I get the data like this tracksSelected[] and get only the last element of it.
And I found a way to avoid to have an array in my data (tracksSelected) on this link
This enables me to have :
in views.py
def sortedTracks(request):
if request.is_ajax():
#do something
print(request)
request_data = request.GET.getlist("tracksSelected")[0].split(",")
print(request_data)
and in clickDetection.js
function ajaxPost(){
tracksSelected = tracksSelected.join();
$.ajax({
method: 'POST',
url: '/modelReco/sortedTracks',
data: {'tracksSelected': tracksSelected},
success: function (data) {
//this gets called when server returns an OK response
alert("it worked! ");
},
error: function (data) {
alert("it didnt work");
}
});
};
This little trick works and I am able to get the array data like this,
print(request_data) returns my array such as [21,25,27]
Thank you for helping me !
According to me to access the data which is sent in the ajax request can be directly accessed .
For Example:
def sortedTracks(request):
if request.method == 'POST':
usersV = request.POST.get('tracksSelected')[0]
for users in usersV:
print users
return HttpResponse("Success")
else:
return HttpResponse("Error")
The correct syntax is data: {tracksSelected: tracksSelected},

How to search item in database if not found in object in angular.js?

Trying to make ajax request when searched data is not found in object.
Html:-
Search programming languages: <input type="Text" ng-model="out.pl">
<div ng-controller="MyContRollEr">
<table border="2">
<tr>
<td>Programming Language:</td>
<td>Percentage:</td>
<td>Salary:</td>
<td>People:</td>
<td>Started Date:</td>
</tr>
<tr ng-repeat="data in info | filter:out">
<td>{{data.pl}}</td>
<td>{{data.percent}}</td>
<td>{{data.salary |currency:'Rs.'}}</td>
<td>{{data.people | number :2}}</td>
<td>{{data.date | date:"yyyy/MM/dd"}}</td>
</tr>
</table>
Controller:-
var app = angular.module('app',[]);
app.controller('MyContRollEr',function($scope) {
var info = [
{pl:'php',percent:'10%',salary:10000000,people:234524},
{pl:'Java',percent:'20%',salary:9822200,people:234443},
{pl:'python',percent:'10%',salary:8739300000,people:2345521)},
];
$scope.info = info;
});
My Function :-
function sendRequest(){
$http({
method:'POST',
url:'index.php',
data:{search:'data'}
}).then(function(data) {
$scope.out = data;
})
}
How to do this combining my controller, function and model.
,This is where angular service comes into play. You should make a new file for both controllers and services. For the sake of simplicity though, you can just add the following code into your current file AFTER the controller.
app.service('myService',function($http) {
this.sendRequest = function() {
$http({
method:'POST',
url:'index.php',
data:{search:'data'}
}).then(function (response) {
console.log(response);
return response.data; // Most APIs have the "data" in the response object. But you can take this out if the console log doesn't show that key in the object.
})
}
)
Once that is done, you'll inject your service into your controller here:
app.controller('MyContRollEr',function($scope, myService) { // Notice that the service is a parameter in controller now.
Next, lets call do the POST by hitting the service. Inside of your controller block, write the following:
myService.sendRequest().then(function (response) {
console.log(response);
})
If you aren't using Gulp (or something similar), then you will need to add the service into your index.html(Or whatever file is your base html file) file just like you did(I assume) with your controller.
Let me know if you have any questions!

AngularJs not rendering value

I am new to AngularJS and need to use AngularJs to render my MVC controller Json output. Below is my MVC Controller that output Json:
[HttpGet]
public JsonResult GetAllData()
{
int Count = 50;
return Json(Workflow.Teacher.GetTeachers(Count), JsonRequestBehavior.AllowGet);
}
My Angular Controller that calls the GetAllData Action method:
angular.module('myFormApp', [])
.controller('HomeController', function ($scope, $http, $location, $window) {
$scope.teacherModel = {};
$scope.message = '';
$scope.result = "color-default";
$scope.isViewLoading = false;
$scope.ListTeachers = null;
getallData();
//******=========Get All Teachers=========******
function getallData() {
$http({
method: 'GET',
url: '/Home/GetAllData'
}).then(function successCallback(response) {
// this callback will be called asynchronously
// when the response is available
$scope.ListTeachers = response;
console.log($scope.ListTeachers);
}, function errorCallback(response) {
// called asynchronously if an error occurs
// or server returns response with an error status.
$scope.errors = [];
$scope.message = 'Unexpected Error while saving data!!';
console.log($scope.message);
});
};
})
.config(function ($locationProvider) {
$locationProvider.html5Mode(true);
});
Further my MVC layout markup is bellow:
#{
Layout = "~/Views/Shared/_Layout.cshtml";
}
<h2>Teachers List</h2>
<div id="content" ng-controller="HomeController">
<span ng-show="isViewLoading" class="viewLoading">
<img src="~/Content/images/ng-loader.gif" /> loading...
</span>
<div ng-class="result">{{message}}</div>
<table class="table table-striped">
<tr ng-repeat="teacherModel in ListTeachers">
<td>{{teacherModel.TeacherNo}}</td>
<td>{{teacherModel.TeaFName}}</td>
<td>{{teacherModel.TeaSName}}</td>
</tr>
</table>
</div>
#section JavaScript{
<script src="~/Scripts/angular.js"></script>
<script src="~/ScriptsNg/HomeController.js"></script>
}
further to above my main layout's body tag also have ng-app
<body ng-app="myFormApp" >
I am using MVC version 5 with AngularJs v1.6.4.
On debugging I can confirm that it does call getallData() actionMethod and does return rows in Json. I am not getting any error but its not rendering the model values either.
Any suggestions would be appreciated.
use response.data to catch the data.
change
$scope.ListTeachers = response;
to this
$scope.ListTeachers = response.data;
You have a number of problems with this code. Firstly, by assigning
$scope.ListTeachers = null;
you are making it more complicated to work with this variable later. If you expect REST interface to return you an array, then it is fine to make initial assignment as an empty array.
$scope.ListTeachers = [];
It is important because you should not override this object when you get a new result back. Angular adds its own magic to objects it is bound to, and by overriding an object you destroy that magic.
How you should update the data is something like this this:
then(function successCallback(response) {
// this callback will be called asynchronously
// when the response is available
$scope.ListTeachers.length = 0;
if( response && response.data){
response.data.forEach(function callback(currentValue)
{
$scope.ListTeachers.push(currentValue);
});
}
console.log($scope.ListTeachers);
}
I hope this helps.
Then callback response has several parameters like data , headers, status , statustext to check your request.

How can i post the ngCart checkout button on http using php and angular js?

I do not know how can i post my data's into a new php page and this is my code:
<ngcart-checkout service="http" settings="{ url:'./checkout.php' }">Checkout </ngcart-checkout>
but the original code from the ngCart docs is
<ngcart-checkout service="http" settings="{ url:'/checkout' }"></ngcart-checkout>
the ngcart-checkout code is
<button class="btn btn-primary" ng-click="checkout()" ng-disabled="!ngCart.getTotalItems()" ng-transclude>Checkout</button>
still it does not redirect me unto checkout.php and so i go to the ngcart.js and the codes for the checkout using http post is
.service('ngCart.fulfilment.http', ['$http', 'ngCart', function($http, ngCart){
this.checkout = function(settings){
return $http.post(settings.url,
{data:ngCart.toObject()})
}
}])
so again my problem was how can i redirect my checkout button unto the checkout.php and how can i post those items unto the checkout.php using http post?
I think perhaps you are looking for something like this in your ngcart.js file
<script>
.service('ngCart.fulfilment.log', ['$http', 'ngCart', function($http, ngCart){
this.checkout = function(settings){
//var item_data = ngCart['$cart']['items'], message;
//return $http.post('checkout.php',
// {data:item_data});
var postData = 'item_data='+JSON.stringify(ngCart['$cart']['items']);
$http({
method : 'POST',
url : 'checkout.php',
data: postData,
headers : {'Content-Type': 'application/x-www-form-urlencoded'}
}).success(function(res){
console.log(res);
}).error(function(error){
console.log(error);
});
}
}])</script>

Categories

Resources