1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34 package info.magnolia.module.blossom.preexecution;
35
36 import java.io.IOException;
37 import javax.jcr.Node;
38 import javax.jcr.RepositoryException;
39 import javax.jcr.Session;
40 import javax.servlet.FilterChain;
41 import javax.servlet.FilterConfig;
42 import javax.servlet.ServletException;
43 import javax.servlet.http.HttpServletRequest;
44 import javax.servlet.http.HttpServletResponse;
45
46 import org.slf4j.Logger;
47 import org.slf4j.LoggerFactory;
48 import org.springframework.core.NestedIOException;
49 import org.springframework.web.servlet.ModelAndView;
50
51 import info.magnolia.cms.core.AggregationState;
52 import info.magnolia.cms.core.Content;
53 import info.magnolia.cms.core.MgnlNodeType;
54 import info.magnolia.cms.filters.OncePerRequestAbstractMgnlFilter;
55 import info.magnolia.cms.util.ContentUtil;
56 import info.magnolia.context.MgnlContext;
57 import info.magnolia.objectfactory.Components;
58 import info.magnolia.rendering.engine.RenderingEngine;
59 import info.magnolia.rendering.engine.ResponseOutputProvider;
60 import info.magnolia.repository.RepositoryConstants;
61
62
63
64
65
66
67
68 public class BlossomFilter extends OncePerRequestAbstractMgnlFilter {
69
70 public static final String PREEXECUTION_CONTEXT_PARAMETER_NAME = "_pecid";
71
72 private final Logger logger = LoggerFactory.getLogger(getClass());
73
74 @Override
75 public void init(FilterConfig filterConfig) throws ServletException {
76 }
77
78 @Override
79 public void doFilter(HttpServletRequest request, HttpServletResponse response, FilterChain chain) throws IOException, ServletException {
80
81 String preexecutionUuid = request.getParameter(PREEXECUTION_CONTEXT_PARAMETER_NAME);
82 if (preexecutionUuid == null) {
83
84 chain.doFilter(request, response);
85 return;
86 }
87
88
89 Node content;
90 try {
91 Session session = MgnlContext.getSystemContext().getJCRSession(RepositoryConstants.WEBSITE);
92 content = session.getNodeByIdentifier(preexecutionUuid);
93 } catch (RepositoryException e) {
94 logger.error("Content for pre-execution [" + preexecutionUuid + "] not found in repository");
95 return;
96 }
97
98
99 PreexecutionContext preexecutionContext = new PreexecutionContext(preexecutionUuid);
100 PreexecutionContextHolder.put(request, preexecutionContext);
101 try {
102
103 executeHandler(content, response);
104
105
106 ModelAndView mv = preexecutionContext.getModelAndView();
107 if (mv == null || mv.wasCleared()) {
108 return;
109 }
110
111
112 chain.doFilter(request, response);
113
114 } catch (RepositoryException e) {
115 throw new ServletException(e);
116 } finally {
117 PreexecutionContextHolder.remove(request);
118 }
119 }
120
121 private void executeHandler(Node content, HttpServletResponse response) throws IOException, RepositoryException {
122
123 AggregationState state = getAggregationStateSafely();
124 Content orgMainContent = null;
125 Content orgCurrentContent = null;
126
127 if (state != null) {
128 orgMainContent = state.getMainContent();
129 orgCurrentContent = state.getCurrentContent();
130
131 state.setCurrentContent(ContentUtil.asContent(content));
132 if (orgMainContent == null) {
133 state.setMainContent(ContentUtil.asContent(findMainContent(content)));
134 }
135 }
136 try {
137
138 try {
139 Components.getComponent(RenderingEngine.class).render(content, new ResponseOutputProvider(response));
140 } catch (info.magnolia.rendering.engine.RenderException e) {
141 throw new NestedIOException("Error pre-executing handler", e);
142 }
143
144 } finally {
145 if (state != null) {
146 state.setMainContent(orgMainContent);
147 state.setCurrentContent(orgCurrentContent);
148 }
149 }
150 }
151
152 protected Node findMainContent(Node content) throws RepositoryException {
153 while (content.getDepth() != 0) {
154 if (content.getPrimaryNodeType().getName().equals(MgnlNodeType.NT_CONTENT)) {
155 return content;
156 }
157 content = content.getParent();
158 }
159 return null;
160 }
161
162 protected AggregationState getAggregationStateSafely() {
163 if (MgnlContext.isWebContext()) {
164 return MgnlContext.getAggregationState();
165 }
166 return null;
167 }
168
169 @Override
170 public void destroy() {
171 }
172 }