Getting the contents of a class file in Android - java

The problem I am facing is that I need to access the contents of a .class file inside my application to send it to another device. (This class is not known by the target device at compilation time so I cannot just send an instance as it will ClassNotFoundException me).
I have successfully solved this with two PC devices by sending the byte array of the class file, but I cannot seem to get the path to the class file in Android. I guess because they are actually inside the classes.dex file. Is there any way to access these .class files inside classes.dex?
This is the code I use to get the class file contents in a PC
try {
this.className = c.getName();
String pathToClass = c.getName().replaceAll("\\.", File.separator) + ".class";
InputStream is = c.getClassLoader().getResourceAsStream(pathToClass);
this.classContents = IOUtils.toByteArray(is);
} catch (IOException e) {
e.printStackTrace();
}
Thank you for your cooperation.

Related

Java throws java.nio.file.NoSuchFileException, but file exists

I'm running a Spring REST application inside a docker container. I have a function inside a Spring controller for saving images and a function for reading them. The function for saving works properly but I have an issue with the function for reading them:
public byte[] getByteArray(String fileName) {
try {
File f = new File("/upload/" + fileName);
return Files.readAllBytes(f.toPath());
} catch (IOException e) {
e.printStackTrace(); // this is for testing
return null;
}
}
However after I use the above function I get this error java.nio.file.NoSuchFileException: /upload/test.png. I checked and this file exists in this directory. What could be the reason Java can't see this file?
Most likely your /upload directory is not accessible to the java process. directories have access rights, an owner, and a group. There is one set of rights for the owner, one for the group, and one for the rest.

java.nio.file.NoSuchFileException When File.transferTo() is called

I've recently inherited a Java API and am having trouble with file uploads. Unfortunately, Java isn't a language I have much experience in so I'm a bit stumped by this.
The MultiPartFile is being received ok, and I can find the file in the temp directory, but when I try to use File.transferTo() to create the final file I just get the below error;
java.nio.file.NoSuchFileException: C:\Users\myUser\AppData\Local\Temp\undertow3706399294849267898upload -> S:\Dev\PolicyData\Temp.xlsx
As I mentioned the temp undertow file exists, and the directory on the S drive also exist, (but there's no Temp.xlsx as my understanding is this should be created by transferTo()). Any solutions I've found to this problem so far are resolved using absolute file paths.
This is a simplified version of the code but the error remains the same.
SpringBoot framework is "1.5.3.RELEASE", running Java 1.8.0_131
ResponseEntity handleFileUpload(#RequestPart(name = "file") MultipartFile file, #PathVariable Long stageFileTypeId) {
if (!file.isEmpty()) {
try {
String filePath = "S:\\Dev\\PolicyData\\Temp.xlsx";
log.info("Upload Path = {}", filePath);
File dest = new File(filePath);
file.transferTo(dest);
return ResponseUtil.wrapOrNotFound(Optional.ofNullable(filePath));
}
catch (Exception ex) {
log.error("An error has occurred uploading the file", ex);
return ResponseEntity.status(HttpStatus.INTERNAL_SERVER_ERROR).build();
}
}
else {
log.error("An error has occurred, no file was received");
return ResponseEntity.status(HttpStatus.INTERNAL_SERVER_ERROR).build();
}
}
If you need any more information please let me know.
Thanks,
Neil
The API for MultipartFile is a bit tricky. The transferTo(File) method javadoc states that (bold are mine):
This may either move the file in the filesystem, copy the file in the
filesystem, or save memory-held contents to the destination file. If
the destination file already exists, it will be deleted first.
If the target file has been moved in the filesystem, this operation
cannot be invoked again afterwards. Therefore, call this method just
once in order to work with any storage mechanism.
It seems that the Undertow implementantion already called it to move the in-memory uploaded file to "C:\Users\myUser\AppData\Loca\Temp\undertow3706399294849267898upload" so another transferTo is failing.
I came across the same problem using javax.servlet.http.Part in a Wildfly containter with Undertow.
If you are using Spring framework >= 5.1, you could try the Multipart.transferTo(Path) method, using dest.toPath()
Or you can copy from the inputStream, with something like this:
try (InputStream is = multipartFile.getInputStream()) {
Files.copy(is, dest.toPath());
}

Reading from A json file, FileNotFoundException

I'm working on a simple app and im trying to understand how to read from a json file using a json parser. I wrote a simple json file and put it in one of my directories. Then I used right clock to get the path, and wrote the following code:
public void myParser() {
JSONParser parser = new JSONParser();
String path = "C:\\Users\\My Name\\IntelliJIDEAProjects\\Intereview\\app\\src\\main\\res\\Data\\dataStructures.json";
try{
JSONArray topics = (JSONArray)parser.parse(new FileReader(path));
for(int i=0;i<topics.length();i++) {
JSONObject object = topics.getJSONObject(i);
String title = object.optString("title").toString();
Log.i(TAG,title);
}
}
catch(JSONException e) {
Log.e("Internal Problem", e.getMessage());
} catch (ParseException e) {
e.printStackTrace();
} catch (FileNotFoundException e) {
e.printStackTrace();
} catch (IOException e) {
e.printStackTrace();
}
}
from some reason, i get this error when running the app:
java.io.FileNotFoundException: C:\Users\My Name\IntelliJIDEAProjects\Intereview\app\src\main\res\Data\dataStructures.json: open failed: ENOENT (No such file or directory)
what could be the reason behind that? i've been working on this for the past few hours and I just can't figure it out..
Thanks
You have android on this question, so I assume that you are trying to write an Android app. If so, this will not work:
String path = "C:\\Users\\My Name\\IntelliJIDEAProjects\\Intereview\\app\\src\\main\\res\\Data\\dataStructures.json";
My guess, based on that path, is that you are trying to package a JSON file with your app. In that case, you cannot create random directories under res/ either. Even if this JSON file were in a proper res/ directory (e.g., res/raw/), you cannot access it via a FileReader. It is a file on your development machine. It is not a file on the Android device.
Your two main options are:
Move that JSON file from res/Data/ into res/raw/. Then, use getResources().openRawResource(R.raw.dataStructures) to get an InputStream on the JSON.
Move that JSON file from res/Data/ into assets/. Then, use getAssets().open("dataStructures.json") to get an InputStream on the JSON.
Note that getResources() and getAssets() are methods on Context and its subclasses, such as Activity.
This appears when the file isn't there...
Check the spelling of your pathname (intereview?) and... check if the file is there.
you need to put json inside the assets folder.
In the perspective window open the Project Perspective.
Create the directory inside your android_test/test folder with name assets depending upon where you need the JSON response
Now simple put your JSON file inside the assets folder
And call your JSON by simply calling their single name like xyz.json

Java copying files to a new path doesn´t work

I have another question. Right now I am writing a little program, which runs on my pc and on my laptop. These two programs communicate with each other. I can write Strings (like a chat) and I want to send files. This little chat works, but the files are making problems right now. Which makes me a little bit wondering, because I got it already running some days ago. But now it isn't working (can't remember that I changed important things). Unfortunately I cant undo because Eclipse was already closed.
So I was looking for the mistake but I couldn't find it since hours. I hope you can help me.
Situation:
I choose a file at my pc/laptop and send it to my laptop/pc (I send the text [Strings] on the same way as the files and it works). The receiver shall save the file at a directory (targetPath - it is defined somewhere else in the code. It is a folder on my desktop). So I get the file as an Object from a "ObjectInputStream" and cast it as a "File":
if(msg instanceof File){ //msg is the object I got from the ObjectInputStream
//its a file
model.copyFileTo((File) msg);
}
this is the method which makes trouble:
public void copyFileTo(File file) throws IOException{
System.out.println(file.getName());//this is just a test and it works. It prints out the name of the sended file
if(targetPath.toFile().exists()){
if(file.exists()){
Path temp = Paths.get(targetPath+"/"+file.getName());
if(!temp.toFile().exists()){
Files.copy( file.toPath(), temp, StandardCopyOption.REPLACE_EXISTING);
System.out.println("copied");
}else{
System.out.println("File already exists");
}
}else{
System.out.println("File doesnt exists");
}
}else{
System.out.println("targetPath doesnt exists!");
}
}
I do not become an error, but it prints "File doesn't exists", so something at "if(file.exists())" goes wrong. If I cut this part out the program hangs up at Files.copy(...), which I know because it doesn't print out "copied".
On the source system, you'd do something like this (Java 7):
Path path = Paths.get("C:\\MyFolder", "MyFile.bin");
byte[] fileContent = Files.readAllBytes(path);
// send fileContent to target system
On the target system, you'd do:
// receive fileContent from source system
Path path = Paths.get("C:\\Where\\To\\Store\\File", "MyFile.bin");
Files.write(path, fileContent);
In Java 6 or lower, you'd use a File object instead of the Path object and copy bytes yourself.
I followed the advice of Andreas
On the source system, you'd do something like this (Java 7):
Path path = Paths.get("C:\\MyFolder", "MyFile.bin");
byte[] fileContent = Files.readAllBytes(path);
// send fileContent to target system
On the target system, you'd do:
Path path = Paths.get("C:\\Where\\To\\Store\\File", "MyFile.bin");
Files.write(path, fileContent);
In Java 6 or lower, you'd use a File object instead of the Path object and copy bytes yourself.
I just want to write down my code for other people:
This part is called when i recived an input:
if(msg instanceof Message){// Message is a self made class wich contains the byte[] as an object and the File/Path as an Object #
model.copyFileTo((byte[]) ((ChatMessage)msg).getMessage(), (File)((ChatMessage)msg).getName());
}
the method:
public void copyFileTo(byte[] bytes, File file) throws IOException{
if(targetPath.toFile().exists()){
Path temp = Paths.get(targetPath+"/"+file.getName());
if(!temp.toFile().exists()){
Files.write(temp, bytes);
System.out.println("Wurde kopiert");
}else{
System.out.println("File already exists");
}
}else{
System.out.println("targetPath doesnt exists!");
}
}
Thanks to Andreas.

Sound will not play in JAR file

I have a problem and I hope you can help me.
Some talk about what I am doing so you know what's going on: So at the moment I'm trying to program a litte piece of software which can play me some music files (mp3 files to be exact, so i'm using the jLayer API). I'm working with Netbeans and I have succesfully imported a music file in the project. If I build my program and open the resulting JAR file with an archive program, I can find my music file in there. My function which I'm using goes like this:
public static String play(String file) {
File test = new File(file);
try {
FileInputStream in = new FileInputStream(test);
Player pl = new Player(in);
pl.play();
return "success";
}
catch (Exception e) {
return e.toString();
}
}
As you can see I'm getting a String with the Path Name and refactor him so I can play the file. I'm calling the function with the following code (the music file is saved in the ressources package):
MP3.play(getClass().getResource("/ressources/angel.mp3").getPath())
So if I start the programm via Netbeans everything works perfectly fine. But if I create a JAR file and start the program nothing happens. The Exception getting is the following:
java.io.FileNotFoundException: file:\C:\Users\Raphael\Documents\NetBeansProjects\MP3\dist\MP3.jar!\ressources\angel.mp3
It says the File does not exist but if I check my JAR the file is there......
Another strange thing I found out is the following: If I use the following function to play the music file:
public static String play(InputStream test) {
try {
Player pl = new Player(test);
pl.play();
return "success";
}
catch (Exception e) {
return e.toString();
}
}
and call the function with the following argument:
MP3.play(getClass().getResourceAsStream("/ressources/angel.mp3"));
Everything works fine in both Netbeans and the final JAR. Can anybody explain me what I'm doing wrong and only the second function works in the JAR version?
It would be really nice if you could help me in this matter.
Greetings,
xXKnightRiderXx
I am assuming that you have 2 packages 1 is src where your .java files is located and other is resources where your sound files is located
So i suggest you to use
MP3.play(getClass().getResourceAsStream("/angel.mp3"));
Because GetResource() automatically finds the resource package

Categories