Java: custom-exception-error - java

$ javac TestExceptions.java
TestExceptions.java:11: cannot find symbol
symbol : class test
location: class TestExceptions
throw new TestExceptions.test("If you see me, exceptions work!");
^
1 error
Code
import java.util.*;
import java.io.*;
public class TestExceptions {
static void test(String message) throws java.lang.Error{
System.out.println(message);
}
public static void main(String[] args){
try {
// Why does it not access TestExceptions.test-method in the class?
throw new TestExceptions.test("If you see me, exceptions work!");
}catch(java.lang.Error a){
System.out.println("Working Status: " + a.getMessage() );
}
}
}

TestExceptions.test returns type void, so you cannot throw it. For this to work, it needs to return an object of a type that extends Throwable.
One example might be:
static Exception test(String message) {
return new Exception(message);
}
However, this isn't very clean. A better pattern would be to define a TestException class that extends Exception or RuntimeException or Throwable, and then just throw that.
class TestException extends Exception {
public TestException(String message) {
super(message);
}
}
// somewhere else
public static void main(String[] args) throws TestException{
try {
throw new TestException("If you see me, exceptions work!");
}catch(Exception a){
System.out.println("Working Status: " + a.getMessage() );
}
}
(Also note that all classes in package java.lang can be referenced by their class name rather than their fully-qualified name. That is, you don't need to write java.lang.)

Working Code
Try this:
public class TestExceptions extends Exception {
public TestExceptions( String s ) {
super(s);
}
public static void main(String[] args) throws TestExceptions{
try {
throw new TestExceptions("If you see me, exceptions work!");
}
catch( Exception a ) {
System.out.println("Working Status: " + a.getMessage() );
}
}
}
Problems
There are a number of issues with the code you posted, including:
Catching Error instead of Exception
Using a static method to construct the exception
Not extending Exception for your exception
Not calling the superclass constructor of Exception with the message
The posted code resolves those issues and displays what you were expecting.

Related

Handling a custom exception without changing the test class (java)

I need to throw a couple times a custom exception. A test class is checking if my solution works but I'm not allowed to make any changes to this class which leads me to my problem.
I simplified the problem here, because the whole code is not needed here
public class Test{
public static final String s = "0test";
#Test
public void testZero(){
Solver sol = new Solver(Parser.run(s));
//IntelliJ is underlining "run" because "Unhandled exception: ParseException", a
//simple solution could be adding "throws ParseException" in the head, but I'm not
//allowed to change the test class
}
}
public class Parser{
public static Pars run(String input) throws ParseException{
if(input.charAt(0) == '0'){
throw new ParseException("...");
}
}
}
public class ParseException extends Exception{
public ParseException(String mess){
super(mess);
}
}
I'm not allowed to make any changes to this class which leads me to my problem.
There is no way that you can throw an Exception to the Test class without catching it over there.
BUT you can prematurely just catch it inside the Parser#run(String input).
Instead of this:
public static Pars run(String input) throws ParseException{
if(input.charAt(0) == '0'){
throw new ParseException("...");
}
}
You could (as I said) catch it in the method instead.
public static Pars run(String input) {
try {
if(input.charAt(0) == '0'){
throw new ParseException("...");
}
} catch (ParseException e) {
// System.out.println(e.toString());
// Just handle it over here if you can't edit Test.java ...
}
}
I have found the solution for my problem.
In my ParseException class, I need to change it to:
public class ParseException extends IllegalArgumentException{...}
Further into the task, the test class didnt accept my exception because there was a IllegalArgumentException exspected.
Changing it into "extends IllegalArgumentException" solves the problem, so I dont need "throws ParseException" in the headings and no try,catch statements

Define an exception called "NO Match Exception" that is thrown when a string is not equal to "India"

In the problem I have to check whether a string is equal to "India" or not. If they are not equal then I have to throw an exception "No Match Exception"
I am creating a class nomatchexception and from constructor I am passing a string "America". Then I am checking whether it equals to "India" or not. If both are equal then printing "Matched" otherwise throwing the exception using throw.
class nomatchexception {
String s;
nomatchexception(String s) {
this.s = s;
if (s.equals("India")) {
System.out.print("Matched!\n");
} else {
throw new NoMatchException("Not Matched!\n");
}
}
}
class nomatchex {
public static void main(String[] a) {
nomatchexception v = new nomatchexception("America");
}
}
Error:
nomatchex.java:9: error: cannot find symbol
throw new NoMatchException("Not Matched!\n");
^
symbol: class NoMatchException
location: class nomatchexception
1 error
You have a class nomatchexception that raises your exception, but NoMatchException excepction class does not exist in your code and is not part of java.
It's required to create a class NoMatchException extending exception and with the proper overrides like:
class NoMatchException extends Exception {
public NoMatchException(String message){
super(message);
}
}
And now you are able to raise your NoMatchException exceptions.
Also for good coding is recommended to use the proper case and naming in the classes maybe your nomatchexception class must be calle IndiaAssertComparer or similar.
Complete example:
class NoMatchException extends Exception {
public NoMatchException(String message){
super(message);
}
}
class IndiaAssertComparer {
private String s;
IndiaAssertComparer(String s) throws NoMatchException {
this.s = s;
if (s.equals("India")) {
System.out.print("Matched!\n");
} else {
throw new NoMatchException("Not Matched!\n");
}
}
}
class NoMatcher {
public static void main(String[] a) throws NoMatchException {
IndiaAssertComparer v = new IndiaAssertComparer("America");
}
}
Create a user defined exception named “NoMatchException” that is fired when the string entered by the user is not “india”.
import java.util.Scanner;
class NoMatchException extends Exception{
String s1;
NoMatchException(String s2)
{
this.s1=s2;
}
public String toString()
{
return s1;
}
public static void main(String[] args) {
String s3;
Scanner sc=new Scanner(System.in);
System.out.println("Please enter a string");
s3=sc.nextLine();
try {
if(!"india".equalsIgnoreCase(s3))
throw new NoMatchException("NoMatch
Exceptioncaught!!!");
else {
System.out.println("String matched!!!");
}
}
catch(NoMatchException e) {
System.out.println(e);
}
}
}

Using jmockit to mock constructor that throws error: NoClassDefFoundError

Jmockit is very powerful, but sometimes I cannot understand what it does behind the scene, so I have a question regarding jmockit. Hopefully the more experienced programmers on here could help shine some light on this situation :)
I have the following two classes in two separate files:
public class SmallClass {
String a;
SmallClass(String arg) throws Exception {
a = arg;
}
public String getString() {
return a;
}
}
And
public class BigClass {
private static final SmallClass smallClass;
static {
try {
smallClass = new SmallClass("dummy");
} catch (Exception e) {
throw new IllegalStateException("Could not initialized", e);
}
}
public static String getString() {
return smallClass.getString();
}
}
Now, I have a class to test BigClass:
public class BigClassTest {
#Test
public void testGet() throws Exception {
///CLOVER:OFF
new MockUp<SmallClass>() {
#Mock
public void $init(String string) throws Exception {
//Do nothing
}
#Mock
public String getString() {
return "dummyString";
}
};
///CLOVER:ON
Assert.assertEquals("dummyString", BigClass.getString());
}
#Test(expected = ExceptionInInitializerError.class)
public void testException() throws Exception {
///CLOVER:OFF
new MockUp<SmallClass>() {
#Mock
public void $init(String string) throws Exception{
throw new Exception("Mocked Exception");
}
};
///CLOVER:ON
BigClass.getString();
}
}
If I run each of these independently, then they each passes. But if I run the whole test file, then the first test fails with:
java.lang.NoClassDefFoundError: Could not initialize class BigClass
I also tried tearing down the mock after each test like this, but it doesn't help:
public class BigClassTest {
MockUp<SmallClass> smallClassMockUp;
#Test
public void testGet() throws Exception {
///CLOVER:OFF
smallClassMockUp = new MockUp<SmallClass>() {
#Mock
public void $init(String string) throws Exception {
//Do nothing
}
#Mock
public String getString() {
return "dummyString";
}
};
///CLOVER:ON
Assert.assertEquals("dummyString", BigClass.getString());
smallClassMockUp.tearDown();
}
#Test(expected = ExceptionInInitializerError.class)
public void testException() throws Exception {
///CLOVER:OFF
smallClassMockUp = new MockUp<SmallClass>() {
#Mock
public void $init(String string) throws Exception{
throw new Exception("Mocked Exception");
}
};
///CLOVER:ON
BigClass.getString();
smallClassMockUp.tearDown();
}
}
Any help would be appreciated. Thank you in advance!
The occurrence of NoClassDefFoundError, in a case like this, is not because the class wasn't found by the JVM (it was), but because its static initialization has failed (by throwing an exception or error from the execution of a static initializer). Once this happens, the class is left in an invalid/uninitialized state and cannot be used in the same JVM instance anymore.
For reference, see the "Initialization of classes and interfaces" section in the JLS.
Also, note that the order in which tests execute is not necessarily the textual order they appear in the test class. Here, testException (the second test) runs first. So, when testGet runs, the class is invalid and the JVM throws the error.

Java program custom exception generates a compile error

I am trying to create a custom exception in Java, however, I get a compile error when I create the custom exception and try to use it. I have searched through this forum and did not provide much help, because I try to use similar code and it still does not fix the problem!
Here's the code:
class CoogieException extends Exception {
public int numCats;
public String msg;
public CoogieException() {
}
public CoogieException(String msg) {
super();
this.msg = msg;
}
public int getNumCats() {
return numCats;
}
}
and the main class -
public class Lab12 {
public int checkValue(int numCats) throws CoogieException {
if (numCats != (int) numCats) {
throw new CoogieException("Sorry, invalid entry");
} else {
return numCats;
}
}
public static void main(String[] args) {
CoogieException test = new CoogieException();
Scanner in = new Scanner(System.in);
System.out.println("Enter num of cats: ");
int numCats = in.nextInt();
try {
lb = new Lab12();
lb.checkValue(numCats);
} catch (CoogieException co) {
System.out.println("numCats is too many cats!!!!!");
}
}
}
FYI...
Lab12.java:27: error: incompatible types: CoogieException cannot be converted to Throwable
public int checkValue(int numCats) throws CoogieException {
^
Lab12.java:29: error: incompatible types: CoogieException cannot be converted to Throwable
throw new CoogieException("Sorry, invalid entry");
^
Lab12.java:119: error: incompatible types: CoogieException cannot be converted to Throwable
} catch (CoogieException co) {
Probably you have a class somewhere called Exception that doesn't extend java.lang.Exception (or implement Throwable). Also possible you have another class called CoogieException with the same problem.

TestNG expectedExceptions throws TestException

I am trying to test the following class:
package com.myclass;
public class MyClass {
private Map<String, String> dataMap = new HashMap<>();
public void extractInfoFromLine(String line) throws InvalidInputException {
String[] words = line.split(" ");
if (dataMap.containsKey(words[0])) {
throw new InvalidInputException();
}
dataMap.put(words[0], words[2]);
}
public void confirmInfoPresent(String name) {
// Do something
}
}
Using this TestNG class:
package com.myclass;
public class MyClassTest {
private MyClass myClass;
#DataProvider(name = "invalid-data-provider")
public Object[][] invalidDataProvider() {
return new Object[][] {
{ "A is B", "A"},
{ "A is D", "A"},
};
}
#BeforeTest()
public void setup() {
myClass = new MyClass();
}
#Test(dataProvider = "invalid-data-provider", expectedExceptions = InvalidInputException.class)
public void testExceptionalExtractValueForKey(String line, String name) throws InvalidInputException {
myClass.extractInfoFromLine(line);
myClass.confirmInfoPresent(name);
}
}
I have defined the following custom exception for this:
package com.myclass;
public class InvalidInputException extends Exception {
public InvalidInputException() {
super();
}
public InvalidInputException(String message) {
super(message);
}
public InvalidInputException(String message, Throwable cause) {
super(message, cause);
}
public InvalidInputException(Throwable cause) {
super(cause);
}
}
However, when I run this test case, I get the following error:
Expected exception com.myclass.InvalidInputException but got org.testng.TestException:
Method MyClassTest.testExceptionalExtractValueForKey(java.lang.String, java.lang.String)[pri:0, instance:com.myclass.MyClassTest#3930015a] should have thrown an exception of class com.myclass.InvalidInputException
I tried replacing my custom exception with a standard exception and still got the same result.
Can someone please help me with this?
#KarthickS, three different people gave you same answer already. I don't understand what else should be explained and how.
On the first #Test iteration dataMap is empty (dataMap.containsKey(words[0]) == false), so, the code inside "if" statement body will not be executed; which means that your exception will not be thrown.
TestNg will threat the test as failed since there is "expectedExceptions" attribute set in your #Test annotation. The second test iteration will pass since dataMap is not empty anymore (dataMap.put(words[0], words[2]) - you've added data on the first run).
Once again, TestNg doc says about "expectedExceptions": The list of exceptions that a test method is expected to throw. If no exception or a different than one on this list is thrown, this test will be marked a failure.

Categories