#author("2021-06-13T12:41:12+09:00","default:ryuichi","ryuichi")
#author("2021-06-13T12:43:24+09:00","default:ryuichi","ryuichi")
* SKIP LOCKEDを使ったジョブキューイング [#kd5e73b7]

** 1. 最初にAが1行取得する [#ff38e4ed]

 Session A                                            │Session B
 =====================================================│===================================================
 PG=> BEGIN; SELECT * FROM jobs WHERE status = 'p     │PG=>
 ending' LIMIT 1 FOR UPDATE SKIP LOCKED;              │PG=>
 BEGIN                                                │PG=>
  id | status                                         │PG=>
 ----+---------                                       │PG=>
   1 | pending                                        │PG=>
 (1 rows)                                             │PG=>
                                                      │PG=>
 PG=*>                                                │PG=> BEGIN; SELECT * FROM jobs FOR UPDATE SKIP L
 PG=*>                                                │OCKED;
 PG=*>                                                │BEGIN
 PG=*>                                                │ id | status
 PG=*>                                                │----+---------
 PG=*>                                                │  2 | pending
 PG=*>                                                │  3 | pending
 PG=*>                                                │(2 rows)


- Aが'''FOR UPDATE SKIP LOCKED'''を指定してjobsテーブルからSELECTして1行取得(上の通りID:1の行)
- BはjobsテーブルからID:1を除いたID:2とID:3の行しかSELECTできなくなる

** 2. 次にAが取得した行をUPDATEしてCOMMITする [#ef39c1c4]

 PG=*> UPDATE jobs SET status = 'runnnig' WHERE i     │PG=*>
 d = 1;                                               │PG=*>
 UPDATE 1                                             │PG=*>
 PG=*>                                                │PG=*> SELECT * FROM jobs FOR UPDATE SKIP LOCKED;
                                                      │ id | status
                                                      │----+---------
                                                      │  2 | pending
                                                      │  3 | pending
                                                      │(2 rows)
                                                      │
                                                      │PG=*> 
 PG=*> COMMIT;                                        │PG=*>
 COMMIT                                               │PG=*>
 ryuichi=>                                            │PG=*> SELECT * FROM jobs FOR UPDATE SKIP LOCKED;
 PG=>                                                 │PG=*> SELECT * FROM jobs FOR UPDATE SKIP LOCKED;
                                                      │ id | status
                                                      │----+---------
                                                      │  2 | pending
                                                      │  3 | pending
                                                      │  1 | runnnig
                                                      │(3 rows)


- Aは1.で取得した行をUPDATEするが、この時点でもBはID:1の行を取得できない
- AがCOMMIT実行した後に、BはID:1の行を取得できるようになるが、この時にはstatusはrunningに更新済み

** 参考 [#d077cac0]

https://spin.atomicobject.com/2021/02/04/redis-postgresql/

トップ   編集 差分 バックアップ 添付 複製 名前変更 リロード   新規 一覧 検索 最終更新   ヘルプ   最終更新のRSS