5. Request/Response Semantics
CoAP operates under a similar request/response model as HTTP: a CoAP
endpoint in the role of a "client" sends one or more CoAP requests to
a "server", which services the requests by sending CoAP responses.
Unlike HTTP, requests and responses are not sent over a previously
established connection but are exchanged asynchronously over CoAP
A CoAP request consists of the method to be applied to the resource,
the identifier of the resource, a payload and Internet media type (if
any), and optional metadata about the request.
CoAP supports the basic methods of GET, POST, PUT, and DELETE, which
are easily mapped to HTTP. They have the same properties of safe
(only retrieval) and idempotent (you can invoke it multiple times
with the same effects) as HTTP (see Section 9.1 of [RFC2616]). The
GET method is safe; therefore, it MUST NOT take any other action on a
resource other than retrieval. The GET, PUT, and DELETE methods MUST
be performed in such a way that they are idempotent. POST is not
idempotent, because its effect is determined by the origin server and
dependent on the target resource; it usually results in a new
resource being created or the target resource being updated.
A request is initiated by setting the Code field in the CoAP header
of a Confirmable or a Non-confirmable message to a Method Code and
including request information.
The methods used in requests are described in detail in Section 5.8.
After receiving and interpreting a request, a server responds with a
CoAP response that is matched to the request by means of a client-
generated token (Section 5.3); note that this is different from the
Message ID that matches a Confirmable message to its Acknowledgement.
A response is identified by the Code field in the CoAP header being
set to a Response Code. Similar to the HTTP Status Code, the CoAP
Response Code indicates the result of the attempt to understand and
satisfy the request. These codes are fully defined in Section 5.9.
The Response Code numbers to be set in the Code field of the CoAP
header are maintained in the CoAP Response Code Registry
0 1 2 3 4 5 6 7
|class| detail |
Figure 9: Structure of a Response Code
The upper three bits of the 8-bit Response Code number define the
class of response. The lower five bits do not have any
categorization role; they give additional detail to the overall class
As a human-readable notation for specifications and protocol
diagnostics, CoAP code numbers including the Response Code are
documented in the format "c.dd", where "c" is the class in decimal,
and "dd" is the detail as a two-digit decimal. For example,
"Forbidden" is written as 4.03 -- indicating an 8-bit code value of
hexadecimal 0x83 (4*0x20+3) or decimal 131 (4*32+3).
There are 3 classes of Response Codes:
2 - Success: The request was successfully received, understood, and
4 - Client Error: The request contains bad syntax or cannot be
5 - Server Error: The server failed to fulfill an apparently valid
The Response Codes are designed to be extensible: Response Codes in
the Client Error or Server Error class that are unrecognized by an
endpoint are treated as being equivalent to the generic Response Code
of that class (4.00 and 5.00, respectively). However, there is no
generic Response Code indicating success, so a Response Code in the
Success class that is unrecognized by an endpoint can only be used to
determine that the request was successful without any further
The possible Response Codes are described in detail in Section 5.9.
Responses can be sent in multiple ways, which are defined in the
In the most basic case, the response is carried directly in the
Acknowledgement message that acknowledges the request (which requires
that the request was carried in a Confirmable message). This is
called a "Piggybacked Response".
The response is returned in the Acknowledgement message, independent
of whether the response indicates success or failure. In effect, the
response is piggybacked on the Acknowledgement message, and no
separate message is required to return the response.
Implementation Note: The protocol leaves the decision whether to
piggyback a response or not (i.e., send a separate response) to
the server. The client MUST be prepared to receive either. On
the quality-of-implementation level, there is a strong expectation
that servers will implement code to piggyback whenever possible --
saving resources in the network and both at the client and at the
It may not be possible to return a piggybacked response in all cases.
For example, a server might need longer to obtain the representation
of the resource requested than it can wait to send back the
Acknowledgement message, without risking the client repeatedly
retransmitting the request message (see also the discussion of
PROCESSING_DELAY in Section 4.8.2). The response to a request
carried in a Non-confirmable message is always sent separately (as
there is no Acknowledgement message).
One way to implement this in a server is to initiate the attempt to
obtain the resource representation and, while that is in progress,
time out an acknowledgement timer. A server may also immediately
send an acknowledgement if it knows in advance that there will be no
piggybacked response. In both cases, the acknowledgement effectively
is a promise that the request will be acted upon later.
When the server finally has obtained the resource representation, it
sends the response. When it is desired that this message is not
lost, it is sent as a Confirmable message from the server to the
client and answered by the client with an Acknowledgement, echoing
the new Message ID chosen by the server. (It may also be sent as a
Non-confirmable message; see Section 5.2.3.)
When the server chooses to use a separate response, it sends the
Acknowledgement to the Confirmable request as an Empty message. Once
the server sends back an Empty Acknowledgement, it MUST NOT send back
the response in another Acknowledgement, even if the client
retransmits another identical request. If a retransmitted request is
received (perhaps because the original Acknowledgement was delayed),
another Empty Acknowledgement is sent, and any response MUST be sent
as a separate response.
If the server then sends a Confirmable response, the client's
Acknowledgement to that response MUST also be an Empty message (one
that carries neither a request nor a response). The server MUST stop
retransmitting its response on any matching Acknowledgement (silently
ignoring any Response Code or payload) or Reset message.
Implementation Notes: Note that, as the underlying datagram
transport may not be sequence-preserving, the Confirmable message
carrying the response may actually arrive before or after the
Acknowledgement message for the request; for the purposes of
terminating the retransmission sequence, this also serves as an
acknowledgement. Note also that, while the CoAP protocol itself
does not make any specific demands here, there is an expectation
that the response will come within a time frame that is reasonable
from an application point of view. As there is no underlying
transport protocol that could be instructed to run a keep-alive
mechanism, the requester may want to set up a timeout that is
unrelated to CoAP's retransmission timers in case the server is
destroyed or otherwise unable to send the response.
If the request message is Non-confirmable, then the response SHOULD
be returned in a Non-confirmable message as well. However, an
endpoint MUST be prepared to receive a Non-confirmable response
(preceded or followed by an Empty Acknowledgement message) in reply
to a Confirmable request, or a Confirmable response in reply to a
5.3. Request/Response Matching
Regardless of how a response is sent, it is matched to the request by
means of a token that is included by the client in the request, along
with additional address information of the corresponding endpoint.
The Token is used to match a response with a request. The token
value is a sequence of 0 to 8 bytes. (Note that every message
carries a token, even if it is of zero length.) Every request
carries a client-generated token that the server MUST echo (without
modification) in any resulting response.
A token is intended for use as a client-local identifier for
differentiating between concurrent requests (see Section 5.3); it
could have been called a "request ID".
The client SHOULD generate tokens in such a way that tokens currently
in use for a given source/destination endpoint pair are unique.
(Note that a client implementation can use the same token for any
request if it uses a different endpoint each time, e.g., a different
source port number.) An empty token value is appropriate e.g., when
no other tokens are in use to a destination, or when requests are
made serially per destination and receive piggybacked responses.
There are, however, multiple possible implementation strategies to
A client sending a request without using Transport Layer Security
(Section 9) SHOULD use a nontrivial, randomized token to guard
against spoofing of responses (Section 11.4). This protective use of
tokens is the reason they are allowed to be up to 8 bytes in size.
The actual size of the random component to be used for the Token
depends on the security requirements of the client and the level of
threat posed by spoofing of responses. A client that is connected to
the general Internet SHOULD use at least 32 bits of randomness,
keeping in mind that not being directly connected to the Internet is
not necessarily sufficient protection against spoofing. (Note that
the Message ID adds little in protection as it is usually
sequentially assigned, i.e., guessable, and can be circumvented by
spoofing a separate response.) Clients that want to optimize the
Token length may further want to detect the level of ongoing attacks
(e.g., by tallying recent Token mismatches in incoming messages) and
adjust the Token length upwards appropriately. [RFC4086] discusses
randomness requirements for security.
An endpoint receiving a token it did not generate MUST treat the
token as opaque and make no assumptions about its content or
5.3.2. Request/Response Matching Rules
The exact rules for matching a response to a request are as follows:
1. The source endpoint of the response MUST be the same as the
destination endpoint of the original request.
2. In a piggybacked response, the Message ID of the Confirmable
request and the Acknowledgement MUST match, and the tokens of the
response and original request MUST match. In a separate
response, just the tokens of the response and original request
In case a message carrying a response is unexpected (the client is
not waiting for a response from the identified endpoint, at the
endpoint addressed, and/or with the given token), the response is
rejected (Sections 4.2 and 4.3).
Implementation Note: A client that receives a response in a CON
message may want to clean up the message state right after sending
the ACK. If that ACK is lost and the server retransmits the CON,
the client may no longer have any state to which to correlate this
response, making the retransmission an unexpected message; the
client will likely send a Reset message so it does not receive any
more retransmissions. This behavior is normal and not an
indication of an error. (Clients that are not aggressively
optimized in their state memory usage will still have message
state that will identify the second CON as a retransmission.
Clients that actually expect more messages from the server
[OBSERVE] will have to keep state in any case.)
Both requests and responses may include a list of one or more
options. For example, the URI in a request is transported in several
options, and metadata that would be carried in an HTTP header in HTTP
is supplied as options as well.
CoAP defines a single set of options that are used in both requests
The semantics of these options along with their properties are
defined in detail in Section 5.10.
Not all options are defined for use with all methods and Response
Codes. The possible options for methods and Response Codes are
defined in Sections 5.8 and 5.9, respectively. In case an option is
not defined for a Method or Response Code, it MUST NOT be included by
a sender and MUST be treated like an unrecognized option by a
Options fall into one of two classes: "critical" or "elective". The
difference between these is how an option unrecognized by an endpoint
o Upon reception, unrecognized options of class "elective" MUST be
o Unrecognized options of class "critical" that occur in a
Confirmable request MUST cause the return of a 4.02 (Bad Option)
response. This response SHOULD include a diagnostic payload
describing the unrecognized option(s) (see Section 5.5.2).
o Unrecognized options of class "critical" that occur in a
Confirmable response, or piggybacked in an Acknowledgement, MUST
cause the response to be rejected (Section 4.2).
o Unrecognized options of class "critical" that occur in a Non-
confirmable message MUST cause the message to be rejected
Note that, whether critical or elective, an option is never
"mandatory" (it is always optional): these rules are defined in order
to enable implementations to stop processing options they do not
understand or implement.
Critical/elective rules apply to non-proxying endpoints. A proxy
processes options based on Unsafe/Safe-to-Forward classes as defined
in Section 5.7.
5.4.2. Proxy Unsafe or Safe-to-Forward and NoCacheKey
In addition to an option being marked as critical or elective,
options are also classified based on how a proxy is to deal with the
option if it does not recognize it. For this purpose, an option can
either be considered Unsafe to forward (UnSafe is set) or Safe-to-
Forward (UnSafe is clear).
In addition, for an option that is marked Safe-to-Forward, the option
number indicates whether or not it is intended to be part of the
Cache-Key (Section 5.6) in a request. If some of the NoCacheKey bits
are 0, it is; if all NoCacheKey bits are 1, it is not (see
Note: The Cache-Key indication is relevant only for proxies that do
not implement the given option as a request option and instead
rely on the Unsafe/Safe-to-Forward indication only. For example,
for ETag, actually using the request option as a part of the
Cache-Key is grossly inefficient, but it is the best thing one can
do if ETag is not implemented by a proxy, as the response is going
to differ based on the presence of the request option. A more
useful proxy that does implement the ETag request option is not
using ETag as a part of the Cache-Key.
NoCacheKey is indicated in three bits so that only one out of
eight codepoints is qualified as NoCacheKey, leaving seven out of
eight codepoints for what appears to be the more likely case.
Proxy behavior with regard to these classes is defined in
Option values are defined to have a specific length, often in the
form of an upper and lower bound. If the length of an option value
in a request is outside the defined range, that option MUST be
treated like an unrecognized option (see Section 5.4.1).
5.4.4. Default Values
Options may be defined to have a default value. If the value of an
option is intended to be this default value, the option SHOULD NOT be
included in the message. If the option is not present, the default
value MUST be assumed.
Where a critical option has a default value, this is chosen in such a
way that the absence of the option in a message can be processed
properly both by implementations unaware of the critical option and
by implementations that interpret this absence as the presence of the
default value for the option.
5.4.5. Repeatable Options
The definition of some options specifies that those options are
repeatable. An option that is repeatable MAY be included one or more
times in a message. An option that is not repeatable MUST NOT be
included more than once in a message.
If a message includes an option with more occurrences than the option
is defined for, each supernumerary option occurrence that appears
subsequently in the message MUST be treated like an unrecognized
option (see Section 5.4.1).
5.4.6. Option Numbers
An Option is identified by an option number, which also provides some
additional semantics information, e.g., odd numbers indicate a
critical option, while even numbers indicate an elective option.
Note that this is not just a convention, it is a feature of the
protocol: Whether an option is elective or critical is entirely
determined by whether its option number is even or odd.
More generally speaking, an Option number is constructed with a bit
mask to indicate if an option is Critical or Elective, Unsafe or
Safe-to-Forward, and, in the case of Safe-to-Forward, to provide a
Cache-Key indication as shown by the following figure. In the
following text, the bit mask is expressed as a single byte that is
applied to the least significant byte of the option number in
unsigned integer representation. When bit 7 (the least significant
bit) is 1, an option is Critical (and likewise Elective when 0).
When bit 6 is 1, an option is Unsafe (and likewise Safe-to-Forward
when 0). When bit 6 is 0, i.e., the option is not Unsafe, it is not
a Cache-Key (NoCacheKey) if and only if bits 3-5 are all set to 1;
all other bit combinations mean that it indeed is a Cache-Key. These
classes of options are explained in the next sections.
0 1 2 3 4 5 6 7
| | NoCacheKey| U | C |
Figure 10: Option Number Mask (Least Significant Byte)
An endpoint may use an equivalent of the C code in Figure 11 to
derive the characteristics of an option number "onum".
Critical = (onum & 1);
UnSafe = (onum & 2);
NoCacheKey = ((onum & 0x1e) == 0x1c);
Figure 11: Determining Characteristics from an Option Number
The option numbers for the options defined in this document are
listed in the "CoAP Option Numbers" registry (Section 12.2).
5.5. Payloads and Representations
Both requests and responses may include a payload, depending on the
Method or Response Code, respectively. If a Method or Response Code
is not defined to have a payload, then a sender MUST NOT include one,
and a recipient MUST ignore it.
The payload of requests or of responses indicating success is
typically a representation of a resource ("resource representation")
or the result of the requested action ("action result"). Its format
is specified by the Internet media type and content coding given by
the Content-Format Option. In the absence of this option, no default
value is assumed, and the format will need to be inferred by the
application (e.g., from the application context). Payload "sniffing"
SHOULD only be attempted if no content type is given.
Implementation Note: On a quality-of-implementation level, there is
a strong expectation that a Content-Format indication will be
provided with resource representations whenever possible. This is
not a "SHOULD" level requirement solely because it is not a
protocol requirement, and it also would be difficult to outline
exactly in what cases this expectation can be violated.
For responses indicating a client or server error, the payload is
considered a representation of the result of the requested action
only if a Content-Format Option is given. In the absence of this
option, the payload is a Diagnostic Payload (Section 5.5.2).
5.5.2. Diagnostic Payload
If no Content-Format option is given, the payload of responses
indicating a client or server error is a brief human-readable
diagnostic message, explaining the error situation. This diagnostic
message MUST be encoded using UTF-8 [RFC3629], more specifically
using Net-Unicode form [RFC5198].
The message is similar to the Reason-Phrase on an HTTP status line.
It is not intended for end users but for software engineers that
during debugging need to interpret it in the context of the present,
English-language specification; therefore, no mechanism for language
tagging is needed or provided. In contrast to what is usual in HTTP,
the payload SHOULD be empty if there is no additional information
beyond the Response Code.
5.5.3. Selected Representation
Not all responses carry a payload that provides a representation of
the resource addressed by the request. It is, however, sometimes
useful to be able to refer to such a representation in relation to a
response, independent of whether it actually was enclosed.
We use the term "selected representation" to refer to the current
representation of a target resource that would have been selected in
a successful response if the corresponding request had used the
method GET and excluded any conditional request options
Certain response options provide metadata about the selected
representation, which might differ from the representation included
in the message for responses to some state-changing methods. Of the
response options defined in this specification, only the ETag
response option (Section 5.10.6) is defined as metadata about the
5.5.4. Content Negotiation
A server may be able to supply a representation for a resource in one
of multiple representation formats. Without further information from
the client, it will provide the representation in the format it
By using the Accept Option (Section 5.10.4) in a request, the client
can indicate which content-format it prefers to receive.
CoAP endpoints MAY cache responses in order to reduce the response
time and network bandwidth consumption on future, equivalent
The goal of caching in CoAP is to reuse a prior response message to
satisfy a current request. In some cases, a stored response can be
reused without the need for a network request, reducing latency and
network round-trips; a "freshness" mechanism is used for this purpose
(see Section 5.6.1). Even when a new request is required, it is
often possible to reuse the payload of a prior response to satisfy
the request, thereby reducing network bandwidth usage; a "validation"
mechanism is used for this purpose (see Section 5.6.2).
Unlike HTTP, the cacheability of CoAP responses does not depend on
the request method, but it depends on the Response Code. The
cacheability of each Response Code is defined along the Response Code
definitions in Section 5.9. Response Codes that indicate success and
are unrecognized by an endpoint MUST NOT be cached.
For a presented request, a CoAP endpoint MUST NOT use a stored
o the presented request method and that used to obtain the stored
o all options match between those in the presented request and those
of the request used to obtain the stored response (which includes
the request URI), except that there is no need for a match of any
request options marked as NoCacheKey (Section 5.4) or recognized
by the Cache and fully interpreted with respect to its specified
cache behavior (such as the ETag request option described in
Section 5.10.6; see also Section 5.4.2), and
o the stored response is either fresh or successfully validated as
The set of request options that is used for matching the cache entry
is also collectively referred to as the "Cache-Key". For URI schemes
other than coap and coaps, matching of those options that constitute
the request URI may be performed under rules specific to the URI
5.6.1. Freshness Model
When a response is "fresh" in the cache, it can be used to satisfy
subsequent requests without contacting the origin server, thereby
The mechanism for determining freshness is for an origin server to
provide an explicit expiration time in the future, using the Max-Age
Option (see Section 5.10.5). The Max-Age Option indicates that the
response is to be considered not fresh after its age is greater than
the specified number of seconds.
The Max-Age Option defaults to a value of 60. Thus, if it is not
present in a cacheable response, then the response is considered not
fresh after its age is greater than 60 seconds. If an origin server
wishes to prevent caching, it MUST explicitly include a Max-Age
Option with a value of zero seconds.
If a client has a fresh stored response and makes a new request
matching the request for that stored response, the new response
invalidates the old response.
5.6.2. Validation Model
When an endpoint has one or more stored responses for a GET request,
but cannot use any of them (e.g., because they are not fresh), it can
use the ETag Option (Section 5.10.6) in the GET request to give the
origin server an opportunity both to select a stored response to be
used, and to update its freshness. This process is known as
"validating" or "revalidating" the stored response.
When sending such a request, the endpoint SHOULD add an ETag Option
specifying the entity-tag of each stored response that is applicable.
A 2.03 (Valid) response indicates the stored response identified by
the entity-tag given in the response's ETag Option can be reused
after updating it as described in Section 126.96.36.199.
Any other Response Code indicates that none of the stored responses
nominated in the request is suitable. Instead, the response SHOULD
be used to satisfy the request and MAY replace the stored response.