简体   繁体   English

两个线程编写同一实体的不同字段

[英]Two threads writing different fields of same entity

I have the following situation. 我有以下情况。

One business entity (BE) consists of 2 parts provided asynchronously by 2 threads. 一个业务实体(BE)由2个线程异步提供的2个部分组成。 Example: our BE has fields id and, A, B, C - all in one table in database. 示例:我们的BE具有字段id和A,B,C-全部在数据库的一个表中。 Id is generated by sequence when entity is stored into database. 当实体存储到数据库中时,Id是按顺序生成的。 B is unique field, there's constraint on it in database. B是唯一字段,数据库中对此有约束。 Process1 provides fields A and B. Process2 provides fields B and C. So after both processes finish, we should have one row in a table with all columns filled in. Process1提供了字段A和B。Process2提供了字段B和C。因此,在两个过程完成之后,我们应该在表中的一行中填满所有列。

What is the good way to make this work? 进行这项工作的好方法是什么?

What is done now: 现在做什么:

In each process we first select all values from table where value in column B is what we now have. 在每个过程中,我们首先从表中选择所有值,其中B列中的值就是现在的值。 (If any - this means the other process already saved it's part). (如果有的话-这意味着其他进程已经保存了它的一部分)。 If there's something, it is enriched with the missing column and persisted. 如果有的话,它会随着缺少的列而丰富并持续存在。 If there's nothing - we just persist what we have. 如果什么都没有-我们只是坚持我们拥有的。 But while all this is done, it can occur that the other process finished it's job and when we persist our entity, we get ConstraintViolationException and hibernate marks transaction to rollback. 但是,尽管所有这些都完成了,但是有可能另一个进程完成了它的工作,并且当我们保留实体时,我们会得到ConstraintViolationException并将休眠事务标记为回滚。 And the missing column is still missing. 并且缺少的列仍然丢失。

You first have to decide how you want conflicts to be handled. 您首先必须决定如何处理冲突。 For this answer the following questions: 为此,请回答以下问题:

If process 1 changes your entity while process 2 is running are the results of 2 still valid? 如果在进程2运行时进程1更改了您的实体,则2的结果仍然有效吗? Or should it rerun? 还是应该重新运行?

If process 1 updates field B should while process 2 is running should process 2 overwrite it? 如果进程1更新了字段B,则进程2在运行时应该覆盖进程2吗? or just keep the value of process 1? 还是只保留过程1的价值?

Of course the questions should also be answered with 1 and 2 interchanged. 当然,问题也应该通过1和2互换来回答。

If you implement the process in a way that they take the original entity, and produce a new modified + the original entity they startet with, you can have a single queue where all these results get added and a single process applying these changes to your database. 如果以某种方式实施流程,使他们采用原始实体,并产生一个新的修改过的实体并以其开始,那么您可以有一个队列,其中添加了所有这些结果,并且有一个流程将这些更改应用于数据库。

In specific scenarios, simpler approaches might be possible, but this is the approach I would recommend in the very general case you describe in your question. 在特定情况下,可能有更简单的方法,但这是我在问题中描述的最一般情况下建议的方法。

i would do it this way 我会这样

  • load or create Entity before launching the threads 在启动线程之前加载或创建实体
  • launch thread and give it to each 启动线程并将其分配给每个线程
  • update it in both threads 在两个线程中更新它
  • when both finished save to db 当两个都完成保存到数据库

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM