How does timeout in jboss works? How does a web-app knows when to re-direct to a login page?
Just to clarify!
-I know how to configure timeout on jboss. My question is, how does Jboss know that a session has timed out and when it does, how do you configure it to send the request to login page once the timeout has happened?
You can configure a time out on an all deployable units like .war files in web.xml
<session-config>
<session-timeout>30</session-timeout>
</session-config>
The HttpSession timeout in JBoss can be set at three different levels:
#1 To change default timeout value for every web application:
Edit the Web Deployer's default wed application configuration: in the web.xml
<session-config>
<session-timeout>30</session-timeout>
</session-config>
#2 To override the default HttpSession timeout on a per-webapp basis:
Add the same tags as above to WEB-INF/web.xml. Here is the DTD for further explanation:
<!--
The session-config element defines the session parameters for
this web application.
Used in: web-app
-->
<!ELEMENT session-config (session-timeout?)>
From https://developer.jboss.org/wiki/HttpSessionTimeout
The session-timeout element defines the default session timeout
interval for all sessions created in this web application. The
specified timeout must be expressed in a whole number of minutes.
If the timeout is 0 or less, the container ensures the default
behaviour of sessions is never to time out.
Used in: session-config
<!ELEMENT session-timeout (#PCDATA)>
#3 To override the global and web app value for a single client,
call
HttpSession.setMaxInactiveInterval(int seconds)
Related
I'm using Apache Camel to route a SOAP request based on a certain attribute in the request message. The message is matched against a regex and if a match is found the request will be routed to "calldestination1" and if not, it will be routed to "calldestination2".
I'm using the following configuration:
<beans xmlns="http://www.springframework.org/schema/beans"
xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xmlns:camel="http://camel.apache.org/schema/spring"
xmlns:cxf="http://camel.apache.org/schema/cxf"
xmlns:context="http://www.springframework.org/schema/context"
xsi:schemaLocation="
http://www.springframework.org/schema/beans http://www.springframework.org/schema/beans/spring-beans.xsd
http://www.springframework.org/schema/context http://www.springframework.org/schema/context/spring-context.xsd
http://camel.apache.org/schema/spring http://camel.apache.org/schema/spring/camel-spring.xsd
http://camel.apache.org/schema/cxf http://camel.apache.org/schema/cxf/camel-cxf.xsd">
<!-- ... -->
<cxf:cxfEndpoint id="testEndpointTest"
address="http://localhost:8080/testEndpoint"
endpointName="s:testEndpoint_Port"
serviceName="s:testEndpoint"
wsdlURL="wsdl/testEndpoint.wsdl"
xmlns:s="http://teste.com/testEndpoint"/>
<!-- ... -->
<camelContext xmlns="http://camel.apache.org/schema/spring">
<endpoint id="calldestination1" uri="http://localhost:8080/destination1?bridgeEndpoint=true&throwExceptionOnFailure=false"/>
<endpoint id="calldestination2" uri="http://localhost:8080/destination2?bridgeEndpoint=true&throwExceptionOnFailure=false"/>
<route streamCache="true">
<!--CXF consumer using MESSAGE format-->
<from uri="cxf:bean:testEndpointTest?dataFormat=MESSAGE"/>
<choice>
<when>
<simple>${bodyAs(java.lang.String)} regex ${properties:router.regex}</simple>
<to uri="calldestination1"/>
</when>
<otherwise>
<to uri="calldestination2"/>
</otherwise>
</choice>
</route>
</camelContext>
When the destination server, where "calldestination2" runs, is under load the requests can take around 1150ms to respond. Apache Camel does not seem to handle this very well.
To replicate this behavior I used SoapUI with a SOAP MockService with a delay (OnRequest Script) and jmeter.
Fist I ran the test against SoapUI MockService with no delay and then with a 1100ms delay.
Then I configured Apache Camel to route the request to SoapUI service and repeated the tests.
JMeter -> SoapUI - 0ms delay
~1200 requests per second; 25ms request average; 0% Errors
JMeter -> SoapUI - 1100ms delay
~100 requests per second; 1128ms request average; 0% Errors
JMeter -> Apache Camel -> SoapUI - 0ms delay
~420 requests per second; 285ms request average; 0% Errors
JMeter -> Apache Camel -> SoapUI - 1100ms delay
~8 requests per second; 14800ms request average; 97.23% Errors by timeout
The timeout in Apache Camel is set to 30 seconds.
Why is Apache Camel having such a low performance in the last case and how can I improve the it?
EDIT 1:
I created a repository in GitHub that contains the Apache Camel project, SoapUI mock service and jmeter tests for easy testing.
https://github.com/jraimundo/apache-camel-route-tester
Basic problem
Such problems are always a problem of resources. As long as all components have enough resources and answer fast, all is fine. As soon as one of them encounters a resource limitation it becomes slow.
In the JMeter-SoapUI scenario, the intentional latency of SoapUI is handled by JMeter. Because SoapUI takes more than a second to respond, the JMeter requests are held open for this time. If the JMeter thread pool for requests is exhausted (all threads are waiting for an answer from SoapUI), it cannot further scale. Based on your measures, the thread pool size could be 100.
Then you put Camel in the middle. With this you introduce new thread pools. There must be one to receive requests (CXF) and probably one that sends requests (Camel HTTP). Now the SoapUI latency must also be handled by these pools. Same situation, but now the thread pools of the Camel component are the limitation.
Let's assume the thread pool for Camel HTTP requests is 10 by default. JMeter begins to send requests. If JMeter sends new requests faster than SoapUI responds, the 10 threads to send HTTP requests to SoapUI are very fast all busy (waiting for SoapUI).
New requests of JMeter arrive, but no new HTTP requests to SoapUI are possible until until one of the threads is free again. Around 8 parallel requests (from your measures) seems to be reasonable in this case.
So it is obvious that if you want to serve 100 requests per second in a scenario like this you need to tune all involved thread pools to handle this. And you must also fine tune the different timeouts (CXF, Camel HTTP).
Your code
One point I noticed in your code is that you use the Camel HTTP component for your target endpoints. That component uses the Apache HTTP client 3.x.
If you want to use a more current Apache HTTP client, you must use the Camel HTTP4 component (4 because it uses Apache HTTP client 4.x). I don't know if it makes a big difference, but the old version is declared as "end of life" since years.
Another thing are the timeouts. You write that you set the Camel timeout to 30 seconds. But that is probably not the timeout of CXF or the Apache HTTP client. HTTP clients have multiple timeouts: it can take too long to establish a connection and it can take too long to receive a response.
I am running tomcat6 and have hooked it up in eclipse as a server so I can quickly debug code changes - however I am running into an issue with the routes that are passed to my servlet.
I am running spring mvc3 with my routes annotated on the class eg:
#Controller
#RequestMapping(value="/rest")
public class HandleItController {
...
in web.xml I have
<welcome-file-list>
<welcome-file>welcome.html</welcome-file>
</welcome-file-list>
<servlet-mapping>
<servlet-mapping>handleit</servletmapping>
<url-pattern>/rest</url-pattern>
</servlet-mapping>
However I can only get one of these settings to work as desired at a time.
lets say "Web Project Settings" has Context root set to be appname
now if I GET localhost:8080/appname I will get the welcome page as desired
however if I hit localhost:8080/appname/rest/yadda I get a warning saying
No mapping found for HTTP request with URI [/appname/rest/yadda] in
DispatcherServlet with name 'handleit'
If I change my servlet url-pattern to / then I get request routed through the servlet without the appname prepended and the servlet handles them as expected - however I cannot then hit the welcome page
I need a solution that does not involve hard coding appname into the web.xml or the controller mappings, there must be some way I can serve both the html file and the servlet that is independent of the uri to which my application is deployed - ie stop sending the context part of the url through to the servlet
The URI in the #RequestMapping will be appended to the url-mapping of the dispatcher servlet. So if both the servlet and controller is mapped to rest, the full URI will become /contextpath/rest/rest. If you don't want that, map your controller to /
Edit: The reason it doesn't work when you map your servlet to / is that the Spring dispatcher servlet handles everything under the context root. So to get that to work, you need to configure Spring MVC to serve static files.
I have been trying to secure an application, which is deployed to glassfish 3 using annotation instead of the deployment descriptor. However, I haven't been able to get it working correctly. If I try to access the service, I end up with a server error 500, which displays this message:
type Exception report
message
descriptionThe server encountered an internal error () that prevented it from fulfilling this request.
exception
javax.servlet.ServletException: javax.ejb.AccessLocalException: Client not authorized for this invocation
root cause
javax.ejb.AccessLocalException: Client not authorized for this invocation
The EJB looks like this:
#Path("/myresource")
#Stateless
#RolesAllowed("user-role")
public class MyResource {
#GET
#Path("/{uuid}")
public Response getData(#PathParam("uuid") final String uuid) {
....
}
}
sun-web.xml:
<?xml version="1.0" encoding="UTF-8"?>
<!DOCTYPE sun-web-app PUBLIC "-//Sun Microsystems, Inc.//DTD GlassFish Application Server 3.0 Servlet 3.0//EN"
"http://www.sun.com/software/appserver/dtds/sun-web-app_3_0-0.dtd">
<sun-web-app>
<security-role-mapping>
<role-name>user-role</role-name>
<group-name>user-group</group-name>
</security-role-mapping>
</sun-web-app>
This is the web.xml:
<web-app id="myservice" version="2.5" xmlns="http://java.sun.com/xml/ns/javaee"
xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xsi:schemaLocation="http://java.sun.com/xml/ns/javaee http://java.sun.com/xml/ns/javaee/web-app_2_5.xsd">
<display-name>org.test.myservice</display-name>
<servlet>
<servlet-name>Jersey Web Application</servlet-name>
<servlet-class>com.sun.jersey.spi.container.servlet.ServletContainer</servlet-class>
<init-param>
<param-name>com.sun.jersey.config.property.packages</param-name>
<param-value>org.test.myservice.rest</param-value>
</init-param>
<load-on-startup>1</load-on-startup>
</servlet>
<servlet-mapping>
<servlet-name>Jersey Web Application</servlet-name>
<url-pattern>/*</url-pattern>
</servlet-mapping>
<login-config>
<auth-method>BASIC</auth-method>
<realm-name>file</realm-name>
</login-config>
<security-role>
<role-name>user-role</role-name>
</security-role>
</web-app>
The file realm in glassfish is set up using the user and role specified in the sun-web.xml and has been working well, when setting up the application security via deployment descriptor.
If I understand this document correctly I do not have to link security role references if their names are the same. http://docs.oracle.com/javaee/5/tutorial/doc/bnbyl.html#bnbyt
Any ideas what I am missing?
Edit
Related to the problem of not being able to specify the required information with annotations, there is a another problem, which caused me to think about this issue. Maybe that will make the initial question a little clearer:
Taken above example, the resource /myresource/* is only available for users with role 'user-role'. However, if there is a second resource at path /myresource/*/thumbnail (translating to /myresource/[uuid]/thumbnail) which should be available without authentication, this is not possible by specifying security-constraints with url-mapping, since it does not seem to be possible to use the wildcard between constants. However, this would be doable by specifying the roles, that are allowed to access a method by annotions. As described above, I haven't been able to do so. How could a mapping like that be done?
You need to use the security-constraint element in web.xml descriptor in order to block specific resources and paths, and to specify the authorization constraints.
This doesn't mean that you can't add more fine-grained controls using Programmatic Security, as explained in Oracle's Java EE 6 Tutorial:
Programmatic security is embedded in an application and is used to make security decisions. Programmatic security is useful when declarative security alone is not sufficient to express the security model of an application.
As per your edited question.
I would use the security-constraint element for blocking the access to all non-registered users. This will force everybody to authenticate, so that your application knows the roles they have.
Then you can fine-grain control the access to the various resources using programmatic security.
With basic authentication I guess there are no other ways. If you want to avoid authentication for basic users, you need to go with form authentication and handle the authentication programmatically behind the scenes, authenticating them even if they aren't aware of, by using HttpServletRequest#login().
In both ways you should be able to setup rights in the way you have described. If you want to handle the unauthorized exception more smoothly, you'd better remove the #RolesAllowed annotation and instead use something like:
#GET
#Path("/{uuid}")
public Response getData(#PathParam("uuid") final String uuid, #Context SecurityContext sc) {
if (sc.isUserInRole("MyRole")) {
return result;
} else {
return notAllowedResult;
}
}
The Roles-Allowed is an EJB construct and not congruent with access to the resource, which is handled by the security constraint.
Unfortunately, the two security concepts do not mesh as well as they should, and instead of getting a 401 if you're not authorized (a web concept), you get the security exception that you are receiving (and EJB concept). In fact, I don't know what error you will receive if you annotate an EJB web service with a RolesAllowed and try to access the web service with an invalid role. I assume you'll get a SOAP fault, in that case.
The EJB security is a system that keeps unauthorized people out, but it's a last ditch effort. It assumes that any decisions to route folks to the method calls is already done up front. For example, there's no high level way to test if a method is allowed or not, rather you can only call it and catch the exception.
So the harsh truth is beyond coarse gatekeepers, you want to leverage Programmatic Security.
I had done web scan for an application(built in struts and hibernate framework) deployed in jboss 5 which reported "Set-cookie does not use HTTPOnly keyword. The web application does not utilize HTTPOnly cookies". What does it mean. I looked for some post and just added one line in my jboss/deploy/jbossweb.sar/context.xml as
<SessionCookie secure="true" useHttpOnly="true" >
After setting that, I am getting error while running the application. Is there any configuration that I am missing?
try this:
<SessionCookie secure="true" httpOnly="true" />
What does it mean
The HttpOnly flag in a http response header indicates to the browser that client-side access to the JSESSION_ID or other session-cookie type identifier should not be permitted. What this is intended to prevent is a malicious access to the session token via client side scripts in an XSS(or other attack involving session hijacking from the client side). Currently almost all major browsers support this flag(see this list for supporting browsers), but it's simply ignored in browsers that don't support it. See more info on this at the OWASP site
Setting it up is similar for tomcat and forks of it, including Jboss, by including the following in your context file:
<session-config>
<cookie-config>
<http-only>true</http-only>
</cookie-config>
</session-config>
or
<SessionCookie secure="true" httpOnly="true" />
I want to pass a security context to my rest service.
On server side I try to get this with:
public Response postObject(#Context SecurityContext security, JAXBElement<Object> object) {
System.out.println("Security Context: " + security.getUserPrincipal());
.....
But actually the Syso is null.
On Client side im just doing:
ClientConfig config = new DefaultClientConfig();
Client client = Client.create(config);
client.addFilter(new HTTPBasicAuthFilter("user", "password"));
So, do I have to change in addition something in my web.xml to get it working?
I hoped its working without setting up static users in the tomcat user xml. So I can compare the user/password from security context with my "persistent" user/password hashmap located server sided. But when it is not working without tomcat user xml, how can it be done to add dynamically user to that user xml? When I ve static users I cant register a new user. I dont want to use this attempt: http://objecthunter.congrace.de/tinybo/blog/articles/89 cuz I want just to work with a semi persistence like a HashMap of user/password.
Besides another question: Why does everybody refer to Apache HttpClient when it is about security in Jersey, when it is working like I wrote as well?
My attempt refers to this post:
Jersey Client API - authentication
You need to set up your application on the server so that it requires Basic authentication. I.e. include something like the following in the web.xml in your application war file - otherwise Tomcat does not perform the authentication and does not populate the security context.
<security-constraint>
<display-name>Authentication Constraint</display-name>
<web-resource-collection>
<web-resource-name>all</web-resource-name>
<description/>
<url-pattern>/*</url-pattern>
</web-resource-collection>
<auth-constraint>
<description>authentication required</description>
</auth-constraint>
</security-constraint>
<login-config>
<auth-method>BASIC</auth-method>
<realm-name>realm_name</realm-name>
</login-config>