diff --git a/python/ray/actor.py b/python/ray/actor.py index 6accf35c0..a03319074 100644 --- a/python/ray/actor.py +++ b/python/ray/actor.py @@ -95,6 +95,8 @@ class ActorMethod(object): # actor method handles to remote functions. if hardref: self._actor_hard_ref = actor + else: + self._actor_hard_ref = None def __call__(self, *args, **kwargs): raise Exception("Actor methods cannot be called directly. Instead " @@ -110,7 +112,7 @@ class ActorMethod(object): num_return_vals = self._num_return_vals def invocation(args, kwargs): - actor = self._actor_ref() + actor = self._actor_hard_ref or self._actor_ref() if actor is None: raise RuntimeError("Lost reference to actor") return actor._actor_method_call( @@ -615,9 +617,13 @@ class ActorHandle(object): self._ray_class_name) return if worker.connected and self._ray_original_handle: - # TODO(rkn): Should we be passing in the actor cursor as a - # dependency here? - self.__ray_terminate__.remote() + # Note: in py2 the weakref is destroyed prior to calling __del__ + # so we need to set the hardref here briefly + try: + self.__ray_terminate__._actor_hard_ref = self + self.__ray_terminate__.remote() + finally: + self.__ray_terminate__._actor_hard_ref = None @property def _actor_id(self): diff --git a/python/ray/tests/test_basic.py b/python/ray/tests/test_basic.py index ee18e5878..aa6ba0d18 100644 --- a/python/ray/tests/test_basic.py +++ b/python/ray/tests/test_basic.py @@ -805,6 +805,8 @@ def test_keyword_args(ray_start_regular): assert ray.get(f3.remote(4)) == 4 +@pytest.mark.skipif( + sys.version_info < (3, 0), reason="This test requires Python 3.") @pytest.mark.parametrize( "ray_start_regular", [{ "local_mode": True @@ -840,6 +842,8 @@ def test_args_starkwargs(ray_start_regular): ray.get(remote_test_function.remote(local_method, actor_method)) +@pytest.mark.skipif( + sys.version_info < (3, 0), reason="This test requires Python 3.") @pytest.mark.parametrize( "ray_start_regular", [{ "local_mode": True @@ -881,6 +885,8 @@ def test_args_named_and_star(ray_start_regular): ray.get(remote_test_function.remote(local_method, actor_method)) +@pytest.mark.skipif( + sys.version_info < (3, 0), reason="This test requires Python 3.") @pytest.mark.parametrize( "ray_start_regular", [{ "local_mode": True