我正在使用Kotlin 1.30。我有以下将从API中填充的实体类。而且某些属性在API中可能为null,因此我已使用安全null类型声明了它们。
但是,我会将这个实体类映射到我的域模型类。并且只是想知道什么是处理null类型的最佳方法?
当我映射类时,我有两个想法。
在以下代码段中,我正在使用elvis运算符。只是想知道什么是最佳做法?
class LoginResponseDomainMapperImp : LoginResponseDomainMapper {
override fun map(entity: LoginResponseEntity): LoginResponse {
return LoginResponse(
entity.token ?: "",
mapUsers(entity.user),
mapEnterprises(entity.enterprises ?: emptyList()),
mapVendors(entity.vendors ?: emptyList()))
}
private fun mapUsers(userEntity: UserEntity?): User {
return User(
userEntity?.id,
userEntity?.email,
userEntity?.firstName,
userEntity?.lastName,
userEntity?.phone,
userEntity?.address,
userEntity?.dob,
userEntity?.customer,
userEntity?.enterpriseIds ?: emptyList(),
userEntity?.vendorIds ?: emptyList())
}
private fun mapEnterprises(enterprisesEntity: List<EnterprisesEntity>): List<Enterprises> {
val enterpriseList = mutableListOf<Enterprises>()
enterprisesEntity.forEach {
val enterprise = Enterprises(
it.id,
it.enterpriseName,
it.typeLabel,
it.country,
it.imageId,
it.managers,
it.members,
it.stripe,
it.locations)
enterpriseList.add(enterprise)
}
return enterpriseList.toList()
}
private fun mapVendors(vendorsEntity: List<VendorsEntity>): List<Vendors> {
val vendorList = mutableListOf<Vendors>()
vendorsEntity.forEach {
val vendor = Vendors(
it.id,
it.vendorName,
it.typeLabel,
it.userRole,
it.latitude,
it.longitude,
it.partner,
it.country,
it.imageId,
it.stripe)
vendorList.add(vendor)
}
return vendorList.toList()
}
}
将从API填充的实体类,因此其中任何一个都可以为空
data class LoginResponseEntity(
@SerializedName("token") val token: String?,
@SerializedName("user") val user: UserEntity?,
@SerializedName("enterprises") val enterprises: List<EnterprisesEntity>?,
@SerializedName("vendors") val vendors: List<VendorsEntity>?)
data class UserEntity(
@SerializedName("id") val id: String?,
@SerializedName("email") val email: String?,
@SerializedName("first_name") val firstName: String?,
@SerializedName("last_name") val lastName: String?,
@SerializedName("phone") val phone: String?,
@SerializedName("address") val address: String?,
@SerializedName("dob") val dob: String?,
@SerializedName("customer") val customer: String?,
@SerializedName("enterprise_ids") val enterpriseIds: List<String>?,
@SerializedName("vendor_ids") val vendorIds: List<String>?)
data class EnterprisesEntity(
@SerializedName("id") val id: String?,
@SerializedName("enterprise_name") val enterpriseName: String?,
@SerializedName("type_label") val typeLabel: String?,
@SerializedName("referral_code") val referralCode: String?,
@SerializedName("country") val country: String?,
@SerializedName("image_id") val imageId: String?,
@SerializedName("managers") val managers: List<String>?,
@SerializedName("members") val members: List<String>?,
@SerializedName("stripe") val stripe: Boolean,
@SerializedName("locations") val locations: List<String>?)
data class VendorsEntity(
@SerializedName("id") val id: String?,
@SerializedName("vendor_name") val vendorName: String?,
@SerializedName("type_label") val typeLabel: String?,
@SerializedName("user_role") val userRole: String?,
@SerializedName("latitude") val latitude: Float,
@SerializedName("longitude") val longitude: Float,
@SerializedName("partner") val partner: Boolean,
@SerializedName("country") val country: String?,
@SerializedName("image_id") val imageId: String?,
@SerializedName("stripe") val stripe: Boolean)
域中的数据模型类,最好将它们声明为所有安全的null类型?
data class LoginResponse(
val token: String,
val user: User?,
val enterprises: List<Enterprises>,
val vendors: List<Vendors>)
data class User(
val id: String?,
val email: String?,
val firstName: String?,
val lastName: String?,
val phone: String?,
val address: String?,
val dob: String?,
val customer: String?,
val enterpriseIds: List<String>,
val vendorIds: List<String>)
data class Enterprises(
val id: String,
val enterpriseName: String,
val typeLabel: String,
val country: String,
val imageId: String,
val managers: List<String>,
val members: List<String>,
val stripe: Boolean,
val locations: List<String>)
data class Vendors(
val id: String,
val vendorName: String,
val typeLabel: String?,
val userRole: String,
val latitude: Float,
val longitude: Float,
val partner: Boolean,
val country: String?,
val imageId: String,
val stripe: Boolean)
答案 0 :(得分:2)
首先,Kotlin中没有安全的null类型。变量是否可以为空。
如果API通过不存在或通过将它们显式设置为null来传递空值,则您的数据类应以那些变量可为空的方式(在数据类型后紧跟问号?
)反映这一点。 / p>
将这些数据类映射到实体(域模型)时,应正确处理null大小写。由于这是一种有效的情况,因此该API可提供您期望的空值,因此应通过分配默认值来处理这种情况。
使用elvis运算符只是优雅地处理可空类型的一种方法,但是如果使用它,仍然是您的选择。
答案 1 :(得分:1)
如果将所有属性都声明为nullable
,即使您使用空安全操作符访问它们,也不会比Java
更好。如果您的JSON属性具有null
值,则意味着在您的业务逻辑中它们并不总是具有值,并且您有责任通过回退到默认值(即emptyList()
或""
),或者更复杂的操作,例如重定向到登录屏幕。