The following may help. It compares the canonical and absolute paths, and if they differ, then it'll fail. Only tested on a mac/linux system (ie no windows).
This is for the case where you want to allow the user to supply a relative path, not an absolute path, and you don't allow any parent directory references.
public void failIfDirectoryTraversal(String relativePath)
{
File file = new File(relativePath);
if (file.isAbsolute())
{
throw new RuntimeException("Directory traversal attempt - absolute path not allowed");
}
String pathUsingCanonical;
String pathUsingAbsolute;
try
{
pathUsingCanonical = file.getCanonicalPath();
pathUsingAbsolute = file.getAbsolutePath();
}
catch (IOException e)
{
throw new RuntimeException("Directory traversal attempt?", e);
}
// Require the absolute path and canonicalized path match.
// This is done to avoid directory traversal
// attacks, e.g. "1/../2/"
if (! pathUsingCanonical.equals(pathUsingAbsolute))
{
throw new RuntimeException("Directory traversal attempt?");
}
}
与恶龙缠斗过久,自身亦成为恶龙;凝视深渊过久,深渊将回以凝视…