Java web application authentication - account design - java

I am working on a web project, backend is Java & Mysql, the client include web(html5) and app(IOS/Android), I have some doubt in design the account of the system.
There are 3 different types of account:
Shop, shop account will have its own website,
Customer, customer access shop/commodity via app(IOS/Android),
Admin, manage everything of the system.
My basic idea of authentication:
There will be account / role / permission table for sure, because both admin & customer will have quite complex user permission issue, customer also have different permission due to their history behavior.
I have kind decided to use Apache Shiro, due to its simplicity & distributed session.
My question is:
(1) Should I create a single account table or 3 individual account tables.
(2) Any advise on design of 3 tables:
account / role / permission ?

If in your first question you're asking how to design a database schema for three very distinct entities (admin user, customer user and shop owner), I suggest you don't combine them into a single table, because they are different concepts and will likely have different features.
You kind of answered your own question, since "ease of programming" rarely trumps business rules/logic.
Your decision to use an existing security framework, or to roll your own, should be independent of the data model for your core business entities.
If you don't want to use a managed solution like Stormpath, and haven't settled on Shiro yet, check out OACC, an open-source permission-based security framework for Java with support for hierarchical security domains, super users, permission inheritance and impersonation.
It might be a good fit for your project because:
you won't need to clutter your database design with authorization-related aspects
OACC was designed for multi-tenancy application architectures (like your project's "shops")
it allows for impersonation, which is a powerful feature if you need to support customer service representatives without giving them "admin" privileges
[Disclaimer: I am a maintainer and co-developer of OACC]

I suggest you to consider delegating all your user-management needs to Stormpath. With Stormpaht, you do not need to worry about such low-level concerns, all your data is securely managed and stored. Stormpath provides:
User management API with different SDKs: node.js, express, java, rest, python, flask.
Off the shelf Hosted Login: login, registration, and password reset.
Off the shelf ID Site to power Single Sign-On across your applications
API keys for your users, secured with HTTP Basic Auth or OAuth2
Social Login: Facebook, Google, LinkedIn, Github
Integration with Shiro and Spring Security
Integration with Active Directory and LDAP
With Stormpath you will only need to create Groups which will represent your roles. Inside your groups and accounts, you can also create finer-grained concepts like permissions using our flexible Custom Data concept.
As mentioned above, we also support Shiro integration, where you can model all your security needs with Shiro while using Stormpath as the authentication and authorization data provider. Please take a look at our Stormpath Shiro plugin and at our Sample Shiro Web App.
Disclaimer, I am an active Stormpath contributor.

To be short: you don't need role / permission tables :)
I would decide first do you really need RBAC security model? Your application looks like a perfect use case for hexagonal architecture with 3 separate isolated front-end parts: Consumer, Shop, Admin. Then I would advise to build separate authentication/authorization mechanism for each of these front-ends. In this case you are flexible to choose the best tool for the purpose (OAuth2, OpenID, LDAP whatever) and follow least common mechanism security principle. Your application doesn't look like the one which needs authorization on method level, thus you don't need RBAC.

I would design each Java object depending on its individual needs. Get clear about what you have to create. Are there overlappings in the account types? Shall a Shop account be able to buy something like (that is. extend) a Customer, or shall an Admin implement both a Shop and a Customer? Shall the address of a Customer, living in the same street as a Shop is located, change if the Shop reports the street got renamed? Does the phone number’s area code depend on the city?
If your Java objects do their job properly, think about the O/R mapping in a second step. Perhaps it will be even very different from what you may think now (just think of carrier codes in telephone numbers that require inline replacement, Packstation boths, Shops with multiple persons of contact, different address layouts in different countries …).
In general, make sure your address fields properly support UTF-8 for diacritics, greek, cyrillic or arabic addresses.

(1) Should I create a single account table or 3 individual account tables.
Yes, I think you should design a single one, as an account is going to have similar data for all 3 types.
(2) Any advise on design of 3 tables: account / role / permission ?
account: PK account_id int, FK role_id int
role: PK role_id int, account_permission enum(admin [0], customer [1])
You do not need a permission table, you may handle your permission levels in your application code, using composite design pattern, where you can have multiple hierarchical levels of admin or customer permissions. Reason for this is it's better to declare your business logic in your model code rather than database design, database is there to persist data with as optimised and normalised state as possible. I suppose you can then use dependency injection to your composite permission hierarchy depending on customer behaviour, which needs to be held in the database under a table, ie named customer_behaviour, with certain columns "ticked" as they behave certain ways.
Hope this helps.

Related

Container vs Servlet Authentication

I am creating a web application using Servlets and JPA. I have a user table that stores usernames,passwords and roles. I would like to create Login and user registration functionality for these users so that some of my content is accessible to certain users.
As I ready through the Servlet specification and also Tomcat, which is the container I use, I have come across two ways of defining users and roles of the system.
The Tomcat specification suggests I can use Realms to tie into another database so that I can choose to use SSO if I wish.
Servlets have their own way of defining users and roles using the web.xml, such as basic authentication for example, so does the Servlet container, using Realms.
But to create users and roles in the Servlet and the Container seems to be something that the system administrator would do. What I am looking for is a self-registration.
This question above highlights my confusion with these approaches, I don’t know if the way I want to proceed is correct or secure?
Can someone explain the differences between these methods of authentication?
Why choose one over the other?
Is my plan to use the self registration a bad idea or insecure for J2E Model?
If you store your user ids and passwords and roles in your database and validate user input against that, you are on your own thereafter. What that means is that later when you may want to restrict access to a particular content for a specific set of user roles, you will have to look up the role stored in your db table against the user and write code that allows/restrict the user.
However if you 'push' the user to the underlying container, then the container can do most of the stuff the application's behalf (that is where the stuff about realms and roles etc come in). A good starting point to understand this is to read a tutorial on JAAS
I think you are confused between users and roles. In your web.xml you have to associate roles to resources, for example "all the requests to /admin should have role Administrator", and then, you create users under your administration tool and asign to that users the proper roles.

Running Google App Engine application on multiple customer domains

I want to allow my company’s customers to integrate our Google App Engine application into their domains. For example, let’s say one customer owns the domain coolcustomer.com and wants to make our app accessible at service.coolcustomer.com.
This article discusses how to set up multi-tenancy internally, but does not mention how to associate client domains with an app.
Ideally, I’d like to allow customers to associate a sub-domain in a self-service manner. This, of course, brings up the issue of validating that the customer has permission to add a sub-domain to a domain name.
What is the best approach to accomplish this?
The customer will add your application as a service via their Google Apps control panel. Some of the details are outlined here.
To handle multi-tenancy you will probably want to use the server host name. From the host name, you'll be able to get the domain name to use for your namespace.
You'll have to handle validating the domain is a valid customer in your app. I would probably let them register, then provide instructions for setting up the Google Apps mapping.
If you want to allow them to login using Google Apps accounts tied to their domain you'll need to use OpenID (federated login).

Help choosing authentication method

I need to choose an authentication method for an application installed and integrated in customers environment. There are two types of environments - windows and linux/unix. Application is user based, no web stuff, pure Java. The requirement is to authenticate users which will use my application against customer provided user base. Meaning, customer installs my app, but uses his own users to grant or deny access to my app. Typical, right?
I have three options to consider and I need to pick up the one which would be a) the most flexible to cover most common modern environments and b) would take least effort while stay robust and standard.
Option (1) - Authenticate locally managing user credentials in some local storage, e.g. file. Customer would then add his users to my application and it will then check the passwords. Simple, clumsy but would work. Customers would have to punch every user they want to grant access to my app using some UI we will have to provide. Lots of work for me, headache to the customer.
Option (2) - Use LDAP authentication. Customers would tell my app where to look for users and I will walk their directory resolving names into user names and trying to bind with found password. This is better approach IMO, but more fragile because I will have to walk an unknown directory structure and who knows if this will be permitted everywhere. Would be harder to test since there are many LDAP implementation out there, last thing I want is drowning in this voodoo.
Option(3) - Use plain Kerberos authentication. Customers would tell my app what realm (domain) and which KDC (key distribution center) to use. In ideal world these two parameters would be all I need to set while customers could use their own administration tools to configure domain and kdc. My application would simply delegate user credentials to this third party (using JAAS or Spring security) and consider success when third party is happy with them.
I personally prefer #3, but not sure what surprises I might face. Would this cover windows and *nix systems entirely? Is there another option to consider?
Go with LDAP. Access is very easy, and the only parameter you need is the LDAP Server (and ActiveDirectory is one). If the user exists and the password is correct, he will always be able to log into the LDAP server.

How to implement Administrator rights in Java Application?

I am developing a Data Modeling Software that is implemented in Java. This application converts the textual data (stored in a database) to graphical form so that users can interpret the data in a more efficient form. Now, this application will be accessed by 3 kinds of persons:
1. Managers (who can fill the database with data and they can also view the visual form of the data after entering the data into the database)
2. Viewers (who can only view the visual form of data that has been filled by managers)
3. Administrators (who can create and manage other administrators, managers and viewers)
Now, how to implement 3 diff. views of the same application.
Note: Managers, Viewers and Administrators can be located in any part of the world and should access the application through internet.
One idea that came in my mind is as follows:
Step1: Code all the business logic in EJBs so that it can be used in distributed environment (means which can be accessed by several users through internet)
Step2: Code 3 Swing GUI Clients: One for administrators, one for managers and one for viewers. These 3 GUI clients can access business logic written in EJBs.
Step3: Distribute the clients corresponding to their users. For instance, manager client to managers.
=================================QUESTIONS=======================================
Q1. Is the above approach is correct?
Q2. This is very common functionality that various softwares have. So, Do they implement this kind of functionality through this way or any other way?
Q3. If any other approach would be more better, then what is that approach?
no
no
yes
Making different clients for different security roles is a :
security hole - what if a viewer obtains the administrator version?
hard to maintain
The way to do this is:
make the data transferred to the client dependent on a security check
also make various parts of the UI visible/enabled depending on that security check
the security check is made on the server
the security check depends on the currently logged user
the user logs in on startup, using his credentials (username/password or digital certificate)
the security roles (administrator, moderator, viewer) are stored on the server side.
Then, if needed, you can extend the security model by adding:
differentiation between per-user and per-role rights
rights on specific resources
transitive rights
permissions for specific actions
But such a complex user rights and security model is perhaps not needed in your application.
I agree with #Bozho except for the following:
make various parts of the UI visible/enabled depending on a security check
You actually need to make sure that unwanted access to the data, etc is blocked on the server side, irrespective of whether the client-side UI is visible / enabled. The reason for this is that any client-side UI disabling code can be subverted. Indeed, a bad guy could even entirely bypass your UIs and reverse engineer the application-specific protocols between your client and server code.
This is not to say that you shouldn't also disable / hide parts of the UI that the user is not allowed to use. It is just not a good basis for decent security / access control.
(UPDATE : #Bozho has ammended his answer now to add server-side blocking to his list. So I now agree with it entirely. )
I agree with Bozho. Another points with the three client approach is: what if the user somehow figures out how to send the operations which isn't available in his client? What if the same user has two roles (hence is required to have two clients). And of course you will have plenty to do maintaining one client...

User Login in Java - JAAS/JNDI/GSSAPI

What is the best way to design a user login mechanism using Java? What are the best practices to be followed to architect a secure and robust login mechanism?
What is the difference between JAAS, JNDI and GSSAPI? How do you decide which one to choose?
Single sign on (SSO) is one of hte best practices. Using one set of credentials for authentication (not necessarily authorization) for a group of applications.
Sun's java based open source -- OpenSSO solution is available at https://opensso.dev.java.net/. This includes OpenDS, an open source LDAP server.
few things you need to consider is
1) is it OK to let the user login simultaneously from multiple computers
2) how to mix authentication and authorization info in the same LDAP server
Some patterns in this area can be obtained from the book : http://www.coresecuritypatterns.com/patterns.htm
It depends on your user referential.
You need to be able to connect your login java module with that base. it is is LDAP, you might consider framework like OpenLDAP.
Plus you have to consider what is include in your "login" perimeter: It is is an "habilitation" login process, you need to have more that just the user name, but also other parameters helping your java module to grant him access (its group, which might be in LDAP, but also the kind of action he wants to make, in order to check if he has the required accreditation level)
I really like Spring Security. It's pretty easy to set up if you've got a Spring project, of course, but I've seen parts of it integrated into other implementations.

Categories