Details
-
New Feature
-
Status: Closed (View Workflow)
-
P2
-
Resolution: Done
-
None
-
-
CP: sprint 103
-
8
-
Core: Platform
Description
PROTOCOL (also relevant for non-RMB modules)
FOLIO OL protocol is based on exchanging the value of _version field between the client and the server during record(s) retrieval (GET) and subsequent record update (PUT or POST in the batch update case), The ides is based on how HTTP ETAGs work: server generates a _version value during initial record creation and inserts it into the designated _version field in the record body. The _version value is then returned to the client (during GET) as a regular field in the record. Client is required is to provide the exact same value in the _version field for a subsequent update (PUT). Server then checks if the provided value matches the value stored on the server and if true accepts the update. If the provided value does not match stored value, server responds with 409 Conflict response code.
Schema
The _version should be added as a top-level field to the entity's JSON schema. See example in mod-inventory-storage's instance record: https://github.com/folio-org/mod-inventory-storage/blob/master/ramls/instance.json
RMB schema.json
OL is enabled by providing a withOptimisticLocking table configuration property in the schema.json with the following values:
- off disables optimisticLocking for this table. If a "version" property exists it is ignored,
removed on save,and no "version" is generated. - logOnConflict in case of version conflict detection a WARN log message is logged to the standard log with the UUID of the record and the conflicting versions but the update is allowed. Uses PostgreSQL's RAISE WARNING that gets logged in the module log: https://www.postgresql.org/docs/current/plpgsql-errors-and-messages.html
- failOnConflict in case of version conflict detection a 409 Conflict HTTP error is returned to the client and the update is prevented
. Uses PostgreSQL's RAISE EXCEPTION that usually rolls back the current transaction: https://www.postgresql.org/docs/current/plpgsql-errors-and-messages.html
For phase 1 the default will be off for all tables without a withOptimisticLocking entry.
RMB/Postgres implementation
On module install and module upgrade RMB installs or changes the triggers to match the off, logOnConflict or failOnConflict option in schema.json:
an INSERT trigger that populates the initial value for the "version" property
an UPDATE trigger that compares NEW value with the OLD value and if they match updates the NEW value to a new generated value and allows the update; the trigger warns or fails on mismatch
Proof-of-concept: https://issues.folio.org/browse/RMB-719?focusedCommentId=86211&page=com.atlassian.jira.plugin.system.issuetabpanels:comment-tabpanel#comment-86211 Note: per comments, magic value "-1" in POC will not be implemented for now
RMB tasks for phase 2 (Per comments, not in scope of this ticket. Most likely will be handled in RMB-769)
TenantLoading needs to be changed to pass the "version" property of the records in the database when upgrading reference and sample data.
PgUtil.postSync (when upsert=true) and PgUtil.put need to handle optimistic locking failures by responding with HTTP 409 status code.
VERSION format
Use a simple (to calculate and update) increment counter.
See RMB-719 why other options have issues without clear benefits: hashing is more computationally complex and a random UUID has issues related to replication/clustering.
TestRail: Results
Attachments
Issue Links
- blocks
-
MODINVSTOR-656 enable "detection-only" OL for instances, holdings and titles
-
- Closed
-
-
UIIN-1245 Implement optimistic locking in Inventory
-
- Closed
-
- defines
-
UXPROD-1752 Prevent update conflicts (via optimistic locking): platform support for detection
-
- Closed
-
-
UXPROD-2796 Prevent update conflicts when doing manual edits (User A and User B)
-
- Closed
-
-
UXPROD-2797 Prevent update conflicts (1 user and system trying to act on the same record)
-
- Closed
-
-
UXPROD-2798 Prevent update conflicts (two automated processes acting on the same record)
-
- Closed
-
-
UXPROD-3089 Inventory. Implementing Optimistic Locking
-
- Closed
-
- is cloned by
-
MODINVSTOR-713 Enable support for optimistic locking (failOnConflict) in instances/holdings/items (part1)
-
- Closed
-
- is required by
-
UXPROD-3089 Inventory. Implementing Optimistic Locking
-
- Closed
-
- relates to
-
DEBT-1 No optimistic locking/update conflict resolution
-
- Closed
-
-
FOLIO-2028 SPIKE: how to handle update conflicts?
-
- Closed
-
-
FOLIO-2442 Name Changes to Existing Reference Records
-
- Closed
-
-
MODINVSTOR-431 Settings > Inventory > Mode of issuance. Misc. renaming and source update of existing values
-
- Closed
-
-
RMB-719 SPIKE: design protocol and implementation for optimistic locking
-
- Closed
-
-
MODINVSTOR-665 Response 409 is not defined for class class ItemStorage PutItemStorageItemsByItemIdResponse
-
- Closed
-