Whats is JAAS?
Java Authentication and
Authorization Service (JAAS): JAAS is a set of APIs that enable
services to authenticate and enforce access controls upon users. JAAS provides
a pluggable and extensible framework for programmatic user authentication and
authorization. JAAS is a core Java SE API and is an underlying technology for
Java EE security mechanisms. It is also known as container provided security.
A container provides two kinds of security:
declarative and programmatic.
Declarative security expresses
an application component’s security requirements by using either deployment
descriptors or annotations.
Programmatic security is
embedded in an application and is used to make
security decisions. Programmatic security is useful when declarative security
alone is not sufficient to express the security model of an application.
The task of securing a web application can primarily be broken down into following sub tasks:
a) Develop/add desired declarative (annotation) and/or programmatic security and artifacts (like login page) to the application.
b) Set up security in the container; which includes
- Configuring Security Realm
- Setting up security repository (file or jdbc)
- Configuring Security for Application in web.xml
- Setting up Groups and Roles in web.xml
- Enable secure communication (HTTPS) in web.xml
c) Configure application security i.e define how to authenticate and who has what authorizations, in web.xml and glassfish-web.xml
I have created a sample application to demonstrate JAAS, which can be Downloaded from Git here
About the sample application.
A very simple JSF based application which the following security requirements:1) Only validated users should be able to access this application.
2) Extra security feature is needed for pages in "admin" sub-context; the pages should be accessible only to users belonging to "Admin" role and secured using SSL.
Getting started
Add Security in the application
To take care of the first security requirement, we will add "Form Based Authentication" to the application i.e. when an user tries to access application, he be presented with a login form.
Here "j_username", "j_password" and "j_security_check" are JEE standards, use them as is, container understands and handles it based on the configuration that we will be doing later.To take care of second security requirement (partially here, the rest is taken care with configuration in web.xml) , we will add programmatic security (see index.xhtml).
<h:link value="click For Admin Page - " outcome="/admin/adminOnly" rendered="#{request.isUserInRole('Admin')}" />
The link for Admin page will appear only if the user has Admin Role.
Now lets see how to set up "Container" security and add users and groups.
Configure Security Realm in Glassfish
Start/load glassfish domain administration module in a browser and go to Configuration -> Server-Config -> Security -> RealmsCreate a New Realm
set form fields to following value
Name LoginRealm
className com.sun.enterprise.security.auth.realm.file.FileRealm (from dropdown menu)
JAAS Context fileRealm
keyFile C:\\glassfish4\\glassfish\\domains\\domain1\\loginRealm\\users.txt
Assign Groups Basic, Admin
Note: make sure JAAS Context is "fileRealm"
click OK, and the Realm definition should look like this.
Click on Manage User add following users and their roles
User Id: David Group: Basic, Admin Password: demo
User Id: Mike Group: Basic Password: demo
User Id: Temp Password: demo
This completes Glassfish Container Security configuration.
Configure Application Security:
All the security is defined in web.xml.
First we need to specify the login mechanism and
<login-config>
<auth-method>FORM</auth-method>
<realm-name>LoginRealm</realm-name>
<form-login-config>
<form-login-page>/faces/login.xhtml</form-login-page>
<form-error-page>/faces/login.xhtml</form-error-page>
</form-login-config>
</login-config>
The <auth-method> specifies that the application uses "Form" based authentication; <realm-name> specifies to use LoginRealm (the one we just defined in Glassfish) for authentication and authorization; <form-login-page> specifies the actual custom login page.
Now its time to define Roles of the application
<security-role>
<description>Basic User</description>
<role-name>Basic</role-name>
</security-role>
<security-role>
<description>AdminUser</description>
<role-name>Admin</role-name>
</security-role>
These Roles will be used later in auth-constraints for web-resources.
Now on to adding Access Control and SSL to the application
<security-constraint>
<display-name>AdminAccess</display-name>
<web-resource-collection>
<web-resource-name>AllAdminOperations</web-resource-name>
<description/>
<url-pattern>/faces/admin/*</url-pattern>
</web-resource-collection>
<auth-constraint>
<description>Admin Only Access</description>
<role-name>Admin</role-name>
</auth-constraint>
<user-data-constraint>
<description>Secured Login</description>
<transport-guarantee>CONFIDENTIAL</transport-guarantee>
</user-data-constraint>
</security-constraint>
A security constraint is used to define the access privileges to a collection of resources using their URL mapping. <url-pattern> within <web-resource-collection> describes set of resources that need to be protected. <auth-constraint> <role-name> describes Roles that can access resources specified by above pattern (In our case only users with Admin role can access admin pages). <user-data-constraint> <transport-guarantee> describes whether data in transfer needs to be protected or Not. Usually CONFIDENTIAL or INTEGRAL means SSL is required.
Now map Roles to Group we just defined in the Glassfish container
<security-role-mapping>
<role-name>Admin</role-name>
<group-name>Admin</group-name>
</security-role-mapping>
<security-role-mapping>
<role-name>Basic</role-name>
<group-name>Basic</group-name>
</security-role-mapping>
That's all what is required to set up a secured web application.
Run Application
Now deploy the downloaded application to the glassfish server and run it; First you will be presented with a login page, enter credential "Mike" & "demo", these being valid credentials, you will be redirected to index.xhtml. Now click on "logout" link, and you will be redirected back to the login screen. This time enter credential "David" & "demo", again these being valid credentials,you will be again redirected to index.xhtml., but this time you will see a link to "admin" page (link visible to only Admin group). click on it, [you will get a security alert stating that the connection is untrusted; ignore warning and click proceed for now] you will be redirected to adminOnly.xhtml, also notice that the URL protocol in the address bar has changed to "https".Note: adminOnly.xhtml is configured such that only users in "Admin" group can access it and communication is protected with SSL.
As you can see adding web security is very simple and JEE provides a very clean and non intrusive way of managing security.
If you have any question or suggestion, please post your comment.
Prasanna Bhale
This comment has been removed by the author.
ReplyDeleteThank you this works ! super !!!!
ReplyDeleteCan I change my password in application? How can I do?
ReplyDeleteHow if I want the admin to create users and assign Roles, How can we make a web page for that?
ReplyDeletethank you for your great post,
ReplyDeletebut one remark
instead of using
C:\\glassfish4\\glassfish\\domains\\domain1\\loginRealm\\users.txt
use
${com.sun.aas.instanceRoot}/loginRealm/users.txt
to avoid hard coding
Login.xhtml takes me to the context Root while printing "404 resource is not available.
ReplyDelete