The requirement is this: When a user session is expired, call expired.htm page, but on the first connection to the web site, show login.htm.
I tried using a filter but it doesn't work, I'm not able to tell to filter how to understand if it's a new request or an old request expired. This is the code I used:
if (session.getAttribute("userProfile") == null) {
logger.debug("Session: " + ( session.isNew() ? "true" : "false"));
logger.debug(request.getSession().isNew());
if ( request.getRequestedSessionId() != null && !request.isRequestedSessionIdValid() ) {
return new ModelAndView("redirect:expired.htm");
} else {
return new ModelAndView("redirect:login.htm");
}
}
I tried different solutions proposed here on Stack Overflow and on the general internet, but nothing has worked and every request goes to expired.htm.
How do you get the session object? Before doing that, use
if (request.getSession(false)==null) {
// no session present (expired or new visitor)
[... do something ...]
} else {
// active session present
}
You need to use the validation above before use any attribute in the session. Because if the session don't exists you can't get an attribute of it.
You need to put false inside parentesis.
if(request.getSession(false) == null) { //Session don't exists
...
}
Java explain:
public HttpSession getSession(boolean create)
Returns the current HttpSession associated with this request or, if there is no current session and create is true, returns a new session.
If create is false and the request has no valid HttpSession, this method returns null.
To make sure the session is properly maintained, you must call this method before the response is committed. If the container is using cookies to maintain session integrity and is asked to create a new session when the response is committed, an IllegalStateException is thrown.
Parameters:
create - true to create a new session for this request if necessary; false to return null if there's no current session
Returns:
the HttpSession associated with this request or null if create is false and the request has no valid session
Related
I have a function in which I would like to check if a user can set a lock on document. If so I know the user can edit the document.
public boolean canWriteDocument(String docId, String userName) {
boolean canWrite = false;
Session session = null;
session = getCurrentSession();
try {
Database db = session.getDatabase("", this.activeDb);
if (db.isDocumentLockingEnabled()) {
//Document locking is enabled
Document doc = db.getDocumentByUNID(docId);
if (doc.lock(userName)) {
canWrite = true;
System.out.println("document can be locked by user");
doc.unlock();
} else {
System.out.println("document can NOT be locked by user");
}
} else {
//Document locking is NOT enabled
}
} catch (NotesException e) {
// fail silently
System.out.println("failure docLock");
//e.printStackTrace();
}
return canWrite;
}
I call the function as followed:
canWriteDocument("99DE330A432849AFC125803400313C73", "CN=John Doe/O=quintessens")
However there must be something wrong because when the user (with ACL Author access level) is not listed in the field of type Authors it returns true.
When I lower the ACL access level to Reader the returned value is still true.
Anyone can explain why this is happening?
It may be that the database access level is cached within the server. Try rebooting the server (if it's a development environment) or testing with a brand new user that has never been in the ACL before.
If Database.queryAccess() is also not correct, that would confirm caching is the issue.
(It's possible that the two ways of checking access work differently under the hood, so if queryAccess() returns the correct value, it may not categorically mean the database locking option should.)
I have implemented a Filter that will check all the patterns - '/*' using the below code..
Here is my filter code:-
First, it checks for session attribute, if its null it sets a session attribute.
If a user tries to access any URL directly, I check the referrer and redirect to accessblocked.jsp page. This works but it does not redirect to the page..Instead it runs the same check to all URL's within the same page(CSS/image files) and does not load anything..How to stop my filter running once a condition is satisfied?
if (session.getAttribute(CHECK_TOKEN) == null) {
if (referer == null) {
session.setAttribute(CHECK_TOKEN, CHECK_TOKEN);
} else if (referer
.equals("http://p4-vsa.com/gui/banana/index.html")) {
httpResponse.sendRedirect(httpRequest.getContextPath()
+ "/accessblocked.jsp");
}
}
I am using UnboundID-LDAPSDK (2.3.8) to change the user's photo in our Microsoft Active Directory.
LDAPConnection ldap = null;
try {
ldap = new LDAPConnection("domain-srv", 389, "CN=admin,OU=Users,OU=ADM,DC=domain,DC=local", "password");
SearchResult sr = ldap.search("DC=domain,DC=local", SearchScope.SUB, "(sAMAccountName=" + getUser().getUsername() + ")");
if (sr.getEntryCount() == 1) {
SearchResultEntry entry = sr.getSearchEntries().get(0);
entry.setAttribute("thumbnailPhoto", getUser().getPhotoAsByteArray());
ldap.close();
return true;
} else
return false;
} catch (LDAPException e) {
e.printStackTrace();
}
But I get a java.lang.UnsupportedOperationException.
The documentation for setAttribute states:
Throws an UnsupportedOperationException to indicate that this is a
read-only entry.
I also tried to change the postalCode but I get the same exception.
Changing those attributes should be possible, because I can change them with jXplorer.
Do I have to enable a write-mode somehow?
Thank you
The SearchResultEntry object extends ReadOnlyEntry and is therefore immutable. But even if it weren't, merely calling entry.setAttribute would have no effect on the data in the server. You have to use a modify operation for that.
To do that, you'd need something like:
ModifyRequest modifyRequest = new ModifyRequest(entry.getDN(),
new Modification(ModificationType.REPLACE,
"thumbnailPhoto", getUser().getPhotoAsByteArray());
ldap.modify(modifyRequest);
Also, you should put the call to ldap.close() in a finally block because as the code is written now, you're only closing the connection if the search is successful and returns exactly one entry, but not if the search fails, doesn't match any entries, or the attempt to perform the modify fails.
I'm implementing a client to a web service (and the guys maintaining the web service have been a litte unresponsive..) I've used axis and WSDL2Java to generate java classes and I can call their login-method on their authentication-service ok, and get a sessionId back (eg z4zojhiqkw40lj55kgtn1oya). However, it seems that i cannot use this sessionId as a parameter anywhere. Even a call to their hasSession()-method directly after login returned false. I managed to solve this by setting setMaintainSession(true) on the Locator-object for this service. But the problem is, that this first service, the Authentication-service, is only used for authentification. If I then call setMaintainSession(true) on eg ProductServiceLocator, and call some method on it, I will get an error because of unauthenticated session. I have to find a way to share the session between the services on the client side.
Looking on their php code example-it seeems like they are storing the session in a cookie. How can I mimic this behaviour in my java client?
php-code:
$authentication = new SoapClient ( "https://webservices.24sevenoffice.com/authenticate/authenticate.asmx?wsdl", $options );
// log into 24SevenOffice if we don't have any active session. No point doing this more than once.
$login = true;
if (!empty($_SESSION['ASP.NET_SessionId'])){
$authentication->__setCookie("ASP.NET_SessionId", $_SESSION['ASP.NET_SessionId']);
try{
$login = !($authentication->HasSession()->HasSessionResult);
}
catch ( SoapFault $fault ) {
$login = true;
}
}
if( $login ){
$result = ($temp = $authentication->Login($params));
// set the session id for next time we call this page
$_SESSION['ASP.NET_SessionId'] = $result->LoginResult;
// each seperate webservice need the cookie set
$authentication->__setCookie("ASP.NET_SessionId", $_SESSION['ASP.NET_SessionId']);
// throw an error if the login is unsuccessful
if($authentication->HasSession()->HasSessionResult == false)
throw new SoapFault("0", "Invalid credential information.");
}
My code is the following:
AuthenticateLocator al = new AuthenticateLocator();
al.setMaintainSession(true);
Credential c = new Credential(CredentialType.Community,username,password,guid);
AuthenticateSoap s = al.getAuthenticateSoap();
String sessionId = s.login(c);
System.out.println("Session id was: "+sessionId);
System.out.println("Has Session: "+s.hasSession()); //Hooray, now works after setMaintainSession(true)
//And now trying to call another Service
CompanyServiceLocator cl = new CompanyServiceLocator();
cl.setMaintainSession(true);
CompanyServiceSoap css = cl.getCompanyServiceSoap();
css.getCountryList(); //FAILS!
So what can I do to make this work?
Hooray, I finally solved it myself :-D
Thanx a lot to the excellent article at http://www.nsftools.com/stubby/ApacheAxisClientTips.htm
I had to do the following with my code to make it work:
CompanyServiceLocator cl = new CompanyServiceLocator();
cl.setMaintainSession(true);
CompanyServiceSoap css = cl.getCompanyServiceSoap();
((Stub)css)._setProperty(HTTPConstants.HEADER_COOKIE, "ASP.NET_SessionId="+sessionId); //New line that does the magic
css.getCountryList(); //SUCCESS :-D
Operating in the high-level abstraction of the autogenerated classes, it was unknown to me that casting the service classes to Stub would expose more methods and properties that could be set. Good to know for later I guess :-)
I have a Portal that combines Spring controllers with a couple of regular servlets.
In the screen the user has a list from which he/she selects a credit card in order to see a report of the transactions of that card. As an extra security measure, I avoid sending the credit card in any request to the client so I have a list of credit cards numbers masked that I send to the user and in the request sent by the user I receive a record id which I use to determine which credit card is querying.
In a controller (ReportController), I have a method that process this input and call (locally) the servlet in charge of processing the report (ReportServlet). If there is any error in the processing it should return it to the screen using the model param "error". This last part isn't working.
If there is an error in the ReportServlet it is not returned to the screen. If I comment the forward line (and force an error) it works, but after doing the forwarding it doesn't. What I'm doing wrong?
Here's the code:
ReportController
try {
...
if (cardholders == null || cardholders.size() < 2 || id <= 0) {
model.put("error","there's an error");
return CARDTRANSACTIONS_PATH;
} else {
...
HttpUpdatetableRequestWrapper customRequest = new HttpUpdatetableRequestWrapper(request);
customRequest.setParameter("cardnumber", cardholder.getCardnumber());
request.getRequestDispatcher(config.getProperty("reportservlet")).forward((HttpServletRequest) customRequest, response);
String error = (String) session.getAttribute("error");
if(!(error == null || "".equals(error))){
throw new RuntimeException(error);
}
}
} catch (Exception ex) {
model.put("error", "there's an error");
} finally{ return CARDTRANSACTIONS_PATH;}
When your controller returns, Spring will give the model to an AbstractView which will decompose it and transfer the attributes over to the request. So when you are adding attributes to the model object in your controller, you're only adding them to a map with no relationship to the request. If you want those attributes to be available to the resource you forward to, you should add them directly to the request.
When you forward, you're expecting the resource you're forwarding to to handle the response, so you should make your controller return null in that situation, so that it doesn't do any further processing.