feat: 定义仓库协议与用例(含会话)

This commit is contained in:
AndyChen1024
2026-09-15 14:35:52 +08:00
parent 14eb5ad44d
commit ec1eed8f04
10 changed files with 139 additions and 4 deletions

View File

@@ -0,0 +1,9 @@
import CoreModel
/// 打卡数据仓库协议(定义在 domain 层,实现放 CoreRepository)。
public protocol CheckinRepository: Sendable {
/// 观察打卡数据。
func observeCheckin() -> AsyncThrowingStream<CheckinRecord, Error>
/// 提交打卡状态。
func submitCheckin(status: CheckinStatus) async throws
}

View File

@@ -0,0 +1,18 @@
import CoreModel
/// 获取/提交打卡数据的用例。
public struct CheckinUseCase: Sendable {
private let repository: CheckinRepository
public init(repository: CheckinRepository) {
self.repository = repository
}
public func observeCheckin() -> AsyncThrowingStream<CheckinRecord, Error> {
repository.observeCheckin()
}
public func submitCheckin(status: CheckinStatus) async throws {
try await repository.submitCheckin(status: status)
}
}

View File

@@ -1,8 +1,9 @@
import CoreModel import CoreModel
/// Home 数据仓库协议(定义在 domain 层,实现放 CoreRepository)。 /// Home 数据仓库协议(定义在 domain 层,实现放 CoreRepository)。
/// Kotlin: interface HomeRepository { fun observeHome(): Flow<HomeData> }
public protocol HomeRepository: Sendable { public protocol HomeRepository: Sendable {
/// Kotlin: Flow<HomeData> → Swift: AsyncThrowingStream<HomeData, Error> /// 已登录首页。
func observeHome() -> AsyncThrowingStream<HomeData, Error> func observeHome() -> AsyncThrowingStream<HomeData, Error>
/// 游客首页。
func observeGuestHome() -> AsyncThrowingStream<HomeData, Error>
} }

View File

@@ -1,7 +1,6 @@
import CoreModel import CoreModel
/// 获取 Home 数据的用例。 /// 获取 Home 数据的用例。
/// Kotlin: class HomeUseCase(...) { suspend operator fun invoke(): HomeData }
public struct HomeUseCase: Sendable { public struct HomeUseCase: Sendable {
private let repository: HomeRepository private let repository: HomeRepository
@@ -9,8 +8,13 @@ public struct HomeUseCase: Sendable {
self.repository = repository self.repository = repository
} }
/// Kotlin: Flow<HomeData> → Swift: AsyncThrowingStream<HomeData, Error> /// 已登录首页。
public func observeHome() -> AsyncThrowingStream<HomeData, Error> { public func observeHome() -> AsyncThrowingStream<HomeData, Error> {
repository.observeHome() repository.observeHome()
} }
/// 游客首页。
public func observeGuestHome() -> AsyncThrowingStream<HomeData, Error> {
repository.observeGuestHome()
}
} }

View File

@@ -0,0 +1,8 @@
import CoreModel
/// 计划数据仓库协议(定义在 domain 层,实现放 CoreRepository)。
public protocol PlanRepository: Sendable {
func observePlan(type: PlanType) -> AsyncThrowingStream<PlanRecord, Error>
func observePlanSubmit(type: PlanType, periodKey: String) -> AsyncThrowingStream<PlanSubmitData, Error>
func savePlan(type: PlanType, periodKey: String, content: String, attachments: [String]) async throws
}

View File

@@ -0,0 +1,22 @@
import CoreModel
/// 获取/提交计划数据的用例。
public struct PlanUseCase: Sendable {
private let repository: PlanRepository
public init(repository: PlanRepository) {
self.repository = repository
}
public func observePlan(type: PlanType) -> AsyncThrowingStream<PlanRecord, Error> {
repository.observePlan(type: type)
}
public func observePlanSubmit(type: PlanType, periodKey: String) -> AsyncThrowingStream<PlanSubmitData, Error> {
repository.observePlanSubmit(type: type, periodKey: periodKey)
}
public func savePlan(type: PlanType, periodKey: String, content: String, attachments: [String]) async throws {
try await repository.savePlan(type: type, periodKey: periodKey, content: content, attachments: attachments)
}
}

View File

@@ -0,0 +1,7 @@
import CoreModel
/// 个人资料仓库协议(定义在 domain 层,实现放 CoreRepository)。
public protocol ProfileRepository: Sendable {
/// Kotlin: Flow<UserProfile> → Swift: AsyncThrowingStream<UserProfile, Error>
func observeProfile() -> AsyncThrowingStream<UserProfile, Error>
}

View File

@@ -0,0 +1,14 @@
import CoreModel
/// 获取个人资料的用例。
public struct ProfileUseCase: Sendable {
private let repository: ProfileRepository
public init(repository: ProfileRepository) {
self.repository = repository
}
public func observeProfile() -> AsyncThrowingStream<UserProfile, Error> {
repository.observeProfile()
}
}

View File

@@ -0,0 +1,28 @@
import Foundation
/// 会话相关错误。
public enum SessionError: Error, Sendable, LocalizedError {
case invalidPhone
case wrongCode
case phoneNotMatched
public var errorDescription: String? {
switch self {
case .invalidPhone: return "请输入正确的手机号"
case .wrongCode: return "验证码错误"
case .phoneNotMatched: return "手机号未匹配,无法登录"
}
}
}
/// 会话仓库协议(登录态 / 手机号登录)。
public protocol SessionRepository: Sendable {
/// 观察登录态。
func observeIsLoggedIn() -> AsyncThrowingStream<Bool, Error>
/// 请求短信验证码。
func requestSmsCode(phone: String) async throws
/// 手机号 + 验证码登录。
func login(phone: String, code: String) async throws
/// 退出登录。
func logout() async throws
}

View File

@@ -0,0 +1,24 @@
/// 会话用例。
public struct SessionUseCase: Sendable {
private let repository: SessionRepository
public init(repository: SessionRepository) {
self.repository = repository
}
public func observeIsLoggedIn() -> AsyncThrowingStream<Bool, Error> {
repository.observeIsLoggedIn()
}
public func requestSmsCode(phone: String) async throws {
try await repository.requestSmsCode(phone: phone)
}
public func login(phone: String, code: String) async throws {
try await repository.login(phone: phone, code: code)
}
public func logout() async throws {
try await repository.logout()
}
}