mirror of
https://github.com/apple/foundationdb.git
synced 2025-06-01 10:45:56 +08:00
Python now blocks on a future in Python rather than in native code to preserve Python's signal handling functionality. In particular, this means that ctrl-c will work in the REPL.
This commit is contained in:
parent
4c0481da40
commit
8960670694
@ -30,6 +30,7 @@ import datetime
|
||||
import platform
|
||||
import os
|
||||
import sys
|
||||
import multiprocessing
|
||||
|
||||
from fdb import six
|
||||
|
||||
@ -38,6 +39,8 @@ _network_thread_reentrant_lock = threading.RLock()
|
||||
|
||||
_open_file = open
|
||||
|
||||
_thread_local_storage = threading.local()
|
||||
|
||||
import weakref
|
||||
|
||||
|
||||
@ -593,7 +596,20 @@ class Future(_FDBBase):
|
||||
return bool(self.capi.fdb_future_is_ready(self.fpointer))
|
||||
|
||||
def block_until_ready(self):
|
||||
self.capi.fdb_future_block_until_ready(self.fpointer)
|
||||
# Checking readiness is faster than using the callback, so it saves us time if we are already
|
||||
# ready. It also doesn't add much to the cost of this function
|
||||
if not self.is_ready():
|
||||
# Blocking in the native client from the main thread prevents Python from handling signals.
|
||||
# To avoid that behavior, we implement the blocking in Python using semaphores and on_ready.
|
||||
# Using a Semaphore is faster than an Event, and we create only one per thread to avoid the
|
||||
# cost of creating one every time.
|
||||
semaphore = getattr(_thread_local_storage, 'future_block_semaphore', None)
|
||||
if semaphore is None:
|
||||
semaphore = multiprocessing.Semaphore(0)
|
||||
_thread_local_storage.future_block_semaphore = semaphore
|
||||
|
||||
self.on_ready(lambda self: semaphore.release())
|
||||
semaphore.acquire()
|
||||
|
||||
def on_ready(self, callback):
|
||||
def cb_and_delref(ignore):
|
||||
|
Loading…
x
Reference in New Issue
Block a user