REP: 106 Title: Polled topics Author: Dirk Thomas Status: Accepted Type: Standards Track Content-Type: text/x-rst Created: 20-Dec-2010 ROS-Version: 1.6 Post-History: 20-Dec-2010
This REP adds support for filtering messages directly at the publishing node. The filtering configuration can be modified dynamically at runtime. It does not require additional nodes to be integrated for performing the filtering.
In several scenarios a subscriber needs only a subset of messages published on a particular topic. Example use cases are:
- Reduce frequency of messages, e.g., a lower number messages per second might be sufficient for visualizing the information.
- Polling messages from topics, e.g. requesting only a single (or any other fixed number of) message(s).
The filtering cannot be performed after receiving the messages since the available bandwidth between publisher (e.g. running on a mobile robot) and subscriber (e.g. a GUI) running on an external computer might be (severly) constrained.
Depending on the scenario the demand for receiving messages of a specific topic might change dynamically at runtime. It should be possible to switch seemlessly between normal (unfiltered) and filtered subscription.
The utilization of an additional filter node is not an optimal solution. Any topic in a large application might be subscribed to with particular filter constraints. The filtering should solely depend on the subscriber:
- Filtering should not require manual adaption of the communication graph (e.g. by introducing a new filtering node).
Currently the package message_filters is used to filter messages. Even when it is running on the same host as the publisher it implies an overhead which would be avoided with this REP:
- All messages need to be marshaled and transfered to the filtering node (even if skipped / not relayed by the filter). For high update rate topics, large complex messages or resource restricted platforms the overhead is significant.
- The publisher is not aware of the active subscribers. The (optional) awareness of the publisher of the subsequent filtering enables skipping resource intensive computations of later dropped messages.
In the first step the filtering should enable simple polling of messages. For that the subscriber must pass the number of polled messages to each publisher. This counter is than decreased by the publisher until it reaches zero, which would result in dropping any further published messages.
In a future extension it might even be imaginable to pass i.e. a Python function which performs the filtering on the publisher.
The implementation consists of three parts:
- The communication protocol to realize filter functionality. It must be implemented for each client library.
- The API for the subscribing node which makes the new features accessible to userland code.
- The API for the publishing node to make information available which messages aresubsequently passed.
The communication protocol is extended with the following opcodes:
- setPollCounter with one argument N. Sets the poll counter to the value N, which demands for the next N message of the topic (actually N messages from each publisher). The argument value zero can be used to drop all further messages.
- addPollCounter with one argument N. Increases the poll counter by the value N.
- restoreUnfilteredMode without arguments. Enables to switch back to normal (unfiltered) subscription.
In order to make filtering work from the beginning an additional flag useFiltering must be passes at connection establishment. This initializes the poll counter with zero and prevents sending messages in the timeframe between the subscription and the first received poll-opcode.
The subscriber must be able to check, if the publisher supports the requested filtering mode. If not: the userland-code might implement a reasonable fallback behavior e.g. filter after reception.
The subscribe methods of the NodeHandle class is extended with an additional boolean parameter useFiltering.
The Subscriber class is extended with additional methods - one for each opcode.
The Publisher class is extended with a new method getActiveNumSubscribers. In contrast to the method getNumSubscribers it returns the subscribers, which will not drop the next published message. If this method would return zero the publisher can omit any computations to calculate the unnecessary message. Nevertheless in order for the poll counter to be decreased the publisher must call the publish method with e.g. a dummy message.
Existing nodes not using the newly introduced filtering functionality continue to work with no changes.
The message_filters package might utilize this new functionality when appropriate.
This document has been placed in the public domain.