Pārlūkot izejas kodu

Replace FastJson by Gson (#903)

Signed-off-by: yhmo <yihua.mo@zilliz.com>
groot 11 mēneši atpakaļ
vecāks
revīzija
d236a6ada5
68 mainītis faili ar 1405 papildinājumiem un 954 dzēšanām
  1. 20 4
      examples/main/java/io/milvus/BinaryVectorExample.java
  2. 61 57
      examples/main/java/io/milvus/BulkWriterExample.java
  3. 20 4
      examples/main/java/io/milvus/Float16VectorExample.java
  4. 10 8
      examples/main/java/io/milvus/GeneralExample.java
  5. 21 19
      examples/main/java/io/milvus/HighLevelExample.java
  6. 12 10
      examples/main/java/io/milvus/HybridSearchExample.java
  7. 6 0
      examples/main/java/io/milvus/RBACExample.java
  8. 8 6
      examples/main/java/io/milvus/SimpleExample.java
  9. 20 4
      examples/main/java/io/milvus/SparseVectorExample.java
  10. 1 1
      examples/main/java/io/milvus/resourcegroup/ResourceGroupManagement.java
  11. 0 5
      examples/pom.xml
  12. 0 6
      pom.xml
  13. 25 30
      src/main/java/io/milvus/bulkwriter/Buffer.java
  14. 135 59
      src/main/java/io/milvus/bulkwriter/BulkWriter.java
  15. 5 3
      src/main/java/io/milvus/bulkwriter/CloudImport.java
  16. 3 2
      src/main/java/io/milvus/bulkwriter/LocalBulkWriter.java
  17. 2 2
      src/main/java/io/milvus/bulkwriter/RemoteBulkWriter.java
  18. 7 0
      src/main/java/io/milvus/bulkwriter/common/utils/ParquetUtils.java
  19. 209 48
      src/main/java/io/milvus/param/ParamUtils.java
  20. 27 7
      src/main/java/io/milvus/param/dml/InsertParam.java
  21. 3 4
      src/main/java/io/milvus/param/dml/UpsertParam.java
  22. 3 3
      src/main/java/io/milvus/param/dml/ranker/RRFRanker.java
  23. 4 3
      src/main/java/io/milvus/param/dml/ranker/WeightedRanker.java
  24. 24 4
      src/main/java/io/milvus/param/highlevel/dml/InsertRowsParam.java
  25. 50 11
      src/main/java/io/milvus/response/FieldDataWrapper.java
  26. 2 2
      src/main/java/io/milvus/response/QueryResultsWrapper.java
  27. 2 2
      src/main/java/io/milvus/response/SearchResultsWrapper.java
  28. 6 5
      src/main/java/io/milvus/response/basic/RowRecordWrapper.java
  29. 6 5
      src/main/java/io/milvus/v2/examples/Simple.java
  30. 8 7
      src/main/java/io/milvus/v2/examples/Simple_Schema.java
  31. 2 2
      src/main/java/io/milvus/v2/service/vector/request/InsertReq.java
  32. 2 2
      src/main/java/io/milvus/v2/service/vector/request/UpsertReq.java
  33. 15 299
      src/main/java/io/milvus/v2/utils/DataUtils.java
  34. 2 2
      src/main/java/io/milvus/v2/utils/VectorUtils.java
  35. 422 71
      src/test/java/io/milvus/client/MilvusClientDockerTest.java
  36. 9 8
      src/test/java/io/milvus/v2/service/vector/VectorTest.java
  37. 3 3
      tests/milvustest/pom.xml
  38. 78 74
      tests/milvustest/src/main/java/com/zilliz/milvustest/common/CommonFunction.java
  39. 16 16
      tests/milvustest/src/main/java/com/zilliz/milvustest/service/CustomerListener.java
  40. 2 2
      tests/milvustest/src/main/java/com/zilliz/milvustest/util/HttpClientUtils.java
  41. 10 9
      tests/milvustest/src/test/java/com/zilliz/milvustest/bulk/BulkWriteTest.java
  42. 21 21
      tests/milvustest/src/test/java/com/zilliz/milvustest/bulkimport/BulkImportTest.java
  43. 5 6
      tests/milvustest/src/test/java/com/zilliz/milvustest/businessflow/ConcurrentTest.java
  44. 5 5
      tests/milvustest/src/test/java/com/zilliz/milvustest/insert/InsertTest.java
  45. 8 8
      tests/milvustest/src/test/java/com/zilliz/milvustest/query/QueryTest.java
  46. 5 6
      tests/milvustest/src/test/java/com/zilliz/milvustest/rbac/GrantRolePrivilegeTest.java
  47. 6 6
      tests/milvustest/src/test/java/com/zilliz/milvustest/search/SearchTest.java
  48. 3 3
      tests/milvustest/src/test/java/com/zilliz/milvustest/serverless/HighLevelTest.java
  49. 2 2
      tests/milvustest/src/test/java/com/zilliz/milvustest/tls/TLSTest.java
  50. 5 5
      tests/milvustestv2/src/main/java/com/zilliz/milvustestv2/common/BaseTest.java
  51. 30 28
      tests/milvustestv2/src/main/java/com/zilliz/milvustestv2/common/CommonFunction.java
  52. 16 16
      tests/milvustestv2/src/main/java/com/zilliz/milvustestv2/listener/CustomerListener.java
  53. 2 2
      tests/milvustestv2/src/main/java/com/zilliz/milvustestv2/utils/HttpClientUtils.java
  54. 2 2
      tests/milvustestv2/src/test/java/com/zilliz/milvustestv2/alias/CreateAliasTest.java
  55. 0 1
      tests/milvustestv2/src/test/java/com/zilliz/milvustestv2/alias/DropAliasTest.java
  56. 2 2
      tests/milvustestv2/src/test/java/com/zilliz/milvustestv2/collection/GetCollectionStatsTest.java
  57. 2 2
      tests/milvustestv2/src/test/java/com/zilliz/milvustestv2/index/CreateIndexTest.java
  58. 2 2
      tests/milvustestv2/src/test/java/com/zilliz/milvustestv2/index/DescribeIndexTest.java
  59. 2 2
      tests/milvustestv2/src/test/java/com/zilliz/milvustestv2/index/DropIndexTest.java
  60. 2 2
      tests/milvustestv2/src/test/java/com/zilliz/milvustestv2/index/ListIndexesTest.java
  61. 2 2
      tests/milvustestv2/src/test/java/com/zilliz/milvustestv2/loadRelease/LoadCollectionTest.java
  62. 2 2
      tests/milvustestv2/src/test/java/com/zilliz/milvustestv2/loadRelease/LoadPartitionsTest.java
  63. 2 2
      tests/milvustestv2/src/test/java/com/zilliz/milvustestv2/loadRelease/ReleaseCollectionTest.java
  64. 2 2
      tests/milvustestv2/src/test/java/com/zilliz/milvustestv2/loadRelease/ReleasePartitionsTest.java
  65. 6 6
      tests/milvustestv2/src/test/java/com/zilliz/milvustestv2/rbac/GrantPrivilegeTest.java
  66. 2 2
      tests/milvustestv2/src/test/java/com/zilliz/milvustestv2/vectorOperation/GetTest.java
  67. 3 3
      tests/milvustestv2/src/test/java/com/zilliz/milvustestv2/vectorOperation/InsertTest.java
  68. 5 5
      tests/milvustestv2/src/test/java/com/zilliz/milvustestv2/vectorOperation/UpsertTest.java

+ 20 - 4
examples/main/java/io/milvus/BinaryVectorExample.java

@@ -18,6 +18,8 @@
  */
 package io.milvus;
 
+import com.google.gson.Gson;
+import com.google.gson.JsonObject;
 import io.milvus.client.MilvusServiceClient;
 import io.milvus.common.clientenum.ConsistencyLevelEnum;
 import io.milvus.grpc.*;
@@ -84,7 +86,7 @@ public class BinaryVectorExample {
         CommonUtils.handleResponseStatus(ret);
         System.out.println("Collection created");
 
-        // Insert entities
+        // Insert entities by columns
         int rowCount = 10000;
         List<Long> ids = new ArrayList<>();
         for (long i = 0L; i < rowCount; ++i) {
@@ -96,12 +98,26 @@ public class BinaryVectorExample {
         fieldsInsert.add(new InsertParam.Field(ID_FIELD, ids));
         fieldsInsert.add(new InsertParam.Field(VECTOR_FIELD, vectors));
 
-        InsertParam insertParam = InsertParam.newBuilder()
+        R<MutationResult> insertR = milvusClient.insert(InsertParam.newBuilder()
                 .withCollectionName(COLLECTION_NAME)
                 .withFields(fieldsInsert)
-                .build();
+                .build());
+        CommonUtils.handleResponseStatus(insertR);
+
+        // Insert entities by rows
+        List<JsonObject> rows = new ArrayList<>();
+        Gson gson = new Gson();
+        for (long i = 1L; i <= rowCount; ++i) {
+            JsonObject row = new JsonObject();
+            row.addProperty(ID_FIELD, rowCount + i);
+            row.add(VECTOR_FIELD, gson.toJsonTree(CommonUtils.generateBinaryVector(VECTOR_DIM).array()));
+            rows.add(row);
+        }
 
-        R<MutationResult> insertR = milvusClient.insert(insertParam);
+        insertR = milvusClient.insert(InsertParam.newBuilder()
+                .withCollectionName(COLLECTION_NAME)
+                .withRows(rows)
+                .build());
         CommonUtils.handleResponseStatus(insertR);
 
         // Flush the data to storage for testing purpose

+ 61 - 57
examples/main/java/io/milvus/BulkWriterExample.java

@@ -18,12 +18,12 @@
  */
 package io.milvus;
 
-import com.alibaba.fastjson.JSONObject;
 import com.fasterxml.jackson.annotation.JsonProperty;
 import com.fasterxml.jackson.dataformat.csv.CsvMapper;
 import com.fasterxml.jackson.dataformat.csv.CsvSchema;
 import com.google.common.collect.Lists;
 import com.google.gson.Gson;
+import com.google.gson.JsonObject;
 import com.google.gson.reflect.TypeToken;
 import io.milvus.bulkwriter.*;
 import io.milvus.bulkwriter.common.clientenum.BulkFileType;
@@ -72,6 +72,8 @@ public class BulkWriterExample {
     public static final String USER_NAME = "user.name";
     public static final String PASSWORD = "password";
 
+    private static final Gson GSON_INSTANCE = new Gson();
+
 
     /**
      * If you need to transfer the files generated by bulkWriter to the corresponding remote storage (AWS S3, GCP GCS, Azure Blob, Aliyun OSS, Tencent Cloud TOS),
@@ -85,14 +87,14 @@ public class BulkWriterExample {
          * please configure the following parameters.
          */
         public static final String STORAGE_ENDPOINT = cloudStorage.getEndpoint("http://127.0.0.1:9000");
-        public static final String STORAGE_BUCKET = "storage.bucket";
-        public static final String STORAGE_ACCESS_KEY = "storage.access.key";
-        public static final String STORAGE_SECRET_KEY = "storage.secret.key";
+        public static final String STORAGE_BUCKET = "a-bucket"; // default bucket name of MinIO/Milvus standalone
+        public static final String STORAGE_ACCESS_KEY = "minioadmin"; // default ak of MinIO/Milvus standalone
+        public static final String STORAGE_SECRET_KEY = "minioadmin"; // default sk of MinIO/Milvus standalone
         /**
          * if using local storage such as Minio
          * Please set this parameter to empty.
          */
-        public static final String STORAGE_REGION = "storage.region";
+        public static final String STORAGE_REGION = "";
 
         /**
          * If using remote storage such as Azure Blob
@@ -197,15 +199,15 @@ public class BulkWriterExample {
             exampleBulkWriter.retrieveImportData(true);
         }
 
-        // float vectors + all scalar types, use cloud import api.
-        // You need to apply a cloud service from Zilliz Cloud(https://zilliz.com/cloud)
-        for (BulkFileType fileType : fileTypes) {
-            CollectionSchemaParam collectionSchema = buildAllTypeSchema(false, true);
-            List<List<String>> batchFiles = exampleBulkWriter.allTypesRemoteWriter(false, collectionSchema, fileType);
-            exampleBulkWriter.createCollection(ALL_TYPES_COLLECTION_NAME, collectionSchema, false);
-            exampleBulkWriter.callCloudImport(batchFiles, ALL_TYPES_COLLECTION_NAME);
-            exampleBulkWriter.retrieveImportData(false);
-        }
+//        // float vectors + all scalar types, use cloud import api.
+//        // You need to apply a cloud service from Zilliz Cloud(https://zilliz.com/cloud)
+//        for (BulkFileType fileType : fileTypes) {
+//            CollectionSchemaParam collectionSchema = buildAllTypeSchema(false, true);
+//            List<List<String>> batchFiles = exampleBulkWriter.allTypesRemoteWriter(false, collectionSchema, fileType);
+//            exampleBulkWriter.createCollection(ALL_TYPES_COLLECTION_NAME, collectionSchema, false);
+//            exampleBulkWriter.callCloudImport(batchFiles, ALL_TYPES_COLLECTION_NAME);
+//            exampleBulkWriter.retrieveImportData(false);
+//        }
     }
 
     private static void localWriter(CollectionSchemaParam collectionSchema, BulkFileType fileType) throws Exception {
@@ -223,10 +225,10 @@ public class BulkWriterExample {
 
             // append rows
             for (int i = 0; i < 100000; i++) {
-                JSONObject row = new JSONObject();
-                row.put("path", "path_" + i);
-                row.put("vector", GeneratorUtils.genFloatVector(DIM));
-                row.put("label", "label_" + i);
+                JsonObject row = new JsonObject();
+                row.addProperty("path", "path_" + i);
+                row.add("vector", GSON_INSTANCE.toJsonTree(GeneratorUtils.genFloatVector(DIM)));
+                row.addProperty("label", "label_" + i);
 
                 localBulkWriter.appendRow(row);
             }
@@ -238,7 +240,7 @@ public class BulkWriterExample {
             List<List<String>> batchFiles = localBulkWriter.getBatchFiles();
             System.out.printf("Local writer done! output local files: %s%n", batchFiles);
         } catch (Exception e) {
-            System.out.println("localWriter catch exception: " + e);
+            System.out.println("Local writer catch exception: " + e);
             throw e;
         }
     }
@@ -252,10 +254,10 @@ public class BulkWriterExample {
 
             // append rows
             for (int i = 0; i < 100000; i++) {
-                JSONObject row = new JSONObject();
-                row.put("path", "path_" + i);
-                row.put("vector", GeneratorUtils.genFloatVector(DIM));
-                row.put("label", "label_" + i);
+                JsonObject row = new JsonObject();
+                row.addProperty("path", "path_" + i);
+                row.add("vector", GSON_INSTANCE.toJsonTree(GeneratorUtils.genFloatVector(DIM)));
+                row.addProperty("label", "label_" + i);
 
                 remoteBulkWriter.appendRow(row);
             }
@@ -268,7 +270,7 @@ public class BulkWriterExample {
 
             System.out.printf("Remote writer done! output remote files: %s%n", batchFiles);
         } catch (Exception e) {
-            System.out.println("remoteWriter catch exception: " + e);
+            System.out.println("Remote writer catch exception: " + e);
             throw e;
         }
     }
@@ -338,10 +340,10 @@ public class BulkWriterExample {
     private static void appendRow(LocalBulkWriter writer, int begin, int end) {
         try {
             for (int i = begin; i < end; ++i) {
-                JSONObject row = new JSONObject();
-                row.put("path", "path_" + i);
-                row.put("vector", GeneratorUtils.genFloatVector(DIM));
-                row.put("label", "label_" + i);
+                JsonObject row = new JsonObject();
+                row.addProperty("path", "path_" + i);
+                row.add("vector", GSON_INSTANCE.toJsonTree(GeneratorUtils.genFloatVector(DIM)));
+                row.addProperty("label", "label_" + i);
 
                 writer.appendRow(row);
                 if (i % 100 == 0) {
@@ -361,31 +363,33 @@ public class BulkWriterExample {
             int batchCount = 10000;
 
             for (int i = 0; i < batchCount; ++i) {
-                JSONObject rowObject = new JSONObject();
+                JsonObject rowObject = new JsonObject();
 
                 // scalar field
-                rowObject.put("id", i);
-                rowObject.put("bool", i % 5 == 0);
-                rowObject.put("int8", i % 128);
-                rowObject.put("int16", i % 1000);
-                rowObject.put("int32", i % 100000);
-                rowObject.put("float", i / 3);
-                rowObject.put("double", i / 7);
-                rowObject.put("varchar", "varchar_" + i);
-                rowObject.put("json", String.format("{\"dummy\": %s, \"ok\": \"name_%s\"}", i, i));
+                rowObject.addProperty("id", i);
+                rowObject.addProperty("bool", i % 5 == 0);
+                rowObject.addProperty("int8", i % 128);
+                rowObject.addProperty("int16", i % 1000);
+                rowObject.addProperty("int32", i % 100000);
+                rowObject.addProperty("float", i / 3);
+                rowObject.addProperty("double", i / 7);
+                rowObject.addProperty("varchar", "varchar_" + i);
+                rowObject.addProperty("json", String.format("{\"dummy\": %s, \"ok\": \"name_%s\"}", i, i));
 
                 // vector field
-                rowObject.put("vector", binVec ? GeneratorUtils.generatorBinaryVector(128) : GeneratorUtils.generatorFloatValue(128));
+                rowObject.add("vector",
+                        binVec ? GSON_INSTANCE.toJsonTree(GeneratorUtils.generatorBinaryVector(128).array()) :
+                                GSON_INSTANCE.toJsonTree(GeneratorUtils.generatorFloatValue(128)));
 
                 // array field
-                rowObject.put("arrayInt64", GeneratorUtils.generatorLongValue(10));
-                rowObject.put("arrayVarchar", GeneratorUtils.generatorVarcharValue(10, 10));
-                rowObject.put("arrayInt8", GeneratorUtils.generatorInt8Value(10));
-                rowObject.put("arrayInt16", GeneratorUtils.generatorInt16Value(10));
-                rowObject.put("arrayInt32", GeneratorUtils.generatorInt32Value(10));
-                rowObject.put("arrayFloat", GeneratorUtils.generatorFloatValue(10));
-                rowObject.put("arrayDouble", GeneratorUtils.generatorDoubleValue(10));
-                rowObject.put("arrayBool", GeneratorUtils.generatorBoolValue(10));
+                rowObject.add("arrayInt64", GSON_INSTANCE.toJsonTree(GeneratorUtils.generatorLongValue(10)));
+                rowObject.add("arrayVarchar", GSON_INSTANCE.toJsonTree(GeneratorUtils.generatorVarcharValue(10, 10)));
+                rowObject.add("arrayInt8", GSON_INSTANCE.toJsonTree(GeneratorUtils.generatorInt8Value(10)));
+                rowObject.add("arrayInt16", GSON_INSTANCE.toJsonTree(GeneratorUtils.generatorInt16Value(10)));
+                rowObject.add("arrayInt32", GSON_INSTANCE.toJsonTree(GeneratorUtils.generatorInt32Value(10)));
+                rowObject.add("arrayFloat", GSON_INSTANCE.toJsonTree(GeneratorUtils.generatorFloatValue(10)));
+                rowObject.add("arrayDouble", GSON_INSTANCE.toJsonTree(GeneratorUtils.generatorDoubleValue(10)));
+                rowObject.add("arrayBool", GSON_INSTANCE.toJsonTree(GeneratorUtils.generatorBoolValue(10)));
 
                 remoteBulkWriter.appendRow(rowObject);
             }
@@ -447,11 +451,11 @@ public class BulkWriterExample {
         Iterator<CsvDataObject> iterator = csvMapper.readerFor(CsvDataObject.class).with(csvSchema).readValues(csvFile);
         while (iterator.hasNext()) {
             CsvDataObject dataObject = iterator.next();
-            JSONObject row = new JSONObject();
+            JsonObject row = new JsonObject();
 
-            row.put("vector", dataObject.toFloatArray());
-            row.put("label", dataObject.getLabel());
-            row.put("path", dataObject.getPath());
+            row.add("vector", GSON_INSTANCE.toJsonTree(dataObject.toFloatArray()));
+            row.addProperty("label", dataObject.getLabel());
+            row.addProperty("path", dataObject.getPath());
 
             writer.appendRow(row);
         }
@@ -475,14 +479,14 @@ public class BulkWriterExample {
             return label;
         }
         public List<Float> toFloatArray() {
-            return new Gson().fromJson(vector, new TypeToken<List<Float>>() {
+            return GSON_INSTANCE.fromJson(vector, new TypeToken<List<Float>>() {
             }.getType());
         }
     }
 
     private void callBulkInsert(CollectionSchemaParam collectionSchema, List<List<String>> batchFiles) throws InterruptedException {
         System.out.println("\n===================== call bulkInsert ====================");
-        createCollection(ALL_TYPES_COLLECTION_NAME, collectionSchema, false);
+        createCollection(ALL_TYPES_COLLECTION_NAME, collectionSchema, true);
 
         List<Long> taskIds = new ArrayList<>();
         for (List<String> batch : batchFiles) {
@@ -491,7 +495,7 @@ public class BulkWriterExample {
             System.out.println("Create a bulkInert task, task id: " + taskId);
         }
 
-        while (taskIds.size() > 0) {
+        while (!taskIds.isEmpty()) {
             Iterator<Long> iterator = taskIds.iterator();
             List<Long> tempTaskIds = new ArrayList<>();
             while (iterator.hasNext()) {
@@ -678,16 +682,16 @@ public class BulkWriterExample {
         BulkImportResponse bulkImportResponse = CloudImport.bulkImport(CloudImportConsts.CLOUD_ENDPOINT, CloudImportConsts.API_KEY,
                 CloudImportConsts.OBJECT_URL, CloudImportConsts.OBJECT_ACCESS_KEY, CloudImportConsts.OBJECT_SECRET_KEY,
                 CloudImportConsts.CLUSTER_ID, CloudImportConsts.COLLECTION_NAME);
-        System.out.println(new Gson().toJson(bulkImportResponse));
+        System.out.println(GSON_INSTANCE.toJson(bulkImportResponse));
 
         System.out.println("\n===================== get import job progress ====================");
         String jobId = bulkImportResponse.getJobId();
         GetImportProgressResponse getImportProgressResponse = CloudImport.getImportProgress(CloudImportConsts.CLOUD_ENDPOINT, CloudImportConsts.API_KEY, jobId, CloudImportConsts.CLUSTER_ID);
-        System.out.println(new Gson().toJson(getImportProgressResponse));
+        System.out.println(GSON_INSTANCE.toJson(getImportProgressResponse));
 
         System.out.println("\n===================== list import jobs ====================");
         ListImportJobsResponse listImportJobsResponse = CloudImport.listImportJobs(CloudImportConsts.CLOUD_ENDPOINT, CloudImportConsts.API_KEY, CloudImportConsts.CLUSTER_ID, 10, 1);
-        System.out.println(new Gson().toJson(listImportJobsResponse));
+        System.out.println(GSON_INSTANCE.toJson(listImportJobsResponse));
     }
 
     private CollectionSchemaParam buildSimpleCollection() {

+ 20 - 4
examples/main/java/io/milvus/Float16VectorExample.java

@@ -18,6 +18,8 @@
  */
 package io.milvus;
 
+import com.google.gson.Gson;
+import com.google.gson.JsonObject;
 import io.milvus.client.MilvusServiceClient;
 import io.milvus.common.clientenum.ConsistencyLevelEnum;
 import io.milvus.grpc.*;
@@ -85,7 +87,7 @@ public class Float16VectorExample {
         CommonUtils.handleResponseStatus(ret);
         System.out.println("Collection created");
 
-        // Insert entities
+        // Insert entities by columns
         int rowCount = 10000;
         List<Long> ids = new ArrayList<>();
         for (long i = 0L; i < rowCount; ++i) {
@@ -97,12 +99,26 @@ public class Float16VectorExample {
         fieldsInsert.add(new InsertParam.Field(ID_FIELD, ids));
         fieldsInsert.add(new InsertParam.Field(VECTOR_FIELD, vectors));
 
-        InsertParam insertParam = InsertParam.newBuilder()
+        R<MutationResult> insertR = milvusClient.insert(InsertParam.newBuilder()
                 .withCollectionName(COLLECTION_NAME)
                 .withFields(fieldsInsert)
-                .build();
+                .build());
+        CommonUtils.handleResponseStatus(insertR);
+
+        // Insert entities by rows
+        List<JsonObject> rows = new ArrayList<>();
+        Gson gson = new Gson();
+        for (long i = 1L; i <= rowCount; ++i) {
+            JsonObject row = new JsonObject();
+            row.addProperty(ID_FIELD, rowCount + i);
+            row.add(VECTOR_FIELD, gson.toJsonTree(CommonUtils.generateFloat16Vector(VECTOR_DIM, bfloat16).array()));
+            rows.add(row);
+        }
 
-        R<MutationResult> insertR = milvusClient.insert(insertParam);
+        insertR = milvusClient.insert(InsertParam.newBuilder()
+                .withCollectionName(COLLECTION_NAME)
+                .withRows(rows)
+                .build());
         CommonUtils.handleResponseStatus(insertR);
 
         // Flush the data to storage for testing purpose

+ 10 - 8
examples/main/java/io/milvus/GeneralExample.java

@@ -18,7 +18,8 @@
  */
 package io.milvus;
 
-import com.alibaba.fastjson.JSONObject;
+import com.google.gson.Gson;
+import com.google.gson.JsonObject;
 import io.milvus.client.MilvusClient;
 import io.milvus.client.MilvusServiceClient;
 import io.milvus.common.clientenum.ConsistencyLevelEnum;
@@ -122,7 +123,7 @@ public class GeneralExample {
                 .build());
         CommonUtils.handleResponseStatus(response);
         System.out.println(response);
-        return response.getData().booleanValue();
+        return response.getData();
     }
 
     private R<RpcStatus> loadCollection() {
@@ -152,7 +153,7 @@ public class GeneralExample {
                 .build());
         CommonUtils.handleResponseStatus(response);
         DescCollResponseWrapper wrapper = new DescCollResponseWrapper(response.getData());
-        System.out.println(wrapper.toString());
+        System.out.println(wrapper);
         return response;
     }
 
@@ -410,12 +411,13 @@ public class GeneralExample {
     private R<MutationResult> insertRows(String partitionName, int count) {
         System.out.println("========== insertRows() ==========");
 
-        List<JSONObject> rowsData = new ArrayList<>();
+        List<JsonObject> rowsData = new ArrayList<>();
         Random ran = new Random();
+        Gson gson = new Gson();
         for (long i = 0L; i < count; ++i) {
-            JSONObject row = new JSONObject();
-            row.put(AGE_FIELD, ran.nextInt(99));
-            row.put(VECTOR_FIELD, CommonUtils.generateFloatVector(VECTOR_DIM));
+            JsonObject row = new JsonObject();
+            row.addProperty(AGE_FIELD, ran.nextInt(99));
+            row.add(VECTOR_FIELD, gson.toJsonTree(CommonUtils.generateFloatVector(VECTOR_DIM)));
 
             rowsData.add(row);
         }
@@ -501,7 +503,7 @@ public class GeneralExample {
         System.out.println("Search with index");
         example.searchFace(searchExpr);
 
-        String deleteExpr = ID_FIELD + " in " + deleteIds.toString();
+        String deleteExpr = ID_FIELD + " in " + deleteIds;
         example.delete(partitionName, deleteExpr);
         String queryExpr = AGE_FIELD + " == 60";
         example.query(queryExpr);

+ 21 - 19
examples/main/java/io/milvus/HighLevelExample.java

@@ -18,7 +18,8 @@
  */
 package io.milvus;
 
-import com.alibaba.fastjson.JSONObject;
+import com.google.gson.Gson;
+import com.google.gson.JsonObject;
 import com.google.common.collect.Lists;
 import io.milvus.client.MilvusServiceClient;
 import io.milvus.common.clientenum.ConsistencyLevelEnum;
@@ -111,30 +112,31 @@ public class HighLevelExample {
 
     private R<InsertResponse> insertRows(int rowCount) {
         System.out.println("========== high level insertRows ==========");
-        List<JSONObject> rowsData = new ArrayList<>();
+        List<JsonObject> rowsData = new ArrayList<>();
         Random ran = new Random();
+        Gson gson = new Gson();
         for (long i = 0L; i < rowCount; ++i) {
-            JSONObject row = new JSONObject();
-            row.put(AGE_FIELD, ran.nextInt(99));
-            row.put(VECTOR_FIELD, CommonUtils.generateFloatVector(VECTOR_DIM));
+            JsonObject row = new JsonObject();
+            row.addProperty(AGE_FIELD, ran.nextInt(99));
+            row.add(VECTOR_FIELD, gson.toJsonTree(CommonUtils.generateFloatVector(VECTOR_DIM)));
 
             // $meta if collection EnableDynamicField, you can input this field not exist in schema, else deny
-            row.put(INT32_FIELD_NAME, ran.nextInt());
-            row.put(INT64_FIELD_NAME, ran.nextLong());
-            row.put(VARCHAR_FIELD_NAME, "测试varchar");
-            row.put(FLOAT_FIELD_NAME, ran.nextFloat());
-            row.put(DOUBLE_FIELD_NAME, ran.nextDouble());
-            row.put(BOOL_FIELD_NAME, ran.nextBoolean());
+            row.addProperty(INT32_FIELD_NAME, ran.nextInt());
+            row.addProperty(INT64_FIELD_NAME, ran.nextLong());
+            row.addProperty(VARCHAR_FIELD_NAME, String.format("varchar_%d", i));
+            row.addProperty(FLOAT_FIELD_NAME, ran.nextFloat());
+            row.addProperty(DOUBLE_FIELD_NAME, ran.nextDouble());
+            row.addProperty(BOOL_FIELD_NAME, ran.nextBoolean());
 
             // $json
-            JSONObject jsonObject = new JSONObject();
-            jsonObject.put(INT32_FIELD_NAME, ran.nextInt());
-            jsonObject.put(INT64_FIELD_NAME, ran.nextLong());
-            jsonObject.put(VARCHAR_FIELD_NAME, "测试varchar");
-            jsonObject.put(FLOAT_FIELD_NAME, ran.nextFloat());
-            jsonObject.put(DOUBLE_FIELD_NAME, ran.nextDouble());
-            jsonObject.put(BOOL_FIELD_NAME, ran.nextBoolean());
-            row.put(USER_JSON_FIELD, jsonObject);
+            JsonObject jsonObject = new JsonObject();
+            jsonObject.addProperty(INT32_FIELD_NAME, ran.nextInt());
+            jsonObject.addProperty(INT64_FIELD_NAME, ran.nextLong());
+            jsonObject.addProperty(VARCHAR_FIELD_NAME, String.format("varchar_%d", i));
+            jsonObject.addProperty(FLOAT_FIELD_NAME, ran.nextFloat());
+            jsonObject.addProperty(DOUBLE_FIELD_NAME, ran.nextDouble());
+            jsonObject.addProperty(BOOL_FIELD_NAME, ran.nextBoolean());
+            row.add(USER_JSON_FIELD, jsonObject);
 
             rowsData.add(row);
         }

+ 12 - 10
examples/main/java/io/milvus/HybridSearchExample.java

@@ -18,7 +18,8 @@
  */
 package io.milvus;
 
-import com.alibaba.fastjson.JSONObject;
+import com.google.gson.Gson;
+import com.google.gson.JsonObject;
 import io.milvus.client.MilvusClient;
 import io.milvus.client.MilvusServiceClient;
 import io.milvus.common.clientenum.ConsistencyLevelEnum;
@@ -160,14 +161,15 @@ public class HybridSearchExample {
         long idCount = 0;
         int rowCount = 10000;
         // Insert entities by rows
-        List<JSONObject> rows = new ArrayList<>();
+        List<JsonObject> rows = new ArrayList<>();
+        Gson gson = new Gson();
         for (long i = 1L; i <= rowCount; ++i) {
-            JSONObject row = new JSONObject();
-            row.put(ID_FIELD, idCount++);
-            row.put(FLOAT_VECTOR_FIELD, CommonUtils.generateFloatVector(FLOAT_VECTOR_DIM));
-            row.put(BINARY_VECTOR_FIELD, CommonUtils.generateBinaryVector(BINARY_VECTOR_DIM));
-            row.put(FLOAT16_VECTOR_FIELD, CommonUtils.generateFloat16Vector(FLOAT16_VECTOR_DIM, false));
-            row.put(SPARSE_VECTOR_FIELD, CommonUtils.generateSparseVector());
+            JsonObject row = new JsonObject();
+            row.addProperty(ID_FIELD, idCount++);
+            row.add(FLOAT_VECTOR_FIELD, gson.toJsonTree(CommonUtils.generateFloatVector(FLOAT_VECTOR_DIM)));
+            row.add(BINARY_VECTOR_FIELD, gson.toJsonTree(CommonUtils.generateBinaryVector(BINARY_VECTOR_DIM).array()));
+            row.add(FLOAT16_VECTOR_FIELD, gson.toJsonTree(CommonUtils.generateFloat16Vector(FLOAT16_VECTOR_DIM, false).array()));
+            row.add(SPARSE_VECTOR_FIELD, gson.toJsonTree(CommonUtils.generateSparseVector()));
             rows.add(row);
         }
 
@@ -275,8 +277,8 @@ public class HybridSearchExample {
         for (int k = 0; k < NQ; k++) {
             System.out.printf("============= Search result of No.%d vector =============\n", k);
             List<SearchResultsWrapper.IDScore> scores = results.getIDScore(0);
-            for (int i = 0; i < scores.size(); ++i) {
-                System.out.println(scores.get(i));
+            for (SearchResultsWrapper.IDScore score : scores) {
+                System.out.println(score);
             }
         }
     }

+ 6 - 0
examples/main/java/io/milvus/RBACExample.java

@@ -109,23 +109,28 @@ public class RBACExample {
         // create a role
         R<RpcStatus> resp = createRole("role1");
         Validate.isTrue(resp.getStatus() == R.success().getStatus(), "create role fail!");
+        System.out.println("role1 created");
 
         //create user
         resp = createUser("user", "pwd123456");
         Validate.isTrue(resp.getStatus() == R.success().getStatus(), "create user fail!");
+        System.out.println("user created");
 
         // grant privilege to role.
         // grant object is all collections, grant object type is Collection, and the privilege is CreateCollection
         resp = grantRolePrivilege("role1","Global","*",  "CreateCollection");
         Validate.isTrue(resp.getStatus() == R.success().getStatus(), "bind privileges to role fail!");
+        System.out.println("grant privilege to role1");
 
         // bind role to user
         resp = grantUserRole("user", "role1");
         Validate.isTrue(resp.getStatus() == R.success().getStatus(), "bind role to user fail!");
+        System.out.println("bind role1 to user");
 
         // revoke privilege from role
         resp = revokeRolePrivilege("role1","Global","*",  "CreateCollection");
         Validate.isTrue(resp.getStatus() == R.success().getStatus(), "revoke privileges to role fail!");
+        System.out.println("revoke privilege from role1");
 
         // list role
         R<SelectRoleResponse> resp1 = selectRole("role1");
@@ -134,5 +139,6 @@ public class RBACExample {
         // delete a role
         resp = dropRole("role1");
         Validate.isTrue(resp.getStatus() == R.success().getStatus(), "drop role fail!");
+        System.out.println("delete role1");
     }
 }

+ 8 - 6
examples/main/java/io/milvus/SimpleExample.java

@@ -18,7 +18,8 @@
  */
 package io.milvus;
 
-import com.alibaba.fastjson.JSONObject;
+import com.google.gson.Gson;
+import com.google.gson.JsonObject;
 import io.milvus.client.MilvusServiceClient;
 import io.milvus.grpc.*;
 import io.milvus.param.*;
@@ -104,13 +105,14 @@ public class SimpleExample {
         System.out.println("Collection created");
 
         // Insert 10 records into the collection
-        List<JSONObject> rows = new ArrayList<>();
+        Gson gson = new Gson();
+        List<JsonObject> rows = new ArrayList<>();
         for (long i = 1L; i <= 10; ++i) {
-            JSONObject row = new JSONObject();
-            row.put(ID_FIELD, i);
+            JsonObject row = new JsonObject();
+            row.addProperty(ID_FIELD, i);
             List<Float> vector = Arrays.asList((float)i, (float)i, (float)i, (float)i);
-            row.put(VECTOR_FIELD, vector);
-            row.put(TITLE_FIELD, "Tom and Jerry " + i);
+            row.add(VECTOR_FIELD, gson.toJsonTree(vector));
+            row.addProperty(TITLE_FIELD, "Tom and Jerry " + i);
             rows.add(row);
         }
 

+ 20 - 4
examples/main/java/io/milvus/SparseVectorExample.java

@@ -18,6 +18,8 @@
  */
 package io.milvus;
 
+import com.google.gson.Gson;
+import com.google.gson.JsonObject;
 import io.milvus.client.MilvusServiceClient;
 import io.milvus.common.clientenum.ConsistencyLevelEnum;
 import io.milvus.grpc.*;
@@ -81,7 +83,7 @@ public class SparseVectorExample {
         CommonUtils.handleResponseStatus(ret);
         System.out.println("Collection created");
 
-        // Insert entities
+        // Insert entities by columns
         int rowCount = 10000;
         List<Long> ids = new ArrayList<>();
         for (long i = 0L; i < rowCount; ++i) {
@@ -93,12 +95,26 @@ public class SparseVectorExample {
         fieldsInsert.add(new InsertParam.Field(ID_FIELD, ids));
         fieldsInsert.add(new InsertParam.Field(VECTOR_FIELD, vectors));
 
-        InsertParam insertParam = InsertParam.newBuilder()
+        R<MutationResult> insertR = milvusClient.insert(InsertParam.newBuilder()
                 .withCollectionName(COLLECTION_NAME)
                 .withFields(fieldsInsert)
-                .build();
+                .build());
+        CommonUtils.handleResponseStatus(insertR);
+
+        // Insert entities by rows
+        List<JsonObject> rows = new ArrayList<>();
+        Gson gson = new Gson();
+        for (long i = 1L; i <= rowCount; ++i) {
+            JsonObject row = new JsonObject();
+            row.addProperty(ID_FIELD, rowCount + i);
+            row.add(VECTOR_FIELD, gson.toJsonTree(CommonUtils.generateSparseVector()));
+            rows.add(row);
+        }
 
-        R<MutationResult> insertR = milvusClient.insert(insertParam);
+        insertR = milvusClient.insert(InsertParam.newBuilder()
+                .withCollectionName(COLLECTION_NAME)
+                .withRows(rows)
+                .build());
         CommonUtils.handleResponseStatus(insertR);
 
         // Flush the data to storage for testing purpose

+ 1 - 1
examples/main/java/io/milvus/resourcegroup/ResourceGroupManagement.java

@@ -207,7 +207,7 @@ public class ResourceGroupManagement {
         for (String collection : showCollectionResponse.getCollectionNamesList()) {
             String currentResourceGroupName = getCollectionResourceGroupName(dbName, collection);
             // skip if the collection is not loaded or is already added to resourceGroup.
-            if (currentResourceGroupName == null || currentResourceGroupName == resourceGroupName) {
+            if (currentResourceGroupName == null || currentResourceGroupName.equals(resourceGroupName)) {
                 continue;
             }
             R<RpcStatus> status = client.transferReplica(TransferReplicaParam.newBuilder()

+ 0 - 5
examples/pom.xml

@@ -73,11 +73,6 @@
                 </exclusion>
             </exclusions>
         </dependency>
-        <dependency>
-            <groupId>com.google.code.gson</groupId>
-            <artifactId>gson</artifactId>
-            <version>2.8.9</version>
-        </dependency>
         <dependency>
             <groupId>org.tensorflow</groupId>
             <artifactId>tensorflow-core-platform</artifactId>

+ 0 - 6
pom.xml

@@ -93,7 +93,6 @@
         <jackson.version>2.16.1</jackson.version>
         <gson.version>2.10.1</gson.version>
         <kotlin.version>1.9.10</kotlin.version>
-        <version.fastjson>1.2.83</version.fastjson>
         <mockito.version>4.11.0</mockito.version>
         <testcontainers.version>1.19.6</testcontainers.version>
 
@@ -292,11 +291,6 @@
             <artifactId>gson</artifactId>
             <version>${gson.version}</version>
         </dependency>
-        <dependency>
-            <groupId>com.alibaba</groupId>
-            <artifactId>fastjson</artifactId>
-            <version>${version.fastjson}</version>
-        </dependency>
 
         <dependency>
             <groupId>org.apache.parquet</groupId>

+ 25 - 30
src/main/java/io/milvus/bulkwriter/Buffer.java

@@ -19,7 +19,7 @@
 
 package io.milvus.bulkwriter;
 
-import com.alibaba.fastjson.JSONObject;
+import com.google.gson.*;
 import com.google.common.collect.Lists;
 import io.milvus.bulkwriter.common.clientenum.BulkFileType;
 import io.milvus.common.utils.ExceptionUtils;
@@ -56,6 +56,8 @@ public class Buffer {
     private Map<String, List<Object>> buffer;
     private Map<String, FieldType> fields;
 
+    private static final Gson GSON_INSTANCE = new Gson();
+
     public Buffer(CollectionSchemaParam collectionSchema, BulkFileType fileType) {
         this.collectionSchema = collectionSchema;
         this.fileType = fileType;
@@ -91,27 +93,12 @@ public class Buffer {
         return null;
     }
 
-    public void appendRow(JSONObject row) {
-        Map<String, Object> dynamicValues = new HashMap<>();
-        if (row.containsKey(DYNAMIC_FIELD_NAME) && !(row.get(DYNAMIC_FIELD_NAME) instanceof Map)) {
-            String msg = String.format("Dynamic field '%s' value should be JSON format", DYNAMIC_FIELD_NAME);
-            ExceptionUtils.throwUnExpectedException(msg);
-        }
-
+    public void appendRow(Map<String, Object> row) {
         for (String key : row.keySet()) {
-            if (DYNAMIC_FIELD_NAME.equals(key)) {
-                dynamicValues.putAll((Map<String, Object>) row.get(key));
-                continue;
-            }
-            if (!buffer.containsKey(key)) {
-                dynamicValues.put(key, row.get(key));
-            } else {
-                buffer.get(key).add(row.get(key));
+            if (key.equals(DYNAMIC_FIELD_NAME) && !this.collectionSchema.isEnableDynamicField()) {
+                continue; // skip dynamic field if it is disabled
             }
-        }
-
-        if (buffer.containsKey(DYNAMIC_FIELD_NAME)) {
-            buffer.get(DYNAMIC_FIELD_NAME).add(dynamicValues);
+            buffer.get(key).add(row.get(key));
         }
     }
 
@@ -172,6 +159,12 @@ public class Buffer {
                 configuration)) {
 
             Map<String, FieldType> nameFieldType = collectionSchema.getFieldTypes().stream().collect(Collectors.toMap(FieldType::getName, e -> e));
+            if (collectionSchema.isEnableDynamicField()) {
+                nameFieldType.put(DYNAMIC_FIELD_NAME, FieldType.newBuilder()
+                        .withName(DYNAMIC_FIELD_NAME)
+                        .withDataType(DataType.JSON)
+                        .build());
+            }
 
             List<String> fieldNameList = Lists.newArrayList(buffer.keySet());
             int size = buffer.get(fieldNameList.get(0)).size();
@@ -194,30 +187,31 @@ public class Buffer {
     }
 
     private void appendGroup(Group group, String paramName, Object value, FieldType fieldType) {
-        switch (fieldType.getDataType()) {
+        DataType dataType = fieldType.getDataType();
+        switch (dataType) {
             case Int8:
             case Int16:
+                group.append(paramName, (Short)value);
+                break;
             case Int32:
-                group.append(paramName, Integer.parseInt(value.toString()));
+                group.append(paramName, (Integer)value);
                 break;
             case Int64:
-                group.append(paramName, Long.parseLong(value.toString()));
+                group.append(paramName, (Long)value);
                 break;
             case Float:
-                group.append(paramName, Float.parseFloat(value.toString()));
+                group.append(paramName, (Float)value);
                 break;
             case Double:
-                group.append(paramName, Double.parseDouble(value.toString()));
+                group.append(paramName, (Double)value);
                 break;
             case Bool:
-                group.append(paramName, Boolean.parseBoolean(value.toString()));
+                group.append(paramName, (Boolean)value);
                 break;
             case VarChar:
             case String:
-                group.append(paramName, String.valueOf(value));
-                break;
             case JSON:
-                group.append(paramName, ((JSONObject) value).toJSONString());
+                group.append(paramName, (String)value);
                 break;
             case FloatVector:
                 addFloatArray(group, paramName, (List<Float>) value);
@@ -226,7 +220,8 @@ public class Buffer {
                 addBinaryVector(group, paramName, (ByteBuffer) value);
                 break;
             case Array:
-                switch (fieldType.getElementType()) {
+                DataType elementType = fieldType.getElementType();
+                switch (elementType) {
                     case Int8:
                     case Int16:
                     case Int32:

+ 135 - 59
src/main/java/io/milvus/bulkwriter/BulkWriter.java

@@ -19,12 +19,11 @@
 
 package io.milvus.bulkwriter;
 
-import com.alibaba.fastjson.JSONObject;
-import com.google.common.collect.Lists;
+import com.google.gson.*;
 import io.milvus.bulkwriter.common.clientenum.BulkFileType;
 import io.milvus.bulkwriter.common.clientenum.TypeSize;
 import io.milvus.common.utils.ExceptionUtils;
-import io.milvus.grpc.DataType;
+import io.milvus.grpc.*;
 import io.milvus.param.ParamUtils;
 import io.milvus.param.collection.CollectionSchemaParam;
 import io.milvus.param.collection.FieldType;
@@ -35,10 +34,11 @@ import org.slf4j.LoggerFactory;
 
 import java.io.IOException;
 import java.nio.ByteBuffer;
-import java.util.List;
-import java.util.Optional;
+import java.util.*;
 import java.util.concurrent.locks.ReentrantLock;
 
+import static io.milvus.param.Constant.DYNAMIC_FIELD_NAME;
+
 public abstract class BulkWriter {
     private static final Logger logger = LoggerFactory.getLogger(BulkWriter.class);
     protected CollectionSchemaParam collectionSchema;
@@ -51,6 +51,8 @@ public abstract class BulkWriter {
     protected Buffer buffer;
     protected ReentrantLock bufferLock;
 
+    private static final Gson GSON_INSTANCE = new Gson();
+
     protected BulkWriter(CollectionSchemaParam collectionSchema, int chunkSize, BulkFileType fileType) {
         this.collectionSchema = collectionSchema;
         this.chunkSize = chunkSize;
@@ -94,11 +96,11 @@ public abstract class BulkWriter {
         return oldBuffer;
     }
 
-    public void appendRow(JSONObject row) throws IOException, InterruptedException {
-        verifyRow(row);
+    public void appendRow(JsonObject row) throws IOException, InterruptedException {
+        Map<String, Object> rowValues = verifyRow(row);
 
         bufferLock.lock();
-        buffer.appendRow(row);
+        buffer.appendRow(rowValues);
         bufferLock.unlock();
     }
 
@@ -113,42 +115,95 @@ public abstract class BulkWriter {
         return "";
     }
 
-    private void verifyRow(JSONObject row) {
+    private Map<String, Object> verifyRow(JsonObject row) {
         int rowSize = 0;
+        Map<String, Object> rowValues = new HashMap<>();
         for (FieldType fieldType : collectionSchema.getFieldTypes()) {
+            String fieldName = fieldType.getName();
             if (fieldType.isPrimaryKey() && fieldType.isAutoID()) {
-                if (row.containsKey(fieldType.getName())) {
-                    String msg = String.format("The primary key field '%s' is auto-id, no need to provide", fieldType.getName());
+                if (row.has(fieldName)) {
+                    String msg = String.format("The primary key field '%s' is auto-id, no need to provide", fieldName);
                     ExceptionUtils.throwUnExpectedException(msg);
                 } else {
                     continue;
                 }
             }
 
-            if (!row.containsKey(fieldType.getName())) {
-                String msg = String.format("The field '%s' is missed in the row", fieldType.getName());
+            if (!row.has(fieldName)) {
+                String msg = String.format("The field '%s' is missed in the row", fieldName);
+                ExceptionUtils.throwUnExpectedException(msg);
+            }
+
+            JsonElement obj = row.get(fieldName);
+            if (obj == null || obj.isJsonNull()) {
+                String msg = String.format("Illegal value for field '%s', value is null", fieldName);
                 ExceptionUtils.throwUnExpectedException(msg);
             }
 
-            switch (fieldType.getDataType()) {
+            DataType dataType = fieldType.getDataType();
+            switch (dataType) {
                 case BinaryVector:
-                case FloatVector:
-                    rowSize += verifyVector(row.get(fieldType.getName()), fieldType);
+                case FloatVector: {
+                    Pair<Object, Integer> objectAndSize = verifyVector(obj, fieldType);
+                    rowValues.put(fieldName, objectAndSize.getLeft());
+                    rowSize += objectAndSize.getRight();
                     break;
-                case VarChar:
-                    rowSize += verifyVarchar(row.get(fieldType.getName()), fieldType, false);
+                }
+                case VarChar: {
+                    Pair<Object, Integer> objectAndSize = verifyVarchar(obj, fieldType);
+                    rowValues.put(fieldName, objectAndSize.getLeft());
+                    rowSize += objectAndSize.getRight();
                     break;
-                case JSON:
-                    Pair<Object, Integer> objectRowSize = verifyJSON(row.get(fieldType.getName()), fieldType);
-                    row.put(fieldType.getName(), objectRowSize.getLeft());
-                    rowSize += objectRowSize.getRight();
+                }
+                case JSON: {
+                    Pair<Object, Integer> objectAndSize = verifyJSON(obj, fieldType);
+                    rowValues.put(fieldName, objectAndSize.getLeft());
+                    rowSize += objectAndSize.getRight();
                     break;
-                case Array:
-                    rowSize += verifyArray(row.get(fieldType.getName()), fieldType);
+                }
+                case Array: {
+                    Pair<Object, Integer> objectAndSize = verifyArray(obj, fieldType);
+                    rowValues.put(fieldName, objectAndSize.getLeft());
+                    rowSize += objectAndSize.getRight();
+                    break;
+                }
+                case Bool:
+                case Int8:
+                case Int16:
+                case Int32:
+                case Int64:
+                case Float:
+                case Double:
+                    Pair<Object, Integer> objectAndSize = verifyScalar(obj, fieldType);
+                    rowValues.put(fieldName, objectAndSize.getLeft());
+                    rowSize += objectAndSize.getRight();
                     break;
                 default:
-                    rowSize += TypeSize.getSize(fieldType.getDataType());
+                    String msg = String.format("Unsupported data type of field '%s', not implemented in BulkWriter.", fieldName);
+                    ExceptionUtils.throwUnExpectedException(msg);
+            }
+        }
+
+        // process dynamic values
+        if (this.collectionSchema.isEnableDynamicField()) {
+            JsonObject dynamicValues = new JsonObject();
+            if (row.has(DYNAMIC_FIELD_NAME)) {
+                JsonElement value = row.get(DYNAMIC_FIELD_NAME);
+                if (!(value instanceof JsonObject)) {
+                    String msg = String.format("Dynamic field '%s' value should be JSON dict format", DYNAMIC_FIELD_NAME);
+                    ExceptionUtils.throwUnExpectedException(msg);
+                }
+                dynamicValues = (JsonObject) value;
+            }
+
+            for (String key : row.keySet()) {
+                if (!key.equals(DYNAMIC_FIELD_NAME) && !rowValues.containsKey(key)) {
+                    dynamicValues.add(key, row.get(key));
+                }
             }
+            String strValues = dynamicValues.toString();
+            rowValues.put(DYNAMIC_FIELD_NAME, strValues);
+            rowSize += strValues.length();
         }
 
         bufferLock.lock();
@@ -156,67 +211,88 @@ public abstract class BulkWriter {
         bufferRowCount += 1;
         totalRowCount += 1;
         bufferLock.unlock();
+
+        return rowValues;
     }
 
-    private Integer verifyVector(Object object, FieldType fieldType) {
+    private Pair<Object, Integer> verifyVector(JsonElement object, FieldType fieldType) {
         if (fieldType.getDataType() == DataType.FloatVector) {
-            ParamUtils.checkFieldData(fieldType, Lists.newArrayList(object), false);
-            return ((List<?>)object).size() * 4;
+            Object vector = ParamUtils.checkFieldValue(fieldType, object);
+            return Pair.of(vector, ((List<?>)vector).size() * 4);
         } else {
-            ParamUtils.checkFieldData(fieldType, Lists.newArrayList(object), false);
-            return ((ByteBuffer)object).position();
+            Object vector = ParamUtils.checkFieldValue(fieldType, object);
+            return Pair.of(vector, ((ByteBuffer)vector).position());
         }
     }
 
-    private Integer verifyVarchar(Object object, FieldType fieldType, boolean verifyElementType) {
-        ParamUtils.checkFieldData(fieldType, Lists.newArrayList(object), verifyElementType);
-
-        return String.valueOf(object).length();
+    private Pair<Object, Integer> verifyVarchar(JsonElement object, FieldType fieldType) {
+        Object varchar = ParamUtils.checkFieldValue(fieldType, object);
+        return Pair.of(varchar, String.valueOf(varchar).length());
     }
 
-    private Pair<Object, Integer> verifyJSON(Object object, FieldType fieldType) {
-        int size = 0;
-        if (object instanceof String) {
-            size = String.valueOf(object).length();
-            object = tryConvertJson(fieldType.getName(), object);
-        } else if (object instanceof JSONObject) {
-            size = ((JSONObject) object).toJSONString().length();
-        } else {
-            String msg = String.format("Illegal JSON value for field '%s', type mismatch", fieldType.getName());
-            ExceptionUtils.throwUnExpectedException(msg);
-        }
-        return Pair.of(object, size);
+    private Pair<Object, Integer> verifyJSON(JsonElement object, FieldType fieldType) {
+        String str = object.toString();
+        return Pair.of(str, str.length());
     }
 
-    private Integer verifyArray(Object object, FieldType fieldType) {
-        ParamUtils.checkFieldData(fieldType, (List<?>)object, true);
+    private Pair<Object, Integer> verifyArray(JsonElement object, FieldType fieldType) {
+        Object array = ParamUtils.checkFieldValue(fieldType, object);
 
         int rowSize = 0;
         DataType elementType = fieldType.getElementType();
         if (TypeSize.contains(elementType)) {
-            rowSize = TypeSize.getSize(elementType) * ((List<?>)object).size();
+            rowSize = TypeSize.getSize(elementType) * ((List<?>)array).size();
         } else if (elementType == DataType.VarChar) {
-            for (String ele : (List<String>) object) {
-                rowSize += verifyVarchar(ele, fieldType, true);
+            for (String str : (List<String>) array) {
+                rowSize += str.length();
             }
         } else {
             String msg = String.format("Unsupported element type for array field '%s'", fieldType.getName());
             ExceptionUtils.throwUnExpectedException(msg);
         }
 
-        return rowSize;
+        return Pair.of(array, rowSize);
     }
 
-    private Object tryConvertJson(String fieldName, Object object) {
-        if (object instanceof String) {
-            try {
-                return JSONObject.parseObject(String.valueOf(object));
-            } catch (Exception e) {
-                String msg = String.format("Illegal JSON value for field '%s', type mismatch or illegal format, error: %s", fieldName, e);
+    private Pair<Object, Integer> verifyScalar(JsonElement object, FieldType fieldType) {
+        if (!object.isJsonPrimitive()) {
+            String msg = String.format("Unsupported value type for field '%s'", fieldType.getName());
+            ExceptionUtils.throwUnExpectedException(msg);
+        }
+
+        JsonPrimitive value = object.getAsJsonPrimitive();
+        DataType dataType = fieldType.getDataType();
+        String fieldName = fieldType.getName();
+        if (dataType == DataType.Bool) {
+            if (!value.isBoolean()) {
+                String msg = String.format("Unsupported value type for field '%s', value is not boolean", fieldName);
+                ExceptionUtils.throwUnExpectedException(msg);
+            }
+            return Pair.of(value.getAsBoolean(), TypeSize.getSize(dataType));
+        } else {
+            if (!value.isNumber()) {
+                String msg = String.format("Unsupported value type for field '%s', value is not a number", fieldName);
                 ExceptionUtils.throwUnExpectedException(msg);
             }
+
+            switch (dataType) {
+                case Int8:
+                case Int16:
+                    return Pair.of(value.getAsShort(), TypeSize.getSize(dataType));
+                case Int32:
+                    return Pair.of(value.getAsInt(), TypeSize.getSize(dataType));
+                case Int64:
+                    return Pair.of(value.getAsLong(), TypeSize.getSize(dataType));
+                case Float:
+                    return Pair.of(value.getAsFloat(), TypeSize.getSize(dataType));
+                case Double:
+                    return Pair.of(value.getAsDouble(), TypeSize.getSize(dataType));
+                default:
+                    String msg = String.format("Field '%s' is not a scalar field", fieldName);
+                    ExceptionUtils.throwUnExpectedException(msg);
+            }
         }
-        return object;
+        return Pair.of(null, null);
     }
 
     private boolean hasPrimaryField(List<FieldType> fieldTypes) {

+ 5 - 3
src/main/java/io/milvus/bulkwriter/CloudImport.java

@@ -36,6 +36,8 @@ import java.util.HashMap;
 import java.util.Map;
 
 public class CloudImport {
+    private static final Gson GSON_INSTANCE = new Gson();
+
     public static BulkImportResponse bulkImport(String url, String apiKey, String objectUrl,
                                                 String accessKey, String secretKey, String clusterId, String collectionName) throws MalformedURLException {
         String requestURL;
@@ -54,7 +56,7 @@ public class CloudImport {
         params.put("collectionName", collectionName);
 
         String body = postRequest(requestURL, apiKey, params, 60 * 1000);
-        RestfulResponse<BulkImportResponse> response = new Gson().fromJson(body, new TypeToken<RestfulResponse<BulkImportResponse>>(){}.getType());
+        RestfulResponse<BulkImportResponse> response = GSON_INSTANCE.fromJson(body, new TypeToken<RestfulResponse<BulkImportResponse>>(){}.getType());
         handleResponse(url, response);
         return response.getData();
     }
@@ -73,7 +75,7 @@ public class CloudImport {
         params.put("jobId", jobId);
 
         String body = getRequest(requestURL, apiKey, params, 60 * 1000);
-        RestfulResponse<GetImportProgressResponse> response = new Gson().fromJson(body, new TypeToken<RestfulResponse<GetImportProgressResponse>>(){}.getType());
+        RestfulResponse<GetImportProgressResponse> response = GSON_INSTANCE.fromJson(body, new TypeToken<RestfulResponse<GetImportProgressResponse>>(){}.getType());
         handleResponse(url, response);
         return response.getData();
     }
@@ -93,7 +95,7 @@ public class CloudImport {
         params.put("currentPage", currentPage);
 
         String body = getRequest(requestURL, apiKey, params, 60 * 1000);
-        RestfulResponse<ListImportJobsResponse> response = new Gson().fromJson(body, new TypeToken<RestfulResponse<ListImportJobsResponse>>(){}.getType());
+        RestfulResponse<ListImportJobsResponse> response = GSON_INSTANCE.fromJson(body, new TypeToken<RestfulResponse<ListImportJobsResponse>>(){}.getType());
         handleResponse(url, response);
         return response.getData();
     }

+ 3 - 2
src/main/java/io/milvus/bulkwriter/LocalBulkWriter.java

@@ -19,7 +19,7 @@
 
 package io.milvus.bulkwriter;
 
-import com.alibaba.fastjson.JSONObject;
+import com.google.gson.JsonObject;
 import com.google.common.collect.Lists;
 import io.milvus.bulkwriter.common.clientenum.BulkFileType;
 import io.milvus.param.collection.CollectionSchemaParam;
@@ -67,7 +67,8 @@ public class LocalBulkWriter extends BulkWriter implements AutoCloseable {
         this.makeDir();
     }
 
-    public void appendRow(JSONObject rowData) throws IOException, InterruptedException {
+    @Override
+    public void appendRow(JsonObject rowData) throws IOException, InterruptedException {
         super.appendRow(rowData);
 
 //        only one thread can enter this section to persist data,

+ 2 - 2
src/main/java/io/milvus/bulkwriter/RemoteBulkWriter.java

@@ -19,7 +19,7 @@
 
 package io.milvus.bulkwriter;
 
-import com.alibaba.fastjson.JSONObject;
+import com.google.gson.JsonObject;
 import com.azure.storage.blob.models.BlobErrorCode;
 import com.azure.storage.blob.models.BlobStorageException;
 import com.google.common.collect.Lists;
@@ -67,7 +67,7 @@ public class RemoteBulkWriter extends LocalBulkWriter {
     }
 
     @Override
-    public void appendRow(JSONObject rowData) throws IOException, InterruptedException {
+    public void appendRow(JsonObject rowData) throws IOException, InterruptedException {
         super.appendRow(rowData);
     }
 

+ 7 - 0
src/main/java/io/milvus/bulkwriter/common/utils/ParquetUtils.java

@@ -28,6 +28,8 @@ import org.apache.parquet.schema.Types;
 
 import java.util.List;
 
+import static io.milvus.param.Constant.DYNAMIC_FIELD_NAME;
+
 public class ParquetUtils {
     public static MessageType parseCollectionSchema(CollectionSchemaParam collectionSchema) {
         List<FieldType> fieldTypes = collectionSchema.getFieldTypes();
@@ -87,6 +89,11 @@ public class ParquetUtils {
 
             }
         }
+
+        if (collectionSchema.isEnableDynamicField()) {
+            messageTypeBuilder.required(PrimitiveType.PrimitiveTypeName.BINARY).as(LogicalTypeAnnotation.stringType())
+                    .named(DYNAMIC_FIELD_NAME);
+        }
         return messageTypeBuilder.named("schema");
     }
 

+ 209 - 48
src/main/java/io/milvus/param/ParamUtils.java

@@ -19,12 +19,11 @@
 
 package io.milvus.param;
 
-import com.alibaba.fastjson.JSONObject;
-import com.google.common.collect.Lists;
+import com.google.gson.*;
+import com.google.gson.reflect.TypeToken;
 import com.google.protobuf.ByteString;
 import io.milvus.common.clientenum.ConsistencyLevelEnum;
 import io.milvus.common.utils.JacksonUtils;
-import io.milvus.exception.IllegalResponseException;
 import io.milvus.exception.ParamException;
 import io.milvus.grpc.*;
 import io.milvus.param.collection.FieldType;
@@ -47,27 +46,51 @@ import java.util.stream.Collectors;
  * Utility functions for param classes
  */
 public class ParamUtils {
-    public static HashMap<DataType, String> getTypeErrorMsg() {
+    private static final Gson GSON_INSTANCE = new Gson();
+
+    private static HashMap<DataType, String> getTypeErrorMsgForColumnInsert() {
+        final HashMap<DataType, String> typeErrMsg = new HashMap<>();
+        typeErrMsg.put(DataType.None, "Type mismatch for field '%s': the field type is illegal.");
+        typeErrMsg.put(DataType.Bool, "Type mismatch for field '%s': Bool field value type must be Boolean.");
+        typeErrMsg.put(DataType.Int8, "Type mismatch for field '%s': Int32/Int16/Int8 field value type must be Short or Integer.");
+        typeErrMsg.put(DataType.Int16, "Type mismatch for field '%s': Int32/Int16/Int8 field value type must be Short or Integer.");
+        typeErrMsg.put(DataType.Int32, "Type mismatch for field '%s': Int32/Int16/Int8 field value type must be Short or Integer.");
+        typeErrMsg.put(DataType.Int64, "Type mismatch for field '%s': Int64 field value type must be Long.");
+        typeErrMsg.put(DataType.Float, "Type mismatch for field '%s': Float field value type must be Float.");
+        typeErrMsg.put(DataType.Double, "Type mismatch for field '%s': Double field value type must be Double.");
+        typeErrMsg.put(DataType.String, "Type mismatch for field '%s': String field value type must be String."); // actually String type is useless
+        typeErrMsg.put(DataType.VarChar, "Type mismatch for field '%s': VarChar field value type must be String, and the string length must shorter than max_length.");
+        typeErrMsg.put(DataType.Array, "Type mismatch for field '%s': Array field value type must be List<Object>, each object type must be element_type, and the array length must be shorter than max_capacity.");
+        typeErrMsg.put(DataType.FloatVector, "Type mismatch for field '%s': Float vector field's value type must be List<Float>.");
+        typeErrMsg.put(DataType.BinaryVector, "Type mismatch for field '%s': Binary vector field's value type must be ByteBuffer.");
+        typeErrMsg.put(DataType.Float16Vector, "Type mismatch for field '%s': Float16 vector field's value type must be ByteBuffer.");
+        typeErrMsg.put(DataType.BFloat16Vector, "Type mismatch for field '%s': BFloat16 vector field's value type must be ByteBuffer.");
+        typeErrMsg.put(DataType.SparseFloatVector, "Type mismatch for field '%s': SparseFloatVector vector field's value type must be SortedMap<Long, Float>.");
+        return typeErrMsg;
+    }
+
+    private static HashMap<DataType, String> getTypeErrorMsgForRowInsert() {
         final HashMap<DataType, String> typeErrMsg = new HashMap<>();
-        typeErrMsg.put(DataType.None, "Type mismatch for field '%s': the field type is illegal");
-        typeErrMsg.put(DataType.Bool, "Type mismatch for field '%s': Bool field value type must be Boolean");
-        typeErrMsg.put(DataType.Int8, "Type mismatch for field '%s': Int32/Int16/Int8 field value type must be Short or Integer");
-        typeErrMsg.put(DataType.Int16, "Type mismatch for field '%s': Int32/Int16/Int8 field value type must be Short or Integer");
-        typeErrMsg.put(DataType.Int32, "Type mismatch for field '%s': Int32/Int16/Int8 field value type must be Short or Integer");
-        typeErrMsg.put(DataType.Int64, "Type mismatch for field '%s': Int64 field value type must be Long");
-        typeErrMsg.put(DataType.Float, "Type mismatch for field '%s': Float field value type must be Float");
-        typeErrMsg.put(DataType.Double, "Type mismatch for field '%s': Double field value type must be Double");
-        typeErrMsg.put(DataType.String, "Type mismatch for field '%s': String field value type must be String");
-        typeErrMsg.put(DataType.VarChar, "Type mismatch for field '%s': VarChar field value type must be String");
-        typeErrMsg.put(DataType.FloatVector, "Type mismatch for field '%s': Float vector field's value type must be List<Float>");
-        typeErrMsg.put(DataType.BinaryVector, "Type mismatch for field '%s': Binary vector field's value type must be ByteBuffer");
-        typeErrMsg.put(DataType.Float16Vector, "Type mismatch for field '%s': Float16 vector field's value type must be ByteBuffer");
-        typeErrMsg.put(DataType.BFloat16Vector, "Type mismatch for field '%s': BFloat16 vector field's value type must be ByteBuffer");
-        typeErrMsg.put(DataType.SparseFloatVector, "Type mismatch for field '%s': SparseFloatVector vector field's value type must be SortedMap");
+        typeErrMsg.put(DataType.None, "Type mismatch for field '%s': the field type is illegal.");
+        typeErrMsg.put(DataType.Bool, "Type mismatch for field '%s': Bool field value type must be JsonPrimitive.");
+        typeErrMsg.put(DataType.Int8, "Type mismatch for field '%s': Int32/Int16/Int8 field value type must be JsonPrimitive of boolean.");
+        typeErrMsg.put(DataType.Int16, "Type mismatch for field '%s': Int32/Int16/Int8 field value type must be JsonPrimitive of number.");
+        typeErrMsg.put(DataType.Int32, "Type mismatch for field '%s': Int32/Int16/Int8 field value type must be JsonPrimitive of number.");
+        typeErrMsg.put(DataType.Int64, "Type mismatch for field '%s': Int64 field value type must be JsonPrimitive of number.");
+        typeErrMsg.put(DataType.Float, "Type mismatch for field '%s': Float field value type must be JsonPrimitive of number.");
+        typeErrMsg.put(DataType.Double, "Type mismatch for field '%s': Double field value type must be JsonPrimitive of number.");
+        typeErrMsg.put(DataType.String, "Type mismatch for field '%s': String field value type must be JsonPrimitive of string."); // actually String type is useless
+        typeErrMsg.put(DataType.VarChar, "Type mismatch for field '%s': VarChar field value type must be JsonPrimitive of string, and the string length must shorter than max_length.");
+        typeErrMsg.put(DataType.Array, "Type mismatch for field '%s': Array field value type must be JsonArray, each object type must be element_type, and the array length must be shorter than max_capacity.");
+        typeErrMsg.put(DataType.FloatVector, "Type mismatch for field '%s': Float vector field's value type must be JsonArray of List<Float>.");
+        typeErrMsg.put(DataType.BinaryVector, "Type mismatch for field '%s': Binary vector field's value type must be JsonArray of byte[].");
+        typeErrMsg.put(DataType.Float16Vector, "Type mismatch for field '%s': Float16 vector field's value type must be JsonArray of byte[].");
+        typeErrMsg.put(DataType.BFloat16Vector, "Type mismatch for field '%s': BFloat16 vector field's value type must be JsonArray of byte[].");
+        typeErrMsg.put(DataType.SparseFloatVector, "Type mismatch for field '%s': SparseFloatVector vector field's value type must be JsonObject of Map<Long, Float>.");
         return typeErrMsg;
     }
 
-    private static void checkFieldData(FieldType fieldSchema, InsertParam.Field fieldData) {
+    public static void checkFieldData(FieldType fieldSchema, InsertParam.Field fieldData) {
         List<?> values = fieldData.getValues();
         checkFieldData(fieldSchema, values, false);
     }
@@ -85,7 +108,7 @@ public class ParamUtils {
     }
 
     public static void checkFieldData(FieldType fieldSchema, List<?> values, boolean verifyElementType) {
-        HashMap<DataType, String> errMsgs = getTypeErrorMsg();
+        HashMap<DataType, String> errMsgs = getTypeErrorMsgForColumnInsert();
         DataType dataType = verifyElementType ? fieldSchema.getElementType() : fieldSchema.getDataType();
 
         if (verifyElementType && values.size() > fieldSchema.getMaxCapacity()) {
@@ -134,7 +157,7 @@ public class ParamUtils {
                     int real_dim = calculateBinVectorDim(dataType, v.position());
                     if (real_dim != dim) {
                         String msg = "Incorrect dimension for field '%s': the no.%d vector's dimension: %d is not equal to field's dimension: %d";
-                        throw new ParamException(String.format(msg, fieldSchema.getName(), i, v.position()*8, dim));
+                        throw new ParamException(String.format(msg, fieldSchema.getName(), i, real_dim, dim));
                     }
                 }
                 break;
@@ -151,13 +174,8 @@ public class ParamUtils {
                         String msg = "Not allow empty SortedMap for sparse vector field '%s'";
                         throw new ParamException(String.format(msg, fieldSchema.getName()));
                     }
-                    if (!(m.firstKey() instanceof Long)) {
-                        String msg = "The key of SortedMap must be Long for sparse vector field '%s'";
-                        throw new ParamException(String.format(msg, fieldSchema.getName()));
-                    }
-                    if (!(m.get(m.firstKey()) instanceof Float)) {
-                        String msg = "The value of SortedMap must be Float for sparse vector field '%s'";
-                        throw new ParamException(String.format(msg, fieldSchema.getName()));
+                    if (!(m.firstKey() instanceof Long) || !(m.get(m.firstKey()) instanceof Float)) {
+                        throw new ParamException(String.format(errMsgs.get(dataType), fieldSchema.getName()));
                     }
                 }
                 break;
@@ -204,11 +222,14 @@ public class ParamUtils {
                     if (!(value instanceof String)) {
                         throw new ParamException(String.format(errMsgs.get(dataType), fieldSchema.getName()));
                     }
+                    if (((String) value).length() > fieldSchema.getMaxLength()) {
+                        throw new ParamException(String.format(errMsgs.get(dataType), fieldSchema.getName()));
+                    }
                 }
                 break;
             case JSON:
                 for (Object value : values) {
-                    if (!(value instanceof JSONObject)) {
+                    if (!(value instanceof JsonElement)) {
                         throw new ParamException(String.format(errMsgs.get(dataType), fieldSchema.getName()));
                     }
                 }
@@ -219,12 +240,153 @@ public class ParamUtils {
                         throw new ParamException(String.format(errMsgs.get(dataType), fieldSchema.getName()));
                     }
 
-                    List<?> temp = (List<?>)value;
-                    checkFieldData(fieldSchema, temp, true);
+                    List<?> array = (List<?>)value;
+                    if (array.size() > fieldSchema.getMaxCapacity()) {
+                        throw new ParamException(String.format(errMsgs.get(dataType), fieldSchema.getName()));
+                    }
+                    checkFieldData(fieldSchema, array, true);
                 }
                 break;
             default:
-                throw new IllegalResponseException("Unsupported data type returned by FieldData");
+                throw new ParamException("Unsupported data type returned by FieldData");
+        }
+    }
+
+    public static Object checkFieldValue(FieldType fieldSchema, JsonElement value) {
+        HashMap<DataType, String> errMsgs = getTypeErrorMsgForRowInsert();
+        DataType dataType = fieldSchema.getDataType();
+
+        switch (dataType) {
+            case FloatVector: {
+                if (!(value.isJsonArray())) {
+                    throw new ParamException(String.format(errMsgs.get(dataType), fieldSchema.getName()));
+                }
+                int dim = fieldSchema.getDimension();
+                try {
+                    List<Float> vector = GSON_INSTANCE.fromJson(value, new TypeToken<List<Float>>() {}.getType());
+                    if (vector.size() != dim) {
+                        String msg = "Incorrect dimension for field '%s': dimension: %d is not equal to field's dimension: %d";
+                        throw new ParamException(String.format(msg, fieldSchema.getName(), vector.size(), dim));
+                    }
+                    return vector; // return List<Float> for genFieldData()
+                } catch (JsonSyntaxException e) {
+                    throw new ParamException(String.format("Unable to convert JsonArray to List<Float> for field '%s'. Reason: %s",
+                            fieldSchema.getName(), e.getCause().getMessage()));
+                }
+            }
+            case BinaryVector:
+            case Float16Vector:
+            case BFloat16Vector: {
+                if (!(value.isJsonArray())) {
+                    throw new ParamException(String.format(errMsgs.get(dataType), fieldSchema.getName()));
+                }
+                int dim = fieldSchema.getDimension();
+                try {
+                    byte[] v = GSON_INSTANCE.fromJson(value, new TypeToken<byte[]>() {}.getType());
+                    int real_dim = calculateBinVectorDim(dataType, v.length);
+                    if (real_dim != dim) {
+                        String msg = "Incorrect dimension for field '%s': dimension: %d is not equal to field's dimension: %d";
+                        throw new ParamException(String.format(msg, fieldSchema.getName(), real_dim, dim));
+                    }
+                    return ByteBuffer.wrap(v); // return ByteBuffer for genFieldData()
+                } catch (JsonSyntaxException e) {
+                    throw new ParamException(String.format("Unable to convert JsonArray to List<Float> for field '%s'. Reason: %s",
+                            fieldSchema.getName(), e.getCause().getMessage()));
+                }
+            }
+            case SparseFloatVector:
+                if (!(value.isJsonObject())) {
+                    throw new ParamException(String.format(errMsgs.get(dataType), fieldSchema.getName()));
+                }
+                try {
+                    // return SortedMap<Long, Float> for genFieldData()
+                    return GSON_INSTANCE.fromJson(value, new TypeToken<SortedMap<Long, Float>>() {}.getType());
+                } catch (JsonSyntaxException e) {
+                    throw new ParamException(String.format("Unable to convert JsonObject to SortedMap<Long, Float> for field '%s'. Reason: %s",
+                            fieldSchema.getName(), e.getCause().getMessage()));
+                }
+            case Int64:
+                if (!(value.isJsonPrimitive())) {
+                    throw new ParamException(String.format(errMsgs.get(dataType), fieldSchema.getName()));
+                }
+                return value.getAsLong(); // return long for genFieldData()
+            case Int32:
+            case Int16:
+            case Int8:
+                if (!(value.isJsonPrimitive())) {
+                    throw new ParamException(String.format(errMsgs.get(dataType), fieldSchema.getName()));
+                }
+                return value.getAsInt(); // return int for genFieldData()
+            case Bool:
+                if (!(value.isJsonPrimitive())) {
+                    throw new ParamException(String.format(errMsgs.get(dataType), fieldSchema.getName()));
+                }
+                return value.getAsBoolean(); // return boolean for genFieldData()
+            case Float:
+                if (!(value.isJsonPrimitive())) {
+                    throw new ParamException(String.format(errMsgs.get(dataType), fieldSchema.getName()));
+                }
+                return value.getAsFloat(); // return float for genFieldData()
+            case Double:
+                if (!(value.isJsonPrimitive())) {
+                    throw new ParamException(String.format(errMsgs.get(dataType), fieldSchema.getName()));
+                }
+                return value.getAsDouble(); // return double for genFieldData()
+            case VarChar:
+            case String:
+                if (!(value.isJsonPrimitive())) {
+                    throw new ParamException(String.format(errMsgs.get(dataType), fieldSchema.getName()));
+                }
+                JsonPrimitive p = value.getAsJsonPrimitive();
+                if (!p.isString()) {
+                    throw new ParamException(String.format("JsonPrimitive should be String type for field '%s'", fieldSchema.getName()));
+                }
+
+                String str = p.getAsString();
+                if (str.length() > fieldSchema.getMaxLength()) {
+                    throw new ParamException(String.format(errMsgs.get(dataType), fieldSchema.getName()));
+                }
+                return str; // return String for genFieldData()
+            case JSON:
+                return value; // return JsonElement for genFieldData()
+            case Array:
+                if (!(value.isJsonArray())) {
+                    throw new ParamException(String.format(errMsgs.get(dataType), fieldSchema.getName()));
+                }
+
+                List<Object> array = convertJsonArray(value.getAsJsonArray(), fieldSchema.getElementType(), fieldSchema.getName());
+                if (array.size() > fieldSchema.getMaxCapacity()) {
+                    throw new ParamException(String.format(errMsgs.get(dataType), fieldSchema.getName()));
+                }
+                return array; // return List<Object> for genFieldData()
+            default:
+                throw new ParamException("Unsupported data type returned by FieldData");
+        }
+    }
+
+    public static List<Object> convertJsonArray(JsonArray jsonArray, DataType elementType, String fieldName) {
+        try {
+            switch (elementType) {
+                case Int64:
+                    return GSON_INSTANCE.fromJson(jsonArray, new TypeToken<List<Long>>() {}.getType());
+                case Int32:
+                case Int16:
+                case Int8:
+                    return GSON_INSTANCE.fromJson(jsonArray, new TypeToken<List<Integer>>() {}.getType());
+                case Bool:
+                    return GSON_INSTANCE.fromJson(jsonArray, new TypeToken<List<Boolean>>() {}.getType());
+                case Float:
+                    return GSON_INSTANCE.fromJson(jsonArray, new TypeToken<List<Float>>() {}.getType());
+                case Double:
+                    return GSON_INSTANCE.fromJson(jsonArray, new TypeToken<List<Double>>() {}.getType());
+                case VarChar:
+                    return GSON_INSTANCE.fromJson(jsonArray, new TypeToken<List<String>>() {}.getType());
+                default:
+                    throw new ParamException(String.format("Unsupported element type of Array field '%s'", fieldName));
+            }
+        } catch (JsonSyntaxException e) {
+            throw new ParamException(String.format("Unable to convert JsonArray to List<Object> for field '%s'. Reason: %s",
+                    fieldName, e.getCause().getMessage()));
         }
     }
 
@@ -335,7 +497,7 @@ public class ParamUtils {
 
             // convert insert data
             List<InsertParam.Field> columnFields = requestParam.getFields();
-            List<JSONObject> rowFields = requestParam.getRows();
+            List<JsonObject> rowFields = requestParam.getRows();
 
             if (CollectionUtils.isNotEmpty(columnFields)) {
                 checkAndSetColumnData(wrapper, columnFields);
@@ -388,7 +550,7 @@ public class ParamUtils {
             }
         }
 
-        private void checkAndSetRowData(DescCollResponseWrapper wrapper, List<JSONObject> rows) {
+        private void checkAndSetRowData(DescCollResponseWrapper wrapper, List<JsonObject> rows) {
             List<FieldType> fieldTypes = wrapper.getFields();
 
             Map<String, InsertDataInfo> nameInsertInfo = new HashMap<>();
@@ -399,22 +561,21 @@ public class ParamUtils {
                             .withIsDynamic(true)
                             .build())
                     .data(new LinkedList<>()).build();
-            for (JSONObject row : rows) {
+            for (JsonObject row : rows) {
                 for (FieldType fieldType : fieldTypes) {
                     String fieldName = fieldType.getName();
                     InsertDataInfo insertDataInfo = nameInsertInfo.getOrDefault(fieldName, InsertDataInfo.builder()
                             .fieldType(fieldType).data(new LinkedList<>()).build());
 
                     // check normalField
-                    Object rowFieldData = row.get(fieldName);
-                    if (rowFieldData != null) {
+                    JsonElement rowFieldData = row.get(fieldName);
+                    if (rowFieldData != null && !rowFieldData.isJsonNull()) {
                         if (fieldType.isAutoID()) {
                             String msg = String.format("The primary key: %s is auto generated, no need to input.", fieldName);
                             throw new ParamException(msg);
                         }
-                        checkFieldData(fieldType, Lists.newArrayList(rowFieldData), false);
-
-                        insertDataInfo.getData().add(rowFieldData);
+                        Object fieldValue = checkFieldValue(fieldType, rowFieldData);
+                        insertDataInfo.getData().add(fieldValue);
                         nameInsertInfo.put(fieldName, insertDataInfo);
                     } else {
                         // check if autoId
@@ -427,10 +588,10 @@ public class ParamUtils {
 
                 // deal with dynamicField
                 if (wrapper.getEnableDynamicField()) {
-                    JSONObject dynamicField = new JSONObject();
+                    JsonObject dynamicField = new JsonObject();
                     for (String rowFieldName : row.keySet()) {
                         if (!nameInsertInfo.containsKey(rowFieldName)) {
-                            dynamicField.put(rowFieldName, row.get(rowFieldName));
+                            dynamicField.add(rowFieldName, row.get(rowFieldName));
                         }
                     }
                     insertDynamicDataInfo.getData().add(dynamicField);
@@ -781,11 +942,11 @@ public class ParamUtils {
         return vectorDataType.contains(dataType);
     }
 
-    private static FieldData genFieldData(FieldType fieldType, List<?> objects) {
+    public static FieldData genFieldData(FieldType fieldType, List<?> objects) {
         return genFieldData(fieldType, objects, Boolean.FALSE);
     }
 
-    private static FieldData genFieldData(FieldType fieldType, List<?> objects, boolean isDynamic) {
+    public static FieldData genFieldData(FieldType fieldType, List<?> objects, boolean isDynamic) {
         if (objects == null) {
             throw new ParamException("Cannot generate FieldData from null object");
         }
@@ -830,9 +991,9 @@ public class ParamUtils {
             for (Object object : objects) {
                 ByteBuffer buf = (ByteBuffer) object;
                 if (totalBuf == null) {
-                    totalBuf = ByteBuffer.allocate(buf.position() * objects.size());
+                    totalBuf = ByteBuffer.allocate(buf.limit() * objects.size());
                     totalBuf.put(buf.array());
-                    dim = calculateBinVectorDim(dataType, buf.position());
+                    dim = calculateBinVectorDim(dataType, buf.limit());
                 } else {
                     totalBuf.put(buf.array());
                 }
@@ -951,7 +1112,7 @@ public class ParamUtils {
                 return ScalarField.newBuilder().setStringData(stringArray).build();
             }
             case JSON: {
-                List<ByteString> byteStrings = objects.stream().map(p -> ByteString.copyFromUtf8(((JSONObject) p).toJSONString()))
+                List<ByteString> byteStrings = objects.stream().map(p -> ByteString.copyFromUtf8(p.toString()))
                         .collect(Collectors.toList());
                 JSONArray jsonArray = JSONArray.newBuilder().addAllData(byteStrings).build();
                 return ScalarField.newBuilder().setJsonData(jsonArray).build();

+ 27 - 7
src/main/java/io/milvus/param/dml/InsertParam.java

@@ -19,7 +19,7 @@
 
 package io.milvus.param.dml;
 
-import com.alibaba.fastjson.JSONObject;
+import com.google.gson.JsonObject;
 import io.milvus.exception.ParamException;
 import io.milvus.param.ParamUtils;
 
@@ -37,7 +37,7 @@ import java.util.List;
 @ToString
 public class InsertParam {
     protected final List<Field> fields;
-    protected final List<JSONObject> rows;
+    protected final List<JsonObject> rows;
 
     protected final String databaseName;
     protected final String collectionName;
@@ -65,7 +65,7 @@ public class InsertParam {
         protected String collectionName;
         protected String partitionName = "";
         protected List<InsertParam.Field> fields;
-        protected List<JSONObject> rows;
+        protected List<JsonObject> rows;
         protected int rowCount;
 
         protected Builder() {
@@ -120,11 +120,31 @@ public class InsertParam {
         /**
          * Sets the row data to insert. The rows list cannot be empty.
          *
+         * Internal class for insert data.
+         * If dataType is Bool/Int8/Int16/Int32/Int64/Float/Double/Varchar, use JsonObject.addProperty(key, value) to input;
+         * If dataType is FloatVector, use JsonObject.add(key, gson.toJsonTree(List[Float]) to input;
+         * If dataType is BinaryVector/Float16Vector/BFloat16Vector, use JsonObject.add(key, gson.toJsonTree(byte[])) to input;
+         * If dataType is SparseFloatVector, use JsonObject.add(key, gson.toJsonTree(SortedMap[Long, Float])) to input;
+         * If dataType is Array, use JsonObject.add(key, gson.toJsonTree(List of Boolean/Integer/Short/Long/Float/Double/String)) to input;
+         * If dataType is JSON, use JsonObject.add(key, JsonElement) to input;
+         *
+         * Note:
+         * 1. For scalar numeric values, value will be cut according to the type of the field.
+         * For example:
+         *   An Int8 field named "XX", you set the value to be 128 by JsonObject.add("XX", 128), the value 128 is cut to -128.
+         *   An Int64 field named "XX", you set the value to be 3.9 by JsonObject.add("XX", 3.9), the value 3.9 is cut to 3.
+         *
+         * 2. String value can be parsed to numeric/boolean type if the value is valid.
+         * For example:
+         *   A Bool field named "XX", you set the value to be "TRUE" by JsonObject.add("XX", "TRUE"), the string "TRUE" is parsed as true.
+         *   A Float field named "XX", you set the value to be "3.5" by JsonObject.add("XX", "3.5", the string "3.5" is parsed as 3.5.
+         *
+         *
          * @param rows insert row data
          * @return <code>Builder</code>
-         * @see JSONObject
+         * @see JsonObject
          */
-        public Builder withRows(@NonNull List<JSONObject> rows) {
+        public Builder withRows(@NonNull List<JsonObject> rows) {
             this.rows = rows;
             return this;
         }
@@ -191,7 +211,7 @@ public class InsertParam {
         }
 
         protected void checkRows() {
-            for (JSONObject row : rows) {
+            for (JsonObject row : rows) {
                 if (row == null) {
                     throw new ParamException("Row cannot be null." +
                             " If the field is auto-id, just ignore it from withRows()");
@@ -220,7 +240,7 @@ public class InsertParam {
      * If dataType is BinaryVector/Float16Vector/BFloat16Vector, values is List of ByteBuffer;
      * If dataType is SparseFloatVector, values is List of SortedMap[Long, Float];
      * If dataType is Array, values can be List of List Boolean/Integer/Short/Long/Float/Double/String;
-     * If dataType is JSON, values is List of JSONObject;
+     * If dataType is JSON, values is List of gson.JsonObject;
      *
      * Note:
      * If dataType is Int8/Int16/Int32, values is List of Integer or Short

+ 3 - 4
src/main/java/io/milvus/param/dml/UpsertParam.java

@@ -19,12 +19,11 @@
 
 package io.milvus.param.dml;
 
-import com.alibaba.fastjson.JSONObject;
+import com.google.gson.JsonObject;
 import io.milvus.exception.ParamException;
 
 import lombok.NonNull;
 import lombok.ToString;
-import org.apache.commons.collections4.CollectionUtils;
 
 import java.util.List;
 
@@ -100,9 +99,9 @@ public class UpsertParam extends InsertParam {
          *
          * @param rows insert row data
          * @return <code>Builder</code>
-         * @see JSONObject
+         * @see JsonObject
          */
-        public Builder withRows(@NonNull List<JSONObject> rows) {
+        public Builder withRows(@NonNull List<JsonObject> rows) {
             super.withRows(rows);
             return this;
         }

+ 3 - 3
src/main/java/io/milvus/param/dml/ranker/RRFRanker.java

@@ -19,7 +19,7 @@
 
 package io.milvus.param.dml.ranker;
 
-import com.alibaba.fastjson.JSONObject;
+import com.google.gson.JsonObject;
 import java.util.HashMap;
 import java.util.Map;
 
@@ -44,8 +44,8 @@ public class RRFRanker extends BaseRanker {
 
     @Override
     public Map<String, String> getProperties() {
-        JSONObject params = new JSONObject();
-        params.put("k", this.k);
+        JsonObject params = new JsonObject();
+        params.addProperty("k", this.k);
 
         Map<String, String> props = new HashMap<>();
         props.put("strategy", "rrf");

+ 4 - 3
src/main/java/io/milvus/param/dml/ranker/WeightedRanker.java

@@ -19,7 +19,8 @@
 
 package io.milvus.param.dml.ranker;
 
-import com.alibaba.fastjson.JSONObject;
+import com.google.gson.*;
+import com.google.gson.reflect.TypeToken;
 import io.milvus.exception.ParamException;
 
 import lombok.Getter;
@@ -43,8 +44,8 @@ public class WeightedRanker extends BaseRanker {
 
     @Override
     public Map<String, String> getProperties() {
-        JSONObject params = new JSONObject();
-        params.put("weights", this.weights);
+        JsonObject params = new JsonObject();
+        params.add("weights", new Gson().toJsonTree(this.weights).getAsJsonArray());
 
         Map<String, String> props = new HashMap<>();
         props.put("strategy", "weighted");

+ 24 - 4
src/main/java/io/milvus/param/highlevel/dml/InsertRowsParam.java

@@ -19,7 +19,7 @@
 
 package io.milvus.param.highlevel.dml;
 
-import com.alibaba.fastjson.JSONObject;
+import com.google.gson.JsonObject;
 import io.milvus.exception.ParamException;
 import io.milvus.param.ParamUtils;
 import io.milvus.param.dml.InsertParam;
@@ -51,7 +51,7 @@ public class InsertRowsParam {
      */
     public static class Builder {
         private String collectionName;
-        private List<JSONObject> rows;
+        private List<JsonObject> rows;
 
         private Builder() {
         }
@@ -71,11 +71,31 @@ public class InsertRowsParam {
         /**
          * Sets the row data to insert. The rows list cannot be empty.
          *
+         * Internal class for insert data.
+         * If dataType is Bool/Int8/Int16/Int32/Int64/Float/Double/Varchar, use JsonObject.addProperty(key, value) to input;
+         * If dataType is FloatVector, use JsonObject.add(key, gson.toJsonTree(List[Float])) to input;
+         * If dataType is BinaryVector/Float16Vector/BFloat16Vector, use JsonObject.add(key, gson.toJsonTree(byte[])) to input;
+         * If dataType is SparseFloatVector, use JsonObject.add(key, gson.toJsonTree(SortedMap[Long, Float])) to input;
+         * If dataType is Array, use JsonObject.add(key, gson.toJsonTree(List of Boolean/Integer/Short/Long/Float/Double/String)) to input;
+         * If dataType is JSON, use JsonObject.add(key, JsonElement) to input;
+         *
+         * Note:
+         * 1. For scalar numeric values, value will be cut according to the type of the field.
+         * For example:
+         *   An Int8 field named "XX", you set the value to be 128 by JsonObject.add("XX", 128), the value 128 is cut to -128.
+         *   An Int64 field named "XX", you set the value to be 3.9 by JsonObject.add("XX", 3.9), the value 3.9 is cut to 3.
+         *
+         * 2. String value can be parsed to numeric/boolean type if the value is valid.
+         * For example:
+         *   A Bool field named "XX", you set the value to be "TRUE" by JsonObject.add("XX", "TRUE"), the string "TRUE" is parsed as true.
+         *   A Float field named "XX", you set the value to be "3.5" by JsonObject.add("XX", "3.5", the string "3.5" is parsed as 3.5.
+         *
+         *
          * @param rows insert row data
          * @return <code>Builder</code>
-         * @see JSONObject
+         * @see JsonObject
          */
-        public Builder withRows(@NonNull List<JSONObject> rows) {
+        public Builder withRows(@NonNull List<JsonObject> rows) {
             this.rows = rows;
             return this;
         }

+ 50 - 11
src/main/java/io/milvus/response/FieldDataWrapper.java

@@ -19,7 +19,7 @@
 
 package io.milvus.response;
 
-import com.alibaba.fastjson.JSONObject;
+import com.google.gson.*;
 import com.google.protobuf.ProtocolStringList;
 import io.milvus.exception.ParamException;
 import io.milvus.grpc.*;
@@ -317,8 +317,12 @@ public class FieldDataWrapper {
 
     public String getAsString(int index, String paramName) throws IllegalResponseException {
         if (isJsonField()) {
-            JSONObject jsonObject = parseObjectData(index);
-            return jsonObject.getString(paramName);
+            JsonElement jsonElement = parseObjectData(index);
+            if (jsonElement instanceof JsonObject) {
+                return ((JsonObject)jsonElement).get(paramName).getAsString();
+            } else {
+                throw new IllegalResponseException("The JSON element is not a dict");
+            }
         }
         throw new IllegalResponseException("Only JSON type support this operation");
     }
@@ -339,12 +343,26 @@ public class FieldDataWrapper {
         throw new IllegalResponseException("Only JSON type support this operation");
     }
 
+    /**
+     * Gets a field's value by field name.
+     *
+     * @param index which row
+     * @param paramName which field
+     * @return returns Long for integer value, returns Double for decimal value,
+     *   returns String for string value, returns JsonElement for JSON object and Array.
+     */
     public Object get(int index, String paramName) throws IllegalResponseException {
-        if (isJsonField()) {
-            JSONObject jsonObject = parseObjectData(index);
-            return jsonObject.get(paramName);
+        if (!isJsonField()) {
+            throw new IllegalResponseException("Only JSON type support this operation");
         }
-        throw new IllegalResponseException("Only JSON type support this operation");
+
+        JsonElement jsonElement = parseObjectData(index);
+        if (!(jsonElement instanceof JsonObject)) {
+            throw new IllegalResponseException("The JSON element is not a dict");
+        }
+
+        JsonElement element = ((JsonObject)jsonElement).get(paramName);
+        return ValueOfJSONElement(element);
     }
 
     public Object valueByIdx(int index) throws ParamException {
@@ -355,18 +373,39 @@ public class FieldDataWrapper {
         return data.get(index);
     }
 
-    private JSONObject parseObjectData(int index) {
+    private JsonElement parseObjectData(int index) {
         Object object = valueByIdx(index);
         return ParseJSONObject(object);
     }
 
-    public static JSONObject ParseJSONObject(Object object) {
+    public static JsonElement ParseJSONObject(Object object) {
         if (object instanceof String) {
-            return JSONObject.parseObject((String)object);
+            return JsonParser.parseString((String)object);
         } else if (object instanceof byte[]) {
-            return JSONObject.parseObject(new String((byte[]) object));
+            return JsonParser.parseString(new String((byte[]) object));
         } else {
             throw new IllegalResponseException("Illegal type value for JSON parser");
         }
     }
+
+    public static Object ValueOfJSONElement(JsonElement element) {
+        if (element == null || element.isJsonNull()) {
+            return null;
+        }
+        if (element.isJsonPrimitive()) {
+            JsonPrimitive primitive = (JsonPrimitive) element;
+            if (primitive.isString()) {
+                return primitive.getAsString();
+            } else if (primitive.isBoolean()) {
+                return primitive.getAsBoolean();
+            } else if (primitive.isNumber()) {
+                if (primitive.getAsBigDecimal().scale() == 0) {
+                    return primitive.getAsLong();
+                } else {
+                    return primitive.getAsDouble();
+                }
+            }
+        }
+        return element;
+    }
 }

+ 2 - 2
src/main/java/io/milvus/response/QueryResultsWrapper.java

@@ -19,7 +19,7 @@
 
 package io.milvus.response;
 
-import com.alibaba.fastjson.JSONObject;
+import com.google.gson.*;
 import io.milvus.exception.ParamException;
 import io.milvus.grpc.*;
 import io.milvus.param.Constant;
@@ -147,7 +147,7 @@ public class QueryResultsWrapper extends RowRecordWrapper {
                 // find the value from dynamic field
                 Object meta = fieldValues.get(Constant.DYNAMIC_FIELD_NAME);
                 if (meta != null) {
-                    JSONObject jsonMata = (JSONObject)meta;
+                    JsonObject jsonMata = (JsonObject)meta;
                     Object innerObj = jsonMata.get(keyName);
                     if (innerObj != null) {
                         return innerObj;

+ 2 - 2
src/main/java/io/milvus/response/SearchResultsWrapper.java

@@ -19,7 +19,7 @@
 
 package io.milvus.response;
 
-import com.alibaba.fastjson.JSONObject;
+import com.google.gson.*;
 import io.milvus.exception.IllegalResponseException;
 import io.milvus.exception.ParamException;
 import io.milvus.grpc.*;
@@ -306,7 +306,7 @@ public class SearchResultsWrapper extends RowRecordWrapper {
                 // find the value from dynamic field
                 Object meta = fieldValues.get(Constant.DYNAMIC_FIELD_NAME);
                 if (meta != null) {
-                    JSONObject jsonMata = (JSONObject)meta;
+                    JsonObject jsonMata = (JsonObject)meta;
                     Object innerObj = jsonMata.get(keyName);
                     if (innerObj != null) {
                         return innerObj;

+ 6 - 5
src/main/java/io/milvus/response/basic/RowRecordWrapper.java

@@ -19,7 +19,7 @@
 
 package io.milvus.response.basic;
 
-import com.alibaba.fastjson.JSONObject;
+import com.google.gson.*;
 import io.milvus.exception.ParamException;
 import io.milvus.grpc.FieldData;
 import io.milvus.response.FieldDataWrapper;
@@ -66,10 +66,11 @@ public abstract class RowRecordWrapper {
                     }
                     Object value = wrapper.valueByIdx((int)index);
                     if (wrapper.isJsonField()) {
-                        JSONObject jsonField = FieldDataWrapper.ParseJSONObject(value);
-                        if (wrapper.isDynamicField()) {
-                            for (String key: jsonField.keySet()) {
-                                record.put(key, jsonField.get(key));
+                        JsonElement jsonField = FieldDataWrapper.ParseJSONObject(value);
+                        if (wrapper.isDynamicField() && jsonField instanceof JsonObject) {
+                            JsonObject jsonObj = (JsonObject) jsonField;
+                            for (String key: jsonObj.keySet()) {
+                                record.put(key, FieldDataWrapper.ValueOfJSONElement(jsonObj.get(key)));
                             }
                         } else {
                             record.put(field.getFieldName(), jsonField);

+ 6 - 5
src/main/java/io/milvus/v2/examples/Simple.java

@@ -1,6 +1,6 @@
 package io.milvus.v2.examples;
 
-import com.alibaba.fastjson.JSONObject;
+import com.google.gson.*;
 import io.milvus.v2.client.ConnectConfig;
 import io.milvus.v2.client.MilvusClientV2;
 import io.milvus.v2.exception.MilvusClientException;
@@ -56,16 +56,17 @@ public class Simple {
         logger.info(String.valueOf(client.listCollections()));
         logger.info(String.valueOf(client.describeCollection(DescribeCollectionReq.builder().collectionName(collectionName).build())));
         //insert data
-        List<JSONObject> insertData = new ArrayList<>();
+        List<JsonObject> insertData = new ArrayList<>();
+        Gson gson = new Gson();
         for(int i = 0; i < 6; i++){
-            JSONObject jsonObject = new JSONObject();
+            JsonObject jsonObject = new JsonObject();
             List<Float> vectorList = new ArrayList<>();
             for(int j = 0; j < dim; j++){
                 // generate random float vector
                 vectorList.add(new Random().nextFloat());
             }
-            jsonObject.put("id", (long) i);
-            jsonObject.put("vector", vectorList);
+            jsonObject.addProperty("id", (long) i);
+            jsonObject.add("vector", gson.toJsonTree(vectorList).getAsJsonArray());
             insertData.add(jsonObject);
         }
         InsertReq insertReq = InsertReq.builder()

+ 8 - 7
src/main/java/io/milvus/v2/examples/Simple_Schema.java

@@ -1,6 +1,6 @@
 package io.milvus.v2.examples;
 
-import com.alibaba.fastjson.JSONObject;
+import com.google.gson.*;
 import io.milvus.v2.client.ConnectConfig;
 import io.milvus.v2.client.MilvusClientV2;
 import io.milvus.v2.common.DataType;
@@ -63,9 +63,10 @@ public class Simple_Schema {
         TimeUnit.SECONDS.sleep(1);
         client.loadCollection(LoadCollectionReq.builder().collectionName(collectionName).build());
         //insert data
-        List<JSONObject> insertData = new ArrayList<>();
+        List<JsonObject> insertData = new ArrayList<>();
+        Gson gson = new Gson();
         for(int i = 0; i < 6; i++){
-            JSONObject jsonObject = new JSONObject();
+            JsonObject jsonObject = new JsonObject();
             List<Float> vectorList = new ArrayList<>();
             for(int j = 0; j < dim; j++){
                 // generate random float vector
@@ -73,10 +74,10 @@ public class Simple_Schema {
             }
             List<Integer> array = new ArrayList<>();
             array.add(i);
-            jsonObject.put("id", (long) i);
-            jsonObject.put("vector", vectorList);
-            jsonObject.put("num", (long) i);
-            jsonObject.put("array", array);
+            jsonObject.addProperty("id", (long) i);
+            jsonObject.add("vector", gson.toJsonTree(vectorList).getAsJsonArray());
+            jsonObject.addProperty("num", (long) i);
+            jsonObject.add("array", gson.toJsonTree(array).getAsJsonArray());
             insertData.add(jsonObject);
         }
 

+ 2 - 2
src/main/java/io/milvus/v2/service/vector/request/InsertReq.java

@@ -1,6 +1,6 @@
 package io.milvus.v2.service.vector.request;
 
-import com.alibaba.fastjson.JSONObject;
+import com.google.gson.JsonObject;
 import lombok.Builder;
 import lombok.Data;
 import lombok.experimental.SuperBuilder;
@@ -11,7 +11,7 @@ import java.util.List;
 @SuperBuilder
 public class InsertReq {
     //private List<> fields;
-    private List<JSONObject> data;
+    private List<JsonObject> data;
     private String collectionName;
     @Builder.Default
     private String partitionName = "";

+ 2 - 2
src/main/java/io/milvus/v2/service/vector/request/UpsertReq.java

@@ -1,6 +1,6 @@
 package io.milvus.v2.service.vector.request;
 
-import com.alibaba.fastjson.JSONObject;
+import com.google.gson.JsonObject;
 import lombok.Builder;
 import lombok.Data;
 import lombok.experimental.SuperBuilder;
@@ -10,7 +10,7 @@ import java.util.List;
 @Data
 @SuperBuilder
 public class UpsertReq {
-    private List<JSONObject> data;
+    private List<JsonObject> data;
     private String collectionName;
     @Builder.Default
     private String partitionName = "";

+ 15 - 299
src/main/java/io/milvus/v2/utils/DataUtils.java

@@ -1,6 +1,7 @@
 package io.milvus.v2.utils;
 
-import com.alibaba.fastjson.JSONObject;
+import com.google.gson.JsonElement;
+import com.google.gson.JsonObject;
 import com.google.common.collect.Lists;
 import com.google.protobuf.ByteString;
 import io.milvus.exception.IllegalResponseException;
@@ -22,10 +23,6 @@ import java.util.stream.Collectors;
 public class DataUtils {
     private InsertRequest.Builder insertBuilder;
     private UpsertRequest.Builder upsertBuilder;
-    private static final Set<DataType> vectorDataType = new HashSet<DataType>() {{
-        add(DataType.FloatVector);
-        add(DataType.BinaryVector);
-    }};
 
     public InsertRequest convertGrpcInsertRequest(@NonNull InsertReq requestParam,
                                                   DescCollResponseWrapper wrapper) {
@@ -99,10 +96,8 @@ public class DataUtils {
         }
 
         // convert insert data
-        List<JSONObject> rowFields = requestParam.getData();
-
+        List<JsonObject> rowFields = requestParam.getData();
         checkAndSetRowData(wrapper, rowFields);
-
     }
 
     private void fillFieldsData(InsertReq requestParam, DescCollResponseWrapper wrapper) {
@@ -125,13 +120,11 @@ public class DataUtils {
         }
 
         // convert insert data
-        List<JSONObject> rowFields = requestParam.getData();
-
+        List<JsonObject> rowFields = requestParam.getData();
         checkAndSetRowData(wrapper, rowFields);
-
     }
 
-    private void checkAndSetRowData(DescCollResponseWrapper wrapper, List<JSONObject> rows) {
+    private void checkAndSetRowData(DescCollResponseWrapper wrapper, List<JsonObject> rows) {
         List<FieldType> fieldTypes = wrapper.getFields();
 
         Map<String, ParamUtils.InsertDataInfo> nameInsertInfo = new HashMap<>();
@@ -142,27 +135,26 @@ public class DataUtils {
                                 .withIsDynamic(true)
                                 .build())
                 .data(new LinkedList<>()).build();
-        for (JSONObject row : rows) {
+        for (JsonObject row : rows) {
             for (FieldType fieldType : fieldTypes) {
                 String fieldName = fieldType.getName();
                 ParamUtils.InsertDataInfo insertDataInfo = nameInsertInfo.getOrDefault(fieldName, ParamUtils.InsertDataInfo.builder()
                         .fieldType(fieldType).data(new LinkedList<>()).build());
 
                 // check normalField
-                Object rowFieldData = row.get(fieldName);
+                JsonElement rowFieldData = row.get(fieldName);
                 if (rowFieldData != null) {
                     if (fieldType.isAutoID()) {
-                        String msg = "The primary key: " + fieldName + " is auto generated, no need to input.";
+                        String msg = String.format("The primary key: %s is auto generated, no need to input.", fieldName);
                         throw new ParamException(msg);
                     }
-                    checkFieldData(fieldType, Lists.newArrayList(rowFieldData), false);
-
-                    insertDataInfo.getData().add(rowFieldData);
+                    Object fieldValue = ParamUtils.checkFieldValue(fieldType, rowFieldData);
+                    insertDataInfo.getData().add(fieldValue);
                     nameInsertInfo.put(fieldName, insertDataInfo);
                 } else {
                     // check if autoId
                     if (!fieldType.isAutoID()) {
-                        String msg = "The field: " + fieldType.getName() + " is not provided.";
+                        String msg = String.format("The field: %s is not provided.", fieldType.getName());
                         throw new ParamException(msg);
                     }
                 }
@@ -170,10 +162,10 @@ public class DataUtils {
 
             // deal with dynamicField
             if (wrapper.getEnableDynamicField()) {
-                JSONObject dynamicField = new JSONObject();
+                JsonObject dynamicField = new JsonObject();
                 for (String rowFieldName : row.keySet()) {
                     if (!nameInsertInfo.containsKey(rowFieldName)) {
-                        dynamicField.put(rowFieldName, row.get(rowFieldName));
+                        dynamicField.add(rowFieldName, row.get(rowFieldName));
                     }
                 }
                 insertDynamicDataInfo.getData().add(dynamicField);
@@ -182,286 +174,10 @@ public class DataUtils {
 
         for (String fieldNameKey : nameInsertInfo.keySet()) {
             ParamUtils.InsertDataInfo insertDataInfo = nameInsertInfo.get(fieldNameKey);
-            this.addFieldsData(genFieldData(insertDataInfo.getFieldType(), insertDataInfo.getData()));
+            this.addFieldsData(ParamUtils.genFieldData(insertDataInfo.getFieldType(), insertDataInfo.getData()));
         }
         if (wrapper.getEnableDynamicField()) {
-            this.addFieldsData(genFieldData(insertDynamicDataInfo.getFieldType(), insertDynamicDataInfo.getData(), Boolean.TRUE));
-        }
-    }
-
-    public InsertRequest buildInsertRequest() {
-        if (insertBuilder != null) {
-            return insertBuilder.build();
-        }
-        throw new ParamException("Unable to build insert request since no input");
-    }
-    private static FieldData genFieldData(FieldType fieldType, List<?> objects) {
-        return genFieldData(fieldType, objects, Boolean.FALSE);
-    }
-
-    @SuppressWarnings("unchecked")
-    private static FieldData genFieldData(FieldType fieldType, List<?> objects, boolean isDynamic) {
-        if (objects == null) {
-            throw new ParamException("Cannot generate FieldData from null object");
-        }
-        DataType dataType = fieldType.getDataType();
-        String fieldName = fieldType.getName();
-        FieldData.Builder builder = FieldData.newBuilder();
-        if (vectorDataType.contains(dataType)) {
-            VectorField vectorField = genVectorField(dataType, objects);
-            return builder.setFieldName(fieldName).setType(dataType).setVectors(vectorField).build();
-        } else {
-            ScalarField scalarField = genScalarField(fieldType, objects);
-            if (isDynamic) {
-                return builder.setType(dataType).setScalars(scalarField).setIsDynamic(true).build();
-            }
-            return builder.setFieldName(fieldName).setType(dataType).setScalars(scalarField).build();
-        }
-    }
-
-    @SuppressWarnings("unchecked")
-    private static VectorField genVectorField(DataType dataType, List<?> objects) {
-        if (dataType == DataType.FloatVector) {
-            List<Float> floats = new ArrayList<>();
-            // each object is List<Float>
-            for (Object object : objects) {
-                if (object instanceof List) {
-                    List<Float> list = (List<Float>) object;
-                    floats.addAll(list);
-                } else {
-                    throw new ParamException("The type of FloatVector must be List<Float>");
-                }
-            }
-
-            int dim = floats.size() / objects.size();
-            FloatArray floatArray = FloatArray.newBuilder().addAllData(floats).build();
-            return VectorField.newBuilder().setDim(dim).setFloatVector(floatArray).build();
-        } else if (dataType == DataType.BinaryVector) {
-            ByteBuffer totalBuf = null;
-            int dim = 0;
-            // each object is ByteBuffer
-            for (Object object : objects) {
-                ByteBuffer buf = (ByteBuffer) object;
-                if (totalBuf == null) {
-                    totalBuf = ByteBuffer.allocate(buf.position() * objects.size());
-                    totalBuf.put(buf.array());
-                    dim = buf.position() * 8;
-                } else {
-                    totalBuf.put(buf.array());
-                }
-            }
-
-            assert totalBuf != null;
-            ByteString byteString = ByteString.copyFrom(totalBuf.array());
-            return VectorField.newBuilder().setDim(dim).setBinaryVector(byteString).build();
-        }
-
-        throw new ParamException("Illegal vector dataType:" + dataType);
-    }
-
-    private static ScalarField genScalarField(FieldType fieldType, List<?> objects) {
-        if (fieldType.getDataType() == DataType.Array) {
-            ArrayArray.Builder builder = ArrayArray.newBuilder();
-            for (Object object : objects) {
-                List<?> temp = (List<?>)object;
-                ScalarField arrayField = genScalarField(fieldType.getElementType(), temp);
-                builder.addData(arrayField);
-            }
-
-            return ScalarField.newBuilder().setArrayData(builder.build()).build();
-        } else {
-            return genScalarField(fieldType.getDataType(), objects);
-        }
-    }
-
-    private static ScalarField genScalarField(DataType dataType, List<?> objects) {
-        switch (dataType) {
-            case None:
-            case UNRECOGNIZED:
-                throw new ParamException("Cannot support this dataType:" + dataType);
-            case Int64: {
-                List<Long> longs = objects.stream().map(p -> (Long) p).collect(Collectors.toList());
-                LongArray longArray = LongArray.newBuilder().addAllData(longs).build();
-                return ScalarField.newBuilder().setLongData(longArray).build();
-            }
-            case Int32:
-            case Int16:
-            case Int8: {
-                List<Integer> integers = objects.stream().map(p -> p instanceof Short ? ((Short) p).intValue() : (Integer) p).collect(Collectors.toList());
-                IntArray intArray = IntArray.newBuilder().addAllData(integers).build();
-                return ScalarField.newBuilder().setIntData(intArray).build();
-            }
-            case Bool: {
-                List<Boolean> booleans = objects.stream().map(p -> (Boolean) p).collect(Collectors.toList());
-                BoolArray boolArray = BoolArray.newBuilder().addAllData(booleans).build();
-                return ScalarField.newBuilder().setBoolData(boolArray).build();
-            }
-            case Float: {
-                List<Float> floats = objects.stream().map(p -> (Float) p).collect(Collectors.toList());
-                FloatArray floatArray = FloatArray.newBuilder().addAllData(floats).build();
-                return ScalarField.newBuilder().setFloatData(floatArray).build();
-            }
-            case Double: {
-                List<Double> doubles = objects.stream().map(p -> (Double) p).collect(Collectors.toList());
-                DoubleArray doubleArray = DoubleArray.newBuilder().addAllData(doubles).build();
-                return ScalarField.newBuilder().setDoubleData(doubleArray).build();
-            }
-            case String:
-            case VarChar: {
-                List<String> strings = objects.stream().map(p -> (String) p).collect(Collectors.toList());
-                StringArray stringArray = StringArray.newBuilder().addAllData(strings).build();
-                return ScalarField.newBuilder().setStringData(stringArray).build();
-            }
-            case JSON: {
-                List<ByteString> byteStrings = objects.stream().map(p -> ByteString.copyFromUtf8(((JSONObject) p).toJSONString()))
-                        .collect(Collectors.toList());
-                JSONArray jsonArray = JSONArray.newBuilder().addAllData(byteStrings).build();
-                return ScalarField.newBuilder().setJsonData(jsonArray).build();
-            }
-            default:
-                throw new ParamException("Illegal scalar dataType:" + dataType);
-        }
-    }
-    private static void checkFieldData(FieldType fieldSchema, InsertParam.Field fieldData) {
-        List<?> values = fieldData.getValues();
-        checkFieldData(fieldSchema, values, false);
-    }
-
-    private static void checkFieldData(FieldType fieldSchema, List<?> values, boolean verifyElementType) {
-        HashMap<DataType, String> errMsgs = getTypeErrorMsg();
-        DataType dataType = verifyElementType ? fieldSchema.getElementType() : fieldSchema.getDataType();
-
-        if (verifyElementType && values.size() > fieldSchema.getMaxCapacity()) {
-            throw new ParamException(String.format("Array field '%s' length: %d exceeds max capacity: %d",
-                    fieldSchema.getName(), values.size(), fieldSchema.getMaxCapacity()));
+            this.addFieldsData(ParamUtils.genFieldData(insertDynamicDataInfo.getFieldType(), insertDynamicDataInfo.getData(), Boolean.TRUE));
         }
-
-        switch (dataType) {
-            case FloatVector: {
-                int dim = fieldSchema.getDimension();
-                for (int i = 0; i < values.size(); ++i) {
-                    // is List<> ?
-                    Object value  = values.get(i);
-                    if (!(value instanceof List)) {
-                        throw new ParamException(String.format(errMsgs.get(dataType), fieldSchema.getName()));
-                    }
-                    // is List<Float> ?
-                    List<?> temp = (List<?>)value;
-                    for (Object v : temp) {
-                        if (!(v instanceof Float)) {
-                            throw new ParamException(String.format(errMsgs.get(dataType), fieldSchema.getName()));
-                        }
-                    }
-
-                    // check dimension
-                    if (temp.size() != dim) {
-                        String msg = "Incorrect dimension for field '%s': the no.%d vector's dimension: %d is not equal to field's dimension: %d";
-                        throw new ParamException(String.format(msg, fieldSchema.getName(), i, temp.size(), dim));
-                    }
-                }
-            }
-            break;
-            case BinaryVector: {
-                int dim = fieldSchema.getDimension();
-                for (int i = 0; i < values.size(); ++i) {
-                    Object value  = values.get(i);
-                    // is ByteBuffer?
-                    if (!(value instanceof ByteBuffer)) {
-                        throw new ParamException(String.format(errMsgs.get(dataType), fieldSchema.getName()));
-                    }
-
-                    // check dimension
-                    ByteBuffer v = (ByteBuffer)value;
-                    if (v.position()*8 != dim) {
-                        String msg = "Incorrect dimension for field '%s': the no.%d vector's dimension: %d is not equal to field's dimension: %d";
-                        throw new ParamException(String.format(msg, fieldSchema.getName(), i, v.position()*8, dim));
-                    }
-                }
-            }
-            break;
-            case Int64:
-                for (Object value : values) {
-                    if (!(value instanceof Long)) {
-                        throw new ParamException(String.format(errMsgs.get(dataType), fieldSchema.getName()));
-                    }
-                }
-                break;
-            case Int32:
-            case Int16:
-            case Int8:
-                for (Object value : values) {
-                    if (!(value instanceof Short) && !(value instanceof Integer)) {
-                        throw new ParamException(String.format(errMsgs.get(dataType), fieldSchema.getName()));
-                    }
-                }
-                break;
-            case Bool:
-                for (Object value : values) {
-                    if (!(value instanceof Boolean)) {
-                        throw new ParamException(String.format(errMsgs.get(dataType), fieldSchema.getName()));
-                    }
-                }
-                break;
-            case Float:
-                for (Object value : values) {
-                    if (!(value instanceof Float)) {
-                        throw new ParamException(String.format(errMsgs.get(dataType), fieldSchema.getName()));
-                    }
-                }
-                break;
-            case Double:
-                for (Object value : values) {
-                    if (!(value instanceof Double)) {
-                        throw new ParamException(String.format(errMsgs.get(dataType), fieldSchema.getName()));
-                    }
-                }
-                break;
-            case VarChar:
-            case String:
-                for (Object value : values) {
-                    if (!(value instanceof String)) {
-                        throw new ParamException(String.format(errMsgs.get(dataType), fieldSchema.getName()));
-                    }
-                }
-                break;
-            case JSON:
-                for (Object value : values) {
-                    if (!(value instanceof JSONObject)) {
-                        throw new ParamException(String.format(errMsgs.get(dataType), fieldSchema.getName()));
-                    }
-                }
-                break;
-            case Array:
-                for (Object value : values) {
-                    if (!(value instanceof List)) {
-                        throw new ParamException(String.format(errMsgs.get(dataType), fieldSchema.getName()));
-                    }
-
-                    List<?> temp = (List<?>)value;
-                    checkFieldData(fieldSchema, temp, true);
-                }
-                break;
-            default:
-                throw new IllegalResponseException("Unsupported data type returned by FieldData");
-        }
-    }
-    public static HashMap<DataType, String> getTypeErrorMsg() {
-        final HashMap<DataType, String> typeErrMsg = new HashMap<>();
-        typeErrMsg.put(DataType.None, "Type mismatch for field '%s': the field type is illegal");
-        typeErrMsg.put(DataType.Bool, "Type mismatch for field '%s': Bool field value type must be Boolean");
-        typeErrMsg.put(DataType.Int8, "Type mismatch for field '%s': Int32/Int16/Int8 field value type must be Short or Integer");
-        typeErrMsg.put(DataType.Int16, "Type mismatch for field '%s': Int32/Int16/Int8 field value type must be Short or Integer");
-        typeErrMsg.put(DataType.Int32, "Type mismatch for field '%s': Int32/Int16/Int8 field value type must be Short or Integer");
-        typeErrMsg.put(DataType.Int64, "Type mismatch for field '%s': Int64 field value type must be Long");
-        typeErrMsg.put(DataType.Float, "Type mismatch for field '%s': Float field value type must be Float");
-        typeErrMsg.put(DataType.Double, "Type mismatch for field '%s': Double field value type must be Double");
-        typeErrMsg.put(DataType.String, "Type mismatch for field '%s': String field value type must be String");
-        typeErrMsg.put(DataType.VarChar, "Type mismatch for field '%s': VarChar field value type must be String");
-        typeErrMsg.put(DataType.FloatVector, "Type mismatch for field '%s': Float vector field's value type must be List<Float>");
-        typeErrMsg.put(DataType.BinaryVector, "Type mismatch for field '%s': Binary vector field's value type must be ByteBuffer");
-        typeErrMsg.put(DataType.Float16Vector, "Type mismatch for field '%s': Float16 vector field's value type must be ByteBuffer");
-        typeErrMsg.put(DataType.BFloat16Vector, "Type mismatch for field '%s': BFloat16 vector field's value type must be ByteBuffer");
-        typeErrMsg.put(DataType.SparseFloatVector, "Type mismatch for field '%s': SparseFloatVector vector field's value type must be SortedMap");
-        return typeErrMsg;
     }
 }

+ 2 - 2
src/main/java/io/milvus/v2/utils/VectorUtils.java

@@ -16,6 +16,7 @@ import java.util.Date;
 import java.util.List;
 
 public class VectorUtils {
+    private static final Gson GSON_INSTANCE = new Gson();
 
     public QueryRequest ConvertToGrpcQueryRequest(QueryReq request){
 //        long guaranteeTimestamp = getGuaranteeTimestamp(ConsistencyLevelEnum.valueOf(request.getConsistencyLevel().name()),
@@ -159,8 +160,7 @@ public class VectorUtils {
 
         if (null != request.getSearchParams()) {
             try {
-                Gson gson = new Gson();
-                String searchParams = gson.toJson(request.getSearchParams());
+                String searchParams = GSON_INSTANCE.toJson(request.getSearchParams());
                 builder.addSearchParams(
                         KeyValuePair.newBuilder()
                                 .setKey(Constant.PARAMS)

+ 422 - 71
src/test/java/io/milvus/client/MilvusClientDockerTest.java

@@ -19,11 +19,19 @@
 
 package io.milvus.client;
 
-import com.alibaba.fastjson.JSONObject;
+import com.google.gson.*;
 import com.google.common.collect.Lists;
 import com.google.common.util.concurrent.ListenableFuture;
+import io.milvus.bulkwriter.LocalBulkWriter;
+import io.milvus.bulkwriter.LocalBulkWriterParam;
+import io.milvus.bulkwriter.common.clientenum.BulkFileType;
+import io.milvus.bulkwriter.common.utils.GeneratorUtils;
+import io.milvus.bulkwriter.common.utils.ParquetReaderUtils;
 import io.milvus.common.clientenum.ConsistencyLevelEnum;
+import io.milvus.exception.ParamException;
 import io.milvus.grpc.*;
+import io.milvus.orm.iterator.QueryIterator;
+import io.milvus.orm.iterator.SearchIterator;
 import io.milvus.param.*;
 import io.milvus.param.alias.AlterAliasParam;
 import io.milvus.param.alias.CreateAliasParam;
@@ -31,7 +39,6 @@ import io.milvus.param.alias.DropAliasParam;
 import io.milvus.param.alias.ListAliasesParam;
 import io.milvus.param.collection.*;
 import io.milvus.param.dml.*;
-import io.milvus.param.dml.ranker.RRFRanker;
 import io.milvus.param.dml.ranker.WeightedRanker;
 import io.milvus.param.highlevel.dml.DeleteIdsParam;
 import io.milvus.param.highlevel.dml.GetIdsParam;
@@ -44,6 +51,7 @@ import io.milvus.param.index.GetIndexStateParam;
 import io.milvus.param.partition.GetPartitionStatisticsParam;
 import io.milvus.param.partition.ShowPartitionsParam;
 import io.milvus.response.*;
+import org.apache.avro.generic.GenericData;
 import org.apache.commons.text.RandomStringGenerator;
 import org.apache.logging.log4j.LogManager;
 import org.apache.logging.log4j.Logger;
@@ -64,9 +72,11 @@ import java.util.concurrent.TimeUnit;
 @Testcontainers(disabledWithoutDocker = true)
 class MilvusClientDockerTest {
     private static final Logger logger = LogManager.getLogger("MilvusClientTest");
-    private static MilvusClient client;
-    private static RandomStringGenerator generator;
-    private static final int dimension = 128;
+    protected static MilvusClient client;
+    protected static RandomStringGenerator generator;
+    protected static final int dimension = 128;
+
+    protected static final Gson GSON_INSTANCE = new Gson();
 
     @Container
     private static final MilvusContainer milvus = new MilvusContainer("milvusdb/milvus:v2.4.0-20240416-ffb6edd4-amd64");
@@ -98,7 +108,7 @@ class MilvusClientDockerTest {
         return ConnectParam.newBuilder().withUri(milvusUri);
     }
 
-    private List<List<Float>> generateFloatVectors(int count) {
+    protected List<List<Float>> generateFloatVectors(int count) {
         Random ran = new Random();
         List<List<Float>> vectors = new ArrayList<>();
         for (int n = 0; n < count; ++n) {
@@ -112,7 +122,7 @@ class MilvusClientDockerTest {
         return vectors;
     }
 
-    private List<List<Float>> normalizeFloatVectors(List<List<Float>> src) {
+    protected List<List<Float>> normalizeFloatVectors(List<List<Float>> src) {
         for (List<Float> vector : src) {
             double total = 0.0;
             for (Float val : vector) {
@@ -127,7 +137,7 @@ class MilvusClientDockerTest {
         return src;
     }
 
-    private List<ByteBuffer> generateBinaryVectors(int count) {
+    protected List<ByteBuffer> generateBinaryVectors(int count) {
         Random ran = new Random();
         List<ByteBuffer> vectors = new ArrayList<>();
         int byteCount = dimension / 8;
@@ -142,7 +152,7 @@ class MilvusClientDockerTest {
 
     }
 
-    private List<SortedMap<Long, Float>> generateSparseVectors(int count) {
+    protected List<SortedMap<Long, Float>> generateSparseVectors(int count) {
         Random ran = new Random();
         List<SortedMap<Long, Float>> vectors = new ArrayList<>();
         for (int n = 0; n < count; ++n) {
@@ -516,26 +526,43 @@ class MilvusClientDockerTest {
         R<RpcStatus> createR = client.createCollection(createParam);
         Assertions.assertEquals(R.Status.Success.getCode(), createR.getStatus().intValue());
 
-        // insert data
         int rowCount = 10000;
         List<ByteBuffer> vectors = generateBinaryVectors(rowCount);
-
+        // insert data by columns
         List<InsertParam.Field> fields = new ArrayList<>();
-        // no need to provide id here since this field is auto_id
-        fields.add(new InsertParam.Field(field2Name, vectors));
+        fields.add(new InsertParam.Field(field2Name, vectors.subList(0, 5000))); // no need to provide id here since this field is auto_id
 
-        InsertParam insertParam = InsertParam.newBuilder()
+        R<MutationResult> insertR1 = client.insert(InsertParam.newBuilder()
                 .withCollectionName(randomCollectionName)
                 .withFields(fields)
-                .build();
+                .build());
+        Assertions.assertEquals(R.Status.Success.getCode(), insertR1.getStatus().intValue());
 
-        R<MutationResult> insertR = client.insert(insertParam);
-        Assertions.assertEquals(R.Status.Success.getCode(), insertR.getStatus().intValue());
-//        System.out.println(insertR.getData());
-        MutationResultWrapper insertResultWrapper = new MutationResultWrapper(insertR.getData());
+        MutationResultWrapper insertResultWrapper = new MutationResultWrapper(insertR1.getData());
         System.out.println(insertResultWrapper.getInsertCount() + " rows inserted");
-        List<Long> ids = insertResultWrapper.getLongIDs();
-//        System.out.println("Auto-generated ids: " + ids);
+        List<Long> ids1 = insertResultWrapper.getLongIDs(); // get returned IDs(generated by server-side)
+
+        // Insert entities by rows
+        List<JsonObject> rows = new ArrayList<>();
+        for (int i = 5000; i < rowCount; ++i) {
+            JsonObject row = new JsonObject();
+            row.add(field2Name, GSON_INSTANCE.toJsonTree(vectors.get(i).array()));
+            rows.add(row);
+        }
+
+        R<MutationResult> insertR2 = client.insert(InsertParam.newBuilder()
+                .withCollectionName(randomCollectionName)
+                .withRows(rows)
+                .build());
+        Assertions.assertEquals(R.Status.Success.getCode(), insertR2.getStatus().intValue());
+
+        insertResultWrapper = new MutationResultWrapper(insertR2.getData());
+        System.out.println(insertResultWrapper.getInsertCount() + " rows inserted");
+        List<Long> ids2 = insertResultWrapper.getLongIDs(); // get returned IDs(generated by server-side)
+        List<Long> ids = new ArrayList<>();
+        ids1.forEach((id) -> { ids.add(id);});
+        ids2.forEach((id) -> { ids.add(id);});
+        Assertions.assertEquals(rowCount, ids.size());
 
         // get collection statistics
         R<GetCollectionStatisticsResponse> statR = client.getCollectionStatistics(GetCollectionStatisticsParam
@@ -547,6 +574,7 @@ class MilvusClientDockerTest {
 
         GetCollStatResponseWrapper stat = new GetCollStatResponseWrapper(statR.getData());
         System.out.println("Collection row count: " + stat.getRowCount());
+        Assertions.assertEquals(rowCount, stat.getRowCount());
 
         // create index
         CreateIndexParam indexParam2 = CreateIndexParam.newBuilder()
@@ -933,6 +961,7 @@ class MilvusClientDockerTest {
                 .withRanker(WeightedRanker.newBuilder()
                         .withWeights(Lists.newArrayList(0.5f, 0.5f, 1.0f))
                         .build())
+                .withOutFields(Collections.singletonList("*"))
                 .build();
 
         R<SearchResults> searchR = client.hybridSearch(searchParam);
@@ -941,8 +970,20 @@ class MilvusClientDockerTest {
         // print search result
         SearchResultsWrapper results = new SearchResultsWrapper(searchR.getData().getResults());
         List<SearchResultsWrapper.IDScore> scores = results.getIDScore(0);
-        for (int i = 0; i < scores.size(); ++i) {
-            System.out.println(scores.get(i));
+        for (SearchResultsWrapper.IDScore score : scores) {
+            System.out.println(score);
+            Object id = score.get(idField);
+            Assertions.assertInstanceOf(Long.class, id);
+            Object fv = score.get(floatVectorField);
+            Assertions.assertInstanceOf(List.class, fv);
+            List<Float> fvec = (List<Float>)fv;
+            Assertions.assertEquals(dimension, fvec.size());
+            Object bv = score.get(binaryVectorField);
+            Assertions.assertInstanceOf(ByteBuffer.class, bv);
+            ByteBuffer bvec = (ByteBuffer)bv;
+            Assertions.assertEquals(dimension, bvec.limit()*8);
+            Object sv = score.get(sparseVectorField);
+            Assertions.assertInstanceOf(SortedMap.class, sv);
         }
 
         // drop collection
@@ -1583,20 +1624,21 @@ class MilvusClientDockerTest {
 
         int rowCount = 10;
         // insert data by row-based
-        List<JSONObject> rows = new ArrayList<>();
+        List<JsonObject> rows = new ArrayList<>();
         for (long i = 0L; i < rowCount; ++i) {
-            JSONObject row = new JSONObject();
-            row.put(field1Name, i);
-            row.put(field2Name, generateFloatVectors(1).get(0));
+            JsonObject row = new JsonObject();
+            row.addProperty(field1Name, i);
+            List<Float> vector = generateFloatVectors(1).get(0);
+            row.add(field2Name, GSON_INSTANCE.toJsonTree(vector));
 
             // JSON field
-            JSONObject info = new JSONObject();
-            info.put("row_based_info", i);
-            row.put(field3Name, info);
+            JsonObject info = new JsonObject();
+            info.addProperty("row_based_info", i);
+            row.add(field3Name, info);
 
             // extra meta is automatically stored in dynamic field
-            row.put("row_based_extra", i % 3 == 0);
-            row.put(generator.generate(5), 100);
+            row.addProperty("row_based_extra", i % 3 == 0);
+            row.addProperty(generator.generate(5), 100);
 
             rows.add(row);
         }
@@ -1612,17 +1654,17 @@ class MilvusClientDockerTest {
 
         // insert data by column-based
         List<Long> ids = new ArrayList<>();
-        List<JSONObject> infos = new ArrayList<>();
-        List<JSONObject> dynamics = new ArrayList<>();
+        List<JsonObject> infos = new ArrayList<>();
+        List<JsonObject> dynamics = new ArrayList<>();
         for (long i = 0L; i < rowCount; ++i) {
             ids.add(rowCount + i);
-            JSONObject obj = new JSONObject();
-            obj.put("column_based_info", i);
-            obj.put(generator.generate(5), i);
+            JsonObject obj = new JsonObject();
+            obj.addProperty("column_based_info", i);
+            obj.addProperty(generator.generate(5), i);
             infos.add(obj);
 
-            JSONObject dynamic = new JSONObject();
-            dynamic.put(String.format("column_based_extra_%d", i), i);
+            JsonObject dynamic = new JsonObject();
+            dynamic.addProperty(String.format("column_based_extra_%d", i), i);
             dynamics.add(dynamic);
         }
         List<List<Float>> vectors = generateFloatVectors(rowCount);
@@ -1671,6 +1713,7 @@ class MilvusClientDockerTest {
         for (QueryResultsWrapper.RowRecord record:records) {
             System.out.println(record);
             Object extraMeta = record.get("row_based_extra");
+            Assertions.assertInstanceOf(Boolean.class, extraMeta);
             System.out.println("'row_based_extra' is from dynamic field, value: " + extraMeta);
         }
 
@@ -1726,6 +1769,14 @@ class MilvusClientDockerTest {
             System.out.println(record);
             long id = (long)record.get(field1Name);
             Assertions.assertEquals((long)rowCount+1L, id);
+            Object vec = record.get(field2Name);
+            Assertions.assertInstanceOf(List.class, vec);
+            List<Float> vector = (List<Float>)vec;
+            Assertions.assertEquals(dimension, vector.size());
+            Object j = record.get(field3Name);
+            Assertions.assertInstanceOf(JsonObject.class, j);
+            JsonObject jon = (JsonObject)j;
+            Assertions.assertTrue(jon.has("column_based_info"));
         }
 
         // drop collection
@@ -1847,11 +1898,12 @@ class MilvusClientDockerTest {
         System.out.println(rowCount + " rows inserted");
 
         // insert data by row-based
-        List<JSONObject> rows = new ArrayList<>();
+        List<JsonObject> rows = new ArrayList<>();
         for (int i = 0; i < rowCount; ++i) {
-            JSONObject row = new JSONObject();
-            row.put(field1Name, 10000L + (long)i);
-            row.put(field2Name, generateFloatVectors(1).get(0));
+            JsonObject row = new JsonObject();
+            row.addProperty(field1Name, 10000L + (long)i);
+            List<Float> vector = generateFloatVectors(1).get(0);
+            row.add(field2Name, GSON_INSTANCE.toJsonTree(vector));
 
             List<String> strArray = new ArrayList<>();
             List<Integer> intArray = new ArrayList<>();
@@ -1861,9 +1913,9 @@ class MilvusClientDockerTest {
                 intArray.add(i*10000 + k);
                 floatArray.add((float)k/1000 + i);
             }
-            row.put(field3Name, strArray);
-            row.put(field4Name, intArray);
-            row.put(field5Name, floatArray);
+            row.add(field3Name, GSON_INSTANCE.toJsonTree(strArray));
+            row.add(field4Name, GSON_INSTANCE.toJsonTree(intArray));
+            row.add(field5Name, GSON_INSTANCE.toJsonTree(floatArray));
 
             rows.add(row);
         }
@@ -1976,6 +2028,7 @@ class MilvusClientDockerTest {
         CreateCollectionParam createParam = CreateCollectionParam.newBuilder()
                 .withCollectionName(randomCollectionName)
                 .withFieldTypes(fieldsSchema)
+                .withEnableDynamicField(true)
                 .build();
 
         R<RpcStatus> createR = client.createCollection(createParam);
@@ -1983,12 +2036,14 @@ class MilvusClientDockerTest {
 
         // insert data by row-based with id from 0 ~ 9
         int rowCount = 10;
-        List<JSONObject> rows = new ArrayList<>();
+        List<JsonObject> rows = new ArrayList<>();
         for (long i = 0L; i < rowCount; ++i) {
-            JSONObject row = new JSONObject();
-            row.put(field1Name, i);
-            row.put(field2Name, generateFloatVectors(1).get(0));
-            row.put(field3Name, String.format("name_%d", i));
+            JsonObject row = new JsonObject();
+            row.addProperty(field1Name, i);
+            List<Float> vector = generateFloatVectors(1).get(0);
+            row.add(field2Name, GSON_INSTANCE.toJsonTree(vector));
+            row.addProperty(field3Name, String.format("name_%d", i));
+            row.addProperty("dynamic_value", String.format("dynamic_%d", i));
             rows.add(row);
         }
 
@@ -2057,10 +2112,11 @@ class MilvusClientDockerTest {
         // since the ids are not exist, the upsert call is equal to an insert call
         rows.clear();
         for (long i = 0L; i < rowCount; ++i) {
-            JSONObject row = new JSONObject();
-            row.put(field1Name, rowCount + i);
-            row.put(field2Name, generateFloatVectors(1).get(0));
-            row.put(field3Name, String.format("name_%d", rowCount + i));
+            JsonObject row = new JsonObject();
+            row.addProperty(field1Name, rowCount + i);
+            List<Float> vector = generateFloatVectors(1).get(0);
+            row.add(field2Name, GSON_INSTANCE.toJsonTree(vector));
+            row.addProperty(field3Name, String.format("name_%d", rowCount + i));
             rows.add(row);
         }
 
@@ -2078,6 +2134,7 @@ class MilvusClientDockerTest {
                 .withCollectionName(randomCollectionName)
                 .withExpr(String.format("%s == 18", field1Name))
                 .addOutField(field3Name)
+                .addOutField("dynamic_value")
                 .withConsistencyLevel(ConsistencyLevelEnum.STRONG)
                 .build();
 
@@ -2092,19 +2149,24 @@ class MilvusClientDockerTest {
             Object name = record.get(field3Name);
             Assertions.assertNotNull(name);
             Assertions.assertEquals("name_18", name);
+            Assertions.assertThrows(ParamException.class, () -> record.get("dynamic_value")); // we didn't set dynamic_value for No.18 row
         }
 
         // upsert to change the no.5 and no.18 items
         rows.clear();
-        JSONObject row = new JSONObject();
-        row.put(field1Name, 5L);
-        row.put(field2Name, generateFloatVectors(1).get(0));
-        row.put(field3Name, "updated_5");
+        JsonObject row = new JsonObject();
+        row.addProperty(field1Name, 5L);
+        List<Float> vector = generateFloatVectors(1).get(0);
+        row.add(field2Name, GSON_INSTANCE.toJsonTree(vector));
+        row.addProperty(field3Name, "updated_5");
+        row.addProperty("dynamic_value", String.format("dynamic_%d", 5));
         rows.add(row);
-        row = new JSONObject();
-        row.put(field1Name, 18L);
-        row.put(field2Name, generateFloatVectors(1).get(0));
-        row.put(field3Name, "updated_18");
+        row = new JsonObject();
+        row.addProperty(field1Name, 18L);
+        vector = generateFloatVectors(1).get(0);
+        row.add(field2Name, GSON_INSTANCE.toJsonTree(vector));
+        row.addProperty(field3Name, "updated_18");
+        row.addProperty("dynamic_value", 18);
         rows.add(row);
 
         upsertParam = UpsertParam.newBuilder()
@@ -2120,6 +2182,7 @@ class MilvusClientDockerTest {
                 .withCollectionName(randomCollectionName)
                 .withExpr(String.format("%s == 5 || %s == 18", field1Name, field1Name))
                 .addOutField(field3Name)
+                .addOutField("dynamic_value")
                 .withConsistencyLevel(ConsistencyLevelEnum.STRONG)
                 .build();
 
@@ -2130,7 +2193,9 @@ class MilvusClientDockerTest {
         records = queryResultsWrapper.getRowRecords();
         Assertions.assertEquals(2, records.size());
         Assertions.assertEquals("updated_5", records.get(0).get(field3Name));
+        Assertions.assertEquals("dynamic_5", records.get(0).get("dynamic_value"));
         Assertions.assertEquals("updated_18", records.get(1).get(field3Name));
+        Assertions.assertEquals(18L, records.get(1).get("dynamic_value"));
 
         // drop collection
         R<RpcStatus> dropR = client.dropCollection(DropCollectionParam.newBuilder()
@@ -2288,11 +2353,16 @@ class MilvusClientDockerTest {
         // insert data
         List<String> primaryIds = new ArrayList<>();
         int rowCount = 10;
-        List<JSONObject> rows = new ArrayList<>();
+        List<JsonObject> rows = new ArrayList<>();
         for (long i = 0L; i < rowCount; ++i) {
-            JSONObject row = new JSONObject();
-            row.put(primaryField.getName(), primaryField.getDataType() == DataType.Int64 ? i : String.valueOf(i));
-            row.put(vectorField.getName(), generateFloatVectors(1).get(0));
+            JsonObject row = new JsonObject();
+            if (primaryField.getDataType() == DataType.Int64) {
+                row.addProperty(primaryField.getName(), i);
+            } else {
+                row.addProperty(primaryField.getName(), String.valueOf(i));
+            }
+            List<Float> vector = generateFloatVectors(1).get(0);
+            row.add(vectorField.getName(), GSON_INSTANCE.toJsonTree(vector));
             rows.add(row);
             primaryIds.add(String.valueOf(i));
         }
@@ -2348,11 +2418,16 @@ class MilvusClientDockerTest {
         // insert data
         List<String> primaryIds = new ArrayList<>();
         int rowCount = 10;
-        List<JSONObject> rows = new ArrayList<>();
+        List<JsonObject> rows = new ArrayList<>();
         for (long i = 0L; i < rowCount; ++i) {
-            JSONObject row = new JSONObject();
-            row.put(primaryField.getName(), primaryField.getDataType() == DataType.Int64 ? i : String.valueOf(i));
-            row.put(vectorField.getName(), generateFloatVectors(1).get(0));
+            JsonObject row = new JsonObject();
+            if (primaryField.getDataType() == DataType.Int64) {
+                row.addProperty(primaryField.getName(), i);
+            } else {
+                row.addProperty(primaryField.getName(), String.valueOf(i));
+            }
+            List<Float> vector = generateFloatVectors(1).get(0);
+            row.add(vectorField.getName(), GSON_INSTANCE.toJsonTree(vector));
             rows.add(row);
             primaryIds.add(String.valueOf(i));
         }
@@ -2393,4 +2468,280 @@ class MilvusClientDockerTest {
         System.out.println(outPutStr);
         Assertions.assertEquals(R.Status.Success.getCode(), deleteResponseR.getStatus().intValue());
     }
+
+    @Test
+    public void testBulkWriter() {
+        String randomCollectionName = generator.generate(10);
+
+        // collection schema
+        FieldType field1 = FieldType.newBuilder()
+                .withPrimaryKey(true)
+                .withAutoID(false)
+                .withDataType(DataType.Int64)
+                .withName("id")
+                .build();
+
+        FieldType field2 = FieldType.newBuilder()
+                .withDataType(DataType.FloatVector)
+                .withName("vector")
+                .withDimension(dimension)
+                .build();
+
+        FieldType field3 = FieldType.newBuilder()
+                .withDataType(DataType.Bool)
+                .withName("bool")
+                .build();
+
+        FieldType field4 = FieldType.newBuilder()
+                .withDataType(DataType.Int16)
+                .withName("int16")
+                .build();
+
+        FieldType field5 = FieldType.newBuilder()
+                .withDataType(DataType.Float)
+                .withName("float")
+                .build();
+
+        FieldType field6 = FieldType.newBuilder()
+                .withDataType(DataType.VarChar)
+                .withName("varchar")
+                .withMaxLength(100)
+                .build();
+
+        FieldType field7 = FieldType.newBuilder()
+                .withDataType(DataType.JSON)
+                .withName("json")
+                .build();
+
+        FieldType field8 = FieldType.newBuilder()
+                .withDataType(DataType.Array)
+                .withElementType(DataType.Int32)
+                .withName("array")
+                .withMaxCapacity(100)
+                .build();
+
+        CollectionSchemaParam schema = CollectionSchemaParam.newBuilder()
+                .withFieldTypes(Lists.newArrayList(field1, field2, field3, field4, field5, field6, field7, field8))
+                .withEnableDynamicField(false)
+                .build();
+
+        // create collection
+        CreateCollectionParam createParam = CreateCollectionParam.newBuilder()
+                .withCollectionName(randomCollectionName)
+                .withSchema(schema)
+                .build();
+
+        R<RpcStatus> createR = client.createCollection(createParam);
+        Assertions.assertEquals(R.Status.Success.getCode(), createR.getStatus().intValue());
+
+        // local bulkwriter
+        LocalBulkWriterParam localWriterParam = LocalBulkWriterParam.newBuilder()
+                .withCollectionSchema(schema)
+                .withLocalPath("/tmp/bulk_writer")
+                .withFileType(BulkFileType.PARQUET)
+                .withChunkSize(4 * 1024 * 1024)
+                .build();
+
+        int rowCount = 10000;
+        List<List<String>> batchFiles = new ArrayList<>();
+        try (LocalBulkWriter localBulkWriter = new LocalBulkWriter(localWriterParam)) {
+            for (int i = 0; i < rowCount; i++) {
+                JsonObject row = new JsonObject();
+                row.addProperty("id", i);
+                row.add("vector", GSON_INSTANCE.toJsonTree(GeneratorUtils.genFloatVector(dimension)));
+                row.addProperty("bool", i % 3 == 0);
+                row.addProperty("int16", i%65535);
+                row.addProperty("float", i/3);
+                row.addProperty("varchar", String.format("varchar_%d", i));
+                JsonObject obj = new JsonObject();
+                obj.addProperty("dummy", i);
+                row.add("json", obj);
+                row.addProperty("dynamic_1", i);
+                row.addProperty("dynamic_2", String.format("dynamic_%d", i));
+                row.add("array", GSON_INSTANCE.toJsonTree(Lists.newArrayList(5, 6, 3, 2, 1)));
+
+                localBulkWriter.appendRow(row);
+            }
+
+            localBulkWriter.commit(false);
+            List<List<String>> files = localBulkWriter.getBatchFiles();
+            System.out.printf("LocalBulkWriter done! output local files: %s%n", files);
+            Assertions.assertEquals(files.size(), 2);
+            Assertions.assertEquals(files.get(0).size(), 1);
+            batchFiles.addAll(files);
+        } catch (Exception e) {
+            System.out.println("LocalBulkWriter catch exception: " + e);
+            Assertions.fail();
+        }
+
+        try {
+            final int[] counter = {0};
+            for (List<String> files : batchFiles) {
+                new ParquetReaderUtils() {
+                    @Override
+                    public void readRecord(GenericData.Record record) {
+                        counter[0]++;
+                    }
+                }.readParquet(files.get(0));
+            }
+            Assertions.assertEquals(rowCount, counter[0]);
+        } catch (Exception e) {
+            System.out.println("Verify parquet file catch exception: " + e);
+            Assertions.fail();
+        }
+    }
+
+    @Test
+    public void testIterator() {
+        String randomCollectionName = generator.generate(10);
+
+        String field1Name = "str_id";
+        String field2Name = "vec_field";
+        String field3Name = "json_field";
+        List<FieldType> fieldsSchema = new ArrayList<>();
+        fieldsSchema.add(FieldType.newBuilder()
+                .withPrimaryKey(true)
+                .withAutoID(false)
+                .withDataType(DataType.VarChar)
+                .withName(field1Name)
+                .withMaxLength(32)
+                .build());
+
+        fieldsSchema.add(FieldType.newBuilder()
+                .withDataType(DataType.FloatVector)
+                .withName(field2Name)
+                .withDimension(dimension)
+                .build());
+
+        fieldsSchema.add(FieldType.newBuilder()
+                .withDataType(DataType.JSON)
+                .withName(field3Name)
+                .build());
+
+
+        // create collection
+        CreateCollectionParam createParam = CreateCollectionParam.newBuilder()
+                .withCollectionName(randomCollectionName)
+                .withFieldTypes(fieldsSchema)
+                .withEnableDynamicField(true)
+                .build();
+
+        R<RpcStatus> createR = client.createCollection(createParam);
+        Assertions.assertEquals(R.Status.Success.getCode(), createR.getStatus().intValue());
+
+        // insert data
+        int rowCount = 1000;
+        List<JsonObject> rows = new ArrayList<>();
+        Gson gson = new Gson();
+        for (long i = 0L; i < rowCount; ++i) {
+            JsonObject row = new JsonObject();
+            row.addProperty(field1Name, Long.toString(i));
+            row.add(field2Name, gson.toJsonTree(generateFloatVectors(1).get(0)));
+            JsonObject json = new JsonObject();
+            if (i%2 == 0) {
+                json.addProperty("even", true);
+            }
+            row.add(field3Name, json);
+            row.addProperty("dynamic", i);
+            rows.add(row);
+        }
+
+        InsertParam insertParam = InsertParam.newBuilder()
+                .withCollectionName(randomCollectionName)
+                .withRows(rows)
+                .build();
+
+        R<MutationResult> insertR = client.insert(insertParam);
+        Assertions.assertEquals(R.Status.Success.getCode(), insertR.getStatus().intValue());
+
+        // create index
+        CreateIndexParam indexParam = CreateIndexParam.newBuilder()
+                .withCollectionName(randomCollectionName)
+                .withFieldName(field2Name)
+                .withIndexType(IndexType.FLAT)
+                .withMetricType(MetricType.L2)
+                .build();
+
+        R<RpcStatus> createIndexR = client.createIndex(indexParam);
+        Assertions.assertEquals(R.Status.Success.getCode(), createIndexR.getStatus().intValue());
+
+        // load collection
+        R<RpcStatus> loadR = client.loadCollection(LoadCollectionParam.newBuilder()
+                .withCollectionName(randomCollectionName)
+                .build());
+        Assertions.assertEquals(R.Status.Success.getCode(), loadR.getStatus().intValue());
+
+        // query iterator
+        QueryIteratorParam.Builder queryIteratorParamBuilder = QueryIteratorParam.newBuilder()
+                .withCollectionName(randomCollectionName)
+                .withExpr("dynamic < 300")
+                .withOutFields(Lists.newArrayList("*"))
+                .withBatchSize(100L)
+                .withConsistencyLevel(ConsistencyLevelEnum.BOUNDED);
+
+        R<QueryIterator> qResponse = client.queryIterator(queryIteratorParamBuilder.build());
+        Assertions.assertEquals(R.Status.Success.getCode(), qResponse.getStatus().intValue());
+
+        QueryIterator queryIterator = qResponse.getData();
+        int counter = 0;
+        while (true) {
+            List<QueryResultsWrapper.RowRecord> res = queryIterator.next();
+            if (res.isEmpty()) {
+                System.out.println("query iteration finished, close");
+                queryIterator.close();
+                break;
+            }
+
+            for (QueryResultsWrapper.RowRecord record : res) {
+                Assertions.assertInstanceOf(Long.class, record.get("dynamic"));
+                Assertions.assertInstanceOf(String.class, record.get(field1Name));
+                Object vec = record.get(field2Name);
+                Assertions.assertInstanceOf(List.class, vec);
+                List<Float> vector = (List<Float>)vec;
+                Assertions.assertEquals(dimension, vector.size());
+                Assertions.assertInstanceOf(JsonElement.class, record.get(field3Name));
+//                System.out.println(record);
+                counter++;
+            }
+        }
+        Assertions.assertEquals(300, counter);
+
+        // search iterator
+        List<List<Float>> vectors = generateFloatVectors(1);
+        SearchIteratorParam.Builder searchIteratorParamBuilder = SearchIteratorParam.newBuilder()
+                .withCollectionName(randomCollectionName)
+                .withOutFields(Lists.newArrayList("*"))
+                .withBatchSize(10L)
+                .withVectorFieldName(field2Name)
+                .withFloatVectors(vectors)
+                .withTopK(50)
+                .withMetricType(MetricType.L2);
+
+        R<SearchIterator> sResponse = client.searchIterator(searchIteratorParamBuilder.build());
+        Assertions.assertEquals(R.Status.Success.getCode(), sResponse.getStatus().intValue());
+
+        SearchIterator searchIterator = sResponse.getData();
+        counter = 0;
+        while (true) {
+            List<QueryResultsWrapper.RowRecord> res = searchIterator.next();
+            if (res.isEmpty()) {
+                System.out.println("search iteration finished, close");
+                searchIterator.close();
+                break;
+            }
+
+            for (QueryResultsWrapper.RowRecord record : res) {
+                Assertions.assertInstanceOf(Long.class, record.get("dynamic"));
+                Assertions.assertInstanceOf(String.class, record.get(field1Name));
+                Object vec = record.get(field2Name);
+                Assertions.assertInstanceOf(List.class, vec);
+                List<Float> vector = (List<Float>)vec;
+                Assertions.assertEquals(dimension, vector.size());
+                Assertions.assertInstanceOf(JsonElement.class, record.get(field3Name));
+//                System.out.println(record);
+                counter++;
+            }
+        }
+        Assertions.assertEquals(50, counter);
+    }
 }

+ 9 - 8
src/test/java/io/milvus/v2/service/vector/VectorTest.java

@@ -1,6 +1,6 @@
 package io.milvus.v2.service.vector;
 
-import com.alibaba.fastjson.JSONObject;
+import com.google.gson.*;
 import io.milvus.v2.BaseTest;
 import io.milvus.v2.service.vector.request.*;
 import io.milvus.v2.service.vector.response.*;
@@ -19,14 +19,15 @@ class VectorTest extends BaseTest {
     @Test
     void testInsert() {
 
-        List<JSONObject> data = new ArrayList<>();
+        List<JsonObject> data = new ArrayList<>();
+        Gson gson = new Gson();
         for (int i = 0; i < 100; i++) {
-            JSONObject vector = new JSONObject();
+            JsonObject vector = new JsonObject();
             List<Float> vectorList = new ArrayList<>();
             vectorList.add(1.0f);
             vectorList.add(2.0f);
-            vector.put("vector", vectorList);
-            vector.put("id", (long) i);
+            vector.add("vector", gson.toJsonTree(vectorList));
+            vector.addProperty("id", (long) i);
             data.add(vector);
         }
 
@@ -41,12 +42,12 @@ class VectorTest extends BaseTest {
     @Test
     void testUpsert() {
 
-        JSONObject jsonObject = new JSONObject();
+        JsonObject jsonObject = new JsonObject();
         List<Float> vectorList = new ArrayList<>();
         vectorList.add(2.0f);
         vectorList.add(3.0f);
-        jsonObject.put("vector", vectorList);
-        jsonObject.put("id", 0L);
+        jsonObject.add("vector", new Gson().toJsonTree(vectorList));
+        jsonObject.addProperty("id", 0L);
         UpsertReq request = UpsertReq.builder()
                 .collectionName("test")
                 .data(Collections.singletonList(jsonObject))

+ 3 - 3
tests/milvustest/pom.xml

@@ -129,9 +129,9 @@
             <version>4.9.0</version>
         </dependency>
         <dependency>
-            <groupId>com.alibaba</groupId>
-            <artifactId>fastjson</artifactId>
-            <version>2.0.12</version>
+            <groupId>com.google.code.gson</groupId>
+            <artifactId>gson</artifactId>
+            <version>2.10.1</version>
         </dependency>
         <!-- https://mvnrepository.com/artifact/org.apache.httpcomponents/httpclient -->
         <dependency>

+ 78 - 74
tests/milvustest/src/main/java/com/zilliz/milvustest/common/CommonFunction.java

@@ -1,6 +1,6 @@
 package com.zilliz.milvustest.common;
 
-import com.alibaba.fastjson.JSONObject;
+import com.google.gson.*;
 import com.google.common.collect.Lists;
 import com.zilliz.milvustest.entity.FileBody;
 import com.zilliz.milvustest.entity.MilvusEntity;
@@ -928,61 +928,63 @@ public class CommonFunction {
     return collectionName;
   }
 
-  public static List<JSONObject> generateJsonData(int num){
-    List<JSONObject> jsonList=new ArrayList<>();
+  public static List<JsonObject> generateJsonData(int num){
+    List<JsonObject> jsonList=new ArrayList<>();
     Random ran = new Random();
+    Gson gson = new Gson();
     for (int i = 0; i < num; i++) {
-      JSONObject row=new JSONObject();
-      row.put("int64_field",(long)i);
-      row.put("float_field",(float)i);
+      JsonObject row=new JsonObject();
+      row.addProperty("int64_field",(long)i);
+      row.addProperty("float_field",(float)i);
       List<Float> vector=new ArrayList<>();
       for (int k = 0; k < 128; ++k) {
         vector.add(ran.nextFloat());
       }
-      row.put("float_vector",vector);
-      row.put("string_field","Str"+i);
-      row.put("boolean_field",i % 2 == 0);
-      JSONObject jsonObject=new JSONObject();
-      jsonObject.put("int64_field", (long)i);
-      jsonObject.put("float_field", (float)i);
-      jsonObject.put("string_field", "Str"+i);
-      jsonObject.put("boolean_field",i % 2 == 0);
-      jsonObject.put("int8", (short)i);
-      jsonObject.put("floatF", (float)i);
-      jsonObject.put("doubleF", (double)i);
-      jsonObject.put("bool", i % 2 == 0);
-      jsonObject.put("array_field",Arrays.asList(i,i+1,i+2));
+      row.add("float_vector",gson.toJsonTree(vector));
+      row.addProperty("string_field","Str"+i);
+      row.addProperty("boolean_field",i % 2 == 0);
+      JsonObject jsonObject=new JsonObject();
+      jsonObject.addProperty("int64_field", (long)i);
+      jsonObject.addProperty("float_field", (float)i);
+      jsonObject.addProperty("string_field", "Str"+i);
+      jsonObject.addProperty("boolean_field",i % 2 == 0);
+      jsonObject.addProperty("int8", (short)i);
+      jsonObject.addProperty("floatF", (float)i);
+      jsonObject.addProperty("doubleF", (double)i);
+      jsonObject.addProperty("bool", i % 2 == 0);
+      jsonObject.add("array_field",gson.toJsonTree(Arrays.asList(i,i+1,i+2)));
       // $innerJson
-      JSONObject innerJson = new JSONObject();
-      innerJson.put("int64", (long)i);
-      innerJson.put("varchar", "Str"+i);
-      innerJson.put("int16", i);
-      innerJson.put("int32", i);
-      innerJson.put("int8", (short)i);
-      innerJson.put("floatF", (float)i);
-      innerJson.put("doubleF", (double)i);
-      innerJson.put("bool", i % 2 == 0);
-      jsonObject.put("inner_json",innerJson);
-      row.put("json_field",jsonObject);
+      JsonObject innerJson = new JsonObject();
+      innerJson.addProperty("int64", (long)i);
+      innerJson.addProperty("varchar", "Str"+i);
+      innerJson.addProperty("int16", i);
+      innerJson.addProperty("int32", i);
+      innerJson.addProperty("int8", (short)i);
+      innerJson.addProperty("floatF", (float)i);
+      innerJson.addProperty("doubleF", (double)i);
+      innerJson.addProperty("bool", i % 2 == 0);
+      jsonObject.add("inner_json",innerJson);
+      row.add("json_field",jsonObject);
       jsonList.add(row);
     }
     return jsonList;
   }
 
-  public static List<JSONObject> generateJsonDataWithArrayField(int num){
-    List<JSONObject> jsonList=new ArrayList<>();
+  public static List<JsonObject> generateJsonDataWithArrayField(int num){
+    List<JsonObject> jsonList=new ArrayList<>();
     Random ran = new Random();
+    Gson gson = new Gson();
     for (int i = 0; i < num; i++) {
-      JSONObject row=new JSONObject();
-      row.put("int64_field",(long)i);
+      JsonObject row=new JsonObject();
+      row.addProperty("int64_field",(long)i);
       List<Float> vector=new ArrayList<>();
       for (int k = 0; k < 128; ++k) {
         vector.add(ran.nextFloat());
       }
-      row.put("float_vector",vector);
-      row.put("str_array_field", Lists.newArrayList("str"+i,"str"+(i+1),"str"+(i+2)));
-      row.put("int_array_field",Lists.newArrayList((long)i,(long)(i+1),(long)(i+2)));
-      row.put("float_array_field",Lists.newArrayList((float)(i+0.1),(float)(i+0.2),(float)(i+0.2)));
+      row.add("float_vector",gson.toJsonTree(vector));
+      row.add("str_array_field", gson.toJsonTree(Lists.newArrayList("str"+i,"str"+(i+1),"str"+(i+2))));
+      row.add("int_array_field", gson.toJsonTree(Lists.newArrayList((long)i,(long)(i+1),(long)(i+2))));
+      row.add("float_array_field", gson.toJsonTree(Lists.newArrayList((float)(i+0.1),(float)(i+0.2),(float)(i+0.2))));
       jsonList.add(row);
     }
     return jsonList;
@@ -1011,60 +1013,62 @@ public class CommonFunction {
     // logger.info("generateTestData"+ JacksonUtil.serialize(fields));
     return fields;
   }
-  public static List<JSONObject> generateDataWithDynamicFiledRow(int num) {
-    List<JSONObject> jsonList = new ArrayList<>();
+  public static List<JsonObject> generateDataWithDynamicFiledRow(int num) {
+    List<JsonObject> jsonList = new ArrayList<>();
     Random ran = new Random();
+    Gson gson = new Gson();
     for (int i = 0; i < num; i++) {
-      JSONObject row = new JSONObject();
-      row.put("book_id", (long) i);
-      row.put("word_count", (long) i);
-      row.put("extra_field", "String" + i);
-      row.put("extra_field2",  i);
+      JsonObject row = new JsonObject();
+      row.addProperty("book_id", (long) i);
+      row.addProperty("word_count", (long) i);
+      row.addProperty("extra_field", "String" + i);
+      row.addProperty("extra_field2",  i);
       // $innerJson
-      JSONObject innerJson = new JSONObject();
-      innerJson.put("int64", (long) i);
-      innerJson.put("varchar", "varchar"+i);
-      innerJson.put("int16", i);
-      innerJson.put("int32", i);
-      innerJson.put("int8", (short)i);
-      innerJson.put("float", (float)i);
-      innerJson.put("double", (double)i);
-      innerJson.put("bool", i % 2 == 0);
-      row.put("json_field", innerJson);
+      JsonObject innerJson = new JsonObject();
+      innerJson.addProperty("int64", (long) i);
+      innerJson.addProperty("varchar", "varchar"+i);
+      innerJson.addProperty("int16", i);
+      innerJson.addProperty("int32", i);
+      innerJson.addProperty("int8", (short)i);
+      innerJson.addProperty("float", (float)i);
+      innerJson.addProperty("double", (double)i);
+      innerJson.addProperty("bool", i % 2 == 0);
+      row.add("json_field", innerJson);
       List<Float> vector = new ArrayList<>();
       for (int k = 0; k < 128; ++k) {
         vector.add(ran.nextFloat());
       }
-      row.put("book_intro", vector);
+      row.add("book_intro", gson.toJsonTree(vector));
       jsonList.add(row);
     }
     return jsonList;
   }
-  public static List<JSONObject> generateVarcharPKDataWithDynamicFiledRow(int num) {
-    List<JSONObject> jsonList = new ArrayList<>();
+  public static List<JsonObject> generateVarcharPKDataWithDynamicFiledRow(int num) {
+    List<JsonObject> jsonList = new ArrayList<>();
     Random ran = new Random();
+    Gson gson = new Gson();
     for (int i = 0; i < num; i++) {
-      JSONObject row = new JSONObject();
-      row.put("book_name",  "StringPK"+i);
-      row.put("word_count", (long) i);
-      row.put("extra_field", "String" + i);
-      row.put("extra_field2",  i);
+      JsonObject row = new JsonObject();
+      row.addProperty("book_name",  "StringPK"+i);
+      row.addProperty("word_count", (long) i);
+      row.addProperty("extra_field", "String" + i);
+      row.addProperty("extra_field2",  i);
       // $innerJson
-      JSONObject innerJson = new JSONObject();
-      innerJson.put("int64", (long) i);
-      innerJson.put("varchar", "varchar"+i);
-      innerJson.put("int16", i);
-      innerJson.put("int32", i);
-      innerJson.put("int8", (short)i);
-      innerJson.put("float", (float)i);
-      innerJson.put("double", (double)i);
-      innerJson.put("bool", i % 2 == 0);
-      row.put("json_field", innerJson);
+      JsonObject innerJson = new JsonObject();
+      innerJson.addProperty("int64", (long) i);
+      innerJson.addProperty("varchar", "varchar"+i);
+      innerJson.addProperty("int16", i);
+      innerJson.addProperty("int32", i);
+      innerJson.addProperty("int8", (short)i);
+      innerJson.addProperty("float", (float)i);
+      innerJson.addProperty("double", (double)i);
+      innerJson.addProperty("bool", i % 2 == 0);
+      row.add("json_field", innerJson);
       List<Float> vector = new ArrayList<>();
       for (int k = 0; k < 128; ++k) {
         vector.add(ran.nextFloat());
       }
-      row.put("book_intro", vector);
+      row.add("book_intro", gson.toJsonTree(vector));
       jsonList.add(row);
     }
     return jsonList;

+ 16 - 16
tests/milvustest/src/main/java/com/zilliz/milvustest/service/CustomerListener.java

@@ -1,7 +1,7 @@
 package com.zilliz.milvustest.service;
 
 
-import com.alibaba.fastjson.JSONObject;
+import com.google.gson.JsonObject;
 import com.zilliz.milvustest.util.HttpClientUtils;
 import com.zilliz.milvustest.util.PropertyFilesUtil;
 import org.slf4j.Logger;
@@ -98,21 +98,21 @@ public class CustomerListener extends TestListenerAdapter {
             : System.getProperty("SDKBranch");
     String jenkinsLink="https://qa-jenkins.milvus.io/job/Java-sdk-test-nightly/"+BuildId+"/";
     String githubLink="https://github.com/milvus-io/milvus-sdk-java/actions/workflows/java_sdk_ci_test.yaml";
-    JSONObject request=new JSONObject();
-    request.put("Product","Milvus");
-    request.put("Category","Function");
-    request.put("Date", LocalDate.now().toString());
-    request.put("Scenario",scenarioDesc);
-    request.put("Branch",SDKBranch);
-    request.put("ImageName","2.2.0");
-    request.put("SDK","java");
-    request.put("MilvusMode","standalone");
-    request.put("MqMode","rocksMq");
-    request.put("TestResult",passRate==100?"pass":"fail");
-    request.put("PassRate", passRate);
-    request.put("RunningTime", costTime);
-    request.put("Link",scenarioDesc.equalsIgnoreCase("CI")?githubLink:jenkinsLink);
-    String s = HttpClientUtils.doPostJson("http://qtp-server.zilliz.cc/results/insert",request.toJSONString());
+    JsonObject request=new JsonObject();
+    request.addProperty("Product","Milvus");
+    request.addProperty("Category","Function");
+    request.addProperty("Date", LocalDate.now().toString());
+    request.addProperty("Scenario",scenarioDesc);
+    request.addProperty("Branch",SDKBranch);
+    request.addProperty("ImageName","2.2.0");
+    request.addProperty("SDK","java");
+    request.addProperty("MilvusMode","standalone");
+    request.addProperty("MqMode","rocksMq");
+    request.addProperty("TestResult",passRate==100?"pass":"fail");
+    request.addProperty("PassRate", passRate);
+    request.addProperty("RunningTime", costTime);
+    request.addProperty("Link",scenarioDesc.equalsIgnoreCase("CI")?githubLink:jenkinsLink);
+    String s = HttpClientUtils.doPostJson("http://qtp-server.zilliz.cc/results/insert",request.toString());
     logger.info("insert result:"+s);
 /*    if (iTestContext.getFailedTests().size()>0){
       throw new RuntimeException("Case Failed "+iTestContext.getFailedTests().size());

+ 2 - 2
tests/milvustest/src/main/java/com/zilliz/milvustest/util/HttpClientUtils.java

@@ -1,7 +1,7 @@
 package com.zilliz.milvustest.util;
 
 
-import com.alibaba.fastjson.JSON;
+import com.google.gson.Gson;
 import org.apache.commons.logging.Log;
 import org.apache.commons.logging.LogFactory;
 import org.apache.http.*;
@@ -271,7 +271,7 @@ public class HttpClientUtils {
                 }*/
                 // 模拟表单
                 //UrlEncodedFormEntity entity = new UrlEncodedFormEntity(param, "utf-8");
-                HttpEntity entity1=new StringEntity(JSON.toJSONString(param),"utf-8");
+                HttpEntity entity1=new StringEntity(new Gson().toJson(param),"utf-8");
                 httpPost.setEntity(entity1);
             }
             // 执行http请求

+ 10 - 9
tests/milvustest/src/test/java/com/zilliz/milvustest/bulk/BulkWriteTest.java

@@ -1,6 +1,6 @@
 package com.zilliz.milvustest.bulk;
 
-import com.alibaba.fastjson.JSONObject;
+import com.google.gson.*;
 import com.zilliz.milvustest.common.BaseTest;
 import com.zilliz.milvustest.common.CommonData;
 import com.zilliz.milvustest.common.CommonFunction;
@@ -67,7 +67,7 @@ public class BulkWriteTest extends BaseTest {
                 .build();
         LocalBulkWriter localBulkWriter=new LocalBulkWriter(localBulkWriterParam);
 
-        List<JSONObject> jsonObjects = CommonFunction.generateJsonData(10000);
+        List<JsonObject> jsonObjects = CommonFunction.generateJsonData(10000);
         jsonObjects.forEach(x->{
             try {
                 localBulkWriter.appendRow(x);
@@ -136,14 +136,15 @@ public class BulkWriteTest extends BaseTest {
                 .build();
         try (RemoteBulkWriter remoteBulkWriter = new RemoteBulkWriter(bulkWriterParam)) {
             // append rows
+            Gson gson = new Gson();
             for (int i = 0; i < 10; i++) {
-                JSONObject row = new JSONObject();
-                row.put("string_field", "path_" + i);
-                row.put("float_vector", GeneratorUtils.genFloatVector(128));
-                row.put("int64_field", (long)i);
-                row.put("boolean_field", false);
-                row.put("json_field", new JSONObject());
-                row.put("float_field", (float)i);
+                JsonObject row = new JsonObject();
+                row.addProperty("string_field", "path_" + i);
+                row.add("float_vector", gson.toJsonTree(GeneratorUtils.genFloatVector(128)));
+                row.addProperty("int64_field", (long)i);
+                row.addProperty("boolean_field", false);
+                row.add("json_field", new JsonObject());
+                row.addProperty("float_field", (float)i);
 
                 remoteBulkWriter.appendRow(row);
             }

+ 21 - 21
tests/milvustest/src/test/java/com/zilliz/milvustest/bulkimport/BulkImportTest.java

@@ -1,6 +1,6 @@
 package com.zilliz.milvustest.bulkimport;
 
-import com.alibaba.fastjson.JSONObject;
+import com.google.gson.*;
 import com.zilliz.milvustest.common.BaseCloudTest;
 import com.zilliz.milvustest.util.PropertyFilesUtil;
 import io.milvus.bulkwriter.CloudImport;
@@ -235,33 +235,33 @@ public class BulkImportTest extends BaseCloudTest {
         try (RemoteBulkWriter remoteBulkWriter = buildRemoteBulkWriter(collectionSchema, BulkFileType.PARQUET)) {
             System.out.println("Append rows");
             int batchCount = 10;
-
+            Gson gson = new Gson();
             for (int i = 0; i < batchCount; ++i) {
-                JSONObject rowObject = new JSONObject();
+                JsonObject rowObject = new JsonObject();
 
                 // scalar field
-                rowObject.put("id", i);
-                rowObject.put("bool", i % 5 == 0);
-                rowObject.put("int8", i % 128);
-                rowObject.put("int16", i % 1000);
-                rowObject.put("int32", i % 100000);
-                rowObject.put("float", i / 3);
-                rowObject.put("double", i / 7);
-                rowObject.put("varchar", "varchar_" + i);
-                rowObject.put("json", String.format("{\"dummy\": %s, \"ok\": \"name_%s\"}", i, i));
+                rowObject.addProperty("id", i);
+                rowObject.addProperty("bool", i % 5 == 0);
+                rowObject.addProperty("int8", i % 128);
+                rowObject.addProperty("int16", i % 1000);
+                rowObject.addProperty("int32", i % 100000);
+                rowObject.addProperty("float", i / 3);
+                rowObject.addProperty("double", i / 7);
+                rowObject.addProperty("varchar", "varchar_" + i);
+                rowObject.addProperty("json", String.format("{\"dummy\": %s, \"ok\": \"name_%s\"}", i, i));
 
                 // vector field
-                rowObject.put("vector", false ? GeneratorUtils.generatorBinaryVector(128) : GeneratorUtils.generatorFloatValue(128));
+                rowObject.add("vector", gson.toJsonTree(GeneratorUtils.generatorFloatValue(128)));
 
                 // array field
-                rowObject.put("arrayInt64", GeneratorUtils.generatorLongValue(10));
-                rowObject.put("arrayVarchar", GeneratorUtils.generatorVarcharValue(10, 10));
-                rowObject.put("arrayInt8", GeneratorUtils.generatorInt8Value(10));
-                rowObject.put("arrayInt16", GeneratorUtils.generatorInt16Value(10));
-                rowObject.put("arrayInt32", GeneratorUtils.generatorInt32Value(10));
-                rowObject.put("arrayFloat", GeneratorUtils.generatorFloatValue(10));
-                rowObject.put("arrayDouble", GeneratorUtils.generatorDoubleValue(10));
-                rowObject.put("arrayBool", GeneratorUtils.generatorBoolValue(10));
+                rowObject.add("arrayInt64", gson.toJsonTree(GeneratorUtils.generatorLongValue(10)));
+                rowObject.add("arrayVarchar", gson.toJsonTree(GeneratorUtils.generatorVarcharValue(10, 10)));
+                rowObject.add("arrayInt8", gson.toJsonTree(GeneratorUtils.generatorInt8Value(10)));
+                rowObject.add("arrayInt16", gson.toJsonTree(GeneratorUtils.generatorInt16Value(10)));
+                rowObject.add("arrayInt32", gson.toJsonTree(GeneratorUtils.generatorInt32Value(10)));
+                rowObject.add("arrayFloat", gson.toJsonTree(GeneratorUtils.generatorFloatValue(10)));
+                rowObject.add("arrayDouble", gson.toJsonTree(GeneratorUtils.generatorDoubleValue(10)));
+                rowObject.add("arrayBool", gson.toJsonTree(GeneratorUtils.generatorBoolValue(10)));
 
                 remoteBulkWriter.appendRow(rowObject);
             }

+ 5 - 6
tests/milvustest/src/test/java/com/zilliz/milvustest/businessflow/ConcurrentTest.java

@@ -1,7 +1,6 @@
 package com.zilliz.milvustest.businessflow;
 
-import com.alibaba.fastjson.JSONArray;
-import com.alibaba.fastjson.JSONObject;
+import com.google.gson.*;
 import com.zilliz.milvustest.common.CommonData;
 import com.zilliz.milvustest.common.CommonFunction;
 import com.zilliz.milvustest.util.FileUtils;
@@ -61,12 +60,12 @@ public class ConcurrentTest {
     public Object[][] providerPrivilegeList() {
         File jsonFile=new File("./src/test/java/resources/testdata/privilege.json");
         String str = FileUtils.getStr(jsonFile);
-        JSONArray jsonArray = JSONObject.parseArray(str);
+        JsonArray jsonArray = new Gson().fromJson(str, JsonArray.class);
         objects=new Object[jsonArray.size()][3];
         for (int i = 0; i < jsonArray.size(); i++) {
-            objects[i][0]=((JSONObject)jsonArray.get(i)).getString("object");
-            objects[i][1]=((JSONObject)jsonArray.get(i)).getString("objectName");
-            objects[i][2]=((JSONObject)jsonArray.get(i)).getString("privilege");
+            objects[i][0]=jsonArray.get(i).getAsJsonObject.get("object").getAsString();
+            objects[i][1]=jsonArray.get(i)).getAsJsonObject.get("objectName").getAsString();
+            objects[i][2]=jsonArray.get(i)).getAsJsonObject.get("privilege").getAsString();
         }
 
         return objects;

+ 5 - 5
tests/milvustest/src/test/java/com/zilliz/milvustest/insert/InsertTest.java

@@ -1,6 +1,6 @@
 package com.zilliz.milvustest.insert;
 
-import com.alibaba.fastjson.JSONObject;
+import com.google.gson.JsonObject;
 import com.zilliz.milvustest.common.BaseTest;
 import com.zilliz.milvustest.common.CommonData;
 import com.zilliz.milvustest.common.CommonFunction;
@@ -441,7 +441,7 @@ public class InsertTest extends BaseTest {
   @Severity(SeverityLevel.BLOCKER)
   @Test(description = "Insert data into collection with JSON field",groups = {"Smoke"})
   public void insertDataCollectionWithJsonField(){
-    List<JSONObject> jsonObjects = CommonFunction.generateJsonData(100);
+    List<JsonObject> jsonObjects = CommonFunction.generateJsonData(100);
     System.out.println(jsonObjects);
     R<MutationResult> insert = milvusClient.insert(InsertParam.newBuilder()
             .withCollectionName(collectionWithJsonField)
@@ -453,7 +453,7 @@ public class InsertTest extends BaseTest {
   @Severity(SeverityLevel.BLOCKER)
   @Test(description = "Insert data into collection with Dynamic field",groups = {"Smoke"})
   public void insertDataCollectionWithDynamicField(){
-    List<JSONObject> jsonObjects = CommonFunction.generateDataWithDynamicFiledRow(100);
+    List<JsonObject> jsonObjects = CommonFunction.generateDataWithDynamicFiledRow(100);
     R<MutationResult> insert = milvusClient.insert(InsertParam.newBuilder()
             .withCollectionName(collectionWithDynamicField)
             .withRows(jsonObjects)
@@ -465,7 +465,7 @@ public class InsertTest extends BaseTest {
   @Test(description = "Insert data into collection with Dynamic field use column data",expectedExceptions = ParamException.class)
   public void insertDataCollectionWithDynamicFieldUseColumnData(){
     List<InsertParam.Field> fields = CommonFunction.generateDataWithDynamicFiledColumn(100);
-    List<JSONObject> jsonObjects = CommonFunction.generateJsonData(100);
+    List<JsonObject> jsonObjects = CommonFunction.generateJsonData(100);
     R<MutationResult> insert = milvusClient.insert(InsertParam.newBuilder()
             .withCollectionName(collectionWithDynamicField)
             .withFields(fields)
@@ -477,7 +477,7 @@ public class InsertTest extends BaseTest {
   @Test(description = "Insert data into collection with Dynamic field",expectedExceptions = ParamException.class)
   public void insertFieldsAndRowsData(){
     List<InsertParam.Field> fields = CommonFunction.generateDataWithDynamicFiledColumn(100);
-    List<JSONObject> jsonObjects = CommonFunction.generateDataWithDynamicFiledRow(100);
+    List<JsonObject> jsonObjects = CommonFunction.generateDataWithDynamicFiledRow(100);
     R<MutationResult> insert = milvusClient.insert(InsertParam.newBuilder()
             .withCollectionName(collectionWithDynamicField)
             .withFields(fields)

+ 8 - 8
tests/milvustest/src/test/java/com/zilliz/milvustest/query/QueryTest.java

@@ -1,6 +1,6 @@
 package com.zilliz.milvustest.query;
 
-import com.alibaba.fastjson.JSONObject;
+import com.google.gson.JsonObject;
 import com.zilliz.milvustest.common.BaseTest;
 import com.zilliz.milvustest.common.CommonData;
 import com.zilliz.milvustest.common.CommonFunction;
@@ -1042,7 +1042,7 @@ public class QueryTest extends BaseTest {
   @Test(description = "query collection with dynamic field",groups = {"Smoke"},dataProvider = "dynamicExpressions")
   @Severity(SeverityLevel.BLOCKER)
   public void queryCollectionWithDynamicField(String expr) {
-    List<JSONObject> jsonObjects = CommonFunction.generateDataWithDynamicFiledRow(1000);
+    List<JsonObject> jsonObjects = CommonFunction.generateDataWithDynamicFiledRow(1000);
     R<MutationResult> insert = milvusClient.insert(InsertParam.newBuilder()
             .withRows(jsonObjects)
             .withCollectionName(collectionWithDynamicField)
@@ -1070,7 +1070,7 @@ public class QueryTest extends BaseTest {
   @Test(description = "query collection with dynamic field use inner json field",groups = {"Smoke"},dataProvider = "dynamicExpressions")
   @Severity(SeverityLevel.BLOCKER)
   public void queryWithDynamicFieldUseInnerJsonField(String expr) {
-    List<JSONObject> jsonObjects = CommonFunction.generateDataWithDynamicFiledRow(1000);
+    List<JsonObject> jsonObjects = CommonFunction.generateDataWithDynamicFiledRow(1000);
     R<MutationResult> insert = milvusClient.insert(InsertParam.newBuilder()
             .withRows(jsonObjects)
             .withCollectionName(collectionWithDynamicField)
@@ -1094,7 +1094,7 @@ public class QueryTest extends BaseTest {
   @Test(description = "query collection with dynamic field use nonexistent field name")
   @Severity(SeverityLevel.NORMAL)
   public void queryWithDynamicFieldUseNonexistentFiledName() {
-    List<JSONObject> jsonObjects = CommonFunction.generateDataWithDynamicFiledRow(1000);
+    List<JsonObject> jsonObjects = CommonFunction.generateDataWithDynamicFiledRow(1000);
     R<MutationResult> insert = milvusClient.insert(InsertParam.newBuilder()
             .withRows(jsonObjects)
             .withCollectionName(collectionWithDynamicField)
@@ -1122,7 +1122,7 @@ public class QueryTest extends BaseTest {
   @Test(description = "query collection with json field",groups = {"Smoke"},dataProvider = "jsonExpressions")
   @Severity(SeverityLevel.BLOCKER)
   public void queryCollectionWithJsonField(String expr) {
-    List<JSONObject> jsonObjects = CommonFunction.generateJsonData(1000);
+    List<JsonObject> jsonObjects = CommonFunction.generateJsonData(1000);
     R<MutationResult> insert = milvusClient.insert(InsertParam.newBuilder()
             .withRows(jsonObjects)
             .withCollectionName(collectionWithJsonField)
@@ -1141,15 +1141,15 @@ public class QueryTest extends BaseTest {
     QueryResultsWrapper wrapperQuery = new QueryResultsWrapper(queryResultsR.getData());
     Assert.assertEquals(queryResultsR.getStatus().intValue(), 0);
     Assert.assertTrue(wrapperQuery.getFieldWrapper("json_field").getFieldData().size()>=4);
-    JSONObject jsonObject = (JSONObject) wrapperQuery.getRowRecords().get(0).get("json_field");
-    String string_field = jsonObject.getString("string_field");
+    JsonObject jsonObject = (JsonObject) wrapperQuery.getRowRecords().get(0).get("json_field");
+    String string_field = jsonObject.get("string_field").getAsString();
     Assert.assertTrue(string_field.contains("Str"));
   }
 
   @Test(description = "query collection with array field",groups = {"Smoke"})
   @Severity(SeverityLevel.BLOCKER)
   public void queryCollectionWithArrayField() {
-    List<JSONObject> jsonObjects = CommonFunction.generateJsonDataWithArrayField(1000);
+    List<JsonObject> jsonObjects = CommonFunction.generateJsonDataWithArrayField(1000);
     R<MutationResult> insert = milvusClient.insert(InsertParam.newBuilder()
             .withRows(jsonObjects)
             .withCollectionName(collectionWithArrayField)

+ 5 - 6
tests/milvustest/src/test/java/com/zilliz/milvustest/rbac/GrantRolePrivilegeTest.java

@@ -1,7 +1,6 @@
 package com.zilliz.milvustest.rbac;
 
-import com.alibaba.fastjson.JSONArray;
-import com.alibaba.fastjson.JSONObject;
+import com.google.gson.*;
 import com.zilliz.milvustest.common.BaseTest;
 import com.zilliz.milvustest.common.CommonData;
 import com.zilliz.milvustest.common.CommonFunction;
@@ -39,12 +38,12 @@ public class GrantRolePrivilegeTest extends BaseTest {
   public Object[][] providerPrivilegeList() {
     File jsonFile=new File("./src/test/java/resources/testdata/privilege.json");
     String str = FileUtils.getStr(jsonFile);
-    JSONArray jsonArray = JSONObject.parseArray(str);
+    JsonArray jsonArray = new Gson().fromJson(str, JsonArray.class);
     Object[][] objects=new Object[jsonArray.size()][3];
     for (int i = 0; i < jsonArray.size(); i++) {
-      objects[i][0]=((JSONObject)jsonArray.get(i)).getString("object");
-      objects[i][1]=((JSONObject)jsonArray.get(i)).getString("objectName");
-      objects[i][2]=((JSONObject)jsonArray.get(i)).getString("privilege");
+      objects[i][0]=jsonArray.get(i).getAsJsonObject().get("object").getAsString();
+      objects[i][1]=jsonArray.get(i).getAsJsonObject().get("objectName").getAsString();
+      objects[i][2]=jsonArray.get(i).getAsJsonObject().get("privilege").getAsString();
     }
 
     return objects;

+ 6 - 6
tests/milvustest/src/test/java/com/zilliz/milvustest/search/SearchTest.java

@@ -1,6 +1,6 @@
 package com.zilliz.milvustest.search;
 
-import com.alibaba.fastjson.JSONObject;
+import com.google.gson.JsonObject;
 import com.google.common.collect.Lists;
 import com.zilliz.milvustest.common.BaseTest;
 import com.zilliz.milvustest.common.CommonData;
@@ -1847,7 +1847,7 @@ public class SearchTest extends BaseTest {
     @Severity(SeverityLevel.BLOCKER)
     @Test(description = "Search with DynamicField.", groups = {"Smoke"}, dataProvider = "dynamicExpressions")
     public void searchWithDynamicField(String expr) {
-        List<JSONObject> jsonObjects = CommonFunction.generateDataWithDynamicFiledRow(1000);
+        List<JsonObject> jsonObjects = CommonFunction.generateDataWithDynamicFiledRow(1000);
         R<MutationResult> insert = milvusClient.insert(InsertParam.newBuilder()
                 .withRows(jsonObjects)
                 .withCollectionName(collectionWithDynamicField)
@@ -1883,7 +1883,7 @@ public class SearchTest extends BaseTest {
     @Severity(SeverityLevel.NORMAL)
     @Test(description = "Search with DynamicField use nonexistent field name")
     public void searchWithDynamicFieldUseNonexistentFiledName() {
-        List<JSONObject> jsonObjects = CommonFunction.generateDataWithDynamicFiledRow(1000);
+        List<JsonObject> jsonObjects = CommonFunction.generateDataWithDynamicFiledRow(1000);
         R<MutationResult> insert = milvusClient.insert(InsertParam.newBuilder()
                 .withRows(jsonObjects)
                 .withCollectionName(collectionWithDynamicField)
@@ -1919,7 +1919,7 @@ public class SearchTest extends BaseTest {
     @Severity(SeverityLevel.BLOCKER)
     @Test(description = "Search with JSON field.", groups = {"Smoke"}, dataProvider = "jsonExpressions")
     public void searchWithJsonField(String expr,int topK,int expected) {
-        List<JSONObject> jsonObjects = CommonFunction.generateJsonData(1000);
+        List<JsonObject> jsonObjects = CommonFunction.generateJsonData(1000);
         R<MutationResult> insert = milvusClient.insert(InsertParam.newBuilder()
                 .withRows(jsonObjects)
                 .withCollectionName(collectionWithJsonField)
@@ -1950,7 +1950,7 @@ public class SearchTest extends BaseTest {
         String string_field = json_field.getAsString(0, "string_field");
         Assert.assertTrue(string_field.contains("Str"));
         // 按照行
-        JSONObject jsonObject = (JSONObject) searchResultsWrapper.getIDScore(0).get(0).get("json_field");
+        JsonObject jsonObject = (JsonObject) searchResultsWrapper.getIDScore(0).get(0).get("json_field");
         String string = jsonObject.getString("string_field");
         Assert.assertTrue(string.contains("Str"));*/
 
@@ -2018,7 +2018,7 @@ public class SearchTest extends BaseTest {
     @Severity(SeverityLevel.BLOCKER)
     @Test(description = "Search with array field", groups = {"Smoke"})
     public void searchWithArrayField() {
-        List<JSONObject> jsonObjects = CommonFunction.generateJsonDataWithArrayField(1000);
+        List<JsonObject> jsonObjects = CommonFunction.generateJsonDataWithArrayField(1000);
         R<MutationResult> insert = milvusClient.insert(InsertParam.newBuilder()
                 .withRows(jsonObjects)
                 .withCollectionName(collectionWithArrayField)

+ 3 - 3
tests/milvustest/src/test/java/com/zilliz/milvustest/serverless/HighLevelTest.java

@@ -1,6 +1,6 @@
 package com.zilliz.milvustest.serverless;
 
-import com.alibaba.fastjson.JSONObject;
+import com.google.gson.JsonObject;
 import com.google.common.collect.Lists;
 import com.zilliz.milvustest.common.BaseTest;
 import com.zilliz.milvustest.common.CommonData;
@@ -72,7 +72,7 @@ public class HighLevelTest extends BaseTest {
     @Severity(SeverityLevel.BLOCKER)
     @Test(description = "insert data into Collection", groups = {"Smoke"}, dependsOnMethods = "listCollectionTest")
     public void insertIntoCollectionTest() {
-        List<JSONObject> jsonObjects = CommonFunction.generateDataWithDynamicFiledRow(10000);
+        List<JsonObject> jsonObjects = CommonFunction.generateDataWithDynamicFiledRow(10000);
         R<InsertResponse> insert = milvusClient.insert(InsertRowsParam.newBuilder()
                 .withCollectionName(commonCollection)
                 .withRows(jsonObjects)
@@ -176,7 +176,7 @@ public class HighLevelTest extends BaseTest {
     @Severity(SeverityLevel.BLOCKER)
     @Test(description = "insert data into varchar PK Collection", groups = {"Smoke"}, dependsOnMethods = "listVarcharPKCollectionTest")
     public void insertIntoVarcharPKCollectionTest() throws InterruptedException {
-        List<JSONObject> jsonObjects = CommonFunction.generateVarcharPKDataWithDynamicFiledRow(10000);
+        List<JsonObject> jsonObjects = CommonFunction.generateVarcharPKDataWithDynamicFiledRow(10000);
         R<InsertResponse> insert = milvusClient.insert(InsertRowsParam.newBuilder()
                 .withCollectionName(varcharPKCollection)
                 .withRows(jsonObjects)

+ 2 - 2
tests/milvustest/src/test/java/com/zilliz/milvustest/tls/TLSTest.java

@@ -1,6 +1,6 @@
 package com.zilliz.milvustest.tls;
 
-import com.alibaba.fastjson.JSONObject;
+import com.google.gson.JsonObject;
 import com.google.common.collect.Lists;
 import com.zilliz.milvustest.common.BaseTest;
 import com.zilliz.milvustest.common.CommonData;
@@ -111,7 +111,7 @@ public class TLSTest {
                         .build();
         R<RpcStatus> collection = milvusClient.createCollection(createCollectionReq);
         // insert data
-        List<JSONObject> jsonObjects = CommonFunction.generateDataWithDynamicFiledRow(10000);
+        List<JsonObject> jsonObjects = CommonFunction.generateDataWithDynamicFiledRow(10000);
         R<InsertResponse> insert = milvusClient.insert(InsertRowsParam.newBuilder()
                 .withCollectionName(collectionName)
                 .withRows(jsonObjects)

+ 5 - 5
tests/milvustestv2/src/main/java/com/zilliz/milvustestv2/common/BaseTest.java

@@ -1,6 +1,6 @@
 package com.zilliz.milvustestv2.common;
 
-import com.alibaba.fastjson.JSONObject;
+import com.google.gson.JsonObject;
 import com.zilliz.milvustestv2.Milvustestv2Application;
 import com.zilliz.milvustestv2.config.ConnectInfoConfig;
 import com.zilliz.milvustestv2.utils.PropertyFilesUtil;
@@ -60,7 +60,7 @@ public class BaseTest extends AbstractTestNGSpringContextTests {
         CommonFunction.createNewCollection(CommonData.dim,CommonData.defaultFloatVectorCollection);
         milvusClientV2.createAlias(CreateAliasReq.builder().collectionName(CommonData.defaultFloatVectorCollection).alias(CommonData.alias).build());
         // insert data
-        List<JSONObject> jsonObjects = CommonFunction.generateDefaultData(CommonData.numberEntities, CommonData.dim);
+        List<JsonObject> jsonObjects = CommonFunction.generateDefaultData(CommonData.numberEntities, CommonData.dim);
         InsertResp insert = milvusClientV2.insert(InsertReq.builder().collectionName(CommonData.defaultFloatVectorCollection).data(jsonObjects).build());
         CommonFunction.createVectorIndex(CommonData.defaultFloatVectorCollection,CommonData.fieldFloatVector, IndexParam.IndexType.AUTOINDEX, IndexParam.MetricType.L2);
         milvusClientV2.loadCollection(LoadCollectionReq.builder().collectionName(CommonData.defaultFloatVectorCollection).build());
@@ -69,9 +69,9 @@ public class BaseTest extends AbstractTestNGSpringContextTests {
        CommonFunction.createPartition(CommonData.defaultFloatVectorCollection,CommonData.partitionNameA);
        CommonFunction.createPartition(CommonData.defaultFloatVectorCollection,CommonData.partitionNameB);
        CommonFunction.createPartition(CommonData.defaultFloatVectorCollection,CommonData.partitionNameC);
-        List<JSONObject> jsonObjectsA = CommonFunction.generateDefaultData(CommonData.numberEntities, CommonData.dim);
-        List<JSONObject> jsonObjectsB = CommonFunction.generateDefaultData(CommonData.numberEntities*2, CommonData.dim);
-        List<JSONObject> jsonObjectsC = CommonFunction.generateDefaultData(CommonData.numberEntities*3, CommonData.dim);
+        List<JsonObject> jsonObjectsA = CommonFunction.generateDefaultData(CommonData.numberEntities, CommonData.dim);
+        List<JsonObject> jsonObjectsB = CommonFunction.generateDefaultData(CommonData.numberEntities*2, CommonData.dim);
+        List<JsonObject> jsonObjectsC = CommonFunction.generateDefaultData(CommonData.numberEntities*3, CommonData.dim);
        milvusClientV2.insert(InsertReq.builder().collectionName(CommonData.defaultFloatVectorCollection).partitionName(CommonData.partitionNameA).data(jsonObjectsA).build());
        milvusClientV2.insert(InsertReq.builder().collectionName(CommonData.defaultFloatVectorCollection).partitionName(CommonData.partitionNameB).data(jsonObjectsB).build());
        milvusClientV2.insert(InsertReq.builder().collectionName(CommonData.defaultFloatVectorCollection).partitionName(CommonData.partitionNameC).data(jsonObjectsC).build());

+ 30 - 28
tests/milvustestv2/src/main/java/com/zilliz/milvustestv2/common/CommonFunction.java

@@ -1,6 +1,6 @@
 package com.zilliz.milvustestv2.common;
 
-import com.alibaba.fastjson.JSONObject;
+import com.google.gson.*;
 import com.google.common.collect.Lists;
 import com.zilliz.milvustestv2.utils.GenerateUtil;
 
@@ -128,34 +128,35 @@ public class CommonFunction {
      * @param dim 维度
      * @return List<JsonObject>
      */
-    public static List<JSONObject> generateDefaultData(long num,int dim){
-        List<JSONObject> jsonList=new ArrayList<>();
+    public static List<JsonObject> generateDefaultData(long num,int dim){
+        List<JsonObject> jsonList=new ArrayList<>();
         Random ran = new Random();
+        Gson gson = new Gson();
         for (long i = 0; i < num; i++) {
-            JSONObject row=new JSONObject();
-            row.put(CommonData.fieldInt64,i);
-            row.put(CommonData.fieldInt32,(int)i%32767);
-            row.put(CommonData.fieldInt16,(int)i%32767);
-            row.put(CommonData.fieldInt8,(short)i%127);
-            row.put(CommonData.fieldDouble,(double)i);
-            row.put(CommonData.fieldArray, Arrays.asList(i,i+1,i+2));
-            row.put(CommonData.fieldBool, i % 2 == 0);
-            row.put(CommonData.fieldVarchar,"Str"+i);
-            row.put(CommonData.fieldFloat,(float)i);
+            JsonObject row=new JsonObject();
+            row.addProperty(CommonData.fieldInt64,i);
+            row.addProperty(CommonData.fieldInt32,(int)i%32767);
+            row.addProperty(CommonData.fieldInt16,(int)i%32767);
+            row.addProperty(CommonData.fieldInt8,(short)i%127);
+            row.addProperty(CommonData.fieldDouble,(double)i);
+            row.add(CommonData.fieldArray, gson.toJsonTree(Arrays.asList(i,i+1,i+2)));
+            row.addProperty(CommonData.fieldBool, i % 2 == 0);
+            row.addProperty(CommonData.fieldVarchar,"Str"+i);
+            row.addProperty(CommonData.fieldFloat,(float)i);
             List<Float> vector=new ArrayList<>();
             for (int k = 0; k < dim; ++k) {
                 vector.add(ran.nextFloat());
             }
-            row.put(CommonData.fieldFloatVector,vector);
-            JSONObject json = new JSONObject();
-            json.put(CommonData.fieldInt64,(int)i%32767);
-            json.put(CommonData.fieldInt32,(int)i%32767);
-            json.put(CommonData.fieldDouble,(double)i);
-            json.put(CommonData.fieldArray, Arrays.asList(i,i+1,i+2));
-            json.put(CommonData.fieldBool, i % 2 == 0);
-            json.put(CommonData.fieldVarchar,"Str"+i);
-            json.put(CommonData.fieldFloat,(float)i);
-            row.put(CommonData.fieldJson,json);
+            row.add(CommonData.fieldFloatVector, gson.toJsonTree(vector));
+            JsonObject json = new JsonObject();
+            json.addProperty(CommonData.fieldInt64,(int)i%32767);
+            json.addProperty(CommonData.fieldInt32,(int)i%32767);
+            json.addProperty(CommonData.fieldDouble,(double)i);
+            json.add(CommonData.fieldArray, gson.toJsonTree(Arrays.asList(i,i+1,i+2)));
+            json.addProperty(CommonData.fieldBool, i % 2 == 0);
+            json.addProperty(CommonData.fieldVarchar,"Str"+i);
+            json.addProperty(CommonData.fieldFloat,(float)i);
+            row.add(CommonData.fieldJson,json);
             jsonList.add(row);
         }
         return jsonList;
@@ -167,17 +168,18 @@ public class CommonFunction {
      * @param dim 维度
      * @return List<JsonObject>
      */
-    public static List<JSONObject> generateSimpleData(long num,int dim){
-        List<JSONObject> jsonList=new ArrayList<>();
+    public static List<JsonObject> generateSimpleData(long num,int dim){
+        List<JsonObject> jsonList=new ArrayList<>();
         Random ran = new Random();
+        Gson gson = new Gson();
         for (long i = 0; i < num; i++) {
-            JSONObject row = new JSONObject();
-            row.put(CommonData.simplePk, i);
+            JsonObject row = new JsonObject();
+            row.addProperty(CommonData.simplePk, i);
             List<Float> vector=new ArrayList<>();
             for (int k = 0; k < dim; ++k) {
                 vector.add(ran.nextFloat());
             }
-            row.put(CommonData.simpleVector,vector);
+            row.add(CommonData.simpleVector, gson.toJsonTree(vector));
             jsonList.add(row);
         }
         return jsonList;

+ 16 - 16
tests/milvustestv2/src/main/java/com/zilliz/milvustestv2/listener/CustomerListener.java

@@ -1,7 +1,7 @@
 package com.zilliz.milvustestv2.listener;
 
 
-import com.alibaba.fastjson.JSONObject;
+import com.google.gson.JsonObject;
 import com.zilliz.milvustestv2.utils.HttpClientUtils;
 import com.zilliz.milvustestv2.utils.PropertyFilesUtil;
 import org.slf4j.Logger;
@@ -95,21 +95,21 @@ public class CustomerListener extends TestListenerAdapter {
             : System.getProperty("SDKBranch");
     String jenkinsLink="https://qa-jenkins.milvus.io/job/Java-sdk-test-nightly/"+BuildId+"/";
     String githubLink="https://github.com/milvus-io/milvus-sdk-java/actions/workflows/java_sdk_ci_test.yaml";
-    JSONObject request=new JSONObject();
-    request.put("Product","Milvus");
-    request.put("Category","Function");
-    request.put("Date", LocalDate.now().toString());
-    request.put("Scenario",scenarioDesc);
-    request.put("Branch",SDKBranch);
-    request.put("ImageName","2.2.0");
-    request.put("SDK","java");
-    request.put("MilvusMode","standalone");
-    request.put("MqMode","rocksMq");
-    request.put("TestResult",passRate==100?"pass":"fail");
-    request.put("PassRate", passRate);
-    request.put("RunningTime", costTime);
-    request.put("Link",scenarioDesc.equalsIgnoreCase("CI")?githubLink:jenkinsLink);
-    String s = HttpClientUtils.doPostJson("http://qtp-server.zilliz.cc/results/insert",request.toJSONString());
+    JsonObject request=new JsonObject();
+    request.addProperty("Product","Milvus");
+    request.addProperty("Category","Function");
+    request.addProperty("Date", LocalDate.now().toString());
+    request.addProperty("Scenario",scenarioDesc);
+    request.addProperty("Branch",SDKBranch);
+    request.addProperty("ImageName","2.2.0");
+    request.addProperty("SDK","java");
+    request.addProperty("MilvusMode","standalone");
+    request.addProperty("MqMode","rocksMq");
+    request.addProperty("TestResult",passRate==100?"pass":"fail");
+    request.addProperty("PassRate", passRate);
+    request.addProperty("RunningTime", costTime);
+    request.addProperty("Link",scenarioDesc.equalsIgnoreCase("CI")?githubLink:jenkinsLink);
+    String s = HttpClientUtils.doPostJson("http://qtp-server.zilliz.cc/results/insert",request.toString());
     logger.info("insert result:"+s);
 /*    if (iTestContext.getFailedTests().size()>0){
       throw new RuntimeException("Case Failed "+iTestContext.getFailedTests().size());

+ 2 - 2
tests/milvustestv2/src/main/java/com/zilliz/milvustestv2/utils/HttpClientUtils.java

@@ -1,7 +1,7 @@
 package com.zilliz.milvustestv2.utils;
 
 
-import com.alibaba.fastjson.JSON;
+import com.google.gson.*;
 import org.apache.commons.logging.Log;
 import org.apache.commons.logging.LogFactory;
 import org.apache.http.*;
@@ -271,7 +271,7 @@ public class HttpClientUtils {
                 }*/
                 // 模拟表单
                 //UrlEncodedFormEntity entity = new UrlEncodedFormEntity(param, "utf-8");
-                HttpEntity entity1=new StringEntity(JSON.toJSONString(param),"utf-8");
+                HttpEntity entity1=new StringEntity(new Gson().toJson(param));
                 httpPost.setEntity(entity1);
             }
             // 执行http请求

+ 2 - 2
tests/milvustestv2/src/test/java/com/zilliz/milvustestv2/alias/CreateAliasTest.java

@@ -1,6 +1,6 @@
 package com.zilliz.milvustestv2.alias;
 
-import com.alibaba.fastjson.JSONObject;
+import com.google.gson.JsonObject;
 import com.zilliz.milvustestv2.common.BaseTest;
 import com.zilliz.milvustestv2.common.CommonData;
 import com.zilliz.milvustestv2.common.CommonFunction;
@@ -32,7 +32,7 @@ public class CreateAliasTest extends BaseTest {
     public void providerCollection(){
         aliasName="a_"+ GenerateUtil.getRandomString(10);
         newCollectionName = CommonFunction.createNewCollection(CommonData.dim, null);
-        List<JSONObject> jsonObjects = CommonFunction.generateDefaultData(CommonData.numberEntities, CommonData.dim);
+        List<JsonObject> jsonObjects = CommonFunction.generateDefaultData(CommonData.numberEntities, CommonData.dim);
         milvusClientV2.insert(InsertReq.builder().collectionName(newCollectionName).data(jsonObjects).build());
         IndexParam indexParam = IndexParam.builder()
                 .fieldName(CommonData.fieldFloatVector)

+ 0 - 1
tests/milvustestv2/src/test/java/com/zilliz/milvustestv2/alias/DropAliasTest.java

@@ -1,6 +1,5 @@
 package com.zilliz.milvustestv2.alias;
 
-import com.alibaba.fastjson.JSONObject;
 import com.zilliz.milvustestv2.common.BaseTest;
 import com.zilliz.milvustestv2.common.CommonData;
 import com.zilliz.milvustestv2.common.CommonFunction;

+ 2 - 2
tests/milvustestv2/src/test/java/com/zilliz/milvustestv2/collection/GetCollectionStatsTest.java

@@ -1,6 +1,6 @@
 package com.zilliz.milvustestv2.collection;
 
-import com.alibaba.fastjson.JSONObject;
+import com.google.gson.JsonObject;
 import com.zilliz.milvustestv2.common.BaseTest;
 import com.zilliz.milvustestv2.common.CommonData;
 import com.zilliz.milvustestv2.common.CommonFunction;
@@ -25,7 +25,7 @@ public class GetCollectionStatsTest extends BaseTest {
     @BeforeClass(alwaysRun = true)
     public void providerCollection(){
         newCollectionName = CommonFunction.createNewCollection(CommonData.dim, null);
-        List<JSONObject> jsonObjects = CommonFunction.generateDefaultData(CommonData.numberEntities, CommonData.dim);
+        List<JsonObject> jsonObjects = CommonFunction.generateDefaultData(CommonData.numberEntities, CommonData.dim);
         milvusClientV2.insert(InsertReq.builder().collectionName(newCollectionName).data(jsonObjects).build());
     }
 

+ 2 - 2
tests/milvustestv2/src/test/java/com/zilliz/milvustestv2/index/CreateIndexTest.java

@@ -1,6 +1,6 @@
 package com.zilliz.milvustestv2.index;
 
-import com.alibaba.fastjson.JSONObject;
+import com.google.gson.JsonObject;
 import com.google.common.collect.Lists;
 import com.zilliz.milvustestv2.common.BaseTest;
 import com.zilliz.milvustestv2.common.CommonData;
@@ -27,7 +27,7 @@ public class CreateIndexTest extends BaseTest {
     @BeforeClass(alwaysRun = true)
     public void providerCollection(){
         newCollectionName = CommonFunction.createNewCollection(CommonData.dim, null);
-        List<JSONObject> jsonObjects = CommonFunction.generateDefaultData(CommonData.numberEntities, CommonData.dim);
+        List<JsonObject> jsonObjects = CommonFunction.generateDefaultData(CommonData.numberEntities, CommonData.dim);
         milvusClientV2.insert(InsertReq.builder().collectionName(newCollectionName).data(jsonObjects).build());
     }
 

+ 2 - 2
tests/milvustestv2/src/test/java/com/zilliz/milvustestv2/index/DescribeIndexTest.java

@@ -1,6 +1,6 @@
 package com.zilliz.milvustestv2.index;
 
-import com.alibaba.fastjson.JSONObject;
+import com.google.gson.JsonObject;
 import com.zilliz.milvustestv2.common.BaseTest;
 import com.zilliz.milvustestv2.common.CommonData;
 import com.zilliz.milvustestv2.common.CommonFunction;
@@ -27,7 +27,7 @@ public class DescribeIndexTest extends BaseTest {
     @BeforeClass(alwaysRun = true)
     public void providerCollection(){
         newCollectionName = CommonFunction.createNewCollection(CommonData.dim, null);
-        List<JSONObject> jsonObjects = CommonFunction.generateDefaultData(CommonData.numberEntities, CommonData.dim);
+        List<JsonObject> jsonObjects = CommonFunction.generateDefaultData(CommonData.numberEntities, CommonData.dim);
         milvusClientV2.insert(InsertReq.builder().collectionName(newCollectionName).data(jsonObjects).build());
         IndexParam indexParam = IndexParam.builder()
                 .fieldName(CommonData.fieldFloatVector)

+ 2 - 2
tests/milvustestv2/src/test/java/com/zilliz/milvustestv2/index/DropIndexTest.java

@@ -1,6 +1,6 @@
 package com.zilliz.milvustestv2.index;
 
-import com.alibaba.fastjson.JSONObject;
+import com.google.gson.JsonObject;
 import com.zilliz.milvustestv2.common.BaseTest;
 import com.zilliz.milvustestv2.common.CommonData;
 import com.zilliz.milvustestv2.common.CommonFunction;
@@ -25,7 +25,7 @@ public class DropIndexTest extends BaseTest {
     @BeforeClass(alwaysRun = true)
     public void providerCollection(){
         newCollectionName = CommonFunction.createNewCollection(CommonData.dim, null);
-        List<JSONObject> jsonObjects = CommonFunction.generateDefaultData(CommonData.numberEntities, CommonData.dim);
+        List<JsonObject> jsonObjects = CommonFunction.generateDefaultData(CommonData.numberEntities, CommonData.dim);
         milvusClientV2.insert(InsertReq.builder().collectionName(newCollectionName).data(jsonObjects).build());
         IndexParam indexParam = IndexParam.builder()
                 .fieldName(CommonData.fieldFloatVector)

+ 2 - 2
tests/milvustestv2/src/test/java/com/zilliz/milvustestv2/index/ListIndexesTest.java

@@ -1,6 +1,6 @@
 package com.zilliz.milvustestv2.index;
 
-import com.alibaba.fastjson.JSONObject;
+import com.google.gson.JsonObject;
 import com.zilliz.milvustestv2.common.BaseTest;
 import com.zilliz.milvustestv2.common.CommonData;
 import com.zilliz.milvustestv2.common.CommonFunction;
@@ -27,7 +27,7 @@ public class ListIndexesTest extends BaseTest {
     @BeforeClass(alwaysRun = true)
     public void providerCollection(){
         newCollectionName = CommonFunction.createNewCollection(CommonData.dim, null);
-        List<JSONObject> jsonObjects = CommonFunction.generateDefaultData(CommonData.numberEntities, CommonData.dim);
+        List<JsonObject> jsonObjects = CommonFunction.generateDefaultData(CommonData.numberEntities, CommonData.dim);
         milvusClientV2.insert(InsertReq.builder().collectionName(newCollectionName).data(jsonObjects).build());
         IndexParam indexParam = IndexParam.builder()
                 .fieldName(CommonData.fieldFloatVector)

+ 2 - 2
tests/milvustestv2/src/test/java/com/zilliz/milvustestv2/loadRelease/LoadCollectionTest.java

@@ -1,6 +1,6 @@
 package com.zilliz.milvustestv2.loadRelease;
 
-import com.alibaba.fastjson.JSONObject;
+import com.google.gson.JsonObject;
 import com.google.common.collect.Lists;
 import com.zilliz.milvustestv2.common.BaseTest;
 import com.zilliz.milvustestv2.common.CommonData;
@@ -30,7 +30,7 @@ public class LoadCollectionTest extends BaseTest {
     @BeforeClass(alwaysRun = true)
     public void providerCollection(){
         newCollectionName = CommonFunction.createNewCollection(CommonData.dim, null);
-        List<JSONObject> jsonObjects = CommonFunction.generateDefaultData(CommonData.numberEntities, CommonData.dim);
+        List<JsonObject> jsonObjects = CommonFunction.generateDefaultData(CommonData.numberEntities, CommonData.dim);
         milvusClientV2.insert(InsertReq.builder().collectionName(newCollectionName).data(jsonObjects).build());
         CommonFunction.createVectorIndex(newCollectionName,CommonData.fieldFloatVector, IndexParam.IndexType.HNSW, IndexParam.MetricType.L2);
     }

+ 2 - 2
tests/milvustestv2/src/test/java/com/zilliz/milvustestv2/loadRelease/LoadPartitionsTest.java

@@ -1,6 +1,6 @@
 package com.zilliz.milvustestv2.loadRelease;
 
-import com.alibaba.fastjson.JSONObject;
+import com.google.gson.JsonObject;
 import com.google.common.collect.Lists;
 import com.zilliz.milvustestv2.common.BaseTest;
 import com.zilliz.milvustestv2.common.CommonData;
@@ -39,7 +39,7 @@ public class LoadPartitionsTest extends BaseTest {
                 .collectionName(newCollection)
                 .partitionName(CommonData.partitionName)
                 .build());
-        List<JSONObject> jsonObjects = CommonFunction.generateDefaultData(CommonData.numberEntities, CommonData.dim);
+        List<JsonObject> jsonObjects = CommonFunction.generateDefaultData(CommonData.numberEntities, CommonData.dim);
         milvusClientV2.insert(InsertReq.builder().collectionName(newCollection).partitionName(CommonData.partitionName).data(jsonObjects).build());
         CommonFunction.createVectorIndex(newCollection,CommonData.fieldFloatVector, IndexParam.IndexType.HNSW, IndexParam.MetricType.L2);
     }

+ 2 - 2
tests/milvustestv2/src/test/java/com/zilliz/milvustestv2/loadRelease/ReleaseCollectionTest.java

@@ -1,6 +1,6 @@
 package com.zilliz.milvustestv2.loadRelease;
 
-import com.alibaba.fastjson.JSONObject;
+import com.google.gson.JsonObject;
 import com.zilliz.milvustestv2.common.BaseTest;
 import com.zilliz.milvustestv2.common.CommonData;
 import com.zilliz.milvustestv2.common.CommonFunction;
@@ -26,7 +26,7 @@ public class ReleaseCollectionTest extends BaseTest {
     @BeforeClass(alwaysRun = true)
     public void providerCollection(){
         newCollectionName = CommonFunction.createNewCollection(CommonData.dim, null);
-        List<JSONObject> jsonObjects = CommonFunction.generateDefaultData(CommonData.numberEntities, CommonData.dim);
+        List<JsonObject> jsonObjects = CommonFunction.generateDefaultData(CommonData.numberEntities, CommonData.dim);
         milvusClientV2.insert(InsertReq.builder().collectionName(newCollectionName).data(jsonObjects).build());
         CommonFunction.createVectorIndex(newCollectionName,CommonData.fieldFloatVector, IndexParam.IndexType.HNSW, IndexParam.MetricType.L2);
         milvusClientV2.loadCollection(LoadCollectionReq.builder()

+ 2 - 2
tests/milvustestv2/src/test/java/com/zilliz/milvustestv2/loadRelease/ReleasePartitionsTest.java

@@ -1,6 +1,6 @@
 package com.zilliz.milvustestv2.loadRelease;
 
-import com.alibaba.fastjson.JSONObject;
+import com.google.gson.JsonObject;
 import com.google.common.collect.Lists;
 import com.zilliz.milvustestv2.common.BaseTest;
 import com.zilliz.milvustestv2.common.CommonData;
@@ -38,7 +38,7 @@ public class ReleasePartitionsTest extends BaseTest {
                 .collectionName(newCollection)
                 .partitionName(CommonData.partitionName)
                 .build());
-        List<JSONObject> jsonObjects = CommonFunction.generateDefaultData(CommonData.numberEntities, CommonData.dim);
+        List<JsonObject> jsonObjects = CommonFunction.generateDefaultData(CommonData.numberEntities, CommonData.dim);
         milvusClientV2.insert(InsertReq.builder().collectionName(newCollection).partitionName(CommonData.partitionName).data(jsonObjects).build());
         CommonFunction.createVectorIndex(newCollection,CommonData.fieldFloatVector, IndexParam.IndexType.HNSW, IndexParam.MetricType.L2);
         milvusClientV2.loadCollection(LoadCollectionReq.builder()

+ 6 - 6
tests/milvustestv2/src/test/java/com/zilliz/milvustestv2/rbac/GrantPrivilegeTest.java

@@ -1,10 +1,10 @@
 package com.zilliz.milvustestv2.rbac;
 
-import com.alibaba.fastjson.JSONArray;
-import com.alibaba.fastjson.JSONObject;
+import com.google.gson.*;
 import com.zilliz.milvustestv2.common.BaseTest;
 import com.zilliz.milvustestv2.common.CommonData;
 import com.zilliz.milvustestv2.utils.FileUtils;
+import io.milvus.grpc.JSONArray;
 import io.milvus.grpc.PrivilegeEntity;
 import io.milvus.param.role.RevokeRolePrivilegeParam;
 import io.milvus.v2.service.rbac.request.*;
@@ -28,12 +28,12 @@ public class GrantPrivilegeTest extends BaseTest {
     public Object[][] providerPrivilegeList() {
         File jsonFile = new File("./src/test/resources/testdata/privilege.json");
         String str = FileUtils.getStr(jsonFile);
-        JSONArray jsonArray = JSONObject.parseArray(str);
+        JsonArray jsonArray = new Gson().fromJson(str, JsonArray.class);
         Object[][] objects = new Object[jsonArray.size()][3];
         for (int i = 0; i < jsonArray.size(); i++) {
-            objects[i][0] = ((JSONObject) jsonArray.get(i)).getString("object");
-            objects[i][1] = ((JSONObject) jsonArray.get(i)).getString("objectName");
-            objects[i][2] = ((JSONObject) jsonArray.get(i)).getString("privilege");
+            objects[i][0] = jsonArray.get(i).getAsJsonObject().get("object").getAsString();
+            objects[i][1] = jsonArray.get(i).getAsJsonObject().get("objectName").getAsString();
+            objects[i][2] = jsonArray.get(i).getAsJsonObject().get("privilege").getAsString();
         }
         return objects;
     }

+ 2 - 2
tests/milvustestv2/src/test/java/com/zilliz/milvustestv2/vectorOperation/GetTest.java

@@ -1,6 +1,6 @@
 package com.zilliz.milvustestv2.vectorOperation;
 
-import com.alibaba.fastjson.JSONObject;
+import com.google.gson.JsonObject;
 import com.zilliz.milvustestv2.common.BaseTest;
 import com.zilliz.milvustestv2.common.CommonData;
 import com.zilliz.milvustestv2.common.CommonFunction;
@@ -28,7 +28,7 @@ public class GetTest extends BaseTest {
     @BeforeClass(alwaysRun = true)
     public void providerCollection(){
         newCollectionName = CommonFunction.createNewCollection(CommonData.dim, null);
-        List<JSONObject> jsonObjects = CommonFunction.generateDefaultData(CommonData.numberEntities, CommonData.dim);
+        List<JsonObject> jsonObjects = CommonFunction.generateDefaultData(CommonData.numberEntities, CommonData.dim);
         milvusClientV2.insert(InsertReq.builder().collectionName(newCollectionName).data(jsonObjects).build());
         IndexParam indexParam = IndexParam.builder()
                 .fieldName(CommonData.fieldFloatVector)

+ 3 - 3
tests/milvustestv2/src/test/java/com/zilliz/milvustestv2/vectorOperation/InsertTest.java

@@ -1,6 +1,6 @@
 package com.zilliz.milvustestv2.vectorOperation;
 
-import com.alibaba.fastjson.JSONObject;
+import com.google.gson.JsonObject;
 import com.zilliz.milvustestv2.common.BaseTest;
 import com.zilliz.milvustestv2.common.CommonData;
 import com.zilliz.milvustestv2.common.CommonFunction;
@@ -35,7 +35,7 @@ public class InsertTest extends BaseTest {
 
     @Test(description = "insert test",groups = {"Smoke"})
     public void insert(){
-        List<JSONObject> jsonObjects = CommonFunction.generateDefaultData(CommonData.numberEntities, CommonData.dim);
+        List<JsonObject> jsonObjects = CommonFunction.generateDefaultData(CommonData.numberEntities, CommonData.dim);
         InsertResp insert = milvusClientV2.insert(InsertReq.builder()
                 .data(jsonObjects)
                 .collectionName(newCollectionName)
@@ -45,7 +45,7 @@ public class InsertTest extends BaseTest {
 
     @Test(description = "insert simple collection test",groups = {"Smoke"})
     public void insertIntoSimpleCollection(){
-        List<JSONObject> jsonObjects = CommonFunction.generateSimpleData(CommonData.numberEntities, CommonData.dim);
+        List<JsonObject> jsonObjects = CommonFunction.generateSimpleData(CommonData.numberEntities, CommonData.dim);
         InsertResp insert = milvusClientV2.insert(InsertReq.builder()
                 .data(jsonObjects)
                 .collectionName(simpleCollectionName)

+ 5 - 5
tests/milvustestv2/src/test/java/com/zilliz/milvustestv2/vectorOperation/UpsertTest.java

@@ -1,6 +1,6 @@
 package com.zilliz.milvustestv2.vectorOperation;
 
-import com.alibaba.fastjson.JSONObject;
+import com.google.gson.JsonObject;
 import com.zilliz.milvustestv2.common.BaseTest;
 import com.zilliz.milvustestv2.common.CommonData;
 import com.zilliz.milvustestv2.common.CommonFunction;
@@ -24,7 +24,7 @@ public class UpsertTest extends BaseTest {
     @BeforeClass(alwaysRun = true)
     public void providerCollection(){
         newCollectionName = CommonFunction.createNewCollection(CommonData.dim, null);
-        List<JSONObject> jsonObjects = CommonFunction.generateDefaultData(CommonData.numberEntities, CommonData.dim);
+        List<JsonObject> jsonObjects = CommonFunction.generateDefaultData(CommonData.numberEntities, CommonData.dim);
         milvusClientV2.insert(InsertReq.builder().collectionName(newCollectionName).data(jsonObjects).build());
     }
 
@@ -35,7 +35,7 @@ public class UpsertTest extends BaseTest {
 
     @Test(description = "upsert collection",groups = {"Smoke"})
     public void upsert(){
-        List<JSONObject> jsonObjects = CommonFunction.generateDefaultData(10, CommonData.dim);
+        List<JsonObject> jsonObjects = CommonFunction.generateDefaultData(10, CommonData.dim);
         UpsertResp upsert = milvusClientV2.upsert(UpsertReq.builder()
                 .collectionName(newCollectionName)
                 .data(jsonObjects)
@@ -47,9 +47,9 @@ public class UpsertTest extends BaseTest {
     @Test(description = "upsert collection",groups = {"Smoke"})
     public void simpleUpsert(){
         String collection=CommonFunction.createSimpleCollection(128,null);
-        List<JSONObject> jsonObjects = CommonFunction.generateSimpleData(CommonData.numberEntities, CommonData.dim);
+        List<JsonObject> jsonObjects = CommonFunction.generateSimpleData(CommonData.numberEntities, CommonData.dim);
         milvusClientV2.insert(InsertReq.builder().collectionName(collection).data(jsonObjects).build());
-        List<JSONObject> jsonObjectsNew = CommonFunction.generateSimpleData(10, CommonData.dim);
+        List<JsonObject> jsonObjectsNew = CommonFunction.generateSimpleData(10, CommonData.dim);
         UpsertResp upsert = milvusClientV2.upsert(UpsertReq.builder()
                 .collectionName(collection)
                 .data(jsonObjectsNew)