try{
WebElement naimi_logo = firefox.findElement(By.xpath("//a[#href=\"/astana/\"]/img") ) ;
naimi_logo.click();
}catch( IllegalStateException e){
throw new IllegalStateException("this image is not clickable!") ;
}
catch(NoSuchElementException e){
throw new NoSuchElementException("logo is not found!!") ;
}
Should I really throw exception in my catch block? Or is it better to just print what happened to console?
Does the order of the catches matter?
It looks like your intent is to add more information when an exception occurs. In that case what you are doing is fine. However you will lose complete stack trace for the underlying exception.
You can use:
java.lang.RuntimeException.RuntimeException(String, Throwable)
If you don't want to lose the stack trace of original exception.
Can I throw exception again when I catch it?
To just rethrow the exception you do
throw e;
On the other hand this is equivalent of not catching the exception at all and let it propagate.
Perhaps you want to give the exception a better message, but keep the exception class. You would then typically do:
}catch( IllegalStateException e){
throw new IllegalStateException("this image is not clickable!", e);
}
catch(NoSuchElementException e){
throw new NoSuchElementException("logo is not found!!", e);
}
Should I really throw exception in my catch block?
This depends on what your method is intended to do. Your options are basically
Catch and handle the exception gracefully. Your method can complete normally even in case of an "internal" exception.
Catch the exception and wrap it in another exception more suitable for your level of abstraction.
Let the exception propagate.
Related
I am learning how to create file and directory in java using this code.
On the ERROR LINE I am getting error as "IOException is never thrown in this block".
So how do I know which function is throwing what type of Exception?
Or if I am not sure I should use generic Exception in every catch block.
public class FileTest {
public static void main(String[] args) {
//file creation
boolean flag = false;
File file = new File("/IdeaProjects/JavaCode/jstest.txt");
try {
flag = file.createNewFile();
}catch (IOException e){
e.printStackTrace();
}
System.out.println("file path is : " + file.getPath());
//dir creation
boolean dirFlag = false;
File fileDir = new File("/IdeaProjects/JavaCode/js");
try{
dirFlag = fileDir.mkdir();
}catch (IOException e){//ERROR LINE
e.printStackTrace();
}
if(dirFlag)
System.out.println("created");
else
System.out.println("exist");
}
}
The java.io.File#mkdir method only declares to throw SecurityException - see API.
java.lang.SecurityException is a RuntimeException and doesn't require being caught, although you may want to, depending on the context (again, see API).
Catching general java.lang.Exception in every catch block is absolutely not a recommended practice, although you may sometimes have to (not in your present case though).
See here for some SO literature on the matter.
Remember what methods throw exceptions and which exceptions they are.
Check the documentation if you think a method may throw an exception.
Just attempt to compile the code and fix the errors the compiler throws (They will tell you what exceptions are thrown by what method if the try-catch block is missing).
The method in question (File.mkdir()) throws a SecurityException which doesn't need to be caught (you can if need be) as it is an unchecked RuntimeException.
java.io.File: https://docs.oracle.com/javase/7/docs/api/java/io/File.html#mkdir()
SecurityException: https://docs.oracle.com/javase/7/docs/api/java/lang/SecurityException.html
Quoting JLS Section 11.2:
It is a compile-time error if a catch clause can catch checked exception class E1 and it is not the case that the try block corresponding to the catch clause can throw a checked exception class that is a subclass or superclass of E1, unless E1 is Exception or a superclass of Exception.
If no method you invoke in the try block declares that it throws IOException (and you don't throw new IOException(..) directly either), it is a compile-time error if you try to catch an IOException.
In GraphicsFileNotFoundException.java all I have is an import of FileNotFoundException and the class GraphicsFileNotFoundException which extends FileNotFoundException.
In my main java file, I'm trying to read in a graphics file with the method getGraphicsFile which throws GraphicsFileNotFoundException.
My brain is pooped after a good 40 minutes trying to find out how to catch this exception. I've tried using a try-catch block and catching GraphicsFileNotFoundException but I still get the error
unreported exception GraphicsFileNotFoundException ; must be caught
or declared to be thrown.
public void getGraphicsFile(String fileName) throws GraphicsFileNotFoundException {
String graphics = "";
Scanner getGraphics = null;
try {
getGraphics = new Scanner(new File(fileName));
}
catch (GraphicsFileNotFoundException e){
System.out.println("Error! File can't be found :/");
}
You need to either properly extend the FileNotFoundException class or manually throw an exception inside your try block.
Assuming this is for an assignment (I'm not sure why else you'd need to specifically extend this exception) you'll need to take another look at your GraphicsFileNotFoundException class and make sure that it does what it needs to.
To throw an exception, simply write your condition and the throw statement:
if(needToThrow) {
throw new GraphicsFileNotFoundException();
}
To catch an exception, surround the throw statement with a try block immediately followed by a catch block.
try {
// code here
if(needToThrow) {
throw new GraphicsFileNotFoundException();
}
}
catch(GraphicsFileNotFoundException e) {
// handle the error (print stack trace or error message for example)
e.printStackTrace(); // this is printing the stack trace
}
I recommend using Eclipse if you aren't already because many times it will offer to surround throw statements that need to be caught with a automatically generated try catch block.
I have a method that throws an Exception, which calls a method which throws an Exception, etc etc. So several methods that "throw Exception" are daisy-chained.
The first method that calls the submethod, puts that submethod in a try-catch block that catches any Exception that gets thrown inside that call. IN THEORY. In practice, no Exception is being caught by that try-catch block. Is there a way to remedy that?
Here is the code:
try {
CSVSingleton.tryToReadBothFiles(FILE1_PATH, FILE2_PATH);
} catch (Exception e) { // THIS BLOCK NEVER GETS ENTERED BY THE PATH O EXECUTION
System.out.println("There was an exception reading from at least one of the files. Exiting.");
System.exit(0);
}
here is the method from the CSVSingleton class:
public static void tryToReadBothFiles(String filePath1, String filePath2) throws Exception {
file1 = new CSVFileForDwellTime1(filePath1);
file2 = new CSVFileForDwellTime2(filePath2);
}
And here is code from the CSVFileForDwellTime1 class:
public CSVFileForDwellTime1(String filePath) throws Exception {
super(filePath);
}
and then here is the code that actually throws an original FileNotFoundException:
public GenericCSVFile(String filePath) throws Exception{
this.filePath = filePath;
try {
fileReader = new FileReader(filePath);
csvReader = new CSVReader(
fileReader);
header = getActualHeaderNames();
} catch (FileNotFoundException e) {
System.out.println("Could not read file with name: " + filePath);
// e.printStackTrace();
}
}
My guess is that the FileNotFoundException in the last method is caught by the catch block and so doesn't "bubble up". But is there a way to force it to bubble up?
Immediate answer:
Your thought is exactly right,
try {
fileReader = new FileReader(filePath);
csvReader = new CSVReader(
fileReader);
header = getActualHeaderNames();
} catch (FileNotFoundException e) {
System.out.println("Could not read file with name: " + filePath);
// e.printStackTrace();
}
This suppresses the exception
Either remove the try-catch block (desired unless you can actually do something with the exception)or re-throw it within the catch block.
Explanation
Generally with checked exceptions like this you have 2 options
Catch the exception and do something to remedy the exception
Throw the exception to the caller
What you have done here falls into the 1st category except that you have not done anything useful in the catch block (printing to console is rarely useful in this case because the exception message itself normally has enough information to see what has gone wrong)
The 2nd category is achieved either by not using a try-catch block and thus adding throws FileNotFoundException to the method signature. Alternatively explicitly throw the exception that you caught using:
catch(FileNotFoundException e)
{
//do something
throw e;
}
however in this case if do something isn't worthwhile you have unnecessarily caught something just to throw it on.
You can think of it like this:
Alice throws a ball to Charlie
Bob intercepts the ball
Bob then looks at the ball and then throws it to Charlie
Bonus Points
When you know the exception that could occur make sure to actually catch or throw that exception and not a parent of that exception.
Take the following method signatures for example:
public String method1() throws Exception
public String method2() throws FileNotFoundException
Here method2 clearly tells the caller what could happen and can help then figure out why the exception is being called (without having to read through the code or experience the error).
Secondly other exceptions can occur and you are potentially catching the wrong exception, take the following example:
try{
fileReader = new FileReader(filePath); //could potentially throw FileNotFoundException
fileReader = null; //woops
csvReader = new CSVReader(fileReader); //throws NullPointerException but the compiler will not know this
//....other stuff....//
}
catch(Exception e){
// the compiler told me that a FileNotFoundException can occur so i assume that is the reason the catch has executed
System.err.println("You have entered an invalid filename");
//doing anything here that would fix a FileNotFoundException is pointless because that is not the exception that occured
}
Use a throw in the catch clause.
} catch (FileNotFoundException e) {
System.out.println("Could not read file with name: " + filePath);
// Continue up, Mr. Exception!
throw e;
}
Alternatively, wrap the exception as appropriate (since an IOException is checked this handy here) - this is called a Chained Exception. Then, depending on what is thrown, the throws Exception can be removed from the method signature.
throw new RuntimeException("Could not read file: " + filePath, e);
If you don't want to catch it, then don't. Alternatively, you can just throw it again with a throw-statement. You can also throw a new Exception of any class you like. You should only catch an Exception at a level where you can react to it properly. As you found out, catching it at that low level is not helpful, so do not catch it there.
You can rethrow the exception once you catch it, for callees further up the stack to handle. You can change what exception it is too if a new type of exception makes more sense at a higher level.
catch (SomeSpecificException e)
{
some code here
throw new AMoreBroadException("I really need the callee to handle this too");
}
Technically you just need to add throw e right after System.out.println("Could not read file with name: " + filePath); and the exception will propagate up to the first method.
However, this would not be a clean way to handle the exception, because in this case all you'd be doing is printing an error message at the cost of changing the location of the original FileNotFoundException. Ideally, when you need to inspect an exception stacktrace, you expect a line of code throwing an exception to be the actual line that really caused the exception.
The throws Exception in the method declaration should be considered part of the contract of the method, i.e. it describes a possible behavior of the method. You should always ask yourself: Does it make sense for a FileNotFoundException to be specified as a possible exceptional behavior for the method/constructor I'm writing? In other words, do I want to make the caller of my method aware of this exception and leave it to the caller to deal with it? If the answer is yes (and in this case I would say it makes sense), then avoid wrapping the code in a try-catch block. If no, then your catch block should be responsible for dealing with the exception itself. In this specific example IMO there is not much you can do in the catch statement, so just remove the try-catch.
As mentioned by others, you should declare the most specific exception in the method signature (throws FileNotFoundException instead of throws Exception).
Does it make sense to throw exception from catch block just to log the message so that we are sure that what is causing the exception?
Code
public void saveLogs(Logs logs) throws RemoteException
{
try
{
LogsOps.saveLogs(logs);
}
catch (RemoteException e)
{
log.info("RemoteException is thrown while trying to save logs ", e);
throw new RemoteException("RemoteException caused while trying to save", e);
}
}
In response to one of the comments below that this method would throw StackOverFlow Exception, here the actual implementation of log.info which just displays those errors.
/** Log the message and the exception with a level of INFO.
* #param message - The message text.
* #param t - An exception to display.
*/
public void info(Object message, Throwable t)
{
String nullSafeMessage = (message != null) ? message.toString() : t.getClass().getSimpleName();
log.info(nullSafeMessage, t);
}
So there never would be Stackoverflow exception thrown.
It depends on what's going to catch the exception higher up. If nothing else is going to log the message, then sure, it makes sense - although I'd probably rethrow the original exception instead of creating a new one:
catch (RemoteException e)
{
log.info("RemoteException is thrown while trying to save logs ", e);
throw e;
}
Ideally, though, you'd have a single catch block higher up the stack, which would log appropriately - if you're just logging the exception, that can get all the information anyway.
It may make sense to catch/log/rethrow when you want to log information which isn't present in the exception, such as parameter values.
Presuming that you will eventually handle the propagated exception, this tactic of catch-log-rethrow just clutters up the log file. Imagine that this is done the entire way up the stacktrace - you end up with reams of redundant error information that serves no useful purpose.
If you are not handling the exception you shouldn't log it either.
Besides for logging, this approach may also be used to perform necessary cleanup in case of a failure before returning control to a caller further up the stack.
For example
InputStream is = new InputStream( ... )
try {
is.read(...);
return is;
} catch ( IOException ioe ) {
is.close();
throw ioe;
}
This is, of course, a somewhat special use which can be avoided elegantly most of the time by using a finally clause - but not always, as the case above demonstrates.
I am doing an app for finding BPM in Android. Based on the input of the file null pointer exception and IO exception is getting thrown. When the exception occurs the program is terminated, even if I surround the code with a try/catch block. My requirement is that the program not terminate, and continue to the other parts.
My Code:
try {
mp3file.seekMP3Frame();
sourcefile = new File("/sdcard/a.mp3");
mp3file = new MP3File(sourcefile);
AbstractID3v2 tag = mp3file.getID3v2Tag();
text=tag.getFrame("TBPM").toString();
}
catch (NullPointerException e) {
System.out.println("null pointer exception");
}
catch (IOException e1) {
System.out.println("IO exception");
}
........ // other coding
If the error occurs between the try - catch block :
You are only catching 2 exceptions here (NullPointerException and IOException).
Any other runtime exception between the try - catch block can still cause your program to crash. catch java.lang.Throwable to ensure all exceptions are catched.
If the error doesn't occur between the try - catch block :
Look in the stacktrace for the line in your class where the error occurs, and implement "proper" error handling there.
If your application crashes, you'll always see a stacktrace in logcat. That stacktrace will be able to tell you what line of code is causing the crash.
Use finally block in your code which is like
`try{
} catch{
} finally{
}`
finally will execute even if your try block throws exception or even if it doesn't.