Languages
[Edit]
EN

Java Jsoup - FIX for exception com.fasterxml.jackson.core.io.JsonEOFException: Unexpected end-of-input in field name at [Source: java.io.StringReader@1725dc0f; line: 1, column: 1046939]

7 points
Created by:
Huzaifa-Ball
475

1. Problem description

Code reproduction to get exception, json from my spring controller backend is quite big about 30 MB

import com.fasterxml.jackson.core.JsonFactory;
import com.fasterxml.jackson.databind.JsonNode;
import com.fasterxml.jackson.databind.ObjectMapper;
import org.jsoup.Connection;
import org.jsoup.Jsoup;

import java.io.IOException;

public class JsoupHttpGetApp {

    public static void main(String[] args) throws IOException {

        String jsonBodyStr;
        try {
            jsonBodyStr = Jsoup.connect("http://localhost:8080/get-all-users")
                    .followRedirects(true)
                    .ignoreHttpErrors(true)
                    .userAgent("Mozilla/5.0 AppleWebKit/537.36 (KHTML," +
                            " like Gecko) Chrome/45.0.2454.4 Safari/537.36")
                    .method(Connection.Method.GET)
                    .timeout(10_000)
                    .ignoreContentType(true)
                    .execute()
                    .body();
        } catch (IOException e) {
            throw new RuntimeException(e);
        }

        JsonNode rootNode = new ObjectMapper(new JsonFactory())
                .readTree(jsonBodyStr);

        System.out.println(rootNode);
    }
}

With above code I get this exception:

Exception in thread "main" com.fasterxml.jackson.core.io.JsonEOFException: Unexpected end-of-input: was expecting closing quote for a string value
 at [Source: java.io.StringReader@1a0dcaa; line: 1, column: 1046947]
	at com.fasterxml.jackson.core.base.ParserMinimalBase._reportInvalidEOF(ParserMinimalBase.java:483)
	at com.fasterxml.jackson.core.json.ReaderBasedJsonParser._finishString2(ReaderBasedJsonParser.java:2039)
	at com.fasterxml.jackson.core.json.ReaderBasedJsonParser._finishString(ReaderBasedJsonParser.java:2026)
	at com.fasterxml.jackson.core.json.ReaderBasedJsonParser.getText(ReaderBasedJsonParser.java:276)
	at com.fasterxml.jackson.databind.deser.std.BaseNodeDeserializer.deserializeObject(JsonNodeDeserializer.java:239)
	at com.fasterxml.jackson.databind.deser.std.BaseNodeDeserializer.deserializeArray(JsonNodeDeserializer.java:273)
	at com.fasterxml.jackson.databind.deser.std.JsonNodeDeserializer.deserialize(JsonNodeDeserializer.java:72)
	at com.fasterxml.jackson.databind.deser.std.JsonNodeDeserializer.deserialize(JsonNodeDeserializer.java:16)
	at com.fasterxml.jackson.databind.ObjectMapper._readMapAndClose(ObjectMapper.java:3789)
	at com.fasterxml.jackson.databind.ObjectMapper.readTree(ObjectMapper.java:2372)

2. Solution

As we can see from stack trace the default size of json response in Jsoup is 1046947 bytes (1_046_947).

As fix for this we need to set bigger max body size.

Jsoup.connect("http://localhost:8080/get-all-users")
    // FIX - this line set max response size without limits
    // the only limit is your machine 
	.maxBodySize(0)
    // ...

From Jsoup.maxBodySize(0) java docs:

Set the maximum bytes to read from the (uncompressed) connection into the body, before the connection is closed, and the input truncated.

The default maximum is 1MB.

A max size of zero is treated as an infinite amount (bounded only by your patience and the memory available on your machine).

@param bytes number of bytes to read from the input before truncating
@return this Connection, for chaining

OR

Jsoup.connect("http://localhost:8080/get-all-users")
    // FIX - this line set max response size to 100 MB
	.maxBodySize(1_000_000 * 100) // 100 mb ~
    // ...

Full working code: 

import com.fasterxml.jackson.core.JsonFactory;
import com.fasterxml.jackson.databind.JsonNode;
import com.fasterxml.jackson.databind.ObjectMapper;
import org.jsoup.Connection;
import org.jsoup.Jsoup;

import java.io.IOException;

public class JsoupHttpGetAppFIX {

    public static void main(String[] args) throws IOException {

        String jsonBodyStr;
        try {
            jsonBodyStr = Jsoup.connect("http://localhost:8080/get-all-users")

                    // FIX - this line set max response size without limit
                    // all our data will be fetched
                    .maxBodySize(0)

                    .followRedirects(true)
                    .ignoreHttpErrors(true)
                    .userAgent("Mozilla/5.0 AppleWebKit/537.36 (KHTML," +
                            " like Gecko) Chrome/45.0.2454.4 Safari/537.36")
                    .method(Connection.Method.GET)
                    .timeout(10_000)
                    .ignoreContentType(true)
                    .execute()
                    .body();
        } catch (IOException e) {
            throw new RuntimeException(e);
        }

        JsonNode rootNode = new ObjectMapper(new JsonFactory())
                .readTree(jsonBodyStr);

        System.out.println(rootNode);
    }
}

 

Donate to Dirask
Our content is created by volunteers - like Wikipedia. If you think, the things we do are good, donate us. Thanks!
Join to our subscribers to be up to date with content, news and offers.
Native Advertising
🚀
Get your tech brand or product in front of software developers.
For more information Contact us
Dirask - we help you to
solve coding problems.
Ask question.

❤️💻 🙂

Join