diff --git a/doc/reference/reference_lua/box.rst b/doc/reference/reference_lua/box.rst index 1868881ab..efa4cd39e 100644 --- a/doc/reference/reference_lua/box.rst +++ b/doc/reference/reference_lua/box.rst @@ -37,6 +37,7 @@ with ``box``, with no arguments. The ``box`` module contains: box_txn_management box_sql + box_events box_once box_snapshot diff --git a/doc/reference/reference_lua/box_events.rst b/doc/reference/reference_lua/box_events.rst new file mode 100644 index 000000000..60a533040 --- /dev/null +++ b/doc/reference/reference_lua/box_events.rst @@ -0,0 +1,82 @@ +.. _box-watchers: + +Event watchers +============== + +The ``box`` module contains some features related to event subscriptions, also known as :term:`watchers `. +The subscriptions are used to inform the client about server-side :term:`events `. +Each event subscription is defined by a certain key. + +.. glossary:: + + Event + + An event is a state change or a system update that triggers the action of other systems. + To read more about built-in events in Tarantool, + check the :doc:`system events ` section. + + State + A state is an internally stored key-value pair. + The key is a string. + The value is an arbitrary type that can be encoded as MsgPack. + To update a state, use the ``box.broadcast()`` function. + + Watcher + A watcher is a :doc:`callback ` that is invoked when a state change occurs. + To register a local watcher, use the ``box.watch()`` function. + To create a remote watcher, use the ``watch()`` function from the ``net.box`` module. + Note that it is possible to register more than one watcher for the same key. + +How a watcher works +------------------- + +First, you register a watcher. +After that, the watcher callback is invoked for the first time. +In this case, the callback is triggered whether or not the key has already been broadcast. +All subsequent invocations are triggered with :doc:`box.broadcast() ` +called on the remote host. +If a watcher is subscribed for a key that has not been broadcast yet, the callback is triggered only once, +after the registration of the watcher. + +The watcher callback takes two arguments. +The first argument is the name of the key for which it was registered. +The second one contains current key data. +The callback is always invoked in a new fiber. It means that it is allowed to yield in it. +A watcher callback is never executed in parallel with itself. +If the key is updated while the watcher callback is running, the callback will be invoked again with the new +value as soon as it returns. + +``box.watch`` and ``box.broadcast`` functions can be used before :doc:`box.cfg `. + +Below is a list of all functions and pages related to watchers or events. + +.. container:: table + + .. rst-class:: left-align-column-1 + .. rst-class:: left-align-column-2 + + .. list-table:: + :widths: 25 75 + :header-rows: 1 + + * - Name + - Use + + * - :doc:`./box_events/watch` + - Create a local watcher. + + * - :ref:`conn:watch() ` + - Create a watcher for the remote host. + + * - :doc:`./box_events/broadcast` + - Update a state. + + * - :ref:`Built-in events ` + - Predefined events in Tarantool + +.. toctree:: + :hidden: + + box_events/watch + box_events/broadcast + box_events/system_events \ No newline at end of file diff --git a/doc/reference/reference_lua/box_events/broadcast.rst b/doc/reference/reference_lua/box_events/broadcast.rst new file mode 100644 index 000000000..45aa91e17 --- /dev/null +++ b/doc/reference/reference_lua/box_events/broadcast.rst @@ -0,0 +1,28 @@ +.. _box-broadcast: + +================================================================================ +box.broadcast() +================================================================================ + +.. function:: box.broadcast(key, value) + + Update the value of a particular key and notify all key watchers of the update. + + :param string key: key name of the event to subscribe to + :param value: any data that can be encoded in MsgPack + + :return: none + + **Possible errors:** + + * The value can't be encoded as MsgPack. + * The key refers to a ``box.`` system event + + **Example:** + + .. code-block:: lua + + -- Broadcast value 42 for the 'foo' key. + box.broadcast('foo', 42) + + diff --git a/doc/reference/reference_lua/box_events/system_events.rst b/doc/reference/reference_lua/box_events/system_events.rst new file mode 100644 index 000000000..8dfaf0c7f --- /dev/null +++ b/doc/reference/reference_lua/box_events/system_events.rst @@ -0,0 +1,121 @@ +.. _system-events: + +System events +============= + +Predefined events have a special naming schema -- theirs names always start with the reserved ``box.`` prefix. +It means that you cannot create new events with it. + +The system processes the following events: + +* ``box.id`` +* ``box.status`` +* ``box.election`` +* ``box.schema`` + +In response to each event, the server sends back certain ``IPROTO`` fields. + +The events are available from the beginning as non-:ref:`MP_NIL `. +If a watcher subscribes to a system event before it has been broadcast, +it receives an empty table for the event value. + +The event is generated when there is a change in any of the values listed in the event. +For example, see the parameters in the ``box.id`` event below -- ``id``, ``instance_uuid``, and ``replicaset_uuid``. +Suppose the ``ìd`` value (``box.info.id``) has changed. +This triggers the ``box.info`` event, which states that the value of ``box.info.id`` has changed, +while ``box.info.uuid`` and ``box.info.cluster.uuid`` remain the same. + +box.id +~~~~~~ + +Contains :ref:`identification ` of the instance. +Value changes are rare. + +* ``id``: the numeric instance ID is unknown before the registration. + For anonymous replicas, the value is ``0`` until they are officially registered. + +* ``instance_uuid``: the UUID of the instance never changes after the first + :doc:`box.cfg `. + The value is unknown before the ``box.cfg`` call. + +* ``replicaset_uuid``: the value is unknown until the instance joins a replicaset or boots a new one. + +.. code-block:: none + + -- box.id value + { + MP_STR “id”: MP_UINT; box.info.id, + MP_STR “instance_uuid”: MP_UUID; box.info.uuid, + MP_STR “replicaset_uuid”: MP_UUID box.info.cluster.uuid, + } + +box.status +~~~~~~~~~~ + +Contains generic information about the instance status. + +* ``is_ro``: :ref:`indicates the read-only mode ` or the ``orphan`` status. +* ``is_ro_cfg``: indicates the :ref:`read_only ` mode for the instance. +* ``status``: shows the status of an instance. + +.. code-block:: none + + { + MP_STR “is_ro”: MP_BOOL box.info.ro, + MP_STR “is_ro_cfg”: MP_BOOL box.cfg.read_only, + MP_STR “status”: MP_STR box.info.status, + } + +box.election +~~~~~~~~~~~~ + +Contains fields of :doc:`box.info.election ` +that are necessary to find out the most recent writable leader. + +* ``term``: shows the current election term. +* ``role``: indicates the election state of the node -- ``leader``, ``follower``, or ``candidate``. +* ``is_ro``: :ref:`indicates the read-only mode ` or the ``orphan`` status. +* ``leader``: shows the leader node ID in the current term. + +.. code-block:: none + + { + MP_STR “term”: MP_UINT box.info.election.term, + MP_STR “role”: MP_STR box.info.election.state, + MP_STR “is_ro”: MP_BOOL box.info.ro, + MP_STR “leader”: MP_UINT box.info.election.leader, + } + +box.schema +~~~~~~~~~~ + +Contains schema-related data. + +* ``version``: shows the schema version. + +.. code-block:: none + + { + MP_STR “version”: MP_UINT schema_version, + } + +Usage example +------------- + +.. code-block:: lua + + local conn = net.box.connect(URI) + local log = require('log') + -- Subscribe to updates of key 'box.id' + local w = conn:watch('box.id', function(key, value) + assert(key == 'box.id') + log.info("The box.id value is '%s'", value) + end) + +If you want to unregister the watcher when it's no longer needed, use the following command: + +.. code-block:: lua + + w:unregister() + + diff --git a/doc/reference/reference_lua/box_events/watch.rst b/doc/reference/reference_lua/box_events/watch.rst new file mode 100644 index 000000000..52a9a10e2 --- /dev/null +++ b/doc/reference/reference_lua/box_events/watch.rst @@ -0,0 +1,50 @@ +.. _box-watch: + +================================================================================ +box.watch() +================================================================================ + +.. function:: box.watch(key, func) + + Subscribe to events broadcast by a local host. + + :param string key: key name of the event to subscribe to + :param function func: callback to invoke when the key value is updated + + :return: a watcher handle. The handle consists of one method -- ``unregister()``, which unregisters the watcher. + + To read more about watchers, see the :ref:`Functions for watchers ` section. + + .. note:: + + Keep in mind that garbage collection of a watcher handle doesn't lead to the watcher's destruction. + In this case, the watcher remains registered. + It is okay to discard the result of ``watch`` function if the watcher will never be unregistered. + + **Example:** + + Server: + + .. code-block:: lua + + -- Broadcast value 42 for the 'foo' key. + box.broadcast('foo', 42) + + Client: + + .. code-block:: lua + + conn = require('net.box').connect(URI) + local log = require('log') + -- Subscribe to updates of the 'foo' key. + local w = box.watch('foo', function(key, value) + assert(key == 'foo') + log.info("The box.id value is '%d'", value) + end) + + If you don't need the watcher anymore, you can unregister it using the command below: + + .. code-block:: lua + + w:unregister() + diff --git a/doc/reference/reference_lua/net_box.rst b/doc/reference/reference_lua/net_box.rst index c154c0a7e..ec1909c07 100644 --- a/doc/reference/reference_lua/net_box.rst +++ b/doc/reference/reference_lua/net_box.rst @@ -1,4 +1,4 @@ -.. _net_box-module: +zc.. _net_box-module: -------------------------------------------------------------------------------- Module net.box @@ -125,14 +125,16 @@ Below is a list of all ``net.box`` functions. * - :ref:`conn:call() ` - Call a stored procedure * - :ref:`conn:timeout() ` - - Set a timeout + - Set a timeout + * - :ref:`conn:watch() ` + - Subscribe to events broadcast by a remote host * - :ref:`conn:on_connect() ` - Define a connect trigger * - :ref:`conn:on_disconnect() ` - Define a disconnect trigger * - :ref:`conn:on_schema_reload() ` - Define a trigger when schema is modified - * - :ref:`conn:new_stream() ` + * - :ref:`conn:new_stream() ` - Create a stream * - :ref:`stream:begin() ` - Begin a stream transaction @@ -216,7 +218,7 @@ Below is a list of all ``net.box`` functions. support the specified features, the connection will fail with an error message. With ``required_protocol_features = {'transactions'}``, all connections fail where the server has ``transactions: false``. - + .. container:: table .. list-table:: @@ -240,7 +242,7 @@ Below is a list of all ``net.box`` functions. - IPROTO_FEATURE_ERROR_EXTENSION - 2 and newer * - ``watchers`` - - Requires remote watchers support on the server + - Requires remote :ref:`watchers ` support on the server - IPROTO_FEATURE_WATCHERS - 3 and newer @@ -533,7 +535,61 @@ Below is a list of all ``net.box`` functions. - B ... + .. _conn-watch: + + .. method:: watch(key, func) + + Subscribe to events broadcast by a remote host. + + :param string key: a key name of an event to subscribe to + :param function func: a callback to invoke when the key value is updated + :return: a watcher handle. The handle consists of one method -- ``unregister()``, which unregisters the watcher. + + To read more about watchers, see the :ref:`Functions for watchers ` section. + + The method has the same syntax as the :doc:`box.watch() ` + function, which is used for subscribing to events locally. + + Watchers survive reconnection (see the ``reconnect_after`` connection :ref:`option `). + All registered watchers are automatically resubscribed when the + connection is reestablished. + + If a remote host supports watchers, the ``watchers`` key will be set in the + connection ``peer_protocol_features``. + For details, check the :ref:`net.box features table `. + + .. note:: + + Keep in mind that garbage collection of a watcher handle doesn't lead to the watcher's destruction. + In this case, the watcher remains registered. + It is okay to discard the result of ``watch`` function if the watcher will never be unregistered. + + **Example:** + + Server: + + .. code-block:: lua + + -- Broadcast value 42 for the 'foo' key. + box.broadcast('foo', 42) + + Client: + + .. code-block:: lua + + conn = net.box.connect(URI) + local log = require('log') + -- Subscribe to updates of the 'foo' key. + w = conn:watch('foo', function(key, value) + assert(key == 'foo') + log.info("The box.id value is '%d'", value) + end) + + If you don't need the watcher anymore, you can unregister it using the command below: + + .. code-block:: lua + w:unregister() .. _conn-timeout: diff --git a/doc/reference/reference_rock/vshard/index.rst b/doc/reference/reference_rock/vshard/index.rst index 41ee7813b..f63cc3803 100644 --- a/doc/reference/reference_rock/vshard/index.rst +++ b/doc/reference/reference_rock/vshard/index.rst @@ -11,13 +11,13 @@ scaling in Tarantool. Check out the :ref:`Quick start guide ` -- or dive into the complete ``vshard`` documentation: -.. toctree:: - :maxdepth: 2 - :numbered: 0 +.. toctree:: + :maxdepth: 2 + :numbered: 0 - vshard_summary_index - vshard_architecture - vshard_admin - vshard_quick - vshard_ref - vshard_api + vshard_summary_index + vshard_architecture + vshard_admin + vshard_quick + vshard_ref + vshard_api diff --git a/doc/reference/reference_rock/vshard/vshard_index.rst b/doc/reference/reference_rock/vshard/vshard_index.rst index 053097866..2f34faafa 100644 --- a/doc/reference/reference_rock/vshard/vshard_index.rst +++ b/doc/reference/reference_rock/vshard/vshard_index.rst @@ -11,12 +11,13 @@ Sharding Check out the :ref:`Quick start guide ` -- or dive into the complete ``vshard`` documentation: -.. toctree:: - :maxdepth: 2 - :numbered: 0 +.. toctree:: + :maxdepth: 2 + :numbered: 0 + + vshard_architecture + vshard_admin + vshard_quick + vshard_ref + vshard_api - vshard_architecture - vshard_admin - vshard_quick - vshard_ref - vshard_api