How to correctly use Jasmine spies to mock transactions - javascript

I am trying to mock the behaviour from my transaction module in my account_spec. I am finding it difficult. Once, I make a deposit from my account, I have to mock the behaviour for the transaction but I am finding it very hard. My test is currently returning 'Transaction' is not undefined
EDIT:
I have an account module:
function Account(statement = new Statement, transaction = new Transaction){
this._statement = statement
this._transaction = transaction
}
Account.prototype.deposit = function(amount) {
this._transaction.deposit(amount)
this._statement.storeHistory(amount, this._balance, "Deposit")
}
Account.prototype.withdraw = function(amount) {
this._transaction.withdraw(amount)
this._statement.storeHistory(amount, this._balance, "Withdraw")
}
Account.prototype.balance = function() {
return this._balance
}
module.exports = Account;
I have a transaction module:
function Transaction(){
this._balance = 0
}
Transaction.prototype.balance = function() {
return this.balance
}
Transaction.prototype.deposit = function(amount) {
this._balance += amount
}
Transaction.prototype.withdraw = function(amount) {
this._balance -= amount
}
module.exports = Transaction;
My Statement:
function Statement(){
this._logs = []
}
Statement.prototype.seeStatement = function() {
return this._logs
}
Statement.prototype.storeHistory = function(amount, balance, type) {
this._logs.push({amount: amount, balance: balance, type: type})
}
module.exports = Statement;
My Account Spec:
'use strict';
describe('Account',function(){
var account;
beforeEach(function(){
statement = new Statement
var transactionSpy = jasmine.createSpyObj('transaction',['balance','withdraw','deposit']);
account = new Account(statement, transactionSpy);
});
it('is able for a user to deposit', function(){
account.deposit(40)
// expect(account.balance()).toEqual(40)
});
it('is able for a user to withdraw', function() {
account.deposit(40)
account.withdraw(20)
// expect(account.balance()).toEqual(20)
});
it('is able for a user to check their balance', function() {
account.deposit(20)
expect(transaction.balance()).toEqual(20)
});
});

Actually I see typo here, or maybe code is incomplete:
describe('Account', function() {
var account;
var transaction;
var statement = {}; //or some mock object
beforeEach(function() {
var spy = jasmine.createSpyObj('transaction',['returnBalance','withdraw','deposit']);
account = new Account(transaction, statement)
});
it("is able to deposit money", function() {
account.deposit(40)
expect(transaction.returnBalance).toEqual(40)
});
});

The code written by Alexander is correct except one note. You need to pass spy to Account constructor. The name transaction you pass to jasmine.createSpyObj is just a name that will be used in error messages. you can omit it (in this case it will be unknown)
beforeEach(function() {
var transactionSpy = jasmine.createSpyObj('transaction',['returnBalance','withdraw','deposit']);
account = new Account(transactionSpy, statement)
});

Related

Promise with async function is not waiting to be fulfilled

I am struggling with the issue of Promise and async/await for last two days. I am trying to configure my protractor.conf.js that would get the browser name just at the starting of the suit and will join with the suit name. I have written jasmine allure reporter code in customized way so that I can get browser name in asynchronously and then use with the suit name. But nothing working properly. In the code I have tried, I get only suit name. Browser name in few seconds later. As a result I could not use that browser name in suit name. Here is my code in detail
Edited
var AllureReporter = function CustomJasmine2AllureReporter(userDefinedConfig, allureReporter) {
let browser = {
getCapabilities: function() {
return new Promise(resolve => {
setTimeout(() => {
resolve({
get: str => str
});
}, 2000);
});
}
};
var result;
let bName = (async () => {
try {
var result = (await browser.getCapabilities()).get('Browser Name');
return result;
} catch (err) {
return "Error or smth"
}
})();
this.suiteStarted = function(suite) {
this.allure.startSuite(suite.fullName + result);
console.log(suite.fullName + result);
};
// other methods like spec done,, spec description.
}
the index code from Allure that can be changed is
'use strict';
var assign = require('object-assign'),
Suite = require('./beans/suite'),
Test = require('./beans/test'),
Step = require('./beans/step'),
Attachment = require('./beans/attachment'),
util = require('./util'),
writer = require('./writer');
function Allure() {
this.suites = [];
this.options = {
targetDir: 'allure-results'
};
}
Allure.prototype.setOptions = function(options) {
assign(this.options, options);
};
Allure.prototype.getCurrentSuite = function() {
return this.suites[0];
};
Allure.prototype.startSuite = function(suiteName, timestamp) {
this.suites.unshift(new Suite(suiteName,timestamp));
};
module.exports = Allure;
and the Suit.js class
function Suite(name, timestamp) {
this.name = name;
this.start = timestamp || Date.now();
this.testcases = [];
}
Suite.prototype.end = function(timestamp) {
this.stop = timestamp || Date.now();
};
Suite.prototype.addTest = function(test) {
this.testcases.push(test);
};
Suite.prototype.toXML = function() {
var result = {
'#': {
'xmlns:ns2' : 'urn:model.allure.qatools.yandex.ru',
start: this.start
},
name: this.name,
title: this.name,
'test-cases': {
'test-case': this.testcases.map(function(testcase) {
return testcase.toXML();
})
}
};
if(this.stop) {
result['#'].stop = this.stop;
}
return result;
};
module.exports = Suite;
I am getting this output after edited the question.the result is undefined in the suit name
Executing 7 defined specs...
Test Suites & Specs:
Test for correct login undefined
1. Test for correct login
(node:9764) [DEP0005] DeprecationWarning: Buffer() is deprecated due to
security and usability issues. Please use the Buffer.alloc(),
Buffer.allocUnsafe(), or Buffer.from() methods instead.
√ Navigate to the login page (5520ms)
√ Click onto language button (406ms)
√ English Language is selected (417ms)
√ Correct user name is written into email field (609ms)
√ Correct password is written into password field (486ms)
√ Login button is clicked and home page is opened with Machine on left top
menu (5622ms)
√ Logout button is clicked and redirect to login page (4049ms)
7 specs, 0 failures
Finished in 17.127 seconds
I want to get browser name after the the line 'Test Suites & Specs:' and want to add the name with suit name.
The function where you want to use await should be async.
I have made a small example for you. hope it will help
//The function we want to use wait in should be async!
async function myFunction() {
//Using callback
thisTakeSomeTime().then((res) => console.log(res)); //Will fire when time out is done. but continue to the next line
//Using await
let a = await thisTakeSomeTime();
console.log(a);//will fire after waiting. a will be defined with the result.
}
function thisTakeSomeTime() {
return new Promise((res) => {
setTimeout(()=>{res("This is the result of the promise")}, 5000)
})
}
myFunction();

Node.Js doesn't execute anonymous functions?? -aws lambda -alexa skill

I'm currently working on a Alexa Skill for my Smart Home.
I created a Lambda function and want to make a http request to a server. but it wont execute any of my anon. functions.
A lambda code example:
/* This code has been generated from your interaction model by skillinator.io
/* eslint-disable func-names */
/* eslint quote-props: ["error", "consistent"]*/
// There are three sections, Text Strings, Skill Code, and Helper Function(s).
// You can copy and paste the contents as the code for a new Lambda function, using the alexa-skill-kit-sdk-factskill template.
// This code includes helper functions for compatibility with versions of the SDK prior to 1.0.9, which includes the dialog directives.
// 1. Text strings =====================================================================================================
// Modify these strings and messages to change the behavior of your Lambda function
const request = require("request");
let speechOutput;
let reprompt;
let welcomeOutput = "Hallo xyz!";
let welcomeReprompt = "xy";
// 2. Skill Code =======================================================================================================
"use strict";
const Alexa = require('alexa-sdk');
const APP_ID = "my id"; // TODO replace with your app ID (OPTIONAL).
speechOutput = '';
const handlers = {
'LaunchRequest': function () {
this.emit(':ask', welcomeOutput, welcomeReprompt);
},
'AMAZON.HelpIntent': function () {
speechOutput = 'Placeholder response for AMAZON.HelpIntent.';
reprompt = '';
this.emit(':ask', speechOutput, reprompt);
},
'AMAZON.CancelIntent': function () {
speechOutput = 'Placeholder response for AMAZON.CancelIntent';
this.emit(':tell', speechOutput);
},
'AMAZON.StopIntent': function () {
speechOutput = 'Placeholder response for AMAZON.StopIntent.';
this.emit(':tell', speechOutput);
},
'SessionEndedRequest': function () {
speechOutput = '';
//this.emit(':saveState', true);//uncomment to save attributes to db on session end
this.emit(':tell', speechOutput);
},
'LichtIntent': function () {
//delegate to Alexa to collect all the required slot values
let filledSlots = delegateSlotCollection.call(this);
speechOutput = '';
//any intent slot variables are listed here for convenience
let zimmerSlotRaw = this.event.request.intent.slots.zimmer.value;
console.log(zimmerSlotRaw);
let zimmerSlot = resolveCanonical(this.event.request.intent.slots.zimmer);
console.log(zimmerSlot);
let was_lichtSlotRaw = this.event.request.intent.slots.was_licht.value;
console.log(was_lichtSlotRaw);
let was_lichtSlot = resolveCanonical(this.event.request.intent.slots.was_licht);
console.log(was_lichtSlot);
//THIS IS THE PART WHERE I NEED HELP!!
MakeRequest(function(data){
console.log("asddd");
speechOutput = "This is a place holder response for the intent named LichtIntent, which includes dialogs. This intent has 2 slots, which are zimmer, and was_licht. Anything else?";
var speechOutput = data;
this.emit(':ask', speechOutput, speechOutput);
});
console.log("asdww");
//DOWN TO HERE!!
},
'StromIntent': function () {
//delegate to Alexa to collect all the required slot values
let filledSlots = delegateSlotCollection.call(this);
speechOutput = '';
//any intent slot variables are listed here for convenience
let geraet_stromSlotRaw = this.event.request.intent.slots.geraet_strom.value;
console.log(geraet_stromSlotRaw);
let geraet_stromSlot = resolveCanonical(this.event.request.intent.slots.geraet_strom);
console.log(geraet_stromSlot);
let wasSlotRaw = this.event.request.intent.slots.was.value;
console.log(wasSlotRaw);
let wasSlot = resolveCanonical(this.event.request.intent.slots.was);
console.log(wasSlot);
//Your custom intent handling goes here
speechOutput = "This is a place holder response for the intent named StromIntent, which includes dialogs. This intent has 2 slots, which are geraet_strom, and was. Anything else?";
this.emit(':ask', speechOutput, speechOutput);
},
'FrageIntent': function () {
//delegate to Alexa to collect all the required slot values
let filledSlots = delegateSlotCollection.call(this);
speechOutput = '';
//any intent slot variables are listed here for convenience
let geraetSlotRaw = this.event.request.intent.slots.geraet.value;
console.log(geraetSlotRaw);
let geraetSlot = resolveCanonical(this.event.request.intent.slots.geraet);
console.log(geraetSlot);
let was_frageSlotRaw = this.event.request.intent.slots.was_frage.value;
console.log(was_frageSlotRaw);
let was_frageSlot = resolveCanonical(this.event.request.intent.slots.was_frage);
console.log(was_frageSlot);
//Your custom intent handling goes here
speechOutput = "This is a place holder response for the intent named FrageIntent, which includes dialogs. This intent has 2 slots, which are geraet, and was_frage. Anything else?";
this.emit(':ask', speechOutput, speechOutput);
},
'TuerIntent': function () {
//delegate to Alexa to collect all the required slot values
let filledSlots = delegateSlotCollection.call(this);
speechOutput = '';
//any intent slot variables are listed here for convenience
let zeitSlotRaw = this.event.request.intent.slots.zeit.value;
console.log(zeitSlotRaw);
let zeitSlot = resolveCanonical(this.event.request.intent.slots.zeit);
console.log(zeitSlot);
//Your custom intent handling goes here
speechOutput = "This is a place holder response for the intent named TuerIntent, which includes dialogs. This intent has one slot, which is zeit. Anything else?";
this.emit(':ask', speechOutput, speechOutput);
},
'Unhandled': function () {
speechOutput = "The skill didn't quite understand what you wanted. Do you want to try something else?";
this.emit(':ask', speechOutput, speechOutput);
}
};
exports.handler = (event, context) => {
const alexa = Alexa.handler(event, context);
alexa.appId = APP_ID;
// To enable string internationalization (i18n) features, set a resources object.
//alexa.resources = languageStrings;
alexa.registerHandlers(handlers);
//alexa.dynamoDBTableName = 'DYNAMODB_TABLE_NAME'; //uncomment this line to save attributes to DB
alexa.execute();
};
// END of Intent Handlers {} ========================================================================================
// 3. Helper Function =================================================================================================
//THESE ARE MY HELPER FUNCTIONS
function url(){
console.log("asd");
return " my server ip";
}
function MakeRequest(callback){
console.log("hallo!");
request.get(url(), function(error, response, body){
console.log("****************************************");
console.log(response);
console.log("****************************************");
console.log(error);
console.log("****************************************");
console.log(body);
console.log("****************************************");
callback("erfolg!");
});
console.log("hffggh");
}
//DOWN TO HERE!!
function resolveCanonical(slot){
//this function looks at the entity resolution part of request and returns the slot value if a synonyms is provided
let canonical;
try{
canonical = slot.resolutions.resolutionsPerAuthority[0].values[0].value.name;
}catch(err){
console.log(err.message);
canonical = slot.value;
};
return canonical;
};
function delegateSlotCollection(){
console.log("in delegateSlotCollection");
console.log("current dialogState: "+this.event.request.dialogState);
if (this.event.request.dialogState === "STARTED") {
console.log("in Beginning");
let updatedIntent= null;
// updatedIntent=this.event.request.intent;
//optionally pre-fill slots: update the intent object with slot values for which
//you have defaults, then return Dialog.Delegate with this updated intent
// in the updatedIntent property
//this.emit(":delegate", updatedIntent); //uncomment this is using ASK SDK 1.0.9 or newer
//this code is necessary if using ASK SDK versions prior to 1.0.9
if(this.isOverridden()) {
return;
}
this.handler.response = buildSpeechletResponse({
sessionAttributes: this.attributes,
directives: getDialogDirectives('Dialog.Delegate', updatedIntent, null),
shouldEndSession: false
});
this.emit(':responseReady', updatedIntent);
} else if (this.event.request.dialogState !== "COMPLETED") {
console.log("in not completed");
// return a Dialog.Delegate directive with no updatedIntent property.
//this.emit(":delegate"); //uncomment this is using ASK SDK 1.0.9 or newer
//this code necessary is using ASK SDK versions prior to 1.0.9
if(this.isOverridden()) {
return;
}
this.handler.response = buildSpeechletResponse({
sessionAttributes: this.attributes,
directives: getDialogDirectives('Dialog.Delegate', null, null),
shouldEndSession: false
});
this.emit(':responseReady');
} else {
console.log("in completed");
console.log("returning: "+ JSON.stringify(this.event.request.intent));
// Dialog is now complete and all required slots should be filled,
// so call your normal intent handler.
return this.event.request.intent;
}
}
function randomPhrase(array) {
// the argument is an array [] of words or phrases
let i = 0;
i = Math.floor(Math.random() * array.length);
return(array[i]);
}
function isSlotValid(request, slotName){
let slot = request.intent.slots[slotName];
//console.log("request = "+JSON.stringify(request)); //uncomment if you want to see the request
let slotValue;
//if we have a slot, get the text and store it into speechOutput
if (slot && slot.value) {
//we have a value in the slot
slotValue = slot.value.toLowerCase();
return slotValue;
} else {
//we didn't get a value in the slot.
return false;
}
}
//These functions are here to allow dialog directives to work with SDK versions prior to 1.0.9
//will be removed once Lambda templates are updated with the latest SDK
function createSpeechObject(optionsParam) {
if (optionsParam && optionsParam.type === 'SSML') {
return {
type: optionsParam.type,
ssml: optionsParam['speech']
};
} else {
return {
type: optionsParam.type || 'PlainText',
text: optionsParam['speech'] || optionsParam
};
}
}
function buildSpeechletResponse(options) {
let alexaResponse = {
shouldEndSession: options.shouldEndSession
};
if (options.output) {
alexaResponse.outputSpeech = createSpeechObject(options.output);
}
if (options.reprompt) {
alexaResponse.reprompt = {
outputSpeech: createSpeechObject(options.reprompt)
};
}
if (options.directives) {
alexaResponse.directives = options.directives;
}
if (options.cardTitle && options.cardContent) {
alexaResponse.card = {
type: 'Simple',
title: options.cardTitle,
content: options.cardContent
};
if(options.cardImage && (options.cardImage.smallImageUrl || options.cardImage.largeImageUrl)) {
alexaResponse.card.type = 'Standard';
alexaResponse.card['image'] = {};
delete alexaResponse.card.content;
alexaResponse.card.text = options.cardContent;
if(options.cardImage.smallImageUrl) {
alexaResponse.card.image['smallImageUrl'] = options.cardImage.smallImageUrl;
}
if(options.cardImage.largeImageUrl) {
alexaResponse.card.image['largeImageUrl'] = options.cardImage.largeImageUrl;
}
}
} else if (options.cardType === 'LinkAccount') {
alexaResponse.card = {
type: 'LinkAccount'
};
} else if (options.cardType === 'AskForPermissionsConsent') {
alexaResponse.card = {
type: 'AskForPermissionsConsent',
permissions: options.permissions
};
}
let returnResult = {
version: '1.0',
response: alexaResponse
};
if (options.sessionAttributes) {
returnResult.sessionAttributes = options.sessionAttributes;
}
return returnResult;
}
function getDialogDirectives(dialogType, updatedIntent, slotName) {
let directive = {
type: dialogType
};
if (dialogType === 'Dialog.ElicitSlot') {
directive.slotToElicit = slotName;
} else if (dialogType === 'Dialog.ConfirmSlot') {
directive.slotToConfirm = slotName;
}
if (updatedIntent) {
directive.updatedIntent = updatedIntent;
}
return [directive];
}
I use the "request" module for my http-request, I think you all know this module.
When I test my function, it gives me NO runtime error!
but the anonymous functions from the MakeRequest call and the request.get call wont execute, and I don't know why.
For Example the console output:
Hallo!,
Asd (very funny.. it gets the params for the request.get.. the bug has to be between the second param(the anon function itself?) in the call and the start of the anon function),
hffggh,
asdww
-the console.logs in the anon. functions doesn't show.
I maybe undestand why the MakeRequest funct. doesn't run -> because the callback from it never came. But why does the request.get not work?? I pasted the necessary parts (the MakeRequest and the helper functions) in a normal node projekt, and it worked!!? -facepalm.... im nearly crying..
My Goal: I want to receive a response from the server.. - thats all. But it just wont go into the function where I can access the response object(s).
(Scroll down to the helper functions)
Please help me out guys, I could really hit my head against the wall.
Reguards

Can't use Angular $q library in Visual Studio (Apache cordova)

I need to use $q to wait until my async function has completed and then do something.
However I have tried injecting $q into my angular module as well as my angular functions and I am getting the message $q is undefined.
Can someone tell me how I can go about being able to use this in my code?
Here is the code for the module and the function I want to use $q in respectively
Module
var droidSync = angular.module('droidSync', ['ionic', 'ngRoute', 'ui.router']);
Controller and FunctionIn this case I want to wait for the results.forEach to finish then I want to hide my loading screen using $ionicLoading.hide()
droidSync.controller('mainController', function ($scope, $ionicLoading) {
$scope.syncContacts = function () {
//Display a loading screen while sync is in execution
$ionicLoading.show({
template: '<p>Syncing Contacts...</p><ion-spinner class="spinner-calm" icon="crescent"/>'
});
var table = AzureService.getTable('contact');
table.read().done(function (results) {
results.forEach(function (result) { //THIS NEEDS TO BE COMPLETE BEFORE HIDING LOAD SCREEN
console.log('result is', result);
// If the contact is flagged as deleted check if its on the device and delete it
if (result.isdeleted == true) {
var options = new ContactFindOptions();
options.filter = result.id;
options.multiple = false;
var fields = ["*"];
navigator.contacts.find(fields, findSuccess, findError, options);
function findSuccess(contact) {
if (contact.length > 0) {
console.log("inside the delete area:", contact);
var contactToDelete = navigator.contacts.create();
//It is safe to use contact[0] as there will only ever be one returned as AzureID is unique
contactToDelete.id = contact[0].id;
contactToDelete.rawId = contact[0].id;
console.log('we want to delete this', contactToDelete);
contactToDelete.remove();
console.log('Contact Deleted');
}
else {
console.log('Contact to delete not present on device. Checking next contact');
}
}
function findError() {
console.log('Contact search failed: Deleted Contact Search');
}
}
else {
//create a contact object to save or update
var emails = [];
var phoneNumbers = [];
var name = new ContactName();
var contactToUpdate = navigator.contacts.create();
contactToUpdate.note = result.id;
name.givenName = result.firstname;
name.familyName = result.lastname;
phoneNumbers[0] = new ContactField('mobile', result.mobilephone, true);
phoneNumbers[1] = new ContactField('home', result.homephone, false);
emails[0] = new ContactField('work', result.email, true);
contactToUpdate.name = name;
contactToUpdate.phoneNumbers = phoneNumbers;
contactToUpdate.emails = emails;
//Search for the contact on the device
var options = new ContactFindOptions();
options.filter = result.id;
options.multiple = false;
var fields = ["*"];
navigator.contacts.find(fields, foundSuccess, foundError, options);
function foundSuccess(contact) {
if (contact.length > 0) {
//The contact has been found on the device. Pass in ids for contact, emails and phone numbers to update.
console.log('object to update is object is', contact);
console.log('contact array length is ', contact.length);
contactToUpdate.id = contact[0].id;
contactToUpdate.rawId = contact[0].rawId;
contactToUpdate.phoneNumbers[0].id = contact[0].phoneNumbers[0].id;
contactToUpdate.phoneNumbers[1].id = contact[0].phoneNumbers[1].id;
contactToUpdate.emails[0].id = contact[0].emails[0].id;
console.log('about to save this', contactToUpdate);
contactToUpdate.save(upSuccess, upError);
function upSuccess() {
console.log('updated a contact!');
}
function upError(ContactError) {
console.log('error updating a contact!');
}
}
else {
//The contact does not exist on the device. Just save it.
console.log('non existent contact: ', contactToUpdate);
contactToUpdate.save(saveSuccess, SaveError);
function saveSuccess() {
console.log('saved a contact!');
}
function SaveError() {
console.log('error saving a contact!');
}
}
}
function foundError() {
console.log('Contact search failed: Undeleted Contact Search');
}
} // end else
})) // end forEach
}) // table.read()
}; // scope.syncContacts()
});
So i'd probably do something like this
This is completely untested code so take that for what you will
$q.all is what your going to want to look into
droidSync.controller('mainController', ["$scope", "$q", "$ionicLoading",
function ($scope, $q, $ionicLoading) {
var loop = function(result){
var deferred = $q.defer();
deferred.resolve(// your loop stuff);
return deferred.promise;
};
var loopingFunction = function(results){
var promises = [];
results.forEach(function(result){
promises.push(loop(result));
});
return $q.all(promises);
};
$scope.syncContacts = function () {
//Display a loading screen while sync is in execution
$ionicLoading.show({
template: '<p>Syncing Contacts...</p><ion-spinner class="spinner-calm" icon="crescent"/>'
});
var table = AzureService.getTable('contact');
table.read().done(function (results) {
loopingFunction(results).then(function(){
// do something after it finishes
$ionicLoading.hide()
});
});
};
}]);

Javascript--Breeze Manager Not Detecting Changes

I'm using the EntityManager from Breeze for the API portion of data-binding. However, the EntityManager fails to track the changes. It will execute the code like it's supposed to but it never recognizes the changes. What's the issue? Please, refrain from saying anything that is not constructive or any personal attacks. We're here as professionals and scientists(i know i am). Here is my code:
Service:
(function () {
var serviceId = 'UWRLService';
angular.module('myApp')
.factory(serviceId, ['$q', 'breeze', 'logger', 'appSettings', UWRLService]);
// console.log('Initialized UWRL Service.js');
function UWRLService($q, breeze, logger, appSettings) {
// console.log('inside datacontext -- UWRLService');
// configure logging for this service
logger = logger.forSource(serviceId);
var logError = logger.logError;
var logSuccess = logger.logSuccess;
var logWarning = logger.logWarning;
//Setup variables with common Breeze query classes
var entityQuery = breeze.EntityQuery;
// setup breeze entity manager
var serviceName = appSettings.apiUrl + '/breeze/Uwrl/';//Where the entire service is pointing to
var manager = new breeze.EntityManager(serviceName);
var entityStateChangeAction = breeze.EntityAction.EntityStateChange;
// expose methods
var service = {
getChangesCount: getChangesCount,
saveChanges: saveChanges,
rejectChanges: rejectChanges,
getDivisions: getDivisions,
getPools: getPools,
getRandomCust: getRandomCust
//createChangeFactorEntity: createChangeFactorEntity,
};
return service;
// FUNCTION DECLARATIONS
//Attaches a new entity to the Breeze repository
//Passes the name and an array of values to seed the entity with
//function createChangeFactorEntity(entityName, initialValues) {
// var newFactor = manager.createEntity(entityName, initialValues);
// return newFactor;
//}
function getRandomCust()
{
var query = breeze.EntityQuery.from('alpha')
.where('customerNumber', '==', 1);
return executeQuery(query, 'Alpha found!');
}
function getDivisions()
{
var query = breeze.EntityQuery
.from('Divisions');
//executeQuery([query name], [query title])
return executeQuery(query, 'Divisions Found');
}
function getPools()
{
var query = breeze.EntityQuery
.from('Pools');
return executeQuery(query, 'Pools Found');
}
//Saves changes and logs exceptions
function saveChanges() {
var hasChanges = manager.hasChanges();
console.log(hasChanges);
console.log(manager.getChanges());
return manager.saveChanges()
.then(saveSucceeded)
.catch(saveFailed);
function saveSucceeded(saveResult) {
logSuccess("# of items saved = " + saveResult.entities.length, null, true);
logger.log(saveResult);
}
function saveFailed(error) {
var reason = error.message;
var detail = error.detail;
if (error.entityErrors) {
//Do nothing
} else if (detail && detail.ExceptionType &&
detail.ExceptionType.indexOf('OptimisticConcurrencyException') !== -1) {
// Concurrency error
reason =
"Another user, perhaps the server, " +
"may have deleted one or all of the todos." +
" You may have to restart the app.";
} else {
reason = "Failed to save changes: " + reason +
" You may have to restart the app.";
}
logError(reason, error, true);
throw error; //Downstream: users know it has failed
}
}
//Discards changes in Breeze Manager
function rejectChanges() {
if (manager.hasChanges()) {
count = getChangesCount();
manager.rejectChanges();
logWarning('Discarded ' + count + ' pending changes(s)', null, true);
}
}
//Returns (Nth-1) index of Breeze manager getChanges array
function getChangesCount() {
var ents = manager.getEntities();
var changes = manager.getChanges();
if (changes.length > 0)
{
alert("Changes made: " + manager.getChanges().length);
}
return manager.getChanges().length;
}
//Query Execution w/ toasters(logger)
function executeQuery(query, entityType) {
var promise = manager.executeQuery(query).then(querySucceeded, queryFailed);
return promise;
function querySucceeded(response) {
logSuccess(entityType + " query was successful", null, true);
return response.results;
}
function queryFailed(response) {
var message = response.message || entityType + " query failed";
logError(message, response, true);
throw error;
}
}
};
})()
Controller (javascript):
(function () {
'use strict';
var controllerId = 'UWRLController';
// console.log('Initialized UWRLController');
//Last item in passed array is the Controller (specific)
angular.module('myApp').controller(controllerId,
['$scope', 'UWRLService', 'logger',
'$routeParams', 'allStatesService', UWRLController]);
function UWRLController($scope, UWRLService, logger, $routeParams, allStatesService) {
// console.log('inside UWRLController');
//Loggin Initialization
logger = logger.forSource(controllerId);
var logError = logger.logError;
var logSuccess = logger.logSuccess;
var logWarning = logger.logWarning;
var uwrl = {};
$scope.uwrl = uwrl;
//Parameters we pass from Renewal Group Maintenance screen
//uwrl.PlanCode = $routeParams.PlanCode;
//uwrl.Contract = $routeParams.ContractNumber;
//uwrl.Mch = $routeParams.Mch;
//Functions in Javascript Controller
//[scope].[property] = [function name]
uwrl.saveChanges = save;
uwrl.discardChanges = discardChanges;
uwrl.changesCount = changesCount();
//uwrl.select = select;
init();//Initialize all customer related data for page
function init()
{
gettingDivisions();//Initialze getting data from Division's table through UWRL-service.js
getAllFiftyStates();
gettingPools();
gettingRandom();
}
function gettingRandom()
{
UWRLService.getRandomCust()
.then(function(alpha)
{
uwrl.alpha = alpha;
uwrl.beta = uwrl.alpha[0].customerName;
});
}
function gettingDivisions()
{
UWRLService.getDivisions()
.then(function (divisionNumber) {
uwrl.divisionNumber = divisionNumber;
});
}
function getAllFiftyStates()
{
allStatesService.getStates()
.then(function (allStates)
{
uwrl.allStates = allStates;
});
}
function gettingPools()
{
UWRLService.getPools()
.then(function (poolNumber)
{
uwrl.poolNumber = poolNumber;
});
}
//Clicking the Drop-down Button
//function select(change) {
// this.MchMcpPlanDesignId = change.MchMcpPlanDesign.MchMcpPlanDesignId;
// change.expanded = !change.expanded; //toggle back and forth
//}
////.then = [if] success
////.fail = failure
////.finally = always executed despite evaluated conditionals
//function getPlans() {//returns a promise
// uwrl.loadingPlans = true;
// UWRLService.getChangeFactors(uwrl.Mch, uwrl.Contract, uwrl.PlanCode)
// .then(function (deltaChangeFactor) {
// uwrl.deltaChangeFactor = deltaChangeFactor;
// }).finally(function () { uwrl.loadingPlans = false; });
//}
////Returns all data in ChangeFactorType table
//function getChangeFactorTypes() {
// UWRLService.getTypes().then(function (changeFactorTypes) {
// uwrl.changeFactorTypes = changeFactorTypes;
// });
//}
//Clicking on Save Button
function save() {
console.log('Save Button Clicked!');
//Validation -- checks for empty values
//if (uwrl.changeFactorType != null && uwrl.effectiveDate != null &&
// uwrl.changeFactorAmount != null) {
// //Adds a new Breeze Entity for ChangeFactor table in SQL database
// UWRLService.createChangeFactorEntity('ChangeFactor',
// {
// MchMcpPlanDesignId: this.MchMcpPlanDesignId,
// ChangeFactorType: uwrl.changeFactorType,
// EffectiveDate: uwrl.effectiveDate,
// ChangeFactorAmount: uwrl.changeFactorAmount
// });
//}
//Saves to Breeze Manager
//Must hit Art's ESB service -- to be researched
UWRLService.saveChanges();
}
//Gets rid of changes and logs it
function discardChanges() {
console.log('Discard Button Clicked!');
UWRLService.rejectChanges();
}
//Notifies user(s) of changes made that are
//either: savable, discardable
function changesCount() {
// console.log("Changes Made: " + UWRLService.getChangesCount)//for debugging purposes
return UWRLService.getChangesCount;
}
};
})();
The answer is to make sure to effect the model. For example: uwrl.alpha[0].customerName instead of urwl.beta

Return local variable in one function to another

I'm building an offline HTML page using Angular and using ydn-db for offline storage.
I have a database service like so,
demoApp.SericeFactory.database = function database() {
var database = {
dataStore: null,
admins: [],
students: [],
errors: [],
getadmindata: function(username) {
self = null, that = this
database.dataStore.get('admins', username).done(function(record) {
that.self = record;
return record;
}).fail(function(e) {
console.log(e);
database.errors.push(e);
});
return self; //This does not change.
}
};
database.dataStore = new ydn.db.Storage('DemoApp');
angular.forEach(INITSTUDENTS, function(student) {
database.dataStore.put('students', student, student.matricno);
database.students.push(student);
});
angular.forEach(INITADMINS, function(admin) {
database.dataStore.put('admins', admin, admin.username);
database.admins.push(admin);
});
return database;
I also have a controller that attempts to use the database;
function AppCntl ($scope, database) {
var user = database.getadmindata('user'); //I get nothing here.
}
What I have tried,
I have tried making changing self to var self
I have tried splitting the function like so
rq = database.dataStore.get('admins', 'user');
rq.done(function(record), {
self = record;
alert(self.name) //Works.
});
alert(self) //Doesn't work.
I have gone through questions like this o StackOverflow but nothings seems to be working for me or maybe I have just been looking in the wrong place.
Database request are asynchronous and hence it executes later after end of execution of the codes.
So when the last alert execute, self is still undefined. Secound alert execute after db request completion and it is usual right design pattern.
EDIT:
I have success with following code:
// Database service
angular.module('myApp.services', [])
.factory('database', function() {
return new ydn.db.Storage('feature-matrix', schema);
}
});
// controller using database service
angular.module('myApp.controllers', [])
.controller('HomeCtrl', ['$scope', 'utils', 'database', function($scope, utils, db) {
var index_name = 'platform, browser';
var key_range = null;
var limit = 200;
var offset = 0;
var reverse = false;
var unique = true;
db.keys('ydn-db-meta', index_name, key_range, limit, offset, reverse, unique)
.then(function(keys) {
var req = db.values('ydn-db', keys);
req.then(function(json) {
$scope.results = utils.processResult(json);
$scope.$apply();
}, function(e) {
throw e;
}, this);
});
}])
Complete app is available at https://github.com/yathit/feature-matrix
Running demo app is here: http://dev.yathit.com/demo/feature-matrix/index.html

Categories

Resources