summaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorLeif Åstrand <leif@vaadin.com>2012-09-19 12:19:30 +0300
committerLeif Åstrand <leif@vaadin.com>2012-09-19 12:19:43 +0300
commitc1e82529b1191d9c41de0dc8a4cde8caf9754329 (patch)
tree47724ea23cd2e4126275b5d82379d29a77578569
parent56a5f6853318acbd743346e0f14faa0ed7325fa4 (diff)
downloadvaadin-framework-c1e82529b1191d9c41de0dc8a4cde8caf9754329.tar.gz
vaadin-framework-c1e82529b1191d9c41de0dc8a4cde8caf9754329.zip
Add some getCurrent() methods (#9505)
This change also clears the current instances in the beginning of each request in case something has accidentally been left uncleared in a previous request on the same thread.
-rw-r--r--server/src/com/vaadin/server/AbstractCommunicationManager.java2
-rw-r--r--server/src/com/vaadin/server/VaadinPortlet.java63
-rw-r--r--server/src/com/vaadin/server/VaadinService.java79
-rw-r--r--server/src/com/vaadin/server/VaadinServlet.java64
-rw-r--r--server/src/com/vaadin/server/VaadinServletSession.java11
-rw-r--r--uitest/src/com/vaadin/tests/components/window/AttachShouldBeCalledForSubWindows.java4
-rw-r--r--uitest/src/com/vaadin/tests/resources/NonExistingFileResource.java9
-rw-r--r--uitest/src/com/vaadin/tests/tickets/Ticket1975.java7
-rw-r--r--uitest/src/com/vaadin/tests/util/SampleDirectory.java6
9 files changed, 222 insertions, 23 deletions
diff --git a/server/src/com/vaadin/server/AbstractCommunicationManager.java b/server/src/com/vaadin/server/AbstractCommunicationManager.java
index a0a59da0ec..9ac33df7d2 100644
--- a/server/src/com/vaadin/server/AbstractCommunicationManager.java
+++ b/server/src/com/vaadin/server/AbstractCommunicationManager.java
@@ -84,6 +84,7 @@ import com.vaadin.ui.ConnectorTracker;
import com.vaadin.ui.HasComponents;
import com.vaadin.ui.UI;
import com.vaadin.ui.Window;
+import com.vaadin.util.CurrentInstance;
/**
* This is a common base class for the server-side implementations of the
@@ -2469,6 +2470,7 @@ public abstract class AbstractCommunicationManager implements Serializable {
assert UI.getCurrent() == null;
CombinedRequest combinedRequest = new CombinedRequest(request);
+ CurrentInstance.set(WrappedRequest.class, combinedRequest);
response.setContentType("application/json; charset=UTF-8");
diff --git a/server/src/com/vaadin/server/VaadinPortlet.java b/server/src/com/vaadin/server/VaadinPortlet.java
index 30d897c6bc..1462db5899 100644
--- a/server/src/com/vaadin/server/VaadinPortlet.java
+++ b/server/src/com/vaadin/server/VaadinPortlet.java
@@ -222,6 +222,19 @@ public class VaadinPortlet extends GenericPortlet implements Constants {
return new PortletCommunicationManager(session);
}
+ public static WrappedPortletRequest getCurrentRequest() {
+ WrappedRequest currentRequest = VaadinService.getCurrentRequest();
+ try {
+ return WrappedPortletRequest.cast(currentRequest);
+ } catch (ClassCastException e) {
+ return null;
+ }
+ }
+
+ public static WrappedPortletResponse getCurrentResponse() {
+ return (WrappedPortletResponse) VaadinService.getCurrentResponse();
+ }
+
}
public static class WrappedHttpAndPortletRequest extends
@@ -377,6 +390,8 @@ public class VaadinPortlet extends GenericPortlet implements Constants {
@Override
public void init(PortletConfig config) throws PortletException {
+ CurrentInstance.clearAll();
+ setCurrent(this);
super.init(config);
Properties initParameters = new Properties();
@@ -397,11 +412,14 @@ public class VaadinPortlet extends GenericPortlet implements Constants {
DeploymentConfiguration deploymentConfiguration = createDeploymentConfiguration(initParameters);
vaadinService = createPortletService(deploymentConfiguration);
+ // Sets current service even though there are no request and response
+ vaadinService.setCurrentInstances(null, null);
addonContext = new AddonContext(vaadinService);
addonContext.init();
portletInitialized();
+ CurrentInstance.clearAll();
}
protected void portletInitialized() {
@@ -499,6 +517,9 @@ public class VaadinPortlet extends GenericPortlet implements Constants {
RequestTimer requestTimer = new RequestTimer();
requestTimer.start();
+ CurrentInstance.clearAll();
+ setCurrent(this);
+
AbstractApplicationPortletWrapper portletWrapper = new AbstractApplicationPortletWrapper(
this);
@@ -507,8 +528,7 @@ public class VaadinPortlet extends GenericPortlet implements Constants {
WrappedPortletResponse wrappedResponse = new WrappedPortletResponse(
response, getVaadinService());
- CurrentInstance.set(WrappedRequest.class, wrappedRequest);
- CurrentInstance.set(WrappedResponse.class, wrappedResponse);
+ getVaadinService().setCurrentInstances(wrappedRequest, wrappedResponse);
RequestType requestType = getRequestType(wrappedRequest);
@@ -928,4 +948,43 @@ public class VaadinPortlet extends GenericPortlet implements Constants {
return Logger.getLogger(VaadinPortlet.class.getName());
}
+ /**
+ * Gets the currently used Vaadin portlet. The current portlet is
+ * automatically defined when initializing the portlet and when processing
+ * requests to the server and in threads started at a point when the current
+ * portlet is defined (see {@link InheritableThreadLocal}). In other cases,
+ * (e.g. from background threads started in some other way), the current
+ * portlet is not automatically defined.
+ *
+ * @return the current vaadin portlet instance if available, otherwise
+ * <code>null</code>
+ *
+ * @see #setCurrent(VaadinPortlet)
+ *
+ * @since 7.0
+ */
+ public static VaadinPortlet getCurrent() {
+ return CurrentInstance.get(VaadinPortlet.class);
+ }
+
+ /**
+ * Sets the current Vaadin portlet. This method is used by the framework to
+ * set the current portlet whenever a new request is processed and it is
+ * cleared when the request has been processed.
+ * <p>
+ * The application developer can also use this method to define the current
+ * portlet outside the normal request handling, e.g. when initiating custom
+ * background threads.
+ * </p>
+ *
+ * @param portlet
+ * the Vaadin portlet to register as the current portlet
+ *
+ * @see #getCurrent()
+ * @see InheritableThreadLocal
+ */
+ public static void setCurrent(VaadinPortlet portlet) {
+ CurrentInstance.setInheritable(VaadinPortlet.class, portlet);
+ }
+
}
diff --git a/server/src/com/vaadin/server/VaadinService.java b/server/src/com/vaadin/server/VaadinService.java
index 5f3f47adba..80590df4a0 100644
--- a/server/src/com/vaadin/server/VaadinService.java
+++ b/server/src/com/vaadin/server/VaadinService.java
@@ -34,6 +34,7 @@ import com.vaadin.LegacyApplication;
import com.vaadin.event.EventRouter;
import com.vaadin.server.ServletPortletHelper.ApplicationClassException;
import com.vaadin.server.VaadinSession.SessionStartEvent;
+import com.vaadin.util.CurrentInstance;
import com.vaadin.util.ReflectTools;
/**
@@ -447,4 +448,82 @@ public abstract class VaadinService implements Serializable {
* for the request; else <code>false</code>
*/
protected abstract boolean requestCanCreateSession(WrappedRequest request);
+
+ /**
+ * Gets the currently used Vaadin service. The current service is
+ * automatically defined when processing requests related to the service and
+ * in threads started at a point when the current service is defined (see
+ * {@link InheritableThreadLocal}). In other cases, (e.g. from background
+ * threads started in some other way), the current service is not
+ * automatically defined.
+ *
+ * @return the current Vaadin service instance if available, otherwise
+ * <code>null</code>
+ *
+ * @see #setCurrentInstances(WrappedRequest, WrappedResponse)
+ */
+ public static VaadinService getCurrent() {
+ return CurrentInstance.get(VaadinService.class);
+ }
+
+ /**
+ * Sets the this Vaadin service as the current service and also sets the
+ * current wrapped request and wrapped response. This method is used by the
+ * framework to set the current instances when a request related to the
+ * service is processed and they are cleared when the request has been
+ * processed.
+ * <p>
+ * The application developer can also use this method to define the current
+ * instances outside the normal request handling, e.g. when initiating
+ * custom background threads.
+ * </p>
+ *
+ * @param request
+ * the wrapped request to set as the current request, or
+ * <code>null</code> if no request should be set.
+ * @param response
+ * the wrapped response to set as the current response, or
+ * <code>null</code> if no response should be set.
+ *
+ * @see #getCurrent()
+ * @see #getCurrentRequest()
+ * @see #getCurrentResponse()
+ */
+ public void setCurrentInstances(WrappedRequest request,
+ WrappedResponse response) {
+ CurrentInstance.setInheritable(VaadinService.class, this);
+ CurrentInstance.set(WrappedRequest.class, request);
+ CurrentInstance.set(WrappedResponse.class, response);
+ }
+
+ /**
+ * Gets the currently processed wrapped request. The current request is
+ * automatically defined when the request is started. The current request
+ * can not be used in e.g. background threads because of the way server
+ * implementations reuse request instances.
+ *
+ * @return the current wrapped request instance if available, otherwise
+ * <code>null</code>
+ *
+ * @see #setCurrentInstances(WrappedRequest, WrappedResponse)
+ */
+ public static WrappedRequest getCurrentRequest() {
+ return CurrentInstance.get(WrappedRequest.class);
+ }
+
+ /**
+ * Gets the currently processed wrapped request. The current request is
+ * automatically defined when the request is started. The current request
+ * can not be used in e.g. background threads because of the way server
+ * implementations reuse request instances.
+ *
+ * @return the current wrapped request instance if available, otherwise
+ * <code>null</code>
+ *
+ * @see #setCurrentInstances(WrappedRequest, WrappedResponse)
+ */
+ public static WrappedResponse getCurrentResponse() {
+ return CurrentInstance.get(WrappedResponse.class);
+ }
+
}
diff --git a/server/src/com/vaadin/server/VaadinServlet.java b/server/src/com/vaadin/server/VaadinServlet.java
index f83477c9bc..1d92151288 100644
--- a/server/src/com/vaadin/server/VaadinServlet.java
+++ b/server/src/com/vaadin/server/VaadinServlet.java
@@ -197,6 +197,20 @@ public class VaadinServlet extends HttpServlet implements Constants {
VaadinSession session) {
return new CommunicationManager(session);
}
+
+ public static WrappedHttpServletRequest getCurrentRequest() {
+ WrappedRequest currentRequest = VaadinService.getCurrentRequest();
+ try {
+ return WrappedHttpServletRequest.cast(currentRequest);
+ } catch (ClassCastException e) {
+ return null;
+ }
+ }
+
+ public static WrappedHttpServletResponse getCurrentResponse() {
+ return (WrappedHttpServletResponse) VaadinService
+ .getCurrentResponse();
+ }
}
private static class AbstractApplicationServletWrapper implements Callback {
@@ -241,6 +255,8 @@ public class VaadinServlet extends HttpServlet implements Constants {
@Override
public void init(javax.servlet.ServletConfig servletConfig)
throws javax.servlet.ServletException {
+ CurrentInstance.clearAll();
+ setCurrent(this);
super.init(servletConfig);
Properties initParameters = new Properties();
@@ -262,17 +278,60 @@ public class VaadinServlet extends HttpServlet implements Constants {
DeploymentConfiguration deploymentConfiguration = createDeploymentConfiguration(initParameters);
servletService = createServletService(deploymentConfiguration);
+ // Sets current service even though there are no request and response
+ servletService.setCurrentInstances(null, null);
addonContext = new AddonContext(servletService);
addonContext.init();
servletInitialized();
+
+ CurrentInstance.clearAll();
}
protected void servletInitialized() {
// Empty by default
}
+ /**
+ * Gets the currently used Vaadin servlet. The current servlet is
+ * automatically defined when initializing the servlet and when processing
+ * requests to the server and in threads started at a point when the current
+ * servlet is defined (see {@link InheritableThreadLocal}). In other cases,
+ * (e.g. from background threads started in some other way), the current
+ * servlet is not automatically defined.
+ *
+ * @return the current Vaadin servlet instance if available, otherwise
+ * <code>null</code>
+ *
+ * @see #setCurrent(VaadinServlet)
+ *
+ * @since 7.0
+ */
+ public static VaadinServlet getCurrent() {
+ return CurrentInstance.get(VaadinServlet.class);
+ }
+
+ /**
+ * Sets the current Vaadin servlet. This method is used by the framework to
+ * set the current servlet whenever a new request is processed and it is
+ * cleared when the request has been processed.
+ * <p>
+ * The application developer can also use this method to define the current
+ * servlet outside the normal request handling, e.g. when initiating custom
+ * background threads.
+ * </p>
+ *
+ * @param servlet
+ * the Vaadin servlet to register as the current servlet
+ *
+ * @see #getCurrent()
+ * @see InheritableThreadLocal
+ */
+ public static void setCurrent(VaadinServlet servlet) {
+ CurrentInstance.setInheritable(VaadinServlet.class, servlet);
+ }
+
protected DeploymentConfiguration createDeploymentConfiguration(
Properties initParameters) {
return new DefaultDeploymentConfiguration(getClass(), initParameters);
@@ -310,6 +369,8 @@ public class VaadinServlet extends HttpServlet implements Constants {
@Override
protected void service(HttpServletRequest request,
HttpServletResponse response) throws ServletException, IOException {
+ CurrentInstance.clearAll();
+ setCurrent(this);
service(createWrappedRequest(request), createWrappedResponse(response));
}
@@ -319,8 +380,7 @@ public class VaadinServlet extends HttpServlet implements Constants {
RequestTimer requestTimer = new RequestTimer();
requestTimer.start();
- CurrentInstance.set(WrappedResponse.class, response);
- CurrentInstance.set(WrappedRequest.class, request);
+ getVaadinService().setCurrentInstances(request, response);
AbstractApplicationServletWrapper servletWrapper = new AbstractApplicationServletWrapper(
this);
diff --git a/server/src/com/vaadin/server/VaadinServletSession.java b/server/src/com/vaadin/server/VaadinServletSession.java
index b2e3b9f54c..b2dc84d857 100644
--- a/server/src/com/vaadin/server/VaadinServletSession.java
+++ b/server/src/com/vaadin/server/VaadinServletSession.java
@@ -23,7 +23,7 @@ import javax.servlet.http.HttpSession;
import javax.servlet.http.HttpSessionBindingEvent;
import javax.servlet.http.HttpSessionBindingListener;
-import com.vaadin.util.CurrentInstance;
+import com.vaadin.server.VaadinServlet.ServletService;
/**
* Web application context for Vaadin applications.
@@ -58,6 +58,12 @@ public class VaadinServletSession extends VaadinSession {
* to avoid session fixation attacks.
*/
public void reinitializeSession() {
+ WrappedHttpServletRequest currentRequest = ServletService
+ .getCurrentRequest();
+ if (currentRequest == null) {
+ throw new IllegalStateException(
+ "Can not reinitialize session outside normal request handling.");
+ }
HttpSession oldSession = getHttpSession();
@@ -77,8 +83,7 @@ public class VaadinServletSession extends VaadinSession {
reinitializingSession = false;
// Create a new session
- HttpSession newSession = WrappedHttpServletRequest.cast(
- CurrentInstance.get(WrappedRequest.class)).getSession();
+ HttpSession newSession = currentRequest.getSession();
// Restores all attributes (security key, reference to this context
// instance)
diff --git a/uitest/src/com/vaadin/tests/components/window/AttachShouldBeCalledForSubWindows.java b/uitest/src/com/vaadin/tests/components/window/AttachShouldBeCalledForSubWindows.java
index 6f21346b7d..4d0dea4f91 100644
--- a/uitest/src/com/vaadin/tests/components/window/AttachShouldBeCalledForSubWindows.java
+++ b/uitest/src/com/vaadin/tests/components/window/AttachShouldBeCalledForSubWindows.java
@@ -1,6 +1,7 @@
package com.vaadin.tests.components.window;
import com.vaadin.event.ShortcutAction.KeyCode;
+import com.vaadin.server.VaadinService;
import com.vaadin.server.WrappedRequest;
import com.vaadin.tests.components.AbstractTestCase;
import com.vaadin.tests.util.Log;
@@ -11,7 +12,6 @@ import com.vaadin.ui.Component;
import com.vaadin.ui.Label;
import com.vaadin.ui.UI;
import com.vaadin.ui.Window;
-import com.vaadin.util.CurrentInstance;
public class AttachShouldBeCalledForSubWindows extends AbstractTestCase {
private static final long serialVersionUID = 1L;
@@ -23,7 +23,7 @@ public class AttachShouldBeCalledForSubWindows extends AbstractTestCase {
@Override
public void init() {
- WrappedRequest request = CurrentInstance.get(WrappedRequest.class);
+ WrappedRequest request = VaadinService.getCurrentRequest();
if (request.getParameter("attachMainFirst") != null) {
addSubWindowBeforeMainWindow = false;
} else {
diff --git a/uitest/src/com/vaadin/tests/resources/NonExistingFileResource.java b/uitest/src/com/vaadin/tests/resources/NonExistingFileResource.java
index c102291b50..f55c1f1f1d 100644
--- a/uitest/src/com/vaadin/tests/resources/NonExistingFileResource.java
+++ b/uitest/src/com/vaadin/tests/resources/NonExistingFileResource.java
@@ -3,11 +3,10 @@ package com.vaadin.tests.resources;
import java.io.File;
import com.vaadin.server.FileResource;
-import com.vaadin.server.WrappedRequest;
+import com.vaadin.server.VaadinService;
import com.vaadin.tests.components.TestBase;
import com.vaadin.ui.Button;
import com.vaadin.ui.Button.ClickEvent;
-import com.vaadin.util.CurrentInstance;
public class NonExistingFileResource extends TestBase {
@@ -26,10 +25,8 @@ public class NonExistingFileResource extends TestBase {
@Override
public void buttonClick(ClickEvent event) {
- FileResource res = new FileResource(new File(CurrentInstance
- .get(WrappedRequest.class).getVaadinService()
- .getBaseDirectory()
- + "/" + filename));
+ FileResource res = new FileResource(new File(VaadinService
+ .getCurrent().getBaseDirectory() + "/" + filename));
getMainWindow().open(res);
}
diff --git a/uitest/src/com/vaadin/tests/tickets/Ticket1975.java b/uitest/src/com/vaadin/tests/tickets/Ticket1975.java
index a688fd9908..f41585ff5d 100644
--- a/uitest/src/com/vaadin/tests/tickets/Ticket1975.java
+++ b/uitest/src/com/vaadin/tests/tickets/Ticket1975.java
@@ -5,14 +5,13 @@ import java.io.File;
import java.io.FileInputStream;
import com.vaadin.LegacyApplication;
-import com.vaadin.server.WrappedRequest;
+import com.vaadin.server.VaadinService;
import com.vaadin.ui.Button;
import com.vaadin.ui.Button.ClickEvent;
import com.vaadin.ui.Button.ClickListener;
import com.vaadin.ui.CustomLayout;
import com.vaadin.ui.GridLayout;
import com.vaadin.ui.UI.LegacyWindow;
-import com.vaadin.util.CurrentInstance;
public class Ticket1975 extends LegacyApplication {
@@ -47,8 +46,8 @@ public class Ticket1975 extends LegacyApplication {
}
}));
- File baseDir = CurrentInstance.get(WrappedRequest.class)
- .getVaadinService().getBaseDirectory().getAbsoluteFile();
+ File baseDir = VaadinService.getCurrent().getBaseDirectory()
+ .getAbsoluteFile();
File f = new File(baseDir + "/VAADIN/themes/" + getTheme()
+ "/layouts/Ticket1975.html");
diff --git a/uitest/src/com/vaadin/tests/util/SampleDirectory.java b/uitest/src/com/vaadin/tests/util/SampleDirectory.java
index 140f778551..5c45e0d64e 100644
--- a/uitest/src/com/vaadin/tests/util/SampleDirectory.java
+++ b/uitest/src/com/vaadin/tests/util/SampleDirectory.java
@@ -19,13 +19,12 @@ package com.vaadin.tests.util;
import java.io.File;
import com.vaadin.server.SystemError;
+import com.vaadin.server.VaadinService;
import com.vaadin.server.VaadinSession;
-import com.vaadin.server.WrappedRequest;
import com.vaadin.shared.ui.label.ContentMode;
import com.vaadin.ui.Label;
import com.vaadin.ui.Panel;
import com.vaadin.ui.UI;
-import com.vaadin.util.CurrentInstance;
/**
* Provides sample directory based on application directory. If this fails then
@@ -48,8 +47,7 @@ public class SampleDirectory {
+ "context base directory failed, "
+ "possible security constraint with Application "
+ "Server or Servlet Container.<br />";
- File file = CurrentInstance.get(WrappedRequest.class)
- .getVaadinService().getBaseDirectory();
+ File file = VaadinService.getCurrent().getBaseDirectory();
if ((file == null) || (!file.canRead())
|| (file.getAbsolutePath() == null)) {
// cannot access example directory, possible security issue with