並行と並列の違い
- 並行 (concurrent)
- 複数の動作 (処理の流れ) を同時に実行状態 (in progress) に保つ機能を備えている。
- 並列 (parallel)
- 複数の動作を同時に実行する。
参考:
parallel と concurrent、並列と並行の違い | 本当は怖い情報科学
Concurrent Ruby
参考:
Concurrent Ruby (ruby-concurrency.github.io)
concurrent-ruby | RubyGems.org
Documentation for concurrent-ruby | RubyDoc.info
Rails アプリで Concurrent Ruby を使う 翻訳 | TechRacho
Concurrent Ruby で並行処理プログラミング | Memento memo.
concurrent-ruby 1.0.5 以前での Promises の使い方 – Qiita
Concurrent::Map
並行処理で使用した際のパフォーマンスに最適化したマップ形式のオブジェクトを提供するクラス
参考:
Class: Concurrent::Map — Documentation for concurrent-ruby | RubyDoc.info
promise.rb
参考:
lgierth/promise.rb: Promises/A+ for Ruby – GitHub
Documentation for promise.rb | RubyDoc.info
スレッドセーフ
処理をスレッドセーフにする方法
- オブジェクトを
freeze
してステートレスにする Concurrent::ThreadLocalVar
を使うMutex#synchronize
ブロック内で処理する (排他処理)Concurrent::Array
/Conrurrent::Hash
を使う (全ての操作が排他的に処理されるスレッドセーフなクラス)- グローバルなオブジェクトを使用しない (処理毎に都度必要なオブジェクトを生成する)
参考:
3 ways to make your ruby object thread-safe | Arkency Blog
Write your own thread-safe data structures | Jesse Storimer’s Blog
Thread-safe collections in Ruby | makandra dev
Thread-safety for hashes in Ruby – Stack Overflow
Thread.current
参考:
Understanding Ruby Thread-Local Variables | RubyTapas
Ruby’s Thread.current | Mauricio Gomes
GVL
参考:
Ruby でスレッドセーフでないことを簡単に確認したい | もょもとの技術ノート
Array と Queue がスレッドセーフか検証してみた – Qiita
RequestStore
リクエスト毎に Thread.current
をリセットする。
参考:
steveklabnik/request_store: Per-request global storage for Rack – GitHub
Store thread-safe global request specific data with Rails – Stack Overflow
リクエスト単位でグローバルな参照を持たせて Audit ログをスッキリ実装したい – Qiita
RequestLocals
参考:
Threads
参考:
yegor256/threads: Ruby Gem to unit-test a piece of code in multiple concurrent threads – GitHub
Do You Test Ruby Code for Thread Safety? | DZone Open Source