1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19 package org.eclipse.jetty.maven.plugin;
20
21 import java.io.File;
22 import java.io.FileInputStream;
23 import java.io.InputStream;
24 import java.net.URL;
25 import java.util.ArrayList;
26 import java.util.Enumeration;
27 import java.util.HashSet;
28 import java.util.Iterator;
29 import java.util.List;
30 import java.util.Properties;
31 import java.util.Set;
32 import java.util.TreeMap;
33
34 import org.eclipse.jetty.server.Connector;
35 import org.eclipse.jetty.server.Handler;
36 import org.eclipse.jetty.server.ShutdownMonitor;
37 import org.eclipse.jetty.server.handler.HandlerCollection;
38 import org.eclipse.jetty.util.log.Log;
39 import org.eclipse.jetty.util.log.Logger;
40 import org.eclipse.jetty.util.resource.Resource;
41 import org.eclipse.jetty.xml.XmlConfiguration;
42
43
44
45
46
47
48
49
50
51 public class Starter
52 {
53 public static final String PORT_SYSPROPERTY = "jetty.port";
54 private static final Logger LOG = Log.getLogger(Starter.class);
55
56 private List<File> jettyXmls;
57 private File contextXml;
58
59 private JettyServer server = new JettyServer();
60 private JettyWebAppContext webApp;
61
62
63 private int stopPort=0;
64 private String stopKey=null;
65 private Properties props;
66 private String token;
67
68
69
70
71
72
73
74
75
76 public class Artifact
77 {
78 public String gid;
79 public String aid;
80 public String path;
81 public Resource resource;
82
83 public Artifact (String csv)
84 {
85 if (csv != null && !"".equals(csv))
86 {
87 String[] atoms = csv.split(",");
88 if (atoms.length >= 3)
89 {
90 gid = atoms[0].trim();
91 aid = atoms[1].trim();
92 path = atoms[2].trim();
93 }
94 }
95 }
96
97 public Artifact (String gid, String aid, String path)
98 {
99 this.gid = gid;
100 this.aid = aid;
101 this.path = path;
102 }
103
104 public boolean equals(Object o)
105 {
106 if (!(o instanceof Artifact))
107 return false;
108
109 Artifact ao = (Artifact)o;
110 return (((gid == null && ao.gid == null) || (gid != null && gid.equals(ao.gid)))
111 && ((aid == null && ao.aid == null) || (aid != null && aid.equals(ao.aid))));
112 }
113 }
114
115
116
117
118
119
120 public void configureJetty () throws Exception
121 {
122 LOG.debug("Starting Jetty Server ...");
123
124
125 applyJettyXml ();
126
127
128
129 Connector[] connectors = this.server.getConnectors();
130 if (connectors == null|| connectors.length == 0)
131 {
132
133 MavenServerConnector httpConnector = new MavenServerConnector();
134 httpConnector.setServer(this.server);
135 String tmp = System.getProperty(PORT_SYSPROPERTY, MavenServerConnector.DEFAULT_PORT_STR);
136 httpConnector.setPort(Integer.parseInt(tmp.trim()));
137 connectors = new Connector[] {httpConnector};
138 this.server.setConnectors(connectors);
139 }
140
141
142 HandlerCollection handlers = (HandlerCollection) server.getChildHandlerByClass(HandlerCollection.class);
143 if (handlers == null)
144 {
145 handlers = new HandlerCollection();
146 server.setHandler(handlers);
147 }
148
149
150 this.server.configureHandlers();
151
152 webApp = new JettyWebAppContext();
153
154
155 configureWebApp();
156
157
158
159
160
161
162
163 if (contextXml != null)
164 {
165 XmlConfiguration xmlConfiguration = new XmlConfiguration(Resource.toURL(contextXml));
166 xmlConfiguration.getIdMap().put("Server",server);
167 xmlConfiguration.configure(webApp);
168 }
169
170 this.server.addWebApplication(webApp);
171
172 System.err.println("STOP PORT="+stopPort+", STOP KEY="+stopKey);
173 if(stopPort>0 && stopKey!=null)
174 {
175 ShutdownMonitor monitor = ShutdownMonitor.getInstance();
176 monitor.setPort(stopPort);
177 monitor.setKey(stopKey);
178 monitor.setExitVm(true);
179 }
180 }
181
182
183
184
185
186 public void configureWebApp ()
187 throws Exception
188 {
189 if (props == null)
190 return;
191
192
193
194 String str = (String)props.get("context.path");
195 if (str != null)
196 webApp.setContextPath(str);
197
198
199
200 str = (String)props.get("web.xml");
201 if (str != null)
202 webApp.setDescriptor(str);
203
204
205
206 str = (String)props.getProperty("tmp.dir");
207 if (str != null)
208 webApp.setTempDirectory(new File(str.trim()));
209
210 str = (String)props.getProperty("tmp.dir.persist");
211 if (str != null)
212 webApp.setPersistTempDirectory(Boolean.valueOf(str));
213
214
215 str = (String)props.getProperty("base.dir");
216 if (str != null && !"".equals(str.trim()))
217 {
218 webApp.setWar(str);
219 webApp.setBaseResource(Resource.newResource(str));
220 }
221
222
223 str = (String)props.getProperty("base.first");
224 if (str != null && !"".equals(str.trim()))
225 webApp.setBaseAppFirst(Boolean.valueOf(str));
226
227
228
229 str = (String)props.getProperty("maven.war.includes");
230 List<String> defaultWarIncludes = fromCSV(str);
231 str = (String)props.getProperty("maven.war.excludes");
232 List<String> defaultWarExcludes = fromCSV(str);
233
234
235 List<Artifact> wars = new ArrayList<Artifact>();
236
237
238 TreeMap<String, OverlayConfig> orderedConfigs = new TreeMap<String, OverlayConfig>();
239 Enumeration<String> pnames = (Enumeration<String>)props.propertyNames();
240 while (pnames.hasMoreElements())
241 {
242 String n = pnames.nextElement();
243 if (n.startsWith("maven.war.artifact"))
244 {
245 Artifact a = new Artifact((String)props.get(n));
246 a.resource = Resource.newResource("jar:"+Resource.toURL(new File(a.path)).toString()+"!/");
247 wars.add(a);
248 }
249 else if (n.startsWith("maven.war.overlay"))
250 {
251 OverlayConfig c = new OverlayConfig ((String)props.get(n), defaultWarIncludes, defaultWarExcludes);
252 orderedConfigs.put(n,c);
253 }
254 }
255
256
257 Set<Artifact> matchedWars = new HashSet<Artifact>();
258
259
260 List<Overlay> overlays = new ArrayList<Overlay>();
261 for (OverlayConfig config:orderedConfigs.values())
262 {
263
264 if (config.isSkip())
265 continue;
266
267
268 if (config.isCurrentProject())
269 {
270 Overlay overlay = new Overlay(config, null);
271 overlays.add(overlay);
272 continue;
273 }
274
275
276 Artifact a = getArtifactForOverlayConfig(config, wars);
277 if (a != null)
278 {
279 matchedWars.add(a);
280 SelectiveJarResource r = new SelectiveJarResource(new URL("jar:"+Resource.toURL(new File(a.path)).toString()+"!/"));
281 r.setIncludes(config.getIncludes());
282 r.setExcludes(config.getExcludes());
283 Overlay overlay = new Overlay(config, r);
284 overlays.add(overlay);
285 }
286 }
287
288
289 for (Artifact a: wars)
290 {
291 if (!matchedWars.contains(a))
292 {
293 Overlay overlay = new Overlay(null, a.resource);
294 overlays.add(overlay);
295 }
296 }
297
298 webApp.setOverlays(overlays);
299
300
301
302 str = (String)props.getProperty("classes.dir");
303 if (str != null && !"".equals(str.trim()))
304 {
305 webApp.setClasses(new File(str));
306 }
307
308 str = (String)props.getProperty("testClasses.dir");
309 if (str != null && !"".equals(str.trim()))
310 {
311 webApp.setTestClasses(new File(str));
312 }
313
314
315
316 str = (String)props.getProperty("lib.jars");
317 if (str != null && !"".equals(str.trim()))
318 {
319 List<File> jars = new ArrayList<File>();
320 String[] names = str.split(",");
321 for (int j=0; names != null && j < names.length; j++)
322 jars.add(new File(names[j].trim()));
323 webApp.setWebInfLib(jars);
324 }
325
326 }
327
328
329
330
331
332 public void getConfiguration (String[] args)
333 throws Exception
334 {
335 for (int i=0; i<args.length; i++)
336 {
337
338 if ("--stop-port".equals(args[i]))
339 stopPort = Integer.parseInt(args[++i]);
340
341
342 if ("--stop-key".equals(args[i]))
343 stopKey = args[++i];
344
345
346 if ("--jetty-xml".equals(args[i]))
347 {
348 jettyXmls = new ArrayList<File>();
349 String[] names = args[++i].split(",");
350 for (int j=0; names!= null && j < names.length; j++)
351 {
352 jettyXmls.add(new File(names[j].trim()));
353 }
354 }
355
356
357 if ("--context-xml".equals(args[i]))
358 {
359 contextXml = new File(args[++i]);
360 }
361
362
363 if ("--props".equals(args[i]))
364 {
365 File f = new File(args[++i].trim());
366 props = new Properties();
367 try (InputStream in = new FileInputStream(f))
368 {
369 props.load(in);
370 }
371 }
372
373
374 if ("--token".equals(args[i]))
375 {
376 token = args[++i].trim();
377 }
378 }
379 }
380
381
382
383
384
385 public void run() throws Exception
386 {
387 LOG.info("Started Jetty Server");
388 server.start();
389 }
390
391
392
393
394
395 public void join () throws Exception
396 {
397 server.join();
398 }
399
400
401
402
403
404 public void communicateStartupResult (Exception e)
405 {
406 if (token != null)
407 {
408 if (e==null)
409 System.out.println(token);
410 else
411 System.out.println(token+"\t"+e.getMessage());
412 }
413 }
414
415
416
417
418
419 public void applyJettyXml() throws Exception
420 {
421 if (jettyXmls == null)
422 return;
423
424 for ( File xmlFile : jettyXmls )
425 {
426 LOG.info( "Configuring Jetty from xml configuration file = " + xmlFile.getCanonicalPath() );
427 XmlConfiguration xmlConfiguration = new XmlConfiguration(Resource.toURL(xmlFile));
428 xmlConfiguration.configure(this.server);
429 }
430 }
431
432
433
434
435
436
437
438
439 protected void prependHandler (Handler handler, HandlerCollection handlers)
440 {
441 if (handler == null || handlers == null)
442 return;
443
444 Handler[] existing = handlers.getChildHandlers();
445 Handler[] children = new Handler[existing.length + 1];
446 children[0] = handler;
447 System.arraycopy(existing, 0, children, 1, existing.length);
448 handlers.setHandlers(children);
449 }
450
451
452
453
454
455
456
457
458 protected Artifact getArtifactForOverlayConfig (OverlayConfig c, List<Artifact> wars)
459 {
460 if (wars == null || wars.isEmpty() || c == null)
461 return null;
462
463 Artifact war = null;
464 Iterator<Artifact> itor = wars.iterator();
465 while(itor.hasNext() && war == null)
466 {
467 Artifact a = itor.next();
468 if (c.matchesArtifact(a.gid, a.aid, null))
469 war = a;
470 }
471 return war;
472 }
473
474
475
476
477
478
479 private List<String> fromCSV (String csv)
480 {
481 if (csv == null || "".equals(csv.trim()))
482 return null;
483 String[] atoms = csv.split(",");
484 List<String> list = new ArrayList<String>();
485 for (String a:atoms)
486 {
487 list.add(a.trim());
488 }
489 return list;
490 }
491
492
493
494
495
496
497 public static final void main(String[] args)
498 {
499 if (args == null)
500 System.exit(1);
501
502 Starter starter = null;
503 try
504 {
505 starter = new Starter();
506 starter.getConfiguration(args);
507 starter.configureJetty();
508 starter.run();
509 starter.communicateStartupResult(null);
510 starter.join();
511 }
512 catch (Exception e)
513 {
514 starter.communicateStartupResult(e);
515 e.printStackTrace();
516 System.exit(1);
517 }
518
519 }
520 }