So as advised I am extending my earlier question to pick up the username of the system opening my web page and then authenticating that user accordingly. Thanks to some useful advice and after long hours of reading and testing I managed to write a very simple Java Applet which I embedded in login.xhtml page. However, now I'm stuck over next appropriate step in order to pass the username picked up by the java applet to the login managed bean. Allowing my web page to authenticate user based on their system's username without user actually having to put his username in the login.xhtml page. Meanwhile trying to search for the next appropriate step I feel my understanding going up and down and sideways. What best i could pick is that now in order to pass the username picked up from java applet to the login bean I will have to write JavaScript? But I am not sure if this is really what is required or there is another appropriate step to handle this more elegantly. Please excuse my limited knowledge on this.
Updates made based on the answer
Java Applet Code
import java.applet.Applet;
public class SSOApplet extends Applet {
/**
*
*/
private static final long serialVersionUID = 1L;
String sysUser = null;
public String getSystemUsername() {
try {
sysUser = System.getProperty("user.name");
return sysUser;
} catch (Exception e) {
System.out.println(e);
return null;
}
}
public void sendToJs() {
String name = getSystemUsername();
System.out.println("sendTOJS picked this username of user" + name);
try {
JSObject window = JSObject.getWindow(this);
window.call("updateServer", new Object[] {name});
} catch (JSException jse) {
jse.printStackTrace();
}
}
}
Code Snippet from my login.xhtml
<script type="text/javascript">
function updateServer(name) {
document.getElementById('username').value = name;
document.getElementById('button').click();
}
</script>
<object>
<param name="myApplet" value="SSOApplet.class" />
</object>
Would be really helpful if someone could advice the next appropriate step. Thanks a lot in advance!
UserDaoBean Controller class
public boolean validateUser(String username) {
try {
String checkUser = (String) entityManager
.createQuery(
"select u.username from User u where u.username =:username")
.setParameter("username", username).getSingleResult();
System.out.println("User found in database: " + checkUser);
if (checkUser.equalsIgnoreCase(username)) {
System.out.println("Loggin sucessful!");
return true;
}
} catch (NoResultException e) {
System.out.println("No result found in database");
return false;
}
return false;
}
Login Managed Bean
@ManagedBean(name = "loginBean")
@RequestScoped
public class LoginBean implements Serializable {
/**
*
*/
private static final long serialVersionUID = 1L;
@EJB
private UserDaoBean uDB;
@EJB
private UserGroupDaoBean uGDB;
private User userId;
SSOApplet myapplet = new SSOApplet();
public String username = myapplet.getSystemUsername();
// private String username;
public String getUsername() {
return username;
}
public void setUsername(String username) {
this.username = username;
}
public String login() {
FacesContext context = FacesContext.getCurrentInstance();
System.out.println("JS sent this username" + username);
if (uDB.validateUser(username)) {
userId = uDB.findUser(username);
context.getExternalContext().getSessionMap().put("userId", userId);
if (uGDB.validateGroup(userId)) {
return "home.jsf?faces-redirect=true&includeViewParams=true";
}
return "normalHome.jsf?faces-redirect=true&includeViewParams=true";
} else {
FacesMessage message = new FacesMessage();
message.setSeverity(FacesMessage.SEVERITY_ERROR);
message.setSummary("Username doesn't exists! OR User is trying to login from someone else's account");
context.addMessage("", message);
return null;
}
}
Message Printed in Console
INFO: JS sent this usernamenull INFO: No result found in database INFO: WARNING: FacesMessage(s) have been enqueued, but may not have been displayed. sourceId=[severity=(ERROR 2), summary=(Username doesn't exists! OR User is trying to login from someone else's account), detail=(Username doesn't exists! OR User is trying to login from someone else's account)]
Exception after invoking Applet in Bean
WARNING: StandardWrapperValve[Faces Servlet]: PWC1406: Servlet.service() for servlet Faces Servlet threw exception
java.lang.ClassNotFoundException: netscape.javascript.JSException
at org.glassfish.web.loader.WebappClassLoader.loadClass(WebappClassLoader.java:1509)
at org.glassfish.web.loader.WebappClassLoader.loadClass(WebappClassLoader.java:1359)
at beans.LoginBean.<init>(LoginBean.java:31)
at sun.reflect.NativeConstructorAccessorImpl.newInstance0(Native Method)
at sun.reflect.NativeConstructorAccessorImpl.newInstance(NativeConstructorAccessorImpl.java:57)
at sun.reflect.DelegatingConstructorAccessorImpl.newInstance(DelegatingConstructorAccessorImpl.java:45)
at java.lang.reflect.Constructor.newInstance(Constructor.java:525)
at java.lang.Class.newInstance0(Class.java:372)
at java.lang.Class.newInstance(Class.java:325)
at com.sun.faces.mgbean.BeanBuilder.newBeanInstance(BeanBuilder.java:188)
at com.sun.faces.mgbean.BeanBuilder.build(BeanBuilder.java:102)
at com.sun.faces.mgbean.BeanManager.createAndPush(BeanManager.java:409)
at com.sun.faces.mgbean.BeanManager.create(BeanManager.java:269)
at com.sun.faces.el.ManagedBeanELResolver.resolveBean(ManagedBeanELResolver.java:244)
at com.sun.faces.el.ManagedBeanELResolver.getValue(ManagedBeanELResolver.java:116)
at com.sun.faces.el.DemuxCompositeELResolver._getValue(DemuxCompositeELResolver.java:176)
at com.sun.faces.el.DemuxCompositeELResolver.getValue(DemuxCompositeELResolver.java:203)
at com.sun.el.parser.AstIdentifier.getValue(AstIdentifier.java:103)
at com.sun.el.parser.AstValue.getTarget(AstValue.java:149)
at com.sun.el.parser.AstValue.invoke(AstValue.java:237)
at com.sun.el.MethodExpressionImpl.invoke(MethodExpressionImpl.java:302)
at com.sun.faces.facelets.el.TagMethodExpression.invoke(TagMethodExpression.java:105)
at javax.faces.component.MethodBindingMethodExpressionAdapter.invoke(MethodBindingMethodExpressionAdapter.java:88)
at com.sun.faces.application.ActionListenerImpl.processAction(ActionListenerImpl.java:102)
at javax.faces.component.UICommand.broadcast(UICommand.java:315)
at javax.faces.component.UIViewRoot.broadcastEvents(UIViewRoot.java:794)
at javax.faces.component.UIViewRoot.processApplication(UIViewRoot.java:1259)
at com.sun.faces.lifecycle.InvokeApplicationPhase.execute(InvokeApplicationPhase.java:81)
at com.sun.faces.lifecycle.Phase.doPhase(Phase.java:101)
at com.sun.faces.lifecycle.LifecycleImpl.execute(LifecycleImpl.java:118)
at javax.faces.webapp.FacesServlet.service(FacesServlet.java:593)
at org.apache.catalina.core.StandardWrapper.service(StandardWrapper.java:1550)
at org.apache.catalina.core.StandardWrapperValve.invoke(StandardWrapperValve.java:281)
at org.apache.catalina.core.StandardContextValve.invoke(StandardContextValve.java:175)
at org.apache.catalina.core.StandardPipeline.doInvoke(StandardPipeline.java:655)
at org.apache.catalina.core.StandardPipeline.invoke(StandardPipeline.java:595)
at org.apache.catalina.core.StandardHostValve.invoke(StandardHostValve.java:161)
at org.apache.catalina.connector.CoyoteAdapter.doService(CoyoteAdapter.java:331)
at org.apache.catalina.connector.CoyoteAdapter.service(CoyoteAdapter.java:231)
at com.sun.enterprise.v3.services.impl.ContainerMapper$AdapterCallable.call(ContainerMapper.java:317)
at com.sun.enterprise.v3.services.impl.ContainerMapper.service(ContainerMapper.java:195)
at com.sun.grizzly.http.ProcessorTask.invokeAdapter(ProcessorTask.java:860)
at com.sun.grizzly.http.ProcessorTask.doProcess(ProcessorTask.java:757)
at com.sun.grizzly.http.ProcessorTask.process(ProcessorTask.java:1056)
at com.sun.grizzly.http.DefaultProtocolFilter.execute(DefaultProtocolFilter.java:229)
at com.sun.grizzly.DefaultProtocolChain.executeProtocolFilter(DefaultProtocolChain.java:137)
at com.sun.grizzly.DefaultProtocolChain.execute(DefaultProtocolChain.java:104)
at com.sun.grizzly.DefaultProtocolChain.execute(DefaultProtocolChain.java:90)
at com.sun.grizzly.http.HttpProtocolChain.execute(HttpProtocolChain.java:79)
at com.sun.grizzly.ProtocolChainContextTask.doCall(ProtocolChainContextTask.java:54)
at com.sun.grizzly.SelectionKeyContextTask.call(SelectionKeyContextTask.java:59)
at com.sun.grizzly.ContextTask.run(ContextTask.java:71)
at com.sun.grizzly.util.AbstractThreadPool$Worker.doWork(AbstractThreadPool.java:532)
at com.sun.grizzly.util.AbstractThreadPool$Worker.run(AbstractThreadPool.java:513)
at java.lang.Thread.run(Thread.java:722)
The easiest way is to make use of JSObject
class, that enables communication of Java with JavaScript from an Applet, to call a JavaScript function with your string as parameter that will do its job of updating server-side managed beans.
Introduce a following method in your applet:
public void sendToJs() {
String name = getSystemUsername();
try {
JSObject window = JSObject.getWindow(this);
window.call("updateServer", new Object[] {name});
} catch (JSException jse) {
jse.printStackTrace();
}
}
function updateServer(name) {
document.getElementById('username').value = name;
document.getElementById('button').click();
}
<h:form prependId="false">
<h:inputHidden id="username"/>
<h:commandButton id="button" style="display:none">
<f:ajax execute="@form/>
</h:commandButton>
</h:form>
You can note that it'd be less code if Primefaces were used (look for <p:remoteCommand>
) and a JS library like jQuery. Also note that username could be sent via POST/GET directly from the applet to a, for example, special dedicated servlet for processing (look for Apache's HttpClient
).