1 package com.atlassian.plugin.servlet;
2
3 import com.atlassian.plugin.elements.ResourceLocation;
4 import com.atlassian.plugin.servlet.util.CapturingHttpServletResponse;
5 import com.atlassian.plugin.util.PluginUtils;
6
7 import com.google.common.collect.ImmutableMap;
8
9 import java.io.ByteArrayInputStream;
10 import java.io.ByteArrayOutputStream;
11 import java.io.InputStream;
12 import java.util.Map;
13
14 import junit.framework.AssertionFailedError;
15 import junit.framework.TestCase;
16
17
18
19
20 public class TestAbstractDownloadableResource extends TestCase
21 {
22 private static final String MINIFIED_CONTENT = "minified content";
23 private static final String PLAIN_CONTENT = "plain content";
24 private static final String NEVER_MINIFIED_CONTENT = "never minified content";
25 private static final Map<String, String> EMPTY_PARAMS = ImmutableMap.of();
26
27 private class MinifiedFileServingDownloadableResource extends AbstractDownloadableResource
28 {
29 public MinifiedFileServingDownloadableResource(final ResourceLocation resourceLocation)
30 {
31 super(null, resourceLocation, null);
32 }
33
34 @Override
35 protected String getLocation()
36 {
37 return "somecode.js";
38 }
39
40 @Override
41 public String getContentType()
42 {
43 return "minified/content";
44 }
45
46 @Override
47 protected InputStream getResourceAsStream(final String resourceLocation)
48 {
49 if (resourceLocation.contains("-min."))
50 {
51 assertEquals("somecode-min.js", resourceLocation);
52 return newStream(MINIFIED_CONTENT);
53 }
54 assertEquals("somecode.js", resourceLocation);
55 return newStream(PLAIN_CONTENT);
56 }
57
58 private InputStream newStream(final String s)
59 {
60 return new ByteArrayInputStream(s.getBytes());
61 }
62 }
63
64 private class MyDownloadableResource extends AbstractDownloadableResource
65 {
66 private String passedResourceLocation;
67
68 public MyDownloadableResource(final ResourceLocation resourceLocation, final boolean disableMinification)
69 {
70 super(null, resourceLocation, "", disableMinification);
71 }
72
73 @Override
74 protected InputStream getResourceAsStream(final String resourceLocation)
75 {
76 passedResourceLocation = resourceLocation;
77 return newStream(resourceLocation);
78 }
79
80 private InputStream newStream(final String s)
81 {
82 return new ByteArrayInputStream(s.getBytes());
83 }
84 }
85
86 private class NotMinifiedFileServingDownloadableResouce extends AbstractDownloadableResource
87 {
88 public NotMinifiedFileServingDownloadableResouce()
89 {
90 super(null, new ResourceLocation("/flintstone/fred.jpg", "fred.jpg", "stuff", "stuff", "stuff", EMPTY_PARAMS), null);
91 }
92
93 @Override
94 protected String getLocation()
95 {
96 return "somemorecode.js";
97 }
98
99 @Override
100 public String getContentType()
101 {
102 return "plain/content";
103 }
104
105 @Override
106 protected InputStream getResourceAsStream(final String resourceLocation)
107 {
108 if (resourceLocation.contains("-min."))
109 {
110 assertEquals("somemorecode-min.js", resourceLocation);
111 return null;
112 }
113 assertEquals("somemorecode.js", resourceLocation);
114 return newStream(PLAIN_CONTENT);
115 }
116
117 private InputStream newStream(final String s)
118 {
119 return new ByteArrayInputStream(s.getBytes());
120 }
121
122 }
123
124 private class NeverMinifiedFileServingDownloadableResource extends AbstractDownloadableResource
125 {
126 public NeverMinifiedFileServingDownloadableResource()
127 {
128 super(null, new ResourceLocation("/flintstone/fred.jpg", "fred.jpg", "stuff", "stuff", "stuff", EMPTY_PARAMS), null);
129 }
130
131 @Override
132 protected String getLocation()
133 {
134 return "neverminified.js";
135 }
136
137 @Override
138 public String getContentType()
139 {
140 return "neverminified/content";
141 }
142
143 @Override
144 protected InputStream getResourceAsStream(final String resourceLocation)
145 {
146 if (resourceLocation.contains("-min."))
147 {
148 fail("it should never ask for this");
149 }
150 assertEquals("neverminified.js", resourceLocation);
151 return newStream(NEVER_MINIFIED_CONTENT);
152 }
153
154 private InputStream newStream(final String s)
155 {
156 return new ByteArrayInputStream(s.getBytes());
157 }
158 }
159
160 @Override
161 public void setUp() throws Exception
162 {
163 super.setUp();
164 System.setProperty("atlassian.webresource.disable.minification", "false");
165 System.setProperty("atlassian.dev.mode", "false");
166 }
167
168 public void testMinificationStrategyWrongFileType() throws Exception
169 {
170 final ResourceLocation resourceLocation = new ResourceLocation("/flintstone/fred.jpg", "fred.jpg", "stuff", "stuff", "stuff", EMPTY_PARAMS);
171 final MyDownloadableResource myDownloadableResource = new MyDownloadableResource(resourceLocation, false);
172 myDownloadableResource.streamResource(new ByteArrayOutputStream());
173
174 assertEquals("/flintstone/fred.jpg", myDownloadableResource.passedResourceLocation);
175 }
176
177 public void testMinificationStrategyCss() throws Exception
178 {
179 final ResourceLocation resourceLocation = new ResourceLocation("/flintstone/fred.css", "fred.css", "stuff", "stuff", "stuff", EMPTY_PARAMS);
180 final MyDownloadableResource myDownloadableResource = new MyDownloadableResource(resourceLocation, false);
181 myDownloadableResource.streamResource(new ByteArrayOutputStream());
182
183 assertEquals("/flintstone/fred-min.css", myDownloadableResource.passedResourceLocation);
184 }
185
186 public void testMinificationStrategyWithTwoMinsInName() throws Exception
187 {
188 final ResourceLocation resourceLocation = new ResourceLocation("/flintstone-min./fred-min.js", "fred-min.js", "stuff", "stuff", "stuff", EMPTY_PARAMS);
189 final MyDownloadableResource myDownloadableResource = new MyDownloadableResource(resourceLocation, false);
190 myDownloadableResource.streamResource(new ByteArrayOutputStream());
191
192 assertEquals("/flintstone-min./fred-min.js", myDownloadableResource.passedResourceLocation);
193 }
194
195 public void testMinificationStrategyAlreadyMinimised() throws Exception
196 {
197 final ResourceLocation resourceLocation = new ResourceLocation("/flintstone/fred-min.js", "fred-min.js", "stuff", "stuff", "stuff", EMPTY_PARAMS);
198 final MyDownloadableResource myDownloadableResource = new MyDownloadableResource(resourceLocation, false);
199 myDownloadableResource.streamResource(new ByteArrayOutputStream());
200
201 assertEquals("/flintstone/fred-min.js", myDownloadableResource.passedResourceLocation);
202 }
203
204 public void testMinificationStrategyNotMinimisedAndEnabled() throws Exception
205 {
206 final ResourceLocation resourceLocation = new ResourceLocation("/flintstone/fred.js", "fred.js", "stuff", "stuff", "stuff", EMPTY_PARAMS);
207 final MyDownloadableResource myDownloadableResource = new MyDownloadableResource(resourceLocation, false);
208 myDownloadableResource.streamResource(new ByteArrayOutputStream());
209
210 assertEquals("/flintstone/fred-min.js", myDownloadableResource.passedResourceLocation);
211 }
212
213 public void testMinificationStrategyNotMinimisedAndDisabled() throws Exception
214 {
215 final ResourceLocation resourceLocation = new ResourceLocation("/flintstone/fred.js", "fred.js", "stuff", "stuff", "stuff", EMPTY_PARAMS);
216 final MyDownloadableResource myDownloadableResource = new MyDownloadableResource(resourceLocation, true);
217 myDownloadableResource.streamResource(new ByteArrayOutputStream());
218
219 assertEquals("/flintstone/fred.js", myDownloadableResource.passedResourceLocation);
220 }
221
222 public void testMinificationStrategyNotMinimisedAndSystemDisabled() throws Exception
223 {
224 System.setProperty("atlassian.webresource.disable.minification", "true");
225
226 final ResourceLocation resourceLocation = new ResourceLocation("/flintstone/fred.js", "fred.js", "stuff", "stuff", "stuff", EMPTY_PARAMS);
227 final MyDownloadableResource myDownloadableResource = new MyDownloadableResource(resourceLocation, false);
228 myDownloadableResource.streamResource(new ByteArrayOutputStream());
229
230 assertEquals("/flintstone/fred.js", myDownloadableResource.passedResourceLocation);
231 }
232
233 public void testMinificationStrategyNotMinimisedAndSystemEnabled() throws Exception
234 {
235 System.setProperty("atlassian.webresource.disable.minification", "false");
236
237 final ResourceLocation resourceLocation = new ResourceLocation("/flintstone/fred.js", "fred.js", "stuff", "stuff", "stuff", EMPTY_PARAMS);
238 final MyDownloadableResource myDownloadableResource = new MyDownloadableResource(resourceLocation, false);
239 myDownloadableResource.streamResource(new ByteArrayOutputStream());
240
241 assertEquals("/flintstone/fred-min.js", myDownloadableResource.passedResourceLocation);
242 }
243
244 public void testWithMinifiedStrategyInPlay() throws DownloadException
245 {
246
247 final MinifiedFileServingDownloadableResource minifiedFileServingDownloadableResource = new MinifiedFileServingDownloadableResource(new ResourceLocation("/flintstone/fred.jpg", "fred.jpg", "stuff", "stuff", "stuff", EMPTY_PARAMS));
248 assertContent(minifiedFileServingDownloadableResource, MINIFIED_CONTENT);
249
250
251 final NotMinifiedFileServingDownloadableResouce notMinifiedFileServingDownloadableResource = new NotMinifiedFileServingDownloadableResouce();
252 assertContent(notMinifiedFileServingDownloadableResource, PLAIN_CONTENT);
253
254 }
255
256 public void testWhenSystemPropertyIsSet() throws DownloadException
257 {
258 verifySystemPropertyRespected("atlassian.webresource.disable.minification");
259 }
260
261 public void testWhenDevModeSystemPropertyIsSet() throws DownloadException
262 {
263 verifySystemPropertyRespected(PluginUtils.ATLASSIAN_DEV_MODE);
264 }
265
266 private void verifySystemPropertyRespected(String sysprop)
267 throws DownloadException
268 {
269 try
270 {
271 System.setProperty(sysprop, "true");
272
273
274 final NeverMinifiedFileServingDownloadableResource neverMinifiedFileServingDownloadableResource = new NeverMinifiedFileServingDownloadableResource();
275 assertContent(neverMinifiedFileServingDownloadableResource, NEVER_MINIFIED_CONTENT);
276
277 final MinifiedFileServingDownloadableResource minifiedFileServingDownloadableResource = new MinifiedFileServingDownloadableResource(new ResourceLocation("/flintstone/fred.jpg", "fred.jpg", "stuff", "stuff", "stuff", EMPTY_PARAMS));
278 assertContent(minifiedFileServingDownloadableResource, PLAIN_CONTENT);
279
280
281 final NotMinifiedFileServingDownloadableResouce notMinifiedFileServingDownloadableResource = new NotMinifiedFileServingDownloadableResouce();
282 assertContent(notMinifiedFileServingDownloadableResource, PLAIN_CONTENT);
283
284 System.setProperty(sysprop, "false");
285
286
287 assertContent(minifiedFileServingDownloadableResource, MINIFIED_CONTENT);
288
289
290 assertContent(notMinifiedFileServingDownloadableResource, PLAIN_CONTENT);
291
292
293
294
295
296 try
297 {
298 assertContent(neverMinifiedFileServingDownloadableResource, "doesnt matter");
299
300 fail("This should have barfed in NeverMinifiedFileServingDownloadableResource");
301 }
302 catch (final AssertionFailedError expected)
303 {
304
305
306 }
307 }
308 finally
309 {
310
311 System.setProperty(sysprop, "false");
312 }
313 }
314
315 private void assertContent(final AbstractDownloadableResource downloadableResource, final String content) throws DownloadException
316 {
317 final CapturingHttpServletResponse httpServletResponse = new CapturingHttpServletResponse();
318 final ByteArrayOutputStream baos = new ByteArrayOutputStream();
319
320 try
321 {
322 downloadableResource.serveResource(null, httpServletResponse);
323 }
324 catch (final DownloadException e)
325 {
326 throw new RuntimeException(e);
327 }
328 downloadableResource.streamResource(baos);
329
330 assertEquals(content, httpServletResponse.toString());
331 assertEquals(content, baos.toString());
332 }
333 }