Relatively new to node.js, trying to get a JS object from Angular2 to my node.js route but i'm always getting a standard "unexpected token blah blah at index 0" from the native object parser.
The object gets up to my node factory just fine but fails when posting to the route.
This is the JSON that is being sent to the route:
{"SQLServerHostName":"MININT-MT0DKDT","SQLServerDBName":"ContosoRetailDW","SQLServerUserName":"svc_sql_D3","SQLServerPassword":"Inspur123#@!","StoredProcedureName":"[dbo].[d3Test]"}
This is the error i'm receiving in the dev console.
angular2.dev.js:23083 EXCEPTION: SyntaxError: Unexpected token S in JSON at position 0BrowserDomAdapter.logError @ angular2.dev.js:23083BrowserDomAdapter.logGroup @ angular2.dev.js:23094ExceptionHandler.call @ angular2.dev.js:1185(anonymous function) @ angular2.dev.js:12591NgZone._notifyOnError @ angular2.dev.js:13635onError @ angular2.dev.js:13539Zone.run @ angular2-polyfills.js:1247(anonymous function) @ angular2.dev.js:13558zoneBoundFn @ angular2-polyfills.js:1220 angular2.dev.js:23083 STACKTRACE:BrowserDomAdapter.logError @ angular2.dev.js:23083ExceptionHandler.call @ angular2.dev.js:1187(anonymous function) @ angular2.dev.js:12591NgZone._notifyOnError @ angular2.dev.js:13635onError @ angular2.dev.js:13539Zone.run @ angular2-polyfills.js:1247(anonymous function) @ angular2.dev.js:13558zoneBoundFn @ angular2-polyfills.js:1220 angular2.dev.js:23083 SyntaxError: Unexpected token S in JSON at position 0 at Object.parse (native) at XMLHttpRequest.req.onload [as _onload] (http://localhost:1557/app/services/xhr-factory.service.js:17:33) at Zone.run (http://localhost:1557/node_modules/angular2/bundles/angular2-polyfills.js:1243:24) at Zone.run (http://localhost:1557/node_modules/angular2/bundles/angular2.dev.js:13558:32) at XMLHttpRequest.zoneBoundFn (http://localhost:1557/node_modules/angular2/bundles/angular2-polyfills.js:1220:26)
-----async gap----- Error at _getStacktraceWithUncaughtError (http://localhost:1557/node_modules/angular2/bundles/angular2-polyfills.js:2244:29) at Zone.fork (http://localhost:1557/node_modules/angular2/bundles/angular2-polyfills.js:2293:47) at Zone.bind (http://localhost:1557/node_modules/angular2/bundles/angular2-polyfills.js:1218:53) at XMLHttpRequest.obj.addEventListener (http://localhost:1557/node_modules/angular2/bundles/angular2-polyfills.js:1503:95) at XMLHttpRequest.desc.set [as onload] (http://localhost:1557/node_modules/angular2/bundles/angular2-polyfills.js:1449:19) at eval (http://localhost:1557/app/services/xhr-factory.service.js:11:24) at lib$es6$promise$$internal$$initializePromise (http://localhost:1557/node_modules/angular2/bundles/angular2-polyfills.js:515:10) at new lib$es6$promise$promise$$Promise (http://localhost:1557/node_modules/angular2/bundles/angular2-polyfills.js:806:10) at _sendRequest (http://localhost:1557/app/services/xhr-factory.service.js:7:16) at Object.post (http://localhost:1557/app/services/xhr-factory.service.js:39:28)
-----async gap----- Error at _getStacktraceWithUncaughtError (http://localhost:1557/node_modules/angular2/bundles/angular2-polyfills.js:2244:29) at Zone.fork (http://localhost:1557/node_modules/angular2/bundles/angular2-polyfills.js:2293:47) at arguments.(anonymous function) (http://localhost:1557/node_modules/angular2/bundles/angular2-polyfills.js:1671:82)
-----async gap----- Error at _getStacktraceWithUncaughtError (http://localhost:1557/node_modules/angular2/bundles/angular2-polyfills.js:2244:29) at Zone.fork (http://localhost:1557/node_modules/angular2/bundles/angular2-polyfills.js:2293:47) at NgZone._createInnerZone (http://localhost:1557/node_modules/angular2/bundles/angular2.dev.js:13546:39) at new NgZone (http://localhost:1557/node_modules/angular2/bundles/angular2.dev.js:13412:32) at createNgZone (http://localhost:1557/node_modules/angular2/bundles/angular2.dev.js:12475:12) at PlatformRef_.application (http://localhost:1557/node_modules/angular2/bundles/angular2.dev.js:12550:31) at Object.bootstrap (http://localhost:1557/node_modules/angular2/bundles/angular2.dev.js:24805:64) at execute (http://localhost:1557/app/boot.js:14:23) at ensureEvaluated (http://localhost:1557/node_modules/systemjs/dist/system.src.js:3186:26) at Object.execute (http://localhost:1557/node_modules/systemjs/dist/system.src.js:3304:13)BrowserDomAdapter.logError @ angular2.dev.js:23083ExceptionHandler.call @ angular2.dev.js:1188(anonymous function) @ angular2.dev.js:12591NgZone._notifyOnError @ angular2.dev.js:13635onError @ angular2.dev.js:13539Zone.run @ angular2-polyfills.js:1247(anonymous function) @ angular2.dev.js:13558zoneBoundFn @ angular2-polyfills.js:1220 angular2.dev.js:1206 Uncaught SyntaxError: Unexpected token S in JSON at position 0req.onload @ xhr-factory.service.ts:28Zone.run @ angular2-polyfills.js:1243(anonymous function) @ angular2.dev.js:13558zoneBoundFn @ angular2-polyfills.js:1220
Here is the Angular2 component that calls the factory
import {Component} from 'angular2/core';
import {WizardStepOneComponent} from './wizardStepOne.component'
import {WizardStepTwoComponent} from './wizardStepTwo.component'
import {WizardStepThreeComponent} from './wizardStepThree.component'
import {ConfigurationData} from '../classes/configurationData'
import {Report} from '../classes/report'
import {ChartType} from '../classes/chartType'
import {WizardFactory} from '../services/WizardFactory.service'
@Component({
selector: 'wizardMain',
templateUrl: '../../partials/_wizardMain.html',
directives: [WizardStepOneComponent
, WizardStepTwoComponent
, WizardStepThreeComponent],
providers: [Report, ChartType]
})
export class WizardMainComponent{
configurationData: ConfigurationData;
report: Report;
chartType: ChartType;
step1Show:boolean;
step2Show:boolean;
step3Show:boolean;
step4Show:boolean;
configMainShow:boolean;
configSQLServerShow:boolean;
configMySQLShow:boolean;
configHadoopShow:boolean;
configNoSQLShow:boolean;
constructor(public _report: Report
,public _chartType: ChartType){
this.report = _report;
this.chartType = _chartType;
this.hideAll();
this.loadStep(1);
}
hideAll(){
this.step1Show = false;
this.step2Show = false;
this.step3Show = false;
this.step4Show = false;
this.configMainShow = false;
this.configSQLServerShow = false;
this.configMySQLShow = false;
this.configHadoopShow = false;
this.configNoSQLShow = false;
}
loadAdminPanel(){
}
loadMainPanel(){
}
loadStep(stepNumber){
switch(stepNumber)
{
case 1:
{
this.step1Show = true;
this.step2Show = false;
this.step3Show = false;
this.step4Show = false;
this.configMainShow = false;
this.configSQLServerShow = false;
this.configMySQLShow = false;
this.configHadoopShow = false;
this.configNoSQLShow = false;
break;
}
case 2:
{
this.step1Show = false;
this.step2Show = true;
this.step3Show = false;
this.step4Show = false;
this.configMainShow = false;
this.configSQLServerShow = false;
this.configMySQLShow = false;
this.configHadoopShow = false;
this.configNoSQLShow = false;
break;
}
case 3:
{
this.step1Show = false;
this.step2Show = false;
this.step3Show = true;
this.step4Show = false;
this.configMainShow = false;
this.configSQLServerShow = false;
this.configMySQLShow = false;
this.configHadoopShow = false;
this.configNoSQLShow = false;
break;
}
case 4:
{
this.step1Show = false;
this.step2Show = false;
this.step3Show = false;
this.step4Show = true;
this.configMainShow = false;
this.configSQLServerShow = false;
this.configMySQLShow = false;
this.configHadoopShow = false;
this.configNoSQLShow = false;
break;
}
}
}
setConfigurationData(ConfigData: ConfigurationData){
this.configurationData = ConfigData;
}
setReportName(ReportName: string){
this.report.ReportName = ReportName;
this.loadStep(2);
}
setChartType(ChartTypeID: number){
this.chartType.ChartTypeID = ChartTypeID;
WizardFactory.getColumnProperties(this.configurationData).then((data) => {
console.log("SQL Server Response: " + data);
});
this.loadStep(3);
}
setXAxis(XAxis: string){
this.configurationData.XAxis = XAxis;
}
setYAxis(YAxis: string){
this.configurationData.YAxis = YAxis;
this.loadStep(4);
}
}
It gets to the factory just fine here:
import {$http} from './xhr-factory.service';
import {ConfigurationData} from '../classes/configurationData';
export const WizardFactory = {
getColumnProperties: function (currentConfig) {
console.log("Current Config in Factory: " + JSON.stringify(currentConfig));
return $http.post('/api/getColumnProperties', currentConfig);
}
}
And to my XHR Handler:
export const $http = {
get: function(url: string) {
return _sendRequest(url, null, 'GET');
},
post: function(url: string, payload: any){
return _sendRequest(url, payload, 'POST');
},
put: function(url: string, payload: any){
return _sendRequest(url, payload, 'PUT');
},
delete: function(url: string, payload: any){
return _sendRequest(url, null, 'DELETE');
}
}
function _sendRequest(url: string, payLoad: any, type: string): Promise<JSON> {
return new Promise(function(resolve, reject) {
var req = new XMLHttpRequest();
req.open(type, url);
req.setRequestHeader("Content-Type", "application/json;charset=UTF-8");
req.onload = function() {
if (req.status == 200) {
console.log("Resolved");
resolve(JSON.parse(req.response));
} else {
reject(JSON.parse(req.response));
}
};
req.onerror = function() {
reject(JSON.parse(req.response));
};
if (payLoad) {
req.send(JSON.stringify(payLoad));
} else {
req.send(null);
}
});
}
But it will not get to the route I have defined; which i've manipulated about 100 times now to try and get the syntax right:
var express = require('express');
var wizardRouter = express.Router();
var sql = require('mssql');
var sqlReturnDefinitionQuery = "SET NO_BROWSETABLE ON; \
SET FMTONLY ON; \
EXEC {0}; \
SET FMTONLY OFF; \
SET NO_BROWSETABLE OFF";
/*Get Stored Procedure Schema*/
wizardRouter.post('/getColumnProperties', function (req, res, next) {
console.log("In router");
_currentConfig = JSON.parse(req.params.currentConfig);
console.log("Current Config in Router: " + req.params.currentConfig);
var config = {
user: _currentConfig.SQLServerUserName,
password: _currentConfig.SQLServerPassword,
server: _currentConfig.SQLServerHostName,
database: _currentConfig.SQLServerDBName
};
var finalReturnDefinitionQuery = sqlReturnDefinitionQuery.replace("{0}", _currentConfig.StoredProcedureName);
sql.connect(config, function () {
if(err) console.log(err);
var request = new sql.Request();
request.query(finalReturnDefinitionQuery, function(err, recordset){
if(err) console.log(err);
res.send(recordset);
});
});
});
module.exports = wizardRouter;
And finally here is my node server file:
var express = require('express');
var path = require('path');
var logger = require('morgan');
var cookieParser = require('cookie-parser');
var bodyParser = require('body-parser');
var index = require('./routes/index');
var wizard = require('./routes/wizard');
var app = express();
// view engine setup
app.set('/', path.join(__dirname, 'partials'));
app.set('view engine', 'ejs');
app.engine('html', require('ejs').renderFile);
app.use('/js', express.static(__dirname + '/js'));
app.use('/app', express.static(__dirname + '/app'));
app.use('/content', express.static(__dirname + '/content'));
app.use('/node_modules', express.static(path.join(__dirname, '/node_modules')));
app.use('/partials', express.static(path.join(__dirname, '/partials')));
app.use(logger('dev'));
app.use(bodyParser.json());
app.use(bodyParser.urlencoded({
extended: false
}));
app.use(cookieParser());
app.use(express.static(path.join(__dirname, 'public')));
app.use('/', index);
app.use('/api/', wizard);
// catch 404 and forward to error handler
app.use(function (req, res, next) {
var err = new Error('Not Found');
err.status = 404;
next(err);
});
var server = app.listen(1557, function () {
var host = 'localhost';
var port = server.address().port;
console.log('App listening at http://%s:%s', host, port);
});
module.exports = app;
Any help would be greatly appreciated; this is driving me nuts.