[Java] Format ray java code (#13056)

This commit is contained in:
chaokunyang
2020-12-29 10:36:16 +08:00
committed by GitHub
parent cc1c2c3dc9
commit d1dd3410c8
422 changed files with 4384 additions and 5035 deletions
@@ -63,5 +63,4 @@ public class ActorPressTest extends RayBenchmarkTest {
return remoteResult;
}
}
}
@@ -37,5 +37,4 @@ public class MaxPressureTest extends RayBenchmarkTest {
public boolean checkResult(Object o) {
return (int) o == 0;
}
}
@@ -20,24 +20,30 @@ public class MicroBenchmarks {
}
final long duration = System.nanoTime() - start;
LOGGER.info(
"Benchmark \"{}\" finished, repeated {} times, total duration {} ms," +
" average duration {} ns.",
name, numRepeats, duration / 1_000_000, duration / numRepeats);
"Benchmark \"{}\" finished, repeated {} times, total duration {} ms,"
+ " average duration {} ns.",
name,
numRepeats,
duration / 1_000_000,
duration / numRepeats);
}
/**
* Benchmark task submission.
*
* Note, this benchmark is supposed to measure the elapased time in Java worker, we should disable
* submitting tasks to raylet in `raylet_client.cc` before running this benchmark.
* <p>Note, this benchmark is supposed to measure the elapased time in Java worker, we should
* disable submitting tasks to raylet in `raylet_client.cc` before running this benchmark.
*/
public static void benchmarkTaskSubmission() {
final int numRepeats = 1_000_000;
Ray.init();
try {
time(() -> {
Ray.task(MicroBenchmarks::simpleFunction).remote();
}, numRepeats, "task submission");
time(
() -> {
Ray.task(MicroBenchmarks::simpleFunction).remote();
},
numRepeats,
"task submission");
} finally {
Ray.shutdown();
}
@@ -7,17 +7,17 @@ public class PressureTestParameter implements Serializable {
private static final long serialVersionUID = -52054601722982473L;
private Integer clientNum = 1; //number of test client
private Integer clientNum = 1; // number of test client
private PressureTestType pressureTestType = PressureTestType.RATE_LIMITER; //pressure test type
private PressureTestType pressureTestType = PressureTestType.RATE_LIMITER; // pressure test type
private Integer totalNum = 1; //total number of task under the mode of MAX
private Integer totalNum = 1; // total number of task under the mode of MAX
private Integer totalQps = 1; //total qps of task under the mode of RATE_LIMITER
private Integer totalQps = 1; // total qps of task under the mode of RATE_LIMITER
private Integer duration = 1; //duration of the pressure test under the mode of RATE_LIMITER
private Integer duration = 1; // duration of the pressure test under the mode of RATE_LIMITER
private RayBenchmarkTest rayBenchmarkTest; //reference of current test case instance
private RayBenchmarkTest rayBenchmarkTest; // reference of current test case instance
// reference of the Actor, if only test remote funtion it could be null
private ActorHandle rayActor;
@@ -1,7 +1,6 @@
package io.ray.benchmark;
public enum PressureTestType {
SINGLE_LATENCY,
RATE_LIMITER,
MAX
@@ -18,7 +18,7 @@ import org.testng.Assert;
public abstract class RayBenchmarkTest<T> extends BaseTest implements Serializable {
private static final Logger LOGGER = LoggerFactory.getLogger(RayBenchmarkTest.class);
//not thread safe ,but we only have one thread here
// not thread safe ,but we only have one thread here
public static final DecimalFormat df = new DecimalFormat("00.00");
private static final long serialVersionUID = 416045641835782523L;
@@ -29,7 +29,7 @@ public abstract class RayBenchmarkTest<T> extends BaseTest implements Serializab
PressureTestType pressureTestType = pressureTestParameter.getPressureTestType();
RayBenchmarkTest rayBenchmarkTest = pressureTestParameter.getRayBenchmarkTest();
int clientNum = pressureTestParameter.getClientNum();
//SimpleDateFormat formatter = new SimpleDateFormat("yyyy-MM-dd HH:mm:ss");
// SimpleDateFormat formatter = new SimpleDateFormat("yyyy-MM-dd HH:mm:ss");
int len;
String logPrefix;
RateLimiter rateLimiter = null;
@@ -70,7 +70,6 @@ public abstract class RayBenchmarkTest<T> extends BaseTest implements Serializab
} catch (Exception e) {
LOGGER.error("singleClient", e);
return null;
}
}
@@ -151,5 +150,4 @@ public abstract class RayBenchmarkTest<T> extends BaseTest implements Serializab
pressureTestParameter.setPressureTestType(PressureTestType.MAX);
notSinglePressTest(pressureTestParameter);
}
}
@@ -9,9 +9,10 @@ import java.util.stream.Collectors;
/**
* This class contains demo code of the Ray introduction doc
* (https://docs.ray.io/en/master/index.html and https://docs.ray.io/en/master/ray-overview/index.html).
* (https://docs.ray.io/en/master/index.html and
* https://docs.ray.io/en/master/ray-overview/index.html).
*
* Please keep them in sync.
* <p>Please keep them in sync.
*/
public class RayDemo {
@@ -43,7 +44,7 @@ public class RayDemo {
objectRefList.add(Ray.task(RayDemo::square, i).remote());
}
// Get the actual results of the tasks with `get`.
System.out.println(Ray.get(objectRefList)); // [0, 1, 4, 9]
System.out.println(Ray.get(objectRefList)); // [0, 1, 4, 9]
}
{
@@ -60,10 +61,11 @@ public class RayDemo {
counter.task(Counter::increment).remote();
}
// Invoke the `read` method on each actor, and print the results.
List<ObjectRef<Integer>> objectRefList = counters.stream()
.map(counter -> counter.task(Counter::read).remote())
.collect(Collectors.toList());
System.out.println(Ray.get(objectRefList)); // [1, 1, 1, 1]
List<ObjectRef<Integer>> objectRefList =
counters.stream()
.map(counter -> counter.task(Counter::read).remote())
.collect(Collectors.toList());
System.out.println(Ray.get(objectRefList)); // [1, 1, 1, 1]
}
}
}
@@ -2,15 +2,15 @@ package io.ray.docdemo;
import io.ray.api.ActorHandle;
import io.ray.api.Ray;
import io.ray.docdemo.WalkthroughDemo.Counter;
import java.util.Optional;
import java.util.concurrent.TimeUnit;
import org.testng.Assert;
/**
* This class contains demo code of the Ray core Using Actors doc (https://docs.ray.io/en/master/actors.html).
* This class contains demo code of the Ray core Using Actors doc
* (https://docs.ray.io/en/master/actors.html).
*
* Please keep them in sync.
* <p>Please keep them in sync.
*/
public class UsingActorsDemo {
@@ -40,9 +40,7 @@ public class UsingActorsDemo {
}
}
public static class GpuActor {
}
public static class GpuActor {}
public static class MyRayApp {
@@ -82,12 +80,12 @@ public class UsingActorsDemo {
}
{
ActorHandle<Counter> a1 = Ray.actor(Counter::new).setResource("CPU", 1.0)
.setResource("Custom1", 1.0).remote();
ActorHandle<Counter> a2 = Ray.actor(Counter::new).setResource("CPU", 2.0)
.setResource("Custom2", 1.0).remote();
ActorHandle<Counter> a3 = Ray.actor(Counter::new).setResource("CPU", 3.0)
.setResource("Custom3", 1.0).remote();
ActorHandle<Counter> a1 =
Ray.actor(Counter::new).setResource("CPU", 1.0).setResource("Custom1", 1.0).remote();
ActorHandle<Counter> a2 =
Ray.actor(Counter::new).setResource("CPU", 2.0).setResource("Custom2", 1.0).remote();
ActorHandle<Counter> a3 =
Ray.actor(Counter::new).setResource("CPU", 3.0).setResource("Custom3", 1.0).remote();
}
{
@@ -11,9 +11,10 @@ import java.util.concurrent.TimeUnit;
import org.testng.Assert;
/**
* This class contains demo code of the Ray core walkthrough doc (https://docs.ray.io/en/master/walkthrough.html).
* This class contains demo code of the Ray core walkthrough doc
* (https://docs.ray.io/en/master/walkthrough.html).
*
* Please keep them in sync.
* <p>Please keep them in sync.
*/
public class WalkthroughDemo {
@@ -79,9 +80,9 @@ public class WalkthroughDemo {
List<Integer> results = Ray.get(objectRefs);
Assert.assertEquals(results, ImmutableList.of(0, 1, 2));
WaitResult<Integer> waitResult = Ray.wait(objectRefs, /*num_returns=*/1, /*timeoutMs=*/1000);
System.out.println(waitResult.getReady()); // List of ready objects.
System.out.println(waitResult.getUnready()); // list of unready objects.
WaitResult<Integer> waitResult = Ray.wait(objectRefs, /*num_returns=*/ 1, /*timeoutMs=*/ 1000);
System.out.println(waitResult.getReady()); // List of ready objects.
System.out.println(waitResult.getUnready()); // list of unready objects.
}
// A regular Java class.
@@ -28,9 +28,7 @@ public class ActorConcurrentCallTest extends BaseTest {
public void testConcurrentCall() {
ActorHandle<ConcurrentActor> actor =
Ray.actor(ConcurrentActor::new)
.setMaxConcurrency(3)
.remote();
Ray.actor(ConcurrentActor::new).setMaxConcurrency(3).remote();
ObjectRef<String> obj1 = actor.task(ConcurrentActor::countDown).remote();
ObjectRef<String> obj2 = actor.task(ConcurrentActor::countDown).remote();
ObjectRef<String> obj3 = actor.task(ConcurrentActor::countDown).remote();
@@ -40,5 +38,4 @@ public class ActorConcurrentCallTest extends BaseTest {
Assert.assertEquals(obj2.get(), "ok");
Assert.assertEquals(obj3.get(), "ok");
}
}
@@ -70,4 +70,3 @@ public class ActorRestartTest extends BaseTest {
}
}
}
@@ -57,14 +57,13 @@ public class ActorTest extends BaseTest {
// Test calling an actor
Assert.assertEquals(Integer.valueOf(1), actor.task(Counter::getValue).remote().get());
actor.task(Counter::increase, 1).remote();
Assert.assertEquals(Integer.valueOf(3),
actor.task(Counter::increaseAndGet, 1).remote().get());
Assert.assertEquals(Integer.valueOf(3), actor.task(Counter::increaseAndGet, 1).remote().get());
}
/**
* Test getting an object twice from the local memory store.
*
* Objects are stored in core worker's local memory. And it will be removed after the first
* <p>Objects are stored in core worker's local memory. And it will be removed after the first
* get. To enable getting it twice, we cache the object in `RayObjectImpl`.
*/
public void testGetObjectTwice() {
@@ -78,7 +77,8 @@ public class ActorTest extends BaseTest {
public void testCallActorWithLargeObject() {
ActorHandle<Counter> actor = Ray.actor(Counter::new, 1).remote();
TestUtils.LargeObject largeObject = new TestUtils.LargeObject();
Assert.assertEquals(Integer.valueOf(largeObject.data.length + 1),
Assert.assertEquals(
Integer.valueOf(largeObject.data.length + 1),
actor.task(Counter::accessLargeObject, largeObject).remote().get());
}
@@ -111,13 +111,17 @@ public class ActorTest extends BaseTest {
public void testPassActorAsParameter() {
ActorHandle<Counter> actor = Ray.actor(Counter::new, 0).remote();
Assert.assertEquals(Integer.valueOf(1),
Assert.assertEquals(
Integer.valueOf(1),
Ray.task(ActorTest::testActorAsFirstParameter, actor, 1).remote().get());
Assert.assertEquals(Integer.valueOf(11),
Assert.assertEquals(
Integer.valueOf(11),
Ray.task(ActorTest::testActorAsSecondParameter, 10, actor).remote().get());
Assert.assertEquals(Integer.valueOf(111),
Ray.task(ActorTest::testActorAsFieldOfParameter,
Collections.singletonList(actor), 100).remote().get());
Assert.assertEquals(
Integer.valueOf(111),
Ray.task(ActorTest::testActorAsFieldOfParameter, Collections.singletonList(actor), 100)
.remote()
.get());
}
// This test case follows `test_internal_free` in `python/ray/tests/test_advanced.py`.
@@ -150,7 +154,6 @@ public class ActorTest extends BaseTest {
default String interfaceName() {
return ChildClassInterface.class.getName();
}
}
public static class ChildClass extends Counter implements ChildClassInterface {
@@ -163,7 +166,6 @@ public class ActorTest extends BaseTest {
public void increase(int delta) {
super.increase(-delta);
}
}
@Test(groups = {"cluster"})
@@ -176,8 +178,8 @@ public class ActorTest extends BaseTest {
counter.task(Counter::increase, 10).remote();
Assert.assertEquals(counter.task(Counter::getValue).remote().get(), Integer.valueOf(80));
// test interface default methods
Assert.assertEquals(counter.task(ChildClassInterface::interfaceName).remote().get(),
Assert.assertEquals(
counter.task(ChildClassInterface::interfaceName).remote().get(),
ChildClassInterface.class.getName());
}
}
@@ -8,8 +8,8 @@ import org.testng.annotations.ITestAnnotation;
public class AnnotationTransformer implements IAnnotationTransformer {
@Override
public void transform(ITestAnnotation annotation, Class testClass,
Constructor testConstructor, Method testMethod) {
public void transform(
ITestAnnotation annotation, Class testClass, Constructor testConstructor, Method testMethod) {
annotation.setRetryAnalyzer(RetryAnalyzer.class);
}
}
@@ -16,8 +16,8 @@ public class BaseTaskOptionsTest {
@Test
public void testLegalResources() {
Map<String, Double> resources = ImmutableMap.of(
"CPU", 0.5, "GPU", 3.0, "memory", 1024.0, "A", 4294967296.0);
Map<String, Double> resources =
ImmutableMap.of("CPU", 0.5, "GPU", 3.0, "memory", 1024.0, "A", 4294967296.0);
new MockActorCreationOptions(resources);
}
@@ -45,5 +45,4 @@ public class BaseTaskOptionsTest {
Map<String, Double> resources = ImmutableMap.of("CPU", 3.5);
new MockActorCreationOptions(resources);
}
}
}
@@ -18,5 +18,4 @@ public class BaseTest {
public void tearDownBase() {
Ray.shutdown();
}
}
@@ -22,8 +22,8 @@ import org.testng.annotations.Test;
public class ClassLoaderTest extends BaseTest {
private final String codeSearchPath = FileUtils.getTempDirectoryPath()
+ "/ray_test/ClassLoaderTest";
private final String codeSearchPath =
FileUtils.getTempDirectoryPath() + "/ray_test/ClassLoaderTest";
@BeforeClass
public void setUp() {
@@ -47,40 +47,41 @@ public class ClassLoaderTest extends BaseTest {
// In this test case the class is expected to be loaded from the job code search path,
// so we need to put the compiled class file into the job code search path and load it
// later.
String testJavaFile = ""
+ "import java.lang.management.ManagementFactory;\n"
+ "import java.lang.management.RuntimeMXBean;\n"
+ "\n"
+ "public class ClassLoaderTester {\n"
+ "\n"
+ " static volatile int value;\n"
+ "\n"
+ " public int getPid() {\n"
+ " RuntimeMXBean runtime = ManagementFactory.getRuntimeMXBean();\n"
+ " String name = runtime.getName();\n"
+ " int index = name.indexOf(\"@\");\n"
+ " if (index != -1) {\n"
+ " return Integer.parseInt(name.substring(0, index));\n"
+ " } else {\n"
+ " throw new RuntimeException(\"parse pid error:\" + name);\n"
+ " }\n"
+ " }\n"
+ "\n"
+ " public int increase() throws InterruptedException {\n"
+ " return increaseInternal();\n"
+ " }\n"
+ "\n"
+ " public static synchronized int increaseInternal() throws InterruptedException {\n"
+ " int oldValue = value;\n"
+ " Thread.sleep(10 * 1000);\n"
+ " value = oldValue + 1;\n"
+ " return value;\n"
+ " }\n"
+ "\n"
+ " public int getClassLoaderHashCode() {\n"
+ " return this.getClass().getClassLoader().hashCode();\n"
+ " }\n"
+ "}";
String testJavaFile =
""
+ "import java.lang.management.ManagementFactory;\n"
+ "import java.lang.management.RuntimeMXBean;\n"
+ "\n"
+ "public class ClassLoaderTester {\n"
+ "\n"
+ " static volatile int value;\n"
+ "\n"
+ " public int getPid() {\n"
+ " RuntimeMXBean runtime = ManagementFactory.getRuntimeMXBean();\n"
+ " String name = runtime.getName();\n"
+ " int index = name.indexOf(\"@\");\n"
+ " if (index != -1) {\n"
+ " return Integer.parseInt(name.substring(0, index));\n"
+ " } else {\n"
+ " throw new RuntimeException(\"parse pid error:\" + name);\n"
+ " }\n"
+ " }\n"
+ "\n"
+ " public int increase() throws InterruptedException {\n"
+ " return increaseInternal();\n"
+ " }\n"
+ "\n"
+ " public static synchronized int increaseInternal() throws InterruptedException {\n"
+ " int oldValue = value;\n"
+ " Thread.sleep(10 * 1000);\n"
+ " value = oldValue + 1;\n"
+ " return value;\n"
+ " }\n"
+ "\n"
+ " public int getClassLoaderHashCode() {\n"
+ " return this.getClass().getClassLoader().hashCode();\n"
+ " }\n"
+ "}";
// Write the demo java file to the job code search path.
String javaFilePath = codeSearchPath + "/ClassLoaderTester.java";
@@ -88,54 +89,60 @@ public class ClassLoaderTest extends BaseTest {
// Compile the java file.
JavaCompiler compiler = ToolProvider.getSystemJavaCompiler();
int result = compiler.run(null, null, null, "-d",
codeSearchPath, javaFilePath);
int result = compiler.run(null, null, null, "-d", codeSearchPath, javaFilePath);
if (result != 0) {
throw new RuntimeException("Couldn't compile ClassLoaderTester.java.");
}
FunctionDescriptor constructor = new JavaFunctionDescriptor(
"ClassLoaderTester", "<init>", "()V");
FunctionDescriptor constructor =
new JavaFunctionDescriptor("ClassLoaderTester", "<init>", "()V");
ActorHandle<?> actor1 = createActor(constructor);
FunctionDescriptor getPid = new JavaFunctionDescriptor(
"ClassLoaderTester", "getPid", "()I");
int pid = this.<Integer>callActorFunction(actor1, getPid, new Object[0],
Optional.of(Integer.class)).get();
FunctionDescriptor getPid = new JavaFunctionDescriptor("ClassLoaderTester", "getPid", "()I");
int pid =
this.<Integer>callActorFunction(actor1, getPid, new Object[0], Optional.of(Integer.class))
.get();
ActorHandle<?> actor2;
while (true) {
// Create another actor which share the same process of actor 1.
actor2 = createActor(constructor);
int actor2Pid = this.<Integer>callActorFunction(actor2, getPid, new Object[0],
Optional.of(Integer.class)).get();
int actor2Pid =
this.<Integer>callActorFunction(actor2, getPid, new Object[0], Optional.of(Integer.class))
.get();
if (actor2Pid == pid) {
break;
}
}
FunctionDescriptor getClassLoaderHashCode = new JavaFunctionDescriptor(
"ClassLoaderTester", "getClassLoaderHashCode", "()I");
ObjectRef<Integer> hashCode1 = callActorFunction(actor1, getClassLoaderHashCode, new Object[0],
Optional.of(Integer.class));
ObjectRef<Integer> hashCode2 = callActorFunction(actor2, getClassLoaderHashCode, new Object[0],
Optional.of(Integer.class));
FunctionDescriptor getClassLoaderHashCode =
new JavaFunctionDescriptor("ClassLoaderTester", "getClassLoaderHashCode", "()I");
ObjectRef<Integer> hashCode1 =
callActorFunction(
actor1, getClassLoaderHashCode, new Object[0], Optional.of(Integer.class));
ObjectRef<Integer> hashCode2 =
callActorFunction(
actor2, getClassLoaderHashCode, new Object[0], Optional.of(Integer.class));
Assert.assertEquals(hashCode1.get(), hashCode2.get());
FunctionDescriptor increase = new JavaFunctionDescriptor(
"ClassLoaderTester", "increase", "()I");
ObjectRef<Integer> value1 = callActorFunction(actor1, increase, new Object[0],
Optional.of(Integer.class));
ObjectRef<Integer> value2 = callActorFunction(actor2, increase, new Object[0],
Optional.of(Integer.class));
FunctionDescriptor increase =
new JavaFunctionDescriptor("ClassLoaderTester", "increase", "()I");
ObjectRef<Integer> value1 =
callActorFunction(actor1, increase, new Object[0], Optional.of(Integer.class));
ObjectRef<Integer> value2 =
callActorFunction(actor2, increase, new Object[0], Optional.of(Integer.class));
Assert.assertNotEquals(value1.get(), value2.get());
}
private ActorHandle<?> createActor(FunctionDescriptor functionDescriptor)
throws Exception {
Method createActorMethod = AbstractRayRuntime.class.getDeclaredMethod("createActorImpl",
FunctionDescriptor.class, Object[].class, ActorCreationOptions.class);
private ActorHandle<?> createActor(FunctionDescriptor functionDescriptor) throws Exception {
Method createActorMethod =
AbstractRayRuntime.class.getDeclaredMethod(
"createActorImpl",
FunctionDescriptor.class,
Object[].class,
ActorCreationOptions.class);
createActorMethod.setAccessible(true);
return (ActorHandle<?>) createActorMethod
.invoke(TestUtils.getUnderlyingRuntime(), functionDescriptor, new Object[0], null);
return (ActorHandle<?>)
createActorMethod.invoke(
TestUtils.getUnderlyingRuntime(), functionDescriptor, new Object[0], null);
}
private <T> ObjectRef<T> callActorFunction(
@@ -144,10 +151,16 @@ public class ClassLoaderTest extends BaseTest {
Object[] args,
Optional<Class<?>> returnType)
throws Exception {
Method callActorFunctionMethod = AbstractRayRuntime.class.getDeclaredMethod("callActorFunction",
BaseActorHandle.class, FunctionDescriptor.class, Object[].class, Optional.class);
Method callActorFunctionMethod =
AbstractRayRuntime.class.getDeclaredMethod(
"callActorFunction",
BaseActorHandle.class,
FunctionDescriptor.class,
Object[].class,
Optional.class);
callActorFunctionMethod.setAccessible(true);
return (ObjectRef<T>) callActorFunctionMethod
.invoke(TestUtils.getUnderlyingRuntime(), rayActor, functionDescriptor, args, returnType);
return (ObjectRef<T>)
callActorFunctionMethod.invoke(
TestUtils.getUnderlyingRuntime(), rayActor, functionDescriptor, args, returnType);
}
}
@@ -32,26 +32,25 @@ public class CrossLanguageInvocationTest extends BaseTest {
@BeforeClass
public void beforeClass() {
// Delete and re-create the temp dir.
File tempDir = new File(
System.getProperty("java.io.tmpdir") + File.separator + "ray_cross_language_test");
File tempDir =
new File(System.getProperty("java.io.tmpdir") + File.separator + "ray_cross_language_test");
FileUtils.deleteQuietly(tempDir);
tempDir.mkdirs();
tempDir.deleteOnExit();
// Write the test Python file to the temp dir.
InputStream in = CrossLanguageInvocationTest.class
.getResourceAsStream("/" + PYTHON_MODULE + ".py");
File pythonFile = new File(
tempDir.getAbsolutePath() + File.separator + PYTHON_MODULE + ".py");
InputStream in =
CrossLanguageInvocationTest.class.getResourceAsStream("/" + PYTHON_MODULE + ".py");
File pythonFile = new File(tempDir.getAbsolutePath() + File.separator + PYTHON_MODULE + ".py");
try {
FileUtils.copyInputStreamToFile(in, pythonFile);
} catch (IOException e) {
throw new RuntimeException(e);
}
System.setProperty("ray.job.code-search-path",
System.getProperty("java.class.path") + File.pathSeparator
+ tempDir.getAbsolutePath());
System.setProperty(
"ray.job.code-search-path",
System.getProperty("java.class.path") + File.pathSeparator + tempDir.getAbsolutePath());
}
@AfterClass
@@ -61,48 +60,49 @@ public class CrossLanguageInvocationTest extends BaseTest {
@Test
public void testCallingPythonFunction() {
Object[] inputs = new Object[]{
true, // Boolean
Byte.MAX_VALUE, // Byte
Short.MAX_VALUE, // Short
Integer.MAX_VALUE, // Integer
Long.MAX_VALUE, // Long
// BigInteger can support max value of 2^64-1, please refer to:
// https://github.com/msgpack/msgpack/blob/master/spec.md#int-format-family
// If BigInteger larger than 2^64-1, the value can only be transferred among Java workers.
BigInteger.valueOf(Long.MAX_VALUE), // BigInteger
"Hello World!", // String
1.234f, // Float
1.234, // Double
"example binary".getBytes()}; // byte[]
Object[] inputs =
new Object[] {
true, // Boolean
Byte.MAX_VALUE, // Byte
Short.MAX_VALUE, // Short
Integer.MAX_VALUE, // Integer
Long.MAX_VALUE, // Long
// BigInteger can support max value of 2^64-1, please refer to:
// https://github.com/msgpack/msgpack/blob/master/spec.md#int-format-family
// If BigInteger larger than 2^64-1, the value can only be transferred among Java workers.
BigInteger.valueOf(Long.MAX_VALUE), // BigInteger
"Hello World!", // String
1.234f, // Float
1.234, // Double
"example binary".getBytes()
}; // byte[]
for (Object o : inputs) {
ObjectRef res = Ray.task(
PyFunction.of(PYTHON_MODULE, "py_return_input", o.getClass()),
o).remote();
ObjectRef res =
Ray.task(PyFunction.of(PYTHON_MODULE, "py_return_input", o.getClass()), o).remote();
Assert.assertEquals(res.get(), o);
}
// null
{
Object input = null;
ObjectRef<Object> res = Ray.task(
PyFunction.of(PYTHON_MODULE, "py_return_input", Object.class), input).remote();
ObjectRef<Object> res =
Ray.task(PyFunction.of(PYTHON_MODULE, "py_return_input", Object.class), input).remote();
Object r = res.get();
Assert.assertEquals(r, input);
}
// array
{
int[] input = new int[]{1, 2};
ObjectRef<int[]> res = Ray.task(
PyFunction.of(PYTHON_MODULE, "py_return_input", int[].class), input).remote();
int[] input = new int[] {1, 2};
ObjectRef<int[]> res =
Ray.task(PyFunction.of(PYTHON_MODULE, "py_return_input", int[].class), input).remote();
int[] r = res.get();
Assert.assertEquals(r, input);
}
// array of Object
{
Object[] input = new Object[]{1, 2.3f, 4.56, "789", "10".getBytes(), null, true,
new int[]{1, 2}};
ObjectRef<Object[]> res = Ray.task(
PyFunction.of(PYTHON_MODULE, "py_return_input", Object[].class), input).remote();
Object[] input =
new Object[] {1, 2.3f, 4.56, "789", "10".getBytes(), null, true, new int[] {1, 2}};
ObjectRef<Object[]> res =
Ray.task(PyFunction.of(PYTHON_MODULE, "py_return_input", Object[].class), input).remote();
Object[] r = res.get();
// If we tell the value type is Object, then all numbers will be Number type.
Assert.assertEquals(((Number) r[0]).intValue(), input[0]);
@@ -124,39 +124,47 @@ public class CrossLanguageInvocationTest extends BaseTest {
}
// Unsupported types, all Java specific types, e.g. List / Map...
{
Assert.expectThrows(Exception.class, () -> {
List<Integer> input = Arrays.asList(1, 2);
ObjectRef<List<Integer>> res = Ray.task(
PyFunction.of(PYTHON_MODULE, "py_return_input",
(Class<List<Integer>>) input.getClass()), input).remote();
List<Integer> r = res.get();
Assert.assertEquals(r, input);
});
Assert.expectThrows(
Exception.class,
() -> {
List<Integer> input = Arrays.asList(1, 2);
ObjectRef<List<Integer>> res =
Ray.task(
PyFunction.of(
PYTHON_MODULE,
"py_return_input",
(Class<List<Integer>>) input.getClass()),
input)
.remote();
List<Integer> r = res.get();
Assert.assertEquals(r, input);
});
}
}
@Test
public void testPythonCallJavaFunction() {
ObjectRef<String> res = Ray.task(PyFunction.of(
PYTHON_MODULE, "py_func_call_java_function", String.class)).remote();
ObjectRef<String> res =
Ray.task(PyFunction.of(PYTHON_MODULE, "py_func_call_java_function", String.class)).remote();
Assert.assertEquals(res.get(), "success");
}
@Test
public void testCallingPythonActor() {
PyActorHandle actor = Ray.actor(
PyActorClass.of(PYTHON_MODULE, "Counter"), "1".getBytes()).remote();
ObjectRef<byte[]> res = actor.task(
PyActorMethod.of("increase", byte[].class),
"1".getBytes()).remote();
PyActorHandle actor =
Ray.actor(PyActorClass.of(PYTHON_MODULE, "Counter"), "1".getBytes()).remote();
ObjectRef<byte[]> res =
actor.task(PyActorMethod.of("increase", byte[].class), "1".getBytes()).remote();
Assert.assertEquals(res.get(), "2".getBytes());
}
@Test
public void testPythonCallJavaActor() {
ObjectRef<byte[]> res = Ray.task(
PyFunction.of(PYTHON_MODULE, "py_func_call_java_actor", byte[].class),
"1".getBytes()).remote();
ObjectRef<byte[]> res =
Ray.task(
PyFunction.of(PYTHON_MODULE, "py_func_call_java_actor", byte[].class),
"1".getBytes())
.remote();
Assert.assertEquals(res.get(), "Counter1".getBytes());
}
@@ -164,8 +172,9 @@ public class CrossLanguageInvocationTest extends BaseTest {
public void testPassActorHandleFromPythonToJava() {
// Call a python function which creates a python actor
// and pass the actor handle to callPythonActorHandle.
ObjectRef<byte[]> res = Ray.task(PyFunction.of(
PYTHON_MODULE, "py_func_pass_python_actor_handle", byte[].class)).remote();
ObjectRef<byte[]> res =
Ray.task(PyFunction.of(PYTHON_MODULE, "py_func_pass_python_actor_handle", byte[].class))
.remote();
Assert.assertEquals(res.get(), "3".getBytes());
}
@@ -174,21 +183,21 @@ public class CrossLanguageInvocationTest extends BaseTest {
// Create a java actor, and pass actor handle to python.
ActorHandle<TestActor> javaActor = Ray.actor(TestActor::new, "1".getBytes()).remote();
Preconditions.checkState(javaActor instanceof NativeActorHandle);
ObjectRef<byte[]> res = Ray.task(
PyFunction.of(PYTHON_MODULE,
"py_func_call_java_actor_from_handle",
byte[].class),
javaActor).remote();
ObjectRef<byte[]> res =
Ray.task(
PyFunction.of(PYTHON_MODULE, "py_func_call_java_actor_from_handle", byte[].class),
javaActor)
.remote();
Assert.assertEquals(res.get(), "12".getBytes());
// Create a python actor, and pass actor handle to python.
PyActorHandle pyActor = Ray.actor(
PyActorClass.of(PYTHON_MODULE, "Counter"), "1".getBytes()).remote();
PyActorHandle pyActor =
Ray.actor(PyActorClass.of(PYTHON_MODULE, "Counter"), "1".getBytes()).remote();
Preconditions.checkState(pyActor instanceof NativeActorHandle);
res = Ray.task(
PyFunction.of(PYTHON_MODULE,
"py_func_call_python_actor_from_handle",
byte[].class),
pyActor).remote();
res =
Ray.task(
PyFunction.of(PYTHON_MODULE, "py_func_call_python_actor_from_handle", byte[].class),
pyActor)
.remote();
Assert.assertEquals(res.get(), "3".getBytes());
}
@@ -197,8 +206,8 @@ public class CrossLanguageInvocationTest extends BaseTest {
try {
throw new RayException("Test Exception");
} catch (RayException e) {
String formattedException = org.apache.commons.lang3.exception.ExceptionUtils
.getStackTrace(e);
String formattedException =
org.apache.commons.lang3.exception.ExceptionUtils.getStackTrace(e);
io.ray.runtime.generated.Common.RayException exception =
io.ray.runtime.generated.Common.RayException.parseFrom(e.toBytes());
Assert.assertEquals(exception.getFormattedExceptionString(), formattedException);
@@ -207,8 +216,9 @@ public class CrossLanguageInvocationTest extends BaseTest {
@Test
public void testRaiseExceptionFromPython() {
ObjectRef<Object> res = Ray.task(PyFunction.of(
PYTHON_MODULE, "py_func_python_raise_exception", Object.class)).remote();
ObjectRef<Object> res =
Ray.task(PyFunction.of(PYTHON_MODULE, "py_func_python_raise_exception", Object.class))
.remote();
try {
res.get();
} catch (RuntimeException ex) {
@@ -218,8 +228,8 @@ public class CrossLanguageInvocationTest extends BaseTest {
Assert.assertEquals(e.getLanguage(), Language.PYTHON);
// ex.cause is null.
Assert.assertNull(ex.getCause());
Assert.assertTrue(ex.getMessage().contains("ZeroDivisionError: division by zero"),
ex.getMessage());
Assert.assertTrue(
ex.getMessage().contains("ZeroDivisionError: division by zero"), ex.getMessage());
return;
}
Assert.fail();
@@ -227,15 +237,16 @@ public class CrossLanguageInvocationTest extends BaseTest {
@Test
public void testThrowExceptionFromJava() {
ObjectRef<Object> res = Ray.task(PyFunction.of(
PYTHON_MODULE, "py_func_java_throw_exception", Object.class)).remote();
ObjectRef<Object> res =
Ray.task(PyFunction.of(PYTHON_MODULE, "py_func_java_throw_exception", Object.class))
.remote();
try {
res.get();
} catch (RuntimeException ex) {
final String message = ex.getMessage();
Assert.assertTrue(message.contains("py_func_java_throw_exception"), message);
Assert.assertTrue(message.contains("io.ray.test.CrossLanguageInvocationTest.throwException"),
message);
Assert.assertTrue(
message.contains("io.ray.test.CrossLanguageInvocationTest.throwException"), message);
Assert.assertTrue(message.contains("java.lang.ArithmeticException: / by zero"), message);
return;
}
@@ -244,8 +255,9 @@ public class CrossLanguageInvocationTest extends BaseTest {
@Test
public void testRaiseExceptionFromNestPython() {
ObjectRef<Object> res = Ray.task(
PyFunction.of(PYTHON_MODULE, "py_func_nest_python_raise_exception", Object.class)).remote();
ObjectRef<Object> res =
Ray.task(PyFunction.of(PYTHON_MODULE, "py_func_nest_python_raise_exception", Object.class))
.remote();
try {
res.get();
} catch (RuntimeException ex) {
@@ -261,15 +273,18 @@ public class CrossLanguageInvocationTest extends BaseTest {
@Test
public void testThrowExceptionFromNestJava() {
ObjectRef<Object> res = Ray.task(
PyFunction.of(PYTHON_MODULE, "py_func_nest_java_throw_exception", Object.class)).remote();
ObjectRef<Object> res =
Ray.task(PyFunction.of(PYTHON_MODULE, "py_func_nest_java_throw_exception", Object.class))
.remote();
try {
res.get();
} catch (RuntimeException ex) {
final String message = ex.getMessage();
Assert.assertTrue(message.contains("py_func_nest_java_throw_exception"), message);
Assert.assertEquals(org.apache.commons.lang3.StringUtils
.countMatches(message, "io.ray.runtime.exception.RayTaskException"), 2);
Assert.assertEquals(
org.apache.commons.lang3.StringUtils.countMatches(
message, "io.ray.runtime.exception.RayTaskException"),
2);
Assert.assertTrue(message.contains("py_func_java_throw_exception"), message);
Assert.assertTrue(message.contains("java.lang.ArithmeticException: / by zero"), message);
return;
@@ -279,7 +294,7 @@ public class CrossLanguageInvocationTest extends BaseTest {
public static Object[] pack(int i, String s, double f, Object[] o) {
// This function will be called from test_cross_language_invocation.py
return new Object[]{i, s, f, o};
return new Object[] {i, s, f, o};
}
public static Object returnInput(Object o) {
@@ -308,9 +323,8 @@ public class CrossLanguageInvocationTest extends BaseTest {
public static byte[] callPythonActorHandle(PyActorHandle actor) {
// This function will be called from test_cross_language_invocation.py
ObjectRef<byte[]> res = actor.task(
PyActorMethod.of("increase", byte[].class),
"1".getBytes()).remote();
ObjectRef<byte[]> res =
actor.task(PyActorMethod.of("increase", byte[].class), "1".getBytes()).remote();
Assert.assertEquals(res.get(), "3".getBytes());
return (byte[]) res.get();
}
@@ -321,14 +335,16 @@ public class CrossLanguageInvocationTest extends BaseTest {
}
public static Object throwJavaException() {
ObjectRef<Object> res = Ray.task(
PyFunction.of(PYTHON_MODULE, "py_func_java_throw_exception", Object.class)).remote();
ObjectRef<Object> res =
Ray.task(PyFunction.of(PYTHON_MODULE, "py_func_java_throw_exception", Object.class))
.remote();
return res.get();
}
public static Object raisePythonException() {
ObjectRef<Object> res = Ray.task(
PyFunction.of(PYTHON_MODULE, "py_func_python_raise_exception", Object.class)).remote();
ObjectRef<Object> res =
Ray.task(PyFunction.of(PYTHON_MODULE, "py_func_python_raise_exception", Object.class))
.remote();
return res.get();
}
@@ -16,29 +16,34 @@ public class DynamicResourceTest extends BaseTest {
}
// Dynamic resources not supported yet.
@Test(groups = {"cluster"}, enabled = false)
@Test(
groups = {"cluster"},
enabled = false)
public void testSetResource() {
// Call a task in advance to warm up the cluster to avoid being too slow to start workers.
TestUtils.warmUpCluster();
String resourceName = "A";
ObjectRef<String> obj = Ray.task(DynamicResourceTest::sayHi)
.setResource(resourceName, 10.0)
.remote();
ObjectRef<String> obj =
Ray.task(DynamicResourceTest::sayHi).setResource(resourceName, 10.0).remote();
WaitResult<String> result = Ray.wait(ImmutableList.of(obj), 1, 1000);
Assert.assertEquals(result.getReady().size(), 0);
Ray.setResource(resourceName, 10.0);
boolean resourceReady = TestUtils.waitForCondition(() -> {
List<NodeInfo> nodes = Ray.getRuntimeContext().getAllNodeInfo();
// NOTE: GCS updates node resources asynchronously.
// If we directly get the value of "A" for comparison without check whether "A" exists or not,
// it maybe lead to NPE.
if (nodes.size() != 1 || !nodes.get(0).resources.containsKey(resourceName)) {
return false;
}
return (0 == Double.compare(10.0, nodes.get(0).resources.get(resourceName)));
}, 2000);
boolean resourceReady =
TestUtils.waitForCondition(
() -> {
List<NodeInfo> nodes = Ray.getRuntimeContext().getAllNodeInfo();
// NOTE: GCS updates node resources asynchronously.
// If we directly get the value of "A" for comparison without check whether "A" exists
// or not,
// it maybe lead to NPE.
if (nodes.size() != 1 || !nodes.get(0).resources.containsKey(resourceName)) {
return false;
}
return (0 == Double.compare(10.0, nodes.get(0).resources.get(resourceName)));
},
2000);
Assert.assertTrue(resourceReady);
@@ -46,7 +51,5 @@ public class DynamicResourceTest extends BaseTest {
result = Ray.wait(ImmutableList.of(obj), 1, 1000);
Assert.assertEquals(result.getReady().size(), 1);
Assert.assertEquals(obj.get(), "hi");
}
}
@@ -35,7 +35,7 @@ public class ExitActorTest extends BaseTest {
try {
Field field = TaskExecutor.class.getDeclaredField("actorContextMap");
field.setAccessible(true);
return ((Map<?, ?>)field.get(taskExecutor)).size();
return ((Map<?, ?>) field.get(taskExecutor)).size();
} catch (Exception e) {
throw new RuntimeException(e);
}
@@ -48,8 +48,7 @@ public class ExitActorTest extends BaseTest {
}
public void testExitActor() throws IOException, InterruptedException {
ActorHandle<ExitingActor> actor = Ray.actor(ExitingActor::new)
.setMaxRestarts(10000).remote();
ActorHandle<ExitingActor> actor = Ray.actor(ExitingActor::new).setMaxRestarts(10000).remote();
Assert.assertEquals(1, (int) (actor.task(ExitingActor::incr).remote().get()));
int pid = actor.task(ExitingActor::getPid).remote().get();
Runtime.getRuntime().exec("kill -9 " + pid);
@@ -64,8 +63,7 @@ public class ExitActorTest extends BaseTest {
public void testExitActorInMultiWorker() {
Assert.assertTrue(TestUtils.getNumWorkersPerProcess() > 1);
ActorHandle<ExitingActor> actor1 = Ray.actor(ExitingActor::new)
.setMaxRestarts(10000).remote();
ActorHandle<ExitingActor> actor1 = Ray.actor(ExitingActor::new).setMaxRestarts(10000).remote();
int pid = actor1.task(ExitingActor::getPid).remote().get();
Assert.assertEquals(
1, (int) actor1.task(ExitingActor::getSizeOfActorContextMap).remote().get());
@@ -94,18 +92,19 @@ public class ExitActorTest extends BaseTest {
}
public void testExitActorWithDynamicOptions() {
ActorHandle<ExitingActor> actor = Ray.actor(ExitingActor::new)
.setMaxRestarts(10000)
// Set dummy JVM options to start a worker process with only one worker.
.setJvmOptions(" ")
.remote();
ActorHandle<ExitingActor> actor =
Ray.actor(ExitingActor::new)
.setMaxRestarts(10000)
// Set dummy JVM options to start a worker process with only one worker.
.setJvmOptions(" ")
.remote();
int pid = actor.task(ExitingActor::getPid).remote().get();
Assert.assertTrue(SystemUtil.isProcessAlive(pid));
ObjectRef<Boolean> obj1 = actor.task(ExitingActor::exit).remote();
Assert.assertThrows(RayActorException.class, obj1::get);
// Now the actor shouldn't be reconstructed anymore.
Assert.assertThrows(RayActorException.class,
() -> actor.task(ExitingActor::getPid).remote().get());
Assert.assertThrows(
RayActorException.class, () -> actor.task(ExitingActor::getPid).remote().get());
// Now the worker process should be dead.
Assert.assertTrue(TestUtils.waitForCondition(() -> !SystemUtil.isProcessAlive(pid), 5000));
}
@@ -133,8 +133,8 @@ public class FailureTest extends BaseTest {
}
public void testGetThrowsQuicklyWhenFoundException() {
List<RayFunc0<Integer>> badFunctions = Arrays.asList(FailureTest::badFunc,
FailureTest::badFunc2);
List<RayFunc0<Integer>> badFunctions =
Arrays.asList(FailureTest::badFunc, FailureTest::badFunc2);
TestUtils.warmUpCluster();
for (RayFunc0<Integer> badFunc : badFunctions) {
ObjectRef<Integer> obj1 = Ray.task(badFunc).remote();
@@ -146,29 +146,37 @@ public class FailureTest extends BaseTest {
} catch (RuntimeException e) {
Instant end = Instant.now();
long duration = Duration.between(start, end).toMillis();
Assert.assertTrue(duration < 5000, "Should fail quickly. " +
"Actual execution time: " + duration + " ms.");
Assert.assertTrue(
duration < 5000,
"Should fail quickly. " + "Actual execution time: " + duration + " ms.");
}
}
}
public void testExceptionSerialization() {
RayTaskException ex1 = Assert.expectThrows(RayTaskException.class, () -> {
Ray.put(new RayTaskException("xxx", new RayActorException())).get();
});
RayTaskException ex1 =
Assert.expectThrows(
RayTaskException.class,
() -> {
Ray.put(new RayTaskException("xxx", new RayActorException())).get();
});
Assert.assertEquals(ex1.getCause().getClass(), RayActorException.class);
RayTaskException ex2 = Assert.expectThrows(RayTaskException.class, () -> {
Ray.put(new RayTaskException("xxx", new RayWorkerException())).get();
});
RayTaskException ex2 =
Assert.expectThrows(
RayTaskException.class,
() -> {
Ray.put(new RayTaskException("xxx", new RayWorkerException())).get();
});
Assert.assertEquals(ex2.getCause().getClass(), RayWorkerException.class);
ObjectId objectId = ObjectId.fromRandom();
RayTaskException ex3 = Assert.expectThrows(RayTaskException.class, () -> {
Ray.put(new RayTaskException("xxx", new UnreconstructableException(objectId)))
.get();
});
RayTaskException ex3 =
Assert.expectThrows(
RayTaskException.class,
() -> {
Ray.put(new RayTaskException("xxx", new UnreconstructableException(objectId))).get();
});
Assert.assertEquals(ex3.getCause().getClass(), UnreconstructableException.class);
Assert.assertEquals(((UnreconstructableException) ex3.getCause()).objectId, objectId);
}
}
@@ -46,6 +46,5 @@ public class GcsClientTest extends BaseTest {
for (int i = 2; i < 100; ++i) {
Assert.assertEquals(gcsClient.nextJobId(), JobId.fromInt(i));
}
}
}
@@ -57,13 +57,14 @@ public class GlobalGcTest extends BaseTest {
private void testGlobalGcWhenFull(boolean withPut) {
// Local driver.
WeakReference<LargeObjectWithCyclicRef> localRef = new WeakReference<>(
new LargeObjectWithCyclicRef());
WeakReference<LargeObjectWithCyclicRef> localRef =
new WeakReference<>(new LargeObjectWithCyclicRef());
// Remote workers.
List<ActorHandle<GarbageHolder>> actors = IntStream
.range(0, 2).mapToObj(i -> Ray.actor(GarbageHolder::new).remote())
.collect(Collectors.toList());
List<ActorHandle<GarbageHolder>> actors =
IntStream.range(0, 2)
.mapToObj(i -> Ray.actor(GarbageHolder::new).remote())
.collect(Collectors.toList());
Assert.assertNotNull(localRef.get());
for (ActorHandle<GarbageHolder> actor : actors) {
@@ -82,8 +83,11 @@ public class GlobalGcTest extends BaseTest {
actors.get(0).task(GarbageHolder::returnLargeObject).remote().get();
}
TestUtils.waitForCondition(() -> localRef.get() == null && actors.stream().noneMatch(
a -> a.task(GarbageHolder::hasGarbage).remote().get()), 10 * 1000);
TestUtils.waitForCondition(
() ->
localRef.get() == null
&& actors.stream().noneMatch(a -> a.task(GarbageHolder::hasGarbage).remote().get()),
10 * 1000);
}
public void testGlobalGcWhenFullWithPut() {
@@ -5,9 +5,7 @@ import io.ray.api.Ray;
import org.testng.Assert;
import org.testng.annotations.Test;
/**
* Hello world.
*/
/** Hello world. */
public class HelloWorldTest extends BaseTest {
private static String hello() {
@@ -29,5 +27,4 @@ public class HelloWorldTest extends BaseTest {
String helloWorld = Ray.task(HelloWorldTest::merge, hello, world).remote().get();
Assert.assertEquals("hello,world!", helloWorld);
}
}
@@ -64,7 +64,6 @@ public class JobConfigTest extends BaseTest {
Assert.assertEquals(TestUtils.getNumWorkersPerProcess(), 3);
}
public void testInActor() {
ActorHandle<MyActor> actor = Ray.actor(MyActor::new).remote();
@@ -61,13 +61,10 @@ public class KillActorTest extends BaseTest {
}
private void testKillActor(BiConsumer<ActorHandle<?>, Boolean> kill, boolean noRestart) {
ActorHandle<HangActor> actor = Ray.actor(HangActor::new)
.setMaxRestarts(1)
.remote();
ActorHandle<HangActor> actor = Ray.actor(HangActor::new).setMaxRestarts(1).remote();
ObjectRef<Boolean> result = actor.task(HangActor::hang).remote();
// The actor will hang in this task.
Assert.assertEquals(0,
Ray.wait(ImmutableList.of(result), 1, 500).getReady().size());
Assert.assertEquals(0, Ray.wait(ImmutableList.of(result), 1, 500).getReady().size());
// Kill the actor
kill.accept(actor, noRestart);
@@ -84,8 +81,8 @@ public class KillActorTest extends BaseTest {
if (noRestart) {
// The actor should not be restarted.
Assert.expectThrows(RayActorException.class,
() -> actor.task(HangActor::hang).remote().get());
Assert.expectThrows(
RayActorException.class, () -> actor.task(HangActor::hang).remote().get());
} else {
Assert.assertEquals(actor.task(HangActor::ping).remote().get(), "pong");
}
@@ -100,10 +97,11 @@ public class KillActorTest extends BaseTest {
public void testRemoteKill() {
testKillActor(KillActorTest::remoteKill, false);
testKillActor(KillActorTest::remoteKill, true);
testKillActor((actor, noRestart) -> {
ActorHandle<KillerActor> killer = Ray.actor(KillerActor::new).remote();
killer.task(KillerActor::killWithoutRestart, actor).remote();
}, true);
testKillActor(
(actor, noRestart) -> {
ActorHandle<KillerActor> killer = Ray.actor(KillerActor::new).remote();
killer.task(KillerActor::killWithoutRestart, actor).remote();
},
true);
}
}
@@ -24,14 +24,14 @@ public class MetricTest extends BaseTest {
return value <= other + 1e-5 && value >= other - 1e-5;
}
private MetricConfig initRayMetrics(long timeIntervalMs,
int threadPoolSize,
long shutdownWaitTimeMs) {
MetricConfig config = MetricConfig.builder()
.timeIntervalMs(timeIntervalMs)
.threadPoolSize(threadPoolSize)
.shutdownWaitTimeMs(shutdownWaitTimeMs)
.create();
private MetricConfig initRayMetrics(
long timeIntervalMs, int threadPoolSize, long shutdownWaitTimeMs) {
MetricConfig config =
MetricConfig.builder()
.timeIntervalMs(timeIntervalMs)
.threadPoolSize(threadPoolSize)
.shutdownWaitTimeMs(shutdownWaitTimeMs)
.create();
Metrics.init(config);
return config;
}
@@ -121,8 +121,7 @@ public class MetricTest extends BaseTest {
boundaries.add(10.0);
boundaries.add(15.0);
boundaries.add(12.0);
Histogram histogram = new Histogram("metric_histogram", "histogram", "1pc",
boundaries, tags);
Histogram histogram = new Histogram("metric_histogram", "histogram", "1pc", boundaries, tags);
for (int i = 1; i <= 200; ++i) {
histogram.update(i * 1.0d);
}
@@ -229,5 +228,4 @@ public class MetricTest extends BaseTest {
}
Assert.assertTrue(doubleEqual(histogram.getValue(), 200.0d));
}
}
@@ -73,22 +73,23 @@ public class MultiDriverTest extends BaseTest {
// Wait for drivers to finish.
for (Process driver : drivers) {
driver.waitFor();
Assert.assertEquals(driver.exitValue(), 0,
"The driver exited with code " + driver.exitValue());
Assert.assertEquals(
driver.exitValue(), 0, "The driver exited with code " + driver.exitValue());
}
// Read driver outputs and check for any PID overlap.
Set<Integer> pids = new HashSet<>();
for (Process driver : drivers) {
try (BufferedReader reader = new BufferedReader(
new InputStreamReader(driver.getInputStream()))) {
try (BufferedReader reader =
new BufferedReader(new InputStreamReader(driver.getInputStream()))) {
String line;
int previousSize = pids.size();
while ((line = reader.readLine()) != null) {
if (line.startsWith(PID_LIST_PREFIX)) {
for (String pidString : line.substring(PID_LIST_PREFIX.length()).split(",")) {
// Make sure the PIDs don't overlap.
Assert.assertTrue(pids.add(Integer.valueOf(pidString)),
Assert.assertTrue(
pids.add(Integer.valueOf(pidString)),
"Worker process with PID " + line + " is shared by multiple drivers.");
}
break;
@@ -103,15 +104,16 @@ public class MultiDriverTest extends BaseTest {
private Process startDriver() throws IOException {
RayConfig rayConfig = TestUtils.getRuntime().getRayConfig();
ProcessBuilder builder = new ProcessBuilder(
"java",
"-cp",
System.getProperty("java.class.path"),
"-Dray.address=" + rayConfig.getRedisAddress(),
"-Dray.object-store.socket-name=" + rayConfig.objectStoreSocketName,
"-Dray.raylet.socket-name=" + rayConfig.rayletSocketName,
"-Dray.raylet.node-manager-port=" + String.valueOf(rayConfig.getNodeManagerPort()),
MultiDriverTest.class.getName());
ProcessBuilder builder =
new ProcessBuilder(
"java",
"-cp",
System.getProperty("java.class.path"),
"-Dray.address=" + rayConfig.getRedisAddress(),
"-Dray.object-store.socket-name=" + rayConfig.objectStoreSocketName,
"-Dray.raylet.socket-name=" + rayConfig.rayletSocketName,
"-Dray.raylet.node-manager-port=" + String.valueOf(rayConfig.getNodeManagerPort()),
MultiDriverTest.class.getName());
builder.redirectError(Redirect.INHERIT);
return builder.start();
}
@@ -17,5 +17,4 @@ public class MultiLanguageClusterTest extends BaseTest {
ObjectRef<String> obj = Ray.task(MultiLanguageClusterTest::echo, "hello").remote();
Assert.assertEquals("hello", obj.get());
}
}
@@ -49,13 +49,16 @@ public class MultiThreadingTest extends BaseTest {
public ActorId getCurrentActorId() throws Exception {
final Object[] result = new Object[1];
Thread thread = new Thread(Ray.wrapRunnable(() -> {
try {
result[0] = Ray.getRuntimeContext().getCurrentActorId();
} catch (Exception e) {
result[0] = e;
}
}));
Thread thread =
new Thread(
Ray.wrapRunnable(
() -> {
try {
result[0] = Ray.getRuntimeContext().getCurrentActorId();
} catch (Exception e) {
result[0] = e;
}
}));
thread.start();
thread.join();
if (result[0] instanceof Exception) {
@@ -69,49 +72,59 @@ public class MultiThreadingTest extends BaseTest {
static String testMultiThreading() {
Random random = new Random();
// Test calling normal functions.
runTestCaseInMultipleThreads(() -> {
int arg = random.nextInt();
ObjectRef<Integer> obj = Ray.task(MultiThreadingTest::echo, arg).remote();
Assert.assertEquals(arg, (int) obj.get());
}, LOOP_COUNTER);
runTestCaseInMultipleThreads(
() -> {
int arg = random.nextInt();
ObjectRef<Integer> obj = Ray.task(MultiThreadingTest::echo, arg).remote();
Assert.assertEquals(arg, (int) obj.get());
},
LOOP_COUNTER);
// Test calling actors.
ActorHandle<Echo> echoActor = Ray.actor(Echo::new).remote();
runTestCaseInMultipleThreads(() -> {
int arg = random.nextInt();
ObjectRef<Integer> obj = echoActor.task(Echo::echo, arg).remote();
Assert.assertEquals(arg, (int) obj.get());
}, LOOP_COUNTER);
runTestCaseInMultipleThreads(
() -> {
int arg = random.nextInt();
ObjectRef<Integer> obj = echoActor.task(Echo::echo, arg).remote();
Assert.assertEquals(arg, (int) obj.get());
},
LOOP_COUNTER);
// Test creating multi actors
runTestCaseInMultipleThreads(() -> {
int arg = random.nextInt();
ActorHandle<Echo> echoActor1 = Ray.actor(Echo::new).remote();
try {
// Sleep a while to test the case that another actor is created before submitting
// tasks to this actor.
TimeUnit.MILLISECONDS.sleep(10);
} catch (InterruptedException e) {
LOGGER.warn("Got exception while sleeping.", e);
}
ObjectRef<Integer> obj = echoActor1.task(Echo::echo, arg).remote();
Assert.assertEquals(arg, (int) obj.get());
}, 1);
runTestCaseInMultipleThreads(
() -> {
int arg = random.nextInt();
ActorHandle<Echo> echoActor1 = Ray.actor(Echo::new).remote();
try {
// Sleep a while to test the case that another actor is created before submitting
// tasks to this actor.
TimeUnit.MILLISECONDS.sleep(10);
} catch (InterruptedException e) {
LOGGER.warn("Got exception while sleeping.", e);
}
ObjectRef<Integer> obj = echoActor1.task(Echo::echo, arg).remote();
Assert.assertEquals(arg, (int) obj.get());
},
1);
// Test put and get.
runTestCaseInMultipleThreads(() -> {
int arg = random.nextInt();
ObjectRef<Integer> obj = Ray.put(arg);
Assert.assertEquals(arg, (int) obj.get());
}, LOOP_COUNTER);
runTestCaseInMultipleThreads(
() -> {
int arg = random.nextInt();
ObjectRef<Integer> obj = Ray.put(arg);
Assert.assertEquals(arg, (int) obj.get());
},
LOOP_COUNTER);
TestUtils.warmUpCluster();
// Test wait for one object in multi threads.
ObjectRef<Integer> obj = Ray.task(MultiThreadingTest::echo, 100).remote();
runTestCaseInMultipleThreads(() -> {
WaitResult<Integer> result = Ray.wait(ImmutableList.of(obj), 1, 1000);
Assert.assertEquals(1, result.getReady().size());
}, 1);
runTestCaseInMultipleThreads(
() -> {
WaitResult<Integer> result = Ray.wait(ImmutableList.of(obj), 1, 1000);
Assert.assertEquals(1, result.getReady().size());
},
1);
return "ok";
}
@@ -134,21 +147,19 @@ public class MultiThreadingTest extends BaseTest {
Assert.assertEquals(actorId, actorIdTester.getId());
}
/**
* Call this method each time to avoid hitting the cache in {@link ObjectRef#get()}.
*/
/** Call this method each time to avoid hitting the cache in {@link ObjectRef#get()}. */
static Runnable[] generateRunnables() {
final ObjectRef<Integer> fooObject = Ray.put(1);
final ActorHandle<Echo> fooActor = Ray.actor(Echo::new).remote();
return new Runnable[]{
() -> Ray.put(1),
() -> Ray.get(ImmutableList.of(fooObject)),
fooObject::get,
() -> Ray.wait(ImmutableList.of(fooObject)),
Ray::getRuntimeContext,
() -> Ray.task(MultiThreadingTest::echo, 1).remote(),
() -> Ray.actor(Echo::new).remote(),
() -> fooActor.task(Echo::echo, 1).remote(),
return new Runnable[] {
() -> Ray.put(1),
() -> Ray.get(ImmutableList.of(fooObject)),
fooObject::get,
() -> Ray.wait(ImmutableList.of(fooObject)),
Ray::getRuntimeContext,
() -> Ray.task(MultiThreadingTest::echo, 1).remote(),
() -> Ray.actor(Echo::new).remote(),
() -> fooActor.task(Echo::echo, 1).remote(),
};
}
@@ -165,16 +176,19 @@ public class MultiThreadingTest extends BaseTest {
{
Runnable[] runnables = generateRunnables();
Thread thread = new Thread(Ray.wrapRunnable(() -> {
try {
// It would be OK to run them in another thread if wrapped the runnable.
for (Runnable runnable : runnables) {
runnable.run();
}
} catch (Throwable ex) {
throwable[0] = ex;
}
}));
Thread thread =
new Thread(
Ray.wrapRunnable(
() -> {
try {
// It would be OK to run them in another thread if wrapped the runnable.
for (Runnable runnable : runnables) {
runnable.run();
}
} catch (Throwable ex) {
throwable[0] = ex;
}
}));
thread.start();
thread.join();
if (throwable[0] != null) {
@@ -184,16 +198,18 @@ public class MultiThreadingTest extends BaseTest {
{
Runnable[] runnables = generateRunnables();
Thread thread = new Thread(() -> {
try {
// It wouldn't be OK to run them in another thread if not wrapped the runnable.
for (Runnable runnable : runnables) {
Assert.expectThrows(RuntimeException.class, runnable::run);
}
} catch (Throwable ex) {
throwable[0] = ex;
}
});
Thread thread =
new Thread(
() -> {
try {
// It wouldn't be OK to run them in another thread if not wrapped the runnable.
for (Runnable runnable : runnables) {
Assert.expectThrows(RuntimeException.class, runnable::run);
}
} catch (Throwable ex) {
throwable[0] = ex;
}
});
thread.start();
thread.join();
if (throwable[0] != null) {
@@ -230,14 +246,16 @@ public class MultiThreadingTest extends BaseTest {
public void testGetAndSetAsyncContext() throws InterruptedException {
Object asyncContext = Ray.getAsyncContext();
Throwable[] throwable = new Throwable[1];
Thread thread = new Thread(() -> {
try {
Ray.setAsyncContext(asyncContext);
Ray.put(1);
} catch (Throwable ex) {
throwable[0] = ex;
}
});
Thread thread =
new Thread(
() -> {
try {
Ray.setAsyncContext(asyncContext);
Ray.put(1);
} catch (Throwable ex) {
throwable[0] = ex;
}
});
thread.start();
thread.join();
if (throwable[0] != null) {
@@ -251,13 +269,15 @@ public class MultiThreadingTest extends BaseTest {
try {
List<Future<String>> futures = new ArrayList<>();
for (int i = 0; i < NUM_THREADS; i++) {
Callable<String> task = Ray.wrapCallable(() -> {
for (int j = 0; j < numRepeats; j++) {
TimeUnit.MILLISECONDS.sleep(1);
testCase.run();
}
return "ok";
});
Callable<String> task =
Ray.wrapCallable(
() -> {
for (int j = 0; j < numRepeats; j++) {
TimeUnit.MILLISECONDS.sleep(1);
testCase.run();
}
return "ok";
});
futures.add(service.submit(task));
}
for (Future<String> future : futures) {
@@ -275,14 +295,16 @@ public class MultiThreadingTest extends BaseTest {
private static boolean testGetAsyncContextAndSetAsyncContext() throws Exception {
final Object asyncContext = Ray.getAsyncContext();
final Object[] result = new Object[1];
Thread thread = new Thread(() -> {
try {
Ray.setAsyncContext(asyncContext);
Ray.put(0);
} catch (Exception e) {
result[0] = e;
}
});
Thread thread =
new Thread(
() -> {
try {
Ray.setAsyncContext(asyncContext);
Ray.put(0);
} catch (Exception e) {
result[0] = e;
}
});
thread.start();
thread.join();
if (result[0] instanceof Exception) {
@@ -296,9 +318,8 @@ public class MultiThreadingTest extends BaseTest {
}
public void testGetAsyncContextAndSetAsyncContextInWorker() {
ObjectRef<Boolean> obj = Ray.task(
MultiThreadingTest::testGetAsyncContextAndSetAsyncContext).remote();
ObjectRef<Boolean> obj =
Ray.task(MultiThreadingTest::testGetAsyncContextAndSetAsyncContext).remote();
Assert.assertTrue(obj.get());
}
}
@@ -32,8 +32,8 @@ public class NamedActorTest extends BaseTest {
Optional<ActorHandle<Counter>> namedActor = Ray.getActor(name);
Assert.assertTrue(namedActor.isPresent());
// Verify that this handle is correct.
Assert.assertEquals(namedActor.get().task(Counter::increment).remote().get(),
Integer.valueOf(2));
Assert.assertEquals(
namedActor.get().task(Counter::increment).remote().get(), Integer.valueOf(2));
}
@Test
@@ -49,30 +49,31 @@ public class NamedActorTest extends BaseTest {
Optional<ActorHandle<Counter>> namedActor = Ray.getGlobalActor(name);
Assert.assertTrue(namedActor.isPresent());
// Verify that this handle is correct.
Assert.assertEquals(namedActor.get().task(Counter::increment).remote().get(),
Integer.valueOf(2));
Assert.assertEquals(
namedActor.get().task(Counter::increment).remote().get(), Integer.valueOf(2));
if (!TestUtils.isSingleProcessMode()) {
// Get the global actor from another driver.
RayConfig rayConfig = TestUtils.getRuntime().getRayConfig();
ProcessBuilder builder = new ProcessBuilder(
"java",
"-cp",
System.getProperty("java.class.path"),
"-Dray.address=" + rayConfig.getRedisAddress(),
"-Dray.object-store.socket-name=" + rayConfig.objectStoreSocketName,
"-Dray.raylet.socket-name=" + rayConfig.rayletSocketName,
"-Dray.raylet.node-manager-port=" + rayConfig.getNodeManagerPort(),
NamedActorTest.class.getName(),
name);
ProcessBuilder builder =
new ProcessBuilder(
"java",
"-cp",
System.getProperty("java.class.path"),
"-Dray.address=" + rayConfig.getRedisAddress(),
"-Dray.object-store.socket-name=" + rayConfig.objectStoreSocketName,
"-Dray.raylet.socket-name=" + rayConfig.rayletSocketName,
"-Dray.raylet.node-manager-port=" + rayConfig.getNodeManagerPort(),
NamedActorTest.class.getName(),
name);
builder.redirectError(ProcessBuilder.Redirect.INHERIT);
Process driver = builder.start();
Assert.assertTrue(driver.waitFor(60, TimeUnit.SECONDS));
Assert.assertEquals(driver.exitValue(), 0,
"The driver exited with code " + driver.exitValue());
Assert.assertEquals(
driver.exitValue(), 0, "The driver exited with code " + driver.exitValue());
Assert.assertEquals(namedActor.get().task(Counter::increment).remote().get(),
Integer.valueOf(4));
Assert.assertEquals(
namedActor.get().task(Counter::increment).remote().get(), Integer.valueOf(4));
}
}
@@ -83,8 +84,8 @@ public class NamedActorTest extends BaseTest {
Optional<ActorHandle<Counter>> namedActor = Ray.getGlobalActor(actorName);
Assert.assertTrue(namedActor.isPresent());
// Verify that this handle is correct.
Assert.assertEquals(namedActor.get().task(Counter::increment).remote().get(),
Integer.valueOf(3));
Assert.assertEquals(
namedActor.get().task(Counter::increment).remote().get(), Integer.valueOf(3));
}
@Test(expectedExceptions = IllegalArgumentException.class)
@@ -97,5 +98,4 @@ public class NamedActorTest extends BaseTest {
// Registering with the same name should fail.
Ray.actor(Counter::new).setName(name).remote();
}
}
@@ -8,9 +8,7 @@ import java.util.stream.Collectors;
import org.testng.Assert;
import org.testng.annotations.Test;
/**
* Test putting and getting objects.
*/
/** Test putting and getting objects. */
public class ObjectStoreTest extends BaseTest {
@Test
@@ -36,8 +34,7 @@ public class ObjectStoreTest extends BaseTest {
@Test
public void testGetMultipleObjects() {
List<Integer> ints = ImmutableList.of(1, 2, 3, 4, 5);
List<ObjectRef<Integer>> refs = ints.stream().map(Ray::put)
.collect(Collectors.toList());
List<ObjectRef<Integer>> refs = ints.stream().map(Ray::put).collect(Collectors.toList());
Assert.assertEquals(ints, Ray.get(refs));
}
}
@@ -32,14 +32,14 @@ public class PlacementGroupTest extends BaseTest {
// This test just creates a placement group with one bundle.
// It's not comprehensive to test all placement group test cases.
public void testCreateAndCallActor() {
PlacementGroupImpl placementGroup = (PlacementGroupImpl)PlacementGroupTestUtils
.createSimpleGroup();
PlacementGroupImpl placementGroup =
(PlacementGroupImpl) PlacementGroupTestUtils.createSimpleGroup();
Assert.assertTrue(placementGroup.wait(10));
Assert.assertEquals(placementGroup.getName(),"unnamed_group");
Assert.assertEquals(placementGroup.getName(), "unnamed_group");
// Test creating an actor from a constructor.
ActorHandle<Counter> actor = Ray.actor(Counter::new, 1)
.setPlacementGroup(placementGroup, 0).remote();
ActorHandle<Counter> actor =
Ray.actor(Counter::new, 1).setPlacementGroup(placementGroup, 0).remote();
Assert.assertNotEquals(actor.getId(), ActorId.NIL);
// Test calling an actor.
@@ -48,20 +48,22 @@ public class PlacementGroupTest extends BaseTest {
@Test(groups = {"cluster"})
public void testGetPlacementGroup() {
PlacementGroupImpl firstPlacementGroup = (PlacementGroupImpl)PlacementGroupTestUtils
.createNameSpecifiedSimpleGroup("CPU", 1, PlacementStrategy.PACK,
1.0, "first_placement_group");
PlacementGroupImpl firstPlacementGroup =
(PlacementGroupImpl)
PlacementGroupTestUtils.createNameSpecifiedSimpleGroup(
"CPU", 1, PlacementStrategy.PACK, 1.0, "first_placement_group");
PlacementGroupImpl secondPlacementGroup = (PlacementGroupImpl)PlacementGroupTestUtils
.createNameSpecifiedSimpleGroup("CPU", 1, PlacementStrategy.PACK,
1.0, "second_placement_group");
PlacementGroupImpl secondPlacementGroup =
(PlacementGroupImpl)
PlacementGroupTestUtils.createNameSpecifiedSimpleGroup(
"CPU", 1, PlacementStrategy.PACK, 1.0, "second_placement_group");
Assert.assertTrue(firstPlacementGroup.wait(10));
Assert.assertTrue(secondPlacementGroup.wait(10));
PlacementGroupImpl firstPlacementGroupRes =
(PlacementGroupImpl)Ray.getPlacementGroup((firstPlacementGroup).getId());
(PlacementGroupImpl) Ray.getPlacementGroup((firstPlacementGroup).getId());
PlacementGroupImpl secondPlacementGroupRes =
(PlacementGroupImpl)Ray.getPlacementGroup((secondPlacementGroup).getId());
(PlacementGroupImpl) Ray.getPlacementGroup((secondPlacementGroup).getId());
Assert.assertNotNull(firstPlacementGroupRes);
Assert.assertNotNull(secondPlacementGroupRes);
@@ -74,25 +76,28 @@ public class PlacementGroupTest extends BaseTest {
List<PlacementGroup> allPlacementGroup = Ray.getAllPlacementGroups();
Assert.assertEquals(allPlacementGroup.size(), 2);
PlacementGroupImpl placementGroupRes = (PlacementGroupImpl)allPlacementGroup.get(0);
PlacementGroupImpl placementGroupRes = (PlacementGroupImpl) allPlacementGroup.get(0);
Assert.assertNotNull(placementGroupRes.getId());
PlacementGroupImpl expectPlacementGroup = placementGroupRes.getId()
.equals(firstPlacementGroup.getId()) ? firstPlacementGroup : secondPlacementGroup;
PlacementGroupImpl expectPlacementGroup =
placementGroupRes.getId().equals(firstPlacementGroup.getId())
? firstPlacementGroup
: secondPlacementGroup;
Assert.assertEquals(placementGroupRes.getName(), expectPlacementGroup.getName());
Assert.assertEquals(placementGroupRes.getBundles().size(),
expectPlacementGroup.getBundles().size());
Assert.assertEquals(
placementGroupRes.getBundles().size(), expectPlacementGroup.getBundles().size());
Assert.assertEquals(placementGroupRes.getStrategy(), expectPlacementGroup.getStrategy());
}
@Test(groups = {"cluster"})
public void testRemovePlacementGroup() {
PlacementGroupTestUtils.createNameSpecifiedSimpleGroup("CPU",
1, PlacementStrategy.PACK, 1.0, "first_placement_group");
PlacementGroupTestUtils.createNameSpecifiedSimpleGroup(
"CPU", 1, PlacementStrategy.PACK, 1.0, "first_placement_group");
PlacementGroupImpl secondPlacementGroup = (PlacementGroupImpl)PlacementGroupTestUtils
.createNameSpecifiedSimpleGroup("CPU", 1, PlacementStrategy.PACK,
1.0, "second_placement_group");
PlacementGroupImpl secondPlacementGroup =
(PlacementGroupImpl)
PlacementGroupTestUtils.createNameSpecifiedSimpleGroup(
"CPU", 1, PlacementStrategy.PACK, 1.0, "second_placement_group");
List<PlacementGroup> allPlacementGroup = Ray.getAllPlacementGroups();
Assert.assertEquals(allPlacementGroup.size(), 2);
@@ -100,7 +105,7 @@ public class PlacementGroupTest extends BaseTest {
Ray.removePlacementGroup(secondPlacementGroup.getId());
PlacementGroupImpl removedPlacementGroup =
(PlacementGroupImpl)Ray.getPlacementGroup((secondPlacementGroup).getId());
(PlacementGroupImpl) Ray.getPlacementGroup((secondPlacementGroup).getId());
Assert.assertEquals(removedPlacementGroup.getState(), PlacementGroupState.REMOVED);
// Wait for placement group after it is removed.
@@ -132,12 +137,12 @@ public class PlacementGroupTest extends BaseTest {
Assert.assertEquals(exceptionCount, 2);
}
@Test (expectedExceptions = { IllegalArgumentException.class })
@Test(expectedExceptions = {IllegalArgumentException.class})
public void testBundleSizeValidCheckWhenCreate() {
PlacementGroupTestUtils.createBundleSizeInvalidGroup();
}
@Test (expectedExceptions = { IllegalArgumentException.class })
@Test(expectedExceptions = {IllegalArgumentException.class})
public void testBundleResourceValidCheckWhenCreate() {
PlacementGroupTestUtils.createBundleResourceInvalidGroup();
}
@@ -8,13 +8,15 @@ import java.util.HashMap;
import java.util.List;
import java.util.Map;
/**
* A utils class for placement group test.
*/
/** A utils class for placement group test. */
public class PlacementGroupTestUtils {
public static PlacementGroup createNameSpecifiedSimpleGroup(String resourceName, int bundleSize,
PlacementStrategy strategy, Double resourceSize, String groupName) {
public static PlacementGroup createNameSpecifiedSimpleGroup(
String resourceName,
int bundleSize,
PlacementStrategy strategy,
Double resourceSize,
String groupName) {
List<Map<String, Double>> bundles = new ArrayList<>();
for (int i = 0; i < bundleSize; i++) {
@@ -26,10 +28,10 @@ public class PlacementGroupTestUtils {
return Ray.createPlacementGroup(groupName, bundles, strategy);
}
public static PlacementGroup createSpecifiedSimpleGroup(String resourceName, int bundleSize,
PlacementStrategy strategy, Double resourceSize) {
return createNameSpecifiedSimpleGroup(resourceName, bundleSize, strategy,
resourceSize, "unnamed_group");
public static PlacementGroup createSpecifiedSimpleGroup(
String resourceName, int bundleSize, PlacementStrategy strategy, Double resourceSize) {
return createNameSpecifiedSimpleGroup(
resourceName, bundleSize, strategy, resourceSize, "unnamed_group");
}
public static PlacementGroup createSimpleGroup() {
@@ -43,5 +45,4 @@ public class PlacementGroupTestUtils {
public static void createBundleResourceInvalidGroup() {
createSpecifiedSimpleGroup("CPU", 1, PlacementStrategy.PACK, 0.0);
}
}
@@ -20,9 +20,14 @@ public class PlasmaFreeTest extends BaseTest {
Assert.assertEquals("hello", helloString);
Ray.internal().free(ImmutableList.of(helloId), true);
final boolean result = TestUtils.waitForCondition(() ->
!TestUtils.getRuntime().getObjectStore()
.wait(ImmutableList.of(((ObjectRefImpl<String>) helloId).getId()), 1, 0).get(0), 50);
final boolean result =
TestUtils.waitForCondition(
() ->
!TestUtils.getRuntime()
.getObjectStore()
.wait(ImmutableList.of(((ObjectRefImpl<String>) helloId).getId()), 1, 0)
.get(0),
50);
if (TestUtils.isSingleProcessMode()) {
Assert.assertTrue(result);
} else {
@@ -21,4 +21,4 @@ public class RayAlterSuiteListener implements IAlterSuiteListener {
groups.setRun(run);
suite.setGroups(groups);
}
}
}
@@ -11,9 +11,7 @@ import java.util.Map;
import org.testng.Assert;
import org.testng.annotations.Test;
/**
* Test Ray.call API
*/
/** Test Ray.call API */
public class RayCallTest extends BaseTest {
private static int testInt(int val) {
@@ -69,9 +67,7 @@ public class RayCallTest extends BaseTest {
return buffer;
}
/**
* Test calling and returning different types.
*/
/** Test calling and returning different types. */
@Test
public void testType() {
Assert.assertEquals(1, (int) Ray.task(RayCallTest::testInt, 1).remote().get());
@@ -134,16 +130,12 @@ public class RayCallTest extends BaseTest {
public void testNumberOfParameters() {
Assert.assertEquals(0, (int) Ray.task(RayCallTest::testNoParam).remote().get());
Assert.assertEquals(1, (int) Ray.task(RayCallTest::testOneParam, 1).remote().get());
Assert.assertEquals(2, (int) Ray.task(
RayCallTest::testTwoParams, 1, 1).remote().get());
Assert.assertEquals(3, (int) Ray.task(
RayCallTest::testThreeParams, 1, 1, 1).remote().get());
Assert.assertEquals(4, (int) Ray.task(
RayCallTest::testFourParams, 1, 1, 1, 1).remote().get());
Assert.assertEquals(5, (int) Ray.task(
RayCallTest::testFiveParams, 1, 1, 1, 1, 1).remote().get());
Assert.assertEquals(6, (int) Ray.task(
RayCallTest::testSixParams, 1, 1, 1, 1, 1, 1).remote().get());
Assert.assertEquals(2, (int) Ray.task(RayCallTest::testTwoParams, 1, 1).remote().get());
Assert.assertEquals(3, (int) Ray.task(RayCallTest::testThreeParams, 1, 1, 1).remote().get());
Assert.assertEquals(4, (int) Ray.task(RayCallTest::testFourParams, 1, 1, 1, 1).remote().get());
Assert.assertEquals(
5, (int) Ray.task(RayCallTest::testFiveParams, 1, 1, 1, 1, 1).remote().get());
Assert.assertEquals(
6, (int) Ray.task(RayCallTest::testSixParams, 1, 1, 1, 1, 1, 1).remote().get());
}
}
@@ -9,9 +9,7 @@ import java.util.stream.Collectors;
import org.testng.Assert;
import org.testng.annotations.Test;
/**
* Integration test for Ray.*
*/
/** Integration test for Ray.* */
public class RayMethodsTest extends BaseTest {
@Test
@@ -33,6 +31,5 @@ public class RayMethodsTest extends BaseTest {
Assert.assertEquals(1, i1);
Assert.assertEquals(3.14, f1, Double.MIN_NORMAL);
Assert.assertNull(n1);
}
}
@@ -13,14 +13,12 @@ public class RaySerializerTest extends BaseTest {
@Test
public void testSerializePyActor() {
PyActorHandle pyActor = Ray.actor(
PyActorClass.of("test", "RaySerializerTest")).remote();
PyActorHandle pyActor = Ray.actor(PyActorClass.of("test", "RaySerializerTest")).remote();
NativeRayObject nativeRayObject = ObjectSerializer.serialize(pyActor);
PyActorHandle result = (PyActorHandle) ObjectSerializer
.deserialize(nativeRayObject, null, Object.class);
PyActorHandle result =
(PyActorHandle) ObjectSerializer.deserialize(nativeRayObject, null, Object.class);
Assert.assertEquals(result.getId(), pyActor.getId());
Assert.assertEquals(result.getModuleName(), "test");
Assert.assertEquals(result.getClassName(), "RaySerializerTest");
}
}
@@ -25,8 +25,10 @@ public class RayletConfigTest extends BaseTest {
public static class TestActor {
public String getConfigValue() {
return TestUtils.getRuntime().getRayConfig()
.rayletConfigParameters.get(RAY_CONFIG_KEY)
return TestUtils.getRuntime()
.getRayConfig()
.rayletConfigParameters
.get(RAY_CONFIG_KEY)
.toString();
}
}
@@ -28,5 +28,4 @@ public class RedisPasswordTest extends BaseTest {
ObjectRef<String> obj = Ray.task(RedisPasswordTest::echo, "hello").remote();
Assert.assertEquals("hello", obj.get());
}
}
@@ -44,12 +44,12 @@ public class ReferenceCountingTest extends BaseTest {
Field referencesField = ObjectRefImpl.class.getDeclaredField("REFERENCES");
referencesField.setAccessible(true);
Set<?> references = (Set<?>) referencesField.get(null);
Class<?> referenceClass = Class
.forName("io.ray.runtime.object.ObjectRefImpl$ObjectRefImplReference");
Class<?> referenceClass =
Class.forName("io.ray.runtime.object.ObjectRefImpl$ObjectRefImplReference");
Method finalizeReferentMethod = referenceClass.getDeclaredMethod("finalizeReferent");
finalizeReferentMethod.setAccessible(true);
for (Object reference : references) {
if (obj.equals(((Reference<?>)reference).get())) {
if (obj.equals(((Reference<?>) reference).get())) {
finalizeReferentMethod.invoke(reference);
break;
}
@@ -91,18 +91,27 @@ public class ReferenceCountingTest extends BaseTest {
checkRefCounts(ImmutableMap.of(objectId, new long[] {localRefCount, submittedTaskRefCount}));
}
private void checkRefCounts(ObjectId objectId1, long localRefCount1, long submittedTaskRefCount1,
ObjectId objectId2, long localRefCount2, long submittedTaskRefCount2) {
checkRefCounts(ImmutableMap.of(objectId1, new long[] {localRefCount1, submittedTaskRefCount1},
objectId2, new long[] {localRefCount2, submittedTaskRefCount2}));
private void checkRefCounts(
ObjectId objectId1,
long localRefCount1,
long submittedTaskRefCount1,
ObjectId objectId2,
long localRefCount2,
long submittedTaskRefCount2) {
checkRefCounts(
ImmutableMap.of(
objectId1,
new long[] {localRefCount1, submittedTaskRefCount1},
objectId2,
new long[] {localRefCount2, submittedTaskRefCount2}));
}
private static void fillObjectStoreAndGet(ObjectId objectId, boolean succeed) {
fillObjectStoreAndGet(objectId, succeed, 40 * 1024 * 1024, 5);
}
private static void fillObjectStoreAndGet(ObjectId objectId, boolean succeed, int objectSize,
int numObjects) {
private static void fillObjectStoreAndGet(
ObjectId objectId, boolean succeed, int objectSize, int numObjects) {
for (int i = 0; i < numObjects; i++) {
Ray.put(new TestUtils.LargeObject(objectSize));
}
@@ -115,9 +124,7 @@ public class ReferenceCountingTest extends BaseTest {
}
}
/**
* Based on Python test case `test_local_refcounts`.
*/
/** Based on Python test case `test_local_refcounts`. */
public void testLocalRefCounts() {
ObjectRefImpl<Object> obj1 = (ObjectRefImpl<Object>) Ray.put(null);
checkRefCounts(obj1.getId(), 1, 0);
@@ -163,19 +170,19 @@ public class ReferenceCountingTest extends BaseTest {
del(result);
}
/**
* Based on Python test case `test_dependency_refcounts`.
*/
/** Based on Python test case `test_dependency_refcounts`. */
public void testDependencyRefCounts() {
{
// Test that regular plasma dependency refcounts are decremented once the
// task finishes.
ActorHandle<SignalActor> signal = SignalActor.create();
ObjectRefImpl<TestUtils.LargeObject> largeDep = (ObjectRefImpl<TestUtils.LargeObject>) Ray
.put(new TestUtils.LargeObject());
ObjectRefImpl<Object> result = (ObjectRefImpl<Object>)
Ray.<TestUtils.LargeObject, ActorHandle<SignalActor>, Object>task(
ReferenceCountingTest::oneDep, largeDep, signal).remote();
ObjectRefImpl<TestUtils.LargeObject> largeDep =
(ObjectRefImpl<TestUtils.LargeObject>) Ray.put(new TestUtils.LargeObject());
ObjectRefImpl<Object> result =
(ObjectRefImpl<Object>)
Ray.<TestUtils.LargeObject, ActorHandle<SignalActor>, Object>task(
ReferenceCountingTest::oneDep, largeDep, signal)
.remote();
checkRefCounts(largeDep.getId(), 1, 1, result.getId(), 1, 0);
sendSignal(signal);
// Reference count should be removed once the task finishes.
@@ -189,12 +196,15 @@ public class ReferenceCountingTest extends BaseTest {
// Test that inlined dependency refcounts are decremented once they are
// inlined.
ActorHandle<SignalActor> signal = SignalActor.create();
ObjectRefImpl<Integer> dep = (ObjectRefImpl<Integer>)
Ray.<Integer, ActorHandle<SignalActor>, Integer>task(ReferenceCountingTest::oneDep,
Integer.valueOf(1), signal).remote();
ObjectRefImpl<Integer> dep =
(ObjectRefImpl<Integer>)
Ray.<Integer, ActorHandle<SignalActor>, Integer>task(
ReferenceCountingTest::oneDep, Integer.valueOf(1), signal)
.remote();
checkRefCounts(dep.getId(), 1, 0);
ObjectRefImpl<Object> result = (ObjectRefImpl<Object>)
Ray.<Integer, Object>task(ReferenceCountingTest::oneDep, dep).remote();
ObjectRefImpl<Object> result =
(ObjectRefImpl<Object>)
Ray.<Integer, Object>task(ReferenceCountingTest::oneDep, dep).remote();
checkRefCounts(dep.getId(), 1, 1, result.getId(), 1, 0);
sendSignal(signal);
// Reference count should be removed as soon as the dependency is inlined.
@@ -209,13 +219,17 @@ public class ReferenceCountingTest extends BaseTest {
// the task finishes.
ActorHandle<SignalActor> signal1 = SignalActor.create();
ActorHandle<SignalActor> signal2 = SignalActor.create();
ObjectRefImpl<TestUtils.LargeObject> dep = (ObjectRefImpl<TestUtils.LargeObject>)
Ray.<TestUtils.LargeObject, ActorHandle<SignalActor>, TestUtils.LargeObject>task(
ReferenceCountingTest::oneDepLarge, (TestUtils.LargeObject) null, signal1).remote();
ObjectRefImpl<TestUtils.LargeObject> dep =
(ObjectRefImpl<TestUtils.LargeObject>)
Ray.<TestUtils.LargeObject, ActorHandle<SignalActor>, TestUtils.LargeObject>task(
ReferenceCountingTest::oneDepLarge, (TestUtils.LargeObject) null, signal1)
.remote();
checkRefCounts(dep.getId(), 1, 0);
ObjectRefImpl<Integer> result = (ObjectRefImpl<Integer>)
Ray.<TestUtils.LargeObject, ActorHandle<SignalActor>, Integer>task(
ReferenceCountingTest::oneDep, dep, signal2).remote();
ObjectRefImpl<Integer> result =
(ObjectRefImpl<Integer>)
Ray.<TestUtils.LargeObject, ActorHandle<SignalActor>, Integer>task(
ReferenceCountingTest::oneDep, dep, signal2)
.remote();
checkRefCounts(dep.getId(), 1, 1, result.getId(), 1, 0);
sendSignal(signal1);
dep.get(); // TODO(kfstorm): timeout=10
@@ -233,11 +247,14 @@ public class ReferenceCountingTest extends BaseTest {
// Test that regular plasma dependency refcounts are decremented if a task
// fails.
ActorHandle<SignalActor> signal = SignalActor.create();
ObjectRefImpl<TestUtils.LargeObject> largeDep = (ObjectRefImpl<TestUtils.LargeObject>)
Ray.put(new TestUtils.LargeObject(10 * 1024 * 1024));
ObjectRefImpl<Integer> result = (ObjectRefImpl<Integer>)
Ray.<TestUtils.LargeObject, ActorHandle<SignalActor>, Boolean, Integer>task(
ReferenceCountingTest::oneDep, largeDep, signal, /* fail= */true).remote();
ObjectRefImpl<TestUtils.LargeObject> largeDep =
(ObjectRefImpl<TestUtils.LargeObject>)
Ray.put(new TestUtils.LargeObject(10 * 1024 * 1024));
ObjectRefImpl<Integer> result =
(ObjectRefImpl<Integer>)
Ray.<TestUtils.LargeObject, ActorHandle<SignalActor>, Boolean, Integer>task(
ReferenceCountingTest::oneDep, largeDep, signal, /* fail= */ true)
.remote();
checkRefCounts(largeDep.getId(), 1, 1, result.getId(), 1, 0);
sendSignal(signal);
// Reference count should be removed once the task finishes.
@@ -252,13 +269,17 @@ public class ReferenceCountingTest extends BaseTest {
// fails.
ActorHandle<SignalActor> signal1 = SignalActor.create();
ActorHandle<SignalActor> signal2 = SignalActor.create();
ObjectRefImpl<TestUtils.LargeObject> dep = (ObjectRefImpl<TestUtils.LargeObject>)
Ray.<Integer, ActorHandle<SignalActor>, TestUtils.LargeObject>task(
ReferenceCountingTest::oneDepLarge, (Integer) null, signal1).remote();
ObjectRefImpl<TestUtils.LargeObject> dep =
(ObjectRefImpl<TestUtils.LargeObject>)
Ray.<Integer, ActorHandle<SignalActor>, TestUtils.LargeObject>task(
ReferenceCountingTest::oneDepLarge, (Integer) null, signal1)
.remote();
checkRefCounts(dep.getId(), 1, 0);
ObjectRefImpl<Integer> result = (ObjectRefImpl<Integer>)
Ray.<TestUtils.LargeObject, ActorHandle<SignalActor>, Boolean, Integer>task(
ReferenceCountingTest::oneDep, dep, signal2, /* fail= */true).remote();
ObjectRefImpl<Integer> result =
(ObjectRefImpl<Integer>)
Ray.<TestUtils.LargeObject, ActorHandle<SignalActor>, Boolean, Integer>task(
ReferenceCountingTest::oneDep, dep, signal2, /* fail= */ true)
.remote();
checkRefCounts(dep.getId(), 1, 1, result.getId(), 1, 0);
sendSignal(signal1);
dep.get(); // TODO(kfstorm): timeout=10
@@ -292,9 +313,7 @@ public class ReferenceCountingTest extends BaseTest {
}
}
/**
* Based on Python test case `test_basic_pinning`.
*/
/** Based on Python test case `test_basic_pinning`. */
public void testBasicPinning() {
ActorHandle<ActorBasicPinning> actor = Ray.actor(ActorBasicPinning::new).remote();
@@ -302,9 +321,11 @@ public class ReferenceCountingTest extends BaseTest {
// evicted before the long-lived object whose reference is held by
// the actor.
for (int i = 0; i < 10; i++) {
ObjectRef<Integer> intermediateResult = Ray
.task(ReferenceCountingTest::fooBasicPinning, new TestUtils.LargeObject(10 * 1024 * 1024))
.remote();
ObjectRef<Integer> intermediateResult =
Ray.task(
ReferenceCountingTest::fooBasicPinning,
new TestUtils.LargeObject(10 * 1024 * 1024))
.remote();
intermediateResult.get();
}
// The ray.get below would fail with only LRU eviction, as the object
@@ -316,9 +337,7 @@ public class ReferenceCountingTest extends BaseTest {
return null;
}
/**
* Based on Python test case `test_pending_task_dependency_pinning`.
*/
/** Based on Python test case `test_pending_task_dependency_pinning`. */
public void testPendingTaskDependencyPinning() {
// The object that is ray.put here will go out of scope immediately, so if
// pending task dependencies aren't considered, it will be evicted before
@@ -326,9 +345,12 @@ public class ReferenceCountingTest extends BaseTest {
// store.
TestUtils.LargeObject input1 = new TestUtils.LargeObject(40 * 1024 * 1024);
ActorHandle<SignalActor> signal = SignalActor.create();
ObjectRef<Object> result = Ray
.task(ReferenceCountingTest::pending, input1, signal.task(SignalActor::waitSignal).remote())
.remote();
ObjectRef<Object> result =
Ray.task(
ReferenceCountingTest::pending,
input1,
signal.task(SignalActor::waitSignal).remote())
.remote();
for (int i = 0; i < 2; i++) {
Ray.put(new TestUtils.LargeObject(40 * 1024 * 1024));
@@ -12,9 +12,7 @@ import org.testng.annotations.AfterClass;
import org.testng.annotations.BeforeClass;
import org.testng.annotations.Test;
/**
* Resources Management Test.
*/
/** Resources Management Test. */
@Test(groups = {"cluster"})
public class ResourcesManagementTest extends BaseTest {
@@ -44,16 +42,14 @@ public class ResourcesManagementTest extends BaseTest {
public void testMethods() {
// This is a case that can satisfy required resources.
// The static resources for test are "CPU:4,RES-A:4".
ObjectRef<Integer> result1 = Ray.task(ResourcesManagementTest::echo, 100)
.setResource("CPU", 4.0)
.remote();
ObjectRef<Integer> result1 =
Ray.task(ResourcesManagementTest::echo, 100).setResource("CPU", 4.0).remote();
Assert.assertEquals(100, (int) result1.get());
// This is a case that can't satisfy required resources.
// The static resources for test are "CPU:4,RES-A:4".
final ObjectRef<Integer> result2 = Ray.task(ResourcesManagementTest::echo, 200)
.setResource("CPU", 4.0)
.remote();
final ObjectRef<Integer> result2 =
Ray.task(ResourcesManagementTest::echo, 200).setResource("CPU", 4.0).remote();
WaitResult<Integer> waitResult = Ray.wait(ImmutableList.of(result2), 1, 1000);
Assert.assertEquals(1, waitResult.getReady().size());
@@ -72,23 +68,17 @@ public class ResourcesManagementTest extends BaseTest {
public void testActors() {
// This is a case that can satisfy required resources.
// The static resources for test are "CPU:4,RES-A:4".
ActorHandle<Echo> echo1 = Ray.actor(Echo::new)
.setResource("CPU", 2.0)
.remote();
ActorHandle<Echo> echo1 = Ray.actor(Echo::new).setResource("CPU", 2.0).remote();
final ObjectRef<Integer> result1 = echo1.task(Echo::echo, 100).remote();
Assert.assertEquals(100, (int) result1.get());
// This is a case that can't satisfy required resources.
// The static resources for test are "CPU:4,RES-A:4".
ActorHandle<Echo> echo2 =
Ray.actor(Echo::new)
.setResource("CPU", 8.0)
.remote();
ActorHandle<Echo> echo2 = Ray.actor(Echo::new).setResource("CPU", 8.0).remote();
final ObjectRef<Integer> result2 = echo2.task(Echo::echo, 100).remote();
WaitResult<Integer> waitResult = Ray.wait(ImmutableList.of(result2), 1, 1000);
Assert.assertEquals(0, waitResult.getReady().size());
Assert.assertEquals(1, waitResult.getUnready().size());
}
}
@@ -49,8 +49,7 @@ public class RuntimeContextTest extends BaseTest {
@Test
public void testRuntimeContextInActor() {
ActorHandle<RuntimeContextTester> actor = Ray.actor(RuntimeContextTester::new).remote();
Assert.assertEquals("ok",
actor.task(RuntimeContextTester::testRuntimeContext, actor.getId()).remote().get());
Assert.assertEquals(
"ok", actor.task(RuntimeContextTester::testRuntimeContext, actor.getId()).remote().get());
}
}
@@ -25,4 +25,4 @@ public class SignalActor {
public static ActorHandle<SignalActor> create() {
return Ray.actor(SignalActor::new).setMaxConcurrency(2).remote();
}
}
}
@@ -18,8 +18,7 @@ public class SingleProcessModeTest extends BaseTest {
private static final int TIMES_TO_CALL_PER_ACTOR = 10;
static class MyActor {
public MyActor() {
}
public MyActor() {}
public long getThreadId() {
return Thread.currentThread().getId();
@@ -10,23 +10,25 @@ import org.testng.ITestResult;
public class TestProgressListener implements IInvokedMethodListener, ITestListener {
private String getFullTestName(ITestResult testResult) {
return testResult.getTestClass().getName() + "."
+ testResult.getMethod().getMethodName();
return testResult.getTestClass().getName() + "." + testResult.getMethod().getMethodName();
}
private void printInfo(String tag, String content) {
System.out.println(
"============ [" + LocalDateTime.now().toString() + "] [" + tag + "] " + content
"============ ["
+ LocalDateTime.now().toString()
+ "] ["
+ tag
+ "] "
+ content
+ " ============");
}
@Override
public void beforeInvocation(IInvokedMethod method, ITestResult testResult) {
}
public void beforeInvocation(IInvokedMethod method, ITestResult testResult) {}
@Override
public void afterInvocation(IInvokedMethod method, ITestResult testResult) {
}
public void afterInvocation(IInvokedMethod method, ITestResult testResult) {}
@Override
public void onTestStart(ITestResult result) {
@@ -58,10 +60,8 @@ public class TestProgressListener implements IInvokedMethodListener, ITestListen
}
@Override
public void onStart(ITestContext context) {
}
public void onStart(ITestContext context) {}
@Override
public void onFinish(ITestContext context) {
}
public void onFinish(ITestContext context) {}
}
@@ -67,12 +67,12 @@ public class TestUtils {
/**
* Warm up the cluster to make sure there's at least one idle worker.
* <p/>
* This is needed before calling `wait`. Because, in Travis CI, starting a new worker process
*
* <p>This is needed before calling `wait`. Because, in Travis CI, starting a new worker process
* could be slower than the wait timeout.
* <p/>
* TODO(hchen): We should consider supporting always reversing a certain number of idle workers in
* Raylet's worker pool.
*
* <p>TODO(hchen): We should consider supporting always reversing a certain number of idle workers
* in Raylet's worker pool.
*/
public static void warmUpCluster() {
ObjectRef<String> obj = Ray.task(TestUtils::hi).remote();
@@ -87,8 +87,8 @@ public class TestUtils {
if (Ray.internal() instanceof AbstractRayRuntime) {
return (RayRuntimeInternal) Ray.internal();
}
RayRuntimeProxy proxy = (RayRuntimeProxy) (java.lang.reflect.Proxy
.getInvocationHandler(Ray.internal()));
RayRuntimeProxy proxy =
(RayRuntimeProxy) (java.lang.reflect.Proxy.getInvocationHandler(Ray.internal()));
return proxy.getRuntimeObject();
}
@@ -70,5 +70,4 @@ public class WaitTest extends BaseTest {
Assert.assertTrue(true);
}
}
}
@@ -18,9 +18,10 @@ public class WorkerJvmOptionsTest extends BaseTest {
public void testJvmOptions() {
// The whitespaces in following argument are intentionally added to test
// that raylet can correctly handle dynamic options with whitespaces.
ActorHandle<Echo> actor = Ray.actor(Echo::new)
.setJvmOptions(" -Dtest.suffix=suffix -Dtest.suffix1=suffix1 ")
.remote();
ActorHandle<Echo> actor =
Ray.actor(Echo::new)
.setJvmOptions(" -Dtest.suffix=suffix -Dtest.suffix1=suffix1 ")
.remote();
ObjectRef<String> obj = actor.task(Echo::getOptions).remote();
Assert.assertEquals(obj.get(), "suffix");
}