You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

如何用密封类减少Kotlin表单验证中的if条件?

表单验证UseCase的优化方案

核心优化方向

1. 封装验证规则,消除重复if判断

把每个字段的验证条件、错误类型、提示信息封装成独立的规则单元,彻底告别零散的if分支。

2. 单一职责拆分

将验证逻辑从UseCase中抽离,让UseCase专注于业务流程,验证逻辑交给专门的验证器类维护。

3. 补充有意义的错误提示

原代码错误信息为空,优化后给用户明确的提示,提升交互体验。

具体实现代码

第一步:定义验证规则数据类

data class ValidationRule(
    val validate: () -> Boolean,
    val error: FormValidationError
)

第二步:创建专门的表单验证器

class UserInfoValidator {
    fun validate(userInfo: UserInfo): FormValidationError? {
        val rules = listOf(
            // 姓名长度验证
            ValidationRule(
                validate = { userInfo.name.length < 3 },
                error = FormValidationError.NameFieldError("姓名长度不能少于3个字符")
            ),
            ValidationRule(
                validate = { userInfo.name.length > 10 },
                error = FormValidationError.NameFieldError("姓名长度不能超过10个字符")
            ),
            // 姓氏长度验证
            ValidationRule(
                validate = { userInfo.surname.length < 2 },
                error = FormValidationError.LastNameError("姓氏长度不能少于2个字符")
            ),
            ValidationRule(
                validate = { userInfo.surname.length > 10 },
                error = FormValidationError.LastNameError("姓氏长度不能超过10个字符")
            )
        )

        // 找到第一个不符合的规则并返回错误
        return rules.firstOrNull { it.validate() }?.error
    }
}

第三步:优化后的UseCase

// 可通过依赖注入方式传入验证器
private val validator: UserInfoValidator = UserInfoValidator()

suspend operator fun invoke(userInfo: UserInfo): Resource<Unit> {
    validator.validate(userInfo)?.let { error ->
        return Resource.Error(type = error)
    }

    return currentUserRepository.insertCurrentUserInfo(userInfo)
}

可选扩展:支持多错误收集

如果需要一次性返回所有验证错误,可以修改验证器返回错误列表:

fun validateAll(userInfo: UserInfo): List<FormValidationError> {
    return rules.filter { it.validate() }.map { it.error }
}

然后在UseCase中判断处理:

val errors = validator.validateAll(userInfo)
if (errors.isNotEmpty()) {
    // 可根据需求返回第一个错误或封装所有错误返回
    return Resource.Error(type = errors.first())
}

额外优化建议

  • 把验证的长度阈值(如3、10)抽成常量,便于统一维护修改
  • 后续新增字段验证时,只需在验证器中添加新的ValidationRule,无需改动UseCase逻辑
  • 若需支持多语言,可将错误提示信息替换为字符串资源引用

内容的提问来源于stack exchange,提问作者Tunahan

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.08.20 16:06:28