17. JSON AST

Smithy models written using the Smithy IDL have an isomorphic JSON abstract syntax tree (AST) representation that can be used to more easily integrate Smithy into languages and tools that do not have a Smithy IDL parser.

  • Smithy JSON models can be merged together with other JSON models or other Smithy IDL models using the rules defined in Merging model files.
  • All shape IDs in the JSON AST MUST be absolute shape IDs that contain a namespace. One of the main drivers of the simplicity of the the JSON AST over the Smithy IDL is that relative and forward references never need to be resolved.

17.1. Top level properties

Smithy JSON models are objects that can contain the following top-level properties:

Property Type Description
smithy string Required. Defines the version of the Smithy specification (e.g., "1.0").
metadata object Defines all of the metadata about the model using a JSON object. Each key is the metadata key to set, and each value is the metadata value to assign to the key.
shapes Map<shape ID, AST shape> A map of absolute shape IDs to shape definitions.

17.2. AST shapes

AST shapes are defined using objects that always contain a type property to define the shape type or apply.

{
    "smithy": "1.0",
    "shapes": {
        "smithy.example#MyString": {
            "type": "string"
        }
    }
}

All entries in the shapes map can contain a traits property that defines the traits attached to the shape. traits is a map of where each key is the absolute shape ID of a trait shape and each value is the value to assign to the trait.

{
    "traits": {
        "smithy.example#documentation": "Hi!",
        "smithy.example#tags": [
            "a",
            "b"
        ]
    }
}

The following example defines a string shape with a documentation trait.

{
    "smithy": "1.0",
    "shapes": {
        "smithy.example#MyString": {
            "type": "string",
            "traits": {
                "smithy.api#documentation": "My documentation string"
            }
        }
    }
}

17.3. Simple shapes

Simple shapes are defined as an object. The following example defines a shape for each simple type:

{
    "smithy": "1.0",
    "shapes": {
        "smithy.example#Blob": {
            "type": "blob"
        },
        "smithy.example#Boolean": {
            "type": "boolean"
        },
        "smithy.example#Document": {
            "type": "document"
        },
        "smithy.example#String": {
            "type": "string"
        },
        "smithy.example#Byte": {
            "type": "byte"
        },
        "smithy.example#Short": {
            "type": "short"
        },
        "smithy.example#Integer": {
            "type": "integer"
        },
        "smithy.example#Long": {
            "type": "long"
        },
        "smithy.example#Float": {
            "type": "float"
        },
        "smithy.example#Double": {
            "type": "double"
        },
        "smithy.example#BigInteger": {
            "type": "bigInteger"
        },
        "smithy.example#BigDecimal": {
            "type": "bigDecimal"
        },
        "smithy.example#Timestamp": {
            "type": "timestamp"
        }
    }
}

17.4. List and set shapes

List and set shapes have a required member property that is an AST member.

The following example defines a list with a string member:

{
    "smithy": "1.0",
    "shapes": {
        "smithy.example#MyList": {
            "type": "list",
            "member": {
                "target": "smithy.api#String"
            }
        }
    }
}

The following example defines a set with a string member:

{
    "smithy": "1.0",
    "shapes": {
        "smithy.example#MySet": {
            "type": "set",
            "member": {
                "target": "smithy.api#String"
            }
        }
    }
}

17.5. AST member

An AST member definition defines a member of a shape. It is a special kind of AST shape reference that also contains an optional traits property that defines traits attached to the member. Each key in the traits property is the absolute shape ID of the trait to apply, and each value is the value to assign to the trait.

{
    "target": "smithy.example#MyShape",
    "traits": {
        "smithy.example#documentation": "Hi!"
    }
}

The following example defines a list shape and its member.

{
    "smithy": "1.0",
    "shapes": {
        "smithy.example#MyList": {
            "type": "list",
            "member": {
                "target": "smithy.api#String",
                "traits": {
                    "smithy.api#documentation": "Member documentation"
                }
            }
        }
    }
}

17.6. AST shape reference

An AST shape reference is an object with a single property, target that maps to an absolute shape ID.

{
    "target": "smithy.example#MyShape"
}

The following example defines a shape reference inside of the operations list of a service shape.

{
    "smithy": "1.0",
    "shapes": {
        "smithy.example#Service": {
            "type": "service",
            "operations": [
                {
                    "target": "smithy.example#Operation"
                }
            ]
        },
        "smithy.example#Operation": {
            "type": "operation"
        }
    }
}

17.7. Map shape

A Map shape has a required key and value AST member. The shape referenced by the key member MUST target a string shape.

The following example defines a map of strings to numbers:

{
    "smithy": "1.0",
    "shapes": {
        "smithy.example#IntegerMap": {
            "type": "map",
            "key": {
                "target": "smithy.api#String"
            },
            "value": {
                "target": "smithy.api#Integer"
            }
        }
    }
}

17.8. Structure and union shapes

Structure and union shapes are defined with a members property that contains a map of member names to AST member definitions. A union shape requires at least one member, and a structure shape MAY omit the members property entirely if the structure contains no members.

Structure and union member names MUST be case-insensitively unique across the entire set of members. Each member name MUST adhere to the identifier ABNF grammar.

The following example defines a structure with one required and one optional member:

{
    "smithy": "1.0",
    "shapes": {
        "smithy.example#MyStructure": {
            "type": "structure",
            "members": {
                "stringMember": {
                    "target": "smithy.api#String",
                    "traits": {
                        "smithy.api#required": {}
                    }
                },
                "numberMember": {
                    "target": "smithy.api#Integer"
                }
            }
        }
    }
}

The following example defines a union:

{
    "smithy": "1.0",
    "shapes": {
        "smithy.example#MyUnion": {
            "type": "union",
            "members": {
                "a": {
                    "target": "smithy.api#String"
                },
                "b": {
                    "target": "smithy.api#Integer"
                }
            }
        }
    }
}

17.9. Service shape

Service shapes are defined using an object. Service shapes defined in JSON support the same properties as the Smithy IDL.

Property Type Description
type string service
version string Required. Defines the version of the service. The version can be provided in any format (e.g., 2017-02-11, 2.0, etc).
operations [AST shape reference] Binds a list of operations to the service. Each reference MUST target an operation.
resources [AST shape reference] Binds a list of resources to the service. Each reference MUST target a resource.
traits Map<shape ID, trait value> Traits to apply to the service
{
    "smithy": "1.0",
    "shapes": {
        "smithy.example#MyService": {
            "type": "service",
            "version": "2017-02-11",
            "operations": [
                {
                    "target": "smithy.example#GetServerTime"
                }
            ],
            "resources": [
                {
                    "target": "smithy.example#SomeResource"
                }
            ]
        }
    }
}

17.10. Resource shape

Resource shapes are defined using an object. Resource shapes defined in JSON support the same properties as the Smithy IDL.

Property Type Description
type string service
identifiers Map<String, AST shape reference> Defines identifier names and shape IDs used to identify the resource.
create AST shape reference Defines the lifecycle operation used to create a resource using one or more identifiers created by the service.
put AST shape reference Defines an idempotent lifecycle operation used to create a resource using identifiers provided by the client.
read AST shape reference Defines the lifecycle operation used to retrieve the resource.
update AST shape reference Defines the lifecycle operation used to update the resource.
delete AST shape reference Defines the lifecycle operation used to delete the resource.
list AST shape reference Defines the lifecycle operation used to list resources of this type.
operations [AST shape reference] Binds a list of non-lifecycle instance operations to the resource. Each reference MUST target an operation.
collectionOperations [AST shape reference] Binds a list of non-lifecycle collection operations to the resource. Each reference MUST target an operation.
resources [AST shape reference] Binds a list of resources to this resource as a child resource, forming a containment relationship. The resources MUST NOT have a cyclical containment hierarchy, and a resource can not be bound more than once in the entire closure of a resource or service. Each reference MUST target a resource.
traits Map<shape ID, trait value> Traits to apply to the resource.
{
    "smithy": "1.0",
    "shapes": {
        "smithy.example#Thing": {
            "type": "resource",
            "identifiers": {
                "forecastId": {
                    "target": "smithy.api#String"
                },
            },
            "create": {
                "target": "smithy.example#CreateThing"
            },
            "read": {
                "target": "smithy.example#GetThing"
            },
            "update": {
                "target": "smithy.example#Updatething"
            },
            "delete": {
                "target": "smithy.example#DeleteThing"
            },
            "list": {
                "target": "smithy.example#ListThings"
            },
            "operations": [
                {
                    "target": "smithy.example#SomeInstanceOperation"
                }
            ],
            "collectionOperations": [
                {
                    "target": "smithy.example#SomeCollectionOperation"
                }
            ],
            "resources": [
                {
                    "target": "smithy.example#SomeResource"
                }
            ]
        }
    }
}

17.11. Operation shape

Operation shapes are defined using an object with the following properties:

Property Type Description
type string operation
input AST shape reference Defines the optional input structure of the operation. The input of an operation MUST resolve to a Structure.
output AST shape reference Defines the optional output structure of the operation. The output of an operation MUST resolve to a Structure.
errors [AST shape reference] Defines the list of errors that MAY be encountered when invoking the operation. Each reference MUST resolve to a Structure shape that is marked with the error trait trait.
traits Map<shape ID, trait value> Traits to apply to the operation.

The following example defines an operation, its input, output, and errors:

{
    "smithy": "1.0",
    "shapes": {
        "smithy.example#MyOperation": {
            "type": "operation",
            "input": {
                "target": "smithy.example#MyOperationInput"
            },
            "output": {
                "target": "smithy.example#MyOperationOutput"
            },
            "errors": [
                {
                    "target": "smithy.example#BadRequestError"
                },
                {
                    "target": "smithy.example#NotFoundError"
                }
            ]
        },
        "smithy.example#MyOperationInput": {
            "type": "structure"
        },
        "smithy.example#MyOperationOutput": {
            "type": "structure"
        },
        "smithy.example#BadRequestError": {
            "type": "structure",
            "traits": {
                "smithy.api#error": "client"
            }
        },
        "smithy.example#NotFoundError": {
            "type": "structure",
            "traits": {
                "smithy.api#error": "client"
            }
        }
    }
}

17.12. AST apply type

Traits can be applied to shapes outside of their definition by setting type to apply. The apply type does not actually define a shape for the shape ID; the shape ID MUST reference a shape to which traits are applied. The apply type allows only the traits property.

{
    "smithy": "1.0",
    "shapes": {
        "smithy.example#Struct": {
            "type": "structure",
            "members": {
                "foo": {
                    "target": "smithy.api#String"
                }
            }
        },
        "smithy.example#Struct$foo": {
            "type": "apply",
            "traits": {
                "smithy.api#documentation": "My documentation string"
            }
        }
    }
}
HTTP Protocol Compliance Tests →