Sha256: 574d2156b456ccf763da87c5e4fa2a57c3b140222a1674a4d4b580659ec0cf76

Contents?: true

Size: 1.35 KB

Versions: 2

Compression:

Stored size: 1.35 KB

Contents

# frozen_string_literal: true

# Released under the MIT License.
# Copyright, 2023, by Samuel Williams.

require 'async'

require_relative 'variable'

module Async
	module Actor
		class Proxy < BasicObject
			class Finalizer
				def initialize(queue, thread)
					@queue = queue
					@thread = thread
				end
				
				def call(id)
					@queue.close
					@thread.join
				end
			end
			
			def initialize(target)
				@target = target
				
				@queue = ::Thread::Queue.new
				@thread = __start__
				
				# Define a finalizer to ensure the thread is closed:
				::ObjectSpace.define_finalizer(self, Finalizer.new(@queue, @thread))
			end
			
			# @parameter return_value [Symbol] One of :ignore, :promise or :wait.
			def method_missing(*arguments, return_value: :wait, **options, &block)
				unless return_value == :ignore
					result = Variable.new
				end
				
				@queue.push([arguments, options, block, result])
				
				if return_value == :promise
					return result
				else
					return result&.get
				end
			end
			
			protected
			
			def __start__
				::Thread.new do
					::Kernel.Sync do |task|
						while operation = @queue.pop
							task.async do
								arguments, options, block, result = operation
								Variable.fulfill(result) do
									@target.public_send(*arguments, **options, &block)
								end
							end
						end
					end
				end
			end
		end
	end
end

Version data entries

2 entries across 2 versions & 1 rubygems

Version Path
async-actor-0.1.1 lib/async/actor/proxy.rb
async-actor-0.1.0 lib/async/actor/proxy.rb