Sequel - grosser/parallel GitHub Wiki

Sequel + Parallel

Especially with the sqlite db backend, it doesn't really work because there's some unresolved threading issues.

A temporary, hacky, slow workaround (which basically defeats Parallel) is to wrap db accesses in .synchronize blocks like so:

$DB.synchronize do
  s = some_model.find_or_create blah: foo
  s.add_whatever
  s.save
end

The following currently results in a Sequel::DatabaseError: SQLite3::BusyException: database is locked error at sqlite3-1.3.11/lib/sqlite3/statement.rb:108:in 'step'

require 'sequel'
require 'parallel'
$DB = Sequel.connect('sqlite://wontwork.sqlite3') # global var is needed to avoid some thread issues

$DB.create_table!(:users) do
  primary_key :id
  String :name, null: false
  index :name, unique: true
end
$DB.create_table!(:posts) do
  primary_key :id
  Integer :user_id, null: false, index: true
end

class User < Sequel::Model($DB)
  one_to_many :posts
end

class Post < Sequel::Model($DB)
  many_to_one :user
end

users = %w[geroge william joe bob jane mary sue sally wilma]

Parallel.each(users, in_threads: 5) do |name|
 u =  User.find_or_create(name: name)
 Parallel.each(1000.times, in_threads: 10) { u.add_post({}) }
end  

Other Sequel + Parallel errors

  • sequel-4.32.0/lib/sequel/model/base.rb:1949:in '_save_refresh': Record not found (Sequel::NoExistingObject)
  • sqlite3-1.3.11/lib/sqlite3/statement.rb:108:in 'step': SQLite3::SQLException: cannot start a transaction within a transaction (Sequel::DatabaseError)
  • sequel-4.32.0/lib/sequel/model/base.rb:1982:in '_update': Attempt to update object did not result in a single row modification (SQL: UPDATE ....
  • sqlite3-1.3.11/lib/sqlite3/database.rb:91:in 'initialize': SQLite3::SQLException: no such table: {{table_name}} (Sequel::DatabaseError) and it darn well exists and works fine without Parallel, when using Sequel associations
  • sequel-4.32.0/lib/sequel/database/transactions.rb:101:in 'block in transaction': undefined method '[]' for nil:NilClass (NoMethodError)

Solved by using concurrent-ruby