Make AJAX call in AngularJS in Cordova App - ajax

I have built an app using Ionic Framework, AngularJS, and Cordova. In it, I have made AJAX calls to several php files using $http.get(), which works perfectly in a browser, but not within the app. The app is able to render internet pages through an iframe so the network is working. I have whitelisted my server where the php files reside inside of the app.js file and using . Also, in my php files I've added header('Access-Control-Allow-Origin: *');
Any suggestions on how to get this AJAX call to work?
.controller('StuffCtrl', function($scope, StuffService, LoadingService) {
StuffService.getStuff().then(function(data) {
LoadingService.show();
$scope.stuff = data;
LoadingService.hide();
});
})
.service('StuffService', function($http){
var myStuff;
return {
getStuff: function(){
return $http.get('http://mydomain/stuff.php').then(function(items) {
myStuff = items.data; return myStuff;
});
}
});
});

I had the same error while working on a hybrid app and then I added these lines in my route config function and it started working
$httpProvider.defaults.useXDomain=true;
delete $httpProvider.defaults.headers.common['X-Requested-With'];
This is to enable CORS.
More info on the same can be found here

Add a catch handler to get the error :
StuffService.getStuff().then(function(data) {
LoadingService.show();
$scope.stuff = data;
LoadingService.hide();
}).catch(function(error){
$scope.error = error;
});
And pretty display the error :
<pre>{{error|json}}</pre>
This should tell you what is going on.

Related

How could be Laravel Socialite be integrated with a SPA?

I know we have the stateless() and and getTargetUrl() methods, than i am trying this at my controller:
public function socialRedirect($provider){
return Socialite::with($provider)->stateless()->redirect()->getTargetUrl();
}
The problem is that in my SPA front end, i can't make a sucessfull request to the provided url as like in the code below:
async facebookLogin() {
try {
const url = await this.$axios.$get('/auth/social/facebook')
this.$axios.$get(url)
} catch (error){
console.log(error)
}
},
I get CORS related stuff errors:
OPTIONShttps://www.facebook.com/v3.3/dialog/oauth?client_id=240805606930310&redirect_uri=http://localhost:8000/api/auth/social/facebook/callback&scope=email&response_type=code
CORS Missing Allow Origin
What am i doing wrong? I am specially confused since i can access the URL by copying it and pasting in another browser tab, but i can't sucessfully make the AJAX request to it.

How to use MVC Bundling + Service Worker Cache

Problem
If I load the page without a service worker, everything is fine but when I introduce a service worker, the page does not load the first time (when online) because it is missing my bundled files which causes both CSS and Script issues. If I refresh the page then everything works because the service worker caches fetch requests when they occur.
Setup
Say I have a bundle such as
bundles.Add(new ScriptBundle("~/js/main").Include(
"~/Scripts/jquery-3.3.1.min.js",
"~/Scripts/moment.min.js",
"~/node_modules/sweetalert/dist/sweetalert.min.js"));
and a service worker in my root directory such as
var cacheName = 'v1:static';
self.addEventListener('install', function (e) {
e.waitUntil(
caches.open(cacheName).then(function (cache) {
return cache.addAll([
'/images/keypad/number 0.png',
'/',
'/Menu/MainMenu',
'**TODO: Cache Bundles**'
]).then(function () {
self.skipWaiting();
});
})
);
});
self.addEventListener('fetch', function (event) {
if (event.request.method != "POST") {
event.respondWith(
caches.match(event.request).then(function (response) {
if (response) {
return response;
}
fetch(event.request).then(function (fetchResponse) {
caches.open(cacheName).then(function (cache) {
cache.put(event.request, fetchResponse.clone());
});
return fetchResponse;
});
})
);
}
});
Question
How do I cache my bundled files in my service worker, in both Debug and Release mode because debug displays them as individual files while Release will combine them, and I don't know the URLs to the bundles?
Additional Thoughts
You can't put a Razor #... in this file because it isn't cshtml.
I don't want to list every file out in both places and maintain both.
I thought about using a server side handler to generate my service-worker.js file but I was wondering if there is an actual clean way to do this without going crazy.
Thank You!
#Scripts.Url("~/bundles/yourBundleName") use this to get the absolute URL for the URL from there you can get the bundle name map that into a variable and use that variable in service worker install event so that assets are cached on load itself.
note:
one mistake which i used to do Also please don’t refer serviceworker.js file directly in to index.html, this will be loaded at the time of registering from sw-registration.js file

a file upload progress bar with node (socket.io and formidable) and ajax

I was in the middle of teaching myself some Ajax, and this lesson required building a simple file upload form locally. I'm running XAMPP on windows 7, with a virtual host set up for http://test. The solution in the book was to use node and an almost unknown package called "multipart" which was supposed to parse the form data but was crapping out on me.
I looked for the best package for the job, and that seems to be formidable. It does the trick and my file will upload locally and I get all the details back through Ajax. BUT, it won't play nice with the simple JS code from the book which was to display the upload progress in a progress element. SO, I looked around and people suggested using socket.io to emit the progress info back to the client page.
I've managed to get formidable working locally, and I've managed to get socket.io working with some basic tutorials. Now, I can't for the life of me get them to work together. I can't even get a simple console log message to be sent back to my page from socket.io while formidable does its thing.
First, here is the file upload form by itself. The script inside the upload.html page:
document.getElementById("submit").onclick = handleButtonPress;
var httpRequest;
function handleResponse() {
if (httpRequest.readyState == 4 && httpRequest.status == 200) {
document.getElementById("results").innerHTML = httpRequest.responseText;
}
}
function handleButtonPress(e) {
e.preventDefault();
var form = document.getElementById("myform");
var formData = new FormData(form);
httpRequest = new XMLHttpRequest();
httpRequest.onreadystatechange = handleResponse;
httpRequest.open("POST", form.action);
httpRequest.send(formData);
}
And here's the corresponding node script (the important part being form.on('progress')
var http = require('http'),
util = require('util'),
formidable = require('formidable');
http.createServer(function(req, res) {
if (req.url == '/upload' && req.method.toLowerCase() == 'post') {
var form = new formidable.IncomingForm(),
files = [],
fields = [];
form.uploadDir = './files/';
form.keepExtensions = true;
form
.on('progress', function(bytesReceived, bytesExpected) {
console.log('Progress so far: '+(bytesReceived / bytesExpected * 100).toFixed(0)+"%");
})
.on('file', function(name, file) {
files.push([name, file]);
})
.on('error', function(err) {
console.log('ERROR!');
res.end();
})
.on('end', function() {
console.log('-> upload done');
res.writeHead(200, "OK", {
"Content-Type": "text/html", "Access-Control-Allow-Origin": "http://test"
});
res.end('received files: '+util.inspect(files));
});
form.parse(req);
} else {
res.writeHead(404, {'content-type': 'text/plain'});
res.end('404');
}
return;
}).listen(8080);
console.log('listening');
Ok, so that all works as expected. Now here's the simplest socket.io script which I'm hoping to infuse into the previous two to emit the progress info back to my page. Here's the client-side code:
var socket = io.connect('http://test:8080');
socket.on('news', function(data){
console.log('server sent news:', data);
});
And here's the server-side node script:
var http = require('http'),
fs = require('fs');
var server = http.createServer(function(req, res) {
fs.createReadStream('./socket.html').pipe(res);
});
var io = require('socket.io').listen(server);
io.sockets.on('connection', function(socket) {
socket.emit('news', {hello: "world"});
});
server.listen(8080);
So this works fine by itself, but my problem comes when I try to place the socket.io code inside my form.... I've tried placing it anywhere it might remotely make sense, i've tried the asynchronous mode of fs.readFile too, but it just wont send anything back to the client - meanwhile the file upload portion still works fine. Do I need to establish some sort of handshake between the two packages? Help me out here. I'm a front-end guy so I'm not too familiar with this back-end stuff. I'll put this aside for now and move onto other lessons.
Maybe you can create a room for one single client and then broadcast the percentage to this room.
I explained it here: How to connect formidable file upload to socket.io in Node.js

NodeJS unable to response.write to the browser when there is delay in callbacks

i'm using simple MVC structure by Nathan Broslawsky. i have these code below.
ArticleProviderDBController.prototype.Show = function(data) {
//Init Model
var res = this.Response;
var model = this.getModel();
var view = this.getView("ArticleProviderDB");
model.findAll(function(error, article_collections){
if( error ) console.log(error);
view.renderGH(res, data, article_collections); //this will actually call the renderGH function to serve a html file with data from DB but it is not working.
res.write('inside callback'); //this will not.
//res.end();
});
//console.log(_self.Response);
res.write('outside callback'); //this will be shown on my browser.
//res.end();
}
actually i try to follow what people have done using expressjs
app.get('/', function(req, res){
articleProvider.findAll( function(error,docs){
res.render('index.jade', {
locals: {
title: 'Blog',
articles:docs
}
});
})
});
but seems like it is not working.
i also saw a post NodeJS response.write not working within callback posted recently but his solution is not working for me. My main objective is to use simple MVC structure created with Nodejs without the use of other templates such as expressjs to serve html with DB query. thank you.

Django Posts Not Working:

I am using Django 1.2.3 to develop a site. My ajax get requests work fine but the post requests work in development mode (127.0.0.1:8000) but not when I push the site into production using apache + nginx.
Here is an example
urls.py:
(r'api/newdoc/$', 'mysite.documents.views.newdoc'),
views.py
def newdoc(request):
# only process POST request
if request.is_ajax():
data= dict(request.POST)
# save data to db
return HttpResponse(simplejson.dumps([True]))
in javascript:
$.post("/api/newdoc/", {data : mydata}, function(data) { alert(data);}, "json");
my alert is never called .... this is a problem because i want to sanitize this data via a django form and the post requests do not seem to making it to the server (in production only).
what am i doing wrong?
UPDATES:
solution: crsf tokens need to be pushed ajax post requests (not gets) as of django 1.3
also, per the link provide below, the following javascript
$.ajaxSetup({
beforeSend: function(xhr, settings) {
if (!(/^http:.*/.test(settings.url) || /^https:.*/.test(settings.url))) {
// Only send the token to relative URLs i.e. locally.
xhr.setRequestHeader("X-CSRFToken",
$("#csrfmiddlewaretoken").val());
}
}
});
needs to be changed as follows:
$.ajaxSetup({
beforeSend: function(xhr, settings) {
if (!(/^http:.*/.test(settings.url) || /^https:.*/.test(settings.url))) {
// Only send the token to relative URLs i.e. locally.
xhr.setRequestHeader("X-CSRFToken",
$('input[name="csrfmiddlewaretoken"]').val());
}
}
});
the way the csrf token gets rendered in the form must have changed between 1.25 - 1.3??
regardless, it works. thanks for all your help everyone
Can you directly access your javascript files from the production server? Which Django version are you using in production? If you are using 1.2.5+ in production, you will need to push the csrf token to the server during an AJAX post operation.
See the release notes in 1.2.5 and CSRF
To check your Django version:
import django
django.get_version()
Print the above in your production site or from the shell in your production server while making sure you are using the proper Python path.
Your code appears fine with a cursory glance, but I'll show you an example of my ajax form processing code in a hope it'll help with figuring out the error that's occurring. Though, what #dmitry commented should be your first debugging step - use firebug or the inspector to see if the ajax call returns an error.
// js (jQuery 1.5)
$(form).submit(function(event) {
event.preventDefault();
$.post(post_url, $(form).serialize())
.success(function(data, status, jqxhr) {
if (data.success) { // form was valid
$(form)
// other irrelevant code
.siblings('span')
.removeClass('error')
.html('Form Successful');
} else { // form was invalid
$(form).siblings('span').addClass('error').html('Error Occurred');
}
})
.error(function(jqxhr, status, error) { // server error
$(form).siblings('span').addClass('error').html("Error: " + error);
});
});
// django
class AjaxFormView(FormView):
def ajax_response(self, context, success=True):
html = render_to_string(self.template_name, context)
response = simplejson.dumps({'success': success, 'html': html})
return HttpResponse(response, content_type="application/json", mimetype='application/json')
// view deriving from AjaxFormView
def form_valid(self, form):
registration = form.save()
if self.request.is_ajax():
context = {'competition': registration.competition }
return self.ajax_response(context, success=True)
return HttpResponseRedirect(registration.competition.get_absolute_url())
def form_invalid(self, form):
if self.request.is_ajax():
context = { 'errors': 'Error Occurred'}
return self.ajax_response(context, success=False)
return render_to_response(self.template_name, {'errors':form.errors})
Actually, comparing the above to your code, you may need to set the content_type in your django view so that jQuery can understand and process the response. Note that the above is using django 1.3 class-based views, but the logic should be familiar regardless. I use context.success to signal if the form processing passed or failed - since a valid response (json) of any kind will signal the jQuery.post that the request was successful.

Resources