From b6ac530c0d8c51886a7aa505ffd228f09099390d Mon Sep 17 00:00:00 2001 From: Jens Klingenberg Date: Sun, 8 Sep 2024 20:12:15 +0200 Subject: [PATCH] Refactoring --- .../ktorfit/model/ClassData.kt | 26 +++++--------- .../ktorfit/model/FunctionData.kt | 36 +++++++++++++++---- .../AttributeCodeGenerator.kt | 4 +-- .../FieldCodeGeneration.kt | 6 ++-- .../ktorfit/TagAnnotationsTest.kt | 4 +-- .../com/example/api/JsonPlaceHolderApi.kt | 3 +- 6 files changed, 48 insertions(+), 31 deletions(-) diff --git a/ktorfit-ksp/src/main/kotlin/de/jensklingenberg/ktorfit/model/ClassData.kt b/ktorfit-ksp/src/main/kotlin/de/jensklingenberg/ktorfit/model/ClassData.kt index 56245b693..1d0a939b5 100644 --- a/ktorfit-ksp/src/main/kotlin/de/jensklingenberg/ktorfit/model/ClassData.kt +++ b/ktorfit-ksp/src/main/kotlin/de/jensklingenberg/ktorfit/model/ClassData.kt @@ -13,6 +13,7 @@ import com.squareup.kotlinpoet.KModifier import com.squareup.kotlinpoet.ksp.toKModifier import com.squareup.kotlinpoet.ksp.toTypeName import de.jensklingenberg.ktorfit.model.annotations.FormUrlEncoded +import de.jensklingenberg.ktorfit.model.annotations.Headers import de.jensklingenberg.ktorfit.model.annotations.Multipart import de.jensklingenberg.ktorfit.model.annotations.ParameterAnnotation import de.jensklingenberg.ktorfit.model.annotations.ParameterAnnotation.Field @@ -48,7 +49,6 @@ fun KSClassDeclaration.toClassData(logger: KSPLogger): ClassData { mutableSetOf( "io.ktor.util.reflect.typeInfo", "io.ktor.client.request.HttpRequestBuilder", - "io.ktor.client.request.headers", "io.ktor.client.request.parameter", "io.ktor.http.URLBuilder", "io.ktor.http.HttpMethod", @@ -63,25 +63,17 @@ fun KSClassDeclaration.toClassData(logger: KSPLogger): ClassData { checkClassForErrors(this, logger) val functionDataList: List = - ksClassDeclaration.getDeclaredFunctions().toList().map { funcDeclaration -> - return@map funcDeclaration.toFunctionData(logger) - } - - functionDataList.forEach { - it.parameterDataList.forEach { - if (it.hasAnnotation()) { - imports.add("io.ktor.client.request.setBody") - } - - if (it.findAnnotationOrNull()?.encoded == false) { - imports.add("io.ktor.http.encodeURLPath") + ksClassDeclaration + .getDeclaredFunctions() + .toList() + .map { funcDeclaration -> + return@map funcDeclaration.toFunctionData(logger, addImport = { imports.add(it) }) } - if (it.hasAnnotation()) { - imports.add("kotlin.reflect.cast") - } + functionDataList.forEach { + if (it.annotations.any { it is Headers || it is FormUrlEncoded }) { + imports.add("io.ktor.client.request.headers") } - if (it.annotations.any { it is FormUrlEncoded || it is Multipart } || it.parameterDataList.any { param -> param.hasAnnotation() || param.hasAnnotation() } ) { diff --git a/ktorfit-ksp/src/main/kotlin/de/jensklingenberg/ktorfit/model/FunctionData.kt b/ktorfit-ksp/src/main/kotlin/de/jensklingenberg/ktorfit/model/FunctionData.kt index be498a2d3..8177f1bac 100644 --- a/ktorfit-ksp/src/main/kotlin/de/jensklingenberg/ktorfit/model/FunctionData.kt +++ b/ktorfit-ksp/src/main/kotlin/de/jensklingenberg/ktorfit/model/FunctionData.kt @@ -9,12 +9,7 @@ import de.jensklingenberg.ktorfit.model.annotations.FunctionAnnotation import de.jensklingenberg.ktorfit.model.annotations.HttpMethod import de.jensklingenberg.ktorfit.model.annotations.HttpMethodAnnotation import de.jensklingenberg.ktorfit.model.annotations.Multipart -import de.jensklingenberg.ktorfit.model.annotations.ParameterAnnotation.Body -import de.jensklingenberg.ktorfit.model.annotations.ParameterAnnotation.Field -import de.jensklingenberg.ktorfit.model.annotations.ParameterAnnotation.FieldMap -import de.jensklingenberg.ktorfit.model.annotations.ParameterAnnotation.Path -import de.jensklingenberg.ktorfit.model.annotations.ParameterAnnotation.Url -import de.jensklingenberg.ktorfit.model.annotations.ParameterAnnotation.RequestBuilder +import de.jensklingenberg.ktorfit.model.annotations.ParameterAnnotation.* import de.jensklingenberg.ktorfit.poetspec.findTypeName import de.jensklingenberg.ktorfit.utils.anyInstance import de.jensklingenberg.ktorfit.utils.getFormUrlEncodedAnnotation @@ -53,7 +48,10 @@ private fun getHttpMethodAnnotations(ksFunctionDeclaration: KSFunctionDeclaratio return listOfNotNull(getAnno, postAnno, putAnno, deleteAnno, headAnno, optionsAnno, patchAnno, httpAnno) } -fun KSFunctionDeclaration.toFunctionData(logger: KSPLogger): FunctionData { +fun KSFunctionDeclaration.toFunctionData( + logger: KSPLogger, + addImport: (String) -> Unit +): FunctionData { val funcDeclaration = this val functionName = funcDeclaration.simpleName.asString() val functionParameters = funcDeclaration.parameters.map { it.createParameterData(logger) } @@ -68,6 +66,30 @@ fun KSFunctionDeclaration.toFunctionData(logger: KSPLogger): FunctionData { typeName = findTypeName(resolvedReturnType, funcDeclaration.containingFile!!.filePath), ) + functionParameters.forEach { parameterData -> + parameterData.annotations.forEach { + if (it is Header || it is HeaderMap) { + addImport("io.ktor.client.request.headers") + } + + if (it is Tag) { + addImport("io.ktor.util.AttributeKey") + } + + if (it is Body) { + addImport("io.ktor.client.request.setBody") + } + + if (it is Path && !it.encoded) { + addImport("io.ktor.http.encodeURLPath") + } + + if (it is RequestType) { + addImport("kotlin.reflect.cast") + } + } + } + val functionAnnotationList = mutableListOf() funcDeclaration.getMultipartAnnotation()?.let { diff --git a/ktorfit-ksp/src/main/kotlin/de/jensklingenberg/ktorfit/reqBuilderExtension/AttributeCodeGenerator.kt b/ktorfit-ksp/src/main/kotlin/de/jensklingenberg/ktorfit/reqBuilderExtension/AttributeCodeGenerator.kt index 8688358ee..3b646973a 100644 --- a/ktorfit-ksp/src/main/kotlin/de/jensklingenberg/ktorfit/reqBuilderExtension/AttributeCodeGenerator.kt +++ b/ktorfit-ksp/src/main/kotlin/de/jensklingenberg/ktorfit/reqBuilderExtension/AttributeCodeGenerator.kt @@ -11,8 +11,8 @@ fun getAttributeCode(parameterDataList: List): String = it.findAnnotationOrNull() ?: throw IllegalStateException("Tag annotation not found") if (it.type.parameterType.isMarkedNullable) { - "${it.name}?.let{ attributes.put(io.ktor.util.AttributeKey(\"${tag.value}\"), it) }" + "${it.name}?.let{ attributes.put(AttributeKey(\"${tag.value}\"), it) }" } else { - "attributes.put(io.ktor.util.AttributeKey(\"${tag.value}\"), ${it.name})" + "attributes.put(AttributeKey(\"${tag.value}\"), ${it.name})" } } diff --git a/ktorfit-ksp/src/main/kotlin/de/jensklingenberg/ktorfit/reqBuilderExtension/FieldCodeGeneration.kt b/ktorfit-ksp/src/main/kotlin/de/jensklingenberg/ktorfit/reqBuilderExtension/FieldCodeGeneration.kt index cdda9cba5..648034eb6 100644 --- a/ktorfit-ksp/src/main/kotlin/de/jensklingenberg/ktorfit/reqBuilderExtension/FieldCodeGeneration.kt +++ b/ktorfit-ksp/src/main/kotlin/de/jensklingenberg/ktorfit/reqBuilderExtension/FieldCodeGeneration.kt @@ -14,7 +14,9 @@ fun getFieldArgumentsText( ): String { val fieldText = params.filter { it.hasAnnotation() }.joinToString("") { parameterData -> - val field = parameterData.annotations.filterIsInstance().first() + val field = + parameterData.annotations.filterIsInstance().firstOrNull() + ?: throw IllegalStateException("Field annotation not found") val encoded = field.encoded val paramName = parameterData.name val fieldValue = field.value @@ -56,7 +58,7 @@ fun getFieldArgumentsText( val fieldMapStrings = params.filter { it.hasAnnotation() }.joinToString("") { parameterData -> - val fieldMap = parameterData.findAnnotationOrNull()!! + val fieldMap = parameterData.findAnnotationOrNull() ?: throw IllegalStateException("FieldMap annotation not found") val encoded = fieldMap.encoded val data = parameterData.name diff --git a/ktorfit-ksp/src/test/kotlin/de/jensklingenberg/ktorfit/TagAnnotationsTest.kt b/ktorfit-ksp/src/test/kotlin/de/jensklingenberg/ktorfit/TagAnnotationsTest.kt index 558877014..e6be1f60b 100644 --- a/ktorfit-ksp/src/test/kotlin/de/jensklingenberg/ktorfit/TagAnnotationsTest.kt +++ b/ktorfit-ksp/src/test/kotlin/de/jensklingenberg/ktorfit/TagAnnotationsTest.kt @@ -27,8 +27,8 @@ interface TestService { ) val expectedHeadersArgumentText = - """attributes.put(io.ktor.util.AttributeKey("myTag1"), myTag1) - someParameter?.let{ attributes.put(io.ktor.util.AttributeKey("myTag2"), it) } """ + """attributes.put(AttributeKey("myTag1"), myTag1) + someParameter?.let{ attributes.put(AttributeKey("myTag2"), it) } """ val compilation = getCompilation(listOf(source)) val result = compilation.compile() diff --git a/sandbox/src/commonMain/kotlin/com/example/api/JsonPlaceHolderApi.kt b/sandbox/src/commonMain/kotlin/com/example/api/JsonPlaceHolderApi.kt index 0e5aa7391..c1a13a35a 100644 --- a/sandbox/src/commonMain/kotlin/com/example/api/JsonPlaceHolderApi.kt +++ b/sandbox/src/commonMain/kotlin/com/example/api/JsonPlaceHolderApi.kt @@ -35,7 +35,8 @@ interface JsonPlaceHolderApi { @GET("posts/{postId}") suspend fun getPostById( - @Path postId: Int = 4 + @Path postId: Int = 4, + @Tag value: String = "test" ): Post @GET("posts/{postId}/comments")