AWS EC2 query protocol#
This specification defines the aws.protocols#ec2
protocol.
aws.protocols#ec2Query
trait#
- Summary
- Adds support for an HTTP protocol that sends requests in a
application/x-www-form-url-encoded
body and responses in XML documents. This protocol is an Amazon EC2-specific extension of theawsQuery
protocol. - Trait selector
service [trait|xmlNamespace]
Service shapes with the xmlNamespace trait
- Value type
- Annotation trait.
Important
- This protocol does not support document types.
- This protocol does not support HTTP binding traits. HTTP binding traits MUST be ignored if they are present.
$version: "2"
namespace smithy.example
use aws.protocols#ec2Query
@ec2Query
service MyService {
version: "2020-02-05"
}
aws.protocols#ec2QueryName
trait#
- Summary
- Allows a serialized query key to differ from a structure member name when used in the model.
- Trait selector
structure > member
Any structure member
- Value type
string
Important
The aws.protocols#ec2QueryName
trait is only used when serializing
operation inputs using the aws.protocols#ec2
protocol.
Given the following structure definition:
$version: "2"
use aws.protocols#ec2QueryName
structure MyStruct {
@ec2QueryName("foo")
bar: String
}
and the following values provided for MyStruct
,
"bar" = "baz"
the serialization of this structure as an input on the aws.protocols#ec2
protocol is:
MyStruct.foo=baz
Query key resolution#
The key component used to serialize a member in a request in ec2Query
is
resolved using the following process:
Use the value of the aws.protocols#ec2QueryName trait applied to the member, if present.
Use the value of the xmlName trait applied to the member with the first letter capitalized, if present.
Use the default value for the member, if present:
Member location Default value structure
memberThe member name
capitalizedunion
memberThe member name
capitalized
Supported traits#
The aws.protocols#ec2Query
protocol supports the following traits
that affect serialization:
Trait | Description |
---|---|
cors | Indicates that the service supports CORS. |
endpoint | Configures a custom operation endpoint. |
hostLabel | Binds a top-level operation input structure member to a label in the hostPrefix of an endpoint trait. |
ec2QueryName | By default, the form-urlencoded key segments used in serialized
structures are the same as a structure member name. The ec2QueryName
changes the key segment name to a custom value. See
Query key resolution for more information. |
xmlAttribute | Serializes an object property as an XML attribute rather than a nested XML element. |
xmlFlattened | By default, entries in lists, sets, and maps have values serialized in
nested elements specific to their type. The xmlFlattened trait
unwraps these elements into the containing structure. |
xmlName | By default, the XML element names and form-urlencoded key segments used
in serialized structures are the same as a structure member name. The
xmlName trait changes the these names to a custom value. See
Query key resolution for more information. |
xmlNamespace | Adds an xmlns namespace definition URI to XML element(s) generated for the targeted shape. |
timestampFormat | Defines a custom timestamp serialization format. |
requestCompression | Indicates that an operation supports compressing requests from clients to services. |
Important
This protocol does not support document types.
Default value serialization#
- To avoid information disclosure, serializers SHOULD omit the default value of structure members that are marked with the internal trait.
- Client deserializers SHOULD attempt to error correct structures that
omit a
@required
member by filling in a default zero value for the member. Error correction allows clients to continue to function while the server is in error.
Request serialization#
Requests SHALL be sent to the root URL (/
). Requests SHALL use a POST
request and a body that contains input parameters serialized with a
Content-Type of application/x-www-form-urlencoded
. All keys and
values MUST be encoded according to RFC 3986. Requests SHALL contain
a Content-Length header; this protocol does not support chunked
Transfer-Encoding.
Requests MUST include the following key value pairs in the serialized body:
Key | Value |
---|---|
Action |
The shape name of the operation's Shape ID. |
Version |
The value of the "version" property of the service. |
These, along with other input members, are serialized in the request body, concatenated with the following rules:
- "&" is used to separate member key-value pairs.
- "=" is used to separate member keys from values.
- "." is used to separate member name segments within keys.
x-www-form-urlencoded shape serialization#
Simple shapes are serialized according to the following rules:
Smithy type | Request entity |
---|---|
blob |
Text value that is base64 encoded. |
boolean |
Text value of either "true" or "false". |
byte |
Text value of the number. |
short |
Text value of the number. |
integer |
Text value of the number. |
long |
Text value of the number. |
float |
Text value of the number. |
double |
Text value of the number. |
bigDecimal |
Text value of the number, using scientific notation if an exponent is needed. Unfortunately, many parsers will either truncate the value or be unable to parse numbers that exceed the size of a double. |
bigInteger |
Text value of the number, using scientific notation if an exponent is needed. Unfortunately, many parsers will either truncate the value or be unable to parse numbers that exceed the size of a double. |
string |
UTF-8 value of the string. Empty strings are serialized as empty
values, meaning a Foo member set to an empty string would be
serialized as "&Foo=". |
timestamp |
Text value of the timestamp. This protocol uses date-time as the
default serialization. However, the timestampFormat
MAY be used to customize timestamp serialization. |
document |
Undefined. Document shapes are not supported in this protocol. |
Aggregate shapes are serialized with additional segments for members appended to the input's key.
Smithy type | Request entity |
---|---|
list |
Each value provided in the list is serialized as a separate key with a "." separator and a "1" indexed incrementing counter appended to the container's key. |
map |
Map serialization is currently undefined for this protocol. |
structure |
Each member value provided for the shape is serialized as a separate key with a "." separator and the member name appended to the container's key. See Query key resolution for how to serialize a property using a custom name. Members with null values are not serialized. |
union |
A union is serialized identically to a structure shape, but only a
single member can be set to a non-null value. |
Examples#
Important
These examples are non-exhaustive. See the Protocol compliance tests
for a suite of compliance tests for the ec2Query
protocol.
Structures and Unions#
Each member value provided for the shape is serialized as a separate key with a "." separator and the member name appended to the container's key. See Query key resolution for how to serialize a property using a custom name. Members with null values are not serialized.
For example, given the following:
@input
structure Ec2QueryStructuresInput {
foo: String
@ec2QueryName("A")
HasQueryName: String
@ec2QueryName("B")
@xmlName("IgnoreMe")
HasQueryAndXmlName: String
@xmlName("c")
UsesXmlName: String
baz: MyStructure
}
structure MyStructure {
temp: String
}
The x-www-form-urlencoded
serialization is:
Action=Ec2QueryStructures
&Version=2020-07-02
&Foo=bar
&A=example0
&B=example1
&C=example2
&Baz.Temp=example3
Lists#
Each value provided in the list is serialized as a separate key with a "." separator and a "1" indexed incrementing counter appended to the container's key.
For example, given the following:
@input
structure Ec2QueryListsInput {
ListArg: StringList
ComplexListArg: GreetingList
@ec2QueryName("Renamed")
@xmlName("IgnoreMe")
RenamedListArg: StringList
}
list StringList {
member: String
}
list GreetingList {
member: GreetingStruct
}
structure GreetingStruct {
hi: String
}
The application/x-www-form-urlencoded
serialization is:
Action=Ec2QueryLists
&Version=2020-07-02
&ListArg.1=foo
&ListArg.2=bar
&ListArg.3=baz
&ComplexListArg.1.Hi=hello
&ComplexListArg.2.Hi=hola
&Renamed.1=A
&Renamed.2=B
Response serialization#
The ec2Query
protocol serializes XML responses within an XML root node with
the name of the operation's output suffixed with "Response", which contains the
contents of the successful response.
The value of the uri
member of the xmlNamespace trait
is serialized in an xmlns
attribute on the response's XML root node. The
following is a sample response to an operation named XmlTest
.
<XmlTestResponse xmlns="https://example.com/">
<testValue>Hello!</testValue>
</XmlTestResponse>
XML shape serialization#
Smithy type | XML entity |
---|---|
blob |
XML text node with a value that is base64 encoded. |
boolean |
XML text node with a value either "true" or "false". |
byte |
XML text node with a value of the number. |
short |
XML text node with a value of the number. |
integer |
XML text node with a value of the number. |
long |
XML text node with a value of the number. |
float |
XML text node with a value of the number. |
double |
XML text node with a value of the number. |
bigDecimal |
XML text node with a value of the number, using scientific notation if an exponent is needed. Unfortunately, many XML parsers will either truncate the value or be unable to parse numbers that exceed the size of a double. |
bigInteger |
XML text node with a value of the number, using scientific notation if an exponent is needed. Unfortunately, many XML parsers will either truncate the value or be unable to parse numbers that exceed the size of a double. |
string |
XML text node with an XML-safe, UTF-8 value of the string. |
timestamp |
XML text node with a value of the timestamp. This protocol uses
date-time as the default serialization. However, the
timestampFormat MAY be used to
customize timestamp serialization. |
document |
Undefined. Document shapes are not supported in this protocol. |
list |
XML element. Each value provided in the list is serialized as a nested
XML element with the name member . The xmlName trait can be
used to serialize a property using a custom name. The
xmlFlattened trait can be used to unwrap the values into a
containing structure or union, with the value XML element using the
structure or union member name. See List serialization
for more. |
map |
XML element. Each key-value pair provided in the map is serialized in
a nested XML element with the name entry that contains nested
elements key and value for the pair. The xmlName trait
can be used to serialize key or value properties using a custom name,
it cannot be used to influence the entry name. The
xmlFlattened trait can be used to unwrap the entries into a
containing structure or union, with the entry XML element using the
structure or union member name. See Map serialization for
more. |
structure |
XML element. Each member value provided for the structure is serialized as a nested XML element where the element name is the same as the member name. The xmlName trait can be used to serialize a property using a custom name. The xmlAttribute trait can be used to serialize a property in an attribute of the containing element. See Structure and union serialization for more. |
union |
XML element. A union is serialized identically to a structure
shape, but only a single member can be set to a non-null value. |
Important
See XML bindings for comprehensive documentation, including examples and behaviors when using multiple XML traits.
Operation error serialization#
Error responses in the ec2Query
protocol are wrapped within an XML root
node named Response
. Inside this, there is an Errors
tag containing
the actual error, and a RequestID
tag holding the request ID. Nested inside
of the Errors
tag is an Error
tag which contains the serialized error
structure members.
Serialized error shapes MUST also contain an additional child element Code
that contains only the shape name
of the error's
Shape ID. This can be used to distinguish which specific error has been
serialized in the response.
<Response>
<Errors>
<Error>
<Code>InvalidGreeting</Code>
<Message>Hi</Message>
<AnotherSetting>setting</AnotherSetting>
</Error>
</Errors>
<RequestID>foo-id</RequestID>
</Response>
Code
: Theshape name
of the error's Shape ID.RequestID
: Contains a unique identifier for the associated request.
In the above example, Message
, and AnotherSetting
are additional,
hypothetical members of the serialized error structure.
Non-numeric float and double serialization#
Smithy floats and doubles are defined by IEEE-754, which includes special values
for "not a number" and both positive and negative infinity. Unless otherwise
specified, the ec2Query
protocol treats those special values as
strings with the following values:
Special Value | String Value |
---|---|
Not a number | NaN |
Positive infinity | Infinity |
Negative infinity | -Infinity |
Protocol compliance tests#
A full compliance test suite is provided and SHALL be considered a normative reference: https://github.com/smithy-lang/smithy/tree/main/smithy-aws-protocol-tests/model/ec2Query
These compliance tests define a model that is used to define test cases and the expected serialized HTTP requests and responses for each case.
TODO: Add specifications, protocol examples, etc.
Error shape renaming#
By default, Smithy permits renaming shapes to disambiguate shape ID conflicts in
the service closure via the rename
property. However, services using this protocol are
not allowed to rename error shapes (shapes with error trait applied).
Client-side implementations rely on the response body field code
or __type
to resolve the error type.
Server-side implementations of this protocol will only send the shape name
for the response body field.
When there are conflicting shape IDs smithy.service#ServiceError
and smithy.other#ServiceError
,
the server will only send the shape name ServiceError
. Clients will not be able to resolve
the correct error type without the namespace.
Server-side implementations of this protocol don't serialize renamed shape names. As a result, renaming will not resolve the conflicting shape IDs issue, and hence it is not permitted.