= nng_surveyor(7)
//
// Copyright 2018 Staysail Systems, Inc. <info@staysail.tech>
// Copyright 2018 Capitar IT Group BV <info@capitar.com>
//
// This document is supplied under the terms of the MIT License, a
// copy of which should be located in the distribution where this
// file was obtained (LICENSE.txt).  A copy of the license may also be
// found online at https://opensource.org/licenses/MIT.
//

== NAME

nng_surveyor - surveyor protocol

== SYNOPSIS

[source,c]
----
#include <nng/nng.h>
#include <nng/protocol/survey0/survey.h>
----

== DESCRIPTION

(((protocol, _surveyor_)))
The ((_surveyor_ protocol)) is one half of a ((survey pattern)).
In this pattern, a surveyor sends a survey, which is broadcast to all
peer respondents.
The respondents then have a chance to reply (but are not obliged to reply).
The survey itself is a timed event, so that responses
received after the survey has finished are discarded.

TIP: This protocol is useful in solving voting problems, such as
((leader election)) in cluster configurations, as well as certain kinds of
((service discovery)) problems.

The _surveyor_ protocol is the surveyor side, and the
<<nng_respondent.7#,_respondent_>> protocol is the respondent side.

=== Socket Operations

The <<nng_surveyor_open.3#,`nng_surveyor0_open()`>>
functions create a surveyor socket.
This socket may be used to send messages (surveys), and then to receive replies.
A reply can only be received after sending a survey.
A surveyor can normally expect to receive at most one reply from each responder.
(Messages can be duplicated in some topologies,
so there is no guarantee of this.)

Attempts to receive on a socket with no outstanding survey will result
in `NNG_ESTATE`.
If the survey times out while the surveyor is waiting
for replies, then the result will be `NNG_ETIMEDOUT`.

Only one survey can be outstanding at a time; sending another survey will
cancel the prior one, and any responses from respondents from the prior
survey that arrive after this will be discarded.

<<nng.7#raw_mode,Raw>> mode sockets ignore all these restrictions.

=== Protocol Versions

Only version 0 of this protocol is supported.
(At the time of writing, no other versions of this protocol have been defined.
An earlier and incompatible version of the protocol was used in older
pre-releases of
http://nanomsg.org[nanomsg], but was not released in any production
version.)

=== Protocol Options

The following protocol-specific options is available.

((`NNG_OPT_SURVEYOR_SURVEYTIME`))::

   This read/write option is an <<nng_duration.5#,`nng_duration`>>
   representing a postive number of milliseconds that following surveys
   will last. 
   When a new survey is started, a timer of this duration is also started.
   Any responses arriving this time will be discarded.
   Attempts to receive
   after the timer expires with no other surveys started will result in
   `NNG_ESTATE`.
   Attempts to receive when this timer expires will result in `NNG_ETIMEDOUT`.

=== Protocol Headers

(((backtrace)))
This form uses a "stack" of 32-bit big-endian identifiers.
There *must* be at least one identifier, the __survey ID__, which will be the
last element in the array, and *must* have the most significant bit set.

There may be additional __peer ID__s preceeding the survey ID.
These will be distinguishable from the survey ID by having their most
significant bit clear.

When a survey message is received by a forwarding node (see
<<nng_device.3#,`nng_device()`>>), the forwarding node prepends a
32-bit peer ID (which *must* have the most significant bit clear),
which is the forwarder's way of identifying the directly connected
peer from which it received the message.
(This peer ID, except for the
most significant bit, has meaning only to the forwarding node itself.)

It may help to think of prepending a peer ID as "pushing" a peer ID onto the
front of the stack of headers for the message.
(It will use the peer ID
it popped from the front to determine the next intermediate destination
for the response.)

When a response message is created, it is created using the same headers
that the survey contained.

A forwarding node can "pop" the peer ID it originally pushed on the
message, stripping it from the front of the message as it does so.

When the response finally arrives back at the initiating surveyor, it
should have only a single element in the message, which will be the
survey ID it originally used for the request.

// TODO: Insert reference to RFC.

== SEE ALSO

<<nng_surveyor_open.3#,nng_surveyor_open(3)>>,
<<nng_respondent.7#,nng_respondent(7)>>,
<<nng.7#,nng(7)>>
