NPE Regression in JWKSet.parse

Issue #557 resolved
rosshellings+trello@gmail.com created an issue

JWKSet.parse has the following method signature:

    public static JWKSet parse(final String s)
        throws ParseException {

However, if we provide a null string the method now throws a NullPointerException instead of the expected ParseException.

This appears to be a regression, and null values used to return a ParseException. The functionality seems to have broken in version 9.24 onwards.

Test that passed in 9.23, but fails in 9.24 (and 9.39.3):

    @Test(expected = ParseException.class)
    public void showThrowParseExceptionWithNullString() throws ParseException {
        final String nullString = null;
        JWKSet.parse(nullString);
    }

Exception thrown:

java.lang.Exception: Unexpected exception, expected<java.text.ParseException> but was<java.lang.NullPointerException>
Caused by: java.lang.NullPointerException: Cannot invoke "java.util.Map.get(Object)" because "o" is null
    at com.nimbusds.jose.util.JSONObjectUtils.getGeneric(JSONObjectUtils.java:161)
    at com.nimbusds.jose.util.JSONObjectUtils.getJSONArray(JSONObjectUtils.java:357)
    at com.nimbusds.jose.jwk.JWKSet.parse(JWKSet.java:369)
    at com.nimbusds.jose.jwk.JWKSet.parse(JWKSet.java:351)

Comments (7)

  1. Yavor Vasilev

    JSON object parsed by com.nimbusds.jose.util.JSONObjectUtils#parse(java.lang.String, int)

    In 9.23 we parsed with JSON Smart:

        public static Map<String, Object> parse(final String s, final int sizeLimit)
            throws ParseException {
    
            if (sizeLimit >= 0 && s.length() > sizeLimit) {
                throw new ParseException("The parsed string is longer than the max accepted size of " + sizeLimit + " characters", 0);
            }
    
            Object o;
            try {
                o = new JSONParser(JSONParser.USE_HI_PRECISION_FLOAT | JSONParser.ACCEPT_TAILLING_SPACE).parse(s);
            } catch (net.minidev.json.parser.ParseException e) {
                throw new ParseException("Invalid JSON: " + e.getMessage(), 0);
            } catch (Exception e) {
                throw new ParseException("Unexpected exception: " + e.getMessage(), 0); <--- NPE handled hereIn 
            } catch (StackOverflowError e) {
                throw new ParseException("Excessive JSON object and / or array nesting", 0);
            }
    
            if (o instanceof JSONObject) {
                return (JSONObject)o;
            } else {
                throw new ParseException("JSON entity is not an object", 0);
            }
        }
    

    In 9.41 we have GSON:

    public static Map<String, Object> parse(final String s, final int sizeLimit)
            throws ParseException {
    
            if (s.trim().isEmpty()) {
                throw new ParseException("Invalid JSON object", 0);
            }
    
            if (sizeLimit >= 0 && s.length() > sizeLimit) {
                throw new ParseException("The parsed string is longer than the max accepted size of " + sizeLimit + " characters", 0);
            }
    
            Type mapType = TypeToken.getParameterized(Map.class, String.class, Object.class).getType();
    
            try {
                return GSON.fromJson(s, mapType);
            } catch (Exception e) {
                throw new ParseException("Invalid JSON: " + e.getMessage(), 0);
            } catch (StackOverflowError e) {
                throw new ParseException("Excessive JSON object and / or array nesting", 0);
            }
        }
    

  2. rosshellings+trello@gmail.com reporter

    Thanks Yavor, thats fantastic. I have pulled down that latest version and the issue looks resolved to me. Thanks for your help!

  3. Log in to comment