/* * Copyright (c) 2012 Eike Stepper (Berlin, Germany) and others. * All rights reserved. This program and the accompanying materials * are made available under the terms of the Eclipse Public License v1.0 * which accompanies this distribution, and is available at * http://www.eclipse.org/legal/epl-v10.html * * Contributors: * Eike Stepper - initial API and implementation */ package org.eclipse.emf.cdo.spi.transfer; import org.eclipse.emf.cdo.transfer.CDOTransferElement; import org.eclipse.emf.cdo.transfer.CDOTransferSystem; import org.eclipse.net4j.util.io.IORuntimeException; import org.eclipse.net4j.util.io.IOUtil; import org.eclipse.emf.common.util.URI; import org.eclipse.core.runtime.IPath; import org.eclipse.core.runtime.IProgressMonitor; import org.eclipse.core.runtime.Path; import java.io.File; import java.io.FileInputStream; import java.io.FileOutputStream; import java.io.FileWriter; import java.io.IOException; import java.io.InputStream; import java.io.InputStreamReader; import java.io.OutputStream; import java.io.Writer; /** * A {@link CDOTransferSystem transfer system} that abstracts the external file system. * * @author Eike Stepper * @since 4.2 */ public class FileSystemTransferSystem extends CDOTransferSystem { public static final FileSystemTransferSystem INSTANCE = new FileSystemTransferSystem(); public static final String TYPE = "fs"; public FileSystemTransferSystem() { super(false); } @Override public String getType() { return TYPE; } @Override public URI getURI(IPath path) { return URI.createFileURI(path.toOSString()); } @Override public CDOTransferElement getElement(IPath path) { File file = getFile(path); if (file.exists()) { return new Element(this, file); } return null; } @Override public CDOTransferElement getElement(URI uri) { if (uri.isFile()) { return getElement(uri.path()); } return null; } @Override public void createFolder(IPath path) { File file = getFile(path); mkDir(file); } @Override public void createBinary(IPath path, InputStream source, IProgressMonitor monitor) { OutputStream target = null; try { File file = getFile(path); long length = file.length(); int totalWork = length > Integer.MAX_VALUE ? Integer.MAX_VALUE : (int)length; monitor.beginTask("", totalWork); mkParent(file); target = new FileOutputStream(file); IOUtil.copy(source, target); monitor.worked(totalWork); // TODO Progress more smoothly } catch (IOException ex) { throw new IORuntimeException(); } finally { IOUtil.close(target); monitor.done(); } } @Override public void createText(IPath path, InputStream source, String encoding, IProgressMonitor monitor) { Writer target = null; try { File file = getFile(path); long length = file.length(); int totalWork = length > Integer.MAX_VALUE ? Integer.MAX_VALUE : (int)length; monitor.beginTask("", totalWork); mkParent(file); target = new FileWriter(file); IOUtil.copyCharacter(new InputStreamReader(source, encoding), target); monitor.worked(totalWork); // TODO Progress more smoothly } catch (IOException ex) { throw new IORuntimeException(); } finally { IOUtil.close(target); monitor.done(); } } @Override public String toString() { return "File System"; } protected File getFile(IPath path) { return new File(path.toOSString()); } protected void mkParent(File file) { File parent = file.getParentFile(); if (parent != null) { mkDir(parent); } } protected void mkDir(File file) { if (file.exists()) { if (!file.isDirectory()) { throw new IORuntimeException("Not a folder " + file); } } else { if (!file.mkdirs()) { throw new IORuntimeException("Could not create folder " + file); } } } /** * @author Eike Stepper */ private static class Element extends CDOTransferElement { private File file; public Element(CDOTransferSystem system, File file) { super(system); this.file = file.getAbsoluteFile(); } @Override public Object getNativeObject() { return file; } @Override public IPath getPath() { return new Path(file.getPath()); } @Override public boolean isDirectory() { return file.isDirectory(); } @Override protected CDOTransferElement[] doGetChildren() { File[] children = file.listFiles(); CDOTransferElement[] result = new Element[children.length]; for (int i = 0; i < children.length; i++) { File child = children[i]; result[i] = new Element(getSystem(), child); } return result; } @Override protected InputStream doOpenInputStream() { try { return new FileInputStream(file); } catch (IOException ex) { throw new IORuntimeException(ex); } } } }