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 ...
Related
I am writing a simple (generic) wrapper Java class that will execute on various computers separate from a deployed web server. I want to download the latest version of a jar file that is the application from that associated Web Server (currently Jetty 8).
I have code like this:
// Get the jar URL which contains the application
URL jarFileURL = new URL("jar:http://localhost:8081/myapplication.jar!/");
JarURLConnection jcl = (JarURLConnection) jarFileURL.openConnection();
Attributes attr = jcl.getMainAttributes();
String mainClass = (attr != null)
? attr.getValue(Attributes.Name.MAIN_CLASS)
: null;
if (mainClass != null) // launch the program
This works well, except that myapplication.jar is a large jar file (a OneJar jarfile, so a lot is in there). I would like this to be as efficient as possible. The jar file isn't going to change very often.
Can the jar file be saved to disk (I see how to get a JarFile object, but not to save it)?
More importantly, but related to #1, can the jar file be cached somehow?
2.1 can I (easily) request the MD5 of the jar file on the web server and only download it when that has changed?
2.2 If not is there another caching mechanism, maybe request only the Manifest? Version/Build info could be stored there.
If anyone done something similar could you sketch out in as much detail what to do?
UPDATES PER INITIAL RESPONSES
The suggestion is to use an If-Modified-Since header in the request and the openStream method on the URL to get the jar file to save.
Based on this feedback, I have added one critical piece of info and some more focused questions.
The java program I am describing above runs the program downloaded from the jar file referenced. This program will run from around 30 seconds to maybe 5 minutes or so. Then it is done and exits. Some user may run this program multiple times per day (say even up to 100 times), others may run it as infrequently as once every other week. It should still be smart enough to know if it has the most current version of the jar file.
More Focused Questions:
Will the If-Modified-Since header still work in this usage? If so, will I need completely different code to add that? That is, can you show me how to modify the code presented to include that? Same question with regard to saving the jar file - ultimately I am really surprised (frustrated!) that I can get a JarFile object, but have no way to persist it - will I even need the JarURLConnection class?
Bounty Question
I didn't initially realize the precise question I was trying to ask. It is this:
How can I save a jar file from a web server locally in a command-line program that exits and ONLY update that jar file when it has been changed on the server?
Any answer that, via code examples, shows how that may be done will be awarded the bounty.
Yes, the file can be saved to the disk, you can get the input stream using the method openStream() in URL class.
As per the comment mentioned by #fge there is a way to detect whether the file is modified.
Sample Code:
private void launch() throws IOException {
// Get the jar URL which contains the application
String jarName = "myapplication.jar";
String strUrl = "jar:http://localhost:8081/" + jarName + "!/";
Path cacheDir = Paths.get("cache");
Files.createDirectories(cacheDir);
Path fetchUrl = fetchUrl(cacheDir, jarName, strUrl);
JarURLConnection jcl = (JarURLConnection) fetchUrl.toUri().toURL().openConnection();
Attributes attr = jcl.getMainAttributes();
String mainClass = (attr != null) ? attr.getValue(Attributes.Name.MAIN_CLASS) : null;
if (mainClass != null) {
// launch the program
}
}
private Path fetchUrl(Path cacheDir, String title, String strUrl) throws IOException {
Path cacheFile = cacheDir.resolve(title);
Path cacheFileDate = cacheDir.resolve(title + "_date");
URL url = new URL(strUrl);
URLConnection connection = url.openConnection();
if (Files.exists(cacheFile) && Files.exists(cacheFileDate)) {
String dateValue = Files.readAllLines(cacheFileDate).get(0);
connection.addRequestProperty("If-Modified-Since", dateValue);
String httpStatus = connection.getHeaderField(0);
if (httpStatus.indexOf(" 304 ") == -1) { // assuming that we get status 200 here instead
writeFiles(connection, cacheFile, cacheFileDate);
} else { // else not modified, so do not do anything, we return the cache file
System.out.println("Using cached file");
}
} else {
writeFiles(connection, cacheFile, cacheFileDate);
}
return cacheFile;
}
private void writeFiles(URLConnection connection, Path cacheFile, Path cacheFileDate) throws IOException {
System.out.println("Creating cache entry");
try (InputStream inputStream = connection.getInputStream()) {
Files.copy(inputStream, cacheFile, StandardCopyOption.REPLACE_EXISTING);
}
String lastModified = connection.getHeaderField("Last-Modified");
Files.write(cacheFileDate, lastModified.getBytes());
System.out.println(connection.getHeaderFields());
}
How can I save a jar file from a web server locally in a command-line program that exits and ONLY update that jar file when it has been changed on the server?
With JWS. It has an API so you can control it from your existing code. It already has versioning and caching, and comes with a JAR-serving servlet.
I have assumed that a .md5 file will be available both locally and at the web server. Same logic will apply if you wanted this to be a version control file.
The urls given in the following code need to updated according to your web server location and app context. Here is how your command line code would go
public class Main {
public static void main(String[] args) {
String jarPath = "/Users/nrj/Downloads/local/";
String jarfile = "apache-storm-0.9.3.tar.gz";
String md5File = jarfile + ".md5";
try {
// Update the URL to your real server location and application
// context
URL url = new URL(
"http://localhost:8090/JarServer/myjar?hash=md5&file="
+ URLEncoder.encode(jarfile, "UTF-8"));
BufferedReader in = new BufferedReader(new InputStreamReader(
url.openStream()));
// get the md5 value from server
String servermd5 = in.readLine();
in.close();
// Read the local md5 file
in = new BufferedReader(new FileReader(jarPath + md5File));
String localmd5 = in.readLine();
in.close();
// compare
if (null != servermd5 && null != localmd5
&& localmd5.trim().equals(servermd5.trim())) {
// TODO - Execute the existing jar
} else {
// Rename the old jar
if (!(new File(jarPath + jarfile).renameTo((new File(jarPath + jarfile
+ String.valueOf(System.currentTimeMillis())))))) {
System.err
.println("Unable to rename old jar file.. please check write access");
}
// Download the new jar
System.out
.println("New jar file found...downloading from server");
url = new URL(
"http://localhost:8090/JarServer/myjar?download=1&file="
+ URLEncoder.encode(jarfile, "UTF-8"));
// Code to download
byte[] buf;
int byteRead = 0;
BufferedOutputStream outStream = new BufferedOutputStream(
new FileOutputStream(jarPath + jarfile));
InputStream is = url.openConnection().getInputStream();
buf = new byte[10240];
while ((byteRead = is.read(buf)) != -1) {
outStream.write(buf, 0, byteRead);
}
outStream.close();
System.out.println("Downloaded Successfully.");
// Now update the md5 file with the new md5
BufferedWriter bw = new BufferedWriter(new FileWriter(md5File));
bw.write(servermd5);
bw.close();
// TODO - Execute the jar, its saved in the same path
}
} catch (IOException e) {
e.printStackTrace();
}
}
}
And just in case you had control over the servlet code as well, this is how the servlet code goes:-
#WebServlet(name = "jarervlet", urlPatterns = { "/myjar" })
public class JarServlet extends HttpServlet {
private static final long serialVersionUID = 1L;
// Remember to have a '/' at the end, otherwise code will fail
private static final String PATH_TO_FILES = "/Users/nrj/Downloads/";
#Override
protected void doGet(HttpServletRequest req, HttpServletResponse resp)
throws ServletException, IOException {
String fileName = req.getParameter("file");
if (null != fileName) {
fileName = URLDecoder.decode(fileName, "UTF-8");
}
String hash = req.getParameter("hash");
if (null != hash && hash.equalsIgnoreCase("md5")) {
resp.getWriter().write(readMd5Hash(fileName));
return;
}
String download = req.getParameter("download");
if (null != download) {
InputStream fis = new FileInputStream(PATH_TO_FILES + fileName);
String mimeType = getServletContext().getMimeType(
PATH_TO_FILES + fileName);
resp.setContentType(mimeType != null ? mimeType
: "application/octet-stream");
resp.setContentLength((int) new File(PATH_TO_FILES + fileName)
.length());
resp.setHeader("Content-Disposition", "attachment; filename=\""
+ fileName + "\"");
ServletOutputStream os = resp.getOutputStream();
byte[] bufferData = new byte[10240];
int read = 0;
while ((read = fis.read(bufferData)) != -1) {
os.write(bufferData, 0, read);
}
os.close();
fis.close();
// Download finished
}
}
private String readMd5Hash(String fileName) {
// We are assuming there is a .md5 file present for each file
// so we read the hash file to return hash
try (BufferedReader br = new BufferedReader(new FileReader(
PATH_TO_FILES + fileName + ".md5"))) {
return br.readLine();
} catch (IOException e) {
e.printStackTrace();
}
return null;
}
}
I can share experience of solving the same problem in our team. We have several desktop product written in java which are updated regularly.
Couple years ago we had separate update server for every product and following process of update: Client application has an updater wrapper that starts before main logic, and stored in a udpater.jar. Before start, application send request to update server with MD5-hash of application.jar file. Server compares received hash with the one that it has, and send new jar file to updater if hashes are different.
But after many cases, where we confused which build is now in production, and update-server failures we switched to continuous integration practice with TeamCity on top of it.
Every commit done by developer is now tracked by build server. After compilation and test passing build server assigns build number to application and shares app distribution in local network.
Update server now is a simple web server with special structure of static files:
$WEB_SERVER_HOME/
application-builds/
987/
988/
989/
libs/
app.jar
...
changes.txt <- files, that changed from last build
lastversion.txt <- last build number
Updater on client side requests lastversion.txt via HttpClient, retrieves last build number and compares it with client build number stored in manifest.mf.
If update is required, updater harvests all changes made since last update iterating over application-builds/$BUILD_NUM/changes.txt files. After that, updater downloads harvested list of files. There could be jar-files, config files, additional resources etc.
This scheme is seems complex for client updater, but in practice it is very clear and robust.
There is also a bash script that composes structure of files on updater server. Script request TeamCity every minute to get new builds and calculates diff between builds. We also upgrading now this solution to integrate with project management system (Redmine, Youtrack or Jira). The aim is to able product manager to mark build that are approved to be updated.
UPDATE.
I've moved our updater to github, check here: github.com/ancalled/simple-updater
Project contains updater-client on Java, server-side bash scripts (retrieves updates from build-server) and sample application to test updates on it.
Can someone please point out what I'm doing wrong here.
I have a small weather app that generates and sends an HTML email. With my code below, everything works fine when I run it from Eclipse. My email gets generated, it's able to access my image resources and it sends the email with the included attachment.
However, when I build the executable jar by running mvn install and run the jar using java -jar NameOfMyJar.jar I get java.io.FileNotFound Exceptions for my image resource.
I know that I have to be doing something wrong with how I'm accessing my image resources, I just don't understand why it works fine when it's not packaged, but bombs out whenever I package it into a jar.
Any advice is very much appreciated it.
My project layout
How I'm accessing my image resource
//Setup the ATTACHMENTS
MimeBodyPart attachmentsPart = new MimeBodyPart();
try {
attachmentsPart.attachFile("resources/Cloudy_Day.png");
} catch (IOException e) {
// TODO Auto-generated catch block
e.printStackTrace();
}
The StackTrace
Exception in thread "main" java.lang.RuntimeException: javax.mail.MessagingException: IOException while sending message;
nested exception is:
java.io.FileNotFoundException: resources/Cloudy_Day.png (No such file or directory)
at Utilities.SendEmailUsingGmailSMTP.SendTheEmail(SendEmailUsingGmailSMTP.java:139)
at Utilities.SendEmailUsingGmailSMTP.SendWeatherEmail(SendEmailUsingGmailSMTP.java:66)
at Weather.Main.start(Main.java:43)
at Weather.Main.main(Main.java:23)
Caused by: javax.mail.MessagingException: IOException while sending message;
nested exception is:
java.io.FileNotFoundException: resources/Cloudy_Day.png (No such file or directory)
at com.sun.mail.smtp.SMTPTransport.sendMessage(SMTPTransport.java:1167)
at javax.mail.Transport.send0(Transport.java:195)
at javax.mail.Transport.send(Transport.java:124)
at Utilities.SendEmailUsingGmailSMTP.SendTheEmail(SendEmailUsingGmailSMTP.java:134)
... 3 more
Caused by: java.io.FileNotFoundException: resources/Cloudy_Day.png (No such file or directory)
at java.io.FileInputStream.open(Native Method)
at java.io.FileInputStream.<init>(FileInputStream.java:146)
at javax.activation.FileDataSource.getInputStream(FileDataSource.java:97)
at javax.activation.DataHandler.writeTo(DataHandler.java:305)
at javax.mail.internet.MimeBodyPart.writeTo(MimeBodyPart.java:1485)
at javax.mail.internet.MimeBodyPart.writeTo(MimeBodyPart.java:865)
at javax.mail.internet.MimeMultipart.writeTo(MimeMultipart.java:462)
at com.sun.mail.handlers.multipart_mixed.writeTo(multipart_mixed.java:103)
at javax.activation.ObjectDataContentHandler.writeTo(DataHandler.java:889)
at javax.activation.DataHandler.writeTo(DataHandler.java:317)
at javax.mail.internet.MimeBodyPart.writeTo(MimeBodyPart.java:1485)
at javax.mail.internet.MimeMessage.writeTo(MimeMessage.java:1773)
at com.sun.mail.smtp.SMTPTransport.sendMessage(SMTPTransport.java:1119)
... 6 more
Others are correct with the use of getResourceAsStream, but the path is a little tricky. You see the little package icon in the resources folder? That signifies that all the files in the resource folder will be put into the root of the classpath. Just like all the packages in src/main/java are put in the root. So you would take out the resources from the path
InputStream is = getClass().getResourceAsStream("/Cloudy_Day.png");
An aside: Maven has a file structure conventions. Class path resources are usually put into src/main/resources. If you create a resources dir in the src/main, Eclipse should automatically pick it up, and create the little package icon for a path src/main/resource that you should see in the project explorer. These files would also go to the root and could be accessed the same way. I would fix the file structure to follow this convention.
Note: A MimeBodyPart, can be Constructed from an InputStream (As suggested by Bill Shannon, this is incorrect). As mentioned in his comment below
"You can also attach the data using"
mbp.setDataHandler(new DataHandler(new ByteArrayDataSource(
this.getClass().getResourceAsStream("/Cloudy_Day.png", "image/png"))));
You can't access resources inside a JAR file as a File, only read them as an InputStream: getResourceAsStream().
As the MimeBodyPart has no attach() method for an InputStream, the easiest way should be to read your resources and write them to temp files, then attach these files.
Try this
new MimeBodyPart().attachFile(new File(this.getClass().getClassLoader().getResource("resources/Cloudy_Day.png").toURI());
I don't know if this will help anyone or not. But, I have a similar case as the OP and I solved the case by finding the file in the classpath using recursive function. The idea is so that when another developer decided to move the resources into another folder/path. It will still be found as long as the name is still the same.
For example, in my work we usually put our resources outside the jar, and then we add said resources path into our classpath, so here the classpath of the resources will be different depending on where it is located.
That's where my code comes to work, no matter where the file is put, as long as it's in the classpath it will be found.
Here is an example of my code in action:
import java.io.File;
public class FindResourcesRecursive {
public File findConfigFile(String paths, String configFilename) {
for (String p : paths.split(File.pathSeparator)) {
File result = findConfigFile(new File(p), configFilename);
if (result != null) {
return result;
}
}
return null;
}
private File findConfigFile(File path, String configFilename) {
if (path.isDirectory()) {
String[] subPaths = path.list();
if (subPaths == null) {
return null;
}
for (String sp : subPaths) {
File subPath = new File(path.getAbsoluteFile() + "/" + sp);
File result = findConfigFile(subPath, configFilename);
if (result != null && result.getName().equalsIgnoreCase(configFilename)) {
return result;
}
}
return null;
} else {
File file = path;
if (file.getName().equalsIgnoreCase(configFilename)) {
return file;
}
return null;
}
}
}
Here I have a test case that is coupled with a file "test.txt" in my test/resources folder. The content of said file is:
A sample file
Now, here is my test case:
import org.junit.Test;
import java.io.*;
import static org.junit.Assert.fail;
public class FindResourcesRecursiveTest {
#Test
public void testFindFile() {
// Here in the test resources I have a file "test.txt"
// Inside it is a string "A sample file"
// My Unit Test will use the class FindResourcesRecursive to find the file and print out the results.
File testFile = new FindResourcesRecursive().findConfigFile(
System.getProperty("java.class.path"),
"test.txt"
);
try (FileInputStream is = new FileInputStream(testFile)) {
int i;
while ((i = is.read()) != -1) {
System.out.print((char) i);
}
System.out.println();
} catch (IOException e) {
fail();
}
}
}
Now, if you run this test, it will print out "A sample file" and the test will be green.
I am trying to createNewFile() in java.I have written down the following example.I have compiled it but am getting a run time error.
import java.io.File;
import java.io.IOException;
public class CreateFileExample
{
public static void main(String [] args)
{
try
{
File file = new File("home/karthik/newfile.txt");
if(file.createNewFile())
{
System.out.println("created new fle");
}else
{
System.out.println("could not create a new file");
}
}catch(IOException e )
{
e.printStackTrace();
}
}
}
It is compiling OK.The run time error that I am getting is
java.io.IOException: No such file or directory
at java.io.UnixFileSystem.createFileExclusively(Native Method)
at java.io.File.createNewFile(File.java:947)
at CreateFileExample.main(CreateFileExample.java:16)
some points here
1- as Victor said you are missing the leading slash
2- if your file is created, then every time you invoke this method "File.createNewFile()" will return false
3- your class is very platform dependent (one of the main reasons why Java is powerful programming language is that it is a NON-PLATFORM dependent), instead you can detect a relative location throw using the System.getProperties() :
// get System properties :
java.util.Properties properties = System.getProperties();
// to print all the keys in the properties map <for testing>
properties.list(System.out);
// get Operating System home directory
String home = properties.get("user.home").toString();
// get Operating System separator
String separator = properties.get("file.separator").toString();
// your directory name
String directoryName = "karthik";
// your file name
String fileName = "newfile.txt";
// create your directory Object (wont harm if it is already there ...
// just an additional object on the heap that will cost you some bytes
File dir = new File(home+separator+directoryName);
// create a new directory, will do nothing if directory exists
dir.mkdir();
// create your file Object
File file = new File(dir,fileName);
// the rest of your code
try {
if (file.createNewFile()) {
System.out.println("created new fle");
} else {
System.out.println("could not create a new file");
}
} catch (IOException e) {
e.printStackTrace();
}
this way you will create your file in any home directory on any platform, this worked for my windows operating system, and is expected to work for your Linux or Ubuntu as well
You're missing the leading slash in the file path.
Try this:
File file = new File("/home/karthik/newfile.txt");
That should work!
Actually this error comes when there is no directory "karthik" as in above example and createNewFile() is only to create file not for directory use mkdir() for directory and then createNewFile() for file.
I have a simple updater for my application. In code i am downloading a new version, deleting old version and renaming new version to old.
It works fine on Linux. But doesn't work on Windows. There are no excepions or something else.
p.s. RemotePlayer.jar it is currently runned application.
UPDATED:
Doesn't work - it means that after file.delete() and file.renameTo(...) file still alive.
I use sun java 7. (because I use JavaFX).
p.s. Sorry for my English.
public void checkUpdate(){
new Thread(new Runnable() {
#Override
public void run() {
System.err.println("Start of checking for update.");
StringBuilder url = new StringBuilder();
url.append(NetworkManager.SERVER_URL).append("/torock/getlastversionsize");
File curJarFile = null;
File newJarFile = null;
try {
curJarFile = new File(new File(".").getCanonicalPath() + "/Player/RemotePlayer.jar");
newJarFile = new File(new File(".").getCanonicalPath() + "/Player/RemotePlayerTemp.jar");
if (newJarFile.exists()){
newJarFile.delete();
}
} catch (IOException e) {
e.printStackTrace(); //To change body of catch statement use File | Settings | File Templates.
System.err.println("Cannot find curr Jar file");
return;
}
if (curJarFile.exists()){
setAccesToFile(curJarFile);
try {
String resp = NetworkManager.makeGetRequest(url.toString());
JSONObject jsresp = new JSONObject(resp);
if (jsresp.getString("st").equals("ok")){
if (jsresp.getInt("size") != curJarFile.length()){
System.out.println("New version available, downloading started.");
StringBuilder downloadURL = new StringBuilder();
downloadURL.append(NetworkManager.SERVER_URL).append("/torock/getlatestversion");
if (NetworkManager.downLoadFile(downloadURL.toString(), newJarFile)){
if (jsresp.getString("md5").equals(Tools.md5File(newJarFile))){
setAccesToFile(newJarFile);
System.err.println("Deleting old version. File = " + curJarFile.getCanonicalPath());
boolean b = false;
if (curJarFile.canWrite() && curJarFile.canRead()){
curJarFile.delete();
}else System.err.println("Cannot delete cur file, doesn't have permission");
System.err.println("Installing new version. new File = " + newJarFile.getCanonicalPath());
if (curJarFile.canWrite() && curJarFile.canRead()){
newJarFile.renameTo(curJarFile);
b = true;
}else System.err.println("Cannot rename new file, doesn't have permission");
System.err.println("last version has been installed. new File = " + newJarFile.getCanonicalPath());
if (b){
Platform.runLater(new Runnable() {
#Override
public void run() {
JOptionPane.showMessageDialog(null, String.format("Внимание, %s", "Установлена новая версия, перезапустите приложение" + "", "Внимание", JOptionPane.ERROR_MESSAGE));
}
});
}
}else System.err.println("Downloading file failed, md5 doesn't match.");
}
} else System.err.println("You use latest version of application");
}
}catch (Exception e){
e.printStackTrace();
System.err.println("Cannot check new version.");
}
}else {
System.err.println("Current jar file not found");
}
}
}).start();
}
private void setAccesToFile(File f){
f.setReadable(true, false);
f.setExecutable(true, false);
f.setWritable(true, false);
}
I found the solution to this problem. The problem of deletion occurred in my case because-:
File f1=new File("temp.txt");
RandomAccessFile raf=new RandomAccessFile(f1,"rw");
f1.delete();//The file will not get deleted because raf is open on the file to be deleted
But if I close RandomAccessFile before calling delete then I am able to delete the file.
File f1=new File("temp.txt");
RandomAccessFile raf=new RandomAccessFile(f1,"rw");
raf.close();
f1.delete();//Now the file will get deleted
So we must check before calling delete weather any object such as FileInputStream, RandomAccessFile is open on that file or not. If yes then we must close that object before calling delete on that file.
windows locks files that are currently in use. you cannot delete them. on windows, you cannot delete a jar file which your application is currently using.
Since you are using Java 7, try java.nio.file.Files.delete(file.toPath()), it'll throw exception if deletion fails.
There are several reasons:
Whether you have permissions to edit the file in windows.
The file is in use or not.
The path is right or not.
I don't know wich version of Java you are using.
I know when Java was sun property they publish that the Object File can't delete files correctly on windows plateform (sorry I don't find the reference no more).
The tricks you can do is to test the plateform directly. When you are on linux just use the classic File object.
On windows launch a command system to ask windows to delete the file you want.
Runtime.getRuntime().exec(String command);
I just want to make one comment. I learned that you can delete files in Java from eclipse if you run eclipse program as Administrator. I.e. when you right click on the IDE Icon (Eclipse or any other IDE) and select Run as Administrator, Windows lets you delete the file.
I hope this helps. It helped me.
Cordially,
Fernando
I have a web application, and I'm trying to return a boolean, of a .zip file that gets (successfully) generated on the server.
Locally I run this on Eclipse with Tomcat on Windows, but I am deploying it to a Tomcat Server on a Linux machine.
//.zip is generated successfully on the SERVER by this point
File file1 = new File("/Project/zip/theZipFile.zip");
boolean exists = file1.exists();// used to print if the file exists, returns false
if (exists)
fileLocation = "YES";
else
fileLocation = "No";
When I do this, it keeps returning false on the debugger and on my page when I print it out. I am sure it has something to do with file paths, but I am unsure.
Once I get the existence of the zip confirmed, I can easily use File.length() to get what I need.
Assume all getters and setters are in existence, and the JSF prints. It is mainly the Java backend I am having a slight issue with.
Thanks for any help! :)
Your path is not good. Try remove the leading / to fix the problem
See the test code for explanations :
import java.io.*;
public class TestFile {
public static void main(String[] args) {
try {
//Creates a myfile.txt file in the current directory
File f1 = new File("myfile.txt");
f1.createNewFile();
System.out.println(f1.exists());
//Creates a myfile.txt file in a sub-directory
File f2 = new File("subdir/myfile.txt");
f2.createNewFile();
System.out.println(f2.exists());
//Throws an IOException because of the leading /
File f3 = new File("/subdir/myfile.txt");
f3.createNewFile();
System.out.println(f3.exists());
} catch(IOException e) {
System.out.println(e.getMessage());
}
}
}
Debug using this statement
System.out.println("Actual file location : " + file1.getAbsolutePath());
This will tell you the absolute path of the file it's looking for