I have the following Java code running in a media module:
File file = new File("/my/path/"+String.format("%02d", date)+"/"+streamAliasRef+".mp4");
// Destination directory
File dir = new File("/mnt/s3");
// Move file to new directory
boolean success = file.renameTo(new File(dir, file.getName()));
if (!success) {
getLogger().info("File failed to move to s3"+file.getName());
}
else {
getLogger().info("File moved to s3 successfully"+ file.getName());
}
For some reason I am consistently getting "File failed to move to s3"
I'm pretty new to Java, so forgive me if this is a simple problem. I know for a fact that both directories exist. One important note which may have something to do with it is I'm using Fuse to mount an S3 bucket to the filesystem.
In Java running on unix, renameTo only works if you are in the same file system. So if you are moving across filesystems, you will need to copy and delete the original. The unix mv command does this as well. This is why mv is instant on the same filesystem, but takes forever across filesystems. It detects the different filesystems and does a copy delete in that case.
I use this method from Guava to move files around on Unix to work around this issue:
public static void move(File from, File to) throws IOException {
Preconditions.checkNotNull(to);
Preconditions.checkArgument(!from.equals(to),
"Source %s and destination %s must be different", from, to);
if (!from.renameTo(to)) {
copy(from, to);
if (!from.delete()) {
if (!to.delete()) {
throw new IOException("Unable to delete " + to);
}
throw new IOException("Unable to delete " + from);
}
}
}
First of all, are you sure that
new File("/my/path/"+String.format("%02d", date)+"/"+streamAliasRef+".mp4")
really exists ? Could you check with file.exists() prior to trying to move it ?
Related
I am trying to create a folder call "YouDown" at the moment I don't care where the folder is located but at this time all I want to figure out is creating it. I found that my first issue was that mkdir() and mkdirs() were being ignored due to not knowing it was a Boolean value. I created the Boolean of success and now its not being ignored. Following this I created log.d of each step in detecting to creating to already existing. It registers that it "Doesn't exist" , "Being Created" then either "Created" or "Creation Failed". It jumps to the "Creation Failed". Everything I find now to help is just being repetitive to what I've been reading for the past few days. I am also looking into how I could apply this to a specific path way like the variable string I want it to be created inside the directories Music folder
// Lastest try
String Tag2 = "YouDown"
if (!dir.exists()) {
Log.d(Tag2,"Doesnt Exist");
boolean success = false;
try{
success = dir.mkdir();
Log.d(Tag2,"Being Created");
}
catch(SecurityException se){
//handle it
}
if(success) {
Log.d(Tag2, "Created");
} else{
Log.d(Tag2, "Creation Failed");
}
}
// Other Try
String path = "/sdcard/Music/Youdown"
if(new File(path).exists()){
Log.d(Tag2, "Exists");
} else {
Log.d(Tag2, "Being Created");
Boolean succes = new File(path).mkdir();
if(success){
Log.d(Tag2, "Created"
} else {
Log.d(Tag2, "Failed"
}
Newest attempt
File dir = new File(Environment.getExternalStorageDirectory(), path2);
Boolean A = dir.mkdirs();
if(A){
Log.d(Tag2,"Created");
}
if(!A){
Log.d(Tag2,"Failed");
}
Although Android has a hierarchical file system your app may read and write in certain places only. As a start I suggest using the method getDir() of android.content.Context. As the doc states:
Retrieve, creating if needed, a new directory in which the application can place its own custom data files. You can use the returned File object to create and access files in this directory. Note that files created through a File object will only be accessible by your own application; you can only set the mode of the entire directory, not of individual files.
If you want to access shared directories you need to call other methods, for example Context.getExternalFilesDir().
If you are creating the directory for your app only, such that if ever your app gets deleted the folder gets deleted too, you can use getFilesDir().
File internalDir = getContext().getFilesDir();
String path = "/Music/Youdown";
// to create it you can call, new File(internalDir, path).mkdir();
Or alternatively if you want the external storage you would use the Environment.getExternalStorage(); like below:
String path = "/Music/Youdown";
File f = new File(Environment.getExternalStorageDirectory(), path );
if (!f.exists()) {
f.mkdirs();
}
So I am trying to copy one file from one place to the other using the solution found here :
Copying files from one directory to another in Java
My code creates the new directory but cant seem to find the file ,even though the landedtitlesFile is pointing to the proper path and file. I always get my "blast" comment in case you were wondering if my program gets to the end of the method.
Thank you for your time and patience.
private File landedtitlesFile = new File("C:\\Program Files (x86)\\Steam\\SteamApps\\common\\Crusader Kings II\\common\\landed_titles\\landed_titles.txt");
private String modPath = "C:\\Users\\Bernard\\Documents\\Paradox Interactive\\Crusader Kings II\\mod\\viking";
public void createCopyLandedTitles(Boolean vanilla){
if (vanilla == true) {
File dir = new File(modPath + "\\common\\landed_titles");
dir.mkdir();
try{
FileUtils.copyFile(landedtitlesFile,dir);
}
catch (IOException e ){
System.out.println("blast");
}
}
copyFile expects the second parameter to be the destination file, not a destination directory. You need to give it the target name of the file within that directory:
FileUtils.copyFile(
landedtitlesFile,
new File(dir, landedtitlesFile.getName());
Exception objects generally contain some information on the cause. If you print out the exception with e.printStackTrace(); (or rethrow it up the stack with throw new RuntimeException(e);) then you will be able to see what it says.
I have the following function inside a Stateless EJB running in Glassfish. All it does is write some data to a file. The first part of the function just creates the path to where the file needs to go. The second part actually writes the file.
private boolean createFile(String companyName, String fileName, byte[] data)
{
logger.log(Level.FINEST, "Creating file: {0} for company {1}", new Object[]{fileName, companyName});
File companyFileDir = new File(LOCAL_FILE_DIR, companyName);
if(companyFileDir.exists() == false)
{
boolean createFileDir = companyFileDir.mkdirs();
if(createFileDir == false)
{
logger.log(Level.WARNING, "Could not create directory to place file in");
return false;
}
}
File newFile = new File(companyFileDir, fileName);
try
{
FileOutputStream fileWriter = new FileOutputStream(newFile);
fileWriter.write(data);
}
catch(IOException e)
{
logger.log(Level.SEVERE,"Could not write file to disk",e);
return false;
}
logger.log(Level.FINEST,"File successfully written to file");
return true;
}
The output I get after this code executes is:
WARNING: Could not create directory to place file in
So obviously Glassfish cant create this directory. I am am assuming this has something to do with permissions. Can anyone give me a direction to go as to what might be wrong here?
I am running this on Glassfish 3.12 on Ubuntu 12
different things:
1) Compare spec: (21.1.2 Programming Restrictions)
An enterprise bean must not use the java.io package to attempt to access files and directories in the file system.
I'm sure GF isn't enforcing this, but you should be aware of that.
2) The code itself is fine. Try chmod +777 on the LOCAL_FILE_DIR to get an idea if it has to do with rights in general ...
Hope that helps ...
Java
The code below was written to read all files in, and send the data to another method (setOutput()), and then call a method to rename the last read file to another directory, and then delete the original. Everything seems to work up until the smdrCleanup() method is called. The renameTo() is failing.
From what I understand, if a FileReader is wrapped in a BufferedReader, I only need to call BufferedReader.close() to release the last read file... which I am doing here.
I have also seen where if the file were still "open", being scanned by anti-virus programs, or otherwise locked by a process, the renameTo() function would fail. I have used Process Explorer to review what may have it locked, and I don't see anything locking it.
I have my method setup to throw any kind of IOExceptions, but I am not getting any exceptions. Everything runs, but the console merely says that the file was not copied.
I am running Eclipse Helios Release 2, Windows 7 Ultimate, local administrator, UAC disabled.
Any help would be greatly appreciated.
public void smdrReader(String path, String oldPath) throws IOException
{
output = null; //nullify the value of output to avoid duplicate data
File folder = new File(path); //setting the directory for raw data files
File[] listOfFiles = folder.listFiles(); //array of files within the folder/directory
//For loop to iterate through the available files, open, & read contents to String Buffer.
for (int i = 0; i < listOfFiles.length; i++)
{
if (listOfFiles[i].isFile()) //verifying next entry in array is a file
{
File fileName = new File(listOfFiles[i].getName());//getting file name from array iteration
StringBuffer fileData = new StringBuffer(2048);//establishing StringBuffer for reading file contents into
BufferedReader reader = new BufferedReader(new FileReader(path + fileName));//reader to actually access/read file
String readData = String.valueOf(reader);//String variable being set to value of the reader
fileData.append(readData);//appending data from String variable into StringBuffer variable
setOutput(fileData);//setting the value of "output" to the value of StringBuffer
fileData.delete(0, i);
reader.close();//closing the reader (closing the file)
smdrCleanup(oldPath,fileName.toString());//calling method to move processed file and delete original
}
}
}
//method to rename input file into another directory and delete the original file to avoid duplicate processing
public void smdrCleanup(String oldPathPassed, String fileNamePassed) throws IOException
{
File oldFile = new File(oldPathPassed);//establishing File object for path to processed folder
File fileName = new File(fileNamePassed);//establishing File object for the fileName to rename/delete
String oldFilePath = oldFile.toString();
boolean success = fileName.renameTo(new File(oldFilePath + "\\" + fileName + ".old"));//attempting to rename file
if (!success) //checking the success of the file rename operation
{
System.out.println("The File Was NOT Successfully Moved!");//reporting error if the file cannot be renamed
}
else
{
fileName.delete();//deleting the file if it was successfully renamed
}
}
oldFile.toString(); returns the full path of the file including its file name, so if your old file path is c:\path\to\file.txt, oldFilePath + "\\" + fileName + ".old" will be c:\path\to\file.txt\file.txt.old.
Since there is no folder c:\path\to\file.txt, it fails. change it to
boolean success = fileName.renameTo(new File(oldFilePath + ".old"));
And you should be good to go.
File.renameTo can fail for any number of reasons:
Many aspects of the behavior of this
method are inherently
platform-dependent: The rename
operation might not be able to move a
file from one filesystem to another,
it might not be atomic, and it might
not succeed if a file with the
destination abstract pathname already
exists. The return value should always
be checked to make sure that the
rename operation was successful.
But there's not much feedback on why it fails. Before calling renameTo, verify that the file you're moving exists, and the parent directory you are moving it to also exists, and canWrite(). Are these on the same disk volume? If not, it might fail.
*EDIT: Code sample added *
Try something like the following. Modifications:
Accepts File objects instead of Strings
Uses 2-arg File constructor to create a child File object in a parent directory
Better error checking
This might give you some clues into what is failing.
public void smdrCleanup(File oldPathPassed, File fileNamePassed) throws IOException {
if (!oldPathPassed.exists() || !oldPathPassed.isDirectory() || !oldPathPassed.canWrite() ) throw new IOException("Dest is not a writable directory: " + oldPathPassed);
if (!fileNamePassed.exists()) throw new IOException("File does not exist: " + fileNamePassed);
final File dest = new File(oldPathPassed, fileNamePassed + ".old");
if (dest.exists()) throw new IOException("File already exists: " + dest);
boolean success = (fileNamePassed).renameTo(dest);//attempting to rename file
if (!success) //checking the success of the file rename operation
{
throw new IOException("The File Was NOT Successfully Moved!");
} else {
// file was successfully renamed, no need to delete
}
}
I'm running Windows and I'm trying to refer to a directory. My function starts off like this:
File file = new File("C:\\somedir\\report");
if (!file.exists()) {
file.mkdirs();
}
doStuffWith(file);
I got a NullPointerException within the doStuffWith function, when I tried to call listFiles. Well I looked in C:\somedir and what did I find - there is a file called "report" with no extension, and also a directory called "report"! What seemed to happen was that the file object was referring to the report file rather than the directory. How do I make sure that I am referring to the directory and not the file?
one way to go about is to pass the file object corresponding to "C:\somedir" to the method and inside the method, do a listFiles() and walk through the contents, each time checking for file name and if it is "report", do a isDirectory(). proceed with actual processing when this returns true.
i think there is a isDirectory() method that will tell you if it is a directory
--EDIt
that's what I get for being up so early. I ran your code locally and it works fine for me. Was able to create new files, read directory contents, etc. What else are you trying to do?
I don't understand the problem this works fine for me:
public class MkDir {
static void doStuff(File dir) {
if ( dir.isDirectory() ) {
File[] listFiles = dir.listFiles();
for ( File f : listFiles ) {
System.out.println( f.getName() );
}
}
}
public static void main(String[] args) {
File file = new File( "C:\\dev\\rep2\\rep" );
if ( !file.exists() ) {
file.mkdirs();
}
doStuff( file );
}
}
Check if your file system has had case sensitivity enabled (HKLM\SYSTEM\CurrentControlSet\Control\Session Manager\kernel\ dword:ObCaseInsensitive in the registry.)
If so, you may be getting bitten by a case-related issue. One way to check:
String someName = "./nameNotUsedYet";
boolean first = new File(someName).mkdirs();
boolean second = new File(someName.toUpperCase()).mkdirs();
System.out.println("first = " + first + ", second = " + second);
If both mkdirs() calls succeeded, you know you have a case related complication. If so, ensure that you get the case for "C:\somedir\report" exactly right.