Reputation: 2228
I'm converting some pet project from java to kotlin and stuck with some problem that can't solve. In java all compile fine but after convertation to Kotlin doesn't want....
...
import org.mapstruct.Mapper
import org.mapstruct.Mapping
import org.mapstruct.Named
...
@Mapper(unmappedTargetPolicy = ReportingPolicy.ERROR)
interface EffectMapper {
@Mapping(source = "icon", target = "icon", qualifiedByName = ["convertIcon"])
fun toDS(effectDTO: EffectDTO): EffectDS
fun toDSarr(effectDTOArrayList: ArrayList<EffectDTO>): ArrayList<EffectDS>
@Named("convertIcon")
fun convertIcon(obj: String?): ByteArray? {
return if (obj != null) {
Base64.decode(obj, Base64.DEFAULT)
} else {
null
}
}
companion object {
val MAPPER = Mappers.getMapper(EffectMapper::class.java)
}
}
Gradle return error
error: Can't generate mapping method from non-iterable type to iterable type.
public abstract byte[] convertIcon(@org.jetbrains.annotations.Nullable()
and
Can't map property "java.lang.String icon" to "byte[] icon". Consider to declare/implement a mapping method: "byte[] map(java.lang.String value)".
@org.mapstruct.Mapping(source = "icon", target = "icon", qualifiedByName = {"convertIcon"})
and
Can't map property "java.lang.String effect" to "one.codium.funart.DataStructure.effect.Effect effect". Consider to declare/implement a mapping method: "one.codium.funart.DataStructure.effect.Effect map(java.lang.String value)".
public abstract one.codium.funart.DataStructure.EffectDS toDS(@org.jetbrains.annotations.NotNull()
finally it was done by this way
@Mapper(unmappedTargetPolicy = ReportingPolicy.ERROR, uses = [EffectMapperImpl::class])
interface EffectMapper {
fun toDS(effectDTO: EffectDTO): EffectDS
fun toDSarr(effectDTOArrayList: ArrayList<EffectDTO>): ArrayList<EffectDS>
companion object {
val MAPPER: EffectMapper = Mappers.getMapper(EffectMapper::class.java)
}
}
object EffectMapperImpl {
fun convertIcon(obj: String?): ByteArray? {
return if (obj != null) {
Base64.decode(obj, Base64.DEFAULT)
} else {
null
}
}
fun toEffect(s: String): Effect {
return Effect(s)
}
}
Thank you @Filip
Upvotes: 5
Views: 6459
Reputation: 4524
I am using Kotlin 1.3.71-release-431 and it works fine with @JvamDefault, so you just need to make your conversion method (toEffect) static in (java).
Mapping(source = "sourceFiledName", target = "destinationFiledName", qualifiedByName = ["converterMethod"])
interface EffectMapper {
fun toDS(effectDTO: EffectDTO): EffectDS
fun toDSarr(effectDTOArrayList: ArrayList<EffectDTO>): ArrayList<EffectDS>
companion object {
@JvmStatic
@Named("converterMethod")
fun toEffect(s: String): Effect {
return Effect(s)
}
}
}
Upvotes: 6
Reputation: 21423
The problem you are seeing is due to the fact that the convertIcon
method is not recognized as a default method in the EffectMapper
interface.
Even if you use @JvmDefault
it won't work due to KT-25960. I would suggest that you extract the convertIcon
method into a public static method in another class and then use it via Mapper#uses
Upvotes: 0