For me make more sense using a messaging paradigm (broadcast) rather than use factory that create a variable that after you bind to scope of the controller, because it does that the controller and the service/factory are coupled so you could never change the variable of the service/factory due that your controller would lose the link with the service/factory variable.
For example, if you would like to create a new method in the service/factory that clear the log's array so you create new array rather than empty the current array then that change wouldn't be reflected in that controller's scope because the scope's variable point to the old one log's array; take a look the example: http://jsfiddle.net/Ww8sS/6/
var userInterfaceApp = angular.module('user-interface', ['userInterfaceFilters']);
userInterfaceApp.factory('errorLogs', function () {
return {
logs: [],
addToErrorLog: function (errorArray) {
for (var i = 0; i < errorArray.length; i++) {
this.logs.push({"text": errorArray[i].text, "type": errorArray[i].type, "timestamp": new Date()});
}
},
clearLogs: function () {
this.logs = [];
}
}
});
userInterfaceApp.controller('AnotherController',
['$scope', '$http', 'errorLogs', function ($scope, $http, errorLogs) {
$scope.doSomething = function () {
$http({method: "JSONP", url: "http://uatu.net/test.php?action=do_something&callback=JSON_CALLBACK"}).
success(function (data) {
if (!data.success) {
errorLogs.addToErrorLog(data.errors);
}
})
.error(function (data, status, headers, config) {
alert("Failure");
// called asynchronously if an error occurs
// or server returns response with an error status.
});
}
}]);
userInterfaceApp.controller('ConsoleEventController',
['$scope', 'errorLogs', function ($scope, errorLogs) {
$scope.errorLog = errorLogs.logs;
$scope.errorSortOrder = "-timestamp";
//Not a real method--just here for demonstration
$scope.createErrorMessage = function () {
errorLogs.addToErrorLog([
{"text": "This is a sample error.", "type": "critical"}
]);
}
$scope.clearLogs = function () {
errorLogs.clearLogs();
};
}]);
var userInterfaceFilters = angular.module("userInterfaceFilters", []);
userInterfaceFilters.filter("logTimestamp", function () {
return function (logDate) {
var hours = logDate.getHours();
var minutes = (logDate.getMinutes() < 10) ? "0" + logDate.getMinutes() : logDate.getMinutes();
var seconds = (logDate.getSeconds() < 10) ? "0" + logDate.getSeconds() : logDate.getSeconds();
return hours + ':' + minutes + ":" + seconds;
};
});
If you use the messaging paradigm, it uncouple controllers with the service, moreover that the service is independent and any controller can listen its events; http://jsfiddle.net/Ww8sS/5/
var userInterfaceApp = angular.module('user-interface', ['userInterfaceServices', 'userInterfaceFilters']);
userInterfaceApp.controller('AnotherController', ['$scope', '$http', 'logger', function($scope, $http, logger) {
$scope.doSomething = function() {
$http({method: "JSONP", url: "http://uatu.net/test.php?action=do_something&callback=JSON_CALLBACK"}).
success(function(data) {
if(!data.success) {
logger.addToErrorLog(data.errors);
//alert("How do I get the errors in data.errors to my error log?");
}
})
.error(function(data, status, headers, config) {
alert("Failure");
// called asynchronously if an error occurs
// or server returns response with an error status.
});
}
$scope.clearLog = function() {
logger.clearLog();
}
}]);
userInterfaceApp.controller('ConsoleEventController', ['$scope', function($scope) {
$scope.errorSortOrder = "-timestamp";
$scope.errorLog;
$scope.$on('logger.newErrors', function (evt, errArray) {
$scope.errorLog = errArray;
});
$scope.$on('logger.clearLog', function (evt) {
$scope.errorLog = [];
});
//Not a real method--just here for demonstration
$scope.createErrorMessage = function() {
// $scope.addToErrorLog([{"text" : "This is a sample error.", "type" : "critical"}]);
}
}]);
var userInterfaceFilters = angular.module("userInterfaceFilters", []);
userInterfaceFilters.filter("logTimestamp", function() {
return function(logDate) {
var hours = logDate.getHours();
var minutes = (logDate.getMinutes() < 10) ? "0" + logDate.getMinutes() : logDate.getMinutes();
var seconds = (logDate.getSeconds() < 10) ? "0" + logDate.getSeconds() : logDate.getSeconds();
return hours + ':' + minutes + ":" + seconds;
};
});
var userInterfaceServices = angular.module('userInterfaceServices', []);
userInterfaceServices.service('logger', ['$rootScope', function ($rootScope) {
var errorLog = [];
this.addToErrorLog = function(errorArray) {
for (var i = 0; i < errorArray.length; i++) {
errorLog.push({"text" : errorArray[i].text, "type" : errorArray[i].type, "timestamp" : new Date()});
}
$rootScope.$broadcast('logger.newErrors', errorLog);
};
this.clearLog = function () {
errorLog = [];
$rootScope.$broadcast('logger.clearLog', '');
};
}]);
Anyway, both solutions have some advantages and drawbacks.