001: /*
002: * Licensed to the Apache Software Foundation (ASF) under one or more
003: * contributor license agreements. See the NOTICE file distributed with
004: * this work for additional information regarding copyright ownership.
005: * The ASF licenses this file to You under the Apache License, Version 2.0
006: * (the "License"); you may not use this file except in compliance with
007: * the License. You may obtain a copy of the License at
008: *
009: * http://www.apache.org/licenses/LICENSE-2.0
010: *
011: * Unless required by applicable law or agreed to in writing, software
012: * distributed under the License is distributed on an "AS IS" BASIS,
013: * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
014: * See the License for the specific language governing permissions and
015: * limitations under the License.
016: */
017: package org.apache.cocoon.components;
018:
019: import java.io.File;
020: import java.io.FileInputStream;
021: import java.io.FileOutputStream;
022: import java.io.IOException;
023: import java.io.InputStream;
024: import java.io.OutputStream;
025: import java.util.ArrayList;
026: import java.util.Enumeration;
027:
028: import org.apache.cocoon.components.flow.javascript.fom.FOM_Cocoon;
029: import org.apache.cocoon.environment.Request;
030: import org.apache.cocoon.servlet.multipart.Part;
031:
032: /**
033: * @author stefano
034: */
035: public class Repository {
036:
037: public static final String FILE_NAME = "document";
038:
039: private static Repository instance;
040:
041: private Repository() {
042: // do nothing;
043: }
044:
045: public static Repository getInstance() {
046: if (instance == null) {
047: instance = new Repository();
048: }
049: return instance;
050: }
051:
052: private static File getDir(String dirName) {
053: File dir = new File(dirName);
054: if (!dir.isDirectory())
055: throw new RuntimeException("'" + dirName
056: + "' is not a directory!");
057: return dir;
058: }
059:
060: public static void save(Request request, String dirName)
061: throws Exception {
062: File dir = getDir(dirName);
063:
064: Enumeration params = request.getParameterNames();
065: while (params.hasMoreElements()) {
066: String name = (String) params.nextElement();
067: if (name.indexOf("..") > -1)
068: throw new Exception("We are under attack!!");
069: //System.out.println("[param] " + name);
070: if (name.startsWith("save:")) {
071: Part part = (Part) request.get(name);
072: String code = name.substring(5);
073: File file = new File(dir, code);
074: save(part, file);
075: } else if (name.startsWith("delete:")) {
076: String value = request.getParameter(name);
077: if (value.length() > 0) {
078: String code = name.substring(7);
079: File file = new File(dir, code);
080: //System.out.println("[delete] " + file);
081: remove(file);
082: }
083: }
084: }
085: }
086:
087: public static void fomSave(FOM_Cocoon cocoon, String dirName)
088: throws Exception {
089: save(cocoon.getRequest(), dirName);
090: }
091:
092: public static void save(Request request, String param, String file)
093: throws Exception {
094: Part part = (Part) request.get(param);
095: save(part, new File(file));
096: }
097:
098: public static void save(Part part, File file) throws Exception {
099: //System.out.println("[upload] " + part.getFileName() + " -> " + file);
100: InputStream in = null;
101: FileOutputStream out = null;
102: try {
103: in = part.getInputStream();
104: out = new FileOutputStream(file);
105: copy(in, out);
106: } finally {
107: if (out != null) {
108: out.close();
109: }
110: if (in != null) {
111: in.close();
112: }
113: }
114: }
115:
116: public static OutputStream getOutputStream(String dir)
117: throws IOException {
118: String mainFile = dir + "/" + FILE_NAME + ".xml";
119: String versionedFile = dir + "/" + FILE_NAME + "."
120: + getVersionID(dir) + ".xml";
121: copy(mainFile, versionedFile);
122: return new FileOutputStream(mainFile);
123: }
124:
125: public static void revertFrom(String dir, int version)
126: throws IOException {
127: String mainFile = dir + "/" + FILE_NAME + ".xml";
128: String versionedFile = dir + "/" + FILE_NAME + "." + version
129: + ".xml";
130: copy(versionedFile, mainFile);
131: }
132:
133: /**
134: * Returns the highest version id of the files included in the given
135: * directory.
136: */
137: public static int getVersionID(String dirName) {
138: File dir = getDir(dirName);
139:
140: File[] content = dir.listFiles();
141: int id = 0;
142: for (int i = 0; i < content.length; i++) {
143: if (content[i].isFile()) {
144: try {
145: int localid = getVersion(content[i].getName());
146: if (localid > id)
147: id = localid;
148: } catch (Exception e) {
149: }
150: }
151: }
152:
153: return ++id;
154: }
155:
156: public static Object[] getVersions(String dirName) {
157: File dir = getDir(dirName);
158: ArrayList versions = new ArrayList();
159:
160: File[] content = dir.listFiles();
161: for (int i = 0; i < content.length; i++) {
162: if (content[i].isFile()) {
163: try {
164: int version = getVersion(content[i].getName());
165: if (version > 0) {
166: versions.add(new Integer(version));
167: }
168: } catch (Exception e) {
169: }
170: }
171: }
172:
173: return versions.toArray();
174: }
175:
176: /**
177: * Return the version encoded into the name as a numeric subextension of
178: * an .xml extension.
179: *
180: * Example:
181: * anything.123.xml -> 123
182: * document.3.xml -> 3
183: * document.0.xml -> 0
184: * document.xml -> -1
185: * image.0.jpg -> -1
186: */
187: private static int getVersion(String name) {
188: int extIndex = name.lastIndexOf(".xml");
189: if (extIndex > 0) {
190: String nameWithoutExtension = name.substring(0, extIndex);
191: int dotIndex = nameWithoutExtension.lastIndexOf('.');
192: if (dotIndex > 0) {
193: String localidString = nameWithoutExtension
194: .substring(dotIndex + 1);
195: return Integer.parseInt(localidString);
196: }
197: }
198: return -1;
199: }
200:
201: public static int getID(String dirName) {
202: File dir = getDir(dirName);
203:
204: File[] content = dir.listFiles();
205: int id = 0;
206: for (int i = 0; i < content.length; i++) {
207: if (content[i].isDirectory()) {
208: try {
209: String name = content[i].getName();
210: int localid = Integer.parseInt(name);
211: if (localid > id)
212: id = localid;
213: } catch (Exception e) {
214: }
215: }
216: }
217:
218: return ++id;
219: }
220:
221: public static boolean remove(String fileName) {
222: return remove(new File(fileName));
223: }
224:
225: public static boolean remove(File file) {
226: boolean success = true;
227:
228: if (file.isDirectory()) {
229: File[] content = file.listFiles();
230: for (int i = 0; i < content.length; i++) {
231: success = remove(content[i]);
232: }
233:
234: }
235:
236: //System.out.println("[delete] " + file);
237: success = file.delete();
238:
239: return success;
240: }
241:
242: public static void copy(String from, String to) throws IOException {
243: copy(new File(from), new File(to));
244: }
245:
246: public static void copy(File from, File to) throws IOException {
247:
248: //System.out.println("[copy] " + from + " -> " + to);
249:
250: if (!from.exists()) {
251: throw new IOException("Cannot find source file/folder");
252: }
253:
254: if (from.isDirectory()) {
255: to.mkdirs();
256: File[] content = from.listFiles();
257: for (int i = 0; i < content.length; i++) {
258: File src = content[i];
259: copy(src, new File(to, src.getName()));
260: }
261: } else {
262: to.createNewFile();
263: FileInputStream in = null;
264: FileOutputStream out = null;
265: try {
266: in = new FileInputStream(from);
267: out = new FileOutputStream(to);
268: copy(in, out);
269: } finally {
270: if (out != null)
271: out.close();
272: if (in != null)
273: in.close();
274: }
275: }
276: }
277:
278: public static void copy(InputStream from, OutputStream to)
279: throws IOException {
280: byte[] buffer = new byte[64 * 1024];
281: int count = 0;
282: do {
283: to.write(buffer, 0, count);
284: count = from.read(buffer, 0, buffer.length);
285: } while (count != -1);
286: }
287: }
|