知识库发布按钮引发的查询版本发布状态(轮询?——>调用后端接口)以及api接口设计学习

知识库发布按钮通过查询当前版本是否之前已经发布过来控制按钮是置灰还是高亮

javascript 复制代码
  // 检查是否有待发布的任务
  const checkPublishStatus = useCallback(async () => {
    if (!kbId) {
      setHasPendingPublishTasks(false)
      return
    }

    try {
      const result = await api.tasks.list({
        task_type: 'upload',
        kb_id: kbId,
        page: 1,
        page_size: 1
      })

      const tasks = Array.isArray(result) ? result : (result?.items || result?.list || [])

      if (!tasks || tasks.length === 0) {
        setHasPendingPublishTasks(false)
        return
      }

      const hasPending = tasks.some(task => {
        const status = String(task.status || '').toLowerCase()
        const completedStatuses = ['completed', 'done', 'success', 'failed', 'error', 'cancelled', 'canceled']
        return !completedStatuses.includes(status) &&
          (status === 'pending' || status === 'running' || status === 'processing' || status === 'waiting' || status === '')
      })

      setHasPendingPublishTasks(hasPending)
    } catch (err) {
      console.error('检查发布状态失败:', err)
      setHasPendingPublishTasks(true)
    }
  }, [kbId])

  // 当kbId变化或文件列表更新时,检查发布状态
  useEffect(() => {
    checkPublishStatus()
  }, [checkPublishStatus])

  useEffect(() => {
    if (kbId && items.length > 0) {
      const timer = setTimeout(() => {
        checkPublishStatus()
      }, 1000)
      return () => clearTimeout(timer)
    }
  }, [kbId, items.length, checkPublishStatus])

这里我详细的理清他的后端逻辑,他是如何向后端请求接口的

【怎么调用后端接口来查询版本发布状态的?】

task_type 必须要是upload

首先第一个我觉得值得学习的就是这个自检查机制

这样子看我们还看不太懂,接下来我们去做详细的剖析

用useEffect套了两层,蛮妙

还有一个我觉得值得学习的就是整个项目的api接口设计

javascript 复制代码
// Task management
tasks: {
  list: ({ task_type, kb_id, status, page = 1, page_size = 20 } = {}) =>
    request('GET', '/v1/tasks/list', { query: { task_type, kb_id, status, page, page_size } }),
  // ...
}
javascript 复制代码
async function request(method, path, { query, body, token, headers, requireAuth = true, responseType } = {}) {
  // 1. 处理认证 token
  if (requireAuth && !token) {
    const storedToken = tokenManager.getToken()
    // ... token 处理逻辑
  }

  // 2. 构建完整的 URL
  const fullPath = API_BASE + API_PREFIX + path
  // API_BASE = '' (空字符串,使用代理)
  // API_PREFIX = '/api'
  // path = '/v1/tasks/list'
  // 最终: '/api/v1/tasks/list'
  
  const url = new URL(fullPath, window.location.origin)
  
  // 3. 添加查询参数
  if (query) {
    Object.entries(query).forEach(([k, v]) => {
      if (v !== undefined && v !== null && v !== '') {
        url.searchParams.append(k, String(v))
      }
    })
  }
  // 最终 URL: http://localhost:5173/api/v1/tasks/list?task_type=upload&kb_id=xxx&page=1&page_size=1

  // 4. 构建请求选项
  const requestOptions = {
    method: 'GET',  // HTTP 方法
    headers: {
      'Content-Type': 'application/json',
      'Authorization': `Bearer ${token}`  // 添加认证头
    }
  }

  // 5. 发送请求(使用浏览器原生的 fetch API)
  const res = await fetch(url.toString(), requestOptions)
  
  // 6. 处理响应
  const data = await res.json()
  return data
}

完整调用流程

javascript 复制代码
你在代码中调用:
  api.tasks.list({ task_type: 'upload', kb_id: kbId, page: 1, page_size: 1 })
         ↓
tasks.list 方法执行:
  request('GET', '/v1/tasks/list', { query: { task_type: 'upload', kb_id: kbId, ... } })
         ↓
request 函数执行:
  1. 获取 token
  2. 构建 URL: '/api/v1/tasks/list'
  3. 添加查询参数: ?task_type=upload&kb_id=xxx&page=1&page_size=1
  4. 添加 Authorization 头: Bearer token
         ↓
fetch API 发送 HTTP 请求:
  GET http://localhost:5173/api/v1/tasks/list?task_type=upload&kb_id=xxx&page=1&page_size=1
  Headers: {
    Authorization: Bearer xxx,
    Content-Type: application/json
  }
         ↓
后端服务器接收请求并处理
         ↓
返回响应数据
         ↓
request 函数解析响应并返回
         ↓
你得到 result 数据
相关推荐
Java小卷36 分钟前
流程设计器为啥选择diagram-js
前端·低代码·工作流引擎
HelloReader1 小时前
Isolation Pattern(隔离模式)在前端与 Core 之间加一道“加密网关”,拦截与校验所有 IPC
前端
兆子龙2 小时前
从 float 到 Flex/Grid:CSS 左右布局简史与「刁钻」布局怎么搞
前端·架构
YukiMori232 小时前
一个有趣的原型继承实验:为什么“男人也会生孩子”?从对象赋值到构造函数继承的完整推演
前端·javascript
_哆啦A梦2 小时前
Vibe Coding 全栈专业名词清单|设计模式·基础篇(创建型+结构型核心名词)
前端·设计模式·vibecoding
百里静修2 小时前
一个 Hook 拦截所有 AJAX 请求:ajax-hooker 使用指南与原理
前端
摸鱼的春哥2 小时前
惊!黑客靠AI把墨西哥政府打穿了,海量数据被黑
前端·javascript·后端
小兵张健2 小时前
Playwright MCP 截图标注方案调研(推荐方案1)
前端·javascript·github
考虑考虑2 小时前
JDK25模块导入声明
java·后端·java ee
小兵张健3 小时前
AI 页面与交互迁移流程参考
前端·ai编程·mcp