Home » Java » How do I get the file extension of a file in Java?

How do I get the file extension of a file in Java?

Posted by: admin November 2, 2017 Leave a comment

Questions:

Just to be clear, I’m not looking for the MIME type.

Let’s say I have the following input: /path/to/file/foo.txt

I’d like a way to break this input up, specifically into .txt for the extension. Is there any built in way to do this in Java? I would like to avoid writing my own parser.

Answers:

In this case, use FilenameUtils.getExtension from Apache Commons IO

Here is an example of how to use it (you may specify either full path or just file name):

String ext1 = FilenameUtils.getExtension("/path/to/file/foo.txt"); // returns "txt"
String ext2 = FilenameUtils.getExtension("bar.exe"); // returns "exe"

Questions:
Answers:

Do you really need a “parser” for this?

String extension = "";

int i = fileName.lastIndexOf('.');
if (i > 0) {
    extension = fileName.substring(i+1);
}

Assuming that you’re dealing with simple Windows-like file names, not something like archive.tar.gz.

Btw, for the case that a directory may have a ‘.’, but the filename itself doesn’t (like /path/to.a/file), you can do

String extension = "";

int i = fileName.lastIndexOf('.');
int p = Math.max(fileName.lastIndexOf('/'), fileName.lastIndexOf('\'));

if (i > p) {
    extension = fileName.substring(i+1);
}

Questions:
Answers:
private String getFileExtension(File file) {
    String name = file.getName();
    try {
        return name.substring(name.lastIndexOf(".") + 1);
    } catch (Exception e) {
        return "";
    }
}

Questions:
Answers:

If you use Guava library, you can resort to Files utility class. It has a specific method, getFileExtension(). For instance:

String path = "c:/path/to/file/foo.txt";
String ext = Files.getFileExtension(path);
System.out.println(ext); //prints txt

In addition you may also obtain the filename with a similar function, getNameWithoutExtension():

String filename = Files.getNameWithoutExtension(path);
System.out.println(filename); //prints foo

Questions:
Answers:

If on Android, you can use this:

String ext = android.webkit.MimeTypeMap.getFileExtensionFromUrl(file.getName());

Questions:
Answers:

In order to take into account file names without characters before the dot, you have to use that slight variation of the accepted answer:

String extension = "";

int i = fileName.lastIndexOf('.');
if (i >= 0) {
    extension = fileName.substring(i+1);
}

"file.doc" => "doc"
"file.doc.gz" => "gz"
".doc" => "doc"

Questions:
Answers:

My dirty and may tiniest using String.replaceAll:

.replaceAll("^.*\.(.*)$", "$1")

Note that first * is greedy so it will grab most possible characters as far as it can and then just last dot and file extension will be left.

Questions:
Answers:

If you plan to use Apache commons-io,and just want to check the file’s extension and then do some operation,you can use this,here is a snippet:

if(FilenameUtils.isExtension(file.getName(),"java")) {
    someoperation();
}

Questions:
Answers:

How about (using Java 1.5 RegEx):

    String[] split = fullFileName.split("\.");
    String ext = split[split.length - 1];

Questions:
Answers:

How about JFileChooser? It is not straightforward as you will need to parse its final output…

JFileChooser filechooser = new JFileChooser();
File file = new File("your.txt");
System.out.println("the extension type:"+filechooser.getTypeDescription(file));

which is a MIME type…

OK…I forget that you don’t want to know its MIME type.

Interesting code in the following link:
http://download.oracle.com/javase/tutorial/uiswing/components/filechooser.html

/*
 * Get the extension of a file.
 */  
public static String getExtension(File f) {
    String ext = null;
    String s = f.getName();
    int i = s.lastIndexOf('.');

    if (i > 0 &&  i < s.length() - 1) {
        ext = s.substring(i+1).toLowerCase();
    }
    return ext;
}

Related question:
How do I trim a file extension from a String in Java?

Questions:
Answers:

Here’s a method that handles .tar.gz properly, even in a path with dots in directory names:

private static final String getExtension(final String filename) {
  if (filename == null) return null;
  final String afterLastSlash = filename.substring(filename.lastIndexOf('/') + 1);
  final int afterLastBackslash = afterLastSlash.lastIndexOf('\') + 1;
  final int dotIndex = afterLastSlash.indexOf('.', afterLastBackslash);
  return (dotIndex == -1) ? "" : afterLastSlash.substring(dotIndex + 1);
}

afterLastSlash is created to make finding afterLastBackslash quicker since it won’t have to search the whole string if there are some slashes in it.

The char[] inside the original String is reused, adding no garbage there, and the JVM will probably notice that afterLastSlash is immediately garbage in order to put it on the stack instead of the heap.

Questions:
Answers:

This is a tested method

public static String getExtension(String fileName) {
    char ch;
    int len;
    if(fileName==null || 
            (len = fileName.length())==0 || 
            (ch = fileName.charAt(len-1))=='/' || ch=='\' || //in the case of a directory
             ch=='.' ) //in the case of . or ..
        return "";
    int dotInd = fileName.lastIndexOf('.'),
        sepInd = Math.max(fileName.lastIndexOf('/'), fileName.lastIndexOf('\'));
    if( dotInd<=sepInd )
        return "";
    else
        return fileName.substring(dotInd+1).toLowerCase();
}

And test case:

@Test
public void testGetExtension() {
    assertEquals("", getExtension("C"));
    assertEquals("ext", getExtension("C.ext"));
    assertEquals("ext", getExtension("A/B/C.ext"));
    assertEquals("", getExtension("A/B/C.ext/"));
    assertEquals("", getExtension("A/B/C.ext/.."));
    assertEquals("bin", getExtension("A/B/C.bin"));
    assertEquals("hidden", getExtension(".hidden"));
    assertEquals("dsstore", getExtension("/user/home/.dsstore"));
    assertEquals("", getExtension(".strange."));
    assertEquals("3", getExtension("1.2.3"));
    assertEquals("exe", getExtension("C:\Program Files (x86)\java\bin\javaw.exe"));
}

Questions:
Answers:
// Modified from EboMike's answer

String extension = "/path/to/file/foo.txt".substring("/path/to/file/foo.txt".lastIndexOf('.'));

extension should have “.txt” in it when run.

Questions:
Answers:

Here I made a small method (however not that secure and doesnt check for many errors), but if it is only you that is programming a general java-program, this is more than enough to find the filetype. This is not working for complex filetypes, but those are normally not used as much.

    public static String getFileType(String path){
       String fileType = null;
       fileType = path.substring(path.indexOf('.',path.lastIndexOf('/'))+1).toUpperCase();
       return fileType;
}

Questions:
Answers:

Without use of any library, you can use the String method split as follows :

        String[] splits = fileNames.get(i).split("\.");

        String extension = "";

        if(splits.length >= 2)
        {
            extension = splits[splits.length-1];
        }

Questions:
Answers:
String extension = com.google.common.io.Files.getFileExtension("fileName.jpg");

Questions:
Answers:

Getting File Extension from File Name

/**
 * The extension separator character.
 */
private static final char EXTENSION_SEPARATOR = '.';

/**
 * The Unix separator character.
 */
private static final char UNIX_SEPARATOR = '/';

/**
 * The Windows separator character.
 */
private static final char WINDOWS_SEPARATOR = '\';

/**
 * The system separator character.
 */
private static final char SYSTEM_SEPARATOR = File.separatorChar;

/**
 * Gets the extension of a filename.
 * <p>
 * This method returns the textual part of the filename after the last dot.
 * There must be no directory separator after the dot.
 * <pre>
 * foo.txt      --> "txt"
 * a/b/c.jpg    --> "jpg"
 * a/b.txt/c    --> ""
 * a/b/c        --> ""
 * </pre>
 * <p>
 * The output will be the same irrespective of the machine that the code is running on.
 *
 * @param filename the filename to retrieve the extension of.
 * @return the extension of the file or an empty string if none exists.
 */
public static String getExtension(String filename) {
    if (filename == null) {
        return null;
    }
    int index = indexOfExtension(filename);
    if (index == -1) {
        return "";
    } else {
        return filename.substring(index + 1);
    }
}

/**
 * Returns the index of the last extension separator character, which is a dot.
 * <p>
 * This method also checks that there is no directory separator after the last dot.
 * To do this it uses {@link #indexOfLastSeparator(String)} which will
 * handle a file in either Unix or Windows format.
 * <p>
 * The output will be the same irrespective of the machine that the code is running on.
 *
 * @param filename  the filename to find the last path separator in, null returns -1
 * @return the index of the last separator character, or -1 if there
 * is no such character
 */
public static int indexOfExtension(String filename) {
    if (filename == null) {
        return -1;
    }
    int extensionPos = filename.lastIndexOf(EXTENSION_SEPARATOR);
    int lastSeparator = indexOfLastSeparator(filename);
    return (lastSeparator > extensionPos ? -1 : extensionPos);
}

/**
 * Returns the index of the last directory separator character.
 * <p>
 * This method will handle a file in either Unix or Windows format.
 * The position of the last forward or backslash is returned.
 * <p>
 * The output will be the same irrespective of the machine that the code is running on.
 *
 * @param filename  the filename to find the last path separator in, null returns -1
 * @return the index of the last separator character, or -1 if there
 * is no such character
 */
public static int indexOfLastSeparator(String filename) {
    if (filename == null) {
        return -1;
    }
    int lastUnixPos = filename.lastIndexOf(UNIX_SEPARATOR);
    int lastWindowsPos = filename.lastIndexOf(WINDOWS_SEPARATOR);
    return Math.max(lastUnixPos, lastWindowsPos);
}

Credits

  1. Copied from Apache FileNameUtils Class – http://grepcode.com/file/repo1.maven.org/maven2/commons-io/commons-io/1.3.2/org/apache/commons/io/FilenameUtils.java#FilenameUtils.getExtension%28java.lang.String%29
Questions:
Answers:

Here’s the version with Optional as a return value (cause you can’t be sure the file has an extension)… also sanity checks…

import java.io.File;
import java.util.Optional;

public class GetFileExtensionTool {

    public static Optional<String> getFileExtension(File file) {
        if (file == null) {
            throw new NullPointerException("file argument was null");
        }
        if (!file.isFile()) {
            throw new IllegalArgumentException("getFileExtension(File file)"
                    + " called on File object that wasn't an actual file"
                    + " (perhaps a directory or device?). file had path: "
                    + file.getAbsolutePath());
        }
        String fileName = file.getName();
        int i = fileName.lastIndexOf('.');
        if (i > 0) {
            return Optional.of(fileName.substring(i + 1));
        } else {
            return Optional.empty();
        }
    }
}

Questions:
Answers:

How about REGEX version:

static final Pattern PATTERN = Pattern.compile("(.*)\.(.*)");

Matcher m = PATTERN.matcher(path);
if (m.find()) {
    System.out.println("File path/name: " + m.group(1));
    System.out.println("Extention: " + m.group(2));
}

or with null extension supported:

static final Pattern PATTERN =
    Pattern.compile("((.*\" + File.separator + ")?(.*)(\.(.*)))|(.*\" + File.separator + ")?(.*)");

class Separated {
    String path, name, ext;
}

Separated parsePath(String path) {
    Separated res = new Separated();
    Matcher m = PATTERN.matcher(path);
    if (m.find()) {
        if (m.group(1) != null) {
            res.path = m.group(2);
            res.name = m.group(3);
            res.ext = m.group(5);
        } else {
            res.path = m.group(6);
            res.name = m.group(7);
        }
    }
    return res;
}


Separated sp = parsePath("/root/docs/readme.txt");
System.out.println("path: " + sp.path);
System.out.println("name: " + sp.name);
System.out.println("Extention: " + sp.ext);

result for *nix:
path: /root/docs/
name: readme
Extention: txt

for windows, parsePath(“c:\windows\readme.txt”):
path: c:\windows\
name: readme
Extention: txt

Questions:
Answers:

Just a regular-expression based alternative. Not that fast, not that good.

Pattern pattern = Pattern.compile("\.([^.]*)$");
Matcher matcher = pattern.matcher(fileName);

if (matcher.find()) {
    String ext = matcher.group(1);
}

Questions:
Answers:

This particular question gives me a lot trouble then i found a very simple solution for this problem which i’m posting here.

file.getName().toLowerCase().endsWith(".txt");

That’s it.

Questions:
Answers:
path = "/Users/test/test.txt"

extension = path.substring(path.lastIndexOf("."), path.length());

return “.txt”

if you want only “txt”, make path.lastIndexOf(".") + 1

Questions:
Answers:

You can use the Java7 feature from java.io package

Files.probeContentType(path);

Refer the below code snippet

public static String returnContentType(String pathText) throws Exception {

    // obtain Path object that represents the file
    Path path = Paths.get(pathText);

    // probe the content
    String contentType = Files.probeContentType(path);

    // return content type
    return contentType;

}

Questions:
Answers:

Java has a built-in way of dealing with this, in the java.nio.file.Files class, that may work for your needs:

File f = new File("/path/to/file/foo.txt");
String ext = Files.probeContentType(f.toPath());
if(ext.equalsIgnoreCase("txt")) do whatever;

Note that this static method uses the specifications found here to retrieve “content type,” which can vary.

Questions:
Answers:

let ‘name’ be the name of the file with extension file.

   int len=name.length();
   int i=0;
   String eXt;
   while(i<len){
       if(name.charAt(i)=='.'){               
           eXt=(String) name.subSequence(i, len);
           break;
       }
       i++;
   }