calling factory function in service in angularjs - javascript

I am trying to call factory function in service.
My factory looks like this:
function LMSAppFactory($http) {
var ajaxRequest = 'processRequest.jsp?';
return {
getTableData: getTableData,
};
function getTableData(params, callback) {
alert(1);
$http.get(ajaxRequest + 'requestType=getRecords'+params+'&value=10').then(function (response) {
callback(response.data[1].LMSRecords, response.data[0].LMSRecordsCount);
});
}
}
My service
$scope.branchSearch = function (code){
alert(code);
getData: LMSAppFactory.getTableData;
}
I am getting value in branchSearch function but not call in factory function.
Please suggest where is my mistake?

the code is incomplete but i don't get what you're trying to do in the below code (invocation? assignment? are you trying to define a label statement but why?)
$scope.branchSearch = function (code){
alert(code);
getData: LMSAppFactory.getTableData; // <-- HERE
}
if you want to invoke getTableData a valid invocation could be
$scope.branchSearch = function (code){
alert(code);
var params = {} //pass the parameters here
LMSAppFactory.getTableData(params, function(val1, val2){
//callback behaviour here
})
}

You factory declaration seems to be right, but there is a problem with its call., here getData: LMSAppFactory.getTableData;, you not calling the factory.
Also, you need to inject LMSAppFactory factory inside your service if not already. Like :
angular.module('yourmodule')
.service('yourBranchService', ['LMSAppFactory', function(LMSAppFactory) {
//service code
}
]);
Then, finally in service, make call to factory method :
$scope.branchSearch = function (code){
alert(code);
var inputParams = {}; // fill params
LMSAppFactory.getTableData(inputParams, callback)
}
function callback(lmsRecords, lmsCount){
// call back implementaion
}

That's because you are not invoking you factory function only aasigning it's reference to the controller.
If you want the $scope.branchSearch method to get the data from the factory you should it like this:
$scope.branchSearch = function (code){
$scope.data = LMSAppFactory.getTableData(params, code); // <= i assume -code- is your calllback
}
This way you invoke the function and send it the code parameter you fgot from the caller function

Related

value returned from ajax call not getting set to variable in controller in angular js

HTML
<div id="SalaryDiv">
<div ng-controller="SalaryController as sal">
<div ng-repeat="salaryDetail in sal.data">
<p>{{salaryDetail.Name}}</p>
<p>{{salaryDetail.Salary}}</p>
</div>
</div>
</div>
JS
(function () {
var salary = angular.module("SalaryDetails", []);
salary.controller("SalaryController", function () {
var newData = getAssociateData();
alert(newData); //here it is alerting as undefined
this.data = salaryDetails;
});
function getAssociateData() {
var returnData;
$.ajax({
url: "https://gist.githubusercontent.com/vigneshvdm/862ec5a97bbbe2021b79/raw/d7155b9c7fd533597c912fc386682e5baee1487a/associate.json",
type: "GET",
success: getDetails
});
function getDetails(data) {
salaryDetails = data;
return data;
};
};
}());
Here the success function is getting called,
but value is not getting set
1) The return value from getAssociateData is whatever the return value is of $.ajax - which is NOT the data that you return. $.ajax is an async call.
2) You should use Angular's $http rather than jQuery's $.ajax - this would apply the changes to the View automatically (i.e. it will call $scope.$apply() on your behalf).
You also seem to be expecting this.data to be an array (I gather from the use of ng-repeat="salaryDetail in sal.data", so push instead of assigning.
salary.controller("SalaryController", function ($http) {
var url = "https://gist.gith....json";
var vm = this; // your "Controller As" ViewModel
vm.data = [];
$http.get(url).then(function(salaryDetail){
vm.data.push(salaryDetail);
}
}
This is by way of illustration. I agree with other suggestions here that HTTP calls should be abstracted away in a Service, rather than keeping them in the controller. But, one step at a time...
You should use the $http service.
salary.controller("SalaryController", function ($scope, $http) {
$scope.salaryDetails = null;
var url = 'https://gist.githubusercontent.com/vigneshvdm/862ec5a97bbbe2021b79/raw/d7155b9c7fd533597c912fc386682e5baee1487a/associate.json';
$http.get(url).
success(function (data) {
$scope.salaryDetails = data;
});
});
Note: I put it in the controller here, but as a best practice, you should only inject an $http dependency into your custom service.
Whenever you trying to call an ajax call inside the controller, it will not fire the angular digest and hence the controller variables wont get updated.
The ideal way to go about it to have this in a factory and then call the factory method from the controller.
Code example:
appModule.factory('Search', function($rootScope, $http, $q) {
return {
var deferred = $q.defer();
$http.get('https://gist.githubusercontent.com/vigneshvdm/862ec5a97bbbe2021b79/raw/d7155b9c7fd533597c912fc386682e5baee1487a/associate.json').success(function(response) {
deferred.resolve({
data: response)};
});
return deferred.promise;
}
});
This code is using $q service inorder to make it more cleaner.Now just inject this factory (Search) into your controller and use it as is.

Load function service in the same service

I'm trying to call a function elsewhere in the same service in AngularJS.
The function I'm calling in my controller is : geocoding, for the moment, all is ok.
But in my geocoding function, I'm calling another function : geovalue.
For now, the script say "geovalue is undefined".
Example of my code
app.service('geo', function(){
this.geovalue = function(val, decimals){
// some code & return a value at the end
};
this.geocoding = function(place, cb) {
// some code
my var = geovalue(val, decimals);
// some code & return a valeu at the end
};
});
geovalue function is also this' method:
my var = this.geovalue(val, decimals);
And seems like it should be:
my var = this.geovalue(place, cb);

angularJS data not available due to async call

This is my controller:
function TestCtrl ($scope, sharedProperties, $resource){
var userDataProfile = sharedProperties.getUserDataProfile();
var userCreatedBoard = $resource('/boards?owner=:owner');
userCreatedBoard.query({'owner':userDataProfile.id}, function (result) {
console.log(result);
});
}
Now problem is sharedProperties.setUserDataProfile() is called after calling a 3rd party service and its async. Hence, when the TestCtrl is bound, userDataProfile is effectively null. How do I handle this situation so that after the sharedProperties.setUserDataProfile() is called and variable has been assigned a value from 3rd party service, then only my controller should get bound?
I think you want to look at resolve:
http://www.youtube.com/watch?v=Kr1qZ8Ik9G8
This allows you to load all your data before instantiating your controller and firing a routeChangeSuccess event.
In the angular docs.
It does not make sense to pass variables into an Angular.js controller like that, that is what the Scope variable is meant for.
Try this
window.activeTestCtrls = [];
window.sharedProperties = [];
function TestCtrl ($scope, $resource){
if (window.sharedProperties) this.createUserData(window.sharedProperties)
window.activeTestCtrls.push[this];
function createUserData(sharedProperties) {
var userDataProfile = sharedProperties.getUserDataProfile();
var userCreatedBoard = $resource('/boards?owner=:owner');
userCreatedBoard.query({'owner':userDataProfile.id}, function (result) {
console.log(result);
}
});
// and when you get your sharedproperties
function gotSharedProperties(sharedProperties) {
$.each(activeTestControllers, function(index,value) {
activeTestControllers[index].createUserData(sharedProperties)})
}
}

Unset object property

I have a provider:
AdviceList.provider('$adviceList',function(){
this.$get = function ($rootScope,$document,$compile,$http,$purr){
function AdviceList(){
$http.post('../sys/core/fetchTreatments.php').success(function(data,status){
this.treatments = data;
console.log(this.treatments); // the correct object
});
this.adviceCategories = [
// available in the controller
];
}
return{
AdviceList: function(){
return new AdviceList();
}
}
}
});
Further, i have this controller:
AdviceList.controller('AdviceListCtrl',function($scope,$adviceList){
var adv = $adviceList.AdviceList();
$scope.treatments = adv.treatments; // undefined
});
Why is it, that the controller's $scope.treatments stays undefined, this.treatments inside the provider however, is filled correctly? Also, adviceCategories is available in my controller.
The call you get teatment is async in nature so the results may not have been populated when you try to assign them.
So here
var adv = $adviceList.AdviceList();
$scope.treatments = adv.treatments; //The treatments would only get filled after the server call is over.
You need to rewrite the code in a way that you assign it to your scope property on the success callback.
I will recommend you to simplify your code
1) Use simple factory method of angular instead of provider
2) return a promise to avoid using callbacks
AdviceList.service('adviceList', function ($http) {
return {
adviceList: function () {
return $http.post('../sys/core/fetchTreatments.php');
}
}
});
AdviceList.controller('AdviceListCtrl', function ($scope, $adviceList) {
adviceList.AdviceList().then(function (data) {
$scope.treatments = data //set value to data when data is recieved from server
});
});

How to invoke function call if it is defined as var?

I'm getting data from server using JQuery and JSON. I defined getBooksDoneFunc
as variable because I need to be able to call this function not only once (when getBooks is done) . Unfortunately, I cannot call getBooksDoneFunc from inside of signInOK as window["getBooksDoneFunc"]();. Why? What is the best way to call this function?
function getBooks(){ return $.getJSON( "bookstore.json" ); }
var getBooksDoneFunc = function(json) {
$.each(json.books, function(i, json){ .......... });
}
getBooks().done(getBooksDoneFunc);
function signInOK(){
window["getBooksDoneFunc"]();
}
PS. The idea for window["getBooksDoneFunc"](); was taken from SO answer
UPDATE:
var booksJSON = {};
window["getBooksDoneFunc"](booksJSON);
getBooksDoneFunc must be called with parameters nevertheless the call to getBooksDoneFunc fails. signInOK is defined outside of $(document).ready(function(){ }); but called inside of it.
Try:
function getBooks(){
return $.getJSON( "bookstore.json" );
}
window.getBooksDoneFunc = function(json) {
$.each(json.books, function(i, json){ .......... });
}
getBooks().done(getBooksDoneFunc);
$(document)ready(function() {
function signInOK(){
var booksJSON = {};
window.getBooksDoneFunc(booksJSON);
}
});
If window["getBooksDoneFunc"](); works, then does getBooksDoneFunc(), the idea of using window is when you want to access a global function but you don't know the function name which is stored in a variable.
In your case, put a hardcoding string is mean less, just do getBooksDoneFunc() is the same, because you already store the function self (not the string of function name) in the variable.
The thing that won't work is that if the variable is not global, please check the scope.
I would do this a bit differently, although I do not really understand the signInOK() function. How will it receive the "json" data. I would reconstruct the getBooks function and rethink the signInOk function. Here's a start:
function getBooks() {
$.getJSON("bookstore.json").done(function (json) {
getBooksDoneFunc(json);
});
}
var getBooksDoneFunc = function(json) {
$.each(json.books, function(i, json){ .......... });
};
...
getBooks();
function signInOK(){
getBooksDoneFunc("some json data");
}

Categories

Resources