@Test
  public void testComplicatedDtoDeserializer() throws Exception {
    final String fooString = "Something";
    final int fooId = 1;
    final String _default = "test_default_keyword";

    JsonArray jsonArray = new JsonArray();
    jsonArray.add(new JsonPrimitive(fooString));

    JsonObject simpleDtoJsonObject = new JsonObject();
    simpleDtoJsonObject.add("name", new JsonPrimitive(fooString));
    simpleDtoJsonObject.add("id", new JsonPrimitive(fooId));
    simpleDtoJsonObject.add("default", new JsonPrimitive(_default));

    JsonObject jsonMap = new JsonObject();
    jsonMap.add(fooString, simpleDtoJsonObject);

    JsonArray simpleDtosArray = new JsonArray();
    simpleDtosArray.add(simpleDtoJsonObject);

    JsonArray arrayOfEnum = new JsonArray();
    arrayOfEnum.add(new JsonPrimitive(ComplicatedDto.SimpleEnum.ONE.name()));
    arrayOfEnum.add(new JsonPrimitive(ComplicatedDto.SimpleEnum.TWO.name()));
    arrayOfEnum.add(new JsonPrimitive(ComplicatedDto.SimpleEnum.THREE.name()));
    JsonArray arrayOfArrayEnum = new JsonArray();
    arrayOfArrayEnum.add(arrayOfEnum);

    JsonObject complicatedDtoJsonObject = new JsonObject();
    complicatedDtoJsonObject.add("strings", jsonArray);
    complicatedDtoJsonObject.add(
        "simpleEnum", new JsonPrimitive(ComplicatedDto.SimpleEnum.ONE.name()));
    complicatedDtoJsonObject.add("map", jsonMap);
    complicatedDtoJsonObject.add("simpleDtos", simpleDtosArray);
    complicatedDtoJsonObject.add("arrayOfArrayOfEnum", arrayOfArrayEnum);

    ComplicatedDto complicatedDto =
        dtoFactory.createDtoFromJson(complicatedDtoJsonObject.toString(), ComplicatedDto.class);

    assertEquals(complicatedDto.getStrings().get(0), fooString);
    assertEquals(complicatedDto.getSimpleEnum(), ComplicatedDto.SimpleEnum.ONE);
    checkSimpleDto(complicatedDto.getMap().get(fooString), fooString, fooId, _default);
    checkSimpleDto(complicatedDto.getSimpleDtos().get(0), fooString, fooId, _default);
    assertEquals(
        complicatedDto.getArrayOfArrayOfEnum().get(0).get(0), ComplicatedDto.SimpleEnum.ONE);
    assertEquals(
        complicatedDto.getArrayOfArrayOfEnum().get(0).get(1), ComplicatedDto.SimpleEnum.TWO);
    assertEquals(
        complicatedDto.getArrayOfArrayOfEnum().get(0).get(2), ComplicatedDto.SimpleEnum.THREE);
  }
  @Test
  public void testComplicatedDtoSerializer() throws Exception {
    final String fooString = "Something";
    final int fooId = 1;
    final String _default = "test_default_keyword";

    List<String> listStrings = new ArrayList<>(2);
    listStrings.add("Something 1");
    listStrings.add("Something 2");

    ComplicatedDto.SimpleEnum simpleEnum = ComplicatedDto.SimpleEnum.ONE;

    // Assume that SimpleDto works. Use it to test nested objects
    SimpleDto simpleDto =
        dtoFactory
            .createDto(SimpleDto.class)
            .withName(fooString)
            .withId(fooId)
            .withDefault(_default);

    Map<String, SimpleDto> mapDtos = new HashMap<>(1);
    mapDtos.put(fooString, simpleDto);

    List<SimpleDto> listDtos = new ArrayList<>(1);
    listDtos.add(simpleDto);

    List<List<ComplicatedDto.SimpleEnum>> listOfListOfEnum = new ArrayList<>(1);
    List<ComplicatedDto.SimpleEnum> listOfEnum = new ArrayList<>(3);
    listOfEnum.add(ComplicatedDto.SimpleEnum.ONE);
    listOfEnum.add(ComplicatedDto.SimpleEnum.TWO);
    listOfEnum.add(ComplicatedDto.SimpleEnum.THREE);
    listOfListOfEnum.add(listOfEnum);

    ComplicatedDto dto =
        dtoFactory
            .createDto(ComplicatedDto.class)
            .withStrings(listStrings)
            .withSimpleEnum(simpleEnum)
            .withMap(mapDtos)
            .withSimpleDtos(listDtos)
            .withArrayOfArrayOfEnum(listOfListOfEnum);

    final String json = dtoFactory.toJson(dto);
    JsonObject jsonObject = new JsonParser().parse(json).getAsJsonObject();

    Assert.assertTrue(jsonObject.has("strings"));
    JsonArray jsonArray = jsonObject.get("strings").getAsJsonArray();
    assertEquals(jsonArray.get(0).getAsString(), listStrings.get(0));
    assertEquals(jsonArray.get(1).getAsString(), listStrings.get(1));

    Assert.assertTrue(jsonObject.has("simpleEnum"));
    assertEquals(jsonObject.get("simpleEnum").getAsString(), simpleEnum.name());

    Assert.assertTrue(jsonObject.has("map"));
    JsonObject jsonMap = jsonObject.get("map").getAsJsonObject();
    JsonObject value = jsonMap.get(fooString).getAsJsonObject();
    assertEquals(value.get("name").getAsString(), fooString);
    assertEquals(value.get("id").getAsInt(), fooId);
    assertEquals(value.get("default").getAsString(), _default);

    Assert.assertTrue(jsonObject.has("simpleDtos"));
    JsonArray simpleDtos = jsonObject.get("simpleDtos").getAsJsonArray();
    JsonObject simpleDtoJsonObject = simpleDtos.get(0).getAsJsonObject();
    assertEquals(simpleDtoJsonObject.get("name").getAsString(), fooString);
    assertEquals(simpleDtoJsonObject.get("id").getAsInt(), fooId);
    assertEquals(simpleDtoJsonObject.get("default").getAsString(), _default);

    Assert.assertTrue(jsonObject.has("arrayOfArrayOfEnum"));
    JsonArray arrayOfArrayOfEnum =
        jsonObject.get("arrayOfArrayOfEnum").getAsJsonArray().get(0).getAsJsonArray();
    assertEquals(arrayOfArrayOfEnum.get(0).getAsString(), ComplicatedDto.SimpleEnum.ONE.name());
    assertEquals(arrayOfArrayOfEnum.get(1).getAsString(), ComplicatedDto.SimpleEnum.TWO.name());
    assertEquals(arrayOfArrayOfEnum.get(2).getAsString(), ComplicatedDto.SimpleEnum.THREE.name());
  }