This discussion is archived
2 Replies Latest reply: Oct 17, 2012 8:07 PM by Ganesh.. RSS

How to authenticate (JAAS) a user programmatically for batch processing

129070 Newbie
Currently Being Moderated
HI,

We're struggling to get our batch user proper authenticated and authorized to enable the batch user to execute various jobs. The Jobs are initially executed by a Quartz scheduler which in turn invokes to execute method on the specific batch job controller class. In this class we'll like to login the batch user before the processing starts and again logout the user before the jobs ends. The batch job processing does some updates on security protected entities - that's where the problems starts. To be able to update certain ADF Entities, the batch user must be in "batch-role". The permissions is configured in the jazn-data.xml file. ADF Security is enabled for the project and various entities is security protected. The application is deployed in one EAR file in into Weblogic 10.3.5. We're using JDeveloper 11.1.2.1.

When we login to the application through the login form in the application, then the security permissions is applied as they should and only users with the correct roles is able to update certain security protected entities. The login form uses something like this, to authenticate the user:
Subject subject = weblogic.security.services.Authentication.login(handler);
weblogic.servlet.security.ServletAuthentication.runAs(mySubject, request);
...

We'd like to do the same kind of authentication in the batch controller class, like:
Subject subject = weblogic.security.services.Authentication.login(new BatchLoginCallBackHandler());
weblogic.security.Security.runAs(subject,
new PrivilegedAction() {
public Object run() {
try {
executeJob(jec);
} catch (JobExecutionException e) {
e.printStackTrace();
}
return null;
}
});
...

But this doesn't work. When the job accesses ADFContext.getSecurityContext() it isn't the correct user which is logged in (actually it is the users which initially started the scheduler). And even thouth

boolean inBatchRole = aDFContext.getSecurityContext().isUserInRole("batch-role");

returns true, the user is not allowed to update entities which requires this role to allow an update. It some how seems to, that the login does affect the ADF application module (ADF Context).

We've tried a lot of other things but we're not able to login the batch user in the same way as the ADF Faces are.

Can anyone please help us?

Regards
Jacob
  • 1. Re: How to authenticate (JAAS) a user programmatically for batch processing
    597173 Newbie
    Currently Being Moderated
    We have the same requirement.
    We've tried these approaches, with no success:

    AuthenticationService vAuthenticationService = AuthenticationServiceUtil.getAuthenticationService();
    vAuthenticationService.login("user", "password");

    resulting in Caused By: oracle.adf.share.security.ADFSecurityRuntimeException: EXC_UNSUPPORTED_AUTHENTICATION_OPERATION

    and JAASAuthenticationService authService = new JAASAuthenticationService();
    authService.login("user", "password");

    Caused By: java.security.AccessControlException: access denied (oracle.security.jps.JpsPermission AppSecurityContext.setApplicationID.default)

    If I test these methods in a simple java class's main method, they work.
    I feel I'm missing something, could somebody please tell me if I'm thinking wrong: We have an application made of a Model project, a UI project(ADF) and a scheduler project(Quartz). Both the UI project and the scheduler use the Model project(ADF BC). We deploy 2 ears, one for the UI and one for the scheduler. The UI application's security is working just fine, and it's about time we enforce security for the scheduler. Scheduler has a Listener that extends QuartzListener, witch implements ServletContextListener. In the contextInitialized we launch different jobs using quartz. How could we make these jobs authenticate using some predefined user credentials?
  • 2. Re: How to authenticate (JAAS) a user programmatically for batch processing
    Ganesh.. Explorer
    Currently Being Moderated
    Hi,
    You can do a programmatic login of any user you want with this code :
              CallbackHandler cb = new CustomCallbackHandler(username, passwordChar);
              LoginContext loginContext = jpsContext.getServiceInstance(LoginService.class);
              loginContext.login();
              Subject subject = loginContext.getSubject();

    This subject gives you the principles of the programmtically logged in user.

    In CustomCallbackHandler :

         public CustomCallbackHandler(String name, char[] password) {
              this.name = name;
              this.password = password.clone();
         }


         public void handle(Callback[] callbacks) throws IOException, UnsupportedCallbackException {
              for (Callback cb : callbacks) {
                   if (cb instanceof NameCallback) {
                        ((NameCallback) cb).setName(name);
                   } else if (cb instanceof PasswordCallback) {
                        ((PasswordCallback) cb).setPassword(password);
                   }
              }
         }

    Make sure LoginService service instance is present in jps-config.xml

Legend

  • Correct Answers - 10 points
  • Helpful Answers - 5 points