Trying to code in Javascript on AWS Lambda. The code is meant for Alexa to go to a URL and stream the audio on there using the AudioPlayer.
Can't figure out what I am missing in this code or what is wrong with it and I get this error through the log.
Code:
'use strict';
var alexa = require('alexa-sdk');
var APP_ID = "amzn1.ask.skill.b5c95058-7134-4044-9e77-a4279e0adaf7";
var PAUSE_MESSAGE = "paused!";
var RESUME_MESSAGE = "resumed!";
exports.handler = function(event, context, callback) {
var alexa = Alexa.handler(event, context);
alexa.APP_ID = APP_ID;
alexa.registerHandlers(handlers);
alexa.execute();
};
var handlers = {
'play': function(audioURL, offsetInMilliseconds) {
var response = {
version: "1.0",
response: {
shouldEndSession: true,
directives: [{
type: "AudioPlayer.Play",
playBehavior: "REPLACE_ALL",
audioItem: {
stream: {
url: 'https://feeds.soundcloud.com/stream/275202399-amazon-web-services-306355661-amazon-web-services.mp3',
offsetInMilliseconds: 10
}
}
}]
}
}
this.context.succeed(response);
},
'AMAZON.PauseIntent': function() {
this.emit(':tell', PAUSE_MESSAGE);
},
'AMAZON.ResumeIntent': function() {
this.emit(':tell', RESUME_MESSAGE);
}
};
I ended up changing my code.
Code:
var lastPlayedByUser = {};
var streamURL = "http://cpdc101-lh.akamaihd.net/i/ISNCPDCMB1_1#314337/master.m3u8";
exports.handler = function(event, context) {
var player = new Player(event, context);
player.handle();
};
var Player = function (event, context) {
this.event = event;
this.context = context;
};
Player.prototype.handle = function () {
var requestType = this.event.request.type;
var userId = this.event.context ? this.event.context.System.user.userId : this.event.session.user.userId;
if (requestType === "LaunchRequest") {
this.play(streamURL, 0);
} else if (requestType === "IntentRequest") {
var intent = this.event.request.intent;
if (intent.name === "Play") {
this.play(streamURL, 0);
} else if (intent.name === "AMAZON.PauseIntent") {
this.stop();
} else if (intent.name === "AMAZON.ResumeIntent") {
var lastPlayed = this.loadLastPlayed(userId);
var offsetInMilliseconds = 0;
if (lastPlayed !== null) {
offsetInMilliseconds = lastPlayed.request.offsetInMilliseconds;
}
this.play(streamURL, offsetInMilliseconds);
}
} else if (requestType === "AudioPlayer.PlaybackStopped") {
this.saveLastPlayed(userId, this.event);
this.context.succeed(true);
}
};
Player.prototype.play = function (audioURL, offsetInMilliseconds) {
var response = {
version: "1.0",
response: {
shouldEndSession: true,
directives: [
{
type: "AudioPlayer.Play",
playBehavior: "REPLACE_ALL",
audioItem: {
stream: {
url: audioURL,
token: "0",
expectedPreviousToken: null,
offsetInMilliseconds: offsetInMilliseconds
}
}
}
]
}
};
this.context.succeed(response);
};
Player.prototype.stop = function () {
var response = {
version: "1.0",
response: {
shouldEndSession: true,
directives: [
{
type: "AudioPlayer.Stop"
}
]
}
};
this.context.succeed(response);
};
Player.prototype.saveLastPlayed = function (userId, lastPlayed) {
lastPlayedByUser[userId] = lastPlayed;
};
Player.prototype.loadLastPlayed = function (userId) {
var lastPlayed = null;
if (userId in lastPlayedByUser) {
lastPlayed = lastPlayedByUser[userId];
}
return lastPlayed;
};
Related
I'm trying to create an iframe and inject it into the webpage when the webpage is loaded, But when I try to do that the content script is injecting the iframe inside all the iframes on the webpage, I have used the chrome.runtime.onMessage.addListener to be used to toggle the iframe when the user clicks on the extension icon so I'm sending a message from background script to handle this however I'm sending the message only once from the background script but chrome.runtime.onMessage.addListener is getting fired multiple times I'm not sure why
This is what is happening
This is the content script
var iframeContainer = undefined;
window.onload = function () {
injectPopup();
chrome.runtime.onMessage.addListener((request, sender, sendResponse) => {
if (request.message == "togglePopup") {
console.log("message arrived");
var appBody = document.getElementById("app-container");
if (appBody.style.display == "none") {
console.log("posting message");
iframeContainer.contentWindow.postMessage(
JSON.stringify({
user: request.user,
token: request.token,
}),
"*",
[]
);
appBody.style.display = "block";
} else {
appBody.style.display = "none";
}
}
});
};
// window.addEventListener("message", function (e) {
// if (JSON.parse(e.data)) {
// const data = JSON.parse(e.data);
// if (data.message) {
// if (data.message == "toggleApp") {
// var appBody = document.getElementById("app-container");
// appBody.style.display = "none";
// }
// }
// }
// });
function injectPopup() {
console.log("inject popup");
iframeContainer = document.createElement("iframe");
console.log(iframeContainer);
iframeContainer.allowFullscreen = false;
iframeContainer.src = chrome.runtime.getURL("/index.html");
iframeContainer.id = "app-container-iframe";
const appContainer = document.createElement("div");
appContainer.id = "app-container";
appContainer.style.display = "none";
console.log(appContainer);
const resizeHandle = document.createElement("div");
resizeHandle.id = "resize-container-handle";
resizeHandle.classList.add("ui-resizable-handle");
resizeHandle.classList.add("ui-resizable-w");
resizeHandle.innerHTML =
'<div class="resize-handle-horizontal-bar"></div><div class="resize-handle-horizontal-bar"></div><div class="resize-handle-horizontal-bar"></div>';
appContainer.appendChild(resizeHandle);
document.querySelector("body").appendChild(appContainer);
appContainer.appendChild(iframeContainer);
$("#app-container").resizable({
handles: { w: "#resize-container-handle" },
});
}
This is the background script from which I'm sending the message
var userLoggedIn = {};
const openTabs = [];
const apiUrl = "http://localhost:5000";
var popupOpen = false;
var currentWindow = undefined;
window.onload = () => {
popupOpen = false;
};
chrome.storage.local.get("token", function (result) {
userLoggedIn = result.token;
chrome.browserAction.onClicked.addListener(function (tab) {
const width = 500;
const height = 900;
const left = screen.width / 2 - width / 2;
const top = screen.height / 2 - height / 2;
console.log("clicked!");
if (!userLoggedIn) {
if (currentWindow == undefined) {
chrome.windows.create(
{
url: "/html/auth.html",
width: width,
height: height,
left: left,
top: top,
focused: true,
},
(window) => {
currentWindow = window;
chrome.windows.onRemoved.addListener(function (id) {
if (currentWindow.id == id) {
currentWindow = undefined;
}
});
}
);
}
} else {
console.log("hi!");
chrome.windows.getCurrent((w) => {
chrome.tabs.query(
{
active: true,
currentWindow: true,
},
function (tabs) {
const userData = parseJwt(userLoggedIn);
console.log("sending message");
chrome.tabs.sendMessage(tabs[0].id, {
message: "togglePopup",
user: userData,
token: userLoggedIn,
});
}
);
});
}
});
chrome.runtime.onMessage.addListener((request, sender, sendResponse) => {
if (request.message === "login") {
loginUser(request.payload)
.then(function (res) {
if (res.ok) {
return res.json();
} else {
sendResponse({
message: "error",
});
}
})
.then(function (data) {
chrome.storage.local.set({ token: data.token }, function (result) {
chrome.windows.remove(currentWindow.id);
const userData = parseJwt(data.token);
userLoggedIn = data.token;
chrome.tabs.query(
{
active: true,
currentWindow: true,
},
function (tabs) {
chrome.tabs.sendMessage(tabs[0].id, {
message: "togglePopup",
payload: {
user: userData,
token: userLoggedIn,
},
});
}
);
sendResponse({ message: "success" });
});
})
.catch(function (err) {
console.log(err);
});
return true;
} else if (request.message === "register") {
registerUser(request.payload)
.then(function (res) {
if (res.ok) {
return res.json();
} else {
sendResponse({
message: "error",
});
}
})
.then(function (data) {
console.log(data);
sendResponse({ message: "success" });
})
.catch(function (err) {
console.log(err);
});
} else if (request.message === "logout") {
} else if (request.message === "userStatus") {
} else if (request.message === "closePopup") {
const index = getIndexOfTab(sender.tab.id, openTabs);
openTabs[index].popupOpen = false;
}
});
});
chrome.tabs.sendMessage sends the message to all frames of the tab per the documentation.
You can limit it to the main page via frameId:
chrome.tabs.sendMessage(tabId, {foo: 'bar'}, {frameId: 0});
I have written three files which are: home-flatfull.jsp, settings-social-prefs.html and
google-js-api-wrapper.js files.
In home-flatfull.jsp file, I have written as below:
head.js('jscore/lib/base64.js', 'jscore/lib/google-js-api.js', 'jscore/lib/google-js-api-wrapper.js', function () {
var config = {
apiKey: 'AIzaSyCa52K8J68kr5b4S7Afu1FQzeleCfvzOFs',
clientId: '492662354647-877atvgj1a0pu82nrutsm50rcmg0lufh.apps.googleusercontent.com',
discoveryDocs: ["https://www.googleapis.com/discovery/v1/apis/gmail/v1/rest"],
scopes: 'https://www.googleapis.com/auth/gmail.readonly',
listener: function(response){
console.log(' Check google ');
console.log(response);
}
};
googleJSAPI = GoogleJSAPI.getInstance(config);
});
In settings-social-prefs.html file I have defined as below:
<a onclick="googleJSAPI.signIn()" class="btn btn-sm btn-default">
{{agile_lng_translate 'prefs-email' 'enable'}}
</a>
In google-js-api-wrapper.js file, I have defined as below:
class GoogleJSAPI {
emailRegx = /^(([^<>()[\]\\.,;:\s#\"]+(\.[^<>()[\]\\.,;:\s#\"]+)*)|(\".+\"))#((\[[0-9]{1,3}\.[0-9]{1,3}\.[0-9]{1,3}\.[0-9]{1,3}\])|(([a-zA-Z\-0-9]+\.)+[a-zA-Z]{2,}))$/;
instance;
isActive = false;
constructor(config) {
console.log(' google code loaded ');
gapi.load('client:auth2', () => {
gapi.client.init({
apiKey: config.apiKey,
clientId: config.clientId,
discoveryDocs: config.discoveryDocs,
scope: config.scopes
}).then(() => {
this.isActive = true;
console.log(' config loaded ');
gapi.auth2.getAuthInstance().isSignedIn.listen(config.listener);
}, (error) => {
this.isActive = false;
console.log(JSON.stringify(error, null, 2));
});
});
}
static getInstance(config) {
if (!this.instance) {
this.instance = new GoogleJSAPI(config);
}
return this.instance;
}
isActive() {
return this.isActive;
}
isUserLoggedIn() {
return gapi.auth2.getAuthInstance().isSignedIn.get();
}
signIn = () => {
gapi.auth2.getAuthInstance().signIn();
}
signOut() {
gapi.auth2.getAuthInstance().signOut();
}
getSorted(a, b) {
return new Date(b.date).getTime() - new Date(a.date).getTime();
}
getMailList(queryObject) {
return new Promise((resolve, reject) => {
gapi.client.gmail.users.messages.list(queryObject).then(function (response) {
resolve(response.result);
});
});
}
getMailContentById(id) {
return new Promise((resolve, reject) => {
gapi.client.gmail.users.messages.get({
'userId': 'me', 'id': id
}).then((response) => {
let message = {};
let headers = response.result.payload.headers;
headers.forEach((header) => {
if (header.name === "From") {
message['from'] = header.value;
} else if (header.name === "Subject") {
message['subject'] = header.value;
} else if (header.name === "To") {
message['to'] = theader.value;
} else if (header.name === "Date") {
message['date'] = header.value;
} else if (header.name === "Cc") {
message['cc'] = header.value;
}
});
try {
if (response.result.payload) {
let body = "";
if (response.result.payload.body.size > 0) {
body = response.result.payload.body.data;
} else {
let bodyParts = response.result.payload.parts;
bodyParts.forEach((part, index) => {
if (part.type = "text/html") {
//console.log(index);
body = part.body.data;
return;
}
});
}
message['message'] = Base64.decode(body);
// console.log(message['body']);
}
} catch (e) {
//console.log(index);
//console.log(response.result);
//console.log(e);
}
resolve(message);
});
});
}
getInboxMailsWithContent(nextPageToken, fromEmail) {
var qData = '';
var queryObject = {
'userId': 'me',
'labelIds': ['INBOX']
};
if (nextPageToken) {
queryObject['pageToken'] = nextPageToken;
}
if (fromEmail) {
qData += 'from:' + fromEmail;
}
queryObject['q'] = qData;
return new Promise((resolve, reject) => {
gapi.client.gmail.users.messages.list(queryObject).then((response) => {
let resultObject = {
nextPageToken: response.result.nextPageToken
};
let messages = new Array();
let rawMessages = response.result.messages;
rawMessages.forEach((rawMessage, index) => {
gapi.client.gmail.users.messages.get({
'userId': 'me', 'id': rawMessage.id
}).then((response) => {
let message = {
id: rawMessage.id
};
let headers = response.result.payload.headers;
headers.forEach((header) => {
if (header.name === "From") {
message['from'] = header.value;
} else if (header.name === "Subject") {
message['subject'] = header.value;
} else if (header.name === "To") {
message['to'] = header.value;
} else if (header.name === "Date") {
message['date'] = header.value;
} else if (header.name === "Cc") {
message['cc'] = header.value;
}
});
try {
if (response.result.payload) {
let body = "";
if (response.result.payload.body.size > 0) {
body = response.result.payload.body.data;
} else {
let bodyParts = response.result.payload.parts;
bodyParts.forEach((part, index) => {
if (part.type = "text/html") {
f //console.log(index);
body = part.body.data;
return;
}
});
}
message['message'] = Base64.decode(body);
// console.log(message['body']);
}
} catch (e) {
//console.log(index);
//console.log(response.result);
//console.log(e);
}
messages[index] = message;
});
});
// resultObject.messages = messages.sort(this.getSorted);
resultObject.messages = messages;
resolve(resultObject);
});
});
}
}
function getInboxMailsWithContent(nextPageToken, fromEmail, callback) {
googleJSAPI.getInboxMailsWithContent(nextPageToken, fromEmail).then((response) => {
setTimeout(() => {
if (callback && typeof (callback) == "function") {
callback(response);
}
}, 3000);
});
}
When I clicked on enable button in settings-social-prefs.html file, I am just getting the gmail login page and gmail password page once I have provided gmail username and password, I got the consent screen which asks to allow access to user's email then I am getting the blank screen without getting the Gmail Read-Only mails of a specified user who has logged in. Can you please help me on this to get Gmail Read-Only mails when I click on enable button.
you may turn off two factor authentication (if on) and also "allow low secure apps to connect" in google my account settings
Ps: Displaying API in public should be avoided :-)
i tried to use MediaSource API for a little player.
this is my code and it work if i use timestampOffset but because video files are not exactly 30 sec (maybe 30 sec and 3 milisecond) there is a gap while playing. it seem using timestampOffset is not necessary so when i try to remove this line sourceBuffer.timestampOffset += settings.segment_time; player only show first part. what i missed?
;(function ($) {
$.fn.player = function (options) {
var settings = $.extend({
mimeCodec: 'video/mp4; codecs="avc1.640015, mp4a.40.2',
segment_time: 30,
download_gap: 60,
end_on_error: true,
autoplay: true,
played: false,
controls: false,
}, options);
if (!('MediaSource' in window && MediaSource.isTypeSupported(settings.mimeCodec)))
throw 'Unsupported MIME type or codec: ' + settings.mimeCodec;
this.start = function () {
this.each(function () {
if (!settings.hasOwnProperty('segment_id'))
throw 'Property segment_id is required.';
var video = this;
if (settings.controls)
$(video).attr('controls', '');
var sourceBuffer = null;
var mediaSource = new MediaSource();
var segment_id = settings.segment_id;
video.src = URL.createObjectURL(mediaSource);
mediaSource.addEventListener('sourceopen', function () {
sourceBuffer = this.addSourceBuffer(settings.mimeCodec);
sourceBuffer.addEventListener('updateend', function () {
sourceBuffer.timestampOffset += settings.segment_time;
console.log('updateend:');
if (!settings.played && video.paused && settings.autoplay) {
console.log('play:');
video.play();
settings.played = true;
}
});
reader()
});
function reader() {
fetcher(video.currentTime);
interval(video, setInterval(function () {
fetcher(video.currentTime);
}, settings.segment_time * 1000 / 4))
}
function fetcher(currentTime) {
if (sourceBuffer.timestampOffset - currentTime < settings.download_gap) {
if (!sourceBuffer.updating) {
console.log('nexting:');
fetch('/tv/segments/next/' + segment_id).then(function (response) {
return response.json();
}).then(function (data) {
if (data.status === 200) {
fetch(data.result.current.filename).then(function (response) {
return response.arrayBuffer()
}).then(function (res) {
segment_id = data.result.next.id;
console.log('appending:');
sourceBuffer.appendBuffer(res);
});
} else {
if (settings.end_on_error)
mediaSource.endOfStream();
}
});
}
}
}
});
};
function interval(obj, data) {
if (data) {
$(obj).data('interval', data);
} else {
return $(obj).data('interval');
}
}
this.stop = function () {
this.each(function () {
clearInterval(interval(this));
});
};
return this;
};
}(jQuery));
User.find({ refUser: req.params.userName }).then(function (users) {
var network_users = [];
network_users.push(users);
users.forEach(function (u) {
network_users.push(User.find({ refUser: u.toObject().userName }));
})
return Promise.all(network_users);
I have 4 users, I expected receive a json with all of childrens but I only received the first and the children of this first.
Someone can help me with this loop? Please! Thanks so much!!!!
function asyncLoop(iterations, func, callback, foo) {
var done = false;
var loop = {
next: function () {
if (done) {
return;
}
if (iterations) {
func(loop);
} else {
done = true;
if (callback) callback(foo);
}
},
isEnd: function () {
return done;
},
refresh: function (it) {
iterations = it;
},
break: function () {
done = true;
callback();
}
};
loop.next();
return loop;
}
function bfs(userName, callback) {
userName = String(userName);
var q = [], res = [];
User.findOne({ "refUser" : userName }).lean().exec(function (err, root) {
root.depth = 0;
q.push(root);
asyncLoop(q.length, function (loop) {
res.push(q[0]);
User.find({ "refUser" : q[0].userName }).lean().exec(function (err, new_nodes) {
if (err) console.log(err);
else {
var d = q[0].depth;
q.shift();
loop.refresh(new_nodes.length + q.length);
if (new_nodes.length > 0) {
new_nodes.forEach(function (new_node) {
new_node.depth = d + 1;
q.push(new_node);
});
}
loop.next();
}
});
}, function () { callback(res) });
});
}
Finishing:
bfs(req.params.userName,function(callback){
res.send(callback)
})
So when I try and run my jasmine tests, i get this error on every test:
TypeError: Property '$' of object [object Object] is not a function
at jasmine.Fixtures.cleanUp (http://localhost:8234/src/target/test-classes/frontend/thirdParty/js/com/github/velesin/jasmine-jquery/0.0.0/jasmine-jquery-0.0.0.js:117:3)
at null.<anonymous> (http://localhost:8234/src/target/test-classes/frontend/thirdParty/js/com/github/velesin/jasmine-jquery/0.0.0/jasmine-jquery-0.0.0.js:548:25)
at jasmine.Block.execute (http://localhost:8234/?:1152:19)
at jasmine.Queue.next_ (http://localhost:8234/?:2184:33)
at jasmine.Queue.start (http://localhost:8234/?:2137:10)
at jasmine.Spec.execute (http://localhost:8234/?:2464:16)
at jasmine.Queue.next_ (http://localhost:8234/?:2184:33)
at onComplete (http://localhost:8234/?:2180:20)
at jasmine.Spec.finish (http://localhost:8234/?:2438:7)
at null.onComplete (http://localhost:8234/?:2465:12)
I've seen the various posts and SO's about jquery running in noConflict mode and that I need to use jQuery throughout my code, but the code I'm testing doesnt have any $'s in it.
code:
$provide.factory('corsHttpInterceptor', ['$q', '$window', '$exceptionHandler', '$rootScope', 'jq360', function($q, $window, $exceptionHandler, $rootScope, jq360){
var corsHttpInterceptor,
ieCorsTimeoutTime;
function fixConfigForXdr(config)
{
if (config.method.toUpperCase() === "PUT")
{
config.method = "POST";
if (angular.isDefined(config.params))
{
config.params._method = "put";
}
else
{
config.params = {_method: "put"};
}
}
else if (config.method.toUpperCase() === "DELETE")
{
config.method = "GET";
if (angular.isDefined(config.params))
{
config.params._method = "delete";
}
else
{
config.params = {_method: "delete"};
}
}
}
function getResponseDataForXdr(xdr)
{
var responseData = xdr.responseText;
if ("application/json" === xdr.contentType)
{
responseData = angular.fromJson(responseData);
}
return responseData;
}
function getIEUrl(config)
{
var url = config.url;
if (angular.isDefined(config.params) && !angular.equals(config.params, {}))
{
if (-1 === url.indexOf("?"))
{
url += "?";
}
else
{
url += "&";
}
url += jq360.param(config.params);
}
return url;
}
corsHttpInterceptor = {
request: function(config){
var deferred,
promise,
xdr;
if ('withCredentials' in new $window.XMLHttpRequest())
{
return config;
}
else if (angular.isDefined($window.XDomainRequest))
{
config.method = angular.uppercase(config.method);
deferred = $q.defer();
//this promise already has the then function so don't need to add it
promise = deferred.promise;
try
{
xdr = new $window.XDomainRequest();
}
catch(e)
{
$exceptionHandler(new Error("CRITICAL: " + e.message), "new XDomainRequest()");
}
try
{
fixConfigForXdr(config);
xdr.open(config.method, getIEUrl(config));
}
catch(e)
{
$exceptionHandler(new Error("CRITICAL: " + e.message), "xdr.open");
}
xdr.onprogress = function() {}; //http://social.msdn.microsoft.com/Forums/en-US/iewebdevelopment/thread/30ef3add-767c-4436-b8a9-f1ca19b4812e/
xdr.ontimeout = function() {};
xdr.onload = function() {
try
{
var responseData = getResponseDataForXdr(xdr);
deferred.resolve({data: responseData, status: 200});
$rootScope.$apply();
}
catch(e)
{
$exceptionHandler(new Error("CRITICAL: " + e.message), "xdr.onload");
}
};
xdr.onerror = function() {
try
{
deferred.reject({data: "", status: 500});
$rootScope.$apply();
}
catch(e)
{
$exceptionHandler(new Error("CRITICAL: " + e.message), "xdr.onerror");
}
};
xdr.timeout = 0;
$window.setTimeout(function() { //IE CORS requests are inconsistent without the setTimeout. Reference: http://stackoverflow.com/questions/5250256/inconsistent-ajax-xdr-response-from-ie
try
{
if ("GET" === config.method)
{
xdr.send();
}
else
{
xdr.send(angular.toJson(config.data));
}
}
catch(e)
{
$exceptionHandler(new Error("CRITICAL: " + e.message), "xdr.send");
}
}, ieCorsTimeoutTime);//TEMPORARY way to dynamically set the timeout time for IE CORS requests
promise.success = function(fn) {
promise.then(function(response) {
fn(response.data, response.status);
});
return promise;
};
promise.error = function(fn) {
promise.then(null, function(response) {
fn(response.data, response.status);
});
return promise;
};
return promise;
}
else
{
throw new Error("Browser doesn't support needed functionality.");
}
},
response: function(response){
return response;
},
responseError: function(rejection){
return $q.reject(rejection);
},
ieCorsTimeoutTime: ieCorsTimeoutTime
};
return corsHttpInterceptor;
}]);
test:
'use strict';
var mockAppbaseModule;
describe('appbaseWithCors', function(){
mockAppbaseModule = angular.module("appbase", []);
beforeEach(module(function($provide, $exceptionHandlerProvider) {
$provide.provider('jq360', function() {
this.$get = function() {
return $;
};
});
$exceptionHandlerProvider.mode('log');
}));
beforeEach(module('appbaseWithCors'));
describe("corsHttpInterceptor", function () {
var successCallback = null;
var errorCallback = null;
var successResponse = {foo: 'blah'};
var errorResponse = {errorCode: 123, appServer: 1};
beforeEach(inject(function() {
successCallback = jasmine.createSpy("successCallback");
errorCallback = jasmine.createSpy("errorCallback");
}));
var appStatus;
describe("Standard CORS", function () {
beforeEach(inject(function($window){
appStatus = {
appBaseUrl : "",
appServer: 1,
token: "TEST_TOKEN"
};
spyOn($window, "XMLHttpRequest").andReturn({withCredentials: 'foo'});
}));
it ("should call the error function when there is an error code in the response data", inject(function($http, $httpBackend) {
$httpBackend.expectGET("TEST_URL").respond(403, errorResponse);
var config = {method: "get", url:"TEST_URL"};
$http(config).success(successCallback).error(errorCallback).then(successCallback, errorCallback);
$httpBackend.flush();
expect(successCallback).not.toHaveBeenCalled();
expect(errorCallback).toHaveBeenCalledWith({data: errorResponse, status: 403, headers: jasmine.any(Function), config: jasmine.any(Object)});
}));
}));
}));
}));