React JS - 为每个表行调用相同的 API 端点,直到响应包含某些条件
Posted
技术标签:
【中文标题】React JS - 为每个表行调用相同的 API 端点,直到响应包含某些条件【英文标题】:React JS - Call same API endpoint for each table row until response contains certain criteria 【发布时间】:2020-04-03 01:59:53 【问题描述】:我有一个应用程序需要调用相同的端点,但表格的每一行使用不同的参数。
到目前为止,我的应用看起来是这样的:
执行以下操作:
当点击 Generate Journey 按钮时,它会向服务器 POST 一堆数据,并得到如下响应:
"id": 1,
"customerId": "db7dab81-0b33-41d3-a4a9-861a45c282b5",
"serviceId": "ac1f0b6f-593e-4377-9697-d8dbe06c6309",
"numberOfJourneys": 3,
"generationStatus": "QUEUED",
注意QUEUED
状态。后端将生成旅程,一旦完成,状态将更改为COMPLETED
。
创建旅程后,我们可以通过单击“模拟”按钮对其进行模拟,然后将一些数据发布到另一个 API 并模拟旅程。
现在我的问题是:
实现此功能的最佳方法是什么?因为我将不得不反复调用端点以检查状态是否为COMPLETED
,然后才能模拟每个表格行的旅程。
我目前还没有解决这个问题的方法,但我在想一些事情:
getJourneyEmulations()
let promise;
promise = journeyCreationStatus();
if (!promise)
return;
this.setState(
isLoading: true
);
promise.then(response =>
const generationStatus = this.state.generationStatus;
this.setState(
generationStatus: generationStatus,
isLoading: false
)
).catch(error =>
this.setState(
isLoading: false
);
console.log(error);
)
然后在componentDidMount
中使用计时器调用它,例如:
componentDidMount()
this.getRouteGenerations();
this.timer = setInterval(()=> this.getJourneyEmulations(), 10000)
但是,我认为这不会起作用,因为我需要为每个表格行调用它。
如果需要更多解释,请发表评论,我会尽力解释。
谢谢
【问题讨论】:
如果您拥有或可以修改服务器,请查看websockets,当QUEUE
为COMPLETE
时,您可以通知您的客户端
【参考方案1】:
因此,此类问题有多种选择,例如长轮询或 websockets,但我假设您无权访问服务器,因此唯一的选择是重复调用服务器。
另外,我猜你会在开始时发送一个 POST,然后端点(或其他一些端点)会通过 GET 向你提供 generationStatus 是否完成的天气信息。
多次获取直到成功的代码可能如下所示:
const url = 'your/api/url/';
const INTERVAL_MS = 5000;
function delay()
return new Promise(resolve => setInterval(resolve, INTERVAL_MS))
function isCompleted(data)
return data.generationStatus === 'COMPLETED'
function postJourney(data)
return fetch(
url,
method:'POST',
body:JSON.stringify(data)
)
.then(response => response.json())
function checkStatusUntilCompleted()
return fetch(url)
.then(response => response.json())
.then(json =>
if (!isCompleted(json))
// we retry after some delay if it was not completed
return delay().then(checkStatusUntilCompleted)
else
return Promise.resolve(json)
)
function postJourneyAndCheckUntilCompleted(rowData)
postJourney(rowData)
.then(json =>
if (!isCompleted(json))
return delay().then(checkStatusUntilCompleted)
else
return Promise.resolve(json)
)
.then((data) =>
// do stuff, it is completed now
)
此外,您可能希望处理 HTTP 错误、CSRF 令牌和/或使用自定义提取包装器。
然后您可以通过以下方式从渲染函数调用 postJourney:
rowDatas.map((rowData) => (
<TableRow key=rowData.key>
<Cell>rowData.customerId</Cell>
/* ... */
<Cell><Button onClick=() => postJourneyAndCheckUntilCompleted(rowData)>Generate Journey</Button></Cell>
</TableRow>
)
干杯
【讨论】:
虽然这是很好的轮询代码,但 OP 主要询问如何为 Journey 表中的每一行创建和管理状态更改轮询请求,OP 在问题中演示了处理 ONE 轮询请求的代码已经。 clearInterval 永远不会在 OP 代码中调用,因此它将继续运行。将它用于多行也非常简单,只需使用单击按钮所在行的数据调用 postJourney。 然后调整您的答案以演示管理多行,特别是如果非常直接,OP 直接要求这样做 我无法访问服务器,但我的一位同事可以。实施网络套接字解决方案会更容易吗? 这取决于技术。例如,如果您使用 Django 作为后端,则可能需要更改一些架构(WSGI -> ASGI,可能是一个 Redis 服务器以在多个客户端之间共享事件)。如果您使用的是 Node,则没有那么复杂,但需要一些设置。以上是关于React JS - 为每个表行调用相同的 API 端点,直到响应包含某些条件的主要内容,如果未能解决你的问题,请参考以下文章
React Hook useEffect :使用 axios 和 async await .api 获取数据,调用连续相同的 api
在 react-redux 应用程序中使用默认错误处理管理 API 调用