['$scope','$location','$window','egCore',
function($scope , $location , $window , egCore) {
$scope.focusMe = true;
+ $scope.args = {};
+ $scope.workstations = [];
// if the user is already logged in, jump to splash page
if (egCore.auth.user()) $location.path('/');
if (! (args.username && args.password) ) return;
+ // if at least one workstation exists, it must be used.
+ if (!args.workstation && $scope.workstations.length > 0) return;
+
args.type = 'staff';
egCore.auth.login(args).then(
- function() {
- // after login, send the user back to the originally
- // requested page or, if none, the home page.
- // TODO: this is a little hinky because it causes 2
- // redirects if no route_to is defined. Improve.
- $window.location.href =
- $location.search().route_to ||
- $location.path('/').absUrl()
+ function(result) {
+ // After login, send the user to:
+ // 1. The WS admin page for WS maintenance.
+ // 2. The page originally requested by the caller
+ // 3. Home page.
+
+ // NOTE: using $location.path(...) results in
+ // confusing intermediate page loads, since
+ // path(...) is a setter function. Build the URL by
+ // hand instead from the configured base path.
+ var route_to = egCore.env.basePath;
+
+ if (result.invalid_workstation) {
+ // route to WS admin page to delete the offending
+ // WS and create a new one.
+ route_to +=
+ 'admin/workstation/workstations?remove='
+ + encodeURIComponent(args.workstation);
+
+ } else if ($location.search().route_to) {
+ // Route to the originally requested page.
+ route_to = $location.search().route_to;
+ }
+
+ $window.location.href = route_to;
},
function() {
$scope.args.password = '';
angular.module('egCoreMod')
.factory('egAuth',
- ['$q','$timeout','$rootScope','egNet','egHatch',
-function($q , $timeout , $rootScope , egNet , egHatch) {
+ ['$q','$timeout','$rootScope','$window','$location','egNet','egHatch',
+function($q , $timeout , $rootScope , $window , $location , egNet , egHatch) {
var service = {
// the currently active user (au) object
// authtoken test succeeded
service._user = user;
service.poll();
-
- if (user.wsid()) {
- // user previously logged in with a workstation.
- // Find the workstation name from the list
- // of configured workstations
- egHatch.getItem('eg.workstation.all')
- .then(function(all) {
- if (all) {
- var ws = all.filter(
- function(w) {return w.id == user.wsid()})[0];
- if (ws) service.ws = ws.name;
- }
- deferred.resolve(); // found WS
- });
- } else {
- deferred.resolve(); // no WS
- }
+ service.check_workstation(deferred);
+
} else {
// authtoken test failed
egHatch.clearLoginSessionItems();
} else {
// no authtoken to test
- deferred.reject();
+ deferred.reject('No authtoken found');
}
return deferred.promise;
};
+ service.check_workstation = function(deferred) {
+
+ var user = service.user();
+ var ws_path = '/admin/workstation/workstations';
+
+ return egHatch.getItem('eg.workstation.all')
+ .then(function(workstations) {
+ if (!workstations) workstations = [];
+
+ // If the user is authenticated with a workstation, get the
+ // name from the locally registered version of the workstation.
+
+ if (user.wsid()) {
+
+ var ws = workstations.filter(
+ function(w) {return w.id == user.wsid()})[0];
+
+ if (ws) { // success
+ service.ws = ws.name;
+ deferred.resolve();
+ return;
+ }
+ }
+
+ if ($location.path() == ws_path) {
+ // User is on the workstation admin page. No need
+ // to redirect.
+ deferred.resolve();
+ return;
+ }
+
+ // At this point, the user is trying to access a page
+ // besides the workstation admin page without a valid
+ // registered workstation. Send them back to the
+ // workstation admin page.
+
+ // NOTE: egEnv also defines basePath, but we cannot import
+ // egEnv here becuase it creates a circular reference.
+ $window.location.href = '/eg/staff' + ws_path;
+ deferred.resolve();
+ });
+ }
+
/**
* Returns a promise, which is resolved on successful
* login and rejected on failed login.
*/
- service.login = function(args) {
- var deferred = $q.defer();
+ service.login = function(args, ops) {
+ // avoid modifying the caller's data structure.
+ args = angular.copy(args);
+
+ if (!ops) { // only set on redo attempts.
+ ops = {deferred : $q.defer()};
+
+ // Clear old LoginSession keys that were left in localStorage
+ // when the previous user closed the browser without logging
+ // out. Under normal circumstance, LoginSession data would
+ // have been cleared by now, either during logout or cookie
+ // expiration. But, if for some reason the user manually
+ // removed the auth token cookie w/o closing the browser
+ // (say, for testing), then this serves double duty to ensure
+ // LoginSession data cannot persist across logins.
+ egHatch.clearLoginSessionItems();
+ }
- // Clear old LoginSession keys that were left in localStorage
- // when the previous user closed the browser without logging
- // out. Under normal circumstance, LoginSession data would
- // have been cleared by now, either during logout or cookie
- // expiration. But, if for some reason the user manually
- // removed the auth token cookie w/o closing the browser
- // (say, for testing), then this serves double duty to ensure
- // LoginSession data cannot persist across logins.
- egHatch.clearLoginSessionItems();
+ service.login_api(args).then(function(evt) {
- egNet.request(
+ if (evt.textcode == 'SUCCESS') {
+ service.handle_login_ok(args, evt);
+ ops.deferred.resolve({
+ invalid_workstation : ops.invalid_workstation
+ });
+
+ } else if (evt.textcode == 'WORKSTATION_NOT_FOUND') {
+ ops.invalid_workstation = true;
+ delete args.workstation;
+ service.login(args, ops); // redo w/o workstation
+
+ } else {
+ // note: the likely outcome here is a NO_SESION
+ // server event, which results in broadcasting an
+ // egInvalidAuth by egNet.
+ console.error('login failed ' + js2JSON(evt));
+ ops.deferred.reject();
+ }
+ });
+
+ return ops.deferred.promise;
+ }
+
+ service.login_api = function(args) {
+ return egNet.request(
'open-ils.auth',
- 'open-ils.auth.authenticate.init', args.username).then(
- function(seed) {
- args.password = hex_md5(seed + hex_md5(args.password))
- egNet.request(
+ 'open-ils.auth.authenticate.init', args.username)
+ .then(function(seed) {
+ // avoid clobbering the bare password in case
+ // we need it for a login redo attempt.
+ var login_args = angular.copy(args);
+ login_args.password = hex_md5(seed + hex_md5(args.password));
+
+ return egNet.request(
'open-ils.auth',
- 'open-ils.auth.authenticate.complete', args).then(
- function(evt) {
- if (evt.textcode == 'SUCCESS') {
- service.ws = args.workstation;
- service.poll();
- egHatch.setLoginSessionItem(
- 'eg.auth.token', evt.payload.authtoken);
- egHatch.setLoginSessionItem(
- 'eg.auth.time', evt.payload.authtime);
- deferred.resolve();
- } else {
- // note: the likely outcome here is a NO_SESION
- // server event, which results in broadcasting an
- // egInvalidAuth by egNet.
- console.error('login failed ' + js2JSON(evt));
- deferred.reject();
- }
- }
- )
+ 'open-ils.auth.authenticate.complete', login_args)
}
);
+ }
- return deferred.promise;
- };
+ service.handle_login_ok = function(args, evt) {
+ service.ws = args.workstation;
+ egHatch.setLoginSessionItem('eg.auth.token', evt.payload.authtoken);
+ egHatch.setLoginSessionItem('eg.auth.time', evt.payload.authtime);
+ service.poll();
+ }
/**
* Force-check the validity of the authtoken on occasion.