I want to fetch data from an Active Directory using Java and JNDI from my EJB.
Doing this search I need to define a user and a password.
I was thinking of creating a service account (for my server) in the AD.
I will also be using Kerberos protocol and WebLogic Server.
As I understand it now, I need to create a keytab file that will contain this service account's credentials. This keytab file will then be configured in the WebLogic Server?
So, this means that I will have to state the username/password both for the keytab file and in my EJB (to fetch the data from the AD using JNDI). What is the best approach for this? Can the keytab file be defined dynamically? Which would simplify changing the password and only doing this at one place.
Have your machine join the domain, start you WebLogic server with the machine account or give access to the machine keytab, create a JDNI resource with the DirContextSourceFactory and you are able to access the AD as you wish.
Related
I'm working on an independent java application inside an Active Directory environment and the usual way for authentication is SingleSignOn.
But there I have some interfaces, which is not supporting SSO. And now I'm thinking of using LDAP for authenticate Users for the applications.
My question is: is it possible to implement LDAP inside an ActiveDirectory environment?
If yes: how does it work together and what do I have to do exactly?
If no: are there any other alternatives except for SSO?
Active Directory Domain Controllers function as LDAP servers. Servers will have clear-text LDAP bound on port 389, and servers that can auto-enroll for a certificate will have ssl encrypted LDAP bound on port 636.
Active Directory as an LDAP server is basically like any other LDAP server, BUT the schema names change. Where you would normally see uid in LDAP, Microsoft uses sAMAccountName or userPrincipalName. The domain is based on domain components (dc=something) instead of organizations (o=something). But the basic concepts remain the same.
You can look at the SRV record for the domain to return a list of candidate domain controllers to use as the LDAP server, you can configure a load balancer VIP to front the directory and add domain controllers that are intended to handle LDAP-sourced authentication traffic, or you can have a primary ldap host with a secondary host to use if that one fails to connect.
If you are using LDAP-SSL (and that's the right thing to do), you'll need to add the public key(s) for the CA chain to the cacerts file unless the domain admins have gone through the process of getting DC certs signed by a public CA. Connect to the AD servers via LDAP, bind with system creds, search for user -- something like (&(sAMAccountName=WhatUserEntered)) -- at the base DN for the organization, return the object fully qualified DN, bind with the fully qualified DN and the password the user provided. Check the result code to determine if authentication passed.
I'm developing a Java application which is run in Windows domain environment.
To authenticate users I'm using Krb5LoginModule available in JAAS.
JAAS Login Configuration File (let's call it jaas.conf) is embedded in application jar, which is stored on network share (read-only access).
Now every user can copy the application jar to his local disk, edit jaas.conf, and set his own LoginModule which would allow him to act as different user.
Is there any way to prevent this? How to secure the application?
Usr e Pwd must be provided by user. You have to call your own login interface where the user can provide username and password. Why you want put the usr&pwd into the jaas.conf?
Anyway, if you want to lock the usr&pwd you can
use certificate
crypt into the file
write into a code
I'm part of a Java Spring Web app which should be very secure. So far, on test environment we're loading database username & password from a property file which lies on classpath. The password is encrypted with a key which we load from local file system.
My job is to find a better way(more secure one) using software tools only. I was thinking about supplying the db username and password on startup of webapp or smth like that(But still does not seem ok because the DB admin should be present on startup). Other than that I'm stuck.
What is the best way to deal with this issue?
You need to lock down the database so that only the app can talk to it with minimal creds as possible.
One way is restrict it so that only app servers private IP is only accepted. Make it so the database only listens to private (internal) network connections.
The password is a red herring.
I have two windows domains A and B.
I have two servers: nasB on domain B, and webserverA on domain A.
I have two users: userB on domain B and access to nasB and userA on domain A with access to webserverA
I am running tomcat as a service on webserverA and it has the logon as property set to userA.
I have \\nasB\myFiles$\ mapped on webserverA using userB credentials. The mapping is only to allow the JVM access. I always access the drive using UNC in the code. I also have credentials in the manage network passwords. Both methods work when running any java app directly but not as a service :(
If I run tomcat as a service it throws a filenotfound except when trying to access \\nasB\myFiles$\somefile.txt. If I run tomcat using the startup.bat it can access the file fine.
I cannot run tomcat service using userB as he does not have access to webserverA. How do I let my tomcat service use the userB credentials when accessing nasB?
Don't try using mapped drives.
Given the fact users' configuration and mapped drives are available only if the user logins using interactive login, you won't be able to use such resources. Try with UNC paths and, if that doesn't work due to user restrictions, get a hand over jcifs library, it is quite handy in those cases because it allows you to authenticate when accesing the resource with the UNC path, so it reduces uncertainty about ability to read folders and files in network drives (also, configuring tomcat service to be ran as an administrative user, giving credentials that shouldn't expire,...).
I' ve faced this myself and this is just my personal view.
Create Windows user with username/password identical on both Windows servers.
Example userA/passA
Then run Tomcat Windows service with that user.
we are using JAAS to enable Single Sign On in a Java application using the Windows Kerberos ticket cache. Our jaas.conf config file looks like this:
LoginJaas {
com.sun.security.auth.module.Krb5LoginModule required
useTicketCache=true
doNotPrompt=true
debug=true;
};
With this, we can create a Jaas LoginContext and successfully get the user's Kerberos ticket. We send this ticket to out server application using JMI. What we don't manage to do though is to verify on the server that the Kerberos ticket was in fact created by our Active Directory.
At the moment, we do a very insecure validation of the ticket by simply checking if the Server Principal (KerberosTicket.getServer()) name has our domain name in the realm part. But of course, anyone could set up an own Kerberos server with the same realm name and use that ticket to start the application.
One idea I have found was to authenticate against the Active Directory LDAP using the Kerberos ticket. Unfortunately, we use Windows 7 and re-using the Kerberos ticket to authenticate against the LDAP only works when setting a Registry entry (see http://java.sun.com/j2se/1.5.0/docs/guide/security/jgss/tutorials/Troubleshooting.html, search for allowtgtsessionkey). This is unacceptable for our users.
Is there any way to validate the ticket against our Active Directory server? I suspect there is a way to check if the KerberosTicket.getServer() ticket equals the ticket of our server, but I have no idea how to do that. UPDATE: KerberosTicket().getServer() only returns a KerberosPrincipal that contains nothing but the server ticket name and realm, so it is not suitable for validation.
Thanks for your help,
memminger
As you mentioned, the proper way to solve this is by kerberizing your service, which is the whole point of the Kerberos protocol (authenticating clients against servers). Ticket reuse doesn't work exactly because it'd be a security problem if it did.
A Kerberos service does not need to "log into Active Directory", it just needs to have a shared key with AD.
BTW, to get SSO using JAAS requires having that allowtgtsessionkey set, there's no way around that on Windows.
As no one seems to really know an answer to this, I suppose we have to make a proper Kerberos service out of our server application. One that logs in to the Active Directory itself and that has the ServicePrincipalName attribute set properly. Kind of like SPNEGO does for HTTP. A good starting point how to do that will be the SPNEGO Servlet filter on SourceForge (http://spnego.sourceforge.net/). http://thejavamonkey.blogspot.com/2008/04/clientserver-hello-world-in-kerberos.html is also a very good example of how to do Service logon.
Unfortunately, this leads to the same problem with the registry key, so I posted a new question on Is there a way in Java or a command-line util to obtain a Kerberos ticket for a service using the native SSPI API?.