1
22
23 package com.liferay.filters.strip;
24
25 import com.liferay.portal.kernel.log.Log;
26 import com.liferay.portal.kernel.log.LogFactoryUtil;
27 import com.liferay.portal.kernel.servlet.BaseFilter;
28 import com.liferay.portal.kernel.util.GetterUtil;
29 import com.liferay.portal.kernel.util.JavaConstants;
30 import com.liferay.portal.kernel.util.ParamUtil;
31 import com.liferay.util.Http;
32 import com.liferay.util.SystemProperties;
33 import com.liferay.util.servlet.ServletResponseUtil;
34
35 import java.io.IOException;
36
37 import javax.servlet.FilterChain;
38 import javax.servlet.ServletException;
39 import javax.servlet.ServletRequest;
40 import javax.servlet.ServletResponse;
41 import javax.servlet.http.HttpServletRequest;
42 import javax.servlet.http.HttpServletResponse;
43
44
51 public class StripFilter extends BaseFilter {
52
53 public static final boolean USE_FILTER = GetterUtil.getBoolean(
54 SystemProperties.get(StripFilter.class.getName()), true);
55
56 public static final String ENCODING = GetterUtil.getString(
57 SystemProperties.get("file.encoding"), "UTF-8");
58
59 public void doFilter(
60 ServletRequest req, ServletResponse res, FilterChain chain)
61 throws IOException, ServletException {
62
63 if (_log.isDebugEnabled()) {
64 if (USE_FILTER) {
65 _log.debug("Strip is enabled");
66 }
67 else {
68 _log.debug("Strip is disabled");
69 }
70 }
71
72 HttpServletRequest httpReq = (HttpServletRequest)req;
73 HttpServletResponse httpRes = (HttpServletResponse)res;
74
75 String completeURL = Http.getCompleteURL(httpReq);
76
77 if (USE_FILTER && isStrip(httpReq) && !isInclude(httpReq) &&
78 !isAlreadyFiltered(httpReq)) {
79
80 if (_log.isDebugEnabled()) {
81 _log.debug("Stripping " + completeURL);
82 }
83
84 httpReq.setAttribute(_ALREADY_FILTERED, Boolean.TRUE);
85
86 StripResponse stripResponse = new StripResponse(httpRes);
87
88 doFilter(StripFilter.class, req, stripResponse, chain);
89
90 String contentType = GetterUtil.getString(
91 stripResponse.getContentType());
92
93 byte[] oldByteArray = stripResponse.getData();
94
95 if ((oldByteArray != null) && (oldByteArray.length > 0)) {
96 byte[] newByteArray = new byte[oldByteArray.length];
97 int newByteArrayPos = 0;
98
99 if (_log.isDebugEnabled()) {
100 _log.debug("Stripping content of type " + contentType);
101 }
102
103 if (contentType.toLowerCase().indexOf("text/") != -1) {
104 boolean ignore = false;
105 char prevChar = '\n';
106
107 for (int i = 0; i < oldByteArray.length; i++) {
108 byte b = oldByteArray[i];
109 char c = (char)b;
110
111 if (c == '<') {
112
113
115 if (!ignore) {
116
117
119 if ((i + 4) < oldByteArray.length) {
120 char c1 = (char)oldByteArray[i + 1];
121 char c2 = (char)oldByteArray[i + 2];
122 char c3 = (char)oldByteArray[i + 3];
123 char c4 = (char)oldByteArray[i + 4];
124
125 if (((c1 == 'p') || (c1 == 'P')) &&
126 ((c2 == 'r') || (c2 == 'R')) &&
127 ((c3 == 'e') || (c3 == 'E')) &&
128 ((c4 == '>'))) {
129
130 ignore = true;
131 }
132 }
133
134
136 if (!ignore &&
137 ((i + 9) < oldByteArray.length)) {
138
139 char c1 = (char)oldByteArray[i + 1];
140 char c2 = (char)oldByteArray[i + 2];
141 char c3 = (char)oldByteArray[i + 3];
142 char c4 = (char)oldByteArray[i + 4];
143 char c5 = (char)oldByteArray[i + 5];
144 char c6 = (char)oldByteArray[i + 6];
145 char c7 = (char)oldByteArray[i + 7];
146 char c8 = (char)oldByteArray[i + 8];
147 char c9 = (char)oldByteArray[i + 9];
148
149 if (((c1 == 't') || (c1 == 'T')) &&
150 ((c2 == 'e') || (c2 == 'E')) &&
151 ((c3 == 'x') || (c3 == 'X')) &&
152 ((c4 == 't') || (c4 == 'T')) &&
153 ((c5 == 'a') || (c5 == 'A')) &&
154 ((c6 == 'r') || (c6 == 'R')) &&
155 ((c7 == 'e') || (c7 == 'E')) &&
156 ((c8 == 'a') || (c8 == 'A')) &&
157 ((c9 == ' '))) {
158
159 ignore = true;
160 }
161 }
162 }
163 else if (ignore) {
164
165
167 if ((i + 5) < oldByteArray.length) {
168 char c1 = (char)oldByteArray[i + 1];
169 char c2 = (char)oldByteArray[i + 2];
170 char c3 = (char)oldByteArray[i + 3];
171 char c4 = (char)oldByteArray[i + 4];
172 char c5 = (char)oldByteArray[i + 5];
173
174 if (((c1 == '/')) &&
175 ((c2 == 'p') || (c2 == 'P')) &&
176 ((c3 == 'r') || (c3 == 'R')) &&
177 ((c4 == 'e') || (c4 == 'E')) &&
178 ((c5 == '>'))) {
179
180 ignore = false;
181 }
182 }
183
184
186 if (ignore &&
187 ((i + 10) < oldByteArray.length)) {
188
189 char c1 = (char)oldByteArray[i + 1];
190 char c2 = (char)oldByteArray[i + 2];
191 char c3 = (char)oldByteArray[i + 3];
192 char c4 = (char)oldByteArray[i + 4];
193 char c5 = (char)oldByteArray[i + 5];
194 char c6 = (char)oldByteArray[i + 6];
195 char c7 = (char)oldByteArray[i + 7];
196 char c8 = (char)oldByteArray[i + 8];
197 char c9 = (char)oldByteArray[i + 9];
198 char c10 = (char)oldByteArray[i + 10];
199
200 if (((c1 == '/')) &&
201 ((c2 == 't') || (c2 == 'T')) &&
202 ((c3 == 'e') || (c3 == 'E')) &&
203 ((c4 == 'x') || (c4 == 'X')) &&
204 ((c5 == 't') || (c5 == 'T')) &&
205 ((c6 == 'a') || (c6 == 'A')) &&
206 ((c7 == 'r') || (c7 == 'R')) &&
207 ((c8 == 'e') || (c8 == 'E')) &&
208 ((c9 == 'a') || (c9 == 'A')) &&
209 ((c10 == '>'))) {
210
211 ignore = false;
212 }
213 }
214 }
215 }
216
217 if ((!ignore) &&
218 ((c == '\n') || (c == '\r') || (c == '\t'))) {
219
220 if ((i + 1) == oldByteArray.length) {
221 }
222
223 if ((prevChar == '\n') || (prevChar == '\r')) {
224 }
225 else {
226 if (c != '\t') {
227 prevChar = c;
228 }
229
230 newByteArray[newByteArrayPos++] = b;
231 }
232 }
233 else {
234 prevChar = c;
235
236 newByteArray[newByteArrayPos++] = b;
237 }
238 }
239 }
240 else {
241 newByteArray = oldByteArray;
242 newByteArrayPos = oldByteArray.length;
243 }
244
245 ServletResponseUtil.write(
246 httpRes, newByteArray, newByteArrayPos);
247 }
248 }
249 else {
250 if (_log.isDebugEnabled()) {
251 _log.debug("Not stripping " + completeURL);
252 }
253
254 doFilter(StripFilter.class, req, res, chain);
255 }
256 }
257
258 protected boolean isAlreadyFiltered(HttpServletRequest req) {
259 if (req.getAttribute(_ALREADY_FILTERED) != null) {
260 return true;
261 }
262 else {
263 return false;
264 }
265 }
266
267 protected boolean isInclude(HttpServletRequest req) {
268 String uri = (String)req.getAttribute(
269 JavaConstants.JAVAX_SERVLET_INCLUDE_REQUEST_URI);
270
271 if (uri == null) {
272 return false;
273 }
274 else {
275 return true;
276 }
277 }
278
279 protected boolean isStrip(HttpServletRequest req) {
280 if (!ParamUtil.get(req, _STRIP, true)) {
281 return false;
282 }
283 else {
284
285
290 boolean action = ParamUtil.getBoolean(req, "p_p_action");
291 String windowState = ParamUtil.getString(req, "p_p_state");
292
293 if (action && windowState.equals("exclusive")) {
294 return false;
295 }
296 else {
297 return true;
298 }
299 }
300 }
301
302 private static final String _ALREADY_FILTERED =
303 StripFilter.class.getName() + "_ALREADY_FILTERED";
304
305 private static final String _STRIP = "strip";
306
307 private static Log _log = LogFactoryUtil.getLog(StripFilter.class);
308
309 }