Add predefined Velocity and CSS template if wiki builder is assigned to a project
[phpeclipse.git] / archive / net.sourceforge.phpeclipse.wiki / src / net / sourceforge / phpeclipse / wiki / builder / CreatePageAction.java
1 package net.sourceforge.phpeclipse.wiki.builder;
2
3 import java.io.BufferedInputStream;
4 import java.io.File;
5 import java.io.FileNotFoundException;
6 import java.io.FileOutputStream;
7 import java.io.FileWriter;
8 import java.io.IOException;
9 import java.io.InputStream;
10 import java.io.InputStreamReader;
11 import java.util.Iterator;
12
13 import net.sourceforge.phpeclipse.wiki.editor.WikiEditorPlugin;
14 import net.sourceforge.phpeclipse.wiki.preferences.Util;
15 import net.sourceforge.phpeclipse.wiki.renderer.IContentRenderer;
16 import net.sourceforge.phpeclipse.wiki.renderer.RendererFactory;
17
18 import org.eclipse.core.resources.IFile;
19 import org.eclipse.core.resources.IResource;
20 import org.eclipse.core.runtime.CoreException;
21 import org.eclipse.jface.action.IAction;
22 import org.eclipse.jface.viewers.ISelection;
23 import org.eclipse.jface.viewers.ISelectionProvider;
24 import org.eclipse.jface.viewers.StructuredSelection;
25 import org.eclipse.ui.IActionDelegate;
26 import org.eclipse.ui.IObjectActionDelegate;
27 import org.eclipse.ui.IWorkbenchPart;
28
29 /**
30  * Create a static HTML page
31  */
32 public class CreatePageAction implements IObjectActionDelegate {
33   /**
34    * Constant for an empty char array
35    */
36   public static final char[] NO_CHAR = new char[0];
37
38   private static final int DEFAULT_READING_SIZE = 8192;
39
40   private IWorkbenchPart workbenchPart;
41
42   /**
43    *  
44    */
45   public CreatePageAction() {
46     super();
47   }
48
49   /**
50    * @see IObjectActionDelegate#setActivePart(IAction, IWorkbenchPart)
51    */
52   public void setActivePart(IAction action, IWorkbenchPart targetPart) {
53     workbenchPart = targetPart;
54   }
55
56   public void run(IAction action) {
57     ISelectionProvider selectionProvider = null;
58     selectionProvider = workbenchPart.getSite().getSelectionProvider();
59
60     StructuredSelection selection = null;
61     selection = (StructuredSelection) selectionProvider.getSelection();
62
63     //Shell shell = null;
64     Iterator iterator = null;
65     iterator = selection.iterator();
66     while (iterator.hasNext()) {
67       //  obj => selected object in the view
68       Object obj = iterator.next();
69
70       // is it a resource
71       if (obj instanceof IResource) {
72         IResource resource = (IResource) obj;
73
74         // check if it's a file resource
75         switch (resource.getType()) {
76
77         case IResource.FILE:
78           createPage((IFile) resource);
79         }
80       }
81     }
82   }
83
84   /**
85    * @see IActionDelegate#selectionChanged(IAction, ISelection)
86    */
87   public void selectionChanged(IAction action, ISelection selection) {
88   }
89
90   public static void createPage(IFile file) {
91     String templateFileName = Util.getLocalTemplate(file);
92     String srcBasePath = Util.getWikiTextsPath(file);
93     String binBasePath = Util.getProjectsWikiOutputPath(file.getProject(), WikiEditorPlugin.HTML_OUTPUT_PATH);
94     createPage(templateFileName, file, binBasePath, srcBasePath);
95   }
96
97   public static void createPage(String templateFileName, IFile file, String binBasepath, String srcBasePath) {
98     //          only interested in files with the "wp" extension
99     if ("wp".equalsIgnoreCase(file.getFileExtension())) {
100       try {
101         IContentRenderer renderer = RendererFactory.createContentRenderer(file.getProject());
102         convertWikiFile(templateFileName, file, binBasepath, srcBasePath, renderer);
103       } catch (InstantiationException e) {
104         // TODO Auto-generated catch block
105         e.printStackTrace();
106       } catch (IllegalAccessException e) {
107         // TODO Auto-generated catch block
108         e.printStackTrace();
109       } catch (ClassNotFoundException e) {
110         // TODO Auto-generated catch block
111         e.printStackTrace();
112       } catch (CoreException e1) {
113         // TODO Auto-generated catch block
114         e1.printStackTrace();
115       }
116     } else {
117       String fname = file.getName().toLowerCase();
118       if ((fname.charAt(0) == '.') || "project.index".equals(fname) || "cvs".equals(fname) || "entries".equals(fname)
119           || "repository".equals(fname) || "root".equals(fname)) {
120         // ignore meta information
121         return;
122       }
123       // copy the file
124       FileOutputStream output = null;
125       InputStream contentStream = null;
126
127       try {
128         String filename = Util.getHTMLFileName(file, binBasepath, srcBasePath);
129         if (filename != null) {
130           int index = filename.lastIndexOf('/');
131           if (index >= 0) {
132             File ioFile = new File(filename.substring(0, index));
133             if (!ioFile.isDirectory()) {
134               ioFile.mkdirs();
135             }
136           }
137           output = new FileOutputStream(filename);
138
139           contentStream = file.getContents(false);
140           int chunkSize = contentStream.available();
141           byte[] readBuffer = new byte[chunkSize];
142           int n = contentStream.read(readBuffer);
143
144           while (n > 0) {
145             output.write(readBuffer);
146             n = contentStream.read(readBuffer);
147           }
148         }
149       } catch (Exception e) {
150
151       } finally {
152         try {
153           if (output != null)
154             output.close();
155           if (contentStream != null)
156             contentStream.close();
157         } catch (IOException e1) {
158         }
159       }
160     }
161   }
162
163   public static void convertWikiFile(String templateFileName, IFile file, String binBasePath, String srcBasePath, IContentRenderer renderer)
164       throws CoreException {
165     StringBuffer htmlBuffer = new StringBuffer();
166     convertWikiBuffer(templateFileName, htmlBuffer, file, renderer, true);
167     String htmlName = Util.getHTMLFileName(file, binBasePath, srcBasePath);
168     if (htmlName != null) {
169       writeHTMLFile(htmlBuffer, htmlName);
170     }
171   }
172
173   public static void getWikiBuffer(StringBuffer htmlBuffer, IFile file) throws CoreException {
174     BufferedInputStream stream = new BufferedInputStream(file.getContents());
175     try {
176       htmlBuffer.append(getInputStreamAsCharArray(stream, -1, null));
177       return;
178       //new String(getInputStreamAsCharArray(stream, -1, null));
179     } catch (IOException e) {
180       e.printStackTrace();
181     } finally {
182       try {
183         if (stream != null) {
184           stream.close();
185         }
186       } catch (IOException e) {
187       }
188     }
189     return;
190   }
191
192   public static void convertWikiBuffer(String templateFileName, StringBuffer htmlBuffer, IFile file, IContentRenderer renderer, boolean completeHTML)
193       throws CoreException {
194     BufferedInputStream stream = new BufferedInputStream(file.getContents());
195     try {
196       String content = new String(getInputStreamAsCharArray(stream, -1, null));
197       String srcPath = Util.getWikiTextsPath(file);
198       String filePath = file.getLocation().toString(); // file.getProjectRelativePath().toString()
199       if (filePath.startsWith(srcPath)) {
200         filePath = filePath.substring(srcPath.length()+1);
201       }
202       createWikiBuffer(templateFileName, htmlBuffer, filePath, content, renderer, completeHTML);
203     } catch (IOException e) {
204       e.printStackTrace();
205     } finally {
206       try {
207         if (stream != null) {
208           stream.close();
209         }
210       } catch (IOException e) {
211       }
212     }
213   }
214
215   /**
216    * @param htmlBuffer
217    * @param fileName
218    * @param content
219    * @param renderer
220    */
221   public static void createWikiBuffer(String templateFileName, StringBuffer htmlBuffer, String fileName, String content, IContentRenderer renderer,
222       boolean completeHTML) {
223     // calculate the <i>depth</i> of the file (i.e. ../../../ as much as needed)
224     int index = 0;
225     int level = 0;
226     while (index >= 0) {
227       index = fileName.indexOf('/', index);
228       if (index >= 0) {
229         level++;
230         index++;
231       }
232     }
233     renderer.render(templateFileName, content, htmlBuffer, level, completeHTML);
234   }
235
236   public static void writeHTMLFile(StringBuffer buffer, String filename) {
237     int index = filename.lastIndexOf('/');
238     if (index >= 0) {
239       File file = new File(filename.substring(0, index));
240       if (!file.isDirectory()) {
241         file.mkdirs();
242       }
243     }
244     FileWriter fileWriter;
245     try {
246       fileWriter = new FileWriter(filename);
247       fileWriter.write(buffer.toString());
248       fileWriter.close();
249     } catch (FileNotFoundException e) {
250       // ignore exception; project is deleted by fUser
251     } catch (IOException e) {
252       // TODO Auto-generated catch block
253       e.printStackTrace();
254     }
255   }
256
257   /**
258    * Returns the given input stream's contents as a character array. If a length is specified (ie. if length != -1), only length
259    * chars are returned. Otherwise all chars in the stream are returned. Note this doesn't close the stream.
260    * 
261    * @throws IOException
262    *           if a problem occured reading the stream.
263    */
264   public static char[] getInputStreamAsCharArray(InputStream stream, int length, String encoding) throws IOException {
265     InputStreamReader reader = null;
266     reader = encoding == null ? new InputStreamReader(stream) : new InputStreamReader(stream, encoding);
267     char[] contents;
268     if (length == -1) {
269       contents = NO_CHAR;
270       int contentsLength = 0;
271       int amountRead = -1;
272       do {
273         int amountRequested = Math.max(stream.available(), DEFAULT_READING_SIZE); // read at least 8K
274
275         // resize contents if needed
276         if (contentsLength + amountRequested > contents.length) {
277           System.arraycopy(contents, 0, contents = new char[contentsLength + amountRequested], 0, contentsLength);
278         }
279
280         // read as many chars as possible
281         amountRead = reader.read(contents, contentsLength, amountRequested);
282
283         if (amountRead > 0) {
284           // remember length of contents
285           contentsLength += amountRead;
286         }
287       } while (amountRead != -1);
288
289       // resize contents if necessary
290       if (contentsLength < contents.length) {
291         System.arraycopy(contents, 0, contents = new char[contentsLength], 0, contentsLength);
292       }
293     } else {
294       contents = new char[length];
295       int len = 0;
296       int readSize = 0;
297       while ((readSize != -1) && (len != length)) {
298         // See PR 1FMS89U
299         // We record first the read size. In this case len is the actual
300         // read size.
301         len += readSize;
302         readSize = reader.read(contents, len, length - len);
303       }
304       // See PR 1FMS89U
305       // Now we need to resize in case the default encoding used more than
306       // one byte for each
307       // character
308       if (len != length)
309         System.arraycopy(contents, 0, (contents = new char[len]), 0, len);
310     }
311
312     return contents;
313   }
314 }