Skip to content

Instantly share code, notes, and snippets.

@akostadinov
Last active November 28, 2023 21:09
Show Gist options
  • Save akostadinov/d7a0b00fabb48ca74f08fb54090993e7 to your computer and use it in GitHub Desktop.
Save akostadinov/d7a0b00fabb48ca74f08fb54090993e7 to your computer and use it in GitHub Desktop.
async redis playground
# frozen_string_literal: true
require "bundler/inline"
gemfile(true) do
source "https://rubygems.org"
git_source(:github) { |repo| "https://github.com/#{repo}.git" }
gem 'concurrent-ruby', '~> 1.1.6'
gem 'hiredis', '~> 0.6.1'
gem 'async-redis', '~> 0.7.0'
gem 'redis', git: 'https://github.com/3scale/redis-rb', branch: 'apisonator'
end
require 'concurrent'
require 'async/io'
require 'async/redis/client'
require 'hiredis'
require 'redis'
$redis_port = 6379
# works fine
def async_thread_isolate
client = Concurrent::ThreadLocalVar.new do
endpoint = Async::IO::Endpoint.tcp('localhost', $redis_port)
Async::Redis::Client.new(endpoint, limit: 5)
end
Async { client.value.set("random_key", "a_key") }.wait
result = []
55.times.map { Thread.new {
Async { result.push client.value.get("random_key") }
}}.map(&:value).map(&:wait)
puts result
end
# errors and deadlocks
# Don't share async client between threads!
def async_thread_share
endpoint = Async::IO::Endpoint.tcp('localhost', $redis_port)
client = Async::Redis::Client.new(endpoint, limit: 5)
Async { client.set("random_key", "a_key") }.wait
result = []
55.times.map { Thread.new {
Async { result.push client.get("random_key") }
}}.map(&:value).map(&:wait)
puts result
end
# works fine
def sync_thread_share
client = Redis.new({url: 'redis:localhost:#{$redis_port}'})
client.set("random_key", "a_key")
result = []
5.times.map { Thread.new {
result.push client.get("random_key")
}}.each(&:join)
puts result
end
method = ARGV.first || "async_thread_isolate"
send(method)
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment