1

我们使用 cadence 0.11

在我们的项目中,有一个经常使用的服务需要 workflowHistory。
所以我们不得不经常调用这个函数:

GetWorkflowHistory(ctx context.Context, workflowID string, runID string, isLongPoll bool, filterType s.HistoryEventFilterType) HistoryEventIterator

问题是,函数调用很慢,这让我们的服务很慢。更重要的是,我们必须确保工作流的正确性,所以我们不能使用缓存,因为缓存不能存储频繁更新的数据。

有没有更快的方法让我们获取 workflowHistory?也许是一个新的 api,或者一些新的配置?

4

1 回答 1

2

没有更快的方法来获取历史记录。延迟取决于历史的长度和大小。这是 Cadence 中的一个关键 api,因此性能已在其架构中优化到最佳状态。

但是,根据您的用例,这是对 api 的滥用。您应该为工作流实现查询处理程序。Worker 将执行与解析历史相同的所有操作。

如果愿意,您可以实现一个非常通用的查询处理程序,它返回工作流事件中的几乎所有内容。这样只有一个 Query 处理程序可以让您从历史中获取任何东西。具体来说,您可以将所有信号、活动输入输出等放入一个列表中,并将该列表作为查询结果返回。

使用工作者查询将为您节省延迟。这是因为 Cadence 工作人员会缓存历史记录。当工作流程没有更改时,它将不会从服务器获取更多历史记录。当添加新事件时,工作人员和服务器之间只会传输事件的增量。因此,无论历史记录的长度如何,延迟都是最小的。

工作人员需要重新加载整个历史记录的唯一情况是缓存被驱逐或工作人员重新启动。所以总是建议保持历史简短,这样在这种情况下就不会花费太多资源。

查看更多关于查询的文档。

https://cadenceworkflow.io/docs/concepts/queries/#stack-trace-query

戈朗

https://cadenceworkflow.io/docs/go-client/queries/

Java https://cadenceworkflow.io/docs/java-client/queries/

以 Golang 为例,如果要返回活动结果作为查询输出:


func MyWorkflow(ctx workflow.Context, input string) error {
    var res map[string]string 
    err := workflow.SetQueryHandler(ctx, "current_state", func() (map[string]string, error) {
        return res, nil
    })
    
    ctx = workflow.WithActivityOptions(ctx, ...)
    var act_out string 
    err = workflow.ExecuteActivity(ctx, ActivityA, "my_input").Get(ctx, &act_out)
    if err != nil {
        res["ActivityA"] = act_out
        return err
    }
    return nil
}

于 2021-09-01T05:51:15.647 回答