Ajax post, converts array of numbers to array of strings - javascript

Im trying to do a post from a .ejs page to a nodejs api.
this is the call i do
var dataSend={
from:from,
to:to,
datesStart: startDates,
datesEnd: endDates,
price: totalPriceOften,
places:JSON.stringify(placesArray),
package: pSizeOften,
transport: $('.activeFilter:eq(1) a').html().toLowerCase(),
pickupRange: pFlexOften,
dropRange: dFlexOften,
};
$.ajax({
url: location.origin + '/publishTravelOften',
headers: {
apiKey: APIKEYWEB
},
type: "POST",
data: dataSend,
dataType: "json",
async: true,
success: function (data) {
//do stuff
},
error: function (err) {
//do other stuff
}
});
the data i send is a object with this information
and in the nodejs api, i have this:
router.post('/publishTravelOften', function (req, res) {
if(req.user == null || req.user == undefined){
res.status(403).send(Error.ERROR_NO_USER);
}
else {
var time = Date.now();
var userLanguage = Geo.getCountry(req);
console.log("LOAD TIME /publishTravelOften: " + (Date.now() - time));
Config.setCountry(Geo.getCountry(req));
publishTravelOften(req, function (error, data) {
if (!error) {
data.lang = Lang.getLang(userLanguage);
data.socketUrl = Config.getSocketUrl();
data.apiUrl = Config.getApiUrlWeb();
res.send(data);
}
else {
res.status(500).send(error);
}
});
}
});
function publishTravelOften(req,callback){
console.log("########");
console.log(req.body);
console.log("########");
var url = Config.getApiUrlWeb() + "travel/often/create?user="+req.user._id+"&currency="+Geo.getCountry(req);
var options = {
url: url,
form:req.body,
headers: {
'apikey': Config.getAPIKeyWeb()
},
};
request.post(options, function (error, response, body) {
var parsedResponse = JSON.parse(body);
if (parsedResponse.success == false)
callback(parsedResponse, parsedResponse);
else {
var data = {
newTravel: parsedResponse.data
};
callback(error, data);
}
});
}
my problem is that when i print the data i get on the nodejs part, i have this
{ from: 'ChIJO_PkYRozGQ0R0DaQ5L3rAAQ',
to: 'ChIJ9xUaAY73vEcRUt8vzFOSk1w',
'datesStart[]': [ '1471683240000', '1471596840000' ],
'datesEnd[]': [ '1471683240000', '1471596840000' ],
price: '134.93',
places: '[]',
package: 'medium',
transport: 'airplane',
pickupRange: '15',
dropRange: '5' }
the number arrays get converted to string arrays, also the field names change from datesStart and datesEnd to 'datesStart[]' and 'datesEnd[]'
is this normal? and how can i prevent the arrays from change from number to string arrays?

Related

Saving File to Share Point - vue.js

Trying to upload file from web application to SharePoint directory. Upon successful upload, only the filename is saved to the database. A SharePoint link is hard coded in the frontend to view the file uploaded.
Problem encountered: Sometimes the upload fails with an error message "session was expired.. Please clear the local storage." Clearing cache does not help.
importFiles: retrieves an array of all files from the database.
saveFile: adds the last successfully file name to the end of the array
clearCache: clears the input type [rename field]
var savingFile = function () {
importFiles(() => saveFile(() => clearCache(() => {
$('#modal').modal('hide');
init();
})));
Following is to upload the selected file to the SharePoint directory.
upon successfully upload, () => { savingFile(); }); is called to save the file.
upload_SP() {
if (app.selectedFile.length == 0) {
alert("please select file to upload..");
app.isLoading = false;
return;
}
_.each(app.selectedFile, function (item, index) {
var blob = item.slice(0, item.size, 'image/jpg');
app.finalFile = new File([blob], app.renameFile[index] + '.jpeg', { type: 'image/jpg' });
});
var formData = new FormData();
_.each(app.finalFile, function (file, index) {
formData.append('file-' + index, file);
});
app.sp_action(app.parentId, app.folderId, app.finalFile.name, app.finalFile,
() => { savingFile(); });
}
},
Following method takes the arguments required to upload the file to the SP.
sp_action(parentId, folderId, fileName, data, callback = null) {
$.fileUploadSP(parentId, folderId, fileName, data, function (response) {
app.isSuccessful = response.isSuccessful;
if (response == "success") {
alert("Successfully Uploaded..");
app.messageDismissCountDown = 3;
if (callback) {
callback(response);
}else {
location.reload();
}
}
else {
clearCache(() => { });
app.message = response.message;
app.isLoading = false;
window.scrollTo(0, 0);
}
});
},
Following is AJAX call made to upload the file to the SharePoint.
window.$.getPathSP = function (parentId, forlderId, fileName) {
var origin = "https://graph.microsoft.com/v1.0/drives/" + parentId + "/items/" + forlderId +
":/" + fileName + ":/content"
return origin;
};
window.$.fileUploadSP = function (parentId, forlderId, fileName, data, callback) {
$.ajax({
type: 'PUT',
url: $.getPathSP(parentId, forlderId, fileName),
headers: graphHeader,
data: data,
contentType: false,
processData: false,
async: true,
crossDomain: true,
cache: false,
success: function (response) {
success(response, function () {
if (callback) {
callback("success");
}
});
},
failure: function (response) {
alert("failed")
failure(response, "fail");
},
error: function (response) {
alert("session was expired.. Please clear the local storage.")
error(response, callback);
}
});
};

How to make pagination from an API with AJAX with the same query?

I don't know how good I could the write the title but it's a little bit complicated.
So I have this webpage in /music-maker endpoint which have a modal. In the modal there is an input field which takes in a user input and post it to the backend through AJAX post request. Then that user query is used to make an API request to https://example.com/api/?key=${key}&q=${query}. The result is then displayed in the webpage.
Now that part is working as it should be but the issue comes when I try to implement an infinite scrolling feature to it.
Please note at this point that the api request above returns the first page of data only and if I specify page 2 then it will return the data from page 2 of that exact query.
So whenever the user scrolls to the bottom I need to make another api request with that exact query as before but for page 2 which I am unable to accomplish. I've tried making a get AJAX request and used a global query variable to store the query from post request but it returns undefined.
Here are the endpoints of the app:
let query;
router.get('/music-maker', (req, res) => {
res.render('music-maker');
});
router.post('/music-maker', async (req, res) => {
query = encodeURI(req.body.input);
const key = '205XxXxX54825-0ab1';
try{
const url = `https://example.com/api/?key=${key}&q=${query}`;
const fullRes = await axios.get(url);
if( fullRes.status === 200 ) {
return res.json({
data: fullRes.data
});
}
}catch(err) {
res.json({
error: 'Unable to retrieve data.'
});
}
});
router.get('/music-maker/page', async (req, res) => {
console.log('1: ', query); // returns undefined
const pageQuery = req.query.q;
try{
console.log('2: ', pageQuery)
}catch(err) {
console.log(err)
}
});
Here are the AJAX requests:
const formInput = $(".searchbar input");
const userSearchInput = formInput.val();
const modalForm = $("form");
$(modalForm).submit((e) => {
e.preventDefault();
const actionUrl = $(e.target).attr("action");
$.ajax({
type: "POST",
url: actionUrl,
dataType: "json",
data: {
input: userSearchInput
},
beforeSend: function() {
$(formInput).val("");
},
success: function({ data }) {
if ( data ) {
$(".data-container").html(data);
} else if (data.error) {
$(".error-container").html(data.error);
}
},
complete: function() {
$(".loader-container").addClass("hidden");
},
});
});
// When the user scrolls to the bottom of the container, this ajax request fires
$('.data-container').on('scroll', function(e) {
const elem = $(e.currentTarget);
if (elem[0].scrollHeight - elem.scrollTop() == elem.outerHeight()) {
console.log(userSearchInput); // this is undefined
$.ajax({
type: "GET",
url: `/music-maker/page/`,
dataType: "json",
beforeSend: function() {
console.log('sending');
},
success: function( data ) {
console.log('incoming');
},
complete: function() {
console.log('complete');
},
});
}
});
How can I get the other pages' data of the same query by making an API request through AJAX?
update:
server part code
router.get("/music-maker/search/:query/:page", async (req, res) => {
let query = req.params.query;
let page = req.params.page;
console.log("query: " + query);
console.log("page: " + page);
return res.json({
query: req.params.query,
page: req.params.page
});
});
client/browser
let userSearchInput = "";
let pageNumber = 1;
function getMusicMaker() {
userSearchInput = $(".searchbar input").val();
userSearchInput = encodeURIComponent(userSearchInput);
const actionUrl = "/music-maker/search";
$.ajax({
url: `${actionUrl}/${userSearchInput}/${pageNumber}`,
dataType: "json",
beforeSend: function () {
$(".searchbar input").val("");
},
success: function (data) {
alert(data.query + "\n" + data.page)
}
});
}
$("form").submit((e) => {
e.preventDefault();
pageNumber = 1; // new search, reset page number
getMusicMaker();
});
$(".data-container").on("scroll", function (e) {
const elem = $(e.currentTarget);
if (elem[0].scrollHeight - elem.scrollTop() == elem.outerHeight()) {
pageNumber++; // set page 2,3,4,....
getMusicMaker();
}
});
I think you have multiple problems, to fix it need whole rewrite to your code (client and server) but I suggest to use single http method, POST or GET.
endpoint for static pages list:
/music-maker/1
/music-maker/2
or
/music-maker = /music-maker/page/1
/music-maker/page/2
for search
/music-maker/search/keywords
/music-maker/search/keywords/2
/music-maker/search/keywords/3
to set page number when user scroll you can do like this
let pageNumber = 1;
$('.data-container').on('scroll', function (e) {
const elem = $(e.currentTarget);
if (elem[0].scrollHeight - elem.scrollTop() == elem.outerHeight()) {
pageNumber++;
$.ajax({
type: "GET",
url: `/music-maker/page/${pageNumber}`,
.......
});
}
});

Why does jQuery's ajax success method doesn't work?

I am trying to add some animation while a type-file input is processing the file, I decided to use jQUery's ajax method to send the form data.
I noticed that the beforeSend method works, but not with the success method, but instead, the error method contains all the response sent by my node server. I tried looking for similiar question but none of them work for me.
JS:
fileForm.on('submit', function(e) {
e.preventDefault();
let formData = new FormData();
formData.append('file', $('#input-file').prop('files')[0]);
$.ajax({
url: this.action,
dataType: 'script',
cache: false,
contentType: false,
processData: false,
beforeSend: () => {
console.log('loading');
},
success: function(response) {
console.log(response); // Not logging anything
setTimeout(() => {
console.log('succeded: ' + response);
}, 500);
},
error: (err) => {
console.log(err); // This logs the response
},
data: formData,
type: this.method.toUpperCase()
});
});
Node.JS:
router.post('/image', upload.single('file'), async (req, res) => {
if (req.session.passport !== undefined) {
try {
console.log(req.file, req.body);
const query = {_id: req.session.passport.user};
const user = await modelAct(userModel, query, 'findOne');
// const opt = {
// query: query,
// data: {
// $set: {
// avatar_path: req.file.path
// }
// }
// };
// await modelAct(userModel, opt, 'updateOne');
res.status(200).json({fileData: req.file});
} catch(err) {
console.log(err);
if ((typeof err.message == 'string')) {
res.sendStatus(err.message);
} else {
res.sendStatus(500);
}
}
} else {
res.sendStatus(401);
}
});

how to cache ajax response in browser and retrieve value from cache browser

I want to cache ajax response into browser database so that i can retrieve the reponse from another web page of the same application.
so far i have tried but i am not able to retrieve the data from browser cache.
any help will be appreciated
this my setting.js
appsetting = {
service1: 'http://localhost:59190/api/Settings/GetConfigurationSettings',
settingsdata: {},
savesettings: function (data) {
//alert('success');
console.log(data);
appsetting.settingsdata = data;
},
getsettings: function () {
var token = { 'token': '00000000-0000-0000-0000-000000000000' };
DBconnection.fetchdata('GET', appsetting.service1, appsetting.savesettings, function () { console.log('Cannot fetch pos') }, token, true);
}
}
this is ajaxcall.js
DBconnection = {
localCache: {
timeout: 30000,
data: {},
remove: function (url) {
delete DBconnection.localCache.data[url];
},
exist: function (url) {
return !!DBconnection.localCache.data[url] && ((new Date().getTime() - DBconnection.localCache.data[url]._) < DBconnection.localCache.timeout);
},
get: function (url) {
console.log('Getting in cache for url' + url);
return DBconnection.localCache.data[url].data;
},
set: function (url, cachedData, callback) {
DBconnection.localCache.remove(url);
DBconnection.localCache.data[url] = {
_: new Date().getTime(),
data: cachedData
};
if ($.isFunction(callback)) callback(cachedData);
}
},
fetchdata: function (typeofcall, url, success, failure, header, cachedata) {
$.ajax({
type: typeofcall,
url: url,
dataType: 'json',
failure: failure,
success: success,
headers: header,
cache: cachedata
});
$.ajaxPrefilter(function (options, originalOptions, jqXHR) {
if (options.cache) {
var complete = originalOptions.complete || $.noop,
url = originalOptions.url;
//remove jQuery cache as we have our own localCache
options.cache = false;
options.beforeSend = function () {
if (DBconnection.localCache.exist(url)) {
complete(DBconnection.localCache.get(url));
return false;
}
return true;
};
options.complete = function (data, textStatus) {
DBconnection.localCache.set(url, data, complete);
};
}
});
}
}
on my webpage i am trying to call like this
var setting = appsetting.getsettings();
console.log(setting);
but i am getting undefined result.

Suspected Javascript Async issue with for loop

I have a pretty simple node script which parses a json file from an external url. I'm attempting to have the script loop over each record returned and make a decision to add it to the DB (using nedb) if we haven't previously got it. At the moment my script below looks to be only processing the last record in the json file.
var Datastore = require('nedb')
, db = new Datastore({ filename: 'foo.db', autoload: true });
var request = require('request');
;
var cgrecentsalesurl = "http://ffo.com.json";
request({
url: cgrecentsalesurl,
headers: {
'User-Agent': 'cgapistats'
},
json: true
}, function (error, response, body) {
if (!error && response.statusCode === 200) {
var cgrecentsales = body["recent-sales"];
for (var i in cgrecentsales) {
console.log( "processing record " + i );
(function() {
var query = { saletimestamp : cgrecentsales[i].sold_at };
db.find( query , function( err, docs ) {
console.log( docs.length );
if ( docs.length == 0 ) {
db.insert( { item: cgrecentsales[i].item, saletimestamp: cgrecentsales[i].sold_at, amount: cgrecentsales[i].amount } );
console.log( "db record inserted" );
} else {
console.log( "record exists!" )
};
});
})();
}
} else {
console.log(response);
}
})
Any ideas what I'm doing wrong?
Thanks!

Categories