/* * Copyright 2010 Google Inc. * * Licensed under the Apache License, Version 2.0 (the "License"); you may not * use this file except in compliance with the License. You may obtain a copy of * the License at * * http://www.apache.org/licenses/LICENSE-2.0 * * Unless required by applicable law or agreed to in writing, software * distributed under the License is distributed on an "AS IS" BASIS, WITHOUT * WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the * License for the specific language governing permissions and limitations under * the License. */ package java.io; import java.util.ArrayList; import com.google.gwt.core.client.JavaScriptObject; import com.google.gwt.corp.localstorage.LocalStorage; /** * LocalStorage based File implementation for GWT. Should probably have used Harmony as a * starting point instead of writing this from scratch. * * @author Stefan Haustein */ public class File { public static final File ROOT = new File(""); public static final char separatorChar = '/'; public static final String separator = "" + separatorChar; public static final char pathSeparatorChar = ':'; public static final String pathSeparator = "" + pathSeparatorChar; File parent; String name; boolean absolute; public File(String pathname) { while (pathname.endsWith(separator) && pathname.length() > 0) { pathname = pathname.substring(0, pathname.length() - 1); } int cut = pathname.lastIndexOf(separatorChar); if (cut == -1) { name = pathname; } else if (cut == 0) { name = pathname.substring(cut); parent = name.equals("") ? null : ROOT; } else { name = pathname.substring(cut + 1); parent = new File(pathname.substring(0, cut)); } // Compatibility.println("new File ('"+pathname+ "'); canonical name: '" + getCanonicalPath() + "'"); } public File(String parent, String child) { this(new File(parent), child); } public File(File parent, String child) { this.parent = parent; this.name = child; } /* public File(URI uri) { } */ public String getName() { return name; } public String getParent() { return parent == null ? "" : parent.getPath(); } public File getParentFile() { return parent; } public String getPath() { return parent == null ? name : (parent.getPath() + separatorChar + name); } private boolean isRoot() { return name.equals("") && parent == null; } public boolean isAbsolute() { if (isRoot()) { return true; } if(parent == null) { return false; } return parent.isAbsolute(); } public String getAbsolutePath() { String path = getAbsoluteFile().getPath(); return path.length() == 0 ? "/" : path; } public File getAbsoluteFile() { if (isAbsolute()) { return this; } if (parent == null) { return new File(ROOT, name); } return new File(parent.getAbsoluteFile(), name); } public String getCanonicalPath() { return getCanonicalFile().getAbsolutePath(); } public File getCanonicalFile() { File cParent = parent == null ? null : parent.getCanonicalFile(); if (name.equals (".")) { return cParent == null ? ROOT : cParent; } if (cParent != null && cParent.name.equals("")) { cParent = null; } if (name.equals("..")) { if (cParent == null) { return ROOT; } if (cParent.parent == null) { return ROOT; } return cParent.parent; } if (cParent == null && !name.equals("")) { return new File(ROOT, name); } return new File(cParent, name); } /* public URL toURL() throws MalformedURLException { } public URI toURI() { } */ public boolean canRead() { return true; } public boolean canWrite() { return true; } public boolean exists() { try { return LocalStorage.getItem(getCanonicalPath()) != null; } catch (IOException e) { return false; } } public boolean isDirectory() { try { String s = LocalStorage.getItem(getCanonicalPath()); return s != null && s.startsWith("{"); } catch (IOException e) { return false; } } public boolean isFile() { try { String s = LocalStorage.getItem(getCanonicalPath()); return s != null && !s.startsWith("{"); } catch (IOException e) { return false; } } public boolean isHidden() { return false; } public long lastModified() { return 0; } public long length() { try { if (!exists()) { return 0; } RandomAccessFile raf = new RandomAccessFile(this, "r"); long len = raf.length(); raf.close(); return len; } catch (IOException e) { return 0; } } public boolean createNewFile() throws IOException { if (exists()) return false; if (!parent.exists()) return false; LocalStorage.setItem(getCanonicalPath(), RandomAccessFile.btoa("")); return true; } public boolean delete() { try { if (!exists()) { return false; } LocalStorage.removeItem(getCanonicalPath()); return true; } catch (IOException e) { return false; } } public void deleteOnExit() { throw new RuntimeException("NYI: File.deleteOnExit()"); } public String[] list() { throw new RuntimeException("NYI: File.list()"); } /* public String[] list(FilenameFilter filter) { return null; } */ public File[] listFiles() { return listFiles(null); } public File[] listFiles(FilenameFilter filter) { ArrayList<File> files = new ArrayList<File>(); try { String prefix = getCanonicalPath(); if (!prefix.endsWith(separator)) { prefix += separatorChar; } int cut = prefix.length(); int cnt = LocalStorage.length(); for (int i = 0; i < cnt; i++) { String key = LocalStorage.key(i); if (key.startsWith(prefix) && key.indexOf(separatorChar, cut) == -1) { String name = key.substring(cut); if (filter == null || filter.accept(this, name)) { files.add(new File(this, name)); } } } } catch (IOException e) { System.err.println("lisFiles() exception: " + e); } return files.toArray(new File[files.size()]); } /* public File[] listFiles(FileFilter filter) { return null; } */ public boolean mkdir() { try { if (parent != null && !parent.exists()) { return false; } if (exists()) { return false; } // We may want to make this a JS map LocalStorage.setItem(getCanonicalPath(), "{}"); return true; } catch (IOException e) { return false; } } public boolean mkdirs() { if (parent != null) { parent.mkdirs(); } return mkdir(); } public boolean renameTo(File dest) { throw new RuntimeException("renameTo()"); } public boolean setLastModified(long time) { return false; } public boolean setReadOnly() { return false; } public static File[] listRoots() { return new File[]{ROOT}; } public static File createTempFile(String prefix, String suffix, File directory) throws IOException { throw new RuntimeException("NYI: createTempFile"); } public static File createTempFile(String prefix, String suffix) throws IOException { throw new RuntimeException("NYI: createTempFile"); } public int compareTo(File pathname) { throw new RuntimeException("NYI: File.compareTo()"); } public boolean equals(Object obj) { if (!(obj instanceof File)) { return false; } return getPath().equals(((File) obj).getPath()); } public int hashCode() { return parent != null ? parent.hashCode() + name.hashCode() : name.hashCode(); } public String toString() { return name; } }