2016-04-12 2 views
0

У меня есть программа AngularJS, которая использует услуги RESTful, предоставляемые через GlassFish 4.1. У меня есть требования к аутентификации для служб RESTful, которые определены в файле web.xml. Во время разработки я полагался на GlassFish, чтобы отменить запрос на аутентификацию браузера всякий раз, когда веб-сайт пытается получить доступ к службе RESTful, и это сработало просто отлично. Теперь, однако, я хочу использовать ui-router и контроллер входа для отправки имени пользователя и пароля в GlassFish через HTTP-сообщение. HTTP-сообщение не работает, так что пока я только что отключил требование проверки подлинности на стороне GlassFish и получил ложный логин, который притворяется успешным входом в GlassFish, а затем ui-router заботится об остальном после того, как пользователь «вошел в систему». Маршрутизация после аутентификации работает красиво, поэтому проблем нет. Моя проблема сводится к следующему: как правильно отправить имя пользователя и пароль на сервер GlassFish в его текущей конфигурации, где требуется аутентификация при доступе к службе? Ниже находится web.xml и контроллер входа. Спасибо за любую помощь.Базовая аутентификация на GlassFish 4.1 Server через AngularJS

web.xml

<?xml version="1.0" encoding="UTF-8"?> 
<web-app version="3.1" xmlns="http://xmlns.jcp.org/xml/ns/javaee" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:schemaLocation="http://xmlns.jcp.org/xml/ns/javaee http://xmlns.jcp.org/xml/ns/javaee/web-app_3_1.xsd"> 
    <session-config> 
     <session-timeout> 
     30 
     </session-timeout> 
    </session-config> 
    <security-constraint> 
     <web-resource-collection> 
     <web-resource-name>Enforce TLS</web-resource-name> 
     <description/> 
     <url-pattern>/*</url-pattern> 
     </web-resource-collection> 
     <user-data-constraint> 
      <!-- require SSL --> 
      <description/> 
      <transport-guarantee>CONFIDENTIAL</transport-guarantee> 
     </user-data-constraint> 
    </security-constraint> 
    <security-constraint> 
     <web-resource-collection> 
      <web-resource-name>Secure Pages</web-resource-name> 
      <description/> 
      <url-pattern>/tsn/*</url-pattern> 
     </web-resource-collection> 
     <auth-constraint> 
      <role-name>tsnadmin</role-name> 
      <role-name>tester</role-name> 
     </auth-constraint> 
    <user-data-constraint> 
     <description/> 
     <transport-guarantee>CONFIDENTIAL</transport-guarantee> 
    </user-data-constraint> 
    </security-constraint> 
    <login-config> 
     <auth-method>BASIC</auth-method> 
     <realm-name>tsnRealm</realm-name> 
    </login-config> 
    <security-role> 
     <role-name>tsnadmin</role-name> 
    </security-role> 
    <security-role> 
     <role-name>tester</role-name> 
    </security-role> 
</web-app> 

Контроллер:

'use strict'; 

angular.module('pisuiteClientExpApp') 
    .controller('LoginModalCtrl', function (
      $scope, 
      $timeout, 
      $http, 
      userRoles, 
      auagByUserSvc) { 
     this.cancel = $scope.$dismiss; 

     /*this.submit = function() { 
      $scope.dataLoading = true; 
      $timeout(function() { 
      $scope.user; 
      if ($scope.username === 'rpurvis') { 
      $scope.user = {uname: 'rpurvis', role: userRoles.tester, 
      success: $scope.username === 'rpurvis' && $scope.password === 'password'}; 
      } else if ($scope.username === userRoles.admin) { 
      $scope.user = {uname: userRoles.admin, role: userRoles.admin, 
      success: $scope.username === userRoles.admin && $scope.password === 'password'}; 
      } 
      if (!$scope.user.success) { 
      $scope.user.message = 'Username or password is incorrect'; 
      $scope.user = null; 
      $scope.$close($scope.user); 
      } else { 
      auagByUserSvc.get({user: $scope.user.uname}, function (auag_success) { 
      /*console.log("setting images to an array of length: " + data.length) 
      if (auag_success.length > 0) { 
      $scope.user.role = auag_success[0].idAuthGroup.idAuthGroup; 
      $scope.user.inspectorid = auag_success[0].idAuthUser.inspectorid; 
      } 
      $scope.$close($scope.user); 
      }, function (error) { 
      $scope.$close($scope.user); 
      }); 
      } 
      }, 1000);*/ 

      var req = { 
      method: 'POST', 
      url: 'https://localhost:9191/PISuiteService_Exp/', 
      headers: {'Content-Type': 'application/x-www-form-urlencoded'}, 
      transformRequest: function (obj) { 
       var str = []; 
       for (var p in obj) 
        str.push(encodeURIComponent(p) + "=" + encodeURIComponent(obj[p])); 
       return str.join("&"); 
      }, 
      data: {username: $scope.username, password: $scope.password} 
      }; 

      $http(req).then(function (success) { 
      $scope.user = {uname: $scope.username}; 
      console.log("in post success"); 
      auagByUserSvc.get({user: $scope.username}, function (auag_success) { 
       if (auag_success.length > 0) { 
        $scope.user.role = auag_success[0].idAuthGroup.idAuthGroup; 
        $scope.user.inspectorid = auag_success[0].idAuthUser.inspectorid; 
       } 
       $scope.$close($scope.user); 
      }, function (error) { 
       $scope.$close($scope.user); 
      }); 
      }, function (error) { 
      console.log("in post error"); 
      $scope.user.message = 'Username or password is incorrect'; 
      $scope.user = null; 
      $scope.$close($scope.user); 
      }, function (progress) { 
      console.log("in post progress"); 
      }); 
     }; 
    }); 

ответ

0

Для авторизации с REST сервера, вам необходимо отправить токен авторизации в заголовке каждого запроса. Значение маркера начинается с BASIC

"Authorization" = "Basic " + btoa(username + ":" + password) 

Вот пример использования JQuery: How to use Basic Auth with jQuery and AJAX?.

С угловатыми, вы можете создать свой запрос, как это (проверить заголовки полей):

var req = { 
     method: 'POST', 
     url: 'https://localhost:9191/PISuiteService_Exp/', 
     headers: { 
      'Content-Type': 'application/x-www-form-urlencoded', 
      'Authorization': 'Basic ' + btoa($scope.username + ':' + $scope.password), 
     }, 
     transformRequest: function (obj) { 
      var str = []; 
      for (var p in obj) 
       str.push(encodeURIComponent(p) + "=" + encodeURIComponent(obj[p])); 
      return str.join("&"); 
     } 
     }; 

выше лицом без аутентификации со службой REST рекомендуется, так как REST услуги должны быть лицами без гражданства по определению.

Однако, возможно, вы захотите пройти аутентификацию в начале сеанса один раз. Вероятно, это было то, что у вас было на месте, так как GlassFish автоматически запускал форму входа в систему, когда не аутентифицировался, и сохранял регистрационную информацию для остальной части сеанса.

В этом случае вы можете использовать аутентификацию на основе форм, чтобы отправлять данные для входа по запросу POST. Для получения дополнительной информации см. Java EE tutorial, я просто отправлю пример формы оттуда:

<form method="POST" action="j_security_check"> 
<input type="text" name="j_username"> 
<input type="password" name="j_password"> 
</form> 
+0

Благодарим вас, OndrejM, за ваш ответ. К сожалению, он все еще не работает. Вы упомянули, что для аутентификации на сервере REST мне нужно отправить токен авторизации с каждым заголовком. Однако этого не произошло, когда я полагался исключительно на сервер GlassFish, чтобы запустить запрос аутентификации, когда он отправляет ответ HTTP 401 на первый запрос службы REST. Я использую угловой заводской сервис для доступа к службам RESTful и не делал ничего конкретного в HTTP-запросах для получения данных. Я проверяю один раз на службу, и все. Я надеюсь, что так будет. –

+0

Поскольку службы REST должны быть неактивными, я рекомендую использовать HTTP-заголовки с каждым запросом. Но если вы хотите иметь такое же поведение в отношении состояния, как и раньше, я добавил дополнительную информацию в ответ на проверку подлинности на основе форм. Пример кода представляет собой HTML-форму, но в JavaScript должен быть легко построить запрос POST. – OndrejM

+0

Еще раз спасибо за помощь OndrejM. Все еще есть проблемы, но я действительно верю, что ваш первый ответ - путь. Я думаю, это означает, что мне действительно нужно задать вопрос: «Как мне настроить службы RESTful в GlassFish, чтобы для каждого запроса требовался токен авторизации?«Я искал, но не нашел убедительного примера, когда кто-то настраивал это. Кто-нибудь знает такой пример? –

Смежные вопросы