How to Perform MalformedURLException / 404 Not Found

585 Views Asked by At

How do I make my program return MalformedUrlException and not just a generic Exception?

I am making a simple function that reads a URL a user enters in the console and it returns the content from the URL. I need it to check if the URL is a valid URL or if it's not a working URL.

Example urls: http://google.com/not-found.html http:/google.com

I created two catch exceptions but it seems like the overall exception is always returned instead of MalformedUrlException.

    public static String getUrlContents(String theUrl) {
    String content = "";
    try {
        URL url = new URL(theUrl);
        //Create a url connection object 
        URLConnection urlConnection = url.openConnection();
        //wrap the url connection a buffered reader 
        BufferedReader bufferedReader = new BufferedReader(new InputStreamReader(urlConnection.getInputStream()));
        String line;
        while((line = bufferedReader.readLine()) != null) {
            content += line + "\n";
        }
        bufferedReader.close();
    } catch (MalformedURLException e) {
        System.out.println("The following url is invalid'" + theUrl + "'");
        //logging error should go here
    } catch (Exception e) {
        System.out.println("Something went wrong, try agian");
    }
    return content;
}
1

There are 1 best solutions below

0
whbogado On

First, java.net.MalformedURLException is not the case for a "not found" resource:

public class MalformedURLException extends IOException

Thrown to indicate that a malformed URL has occurred. Either no legal protocol could be found in a specification string or the string could not be parsed.

I understand that you want to catch a situation when the URL results in a not found return code (404). To do this you need to examine the HTTP response code.

The easiest way is to use java.net.HttpURLConnection:

https://docs.oracle.com/en/java/javase/11/docs/api/java.base/java/net/HttpURLConnection.html

public abstract class HttpURLConnection extends URLConnection

A URLConnection with support for HTTP-specific features. See the spec for details.

Each HttpURLConnection instance is used to make a single request but the underlying network connection to the HTTP server may be transparently shared by other instances. Calling the close() methods on the InputStream or OutputStream of an HttpURLConnection after a request may free network resources associated with this instance but has no effect on any shared persistent connection. Calling the disconnect() method may close the underlying socket if a persistent connection is otherwise idle at that time.

You can check the response code by calling getResponseCode(). If the result is less than 400, you got a valid response, otherwise there was a client error (4xx) or a server error (5xx).

Something like this:

public static String getUrlContents(String theUrl) {
    String content = "";
    try {
        URL url = new URL(theUrl);
        //Create a url connection object 
        URLConnection urlConnection = url.openConnection();
        if (urlConnection instanceof HttpURLConnection) {
            HttpURLConnection conn = (HttpURLConnection) urlConnection;
            if (conn.getResponseCode() < 400) {
                // read contents
            } else {
                System.out.println(conn.getResponseMessage());
                // treat the error as you like
            }
        } else {
            // not a HTTP connection, treat as you like
        }
    } catch (MalformedURLException e) {
        System.out.println("The following url is invalid'" + theUrl + "'");
        //logging error should go here
    } catch (Exception e) {
        System.out.println("Something went wrong, try agian");
    }
    return content;
}

I have not checked the code, but I think you can get the overall idea.