stanfordnlp/CoreNLP · error · IllegalArgumentException

Unclosed paren in encoded map: " + encoded

Error message

Unclosed paren in encoded map: " + encoded

What it means

StringUtils' encoded-map decoder accepts maps wrapped in parentheses, brackets, or braces. If the string starts with '(' the decoder strips one character from each end and requires the final character to be ')'. A mismatch means the encoded map is unbalanced and the decoder throws IllegalArgumentException.

Solutions

  1. Append the closing ')' to the encoded map string
  2. Fix the generator to emit matching open/close delimiters
  3. Trim trailing whitespace or stray characters before decoding
  4. Catch IllegalArgumentException and validate user-supplied map strings

Example fix

// before
StringUtils.decodeMap("(a->1, b->2");
// after
StringUtils.decodeMap("(a->1, b->2)");
Defensive patterns

Strategy: validation

Validate before calling

if (s != null && s.startsWith("(") && !s.endsWith(")")) throw new IllegalArgumentException("Encoded map must end with ')': " + s);

Type guard

static boolean isParenClosed(String s) { return s != null && s.length() >= 2 && s.charAt(0)=='(' && s.charAt(s.length()-1)==')'; }

Try / catch

try { map = StringUtils.decodeMap(encoded); } catch (IllegalArgumentException e) { log.error("Malformed encoded map: " + encoded, e); throw e; }

Prevention

When it happens

Trigger: Calling the public StringUtils map-decode method with a string starting with '(' whose last character is not ')' (e.g. "(key->value", "(k:v]").

Common situations: Hand-written map strings in config/properties-style files with a missing closer; programmatic builders emitting mismatched delimiters; truncation by copy-paste or log capture.

Understand the failure class

Background: "Invalid ... format", "must be in format X", "does not look like a ..." — invalid argument format errors across CLI tools and libraries — this error's family across 17 libraries.

Related errors


AI-assisted analysis of stanfordnlp/CoreNLP@1b7edd19c4 (2026-09-10). Data as JSON: /api/errors/96d051c139169ede. Report an issue: GitHub.

Appendix: source

Thrown at src/edu/stanford/nlp/util/StringUtils.java:2630

   *
   * @param encoded The String encoded map
   * @return A String map corresponding to the encoded map
   */
  public static Map<String, String> decodeMap(String encoded){
    if (encoded.isEmpty()) return new HashMap<>();
    char[] chars = encoded.trim().toCharArray();

    //--Parse the String
    //(state)
    char quoteCloseChar = (char) 0;
    Map<String, String> map = new HashMap<>();
    String key = "";
    String value = "";
    boolean onKey = true;
    StringBuilder current = new StringBuilder();
    //(start/stop overhead)
    int start = 0; int end = chars.length;
    if(chars[0] == '('){ start += 1; end -= 1; if(chars[end] != ')') throw new IllegalArgumentException("Unclosed paren in encoded map: " + encoded); }
    if(chars[0] == '['){ start += 1; end -= 1; if(chars[end] != ']') throw new IllegalArgumentException("Unclosed bracket in encoded map: " + encoded); }
    if(chars[0] == '{'){ start += 1; end -= 1; if(chars[end] != '}') throw new IllegalArgumentException("Unclosed bracket in encoded map: " + encoded); }
    //(finite state automata)
    for(int i=start; i<end; i++){
      if (chars[i] == '\r') {
        // Ignore funny windows carriage return
        continue;
      } else if(quoteCloseChar != 0){
        //(case: in quotes)
        if(chars[i] == quoteCloseChar){
          quoteCloseChar = (char) 0;
        }else{
          current.append(chars[i]);
        }
      } else if(chars[i] == '\\'){
        //(case: escaped character)
        if(i == chars.length - 1) {
          throw new IllegalArgumentException("Last character of encoded pair is escape character: " + encoded);

View on GitHub (pinned to 1b7edd19c4)