Skip to content

Commit 59d096b

Browse files
committed
support multiple interfaces (#247)
1 parent dac1c01 commit 59d096b

File tree

7 files changed

+65
-14
lines changed

7 files changed

+65
-14
lines changed

openapi-processor-core/src/main/kotlin/io/openapiprocessor/core/model/datatypes/AllOfObjectDataType.kt

Lines changed: 7 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -14,7 +14,9 @@ class AllOfObjectDataType(
1414
private val items: List<DataType> = emptyList(),
1515
override val deprecated: Boolean = false
1616
): ModelDataType {
17-
override var implementsDataType: InterfaceDataType? = null
17+
private val _implementsDataTypes: MutableCollection<InterfaceDataType> = mutableListOf()
18+
override val implementsDataTypes: Collection<InterfaceDataType>
19+
get() = _implementsDataTypes.toList()
1820

1921
override fun getName(): String {
2022
return name.id
@@ -55,6 +57,10 @@ class AllOfObjectDataType(
5557
return constraints?.isRequired(prop) ?: false
5658
}
5759

60+
override fun addInterface(implement: InterfaceDataType) {
61+
_implementsDataTypes.add(implement)
62+
}
63+
5864
override fun forEach(action: (property: String, dataType: DataType) -> Unit) {
5965
properties.forEach {
6066
action(it.key, it.value)

openapi-processor-core/src/main/kotlin/io/openapiprocessor/core/model/datatypes/ModelDataType.kt

Lines changed: 3 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -7,9 +7,9 @@ package io.openapiprocessor.core.model.datatypes
77

88
interface ModelDataType: DataType {
99
/**
10-
* implements this interface.
10+
* implements interfaces.
1111
*/
12-
var implementsDataType: InterfaceDataType?
12+
val implementsDataTypes: Collection<InterfaceDataType>
1313

1414
/**
1515
* loop object properties.
@@ -18,4 +18,5 @@ interface ModelDataType: DataType {
1818

1919
fun isRequired(prop: String): Boolean
2020

21+
fun addInterface(implement: InterfaceDataType)
2122
}

openapi-processor-core/src/main/kotlin/io/openapiprocessor/core/model/datatypes/ObjectDataType.kt

Lines changed: 11 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -19,7 +19,9 @@ open class ObjectDataType(
1919
override val deprecated: Boolean = false,
2020
override val documentation: Documentation? = null
2121
): ModelDataType {
22-
override var implementsDataType: InterfaceDataType? = null
22+
private val _implementsDataTypes: MutableCollection<InterfaceDataType> = mutableListOf()
23+
override val implementsDataTypes: Collection<InterfaceDataType>
24+
get() = _implementsDataTypes.toList()
2325

2426
override fun getName(): String {
2527
return name.id
@@ -58,6 +60,10 @@ open class ObjectDataType(
5860
return constraints?.isRequired(prop) ?: false
5961
}
6062

63+
override fun addInterface(implement: InterfaceDataType) {
64+
_implementsDataTypes.add(implement)
65+
}
66+
6167
override fun forEach(action: (property: String, dataType: DataType) -> Unit) {
6268
for (p in properties) action(p.key, p.value)
6369
}
@@ -72,6 +78,9 @@ open class ObjectDataType(
7278

7379
private val implementsImports: Set<String>
7480
get() {
75-
return implementsDataType?.getImports() ?: emptySet()
81+
return implementsDataTypes
82+
.map { it.getImports() }
83+
.flatten()
84+
.toSet()
7685
}
7786
}

openapi-processor-core/src/main/kotlin/io/openapiprocessor/core/writer/java/DataTypeWriterPojo.kt

Lines changed: 9 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -7,6 +7,7 @@ package io.openapiprocessor.core.writer.java
77

88
import io.openapiprocessor.core.converter.ApiOptions
99
import io.openapiprocessor.core.model.datatypes.DataType
10+
import io.openapiprocessor.core.model.datatypes.InterfaceDataType
1011
import io.openapiprocessor.core.model.datatypes.ModelDataType
1112
import io.openapiprocessor.core.model.datatypes.NullDataType
1213
import io.openapiprocessor.core.support.capitalizeFirstChar
@@ -41,8 +42,8 @@ class DataTypeWriterPojo(
4142
}
4243

4344
private fun writeClassOpen(target: Writer, dataType: ModelDataType) {
44-
val implements: DataType? = dataType.implementsDataType
45-
if (implements != null) {
45+
val implements: Collection<InterfaceDataType> = dataType.implementsDataTypes
46+
if (implements.isNotEmpty()) {
4647
writeClassImplementsHeader(target, dataType, implements)
4748
} else {
4849
writeClassHeader(target, dataType)
@@ -90,9 +91,13 @@ class DataTypeWriterPojo(
9091
private fun writeClassImplementsHeader(
9192
target: Writer,
9293
dataType: ModelDataType,
93-
implements: DataType
94+
implements: Collection<InterfaceDataType>
9495
) {
95-
target.write("public class ${dataType.getTypeName()} implements ${implements.getTypeName()} {\n\n")
96+
var result = "public class ${dataType.getTypeName()} implements "
97+
result += implements.joinToString(", ") { it.getTypeName() }
98+
result += " {\n\n"
99+
100+
target.write(result)
96101
}
97102

98103
private fun writeClassHeader(

openapi-processor-core/src/main/kotlin/io/openapiprocessor/core/writer/java/DataTypeWriterRecord.kt

Lines changed: 6 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -7,6 +7,7 @@ package io.openapiprocessor.core.writer.java
77

88
import io.openapiprocessor.core.converter.ApiOptions
99
import io.openapiprocessor.core.model.datatypes.DataType
10+
import io.openapiprocessor.core.model.datatypes.InterfaceDataType
1011
import io.openapiprocessor.core.model.datatypes.ModelDataType
1112
import io.openapiprocessor.core.writer.Identifier
1213
import java.io.Writer
@@ -68,9 +69,11 @@ class DataTypeWriterRecord(
6869
}
6970

7071
private fun writeRecordImplements(target: Writer, dataType: ModelDataType) {
71-
val implements: DataType? = dataType.implementsDataType
72-
if (implements != null) {
73-
target.write(" implements ${implements.getTypeName()}")
72+
val implements: Collection<InterfaceDataType> = dataType.implementsDataTypes
73+
if (implements.isNotEmpty()) {
74+
var result = " implements "
75+
result += implements.joinToString(", ") { it.getTypeName() }
76+
target.write(result)
7477
}
7578
}
7679

openapi-processor-core/src/test/kotlin/io/openapiprocessor/core/converter/DataTypeConverterOneOfSpec.kt

Lines changed: 2 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -6,6 +6,7 @@
66
package io.openapiprocessor.core.converter
77

88
import io.kotest.core.spec.style.StringSpec
9+
import io.kotest.matchers.collections.shouldContainExactly
910
import io.kotest.matchers.shouldBe
1011
import io.openapiprocessor.core.model.DataTypes
1112
import io.openapiprocessor.core.parser.HttpMethod
@@ -82,7 +83,7 @@ class DataTypeConverterOneOfSpec: StringSpec({
8283
ifDataType.getName() shouldBe "GenericProperties"
8384
ifDataType.items.size shouldBe 2
8485
ifDataType.items.forEach {
85-
(it as ModelDataType).implementsDataType shouldBe ifDataType
86+
(it as ModelDataType).implementsDataTypes shouldContainExactly listOf(ifDataType)
8687
}
8788
}
8889

openapi-processor-core/src/test/kotlin/io/openapiprocessor/core/writer/java/DataTypeWriterPojoSpec.kt

Lines changed: 27 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -214,14 +214,40 @@ class DataTypeWriterPojoSpec: StringSpec({
214214
val ifDataType = InterfaceDataType(
215215
DataTypeName("MarkerInterface"), "pkg", listOf(dataType))
216216

217-
dataType.implementsDataType = ifDataType
217+
dataType.addInterface(ifDataType)
218218

219219
// when:
220220
createWriter().write (target, dataType)
221221

222222
target.toString() shouldContain ("public class Foo implements MarkerInterface {")
223223
}
224224

225+
"writes class with multiple implements" {
226+
options.oneOfInterface = true
227+
228+
val dataType = ObjectDataType ("Foo", "pkg", linkedMapOf(
229+
"foo" to PropertyDataType (
230+
readOnly = false,
231+
writeOnly = false,
232+
dataType = StringDataType (),
233+
documentation = Documentation()
234+
)
235+
))
236+
237+
val ifDataTypeA = InterfaceDataType(
238+
DataTypeName("MarkerInterfaceA"), "pkg", listOf(dataType))
239+
val ifDataTypeB = InterfaceDataType(
240+
DataTypeName("MarkerInterfaceB"), "pkg", listOf(dataType))
241+
242+
dataType.addInterface(ifDataTypeA)
243+
dataType.addInterface(ifDataTypeB)
244+
245+
// when:
246+
createWriter().write (target, dataType)
247+
248+
target.toString() shouldContain ("public class Foo implements MarkerInterfaceA, MarkerInterfaceB {")
249+
}
250+
225251
"writes additional object annotation import from annotation mapping" {
226252
val opts = parseOptions(
227253
"""

0 commit comments

Comments
 (0)