So here's my code so far, yes I know it's pretty basic. But what I would Like to accomplish is to Replace the host file located in the System32\drivers\etc folder, the problem I am having in doing this is that I am getting an access denied error. How can I give the program access to make changes within the windows folder, also the class SaveURL just downloads the file and uses two strings to pass the name and download location through the function saveImage. How can I give myself access? Thanks in advance I truly appreciate it.
private void jButton7MouseClicked(java.awt.event.MouseEvent evt) {
String destinationHosts = "hosts";
String urlHosts = "https://dl.dropbox.com/s/awdvoprxyo7r2q6/hosts?dl=1";
Object hostOptions[] = {"Replace", "Close"};
File fileHosts = new File(destinationHosts);
File dirHost = new File("hosts");
boolean dirHosts = dirHost.mkdir();
try {
Runtime.getRuntime().exec("notepad.exe \\Windows\\system32\\drivers\\etc\\hosts");
jTextArea2.append("Opening Host File \n");
int hostFile = JOptionPane.showOptionDialog(rootPane, "Would you like to replace the Hosts File?",
"Yes or No", JOptionPane.YES_NO_OPTION, JOptionPane.NO_OPTION, null, hostOptions, hostOptions[0]);
if (hostFile == JOptionPane.YES_NO_OPTION) {
jTextArea2.append("Downloading New Host File");
SaveUrl.saveImage(urlHosts, destinationHosts);
fileHosts.renameTo(new File(dirHost, fileHosts.getName()));
Path source = Paths.get("\\hosts\\hosts");
Path target = Paths.get("\\Windows\\system32\\drivers\\etc\\");
Files.copy(source, target);
jTextArea2.append("Host file replaced");
}
} catch (IOException ex) {
Logger.getLogger(ToolKit1.class.getName()).log(Level.SEVERE, null, ex);
}
}
Related
I'm new to Android Studio 3.0, emulating on a Nexus 4, Marshmallow. I'm trying to build simple "Save File" and "Load File" parts of my app. Here's the "Save File" part:
String filename = "myFile01"; // Then "myFile02", "myFile03", etc...
String userData = "Some useful data here...";
try {
// Adapted from: https://www.youtube.com/watch?v=_15mKw--RG0
FileOutputStream fileOutputStream = openFileOutput(filename, MODE_PRIVATE); // creates a file with given filename
fileOutputStream.write(userData.getBytes()); // puts userData into the file
fileOutputStream.close();
Toast.makeText(getApplicationContext(), "File saved!", Toast.LENGTH_LONG).show();
} catch (FileNotFoundException e) {
e.printStackTrace();
} catch (IOException e) {
e.printStackTrace();
}
The above code will be called again and again as the user creates and saves additional files. Later, the user may want to view all the saved files and load one. I'll have a ListView displaying all the files... but I need help reading the current directory to get that list.
I thought I read somewhere that in Android, there's one flat directory for your app to save and retrieve files. So I was hoping if I saved a bunch of files and then called a read() method, all my saved files would simply be in the default directory, no need to search. That seems to be a bad assumption; here's why:
Here's my code looking in the default directory and listing all the files found within there. First, I need the path of said default directory:
// Get current directory adapted from: https://stackoverflow.com/questions/5527764/get-application-directory
String packName, currDir;
PackageManager m = getPackageManager();
packName = getPackageName();
PackageInfo p = null;
try {
p = m.getPackageInfo(packName, 0);
} catch (PackageManager.NameNotFoundException e) {
e.printStackTrace();
}
currDir = p.applicationInfo.dataDir;
And then I open "currDir," and store the names of all the local files in an array:
// get list of files adapted from: https://stackoverflow.com/questions/9317483/showing-a-list-of-files-in-a-listview#9317583
File dir = new File(currDir);
File[] filelist = dir.listFiles();
String[] fileArr = new String[filelist.length];
for (int i = 0; i < fileArr.length; i++) {
fileArr[i] = filelist[i].getName();
}
The plan from here is to load the "fileArr" into a ListView and go from there. But when I step through the debugger, I see this as the contents of "fileArr":
"cache"
"code_cache"
"files"
This is true no matter how many files I've saved previously.
BTW, in the debugger, the assignments for packName and currDir look 100% correct:
packName = com.mydomain.myapp
currDir = /data/user/0/com.mydomain.myapp
So... I'm kinda assuming that my saved files are actually here:
/data/user/0/com.mydomain.myapp/files
And therefore, I should append this to my "get current directory" code:
// Get current directory adapted from: https://stackoverflow.com/questions/5527764/get-application-directory
String packName, currDir;
...everything from before...
currDir = p.applicationInfo.dataDir+"/files"; // <---- appending "+"/files"
Or am I way off? Any advice will be appreciated, thanks!
First of all, if you want to save your files in the app's directory, then you should call create a directory,
File directoryDefault = new File(Environment.DIRECTORY_DOCUMENTS, "YOUR_FOLDER_NAME");
if (!directoryDefault.exists()) {
directoryDefault.mkdir();
}
Then you have to save whatever files you have to save in the above mentioned default directory. Afterwards, when you want to list all the files available in that directory, you should call,
private ArrayList<String> fileNames() {
ArrayList<String> namesArray = new ArrayList<>();
File[] arrayFiles = directoryDefault.listFiles();
for (File file : arrayFiles) {
namesArray.add(file.getName());
}
return namesArray;
}
My task is to save a file in the path specified by the end user (must be an absolute path). Am currently facing three different scenarios as in below:
Path name is invalid (cannot be created) - for ex, path name provided by user : sfg rgdf gfggdgfudf
Path name is invalid (but, it can be created) - for ex : C:\Parent\Child\GrandChildren (here C:\Parent exists whereas Child\GrandChildren does not.
Path name is valid (i.e. directory exists) - for ex : C:\Parent\Test
For the first case, I need to save the file in a default location.
For the second, I need to create directories and save the file.
And for the last, I'll save in the specified path.
Below is my code snippet which is saving the file in default location for both first and second scenarios. Am having difficulty to distinguish between first and second. java.io.File.mkdirs works for the second case, but not for the first.
Please ignore my poor code as am new to this programming language. Any inputs would be much appreciated.
//User input must be absolute path
String saveToFolder = "kut igeiguye jh";
String defaultFolder = "C:\\Parent\\Data";
try{
File file = new File(saveToFolder);
if(!file.exists()){
saveToFolder = defaultFolder;
}
file.mkdirs();
}catch(Exception e){
saveToFolder = defaultFolder;
}
//code to save data in path **saveToFolder**
1) For 1st case use regex to determine if path is valid or not
String regularExpression = "([a-zA-Z]:)?(\\[a-zA-Z0-9_-]+)+\\?" ; // this regex for windows. If you are running in linux then regex will be different.
Pattern pattern = Pattern.compile(regularExpression);
boolean isMatched = Pattern.matches(regularExpression,saveToFolder);
2) Check if path is valid or not again using 1st method. If its valid check if folder exists or not.
File f = new File(saveToFolder);
if (f.exists() && f.isDirectory()) {
...
}
3) If path is valid by first method and if it exists second method .
kut igeiguye jh is happily accepted by most file systems out there. If you don't want spaces in your path/filenames, you already need to check the validity by yourself e.g. using a Regular Expression.
Appreciate all those who added their inputs. I made few changes to my code which works. One of my assignments requirement was that my program must take absolute path as input.
With my below code, am able to save data in default location for case 1; New folders are being created and file is being saved in the newly created folder for case 2; And saving the file in specified path for case 3.
String saveToFolder = "kut igeiguye jh";
String defaultFolder = "C:\\Parent\\Data";
try{
File file = new File(saveToFolder);
boolean dirCreated = file.mkdirs();
if(!dirCreated || (file.getParent().equals(null))){
saveToFolder = defaultFolder;
}
}catch(Exception e){
saveToFolder = defaultFolder;
}
System.out.println("save to folder : " +saveToFolder);
you can use isFile() to valid over exists(). I have not checked for all cases but this should help you.
public static void checkPath(){
String saveToFolder = "file/User.txt";
String defaultFolder = "file/data/";
try{
File file = new File(saveToFolder);
if(!file.isFile()){
saveToFolder = defaultFolder;
System.out.println("File not found");
}
file.mkdirs();
}catch(Exception e){
saveToFolder = defaultFolder;
}
}
Java NIO make this simple. The method Files.createDirectories succeeds whether the directory already exists or didn't exist and has been created.
try {
Files.createDirectories(Paths.get(saveToFolder));
}
catch (IOException e) {
System.err.println("Using default folder due to the following exception: " + e);
saveToFolder = defaultFolder;
}
If you really want to check whether the user entered an absolute path, just use Path.isAbsolute().
I want to convert a text file to a html file and then open it with a browser. I try to use file.renameTo() to rename the text file's extension to .html but the rename attempt always fails and file.renameTo() always returns false. Therefore, when I try to open the file in the below method, the file is opened in notepad.
file declaration:
private File file;
file declaration in constructor:
file = new File("D:/dc1000/Project/webPage.txt");
file.getParentFile().mkdirs();
method that doesn't work:
public void compileWebpage(){
File file2 = new File("D:/dc1000/Project/CompiledWebpage.html");
file2.getParentFile().mkdirs();
addFileTags("end"); //add ending tags like </body>
boolean success = true;
try{
success = file.renameTo(file2);
}catch (Exception e){
System.out.println(e);
}
if(!success){
System.out.println("webPage compilation failed.");
}
Desktop desktop = Desktop.getDesktop();
try{
desktop.browse(file.toURI());
}catch (IOException e){
e.printStackTrace();
}
}
No exceptions are thrown, "Webpage compilation failed" is printed to the console and then notepad opens the file. The file looks like this when opened in notepad:
<html>
<head>
</head>
<body>
<p>hi</p>
</body>
</html>
Why does File.renameTo() always fail? How can I open this text file in a browser as a html file?
Well, off hand it's rather hard to tell without truly knowing what the addFileTag() method is doing. The only reason I can think of is that the webPage.txt file is still open for either read or write operations.
Your code has accessed the file but never closed it again. You can't rename a file that is open. I would have to assume this is in fact done somewhere within the addFileTag() method.
Because your call to the File.renameTo() method was unsuccessful the "webPage.txt" text file was never renamed to "CompiledWebpage.html" so in essence the "CompiledWebpage.html" file simply does not exist within the system. This however is not the reason why the Windows NotePad application is opening your file instead of the expected default Web Browser:
To begin with the File object variable so conveniently named 'file' was declared and initialized to be related to the "D:/dc1000/Project/webPage.txt" text file and it always will be since it's Class global unless of course that relationship is changed somewhere within your code. To be blunt... it's not and I guess it's a good thing for now because IF your File Rename was successful you would have simply gotten an FileNotFound Exception because the text file related to the 'file' variable would no longer exist due to the simple fact that it was renamed.
What you really want to pass to the DeskTop.browse() method is the File object 'file2' variable which is related to the "D:/dc1000/Project/CompiledWebpage.html" text file. Mind you, you'll still get an FileNotFound Exception because the File.renameTo() method had failed. So you definitely want to make sure you have success here.
Whatever...Why did the Windows NotePad application open instead of the Web Browser?
Here's why:
The Operating System File Associations is what determines which application will open the file when using the DeskTop.browse() method. In the Windows Operating System, by default, a file with the file name extension of ".txt" is automatically opened and displayed within NotePad, a file with the file name extension of ".docx" is automatically opened and displayed in MS Office WORD, a file with the file name extension of ".html" is opened and displayed within the default Web Browser. I think you get the idea here.
Because the 'file' variable is still related to the file "D:/dc1000/Project/webPage.txt" and because the File.renameTo() method failed, Windows simply seen the .txt file extension and displayed the file (as stipulated within the 'file' variable) to NotePad.
So...How do I get all this to actually Work!?
Well, if I may be so bold, do this instead:
Place this somewhere in your code, a button action event or whatever:
String sourceFile = "D:/dc1000/Project/webPage.txt";
String destinationFile = "D:/dc1000/Project/CompiledWebpage.html";
boolean success = CompileToWebPage(sourceFile, destinationFile, "This is My Head Text");
if (success) {
System.out.println("Text File Successfully Compiled!");
}
else {
System.out.println("Text File Compilation FAILED!");
}
//Display our new file in the web Browser...
try {
File htmlFile = new File(destinationFile);
Desktop.getDesktop().browse(htmlFile.toURI());
} catch (IOException ex) {}
Here is a new CompileToWebPage() method:
private static boolean CompileToWebPage(final String sourcefilePath,
final String destinationFilePath, String... headText) {
// headText is OPTIONAL.
String headTxt = "";
if (headText.length != 0) { headTxt = headText[0]; }
//Read sourcefilePath file data into a String ArrayList...
BufferedReader input;
try {
input = new BufferedReader(new FileReader(sourcefilePath));
if (!input.ready()) { throw new IOException(); }
}
catch (FileNotFoundException ex) {
JOptionPane.showMessageDialog(null,"CompileToWebPage() Method Error!\n\nThe supplied "
+ "file path was not found!\n\n" + sourcefilePath, "File NotFound",
JOptionPane.ERROR_MESSAGE);
return false;
}
catch (IOException ex) {
JOptionPane.showMessageDialog(null,"CompileToWebPage() Method Error!\n\nThe supplied "
+ "file is not ready to be read!\n\n" + ex.getMessage(), "File Not Ready",
JOptionPane.ERROR_MESSAGE);
return false;
}
// Place required HTML Tags into String ArrayList
ArrayList<String> txt = new ArrayList<>();
txt.add("<html>");
txt.add("<head>");
txt.add(headTxt);
txt.add("</head>");
txt.add("<body>");
// Read each line of the source text File and add
// them to our String ArrayList...
try {
String str;
while((str = input.readLine()) != null){
txt.add("<p>" + str + "</p>");
}
input.close();
}
catch (IOException ex) {
JOptionPane.showMessageDialog(null,"CompileToWebPage() Method Error!\n\n"
+ "There was a problem reading the source Text from file!\n\n"
+ ex.getMessage(), "File Read Error", JOptionPane.ERROR_MESSAGE);
return false;
}
// Place our HTML finishing Tags into our String ArrayList...
txt.add("</body>");
txt.add("</html>");
// Write the String ArrayList to our supplied Destination
// File Path...
try {
FileWriter fw = new FileWriter(destinationFilePath);
Writer output = new BufferedWriter(fw);
for (int i = 0; i < txt.size(); i++) {
// Some Windows applications (such as NotePad require
// the \r tag for a new line to actually be accomplished
// within a text file.
output.write(txt.get(i) + "\r\n");
}
output.close();
return true;
}
catch (IOException ex) {
JOptionPane.showMessageDialog(null,"CompileToWebPage() Method Error!\n\n"
+ "There was a problem writing the Compiled Web Text to file!\n"
+ "Ensure that permissions are properly set.\n\n" + ex.getMessage(),
"File Write Error", JOptionPane.ERROR_MESSAGE);
return false;
}
}
Well, I hope this has helped you somewhat or at the very least been entertaining.
The following program has the purpose of creating a directory,
folderforallofmyjavafiles.mkdir();
and making a file to go inside that directory,
File myfile = new File("C:\\Users\\username\\Desktop\\folderforallofmyjavafiles\\test.txt");
There are two problems though. One is that it says the directory is being created at the desktop, but when checking for the directory, it is not there. Also, when creating the file, I get the exception
ERROR: java.io.FileNotFoundException: folderforallofmyjavafiles\test.txt (The system cannot find the path specified)
Please help me resolve these issues, here is the full code:
package mypackage;
import java.io.*;
public class Createwriteaddopenread {
public static void main(String[] args) {
File folderforallofmyjavafiles = new File("C:\\Users\\username\\Desktop");
try {
folderforallofmyjavafiles.mkdir(); //Creates a directory (mkdirs makes a directory)
if (folderforallofmyjavafiles.isDirectory() == true) {
System.out.println("Folder created at " + "'" + folderforallofmyjavafiles.getPath() + "'");
}
} catch (Exception e) {
System.out.println("Not working...?");
}
File myfile = new File("C:\\Users\\username\\Desktop\\folderforallofmyjavafiles\\test.txt");
//I even tried this:
//File myfile = new File("folderforallofmyjavafiles/test.txt");
//write your name and age through the file
try {
PrintWriter output = new PrintWriter(myfile); //Going to write to myfile
//This may throw an exception, so I always need a try catch when writing to a file
output.println("myname");
output.println("myage");
output.close();
System.out.println("File created");
} catch (IOException e) {
System.out.printf("ERROR: %s\n", e); //e is the IOException
}
}
}
Thank you so much for helping me out, I really appreciate it.
:)
You're creating the Desktop folder in the C:\Users\username folder. If you check the return value of mkdir, you'd notice it's false because the folder already exists.
How would the system know that you want a folder named folderforallofmyjavafiles unless you tell it so?
So, you didn't create the folder, and then you try to create a file in the (nonexistent) folder, and Java tells you the folder doesn't exist.
Agreed that it's a bit obscure, using a FileNotFoundException, but the text does say "The system cannot find the path specified".
Update
You're probably confused about the variable name, so let me say this. The following are all the same:
File folderforallofmyjavafiles = new File("C:\\Users\\username\\Desktop");
folderforallofmyjavafiles.mkdir();
File x = new File("C:\\Users\\username\\Desktop");
x.mkdir();
File folderToCreate = new File("C:\\Users\\username\\Desktop");
folderToCreate.mkdir();
File gobbledygook = new File("C:\\Users\\username\\Desktop");
gobbledygook.mkdir();
new File("C:\\Users\\username\\Desktop").mkdir();
I've got a JComboBox filled with some java.io.File objects. By selecting one of these files in the ComboBox, I want to delete it either from the ComboBox and Filesystem.
Code snippet:
deleteButton.addActionListener(new ActionListener()
{
public void actionPerformed(ActionEvent e)
{
int dialogButton = JOptionPane.YES_NO_OPTION;
int dialogResult = JOptionPane.showConfirmDialog(null, "Are you sure?", "Warning", dialogButton);
if (dialogResult == JOptionPane.YES_OPTION)
{
Path path = Paths.get(mailingLists.getSelectedItem().toString());
mailingLists.removeItem(mailingLists.getSelectedItem());
try
{
Files.delete(path);
JOptionPane.showMessageDialog(null, "File deleted!", "SUCCESS", JOptionPane.INFORMATION_MESSAGE);
} catch (IOException e1)
{
JOptionPane.showMessageDialog(null, e1.toString(), "ERROR", JOptionPane.ERROR_MESSAGE);
e1.printStackTrace();
}
}
}
});
It gives this exception: java.nio.file.FileSystemException [...] file already in use this is because it's used by my application, then I thought first to remove it from the ComboBox and then delete it using Files.delete(path); but still have the exception.
What's wrong?
P.S.
Is the first time that I deal in this context so I guess if it's better to use File f = new File("path"); f.delete(); instead of Files.delete(path);.
EDIT: Provided more information about the JComboBox load.
Scratch:
LinkedList<File> listFolder = new LinkedList<File>();
listFolder.add(new File("mailinglists"));//<--- root folder
File[] stuffInFolder = listFolder.get(0).listFiles();
JComboBox<File> mailingLists = new JComboBox<File>(stuffInFolder);
Sounds like you need to close the file.
When you open a file the OS will prevent a file from being deleted until the connection to the file has been closed.
I would recommend, instead of JComboBox filled with some java.io.File objects use file names with path as String. And when you have to delete the file create an Object of File using the path and delete it.
Use Java.io.File.delete()
try
{
File f = new File(path);
if(f.delete())
JOptionPane.showMessageDialog(null, "File Deleted Succesfully!");
else
JOptionPane.showMessageDialog(null, "File couldn't be deleted!");
}
Solved!
I was using a "bugged" external library developed by a workmate. Its goal was to read a .properties file. Once readed, the file was still opened.
Fixed and everything works well now.