简体   繁体   中英

How can I handle the primary key of a table with multiple batch inserts?

I previously was working on an app that populated the ODS in real time. Every it was determined that all the records for a given table were correct, a sequence object specific to each table's PK would be called to generate the PK. Once returned, it would be stored in a Map for use in FK references on other tables in the same session; it was inserted directly, not auto generated. I understand that the sequence is thread safe, in that
A friend mentioned that on one of his prior projects at a different company they used batch processing and simply used the range of max index +1 up to the number of rows to be inserted. However, the tables were locked inside one instance of the app, not a cluster.
Say one wanted to support both batch and real-time operations for the same collection of tables. With a stored procedure would it be possible to:

  1. Lock a sequence object.
  2. Increment it by an parameter for # of rows.
  3. Store in a temp variable the last value.
  4. Unlock the sequence object.
  5. Finally, return the temp variable.

The first problem I have with this idea is that unless the command to lock the sequence can be blocked, there is nothing to prevent this stored procedure from being run multiple times simultaneously. I add the J2E tag in the event someone could provide a better solution that is primarily on the Java side.

You cannot lock a DB2 SEQUENCE , nor do you need to. The DB2 engine handles sequence synchronization and guarantees that each concurrent sessions receives non-conflicting sequence values.

For batch inserts you can set the sequence cache to the batch size, which significantly improves concurrency.

You can obtain the last generated sequence value for reuse as a foreign key value in multiple ways. The simplest is to use the PREVIOUS VALUE FOR <sequence name> expression and store the result in an application variable. An alternative is to query the data change table of the INSERT :

SELECT id INTO :my_fk_variable FROM FINAL TABLE (
 INSERT INTO my_table (id, something) 
 VALUES (NEXT VALUE FOR my_sequence, 'whatever'))

Use randomly generated 16 byte primary keys. Generate them in your Java code. No need to look them up. Absurdly low risk of collisions. Master-master replication friendly. Never any locking. Batch as many as you want. Fantastic performance within indexes (excellent key dispersion).

Also known as: GUID's or UUID's.

Something like:

  1. Start of transaction
  2. Alter sequence (Increment by No. of rows) 1
  3. Store in a temp variable the last value.
  4. return the temp variable.
  5. End of transaction.

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

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