View Javadoc

1   //
2   //  ========================================================================
3   //  Copyright (c) 1995-2015 Mort Bay Consulting Pty. Ltd.
4   //  ------------------------------------------------------------------------
5   //  All rights reserved. This program and the accompanying materials
6   //  are made available under the terms of the Eclipse Public License v1.0
7   //  and Apache License v2.0 which accompanies this distribution.
8   //
9   //      The Eclipse Public License is available at
10  //      http://www.eclipse.org/legal/epl-v10.html
11  //
12  //      The Apache License v2.0 is available at
13  //      http://www.opensource.org/licenses/apache2.0.php
14  //
15  //  You may elect to redistribute this code under either of these licenses.
16  //  ========================================================================
17  //
18  
19  package org.eclipse.jetty.osgi.boot.internal.serverfactory;
20  
21  import java.util.HashMap;
22  import java.util.Map;
23  import java.util.Properties;
24  
25  import org.eclipse.jetty.osgi.boot.OSGiServerConstants;
26  import org.eclipse.jetty.server.Server;
27  import org.eclipse.jetty.util.log.Log;
28  import org.eclipse.jetty.util.log.Logger;
29  import org.osgi.framework.Bundle;
30  import org.osgi.framework.ServiceEvent;
31  import org.osgi.framework.ServiceListener;
32  import org.osgi.framework.ServiceReference;
33  
34  /**
35   * JettyServerServiceTracker
36   * 
37   * Tracks instances of Jetty Servers, and configures them so that they can deploy 
38   * webapps or ContextHandlers discovered from the OSGi environment.
39   * 
40   */
41  public class JettyServerServiceTracker implements ServiceListener
42  {
43      private static Logger LOG = Log.getLogger(JettyServerServiceTracker.class.getName());
44  
45  
46      /** The context-handler to deactivate indexed by ServerInstanceWrapper */
47      private Map<ServiceReference, ServerInstanceWrapper> _indexByServiceReference = new HashMap<ServiceReference, ServerInstanceWrapper>();
48  
49      /**
50       * Stops each one of the registered servers.
51       */
52      public void stop()
53      {
54          for (ServerInstanceWrapper wrapper : _indexByServiceReference.values())
55          {
56              try
57              {
58                  wrapper.stop();
59              }
60              catch (Throwable t)
61              {
62                  LOG.warn(t);
63              }
64          }
65      }
66  
67      /**
68       * Receives notification that a service has had a lifecycle change.
69       * 
70       * @param ev The <code>ServiceEvent</code> object.
71       */
72      public void serviceChanged(ServiceEvent ev)
73      {
74          ServiceReference sr = ev.getServiceReference();
75          switch (ev.getType())
76          {
77              case ServiceEvent.MODIFIED:
78              case ServiceEvent.UNREGISTERING:
79              {
80                  ServerInstanceWrapper instance = unregisterInIndex(ev.getServiceReference());
81                  if (instance != null)
82                  {
83                      try
84                      {
85                          instance.stop();
86                      }
87                      catch (Exception e)
88                      {
89                          LOG.warn(e);
90                      }
91                  }
92  
93                  if (ev.getType() == ServiceEvent.UNREGISTERING)
94                  {
95                      break;
96                  }
97                  else
98                  {
99                      // modified, meaning: we reload it. now that we stopped it;
100                     // we can register it.
101                 }
102             }
103             case ServiceEvent.REGISTERED:
104             {
105                 try
106                 {
107                     Bundle contributor = sr.getBundle();
108                     Server server = (Server) contributor.getBundleContext().getService(sr);
109                     ServerInstanceWrapper wrapper = registerInIndex(server, sr);
110                     Properties props = new Properties();
111                     for (String key : sr.getPropertyKeys())
112                     {
113                         Object value = sr.getProperty(key);
114                         props.put(key, value);
115                     }
116                     wrapper.start(server, props);
117                 }
118                 catch (Exception e)
119                 {
120                     LOG.warn(e);
121                 }
122                 break;
123             }
124         }
125     }
126 
127     private ServerInstanceWrapper registerInIndex(Server server, ServiceReference sr)
128     {
129         String name = (String) sr.getProperty(OSGiServerConstants.MANAGED_JETTY_SERVER_NAME);
130         if (name == null) { throw new IllegalArgumentException("The property " + OSGiServerConstants.MANAGED_JETTY_SERVER_NAME + " is mandatory"); }
131         ServerInstanceWrapper wrapper = new ServerInstanceWrapper(name);
132         _indexByServiceReference.put(sr, wrapper);
133         return wrapper;
134     }
135 
136     /**
137      * Returns the ContextHandler to stop.
138      * 
139      * @param reg
140      * @return the ContextHandler to stop.
141      */
142     private ServerInstanceWrapper unregisterInIndex(ServiceReference sr)
143     {
144         ServerInstanceWrapper handler = _indexByServiceReference.remove(sr);
145         if (handler == null)
146         {
147             LOG.warn("Unknown Jetty Server ServiceReference: ", sr);
148             return null;
149         }
150        
151         return handler;
152     }
153 }