mirror of
https://github.com/ansible/awx.git
synced 2024-11-02 18:21:12 +03:00
AC-363 token expiration now handled exclusively on server.
This commit is contained in:
parent
1763d373eb
commit
f8e1d2e0e3
@ -230,8 +230,8 @@ angular.module('ansible', [
|
||||
|
||||
otherwise({redirectTo: '/'});
|
||||
}])
|
||||
.run(['$rootScope', 'CheckLicense', '$location', 'Authorization','LoadBasePaths', 'ViewLicense',
|
||||
function($rootScope, CheckLicense, $location, Authorization, LoadBasePaths, ViewLicense) {
|
||||
.run(['$cookieStore', '$rootScope', 'CheckLicense', '$location', 'Authorization','LoadBasePaths', 'ViewLicense',
|
||||
function($cookieStore, $rootScope, CheckLicense, $location, Authorization, LoadBasePaths, ViewLicense) {
|
||||
|
||||
LoadBasePaths();
|
||||
|
||||
@ -239,8 +239,8 @@ angular.module('ansible', [
|
||||
$rootScope.crumbCache = new Array();
|
||||
|
||||
$rootScope.$on("$routeChangeStart", function(event, next, current) {
|
||||
// Evaluate the token on each navigation request. Redirect to login page when not valid
|
||||
if (Authorization.isTokenValid() == false) {
|
||||
// On each navigation request, check that the user is logged in
|
||||
if (Authorization.isUserLoggedIn() == false) {
|
||||
if ( next.templateUrl != (urlPrefix + 'partials/login.html') ) {
|
||||
$location.path('/login');
|
||||
}
|
||||
@ -262,8 +262,10 @@ angular.module('ansible', [
|
||||
}
|
||||
});
|
||||
|
||||
if (! Authorization.isTokenValid() ) {
|
||||
if (!Authorization.getToken()) {
|
||||
// When the app first loads, redirect to login page
|
||||
$rootScope.sessionExpired = false;
|
||||
$cookieStore.put('sessionExpired', false);
|
||||
$location.path('/login');
|
||||
}
|
||||
|
||||
|
@ -9,10 +9,7 @@
|
||||
*/
|
||||
|
||||
var $AnsibleConfig =
|
||||
{
|
||||
session_timeout: 3600, // cookie expiration in seconds. session will expire after this many
|
||||
// seconds of inactivity.
|
||||
|
||||
{
|
||||
tooltip_delay: {show: 500, hide: 100}, // Default number of milliseconds to delay displaying/hiding tooltips
|
||||
|
||||
debug_mode: true, // Enable console logging messages
|
||||
|
@ -10,7 +10,7 @@
|
||||
|
||||
'use strict';
|
||||
|
||||
function Authenticate($window, $scope, $rootScope, $location, Authorization, ToggleClass, Alert)
|
||||
function Authenticate($cookieStore, $window, $scope, $rootScope, $location, Authorization, ToggleClass, Alert)
|
||||
{
|
||||
var setLoginFocus = function() {
|
||||
$('#login-username').focus();
|
||||
@ -18,6 +18,7 @@ function Authenticate($window, $scope, $rootScope, $location, Authorization, Tog
|
||||
|
||||
// Display the login dialog
|
||||
$('#login-modal').modal({ show: true, keyboard: false, backdrop: 'static' });
|
||||
|
||||
// Set focus to username field
|
||||
$('#login-modal').on('shown.bs.modal', function() {
|
||||
setLoginFocus();
|
||||
@ -36,18 +37,8 @@ function Authenticate($window, $scope, $rootScope, $location, Authorization, Tog
|
||||
Authorization.logout();
|
||||
}
|
||||
|
||||
scope.sessionTimeout = ($AnsibleConfig.session_timeout / 60).toFixed(2);
|
||||
|
||||
if ($rootScope.userLoggedIn) {
|
||||
// If we're logged in, check for session timeout
|
||||
scope.sessionExpired = Authorization.didSessionExpire();
|
||||
}
|
||||
else {
|
||||
scope.sessionExpired = false;
|
||||
}
|
||||
|
||||
$rootScope.userLoggedIn = false; //hide the logout link. if you got here, you're logged out.
|
||||
//gets set back to true by Authorization.setToken().
|
||||
$rootScope.userLoggedIn = false; //hide the logout link. if you got here, you're logged out.
|
||||
$cookieStore.put('userLoggedIn', false); //gets set back to true by Authorization.setToken().
|
||||
|
||||
$('#login-password').bind('keypress', function(e) {
|
||||
var code = (e.keyCode ? e.keyCode : e.which);
|
||||
@ -73,16 +64,7 @@ function Authenticate($window, $scope, $rootScope, $location, Authorization, Tog
|
||||
.success( function(data, status, headers, config) {
|
||||
$('#login-modal').modal('hide');
|
||||
token = data.token;
|
||||
Authorization.setToken(data.token);
|
||||
scope.reset();
|
||||
|
||||
// Force request to /organizations to query with the correct token -in the event a new user
|
||||
// has logged in.
|
||||
var today = new Date();
|
||||
today.setTime(today.getTime() + ($AnsibleConfig.session_timeout * 1000));
|
||||
$rootScope.token = token;
|
||||
$rootScope.userLoggedIn = true;
|
||||
$rootScope.token_expire = today.getTime();
|
||||
Authorization.setToken(data.token, data.expires);
|
||||
|
||||
// Get all the profile/access info regarding the logged in user
|
||||
Authorization.getUser()
|
||||
@ -126,5 +108,5 @@ function Authenticate($window, $scope, $rootScope, $location, Authorization, Tog
|
||||
}
|
||||
}
|
||||
|
||||
Authenticate.$inject = ['$window', '$scope', '$rootScope', '$location', 'Authorization', 'ToggleClass', 'Alert'];
|
||||
Authenticate.$inject = ['$cookieStore', '$window', '$scope', '$rootScope', '$location', 'Authorization', 'ToggleClass', 'Alert'];
|
||||
|
||||
|
@ -29,6 +29,9 @@ function CredentialsList ($scope, $rootScope, $location, $log, $routeParams, Res
|
||||
|
||||
SelectionInit({ scope: scope, list: list, url: url, returnToCaller: 1 });
|
||||
|
||||
if (scope.PostRefreshRemove) {
|
||||
scope.PostRefreshRemove();
|
||||
}
|
||||
scope.PostRefershRemove = scope.$on('PostRefresh', function() {
|
||||
// After a refresh, populate the organization name on each row
|
||||
for(var i=0; i < scope.credentials.length; i++) {
|
||||
|
@ -176,7 +176,7 @@ function OrganizationsEdit ($scope, $rootScope, $compile, $location, $log, $rout
|
||||
})
|
||||
.error( function(data, status, headers, config) {
|
||||
ProcessErrors(scope, data, status, form,
|
||||
{ hdr: 'Error!', msg: 'Failed to retrieve organization: ' + $routeParams.id + '. GET status: ' + status });
|
||||
{ hdr: 'Error!', msg: 'Failed to retrieve organization: ' + $routeParams.id + '. GET status: ' + status });
|
||||
});
|
||||
|
||||
|
||||
@ -194,7 +194,7 @@ function OrganizationsEdit ($scope, $rootScope, $compile, $location, $log, $rout
|
||||
})
|
||||
.error( function(data, status, headers, config) {
|
||||
ProcessErrors(scope, data, status, OrganizationForm,
|
||||
{ hdr: 'Error!', msg: 'Failed to update organization: ' + id + '. PUT status: ' + status });
|
||||
{ hdr: 'Error!', msg: 'Failed to update organization: ' + id + '. PUT status: ' + status });
|
||||
});
|
||||
};
|
||||
|
||||
|
@ -54,6 +54,7 @@ angular.module('JobTemplateFormDefinition', [])
|
||||
addRequired: true,
|
||||
editRequired: true,
|
||||
ngClick: 'lookUpInventory()',
|
||||
awRequiredWhen: {variable: "inventoryrequired", init: "true" },
|
||||
column: 1
|
||||
},
|
||||
project: {
|
||||
@ -64,6 +65,7 @@ angular.module('JobTemplateFormDefinition', [])
|
||||
addRequired: true,
|
||||
editRequired: true,
|
||||
ngClick: 'lookUpProject()',
|
||||
awRequiredWhen: {variable: "projectrequired", init: "true" },
|
||||
column: 1
|
||||
},
|
||||
playbook: {
|
||||
@ -73,6 +75,7 @@ angular.module('JobTemplateFormDefinition', [])
|
||||
id: 'playbook-select',
|
||||
addRequired: true,
|
||||
editRequired: true,
|
||||
awRequiredWhen: {variable: "playbookrequired", init: "true" },
|
||||
column: 1
|
||||
},
|
||||
credential: {
|
||||
|
@ -15,7 +15,7 @@
|
||||
*/
|
||||
|
||||
angular.module('RefreshRelatedHelper', ['RestServices', 'Utilities'])
|
||||
.factory('RefreshRelated', ['Alert', 'Rest', function(Alert, Rest) {
|
||||
.factory('RefreshRelated', ['ProcessErrors', 'Rest', function(ProcessErrors, Rest) {
|
||||
return function(params) {
|
||||
|
||||
var scope = params.scope;
|
||||
@ -40,7 +40,8 @@ angular.module('RefreshRelatedHelper', ['RestServices', 'Utilities'])
|
||||
})
|
||||
.error ( function(data, status, headers, config) {
|
||||
scope[iterator + 'SearchSpin'] = true;
|
||||
Alert('Error!', 'Failed to retrieve related set: ' + set + '. GET returned status: ' + status);
|
||||
ProcessErrors(scope, data, status, null,
|
||||
{ hdr: 'Error!', msg: 'Failed to retrieve ' + set + '. GET returned status: ' + status });
|
||||
});
|
||||
}
|
||||
}]);
|
@ -15,7 +15,7 @@
|
||||
*/
|
||||
|
||||
angular.module('RefreshHelper', ['RestServices', 'Utilities'])
|
||||
.factory('Refresh', ['Alert', 'Rest', function(Alert, Rest) {
|
||||
.factory('Refresh', ['ProcessErrors', 'Rest', function(ProcessErrors, Rest) {
|
||||
return function(params) {
|
||||
|
||||
var scope = params.scope;
|
||||
@ -37,7 +37,8 @@ angular.module('RefreshHelper', ['RestServices', 'Utilities'])
|
||||
})
|
||||
.error ( function(data, status, headers, config) {
|
||||
scope[iterator + 'SearchSpin'] = false;
|
||||
Alert('Error!', 'Failed to retrieve ' + set + '. GET returned status: ' + status);
|
||||
ProcessErrors(scope, data, status, null,
|
||||
{ hdr: 'Error!', msg: 'Failed to retrieve ' + set + '. GET returned status: ' + status });
|
||||
});
|
||||
}
|
||||
}]);
|
@ -13,11 +13,11 @@ angular.module('JobHostDefinition', [])
|
||||
name: 'jobhosts',
|
||||
iterator: 'jobhost',
|
||||
editTitle: 'Job Host Summary',
|
||||
index: true,
|
||||
indexShow: 'host_id == null',
|
||||
hover: true,
|
||||
|
||||
fields: {
|
||||
job: {
|
||||
id: {
|
||||
label: 'Job ID',
|
||||
ngClick: "showJob(\{\{ jobhost.job \}\})",
|
||||
columnShow: 'host_id !== null',
|
||||
|
@ -1,67 +1,45 @@
|
||||
/*********************************************
|
||||
* Copyright (c) 2013 AnsibleWorks, Inc.
|
||||
*
|
||||
* User authentication functions
|
||||
* AuthService.js
|
||||
*
|
||||
* User authentication functions
|
||||
*/
|
||||
|
||||
angular.module('AuthService', ['ngCookies'])
|
||||
.factory('Authorization', ['$http', '$rootScope', '$location', '$cookieStore', function($http, $rootScope, $location, $cookieStore) {
|
||||
angular.module('AuthService', ['ngCookies', 'Utilities'])
|
||||
.factory('Authorization', ['$http', '$rootScope', '$location', '$cookieStore', 'GetBasePath',
|
||||
function($http, $rootScope, $location, $cookieStore, GetBasePath) {
|
||||
return {
|
||||
setToken: function(token) {
|
||||
setToken: function(token, expires) {
|
||||
// set the session cookie
|
||||
var today = new Date();
|
||||
today.setTime(today.getTime() + ($AnsibleConfig.session_timeout * 1000));
|
||||
$cookieStore.remove('token');
|
||||
$cookieStore.remove('token_expire');
|
||||
$cookieStore.remove('token_expires');
|
||||
$cookieStore.remove('userLoggedIn');
|
||||
$cookieStore.put('token', token);
|
||||
$cookieStore.put('token_expire', today.getTime());
|
||||
$cookieStore.put('token_expires', expires);
|
||||
$cookieStore.put('userLoggedIn', true);
|
||||
$cookieStore.put('sessionExpired', false);
|
||||
$rootScope.token = token;
|
||||
$rootScope.userLoggedIn = true;
|
||||
$rootScope.token_expire = today.getTime();
|
||||
$rootScope.token_expires = expires;
|
||||
$rootScope.sessionExpired = false;
|
||||
},
|
||||
|
||||
isTokenValid: function() {
|
||||
// check if token exists and is not expired
|
||||
var response = false;
|
||||
var token = ($rootScope.token) ? $rootScope.token : $cookieStore.get('token');
|
||||
var token_expire = ($rootScope.token_expire) ? $rootScope.token_expire : $cookieStore.get('token_expire');
|
||||
if (token && token_expire) {
|
||||
var exp = new Date(token_expire);
|
||||
var today = new Date();
|
||||
if (today < exp) {
|
||||
this.setToken(token); //push expiration into the future while user is active
|
||||
response = true;
|
||||
}
|
||||
isUserLoggedIn: function() {
|
||||
if ($rootScope.userLoggedIn == undefined) {
|
||||
// Browser refresh may have occurred
|
||||
$rootScope.userLoggedIn = $cookieStore.get('userLoggedIn');
|
||||
$rootScope.sessionExpired = $cookieStore.get('sessionExpired');
|
||||
}
|
||||
return response;
|
||||
return $rootScope.userLoggedIn;
|
||||
},
|
||||
|
||||
didSessionExpire: function() {
|
||||
// use only to test why user was sent to login page.
|
||||
var response = false;
|
||||
var token_expire = ($rootScope.token_expire) ? $rootScope.token_expire : $cookieStore.get('token_expire');
|
||||
if (token_expire) {
|
||||
var exp = new Date(token_expire);
|
||||
var today = new Date();
|
||||
if (exp < today) {
|
||||
response = true;
|
||||
}
|
||||
}
|
||||
return response;
|
||||
},
|
||||
|
||||
getToken: function() {
|
||||
if ( this.isTokenValid() ) {
|
||||
return ($rootScope.token) ? $rootScope.token : $cookieStore.get('token');
|
||||
}
|
||||
else {
|
||||
$location.path('/login');
|
||||
}
|
||||
},
|
||||
return ($rootScope.token) ? $rootScope.token : $cookieStore.get('token');
|
||||
},
|
||||
|
||||
retrieveToken: function(username, password) {
|
||||
return $http({ method: 'POST', url: '/api/v1/authtoken/',
|
||||
return $http({ method: 'POST', url: GetBasePath('authtoken'),
|
||||
data: {"username": username, "password": password} });
|
||||
},
|
||||
|
||||
@ -70,15 +48,17 @@ angular.module('AuthService', ['ngCookies'])
|
||||
// should prevent content flash from the prior user.
|
||||
var scope = angular.element(document.getElementById('main-view')).scope();
|
||||
scope.$destroy();
|
||||
$rootScope.$destroy();
|
||||
|
||||
$rootScope.$destroy();
|
||||
$cookieStore.remove('accordions');
|
||||
$cookieStore.remove('token');
|
||||
$cookieStore.remove('token_expire');
|
||||
$cookieStore.remove('current_user');
|
||||
$cookieStore.put('userLoggedIn', false);
|
||||
$cookieStore.put('sessionExpired', false);
|
||||
$rootScope.current_user = {};
|
||||
$rootScope.license_tested = undefined;
|
||||
$rootScope.userLoggedIn = false;
|
||||
$rootScope.sessionExpired = false;
|
||||
$rootScope.token = null;
|
||||
$rootScope.token_expire = new Date(1970, 0, 1, 0, 0, 0, 0);
|
||||
},
|
||||
@ -86,7 +66,7 @@ angular.module('AuthService', ['ngCookies'])
|
||||
getLicense: function() {
|
||||
return $http({
|
||||
method: 'GET',
|
||||
url: '/api/v1/config/',
|
||||
url: GetBasePath('config'),
|
||||
headers: { 'Authorization': 'Token ' + this.getToken() }
|
||||
});
|
||||
},
|
@ -78,8 +78,14 @@ angular.module('Utilities',[])
|
||||
}
|
||||
}])
|
||||
|
||||
.factory('ProcessErrors', ['$log', 'Alert', function($log, Alert) {
|
||||
.factory('ProcessErrors', ['$cookieStore', '$log', '$location', '$rootScope', 'Alert',
|
||||
function($cookieStore, $log, $location, $rootScope, Alert) {
|
||||
return function(scope, data, status, form, defaultMsg) {
|
||||
if ($AnsibleConfig.debug_mode && console) {
|
||||
console.log('Debug status: ' + status);
|
||||
console.log('Debug data: ');
|
||||
console.log(data);
|
||||
}
|
||||
if (status == 403) {
|
||||
var msg = 'The API responded with a 403 Access Denied error. ';
|
||||
if (data['detail']) {
|
||||
@ -90,6 +96,11 @@ angular.module('Utilities',[])
|
||||
}
|
||||
Alert(defaultMsg.hdr, msg);
|
||||
}
|
||||
else if (status == 401 && data.detail && data.detail == 'Token is expired') {
|
||||
$rootScope.sessionExpired = true;
|
||||
$cookieStore.put('sessionExpired', true);
|
||||
$location.path('/login');
|
||||
}
|
||||
else if (data.non_field_errors) {
|
||||
Alert('Error!', data.non_field_errors);
|
||||
}
|
||||
@ -250,4 +261,3 @@ angular.module('Utilities',[])
|
||||
}
|
||||
}
|
||||
}]);
|
||||
|
@ -25,9 +25,9 @@
|
||||
<script src="{{ STATIC_URL }}js/awx-min.js"></script>
|
||||
{% else %}
|
||||
<script src="{{ STATIC_URL }}js/app.js"></script>
|
||||
<script src="{{ STATIC_URL }}lib/ansible/authenticate.js"></script>
|
||||
<script src="{{ STATIC_URL }}lib/ansible/rest-services.js"></script>
|
||||
<script src="{{ STATIC_URL }}lib/ansible/utilities.js"></script>
|
||||
<script src="{{ STATIC_URL }}lib/ansible/AuthService.js"></script>
|
||||
<script src="{{ STATIC_URL }}lib/ansible/RestServices.js"></script>
|
||||
<script src="{{ STATIC_URL }}lib/ansible/Utilities.js"></script>
|
||||
<script src="{{ STATIC_URL }}lib/ansible/form-generator.js"></script>
|
||||
<script src="{{ STATIC_URL }}lib/ansible/list-generator.js"></script>
|
||||
<script src="{{ STATIC_URL }}lib/ansible/prompt-dialog.js"></script>
|
||||
|
Loading…
Reference in New Issue
Block a user