9

Error Message

java.lang.NoSuchMethodError: org.json.JSONArray.isEmpty()Z

My Scenario

I tried using the isEmpty() method of JSONArrayfrom the org.json JAR.

I'm using IntelliJ as my IDE. I'm not using anything close to reflection in my code. I declare a JSONArray, and after some lines trying to check if it is empty or not, however I get this Error when trying to use isEmpty().

I did work around the issue simply by using jsonArray.length() > 0, but the error message is what fascinates me. I looked into the de-compiled .class file of JSONArray, and the method isEmpty() exists, and has a public access modifier. Futhermore, InteliiJ is suggesting me I can use isEmpty() when typing the code. So what could be causing this error to occur?

Code Example

JSONArray filesJsonArray = new JSONArray();

JSONObject fileObject = new JSONObject();
fileObject.put("fileId",fileId);
fileObject.put("fileName",fileName);
fileObject.put("mimeType",mimeType);

filesJsonArray.put(fileObject);

if (!filesJsonArray.isEmpty()){ //the condition check here throws the error.
}

(Catch blocks were dismissed for brevity)

My Imports

In the class I'm using this code, this is all my imports

import org.json.JSONArray;
import org.json.JSONException;
import org.json.JSONObject;

import javax.servlet.ServletException;
import javax.servlet.annotation.WebServlet;
import javax.servlet.http.HttpServlet;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;
import java.io.*;
import java.nio.ByteBuffer;
import java.sql.*;
import java.util.Base64;
7
  • Which package are you using? org.json.simple.JSONArray this has isEmpty() method. org.json.JSONArray this one does not have the method. Commented Jan 29, 2019 at 10:21
  • According to the documentation there is no isEmpty() method. Maybe you have an issue with IntelliJ, have you tried compiling from the command line? Maybe check File->Project structure to see that IntelliJ uses the right library Commented Jan 29, 2019 at 10:21
  • @PrashantZombade using org.json.JSONArray Commented Jan 29, 2019 at 10:23
  • @DanielB., check with org.json.simple.JSONArray . You will have to handle JSONException while putting the objects. Commented Jan 29, 2019 at 10:28
  • @PrashantZombade There is a catch block for JSONException in my code. I'm not using org.json.simple.JSONArray, Im not familiar with this pacakge. Commented Jan 29, 2019 at 10:51

6 Answers 6

11

If you are using spring boot, then you can try this:

<dependency>
        <groupId>org.springframework.boot</groupId>
        <artifactId>spring-boot-starter-test</artifactId>
        <exclusions>
            <exclusion>
                <groupId>org.skyscreamer</groupId>
                <artifactId>jsonassert</artifactId>
            </exclusion>
        </exclusions>
    </dependency>

It worked for me..

Sign up to request clarification or add additional context in comments.

Comments

4

For anyone still looking at this, the main problem is with JSONAssert.

To confirm, use whatever dependency graph tool you have to verify that JSONAssert is adding "android-json".

Example for maven:

mvn dependency:tree

android-json provides its own implementations of org.json.* objects that aren't up to date. So exclude them as JSONAssert dependencies.

Example for maven:

<dependency>
   <groupId>org.skyscreamer</groupId>
   <artifactId>jsonassert</artifactId>
   <version>1.5.0</version>
   <scope>test</scope>
   <exclusions>
       <exclusion>
           <groupId>com.vaadin.external.google</groupId>
           <artifactId>android-json</artifactId>
       </exclusion>
   </exclusions>
</dependency>

That should save you from this problem while letting you use the great output of JSONAssert!

Comments

2

You need to clean the package of org.json dependency from spring-boot-starter-test artifactId, here is how to clean any depency (considering I was using spring-boot-starter-parent 2.4.4)

    <dependency>
        <groupId>org.springframework.boot</groupId>
        <artifactId>spring-boot-starter-test</artifactId>
        <scope>test</scope>
        <exclusions>
            <exclusion>
                <groupId>org.json</groupId>
                <artifactId>json</artifactId>
            </exclusion>
            <exclusion>
                <groupId>com.vaadin.external.google</groupId>
                <artifactId>android-json</artifactId>
            </exclusion>
            <exclusion>
                <groupId>org.skyscreamer</groupId>
                <artifactId>jsonassert</artifactId>
            </exclusion>
        </exclusions>
    </dependency>

1 Comment

And how to find these dependecies conflicts ? Type mvn dependency:tree into your root folder from a command line tool, it will give you the list of dependencies used, it can looks tedious, but this is the easiest way
0

I believe you added to your project

compile group: 'com.googlecode.json-simple', name: 'json-simple', version: '1.1'

Cause it seems like you've confused 2 classes: org.json.JSONArray with org.json.simple.JSONArray. First one doesn't have that method and the second one does. Here are code examples for both classes:

https://www.programcreek.com/java-api-examples/org.json.JSONArray

https://www.programcreek.com/java-api-examples/org.json.simple.JSONArray

So as a solution i’d recommend clean and rebuild the project.

2 Comments

This is not the case. I'm not using org.json.simple.JSONArray anywhere in my code. Just org.json.JSONArray
@DanielB. SO you say that cleaning and rebuilding the project doesn't work?
0

I've got the same error after i added to my project:

<dependency>    
  <groupId>com.fasterxml.jackson.datatype</groupId>
  <artifactId>jackson-datatype-json-org</artifactId>
  <version>2.9.2</version>
</dependency>
<dependency>
  <groupId>com.fasterxml.jackson.datatype</groupId>
  <artifactId>jackson-datatype-jsr310</artifactId>
  <version>2.9.2</version>
</dependency>

After that I cleaned and updated dependencies,

<dependency>
            <groupId>org.json</groupId>
            <artifactId>json</artifactId>
            <version>20180813</version>
        </dependency>
        <dependency>
            <groupId>com.fasterxml.jackson.datatype</groupId>
            <artifactId>jackson-datatype-jsr310</artifactId>
            <version>2.9.7</version>
        </dependency>
        <dependency>
            <groupId>com.fasterxml.jackson.datatype</groupId>
            <artifactId>jackson-datatype-json-org</artifactId>
            <version>2.9.7</version>
            <exclusions>
                <exclusion>
                    <groupId>org.json</groupId>
                    <artifactId>json</artifactId>
                </exclusion>
            </exclusions>
        </dependency>

and it was gone.

Comments

0

I know this is old, but posting this in case this might be useful to someone.

Here is what my updated dependency

  <dependency>
  <groupId>org.springframework.boot</groupId>
  <artifactId>spring-boot-starter-test</artifactId>
  <scope>test</scope>
  <exclusions>
    <exclusion>
      <groupId>org.json</groupId>
      <artifactId>json</artifactId>
    </exclusion>
    <exclusion>
      <groupId>com.vaadin.external.google</groupId>
      <artifactId>android-json</artifactId>
    </exclusion>
  </exclusions>
</dependency>

In my case, the JSONArray from com.vaadin.external.google from android-json was being used, instead of org.json.JSONArray which has the spliterator() throwing

Caused by: java.lang.NoSuchMethodError: org.json.JSONArray.spliterator()Ljava/util/Spliterator;

here is the code which threw that

  JSONArray someJsonArray = getSomeJsonArray();
  if (someJsonArray != null) {
    List<SecretEntry> secretEntries = (List)StreamSupport.stream(someJsonArray.spliterator(), false).map((obj) -> {
      return (JSONObject)obj;
...

And, I could not exclude org.skyscreamer.jsonassert, since it was being used by the assertJSONEqual() called by andExpect(content().json(getJsonBody()))

here is the code

 private MockMvc mockMvc;

 @Inject
 private WebApplicationContext webApplicationContext;

 mockMvc = webAppContextSetup(webApplicationContext).build();
 MvcResult result = mockMvc.perform(
        get("basePath").header(
            "headerName", "headerValue")).andExpect(content().contentType("application/json"))
    .andExpect(status().isOk()).andExpect(content().json(getJsonBody())).andReturn();

}

Comments

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.