Files
Inbound20260114/.claude/commands/new-api.md
lvmeng c697b4aa65 feat(activity): 添加 Zip 文件下载解压工具和趣味页面
- 新增 ZipDownloadUtils:支持大文件下载、进度回调、断点续传
- 新增 ZipExtractUtils:支持 Zip 文件解压、进度回调、自动创建目录
- 新增 ModelResourceManager:高层资源管理器,协调下载和解压流程
- 新增 FunActivity:趣味测试页面,包含 3 个按钮
  - 按钮 1:下载 Zip 文件
  - 按钮 2:解压 Zip 文件
  - 按钮 3:读取 JSON 并保存到 ObjectBox 数据库
- 新增 activity_fun.xml:趣味页面布局
- 新增 ZipToolsUsageExample:工具使用示例文档
- 改进 ToastUtils:改为 Context 扩展方法 (toast/toastLong)
- 暂时注释 HomeActivity 中 tvTime 的点击事件
2026-03-13 11:27:53 +08:00

3.2 KiB
Raw Permalink Blame History

在本项目中新增一个后端 API 接口,需要同时修改三层:ApiService → RemoteRepository → ViewModel。

步骤

1. 收集信息

询问用户以下信息(如已在指令中提供则跳过):

  • 接口名称/功能描述
  • 请求方式:GET / POST / POST + FormUrlEncoded / Multipart
  • 接口路径(相对路径,如 /sideboard/app/xxx
  • 请求参数字段和类型
  • 响应数据类型(已有类 or 需新建)
  • 归属哪个 ViewModelSettingViewModel / UserViewModel / DeviceViewModel

2. 创建数据模型(如需要)

请求参数类: app/src/main/java/com/sw/platecabinet/model/request/<XxxParam>.kt 响应数据类: app/src/main/java/com/sw/platecabinet/model/response/<XxxModel>.kt

数据类规范:

/**
 * <描述>
 */
data class XxxParam(
    val fieldName: String  // 字段说明
)

3. 在 ApiService 中添加接口方法

文件:app/src/main/java/com/sw/platecabinet/network/api/ApiService.kt

关键规则:

  • 必须使用 @Url 注解,URL 格式为:"${GlobalData.appBaseUrl}/terminal/neglect/<路径>"
  • 不要使用相对路径(baseUrl 拦截器不适用于本项目)
  • 方法必须为 suspend 函数,返回 ApiResponse<T>
/**
 * <接口功能描述>
 */
@POST  // 或 @GET / @FormUrlEncoded @POST / @Multipart @POST
suspend fun <methodName>(
    @Url url: String = "${GlobalData.appBaseUrl}/terminal/neglect/<路径>",
    @Body param: XxxParam  // 或 @Query / @Field / @Part
): ApiResponse<XxxModel?>

4. 在 RemoteRepository 中添加调用方法

文件:app/src/main/java/com/sw/platecabinet/repository/RemoteRepository.kt

/**
 * <功能描述>
 */
suspend fun <methodName>(/* 参数 */): ApiResponse<XxxModel?> {
    return safeApiCall {
        apiService.<methodName>(/* 参数传递 */)
    }
}

约束:

  • 必须用 safeApiCall { } 包裹,不要裸调用 apiService
  • 参数直接透传,不在 Repository 层做业务逻辑

5. 在 ViewModel 中添加调用逻辑

文件:app/src/main/java/com/sw/platecabinet/viewmodel/<XxxViewModel>.kt

/**
 * <功能描述>
 * @param callback 成功时回调,参数为响应数据
 */
fun <methodName>(/* 业务参数 */, callback: (XxxModel?) -> Unit) {
    launch {   // 不需要 loading 时用 launch;需要 loading 时用 launchWithLoading
        val response = repository.<methodName>(/* 参数 */)
        if (parseResponse(response)) {
            runOnMainThread { callback(response.result) }
        }
    }
}

注意: launch / launchWithLoading 在协程中执行,回调若需更新 UI 需切换到主线程(使用 withContext(Dispatchers.Main) 或在 Activity 中用 runOnUiThread)。

6. 在 Activity/Fragment 中调用

viewModel.<methodName>(/* 参数 */) { result ->
    // 处理结果
}

注意事项

  • 所有注释使用简体中文
  • 向用户展示将要修改的文件清单(含 Diff 预览),等待确认后再写文件
  • RequestInterceptor 已自动注入认证 header,无需在方法中手动添加
  • 响应体统一为 ApiResponse<T>,通过 response.isSuccess()response.result 取数据