001 /*
002 * Copyright (C) 2012 eXo Platform SAS.
003 *
004 * This is free software; you can redistribute it and/or modify it
005 * under the terms of the GNU Lesser General Public License as
006 * published by the Free Software Foundation; either version 2.1 of
007 * the License, or (at your option) any later version.
008 *
009 * This software is distributed in the hope that it will be useful,
010 * but WITHOUT ANY WARRANTY; without even the implied warranty of
011 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
012 * Lesser General Public License for more details.
013 *
014 * You should have received a copy of the GNU Lesser General Public
015 * License along with this software; if not, write to the Free
016 * Software Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA
017 * 02110-1301 USA, or see the FSF site: http://www.fsf.org.
018 */
019
020 package org.crsh.standalone;
021
022 import org.crsh.plugin.PluginContext;
023 import org.crsh.plugin.PluginLifeCycle;
024 import org.crsh.plugin.ServiceLoaderDiscovery;
025 import org.crsh.vfs.FS;
026 import org.crsh.vfs.Path;
027
028 import java.io.File;
029 import java.io.IOException;
030 import java.net.URISyntaxException;
031 import java.net.URL;
032 import java.net.URLClassLoader;
033 import java.util.Collections;
034 import java.util.Map;
035 import java.util.logging.Logger;
036
037 /**
038 * A boostrap for starting a standalone CRaSH.
039 */
040 public class Bootstrap extends PluginLifeCycle {
041
042 /** . */
043 protected final Logger log = Logger.getLogger(getClass().getName());
044
045 /** The configuration file system. */
046 private final FS confFS = new FS();
047
048 /** The command file system. */
049 private final FS cmdFS = new FS();
050
051 /** The base classloader. */
052 private final ClassLoader loader;
053
054 /** The attributes. */
055 private Map<String, Object> attributes;
056
057 /**
058 * Create a bootstrap instance with the base classloader and an empty and unmodifiable attribute map.
059 *
060 * @param baseLoader the base classloader crash will use
061 * @throws NullPointerException if the loader argument is null
062 */
063 public Bootstrap(ClassLoader baseLoader) throws NullPointerException {
064 if (baseLoader == null) {
065 throw new NullPointerException("No null base loader accepted");
066 }
067 this.attributes = Collections.emptyMap();
068 this.loader = new URLClassLoader(new URL[]{}, baseLoader);
069 }
070
071 /**
072 * Replaces the attributes to use, the new attributes map will be used as is and not copied.
073 *
074 * @param attributes the attribute map
075 */
076 public void setAttributes(Map<String, Object> attributes) {
077 this.attributes = attributes;
078 }
079
080 /**
081 * Add a configuration path directory.
082 *
083 * @param path the configuration path
084 * @return this bootstrap
085 * @throws NullPointerException when the path argument is null
086 * @throws IOException any io exception
087 */
088 public Bootstrap addToConfPath(File path) throws NullPointerException, IOException {
089 if (path == null) {
090 throw new NullPointerException("No null conf path");
091 }
092 log.info("Added " + path.getCanonicalPath() + " command to conf path");
093 confFS.mount(path);
094 return this;
095 }
096
097 /**
098 * Add a configuration path.
099 *
100 * @param path the configuration path
101 * @return this bootstrap
102 * @throws NullPointerException when the path argument is null
103 * @throws IOException any io exception
104 * @throws URISyntaxException any uri syntax exception
105 */
106 public Bootstrap addToConfPath(Path path) throws NullPointerException, IOException, URISyntaxException {
107 if (path == null) {
108 throw new NullPointerException("No null conf path");
109 }
110 log.info("Added " + path.getValue() + " command to conf path");
111 confFS.mount(loader, path);
112 return this;
113 }
114
115 /**
116 * Add a command path directory.
117 *
118 * @param path the command path
119 * @return this bootstrap
120 * @throws NullPointerException when the path argument is null
121 * @throws IOException any io exception
122 */
123 public Bootstrap addToCmdPath(File path) throws NullPointerException, IOException {
124 if (path == null) {
125 throw new NullPointerException("No null command path");
126 }
127 log.info("Added " + path.getAbsolutePath() + " command to command path");
128 cmdFS.mount(path);
129 return this;
130 }
131
132 /**
133 * Add a command path directory.
134 *
135 * @param path the command path
136 * @return this bootstrap
137 * @throws NullPointerException when the path argument is null
138 * @throws IOException any io exception
139 * @throws URISyntaxException any uri syntax exception
140 */
141 public Bootstrap addToCmdPath(Path path) throws NullPointerException, IOException, URISyntaxException {
142 if (path == null) {
143 throw new NullPointerException("No null command path");
144 }
145 log.info("Added " + path.getValue() + " command to command path");
146 cmdFS.mount(loader, path);
147 return this;
148 }
149
150 /**
151 * Trigger the boostrap.
152 *
153 * @throws Exception any exception that would prevent the bootstrap
154 */
155 public void bootstrap() throws Exception {
156
157 // The service loader discovery
158 ServiceLoaderDiscovery discovery = new ServiceLoaderDiscovery(loader);
159
160 //
161 PluginContext context = new PluginContext(
162 discovery,
163 attributes,
164 cmdFS,
165 confFS,
166 loader);
167
168 //
169 context.refresh();
170
171 //
172 start(context);
173 }
174
175 public void shutdown() {
176 stop();
177 }
178 }