我可以将JSON文件转换为kotlin多平台对象在Swift?



对于上下文:我使用kotlin多平台与我的后端为我的两个应用程序进行通信,我也试图遵循清洁架构+ MVVM。我的多平台项目包含我的数据层(存储库和dtos),我的应用程序项目包含表示层和领域层(VC,视图模型,用例)。

我想在多平台项目中模拟我的存储库。

我有一个类(DTO)在我的Kotlin多平台项目,看起来像这样

@Serializable
data class LoginResponse(val data: LoginResponseBody){
@Serializable
data class LoginResponseBody(
var accessToken: String,
var lastChannel: String? = null,
var lastDateTime: String? = null,
var userId: String? = null,
var transactionalKeyStatus: String? = null,
var accessStatus: String? = null
)
}

当我将这个多平台项目添加到我的xcode项目中时,对象转换为:

__attribute__((objc_subclassing_restricted))
__attribute__((swift_name("LoginResponse")))
@interface SharedEmaLoginResponse : SharedEmaBase
- (instancetype)initWithData:(SharedEmaLoginResponseLoginResponseBody *)data __attribute__((swift_name("init(data:)"))) __attribute__((objc_designated_initializer));
- (SharedEmaLoginResponseLoginResponseBody *)component1 __attribute__((swift_name("component1()")));
- (SharedEmaLoginResponse *)doCopyData:(SharedEmaLoginResponseLoginResponseBody *)data __attribute__((swift_name("doCopy(data:)")));
- (BOOL)isEqual:(id _Nullable)other __attribute__((swift_name("isEqual(_:)")));
- (NSUInteger)hash __attribute__((swift_name("hash()")));
- (NSString *)description __attribute__((swift_name("description()")));
@property (readonly) SharedEmaLoginResponseLoginResponseBody *data __attribute__((swift_name("data")));
@end;

我认为类LoginResponse将符合'可解码',但它没有,这是我的假库看起来像在我的xcode项目

final class LoginRepositoryTest : XCTestCase, IAuthRepository {
var hasError = false
func login(loginRequest: LoginRequest, success: @escaping (LoginResponse) -> Void, failure: @escaping (ErrorResponse) -> Void, completionHandler: @escaping (KotlinUnit?, Error?) -> Void) {
if hasError {
failure(ErrorResponse(messages: []))
} else {
let data = loadStub(name: "loginResponse", extension: "json")
let decoder = JSONDecoder()
decoder.dateDecodingStrategy = .secondsSince1970

let loginData = try! decoder.decode(LoginResponse.self, from: data)
success(loginData)
}
}

func getKoin() -> Koin_coreKoin {}
}

误差

实例方法'decode(_:from:)'要求'LoginResponse'符合'Decodable'

我想我有两个选择:

  • 我使kotlin类符合'可解码'
  • 我找到了一种方法将JSON转换为该对象而不使用可解码

任何帮助都是感激的

Kotlin序列化并不意味着向类确认Decodable协议。它意味着在kotlin中使用kotlin序列化,如下所示:

val response: LoginResponse = Json.decodeFromString(
LoginResponse.serializer(),
string
)

注。最初您可以使用Json.decodeFromString<LoginResponse>(string),但据我所知,这还不支持多平台

网络和JSON解析是最容易在KMM上完成的事情,你也可以在那里编写测试,但如果你仍然需要直接从iOS使用它,你可以尝试以下包装器:

object JsonHelper {
@Throws(Throwable::class)
fun decodeRtcMsg(string: String) = 
Json.decodeFromString(
RtcMsg.serializer(), 
string
)
}

那么你可以从swift:

do {
try JsonHelper().decodeLoginResponse(string: "")
} catch {
print(error)
}

如果你真的需要Decodable,我会创建Decodableexpect/actual:

// in common
expect interface Decodable
// on Android
actual interface Decodable
// on iOS
actual typealias Decodable = Decodable

然后为你的dto实现Decodable。也许最好的例子是如何在共享代码中使用Parcelize: https://github.com/icerockdev/moko-parcelize/blob/master/parcelize/src/androidMain/kotlin/dev/icerock/moko/parcelize/Parcelize.kt

最新更新