KickJava   Java API By Example, From Geeks To Geeks.

Java > Open Source Codes > com > sslexplorer > extensions > ExtensionInstaller


1 /*
2  * SSL-Explorer
3  *
4  * Copyright (C) 2003-2006 3SP LTD. All Rights Reserved
5  *
6  * This program is free software; you can redistribute it and/or
7  * modify it under the terms of the GNU General Public License
8  * as published by the Free Software Foundation; either version 2 of
9  * the License, or (at your option) any later version.
10  * This program is distributed in the hope that it will be useful,
11  * but WITHOUT ANY WARRANTY; without even the implied warranty of
12  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
13  * GNU General Public License for more details.
14  *
15  * You should have received a copy of the GNU General Public
16  * License along with this program; if not, write to the Free Software
17  * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
18  */

19             
20 package com.sslexplorer.extensions;
21
22 import java.io.File JavaDoc;
23 import java.io.IOException JavaDoc;
24 import java.util.ArrayList JavaDoc;
25 import java.util.List JavaDoc;
26
27 import org.apache.commons.logging.Log;
28 import org.apache.commons.logging.LogFactory;
29
30 import com.sslexplorer.boot.Util;
31 import com.sslexplorer.core.CoreUtil;
32 import com.sslexplorer.core.stringreplacement.ExtensionBundleReplacer;
33 import com.sslexplorer.extensions.store.ExtensionStore;
34
35 /**
36  * Encapsulates an installation process. Implementations of
37  * {@link ExtensionInstallOp} should be added using
38  * {@link #addOp(com.sslexplorer.extensions.ExtensionInstaller.ExtensionInstallOp)}.
39  * The entire process may then be run by invoking {@link #doInstall(String)}.
40  * <p>
41  * Installers may currently be run in two different phases, <i>Extension
42  * Activation</i> and <i>Extension Startup</i>. This is determined by the
43  * {@link ExtensionInstallOp#getPhase()}.
44  * <p>
45  * Before calling {@link #doInstall(String)},
46  *
47  *
48  * @author Brett Smith <a HREF="mailto: brett@3sp.com">&lt;brett@3sp.com&gt;</a>
49  */

50 public class ExtensionInstaller {
51
52     final static Log log = LogFactory.getLog(ExtensionInstaller.class);
53
54     /**
55      * State returned by {@link ExtensionInstallOp#getPhase()} for actions that
56      * should be run when extension is activated
57      */

58     public static final String JavaDoc ON_ACTIVATE = "activate";
59
60     /**
61      * State returned by {@link ExtensionInstallOp#getPhase()} for actions that
62      * should be run when extension is started
63      */

64     public static final String JavaDoc ON_START = "start";
65
66     // Private instance variables
67

68     private ExtensionBundle bundle;
69     private List JavaDoc<ExtensionInstallOp> ops;
70
71     /**
72      * Constructor.
73      *
74      * @param bundle bundle this installer is for
75      */

76     public ExtensionInstaller(ExtensionBundle bundle) {
77         this.bundle = bundle;
78         ops = new ArrayList JavaDoc<ExtensionInstallOp>();
79     }
80
81     /**
82      * Get the bundle this installer is for.
83      *
84      * @return bundle
85      */

86     public ExtensionBundle getBundle() {
87         return bundle;
88     }
89
90     /**
91      * Add a new operation to the installer.
92      *
93      * @param op operation
94      */

95     public void addOp(ExtensionInstallOp op) {
96         ops.add(op);
97     }
98
99     /**
100      * Utility method to check if it is ok to use a file in the installer.
101      *
102      * @param file
103      * @return file
104      * @throws IOException on any error
105      */

106     public static File JavaDoc checkFile(File JavaDoc file) throws IOException JavaDoc {
107         /*
108          * TODO Make sure the file is ok for use (e.g. not a file somewhere
109          * outside of SSL-Explorers tree)
110          */

111         return file;
112     }
113
114     /**
115      * Start the install.
116      *
117      * @param phase TODO
118      *
119      * @throws Exception on any error
120      */

121     public void doInstall(String JavaDoc phase) throws Exception JavaDoc {
122         if (ops.size() == 0) {
123             if (log.isInfoEnabled())
124                 log.info("Bundle " + bundle.getName() + " has no installer script.");
125         } else {
126             boolean started = false;
127             try {
128                 for (ExtensionInstallOp op : ops) {
129                     if(op.getPhase().equals(phase) || ( phase.equals(ExtensionInstaller.ON_ACTIVATE) && op.getPhase() == null) ) {
130                         if(!started) {
131                             if (log.isInfoEnabled())
132                                 log.info("Starting installer for " + bundle.getName());
133                             started = true;
134                         }
135                         op.doOp(this);
136                     }
137                 }
138                 if (log.isInfoEnabled())
139                     log.info("Completed installation for " + bundle.getName());
140             } finally {
141                 ExtensionStore.VERSION_PREFS.put(bundle.getId(), bundle.getVersion().toString());
142                 ExtensionStore.VERSION_PREFS.flush();
143             }
144         }
145     }
146
147     /**
148      * Get the number of operations in this install
149      *
150      * @return operations
151      */

152     public int getOpCount() {
153         return ops.size();
154     }
155
156     /**
157      * Interface to be implemented by all extension installer operations
158      *
159      * @see ExtensionInstaller
160      */

161     public static interface ExtensionInstallOp {
162
163         /**
164          * Get the phase this operation should occur in. Will be one of
165          * {@link ExtensionInstaller#ON_ACTIVATE} or
166          * {@link ExtensionInstaller#ON_START}. If this is null it
167          * should be assumed to be {@link ExtensionInstaller#ON_ACTIVATE}.
168          *
169          * @return phase
170          */

171         public String JavaDoc getPhase();
172
173         /**
174          * Perform the install operation.
175          *
176          * @param install
177          * @throws Exception
178          */

179         public void doOp(ExtensionInstaller install) throws Exception JavaDoc;
180     }
181
182     /**
183      * Abstract implementation of an {@link ExtensionInstallOp} providing a
184      * constructor for the <i>Phase</i> attribute.
185      */

186     public static abstract class AbstractExtensionInstallOp implements ExtensionInstallOp {
187         private String JavaDoc phase;
188
189         /**
190          * Constructor.
191          *
192          * @param phase phase
193          */

194         public AbstractExtensionInstallOp(String JavaDoc phase) {
195             this.phase = phase;
196         }
197
198         /*
199          * (non-Javadoc)
200          *
201          * @see com.sslexplorer.extensions.ExtensionInstaller.ExtensionInstallOp#getPhase()
202          */

203         public String JavaDoc getPhase() {
204             return phase;
205         }
206     }
207
208     /**
209      * Create a directory.
210      */

211     public static class MkdirInstallOp extends AbstractExtensionInstallOp {
212         private String JavaDoc path;
213
214         /**
215          * Constructor.
216          *
217          * @param phase phase
218          * @param path path to create
219          * @throws IllegalArgumentException
220          */

221         public MkdirInstallOp(String JavaDoc phase, String JavaDoc path) throws IllegalArgumentException JavaDoc {
222             super(phase);
223             this.path = path;
224         }
225
226         /*
227          * (non-Javadoc)
228          *
229          * @see com.sslexplorer.extensions.ExtensionInstaller.ExtensionInstallOp#doOp(com.sslexplorer.extensions.ExtensionInstaller)
230          */

231         public void doOp(ExtensionInstaller install) throws Exception JavaDoc {
232             path = CoreUtil.platformPath(ExtensionBundleReplacer.replace(install.getBundle(), path));
233             File JavaDoc f = checkFile(new File JavaDoc(path));
234             if (log.isInfoEnabled())
235                 log.info("Creating directory " + f.getAbsolutePath());
236             f.mkdirs();
237         }
238     }
239
240     /**
241      * Remove a file or directory
242      */

243     public static class RmInstallOp extends AbstractExtensionInstallOp {
244         private String JavaDoc path;
245
246         /**
247          * Constructor.
248          *
249          * @param phase phase
250          * @param path path to remove
251          * @throws IllegalArgumentException
252          */

253         public RmInstallOp(String JavaDoc phase, String JavaDoc path) throws IllegalArgumentException JavaDoc {
254             super(phase);
255             this.path = path;
256         }
257
258         /*
259          * (non-Javadoc)
260          *
261          * @see com.sslexplorer.extensions.ExtensionInstaller.ExtensionInstallOp#doOp(com.sslexplorer.extensions.ExtensionInstaller)
262          */

263         public void doOp(ExtensionInstaller install) throws Exception JavaDoc {
264             path = CoreUtil.platformPath(ExtensionBundleReplacer.replace(install.getBundle(), path));
265             File JavaDoc f = checkFile(new File JavaDoc(path));
266             Util.delTree(f);
267         }
268     }
269
270     /**
271      * Copy a file or directory to another file or directory
272      */

273     public static class CpInstallOp extends AbstractExtensionInstallOp {
274         private String JavaDoc from;
275         private String JavaDoc to;
276         private String JavaDoc toDir;
277         private boolean overwrite;
278
279         /**
280          * Constructor.
281          *
282          * @param phase phase
283          * @param from file or directory to copy
284          * @param to to file (use <code>null</code> when copying to dir)
285          * @param toDir to directory (use <code>null</code> when copying to
286          * file)
287          * @param overwrite overwrite target
288          * @throws IllegalArgumentException
289          */

290         public CpInstallOp(String JavaDoc phase, String JavaDoc from, String JavaDoc to, String JavaDoc toDir, boolean overwrite) throws IllegalArgumentException JavaDoc {
291             super(phase);
292             this.from = from;
293             this.to = to;
294             this.toDir = toDir;
295             this.overwrite = overwrite;
296         }
297
298         public void doOp(ExtensionInstaller install) throws Exception JavaDoc {
299             from = CoreUtil.platformPath(ExtensionBundleReplacer.replace(install.getBundle(), from));
300             File JavaDoc f = checkFile(new File JavaDoc(from));
301             if (to != null) {
302                 File JavaDoc t = checkFile(new File JavaDoc(CoreUtil.platformPath(ExtensionBundleReplacer.replace(install.getBundle(), to))));
303                 if (f.isDirectory()) {
304                     throw new Exception JavaDoc("Cannot copy directory to a file");
305                 }
306                 if (log.isInfoEnabled())
307                     log.info("Copying " + f.getAbsolutePath() + " to " + t.getAbsolutePath());
308                 if (t.exists() && !overwrite) {
309                     log.error("Failed to copy to target because it already exists and overwrite attribute is not true");
310                 } else {
311                     Util.copy(f, t);
312                 }
313             } else if (toDir != null) {
314                 File JavaDoc t = checkFile(new File JavaDoc(ExtensionBundleReplacer.replace(install.getBundle(), toDir)));
315                 if (log.isInfoEnabled())
316                     log.info("Copying " + f.getAbsolutePath() + " to " + t.getAbsolutePath());
317                 if (((!t.isDirectory() && t.exists()) || (t.isDirectory() && new File JavaDoc(t, f.getName()).exists())) && !overwrite) {
318                     log.error("Failed to copy to target because it already exists and overwrite attribute is not true");
319                 } else {
320                     Util.copyToDir(f, t, false, true);
321                 }
322             }
323         }
324     }
325
326     /**
327      * Provides a wrapper around another {@link ExtensionInstallOp}
328      * implementation that may be specified by its class name.
329      *
330      * @author Brett Smith <a HREF="mailto: brett@3sp.com">&lt;brett@3sp.com&gt;</a>
331      */

332     public static class CustomInstallOpWrapper extends AbstractExtensionInstallOp {
333
334         private String JavaDoc clazz;
335
336         /**
337          * Constructor.
338          *
339          * @param phase phase
340          * @param clazz class name of wrapper operation
341          */

342         public CustomInstallOpWrapper(String JavaDoc phase, String JavaDoc clazz) {
343             super(phase);
344             this.clazz = clazz;
345         }
346
347         /*
348          * (non-Javadoc)
349          *
350          * @see com.sslexplorer.extensions.ExtensionInstaller.ExtensionInstallOp#doOp(com.sslexplorer.extensions.ExtensionInstaller)
351          */

352         public void doOp(ExtensionInstaller install) throws Exception JavaDoc {
353             if (log.isInfoEnabled())
354                 log.info("Running custom install op. " + clazz);
355             ExtensionInstallOp op = (ExtensionInstallOp) Class.forName(clazz, true, getClass().getClassLoader()).newInstance();
356             op.doOp(install);
357         }
358
359     }
360 }
361
Popular Tags