OpenApi gradle serialize/deserialize multiple datetime formats
Asked Answered
S

1

0

I would like to know is there a way to make the OpenApi generated classes to show their proper date and time format. I read a few topics on this and none of them help. Here is a sample of the build.gradle:

configOptions.set([
                dateLibrary : "java8",
        ])
        library.set("jersey2")
        typeMappings.set([
                ZonedDateTime: ZonedDateTime,
                LocalDateTime: LocalDateTime,
        ])
        importMappings.set([
                ZonedDateTime: "java.time.ZonedDateTime",
                LocalDateTime: "java.time.LocalDateTime",
        ])

The thing is, this will generate all datetime formats in OffsetDateTime. I did this in typeMappings: OffsetDateTime: "java.time.ZonedDateTime". This forced everything to be generated in ZonedDateTime. Is there a way to have multiple date and time formats? I want to have ZonedDateTime, LocalDateTime and etc. Also tried to set the dateLibrary: "custom" and to create the mappings my self, didn't work as well.

Skip answered 21/4, 2023 at 11:50 Comment(0)
T
0

This can be done by defining your own format. Let's say we have the following schema

components:
  schemas:
    myDate:
      type: object
      properties:
        ZonedDateTime:
          type: string
          format: date-time
        LocalDateTime:
          type: string
          format: date-time
        OffsetDateTime:
          type: string
          format: date-time
        Instant:
          type: string
          format: date-time

The generator will generate every one of these as an OffsetDateTime. You're on the right track when you changed your typeMappings. However, as you noticed, this is a global change.

According to the swagger documentation:

format is an open value, so you can use any formats, even not those defined by the OpenAPI Specification

So, the best way to fix this would be to change the above schema to use custom format values like this:

myDate:
  type: object
  properties:
    ZonedDateTime:
      type: string
      format: zoned
    LocalDateTime:
      type: string
      format: local
    OffsetDateTime:
      type: string
      format: date-time # Nothing needed here.  This is already handled by the generator
    Instant:
      type: string
      format: instant

Now you can change your typeMappings and importMappings as follows

    typeMappings = [
            string+instant: "Instant",
            string+zoned: "ZonedDateTime",
            string+local: "LocalDateTime"
    ]
    importMappings = [
            LocalDateTime: "java.time.OffsetDateTime",
            ZonedDateTime: "java.time.ZonedDateTime",
            Instant: "java.time.Instant"
    ]

This should get you what you need.

Ton answered 21/4, 2023 at 16:17 Comment(2)
Is there any other way than defining my own format? Currently the project just scans the folders in src/main/java and generates the classes.Skip
There are a number of other options you could try, but none of them are as good as this. You could create your own generator using the openApiMeta task, you could stick with the default OffsetDateTime and convert the time to whichever other Temporal you need, or you could create a custom deserializer.Ton

© 2022 - 2024 — McMap. All rights reserved.