What is the correct scope of DAF pipeline servlet - atg

What is the correct scope for a DAF pipeline servlet component used for REST services (like ActorServlet)? Should it be set to global or request?

From the ATG Documentation:
If a component’s $scope property is not explicitly set, it automatically has global scope.
Looking at the ActorServlet in the Component Browser in dynadmin it shows that there is no explicit scope set so it should indicate it is global scope by default.
Looking into this a bit more, the ActorServlet (which is the component of the RestPipelineServlet) extends the the PipelineableServletImpl which implements the PipelineableServlet interface. Here there is an abstract method passRequest which forms part of the actual pipeline 'chain' being executed.
public abstract void passRequest(ServletRequest paramServletRequest, ServletResponse paramServletResponse)
throws IOException, ServletException;
This means you will always have access to the current request. In the PipelineableServletImpl it internally calls the service method.
public void service(DynamoHttpServletRequest pRequest, DynamoHttpServletResponse pResponse) throws IOException, ServletException {
//Insert your logic here
passRequest(pRequest, pResponse);
}
You would normally override the service method and add your own logic in there but still have access to the current request which should indicate to you that, as long as the rest of your variables are thread safe, specifying your Pipeline Servlet as global scope is the correct way to go.

Related

#ScriptVariable resourceResolver vs #SlingObject resourceResolver

Can anyone explain to me the difference between calling resourceResolver by annotating #ScriptVariable and by annotating #SlingObject? In what context do they behave differently?
The key difference is in the way the object is retrieved. #ScriptVariable and #SlingObject are injector-specific annotations. This means that you can use them to instruct Sling Models to use a particular injector.
The injector that recognises the #ScriptVariable annotation can inject objects available as Scripting Variables. In case ot the resourceResolver, it should be the one associated with the request. Same as slingRequest.getResourceResolver().
Looking at the code, the injector that kicks in on fields annotated with #SlingObject is a bit more interesting in that it will inspect the adaptable (from which your Sling Model is being adapted) and obtain the resolver accordingly:
If the adaptable is a Resource, it'll return resource.getResourceResolver(), i.e. the resolver originally used to load the resource. This may be quite aribtrary.
If the adaptable is a SlingHttpServletRequest, it'll return request.getResourceResolver(), i.e. the resolver instantiated by Sling in association with the request and the session of the user issuing the request.
If the adaptable itself is a ResourceResolver, it will be returned directly.
In some cases, the difference between the three will be negligible, but sometimes it will be important which resolver you choose. If your model is, for example, supposed to be used outside the scope of a request (imagine it's instantiated by an OSGi service that runs on a schedule and there's no incoming request), you'll be better off using resource or resourceResolver as an adaptable.

Create Spring Boot RestController dynamically

I need to create a Rest endpoint dynamically in my Spring Boot application. Instead of statically creating the class with #RestController, is there a way to instantiate and activate a Rest service at runtime? It should be possible to specify the endpoint, input parameters etc at runtime.
Are there some Groovy options too?
Thanks,
Sandeep Joseph
I think the approach to take would be to create a custom MvcEndpoint that will handle all requests on a specific path, from there depending on your internal configuration you can process requests. It's basically just a Servlet (that's also an option). You're fully in control of the request.
public class MyEndpoint extends AbstractMvcEndpoint
// can optionally implements ApplicationContextAware, ServletContextAware
// to inject configuration, etc.
{
#RequestMapping("/dynamic-enpoints-prefix/**")
public ModelAndView handle(HttpServletRequest request, HttpServletResponse response)
throws Exception {
// here you have the request and response. Can do anything.
}
}

Jersey 2: filters and #Context injections

I've the following question:
ContainerRequestFilter is a singleton, but reading this:
Jaxrs-2_0 Oracle Spec
in chapter 9.2, they say:
Context is specific to a particular request but instances of certain JAX-RS components (providers and resource classes with a lifecycle other than per-request) may need to support multiple concurrent requests. When injecting an instance of one of the types listed in Section 9.2, the instance supplied MUST be capable of selecting the correct context for a particular request. Use of a thread-local proxy is a common way to achieve this.
In the chapter 9.2, the HttpServletRequest is not mentioned.
So the question is: is it safe in terms of concurrency to inject the HttpServletRequest inside a custom ContainRequestFilter?
I mean this:
#Provider
#PreMatching
public class AuthenticationFilter implements ContainerRequestFilter {
#Context private HttpServletRequest request;
#Override
public void filter(ContainerRequestContext requestContext) throws IOException {
// This is safe because every thread call the method with its requestContext
String path = requestContext.getUriInfo().getPath(true);
// Is this safe? The property request is injected by using #Context annotation (see above)
String toReturn = (String)request.getAttribute(name);
[...]
}
I did some empirical tests on my IDE in debug mode, sending with two different browsers two different and concurrent requests and it seems to work well; I noticed that the filter's instance is ever the same (it's a singleton), but the injected HttpServletRequest is different in the two cases.
I readed even this thread: How to access wicket session from Jersey-2 request filter? and it seems that my tests are confirmed.
But I still have doubts.
Confirm?
Yes it's safe. To understand the problem, you should understand how scopes work. In any framework that deals with scopes (and injection), the feature is implemented similarly. If an object is in a singleton scope and another object in a lesser scope needs to be injected, usually a proxy of the object will be injected instead. When a call is made on the object, it's actually a call on the proxy.
Though the spec may not mention the HttpServletRequest specifically, most JAX-RS implementation have support for this. With Jersey in particular, if this was not possible (meaning the object is not proxiable), then you would get an error message on startup with something like "not within a request scope". The reason is that the ContainerRequestFilter is created on app startup, and all the injections are handled at that time also. If the HttpServletRequest was not proxiable, it would fail to inject because on startup, there is no request scope context.
To confirm that it is not the actual HttpServletRequest and is a proxy, you can log the request.getClass(), and you will see that it is indeed a proxy.
If you are unfamiliar with this pattern, you can see this answer for an idea of how it works.
See Also:
Injecting Request Scoped Objects into Singleton Scoped Object with HK2 and Jersey

TransactionTimeout annotation seems not to override global seetting on JBoss 5.x

I have an EJB 3.0 based applicattion deployed on JBoss 5.1. The global value for transaction timeout configured at ${JBOSS_HOME}/server/default/deploy/transaction-jboss-beans.xml on property transactionTimeout is fine for most of our EJB methods. However, we have some methods whose duration is expected to be much longer than the value set there. We'd like to override the timeout specifically for those methods.
We've tried to do it as explained here, i.e. let the global value with a sensible value and then try to override specifically some methods via deployment descriptor at jboss.xml or via jboss specific annotations within the method.
The methods are within stateless session beans container managed. I've even forced those methods to create a new transaction as in some places is said that the annotation only works if the transaction is created in that moment.
../..
import org.jboss.ejb3.annotation.TransactionTimeout;
../..
#Override
#TransactionAttribute(TransactionAttributeType.REQUIRES_NEW)
#TransactionTimeout(900)
public FileInfoObject setFileVariable(Desk desk, String variable, int maxBytes,
String mimeAccepted, FileWithStream file)
throws ParticipationFinishedException, PersistenceException {
../..
}
The expected behavior is that for this method the timeout should be 900.
The actual behavior is quite fine and is the following:
if global timeout > method timeout then method timeout is applied
if global timeout <= method timeout then global timeout is applied
It seems that the applied timeout is the minimum of both which is a real problem if what we want is to extend the timeout for a specific method overriding the global value.
Any ideas? Am I missing something?

Variables in GWT server side code

I'm fairly new to GWT and have never worked with Java Servlets before. I know how to make RPCs but I was wondering if there are any concurrency issues with declaring member variables in my RPC's ServiceImpl/RemoteServiceServlet class. I.e. From multiple "simultaneous" RPCs overwriting the same variable, similar to what happens with threads when a variable isn't declared volatile.
I also need to use an extra thread in my server side code, so I was wondering if there's any problems (outside of the usual thread safety problems) with declaring some of the servlet's members as static so the other thread can access the variables without a reference to the servlet instance. Is it possible for more than one instance of the same RemoteServiceServlet class to be running at the same time?
E.g.
public class MyServiceImpl extends RemoteServiceServlet implements MyService {
// Which of these variable declarations are a bad idea in a servlet?
private String someVariable;
private static String anotherVariable;
volatile private static String multiThreadedVariable;
public void init() { ... }
...
}
Thanks.
A Servlet is a singleton, therefore there is only one instance of the MyServiceImpl class. By introducing these state variables you will run into thread-safety issues not because there might be more than one MyServiceImpl instance, but because there is only one instance that will service ALL of your requests. Unless you synchronize access to these variables, you will have thread-safety issues, so I recommend removing them completely (most likely you don't even need them).