私はデータストアに関して次のことに迷っています:
データストアは結合クエリをサポートしていないため、データを非正規化することをお勧めします。これは、同じ情報が複数のエンティティにコピーされることを意味します
非正規化とは、データを更新する必要がある場合は常に、別のエンティティで更新する必要があることを意味します
ただし、単一のエンティティグループには1書き込み/秒の制限があります。
したがって、私が抱えている問題は次のとおりです。
レコードを更新するために、トランザクションを開いてから
必要なすべてのエンティティを更新します。更新されるエンティティは同じエンティティグループ内にありますが、異なる種類に関連しています
「リソース競合」例外が発生します
==>したがって、非正規化されたデータを更新する唯一の方法は、トランザクションの外部にあるようです。しかし、これを行うことは、一部のエンティティが更新される可能性があるのに対し、他のエンティティは更新されないため、非常に悪いことです。
この問題を抱えているのは私だけですか?どのようにそれを解決しましたか?
ありがとう、
ヒューグ
(簡略化されたバージョンの)コードは次のとおりです。
Objectify ofy=ObjectifyService.beginTransaction();
try {
Key<Party> partyKey=new Key<Party>(realEstateKey, Party.class, partyDTO.getId());
//--------------------------------------------------------------------------
//-- 1 - We update the party
//--------------------------------------------------------------------------
Party party=ofy.get(partyKey);
party.update(partyDTO);
//---------------------------------------------------------------------------------------------
//-- 2 - We update the kinds which have Party as embedded field, all in the same entity group
//---------------------------------------------------------------------------------------------
//2.1 Invoices
Query<Invoice> q1=ofy.query(Invoice.class).ancestor(realEstateKey).filter("partyKey", partyKey);
for (Invoice invoice: q1) {
invoice.setParty(party);
ofy.put(invoice);
}
//2.2Payments
Query<Payment> q2=ofy.query(Payment.class).ancestor(realEstateKey).filter("partyKey", partyKey);
for (Payment payment: q2) {
payment.setParty(payment);
ofy.put(payment);
}
}
ofy.getTxn().commit();
return (RPCResults.SUCCESS);
}
catch (Exception e) {
final Logger log = Logger.getLogger(InternalServiceImpl.class.getName());
log.severe("Problem while updating party : " + e.getLocalizedMessage());
return (RPCResults.FAILURE) ;
}
finally {
if (ofy.getTxn().isActive()) {
ofy.getTxn().rollback();
partyDTO.setCreationResult(RPCResults.FAILURE);
return (RPCResults.FAILURE) ;
}
}