diff --git a/doc/source/starting-ray.rst b/doc/source/starting-ray.rst
index a3cfd251a..63bc7ce6c 100644
--- a/doc/source/starting-ray.rst
+++ b/doc/source/starting-ray.rst
@@ -10,36 +10,113 @@ Installation
Install Ray with ``pip install -U ray``. For the latest wheels (a snapshot of the ``master`` branch), you can use the instructions at :ref:`install-nightlies`.
+.. note:: This step is not required if you are writing a Ray application in Java and you don't have the need of running your Java application in a multi-node Ray cluster at the development stage. See `Local mode`_ for more details.
+
+Build your Java code
+--------------------
+
+If your application is written in Java, you need to add Ray dependencies to your project in order to build it.
+
+.. code-block:: xml
+
+
+
+ io.ray
+ ray-api
+ ...
+
+
+ io.ray
+ ray-runtime
+ ...
+
+
+
+.. note::
+
+ When you run ``pip install`` to install Ray, Java jars are installed as well. The above dependencies are only used to build your Java code and to run your code in local or single machine mode.
+
+ If you want to run your Java code in a multi-node Ray cluster, it's better to exclude Ray jars when packaging your code to avoid jar conficts if the versions (installed Ray with ``pip install`` and maven dependencies) don't match.
+
Starting Ray on a single machine
--------------------------------
-You can start Ray by calling ``ray.init()`` in your Python script. This will start the local services that Ray uses to schedule remote tasks and actors and then connect to them. Note that you must initialize Ray before any tasks or actors are called (i.e., ``function.remote()`` will not work until `ray.init()` is called).
+You can start Ray with the ``init`` API (see the code snippet below). It will start the local services that Ray uses to schedule remote tasks and actors and then connect to them. Note that you must initialize Ray before any tasks or actors are called.
-.. code-block:: python
+.. tabs::
+ .. code-tab:: python
- import ray
- ray.init()
+ import ray
+ # Other Ray APIs will not work until `ray.init()` is called.
+ ray.init()
-To stop or restart Ray, use ``ray.shutdown()``.
+ .. code-tab:: java
-.. code-block:: python
+ import io.ray.api.Ray;
- import ray
- ray.init()
- ... # ray program
- ray.shutdown()
+ public class MyRayApp {
+ public static void main(String[] args) {
+ // Other Ray APIs will not work until `Ray.init()` is called.
+ Ray.init();
+ ...
+ }
+ }
-To check if Ray is initialized, you can call ``ray.is_initialized()``:
+To stop or restart Ray, use the shutdown API.
-.. code-block:: python
+.. tabs::
+ .. code-tab:: python
- import ray
- ray.init()
- assert ray.is_initialized() == True
+ import ray
+ ray.init()
+ ... # ray program
+ ray.shutdown()
- ray.shutdown()
- assert ray.is_initialized() == False
+ .. code-tab:: java
+
+ import io.ray.api.Ray;
+
+ public class MyRayApp {
+
+ public static void main(String[] args) {
+ Ray.init();
+ ... // ray program
+ Ray.shutdown();
+ }
+ }
+
+.. tabs::
+ .. group-tab:: Python
+
+ To check if Ray is initialized, you can call ``ray.is_initialized()``:
+
+ .. code-block:: python
+
+ import ray
+ ray.init()
+ assert ray.is_initialized() == True
+
+ ray.shutdown()
+ assert ray.is_initialized() == False
+
+ .. group-tab:: Java
+
+ To check if Ray is initialized, you can call ``Ray.isInitialized()``:
+
+ .. code-block:: java
+
+ import io.ray.api.Ray;
+
+ public class MyRayApp {
+
+ public static void main(String[] args) {
+ Ray.init();
+ Assert.assertTrue(Ray.isInitialized());
+ Ray.shutdown();
+ Assert.assertFalse(Ray.isInitialized());
+ }
+ }
See the `Configuration `__ documentation for the various ways to configure Ray.
@@ -51,23 +128,46 @@ Using Ray on a cluster
There are two steps needed to use Ray in a distributed setting:
1. You must first start the Ray cluster.
- 2. You need to add the ``address`` parameter to ``ray.init`` (like ``ray.init(address=...)``). This causes Ray to connect to the existing cluster instead of starting a new one on the local node.
-If you have a Ray cluster specification (:ref:`ref-automatic-cluster`), you can launch a multi-node cluster with Ray initialized on each node with ``ray up``. **From your local machine/laptop**:
+ If you have a Ray cluster specification (:ref:`ref-automatic-cluster`), you can launch a multi-node cluster with Ray initialized on each node with ``ray up``. **From your local machine/laptop**:
-.. code-block:: bash
+ .. code-block:: bash
- ray up cluster.yaml
+ ray up cluster.yaml
-You can monitor the Ray cluster status with ``ray monitor cluster.yaml`` and ssh into the head node with ``ray attach cluster.yaml``.
+ You can monitor the Ray cluster status with ``ray monitor cluster.yaml`` and ssh into the head node with ``ray attach cluster.yaml``.
-Your Python script **only** needs to execute on one machine in the cluster (usually the head node). To connect your program to the Ray cluster, add the following to your Python script:
+ 2. Specify the address of the Ray cluster when initializing Ray in your code. This causes Ray to connect to the existing cluster instead of starting a new one on the local node.
-.. code-block:: python
+ .. tabs::
+ .. group-tab:: Python
- ray.init(address="auto")
+ You need to add the ``address`` parameter to ``ray.init`` (like ``ray.init(address=...)``). To connect your program to the Ray cluster, add the following to your Python script:
-.. note:: Without ``ray.init(address...)``, your Ray program will only be parallelized across a single machine!
+ .. code-block:: python
+
+ ray.init(address="auto")
+
+ .. group-tab:: Java
+
+ You need to add the ``ray.redis.address`` parameter to your command line (like ``-Dray.redis.address=...``).
+
+ You need to add the ``ray.job.resource-path`` parameter as well. Your jar files must be distributed to all the nodes of the Ray cluster before running your code. You also need to make sure the paths of jar files are the same among nodes. Let's say your jar files are located in ``/path/to/jars/``, all files under this path will be loaded by worker processes.
+
+ To connect your program to the Ray cluster, run it like this:
+
+ .. code-block:: bash
+
+ java -classpath /path/to/jars/ \
+ -Dray.job.resource-path=/path/to/jars/ \
+ -Dray.redis.address= \
+
+
+ .. note:: Specifying ``auto`` as the Redis address hasn't been implemented in Java yet. You need to provide the actual Redis address. You can find the address of the Redis server from the output of the ``ray up`` command.
+
+ Your driver code **only** needs to execute on one machine in the cluster (usually the head node).
+
+ .. note:: Without the address parameter, your Ray program will only be parallelized across a single machine!
Manual cluster setup
~~~~~~~~~~~~~~~~~~~~
@@ -90,19 +190,31 @@ The command will print out the address of the Redis server that was started (and
$ ray start --address=
-Turning off parallelism
------------------------
+Local mode
+----------
.. caution:: This feature is maintained solely to help with debugging, so it's possible you may encounter some issues. If you do, please `file an issue `_.
-By default, Ray will parallelize its workload. However, if you need to debug your Ray program, it may be easier to do everything on a single process. You can force all Ray functions to occur on a single process with ``local_mode`` by calling the following:
+By default, Ray will parallelize its workload and run tasks on multiple processes and multiple nodes. However, if you need to debug your Ray program, it may be easier to do everything on a single process. You can force all Ray functions to occur on a single process by enabling local mode as the following:
-.. code-block:: python
+.. tabs::
+
+ .. code-tab:: python
ray.init(local_mode=True)
+ .. group-tab:: Java
+
+ .. code-block:: bash
+
+ java -classpath \
+ -Dray.local-mode=true \
+
+
Note that some behavior such as setting global process variables may not work as expected.
+.. note:: If you just want to run your Java code in local mode, you can run it without Ray or even Python installed.
+
What's next?
------------
diff --git a/doc/source/walkthrough.rst b/doc/source/walkthrough.rst
index 7333a77ea..2250e6a57 100644
--- a/doc/source/walkthrough.rst
+++ b/doc/source/walkthrough.rst
@@ -15,7 +15,14 @@ Java demo code in this documentation can be found `here `_ and `Ray Runtime `_ as dependencies. We don't publish snapshot versions right now.
Starting Ray
------------
@@ -35,14 +42,14 @@ You can start Ray on a single machine by adding this to your code.
.. code-tab:: java
- import io.ray.Ray;
+ import io.ray.api.Ray;
public class MyRayApp {
public static void main(String[] args) {
// Start Ray runtime. If you're connecting to an existing cluster, you can set
// the `-Dray.redis.address=` java system property.
- Ray.init()
+ Ray.init();
...
}
}
diff --git a/java/api/src/main/java/io/ray/api/Ray.java b/java/api/src/main/java/io/ray/api/Ray.java
index 20c5422c6..d7db1f46b 100644
--- a/java/api/src/main/java/io/ray/api/Ray.java
+++ b/java/api/src/main/java/io/ray/api/Ray.java
@@ -37,7 +37,7 @@ public final class Ray extends RayCall {
*
* @param factory A factory that produces the runtime instance.
*/
- public static synchronized void init(RayRuntimeFactory factory) {
+ private static synchronized void init(RayRuntimeFactory factory) {
if (runtime == null) {
runtime = factory.createRayRuntime();
Runtime.getRuntime().addShutdownHook(new Thread(Ray::shutdown));
@@ -54,6 +54,14 @@ public final class Ray extends RayCall {
}
}
+ /**
+ * Check if {@link #init} has been called yet.
+ * @return True if {@link #init} has already been called and false otherwise.
+ */
+ public static boolean isInitialized() {
+ return runtime != null;
+ }
+
/**
* Store an object in the object store.
*
diff --git a/java/runtime/src/main/java/io/ray/runtime/config/RayConfig.java b/java/runtime/src/main/java/io/ray/runtime/config/RayConfig.java
index 1c80a6d86..e2197cfd1 100644
--- a/java/runtime/src/main/java/io/ray/runtime/config/RayConfig.java
+++ b/java/runtime/src/main/java/io/ray/runtime/config/RayConfig.java
@@ -130,7 +130,11 @@ public class RayConfig {
workerMode = localWorkerMode;
boolean isDriver = workerMode == WorkerType.DRIVER;
// Run mode.
- runMode = config.getEnum(RunMode.class, "ray.run-mode");
+ if (config.hasPath("ray.local-mode")) {
+ runMode = config.getBoolean("ray.local-mode") ? RunMode.SINGLE_PROCESS : RunMode.CLUSTER;
+ } else {
+ runMode = config.getEnum(RunMode.class, "ray.run-mode");
+ }
// Node ip.
if (config.hasPath("ray.node-ip")) {
nodeIp = config.getString("ray.node-ip");