-
Notifications
You must be signed in to change notification settings - Fork 33
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
Allow specifying format of parameter in request #168
Comments
I am using a custom processor and would also love the ability to set the "format".
i am pretty new to the library, but it feels ergonomic to be able to set the format through the custom processor override. |
@ddenchev I was using a custom processor as well, but there was a deprecation somewhere in there. Did you hit it too? If you did, how did you proceed? For now, I am using type redirection so I need formatting to get help from Swagger schemas {
generator = { type ->
type
.collectJacksonSubTypes({ it.processReflection() })
.processReflection {
redirect<OffsetDateTime, String>()
redirect<UUID, String>()
}
}
} |
@king-phyte
As I said, I am new to the library so not sure about all the customization options and what rough edges are me not knowing about it. The generated schema looks like this:
|
@ddenchev Thank you for sharing that. It looks like we have hit the same wall. |
@SMILEY4 Can you please take a look at this? |
Hi @king-phyte, @ddenchev, I'm sorry for the confusion, i'm still trying to figure out how to make this simpler or document it better :) For a bit of context: Generating a schema for a kotlin type happens (very rougly) in two independent steps:
The general idea for the uuids here would be:
Assuming this model with the uuid field and the UUIDSerializer: @Serializable
class Id(
@Serializable(with = UUIDSerializer::class)
val id: UUID, // no need for @Format("uuid") here. This can just be handled in the custom processor that is required anyway here.
)
object UUIDSerializer : KSerializer<UUID> {
override val descriptor = PrimitiveSerialDescriptor("UUID", PrimitiveKind.STRING)
override fun deserialize(decoder: Decoder): UUID {
return UUID.fromString(decoder.decodeString())
}
override fun serialize(encoder: Encoder, value: UUID) {
encoder.encodeString(value.toString())
}
} When using reflection, the schema generator config could look something like this (sticking close the the default plugin config here): install(SwaggerUI) {
schemas {
generator = { type ->
type
.collectSubTypes()
.processReflection {
// add a custom processor for type "UUID"
customProcessor<UUID> {
PrimitiveTypeData(
// needs a (unique) id for our type, overwriting UUID so taking that
id = TypeId.build(UUID::class.qualifiedName!!),
// qualified name must be the one of "String".
// The generator currently looks at the qualified name to
// determine the type of the swagger schema :/
qualifiedName = String::class.qualifiedName!!,
// simple name can be anything.
// Using uuid here since this will become
// the "title" in the swagger schema.
simpleName = UUID::class.simpleName!!,
annotations = mutableListOf(AnnotationData(
// adding the @Format annotation to our custom type here.
// This way it does not need to be added on every field in the models.
name = Format::class.qualifiedName!!,
values = mutableMapOf("format" to "uuid") // with value "uuid"
))
)
}
}
.connectSubTypes()
.handleNameAnnotation()
.generateSwaggerSchema()
// @Format annotations will be handled in this step and is set in the swagger schema
.handleCoreAnnotations()
.withTitle(TitleType.SIMPLE)
.compileReferencingRoot()
}
}
} For kotlinx it's (almost) the same: install(SwaggerUI) {
schemas {
generator = { type ->
type
.processKotlinxSerialization {
// register the custom processor the name matching the
// one defined in the custom KSerializer here:
// PrimitiveSerialDescriptor("UUID", PrimitiveKind.STRING)
customProcessor("UUID") {
PrimitiveTypeData(
id = TypeId.build(UUID::class.qualifiedName!!),
qualifiedName = String::class.qualifiedName!!,
simpleName = UUID::class.simpleName!!,
annotations = mutableListOf(AnnotationData(
name = Format::class.qualifiedName!!,
values = mutableMapOf("format" to "uuid")
))
)
}
}
.generateSwaggerSchema()
// set "format" in swagger schema according to @Format annotation
.handleCoreAnnotations()
.withTitle(SIMPLE)
.compileReferencingRoot()
}
}
} I hope this helps and clears up some of the confusion. If you have any open questions, please feel free to ask. |
@SMILEY4 Thank you for the response. It indeed works if I proceed with it like you described above. I was using custom processors by following the docs/examples, but as I said in my comment above, I hit some deprecation warnings so I gave up and switched to redirection. Also, please evaluate the attached pull request, and decide if it is necessary or not (maybe for one-off moments of wanting to specify format), since the method you described here works fine if we always want to override the type. Thank you once again! |
I updated the ktor-swagger-ui and schema-kenerator wiki and replaced mentions of the deprecated
I don't think we need it since we have the custom processor that is required for larger modifications and the |
I don't remember which one exactly I encountered, but it was somewhere inside the PrimitiveTypeData
Alright then. You wouldn't mind if I closed this issue (and the PR), yes? |
thanks, i'll have another look. From my side this issue and the pr can be closed 👍 |
Alright. Thank you yet once more for everything! |
@SMILEY4 whilst I have you here, if you don't mind me asking, do you have plans of adding support for ReDoc? |
not until now, though i quickly looked into it and it seems quite simple to implement. |
Believe me when I say I have thought about that a lot 😅. But I figured having the functionalty first then worry about the naming later is a better approach I considered forking the repo and maintaining a separate package for redoc, but I thought that would be a bit overboard, considering ReDoc consumes OpenAPI almost the same way as Swagger UI does and this package already does 99% of that work What we need may be adding install(SwaggerUI){
redoc {...}
} and routing {
route("docs/redoc") {
redoc("/openapi.json")
}
} |
Hello. First of all, thank you for the excellent work you put into this well thought out and executed package.
I am using ktor-swagger-ui:4.1.2. I want a way to specify the format of a path parameter in the request section of the route documentation. See the sample below:
This generates the following (some fields are removed for brevity)
If you need any additional information, let me know and I will do my best to provide it. Thank you.
The text was updated successfully, but these errors were encountered: