package net.sourceforge.javautil.common.io;
import java.io.ByteArrayInputStream;
import java.io.ByteArrayOutputStream;
import java.io.IOException;
import java.io.InputStream;
import java.io.InputStreamReader;
import java.io.OutputStream;
import java.io.OutputStreamWriter;
import java.net.URL;
import java.util.ArrayList;
import java.util.Arrays;
import java.util.Collections;
import java.util.List;
import net.sourceforge.javautil.common.IOUtil;
import net.sourceforge.javautil.common.diff.IComparison;
import net.sourceforge.javautil.common.diff.ComparisonReport;
import net.sourceforge.javautil.common.diff.IComparison.Result;
import net.sourceforge.javautil.common.exception.ThrowableManagerRegistry;
import net.sourceforge.javautil.common.io.VirtualArtifactWatcher.VirtualArtifactChange;
import net.sourceforge.javautil.common.io.VirtualArtifactWatcher.VirtualArtifactWatchable;
import net.sourceforge.javautil.common.io.IVirtualArtifactWatcherListener.VirtualArtifactWatcherEvent.Type;
/**
* The base for most {@link IVirtualFile} implementations.
*
* @author elponderador
* @author $Author: ponderator $
* @version $Id: VirtualFileAbstract.java 2355 2010-07-27 20:25:32Z ponderator $
*/
public abstract class VirtualFileAbstract extends VirtualArtifactAbstract<IVirtualFile> implements IVirtualFile, IVirtualArtifactIOHandler {
protected String name;
protected IVirtualDirectory owner;
protected IVirtualArtifactIOHandler ioHandler = this;
public VirtualFileAbstract(String name, IVirtualDirectory owner) {
this.name = name;
this.owner = owner;
}
public InputStreamReader getReader() throws IOException {
return new InputStreamReader(getInputStream());
}
public OutputStreamWriter getWriter() throws IOException {
return new OutputStreamWriter(getOutputStream());
}
public ComparisonReport<IVirtualFile> compare(IVirtualFile artifact, boolean complete) {
if (artifact.getName().equals(getName())) {
return new ComparisonReport<IVirtualFile>(complete, new IComparison(this, artifact,
getSize() == artifact.getSize() ? Result.EQUAL : Result.DIFFERENT
));
}
return new ComparisonReport<IVirtualFile>(complete, new IComparison(this, artifact, Result.DIFFERENT));
}
public boolean create() {
if (!this.isExists()) this.write(new byte[0]);
return true;
}
public IVirtualFile getArtifact() { return this; }
public List<VirtualArtifactChange> getArtifactChangeList(long since) {
if (!this.isExists()) return null;
return this.getLastModified() > since ? Arrays.asList(new VirtualArtifactChange(this, this.getPath(), Type.MODIFIED, this.getLastModified())) : null;
}
public IVirtualFile move(IVirtualDirectory moveTarget) {
IVirtualFile moved = this.copy(moveTarget);
this.remove();
return moved;
}
public String getName() { return name; }
public String getExtension() {
return name.contains(".") && !name.startsWith(".") && !name.endsWith(".") ? name.substring(name.lastIndexOf('.')+1, name.length()) : null;
}
public IVirtualDirectory getOwner() { return owner; }
public IVirtualFile copy(IVirtualDirectory directory) { return this.copy( directory.getFile(getName(), true) ); }
public IVirtualFile copy(IVirtualFile file) { file.writeAll(this.readAll()); return file; }
public byte[] readAll() {
try {
return IOUtil.transfer(this.getInputStream(), new ByteArrayOutputStream()).toByteArray();
} catch (IOException e) {
throw ThrowableManagerRegistry.caught(e);
}
}
public String readAsText() { return new String(this.readAll()); }
public void writeAll(byte[] contents) {
try {
IOUtil.transfer(new ByteArrayInputStream(contents), this.getOutputStream()).close();
} catch (IOException e) {
throw ThrowableManagerRegistry.caught(e);
}
}
public void writeAsText(String textContents) { this.writeAll(textContents.getBytes()); }
public String toString () { return getPath().toString("/"); }
/**
* @param contents The string contents to write to this file
*
* @see #write(byte[])
*/
public void write (String contents) { this.write(contents.getBytes()); }
/**
* Write the contents to the {@link #getOutputStream()} of this artifact.
*
* @param content The contents to write to this file
*/
public void write (byte[] content) {
try {
IOUtil.transfer(new ByteArrayInputStream(content), this.getOutputStream());
} catch (IOException e) {
throw ThrowableManagerRegistry.caught(new VirtualArtifactException(this, "Could not write to artifact", e));
}
}
public IVirtualArtifactIOHandler getIOHandler() { return this.ioHandler; }
public void setIOHandler(IVirtualArtifactIOHandler handler) { this.ioHandler = handler == null ? this : handler; }
public InputStream getInputStream(IVirtualArtifactIO artifact, InputStream input) throws IOException { return input; }
public OutputStream getOutputStream(IVirtualArtifactIO artifact, OutputStream output) throws IOException { return output; }
public InputStream getInputStream() throws IOException {
return this.ioHandler.getInputStream(this, this.getRawInputStream());
}
public OutputStream getOutputStream() throws IOException {
return this.ioHandler.getOutputStream(this, this.getRawOutputStream());
}
protected abstract InputStream getRawInputStream () throws IOException;
protected abstract OutputStream getRawOutputStream () throws IOException;
}