books.html
<div ng-controller="BookController">
<table datatable="ng" class="row-border hover" ng-table="tableParams">
<thead>
<tr>
<th>BookID</th>
<th>BookName</th>
<th>Author</th>
<th>ISBNCode</th>
<th>NoOfBooks</th>
<th>PublishDate</th>
<th>NoOfBooksIssued</th>
<th>Edit</th>
<th>Delete</th>
</tr>
</thead>
<tbody>
<tr ng-repeat="book in books">
<td>{{book.BookId}}</td>
<td>{{book.BookName}}</td>
<td>{{book.Author}}</td>
<td>{{book.ISBNCode}}</td>
<td>{{book.NoOfBooks}}</td>
<td>{{book.PublishDate}}</td>
<td>{{book.NoOfBooksIssued}}</td>
<td><p data-placement="top" data-toggle="tooltip" title="Edit"><button class="btn btn-primary btn-xs" data-title="Edit" data-toggle="modal" data-target="#edit"><span class="glyphicon glyphicon-pencil"></span></button></p></td>
<td><p data-placement="top" data-toggle="tooltip" title="Delete"><button class="btn btn-danger btn-xs" data-title="Delete" data-toggle="modal" data-target="#delete"><span class="glyphicon glyphicon-trash"></span></button></p></td>
</tr>
</table>
</div>
Bookcontroller.js
"use strict";
(function () {
angular.module("Bookapp")
.controller("BookController", ["$scope", "BookService",
function ($scope, bookService) {
bookService.getRequest()
.then(function (response) {
$scope.books = JSON.parse(response);
});
}]);
})();
AddBookController.js
"use strict";
(function () {
angular.module('Bookapp')
.controller('AddBookController', ["$scope", "BookService",
function ($scope, bookService) {
$scope.save = function (item) {
bookService.postRequest(item)
.then(function () {
location.path("books");
});
}
}]);
})();
Both the js files are 2 different custom files which are included in the master page. I have also written BookService.js. Which is as follows:
"use strict";
(function () {
angular.module("Bookapp")
.factory("BookService", ["$http", "$q", function ($http, $q) {
var baseURL = "http://localhost:27136/api/book";
var getRequest = function (query) {
var deferred = $q.defer();
$http({
url: baseURL,
method: "GET"
})
.success(function (result) {
deferred.resolve(result);
})
.error(function (result, status) {
deferred.reject(status);
});
return deferred.promise;
};
var getByIdRequest = function (id) {
var deferred = $q.defer();
$http({
url: baseURL + "/" + id,
method: "GET"
})
.success(function (result) {
deferred.resolve(result);
})
.error(function (result, status) {
deferred.reject(status);
});
return deferred.promise;
};
var postRequest = function (data) {
var deferred = $q.defer();
$http({
url: baseURL,
method: "POST",
data: JSON.stringify(data)
})
.success(function (result) {
deferred.resolve(result);
})
.error(function (result, status) {
deferred.reject(status);
});
return deferred.promise;
};
var updateRequest = function (data, id) {
var deferred = $q.defer();
$http({
url: baseURL + "/" + id,
method: "PUT",
data: JSON.stringify(data)
})
.success(function (result) {
deferred.resolve(result);
})
.error(function (result, status) {
deferred.reject(status);
});
return deferred.promise;
};
var deleteRequest = function (id) {
var deferred = $q.defer();
$http({
url: baseURL + "/" + id,
method: "DELETE"
})
.success(function (result) {
deferred.resolve(result);
})
.error(function (result, status) {
deferred.reject(status);
});
return deferred.promise;
};
return {
getRequest: getRequest,
getByIdRequest: getByIdRequest,
postRequest: postRequest,
updateRequest: updateRequest,
deleteRequest: deleteRequest
};
}]);
})()
My problem is when I click on the add button below my table the details of the book that i have entered must update in the table immediately which is not happening in my case. I have 2 different controllers one is BookController which will get all the books details from db using a service method and display in the table. The other one is AddBookController which will add the new book details to the table.In AddBookController itself i have written code to get the data after posting it to db. But i am not able to refresh the table with new data.Please help me. Thank you so Much in advance!
First of all you have a code smell in your service because you don't need to use $q service for retrieving a promise from $http.
$http always return a promise itself!
so you can simplify all your functions like this:
var getRequest = function (query) {
return $http({
url: baseURL,
method: "GET"
});
};
For your question
Have you try debugging the bookService.getRequest() request?
Try putting a console.log in your book controller and see if it's called after the add.
Maybe you need to trigger the get request after the add.
"use strict";
(function () {
angular.module('Bookapp')
.controller('AddBookController', ["$scope", "BookService",
function ($scope, bookService) {
$scope.save = function (item) {
console.log(item);
bookService.postRequest(item)
.then(function () {
bookService.getRequest()
.then(function (response) {
$scope.books = JSON.parse(response);
});
});
}
}]);
})();
Related
I call getBookIDs from factory and by using the result I call getBookInfo from the same factory. but in the Console.log(bookInfo) it shows me the result of previous call!
how can I update the deferred.promise value before returning??
this is my controller
angular.module('myApp.products',[])
.controller('productController', function ($scope , MainFactory , $location) {
function getBookInfo(bookIDs){
MainFactory.getBookList(bookIDs)
.then(function (bookInfo) {
console.log(bookInfo)
})
}
MainFactory.getBookIDs()
.then(function (result) {
$scope.bookIDList = result;
getBookInfo($scope.bookIDList);
});
});
and this is my factory
app = angular.module('myApp');
app.factory("MainFactory", ['$soap', '$http', '$q', function ($soap, $http, $q) {
var viewFactory = {};
var deferred = $q.defer();
viewFactory.getBookIDs = function () {
//var bookIDs = [];
$http({
url: 'http://127.0.0.1/client.php?fn=getBooks',
method: "GET"
}).then(function success(response) {
deferred.resolve(response.data.result);
}, function myError(error) {
console.log('error', error);
});
return deferred.promise;
};
viewFactory.getBookList = function (bookIDs) {
$http({
url: 'http://127.0.0.1/client.php?fn=getBooksInfo&p1=' + bookIDs,
method: "GET"
}).then(function success(response) {
deferred.resolve(response.data.result);
}, function myError(error) {
deferred.reject(error);
});
return deferred.promise;
};
return viewFactory;
}]);
You should return a new promise for each of your service methods:
app.factory("MainFactory", ['$soap', '$http', '$q', function ($soap, $http, $q) {
var viewFactory = {};
viewFactory.getBookIDs = function () {
var deferred = $q.defer();
//var bookIDs = [];
$http({
url: 'http://127.0.0.1/client.php?fn=getBooks',
method: "GET"
}).then(function success(response) {
deferred.resolve(response.data.result);
}, function myError(error) {
console.log('error', error);
});
return deferred.promise;
};
viewFactory.getBookList = function (bookIDs) {
var deferred = $q.defer();
$http({
url: 'http://127.0.0.1/client.php?fn=getBooksInfo&p1=' + bookIDs,
method: "GET"
}).then(function success(response) {
deferred.resolve(response.data.result);
}, function myError(error) {
deferred.reject(error);
});
return deferred.promise;
};
return viewFactory;
}]);
Promises should not be reused (unless you wish to perform multiples tasks triggering the same resolve/reject... still, you should explicitly implement a promise aggregator for that, I think).
All angular services are singletons, so i guess the reason you got this bug is getBookIDs and getBookList share the same deferred
try change your factory to
app.factory("MainFactory", ['$soap', '$http', '$q', function ($soap, $http, $q) {
var viewFactory = {};
viewFactory.getBookIDs = function () {
//var bookIDs = [];
var deferred = $q.defer();
$http({
url: 'http://127.0.0.1/client.php?fn=getBooks',
method: "GET"
}).then(function success(response) {
deferred.resolve(response.data.result);
}, function myError(error) {
console.log('error', error);
});
return deferred.promise;
};
viewFactory.getBookList = function (bookIDs) {
var deferred = $q.defer();
$http({
url: 'http://127.0.0.1/client.php?fn=getBooksInfo&p1=' + bookIDs,
method: "GET"
}).then(function success(response) {
deferred.resolve(response.data.result);
}, function myError(error) {
deferred.reject(error);
});
return deferred.promise;
};
return viewFactory;
}]);
I'm trying to write down a Controller that pass a var to a Factory in Angularjs.. The following code return (in console) the values, but I'm not been able to load that into my html page.
Just to record, yes, I'm starting in angularjs.
app.js
var myApp = angular.module('myApp',[]);
myApp.factory('eventData', function ($http, $q) {
delete $http.defaults.headers.common['X-Requested-With'];
return {
getEvent: function (id) {
var deferred = $q.defer();
$http({
method: 'GET',
url: 'page' + id
}).
success(function (data, status, headers, config) {
deferred.resolve(data);
}).
error(function (data, status, headers, config) {
deferred.reject(status);
});
return deferred.promise;
}
};
});
myApp.controller('AngularJSCtrl',
function FeederController($scope, eventData) {
$scope.data = [];
for (var i = 0; i < 10; i++) {
eventData.getEvent(i).then(
function (data) {
$scope.data = data;
console.log($scope.data);
},
function (statusCode) {
console.log(statusCode)
});
}
}
);
page.html
<div ng-controller="AngularJSCtrl">
<div ng-repeat="patient in patients">
<businesscard>{{patient.name}}</businesscard>
</div>
</div>
Problem solved. I've searched for a while until get this right.
Thanks for #Claies and Brad Barrow for the tips :)
app.js
var myApp = angular.module('myApp',[]);
myApp.factory('patientsData', function ($http) {
delete $http.defaults.headers.common['X-Requested-With'];
return {
getPatients: function () {
return $http({
url: 'http://localhost/ucamradio/php/tst.php?campusId=1',
method: 'GET'
})
}
}
});
myApp.controller('AngularJSCtrl', function($scope, patientsData){
$scope.patients = [];
var handleSuccess = function(data, status) {
//$scope.patients = data;
$scope.patients.push(data);
console.log($scope.patients);
};
patientsData.getPatients().success(handleSuccess);
});
page.html
<div ng-controller="AngularJSCtrl">
<div ng-repeat="patient in patients">
<businesscard>{{patient.name}}</businesscard>
</div>
<!--
<div ng-repeat="patient in patients ">
<businesscard>{{patient.id}}</businesscard>
</div> -->
</div>
I'm new to json and can't get data from request correct.
I haven't got any problems with getDrivers(), but when I try to get data from getDriverRaces($scope.id) I get nothing.
I've tried to do it manualy: http://ergast.com/api/f1/2015/drivers/hamilton/results.json?callback=JSON_CALLBACK
and result was -
angular.module('F1FeederApp.controllers', []).
controller('driversController', function ($scope, ergastAPIservice) {
$scope.nameFilter = null;
$scope.driversList = [];
$scope.searchFilter = function (driver) {
var re = new RegExp($scope.nameFilter, 'i');
return !$scope.nameFilter || re.test(driver.Driver.givenName) || re.test(driver.Driver.familyName);
};
ergastAPIservice.getDrivers().success(function (response) {
$scope.driversList = response.MRData.StandingsTable.StandingsLists[0].DriverStandings;
});
}).
controller('driverController', function ($scope, $routeParams, ergastAPIservice) {
$scope.id = $routeParams.id;
$scope.races = [];
$scope.driver = null;
ergastAPIservice.getDriverRaces($scope.id).success(function (response) {
$scope.races = response.MRData.RaceTable.Races;
});
});
<div class="main-content">
<table class="result-table">
<thead>
<tr><th colspan="5">Formula 1 2015 Results</th></tr>
</thead>
<tbody>
<tr>
<td>Round</td>
<td>Grand Prix</td>
<td>Team</td>
<td>Grid</td>
<td>Race</td>
</tr>
<tr ng-repeat="race in races">
<td>{{race.round}}</td>
<td>{{race.raceName}}</td>
<td>{{race.Results[0].Constructor.name}}</td>
<td>{{race.Results[0].grid}}</td>
<td>{{race.Results[0].position}}</td>
</tr>
</tbody>
</table>
</div>
angular.module('F1FeederApp.services', [])
.factory('ergastAPIservice', function ($http) {
var ergastAPI = {};
ergastAPI.getDrivers = function () {
return $http({
method: 'JSONP',
url: 'http://ergast.com/api/f1/2015/driverStandings.json?callback=JSON_CALLBACK'
});
}
ergastAPI.getDriverRaces = function (id) {
return $http({
method: 'JSONP',
url: 'http://ergast.com/api/f1/2015/drivers/' + id + '/results.json?callback=JSON_CALLBACK'
});
}
return ergastAPI;
});
Any help would appreciate.
The problem is that because of carelessness I entered same controller twice, because of common name.
.
config(['$routeProvider', function ($routeProvider) {
$routeProvider.
when("/drivers", { templateUrl: "partials/drivers.cshtml", controller: "driversController" }).
when("/drivers/:id", { templateUrl: "partials/driver.cshtml", controller: "driverController" }).
otherwise({ redirectTo: "/drivers" });
}]);
I think your problem is how you are trying to get at the data in the success functions.
This
ergastAPIservice.getDriverRaces($scope.id).success(function (response) {
$scope.races = response.MRData.RaceTable.Races;
});
should be this (data returned from a $http call is in response.data)
ergastAPIservice.getDriverRaces($scope.id).success(function (response) {
$scope.races = response.data.MRData.RaceTable.Races;
});
The response object has the following properties (see documentation here near top)
data - your response should be in here
status
headers
config
statusText
You are trying to access property response.MRData which will never exist but response.data.MRData should
In my angularjs code below why is the IsLoggedIn and Username not available to the view. Not sure what's wrong, any help will be highly appreciated:
'use strict';
myApp.controller('masterPageController',
function masterPageController($scope, loginService, stateService) {
$scope.State = stateService.State;
});
myApp.factory('stateService', function () {
// todo: fetch the state from server when the service is initialised
var state = {};
return {
State: state,
};
});
myApp.factory('loginService', function ($http, $q, stateService) {
return {
Login: function (logindetails) {
var deferred = $q.defer();
$http({ method: 'POST', url: '/api/Login/Login', data: JSON.stringify(logindetails), headers: { 'Content-Type': 'application/json' } }).
success(function (data, status, headers, config) {
stateService.State = data.State;
deferred.resolve(data);
}).
error(function (data, status, headers, config) {
deferred.reject(status);
});
return deferred.promise;
}
};
});
<div ng-controller="masterPageController">
<div>
<div>
<div>
<a href="/logout" ng-show="State.IsLoggedIn" >{{ State.Username }}</a>
</div>
</div>
</div>
</div>
EDIT: It doesn't work when I set the stateService.State property in my loginService
Change the way you build the service from "factory" to "service" and define "state" on this and do not return anything.
myApp.service('stateService', function () {
// todo: fetch the state from server when the service is initialised
this.state = {};
});
http://codepen.io/rotempe4/pen/KNMpzZ
Consider the code:
var myApp = angular.module('myApp', []);
The routes:
myApp.config(['$routeProvider', function($routeProvider) {
$routeProvider.when('/', {
templateUrl: 'app.html',
controller:myAppController,
resolve:{
resolveData:function(Resolver){
return Resolver();
}
}
});
});
Resolve:
myApp.factory('Resolver', ['$http', function($http){
return function(){
return $http({url: '/someurl',method: "GET"}).then(function(data) {
// dependent call 1
$http({url: '/someotherurl',method: "GET" }).then(function(data) {
});
// dependent call 2
$http({url: '/someanotherurl',method: "GET" }).then(function(data) {
});
});
}
}]);
Above I have nested 2 calls inside one as they are dependent on the data returned by the parent call.
What I want to do: return the Resolver when all of them have completed and not just the parent call.
I cannot use $q.all() because 2 of the calls are dependent of the first call.
In short, myAppController must be loaded only after all the 3 calls have completed.
You should be using chaining promise and $q service to solve your problem .Just use the below sample code it should work
myApp.factory('Resolver', ['$http','$q', function ($http,$q) {
return function () {
var deferred = $q.defer();
$http({ url: '/someurl', method: "GET" }).then(function (data) {
return $http({ url: '/someurl', method: "GET" })
}).then(function (data) {
return $http({ url: '/someanotherurl', method: "GET" })
}).then(function (data) {
deferred.resolve(data);
});
return deferred.promise;
}
}]);
This works for me:
resolve : {
message: function($q, $route, Restangular) {
var msgId = $route.current.params.msgId;
var deferred = $q.defer();
Restangular.one('message', msgId).get().then(function(message) {
Restangular.one('file', message.audioFile.id).get().then(function (blob) {
message.blob = blob;
deferred.resolve(message);
});
});
return deferred.promise;
}
}