我可以创建自定义json字符串与示例化的数据类在java中

idfiyjo8  于 2023-02-14  发布在  Java
关注(0)|答案(1)|浏览(120)

有一个类定义如下:

@Data // lombok
public class MyData {
    @Required // my custom annotation
    String testValue1;
    Integer testValue2;
}

myData是这样示例化的:

MyData myData = new MyData();
myData.setTestValue1("test1");
myData.setTestValue2(123);

我想将myData序列化为json字符串,如下所示:

{
    "testValue1": {
        "type": "String",
        "isRequired": "true",
        "value": "test1"
    },
    "testValue2": {
        "type": "Integer",
        "isRequired": "false",
        "value": "123"
    },
}

有没有好的方法来创建json字符串?
编辑|
我把json字符串的引号,以便能够有效。
我想将键设置为字段名称并创建附加字段信息。在“type”键上设置字段类型,如果字段具有@Required注解,则在“isRequired”上设置true,并在“value”上设置示例化字段值。

fxnxkyjh

fxnxkyjh1#

因此,我对Jackson序列化进行了一些研究,并得出了以下结果(当然未完成,也未完全测试,但可用于给定的对象):
使Spring /Jackson知道新串行器的模块。

@JsonComponent
public class TestSerializerModule extends SimpleModule {

    @Override
    public String getModuleName() {
        return TestSerializerModule.class.getSimpleName();
    }

    @Override
    public Version version() {
        return new Version(
                1,
                0,
                0,
                "",
                TestSerializerModule.class.getPackage().getName(),
                "TestModule"
        );
    }

    @Override
    public void setupModule(SetupContext context) {
        context.addBeanSerializerModifier(new BeanSerializerModifier() {

            @Override
            public JsonSerializer<?> modifySerializer(SerializationConfig config, BeanDescription beanDesc, JsonSerializer<?> serializer) {

                if (beanDesc.getBeanClass().equals(MyData.class)) { //Add some smart logic here to identify your objects
                    return new TestSerializer();
                }

                return serializer;
            }
        });
    }
}

然后序列化器本身:

public class TestSerializer extends StdSerializer<Object> {

    protected TestSerializer() {
        super(Object.class);
    }

    @Override
    public void serialize(Object value, JsonGenerator gen, SerializerProvider provider) throws IOException {
        ClassIntrospector classIntrospector = provider.getConfig().getClassIntrospector();
        BasicBeanDescription beanDescription = (BasicBeanDescription) classIntrospector.forSerialization(provider.getConfig(), provider.constructType(value.getClass()), null);

        // Start of the MyValue Object
        gen.writeStartObject();
        beanDescription.findProperties().forEach(p -> {

                    // Requiered if Annoation is present
                    boolean required = p.getField().hasAnnotation(Required.class);

                    try {

                        // Write all the wanted fields
                        gen.writeFieldName(p.getName());
                        gen.writeStartObject();
                        gen.writeBooleanField("isRequired", required);
                        gen.writeStringField("type", p.getField().getRawType().getSimpleName());
                        gen.writeFieldName("value");

                        Object value1 = p.getGetter().getValue(value);
                        
                        // Use existing serializer for the value    provider.findValueSerializer(value1.getClass()).serialize(value1, gen, provider);
                        gen.writeEndObject();

                    } catch (IOException e) {
                        throw new RuntimeException(e);
                    }
                }

        );
        gen.writeEndObject();

    }
}

运行此测试:

@JsonTest
class TestSerializerTest {

    @Autowired
    ObjectMapper objectMapper;

    @Test
    public void testSerializer() throws Exception {

        MyData value = new MyData();
        value.setTestValue1("test1");
        value.setTestValue2(123);

        String s = objectMapper.writeValueAsString(value);

        System.out.println(s);

    }

}

输出如下:

{"testValue1":{"isRequired":false,"type":"String","value":"test1"},"testValue2":{"isRequired":false,"type":"Integer","value":123}}

希望这能给你一个从哪里开始以及如何从这里着手的想法!

相关问题