org.eclipse.jetty.util.resource.FileResource Maven / Gradle / Ivy
Go to download
Show more of this group Show more artifacts with this name
Show all versions of ehcache Show documentation
Show all versions of ehcache Show documentation
Ehcache is an open source, standards-based cache used to boost performance,
offload the database and simplify scalability. Ehcache is robust, proven and full-featured and
this has made it the most widely-used Java-based cache.
//
// ========================================================================
// Copyright (c) 1995-2014 Mort Bay Consulting Pty. Ltd.
// ------------------------------------------------------------------------
// All rights reserved. This program and the accompanying materials
// are made available under the terms of the Eclipse Public License v1.0
// and Apache License v2.0 which accompanies this distribution.
//
// The Eclipse Public License is available at
// http://www.eclipse.org/legal/epl-v10.html
//
// The Apache License v2.0 is available at
// http://www.opensource.org/licenses/apache2.0.php
//
// You may elect to redistribute this code under either of these licenses.
// ========================================================================
//
package org.eclipse.jetty.util.resource;
import java.io.File;
import java.io.FileInputStream;
import java.io.FileOutputStream;
import java.io.IOException;
import java.io.InputStream;
import java.io.OutputStream;
import java.net.MalformedURLException;
import java.net.URI;
import java.net.URISyntaxException;
import java.net.URL;
import java.net.URLConnection;
import java.security.Permission;
import org.eclipse.jetty.util.IO;
import org.eclipse.jetty.util.URIUtil;
import org.eclipse.jetty.util.log.Log;
import org.eclipse.jetty.util.log.Logger;
/* ------------------------------------------------------------ */
/** File Resource.
*
* Handle resources of implied or explicit file type.
* This class can check for aliasing in the filesystem (eg case
* insensitivity). By default this is turned on, or it can be controlled
* by calling the static method @see FileResource#setCheckAliases(boolean)
*
*/
public class FileResource extends URLResource
{
private static final Logger LOG = Log.getLogger(FileResource.class);
private static boolean __checkAliases = true;
/* ------------------------------------------------------------ */
private File _file;
private transient URL _alias=null;
private transient boolean _aliasChecked=false;
/* ------------------------------------------------------------------------------- */
/** setCheckAliases.
* @param checkAliases True of resource aliases are to be checked for (eg case insensitivity or 8.3 short names) and treated as not found.
*/
public static void setCheckAliases(boolean checkAliases)
{
__checkAliases=checkAliases;
}
/* ------------------------------------------------------------------------------- */
/** getCheckAliases.
* @return True of resource aliases are to be checked for (eg case insensitivity or 8.3 short names) and treated as not found.
*/
public static boolean getCheckAliases()
{
return __checkAliases;
}
/* -------------------------------------------------------- */
public FileResource(URL url)
throws IOException, URISyntaxException
{
super(url,null);
try
{
// Try standard API to convert URL to file.
_file =new File(new URI(url.toString()));
}
catch (URISyntaxException e)
{
throw e;
}
catch (Exception e)
{
LOG.ignore(e);
try
{
// Assume that File.toURL produced unencoded chars. So try
// encoding them.
String file_url="file:"+URIUtil.encodePath(url.toString().substring(5));
URI uri = new URI(file_url);
if (uri.getAuthority()==null)
_file = new File(uri);
else
_file = new File("//"+uri.getAuthority()+URIUtil.decodePath(url.getFile()));
}
catch (Exception e2)
{
LOG.ignore(e2);
// Still can't get the file. Doh! try good old hack!
checkConnection();
Permission perm = _connection.getPermission();
_file = new File(perm==null?url.getFile():perm.getName());
}
}
if (_file.isDirectory())
{
if (!_urlString.endsWith("/"))
_urlString=_urlString+"/";
}
else
{
if (_urlString.endsWith("/"))
_urlString=_urlString.substring(0,_urlString.length()-1);
}
}
/* -------------------------------------------------------- */
FileResource(URL url, URLConnection connection, File file)
{
super(url,connection);
_file=file;
if (_file.isDirectory() && !_urlString.endsWith("/"))
_urlString=_urlString+"/";
}
/* -------------------------------------------------------- */
@Override
public Resource addPath(String path)
throws IOException,MalformedURLException
{
URLResource r=null;
String url=null;
path = org.eclipse.jetty.util.URIUtil.canonicalPath(path);
if ("/".equals(path))
return this;
else if (!isDirectory())
{
r=(FileResource)super.addPath(path);
url=r._urlString;
}
else
{
if (path==null)
throw new MalformedURLException();
// treat all paths being added as relative
String rel=path;
if (path.startsWith("/"))
rel = path.substring(1);
url=URIUtil.addPaths(_urlString,URIUtil.encodePath(rel));
r=(URLResource)Resource.newResource(url);
}
// Check for encoding aliases
// The encoded path should be a suffix of the resource (give or take a directory / )
String encoded=URIUtil.encodePath(path);
int expected=r.toString().length()-encoded.length();
int index = r._urlString.lastIndexOf(encoded, expected);
if (expected!=index && ((expected-1)!=index || path.endsWith("/") || !r.isDirectory()))
{
if (r instanceof FileResource)
{
((FileResource)r)._alias=((FileResource)r)._file.getCanonicalFile().toURI().toURL();
((FileResource)r)._aliasChecked=true;
}
}
return r;
}
/* ------------------------------------------------------------ */
@Override
public URL getAlias()
{
if (__checkAliases && !_aliasChecked)
{
try
{
String abs=_file.getAbsolutePath();
String can=_file.getCanonicalPath();
if (abs.length()!=can.length() || !abs.equals(can))
_alias=Resource.toURL(new File(can));
_aliasChecked=true;
if (_alias!=null && LOG.isDebugEnabled())
{
LOG.debug("ALIAS abs="+abs);
LOG.debug("ALIAS can="+can);
}
}
catch(Exception e)
{
LOG.warn(Log.EXCEPTION,e);
return getURL();
}
}
return _alias;
}
/* -------------------------------------------------------- */
/**
* Returns true if the resource exists.
*/
@Override
public boolean exists()
{
return _file.exists();
}
/* -------------------------------------------------------- */
/**
* Returns the last modified time
*/
@Override
public long lastModified()
{
return _file.lastModified();
}
/* -------------------------------------------------------- */
/**
* Returns true if the respresenetd resource is a container/directory.
*/
@Override
public boolean isDirectory()
{
return _file.isDirectory();
}
/* --------------------------------------------------------- */
/**
* Return the length of the resource
*/
@Override
public long length()
{
return _file.length();
}
/* --------------------------------------------------------- */
/**
* Returns the name of the resource
*/
@Override
public String getName()
{
return _file.getAbsolutePath();
}
/* ------------------------------------------------------------ */
/**
* Returns an File representing the given resource or NULL if this
* is not possible.
*/
@Override
public File getFile()
{
return _file;
}
/* --------------------------------------------------------- */
/**
* Returns an input stream to the resource
*/
@Override
public InputStream getInputStream() throws IOException
{
return new FileInputStream(_file);
}
/* --------------------------------------------------------- */
/**
* Returns an output stream to the resource
*/
@Override
public OutputStream getOutputStream()
throws java.io.IOException, SecurityException
{
return new FileOutputStream(_file);
}
/* --------------------------------------------------------- */
/**
* Deletes the given resource
*/
@Override
public boolean delete()
throws SecurityException
{
return _file.delete();
}
/* --------------------------------------------------------- */
/**
* Rename the given resource
*/
@Override
public boolean renameTo( Resource dest)
throws SecurityException
{
if( dest instanceof FileResource)
return _file.renameTo( ((FileResource)dest)._file);
else
return false;
}
/* --------------------------------------------------------- */
/**
* Returns a list of resources contained in the given resource
*/
@Override
public String[] list()
{
String[] list =_file.list();
if (list==null)
return null;
for (int i=list.length;i-->0;)
{
if (new File(_file,list[i]).isDirectory() &&
!list[i].endsWith("/"))
list[i]+="/";
}
return list;
}
/* ------------------------------------------------------------ */
/** Encode according to this resource type.
* File URIs are encoded.
* @param uri URI to encode.
* @return The uri unchanged.
*/
@Override
public String encode(String uri)
{
return uri;
}
/* ------------------------------------------------------------ */
/**
* @param o
* @return true
of the object o
is a {@link FileResource} pointing to the same file as this resource.
*/
@Override
public boolean equals( Object o)
{
if (this == o)
return true;
if (null == o || ! (o instanceof FileResource))
return false;
FileResource f=(FileResource)o;
return f._file == _file || (null != _file && _file.equals(f._file));
}
/* ------------------------------------------------------------ */
/**
* @return the hashcode.
*/
@Override
public int hashCode()
{
return null == _file ? super.hashCode() : _file.hashCode();
}
/* ------------------------------------------------------------ */
@Override
public void copyTo(File destination)
throws IOException
{
if (isDirectory())
{
IO.copyDir(getFile(),destination);
}
else
{
if (destination.exists())
throw new IllegalArgumentException(destination+" exists");
IO.copy(getFile(),destination);
}
}
}