From 19a047bccb7cc0994db5151571a0efc934e98a61 Mon Sep 17 00:00:00 2001 From: Julian Sommer <115516918+juliansommer@users.noreply.github.com> Date: Mon, 14 Sep 2026 12:05:32 +1000 Subject: [PATCH] fix: footnotes instead of notes for compatibility --- docs/COMMANDS.md | 1012 +------------ docs/compatibility/acm-api-coverage/README.md | 2 +- docs/compatibility/aws-api-coverage/README.md | 22 +- docs/compatibility/ec2-api-coverage/README.md | 1260 +++++++++-------- docs/compatibility/ecr-api-coverage/README.md | 2 +- docs/compatibility/ecs-api-coverage/README.md | 2 +- docs/compatibility/eks-api-coverage/README.md | 2 +- .../elbv2-api-coverage/README.md | 2 +- docs/compatibility/iam-api-coverage/README.md | 331 ++--- docs/compatibility/pages.json | 49 +- docs/compatibility/rds-api-coverage/README.md | 31 +- docs/compatibility/rds-api-coverage/intro.md | 29 +- docs/compatibility/sts-api-coverage/README.md | 2 +- .../rds-quickstart/README.md | 6 +- internal/awsmodel/page.go | 102 +- internal/awsmodel/page_test.go | 73 +- 16 files changed, 1052 insertions(+), 1875 deletions(-) diff --git a/docs/COMMANDS.md b/docs/COMMANDS.md index 28297c7dd..6701667ea 100644 --- a/docs/COMMANDS.md +++ b/docs/COMMANDS.md @@ -1,4 +1,4 @@ -# Command Implementation Matrix +# Spinifex Admin Commands ## Spinifex Admin CLI @@ -208,1013 +208,3 @@ Each method is a separate grant, and `spx admin principal create` decides which The surface is unreachable until an operator runs `spx admin principal create`; there is no config toggle and no default credential for it. The super-admin account's own `admin` user does hold these grants already, through the `AdministratorAccess` policy every account's administrator carries (`Action: "*"`), so its bootstrap key can call the surface without any further setup — but it is unscoped and unrotatable without locking out the operator, which is why automation should use a named principal. Revocation is `spx admin principal revoke ` (or `aws iam delete-access-key`), which is immediate and cluster-wide. `[signup] max_accounts` in `awsgw.toml` caps how many accounts may exist; it defaults to 128 when the section is absent, and 0 means uncapped. -## AWS-Compatible API - -### EC2 — Instance Management - -| Command | Implemented Flags | Missing Flags | Status | -|---------|-------------------|---------------|--------| -| `run-instances` | `--image-id`, `--instance-type`, `--count`, `--key-name`, `--user-data`, `--subnet-id`, `--security-group-ids`, `--tag-specifications` (instance-scoped), `--block-device-mappings` (DeviceName, VolumeSize, VolumeType, Iops, DeleteOnTermination), `--placement` (GroupName), `--iam-instance-profile` (Name/Arn), `--capacity-reservation-specification` (CapacityReservationTarget.CapacityReservationId, targeted-by-id only), `--metadata-options` (HttpPutResponseHopLimit; `HttpTokens` `required`/`optional`, defaulting to `required` except on Windows images), `--launch-template` (LaunchTemplateId/LaunchTemplateName, Version — resolves `$Default`/`$Latest`; direct params override the template) | `--dry-run`, `--client-token`, `--disable-api-termination`, `--ebs-optimized`, `--network-interfaces`, `--private-ip-address`, `--monitoring`, `--credit-specification`, `--cpu-options`, `--hibernate-options` | **DONE** | -| `describe-instances` | `--instance-ids`, `--filters` (instance-state-name, instance-id, instance-type, vpc-id, subnet-id, tag:*, tag-key, tag-value) | `--max-results`, `--next-token`, `--dry-run` | **DONE** | -| `start-instances` | `--instance-ids` | `--dry-run`, `--force` | **DONE** | -| `stop-instances` | `--instance-ids` | `--force`, `--hibernate`, `--dry-run` | **DONE** | -| `terminate-instances` | `--instance-ids`, `DeleteOnTermination` (per-volume) | `--dry-run` | **DONE** | -| `reboot-instances` | `--instance-ids` | `--dry-run` | **DONE** | -| `describe-instance-types` | `--filters` (capacity only) | `--instance-types`, `--max-results`, `--next-token`, `--dry-run`, other filters | **DONE** | -| `modify-instance-attribute` | `--instance-id`, `--instance-type`, `--user-data`, `--disable-api-termination` | `--ebs-optimized`, `--source-dest-check`, `--instance-initiated-shutdown-behavior`, `--block-device-mappings`, `--groups`, `--ena-support`, `--sriov-net-support` | **DONE** | -| `get-console-output` | `--instance-id` | `--latest`, `--dry-run` | **DONE** | -| `get-password-data` | `--instance-id` | `--dry-run` | **DONE** | -| `describe-instance-attribute` | `--instance-id`, `--attribute` (instanceType, userData, disableApiTermination, instanceInitiatedShutdownBehavior, disableApiStop, ebsOptimized, enaSupport, sourceDestCheck, rootDeviceName, kernel, ramdisk) | `--dry-run` | **DONE** | -| `modify-instance-metadata-options` | `--instance-id`, `--http-put-response-hop-limit` (1–64), `--http-tokens` (`required`/`optional`), `--http-endpoint` (`enabled`), `--http-protocol-ipv6`/`--instance-metadata-tags` (`disabled`) — unmodelled values return `UnsupportedOperation` | `--dry-run` | **DONE** | -| `describe-instance-credit-specifications` | `--instance-ids` | `--filters`, `--max-results`, `--dry-run` | **DONE** (stub — always returns `standard`) | -| `describe-instance-status` | `--instance-ids`, `--include-all-instances`, `--filters` (availability-zone, instance-state-code, instance-state-name, tag:*) | `--max-results`, `--next-token`, `--dry-run`, event/instance-status/system-status filters | **DONE** (static health) | -| `monitor-instances` | `--instance-ids` | `--dry-run` | **DONE** (60s detailed telemetry; state is `enabled`/`disabled` only, never `pending`/`disabling`) | -| `unmonitor-instances` | `--instance-ids` | `--dry-run` | **DONE** (returns the instance to the 300s basic tier) | - -### EC2 — Spot Instances - -Spot Instance Requests (SIRs) are a **mock** over the on-demand `run-instances` path: a request synchronously launches real VMs on the operator's own compute and is then reported `active`/`fulfilled`. There is no spot market — no bidding, price rejection, interruption, or reclamation, and instances are never reclaimed. - -| Command | Implemented Flags | Missing Flags | Status | -|---------|-------------------|---------------|--------| -| `request-spot-instances` | `--instance-count` (default 1), `--type` (`one-time`/`persistent` — stored, behaviour identical), `--spot-price` (echoed only), `--client-token`, `--launch-specification` (ImageId, InstanceType, KeyName, SubnetId, SecurityGroupIds, UserData, BlockDeviceMappings, IamInstanceProfile, Placement.GroupName, NetworkInterfaces), `--tag-specifications` (spot-instances-request) | `--valid-from`, `--valid-until`, `--launch-group`, `--availability-zone-group`, `--block-duration-minutes`, `--instance-interruption-behavior`, `--dry-run` | **DONE** (mock) | -| `describe-spot-instance-requests` | `--spot-instance-request-ids`, `--filters` (spot-instance-request-id, state, instance-id, launch.image-id, launch.instance-type, launch.key-name, type, launched-availability-zone, tag-key, tag:*) | `--max-results`, `--next-token`, `--dry-run` | **DONE** | -| `cancel-spot-instance-requests` | `--spot-instance-request-ids` | `--dry-run` | **DONE** | -| `describe-spot-price-history` | — | all | **NOT STARTED** (`InvalidAction`) — on owned hardware there is no spot/on-demand price differential, so any synthetic price would be misleading rather than helpful | - -### EC2 — IAM Instance Profile Associations - -| Command | Implemented Flags | Missing Flags | Status | -|---------|-------------------|---------------|--------| -| `associate-iam-instance-profile` | `--instance-id`, `--iam-instance-profile` (Name/Arn) | `--dry-run` | **DONE** | -| `disassociate-iam-instance-profile` | `--association-id` | `--dry-run` | **DONE** | -| `replace-iam-instance-profile-association` | `--association-id`, `--iam-instance-profile` (Name/Arn) | `--dry-run` | **DONE** | -| `describe-iam-instance-profile-associations` | `--association-ids`, `--filters` (instance-id, state) | `--max-results`, `--next-token`, `--dry-run` | **DONE** | - -### EC2 — Key Pairs - -| Command | Implemented Flags | Missing Flags | Status | -|---------|-------------------|---------------|--------| -| `create-key-pair` | `--key-name`, `--key-type` (rsa/ed25519), `--tag-specifications` | `--key-format`, `--dry-run` | **DONE** | -| `describe-key-pairs` | `--key-names`, `--key-pair-ids`, `--filters` (key-pair-id, key-name, fingerprint, tag:*) | `--max-results`, `--dry-run` | **DONE** | -| `delete-key-pair` | `--key-name`, `--key-pair-id` | `--dry-run` | **DONE** | -| `import-key-pair` | `--key-name`, `--public-key-material`, `--tag-specifications` | `--dry-run` | **DONE** | - -### EC2 — AMI Images - -| Command | Implemented Flags | Missing Flags | Status | -|---------|-------------------|---------------|--------| -| `describe-images` | `--image-ids`, `--owners` (self/account-id/alias), `--filters` (name, state, architecture, image-id, is-public, owner-id, description, image-type, tag:*) | `--executable-users`, `--include-deprecated`, `--include-disabled`, `--max-results`, `--next-token`, `--dry-run` | **DONE** | -| `create-image` | `--instance-id`, `--name`, `--description`, `--tag-specifications` | `--no-reboot`, `--block-device-mappings`, `--dry-run` | **DONE** | -| `register-image` | `--name`, `--description`, `--architecture` (x86_64/arm64/i386), `--root-device-name`, `--virtualization-type` (hvm), `--boot-mode` (bios/uefi/uefi-preferred), `--block-device-mappings` (root w/ `Ebs.SnapshotId`+`VolumeSize`), `--tag-specifications` | `--billing-products`, `--uefi-data` | **DONE** | -| `deregister-image` | `--image-id` | `--dry-run` | **DONE** | -| `copy-image` | `--source-image-id`, `--source-region`, `--name`, `--description`, `--client-token`, `--copy-image-tags`, `--tag-specifications` (image only) | `--encrypted`, `--kms-key-id`, `--destination-outpost-arn`, `--dry-run` | **DONE** — metadata-only, no block copy; the new snapshot inherits the source `VolumeID` | -| `describe-image-attribute` | `--image-id`, `--attribute` (`description`, `blockDeviceMapping`) | `--dry-run`, other attributes (`launchPermission`, `bootMode`, `kernel`, `ramdisk`, `sriovNetSupport`, `productCodes`, `tpmSupport`, `uefiData`, `imdsSupport`, `lastLaunchedTime`, `deregistrationProtection`) | **DONE** | -| `modify-image-attribute` | `--image-id`, `--description` (top-level or structured) | `--launch-permission`, `--imds-support`, `--operation-type`, `--user-ids`, `--user-groups`, `--organization-arns`, `--product-codes`, `--dry-run`, other `--attribute` values | **DONE** | -| `reset-image-attribute` | `--image-id`, `--attribute description` | `--attribute launchPermission`, `--dry-run` | **DONE** | -| `import-image` | — | `--disk-containers`, `--description`, `--architecture`, `--platform` | **NOT STARTED** | - -### EC2 — Volumes (EBS) - -| Command | Implemented Flags | Missing Flags | Status | -|---------|-------------------|---------------|--------| -| `describe-volumes` | `--volume-ids`, `--filters` (volume-id, status, size, volume-type, attachment.instance-id, attachment.status, attachment.device, availability-zone, tag:*), persisted `DeleteOnTermination` | `--max-results`, `--next-token`, `--dry-run` | **DONE** | -| `create-volume` | `--size`, `--availability-zone`, `--volume-type` (gp3), `--snapshot-id`, `--tag-specifications`, `--iops`, `--throughput` | `--encrypted` (hardcoded false) | **DONE** | -| `delete-volume` | `--volume-id` | `--dry-run` | **DONE** | -| `modify-volume` | `--volume-id`, `--size`, `--volume-type`, `--iops` | `--throughput`, `--dry-run`, `--multi-attach-enabled` | **DONE** | -| `attach-volume` | `--volume-id`, `--instance-id`, `--device` (auto-assigns `/dev/sd[f-p]`) | `--dry-run` | **DONE** | -| `detach-volume` | `--volume-id`, `--instance-id` (optional), `--device`, `--force` | `--dry-run` | **DONE** | -| `describe-volume-status` | `--volume-ids`, `--filters` (volume-id, volume-status.status, availability-zone) | `--max-results`, `--next-token`, `--dry-run` | **DONE** | -| `describe-volumes-modifications` | `--volume-ids`, `--filters` (modification-state, original-iops, original-size, original-volume-type, start-time, target-iops, target-size, target-volume-type, volume-id) | `--max-results`, `--next-token`, `--dry-run` | **DONE** | - -### EC2 — Snapshots - -| Command | Implemented Flags | Missing Flags | Status | -|---------|-------------------|---------------|--------| -| `create-snapshot` | `--volume-id`, `--description`, `--tag-specifications` | `--dry-run` | **DONE** | -| `delete-snapshot` | `--snapshot-id` | `--dry-run` | **DONE** | -| `describe-snapshots` | `--snapshot-ids`, `--filters` (snapshot-id, status, volume-id, volume-size, owner-id, tag:*) | `--owner-ids`, `--max-results`, `--dry-run` | **DONE** | -| `copy-snapshot` | `--source-snapshot-id`, `--source-region`, `--description` | `--encrypted`, `--dry-run` | **DONE** | -| `create-snapshots` | — | `--instance-specification`, `--description`, `--tag-specifications` | **NOT STARTED** | - -### EC2 — Tags - -| Command | Implemented Flags | Missing Flags | Status | -|---------|-------------------|---------------|--------| -| `create-tags` | `--resources`, `--tags` | `--dry-run` | **DONE** | -| `delete-tags` | `--resources`, `--tags` | `--dry-run` | **DONE** | -| `describe-tags` | `--filters` (resource-id, resource-type, key, value) | `--max-results`, `--next-token`, `--dry-run` | **DONE** | - -### EC2 — Regions, AZs, Account Attributes - -| Command | Implemented Flags | Missing Flags | Status | -|---------|-------------------|---------------|--------| -| `describe-regions` | — (returns configured region) | `--region-names`, `--filters`, `--all-regions`, `--dry-run` | **DONE** | -| `describe-availability-zones` | — (returns configured AZ) | `--zone-names`, `--filters`, `--all-availability-zones` | **DONE** | -| `describe-account-attributes` | `--attribute-names` | `--dry-run` | **DONE** | - -### EC2 — Account Settings - -Persistence works but stored values are not yet enforced by downstream services. - -| Command | Implemented Flags | Missing Flags | Status | -|---------|-------------------|---------------|--------| -| `enable-ebs-encryption-by-default` | — | `--dry-run` | **STARTED** (enforcement pending) | -| `disable-ebs-encryption-by-default` | — | `--dry-run` | **STARTED** (enforcement pending) | -| `get-ebs-encryption-by-default` | — | `--dry-run` | **STARTED** (enforcement pending) | -| `enable-serial-console-access` | — | `--dry-run` | **STARTED** (enforcement pending) | -| `disable-serial-console-access` | — | `--dry-run` | **STARTED** (enforcement pending) | -| `get-serial-console-access-status` | — | `--dry-run` | **DONE** | -| `enable-snapshot-block-public-access` | — | `--state` | **NOT STARTED** | -| `disable-snapshot-block-public-access` | — | `--dry-run` | **NOT STARTED** | -| `get-snapshot-block-public-access-state` | — | `--dry-run` | **NOT STARTED** | -| `enable-image-block-public-access` | — | `--image-block-public-access-state` | **NOT STARTED** | -| `disable-image-block-public-access` | — | `--dry-run` | **NOT STARTED** | -| `get-image-block-public-access-state` | — | `--dry-run` | **NOT STARTED** | -| `modify-instance-metadata-defaults` | — | `--http-tokens`, `--http-put-response-hop-limit`, `--http-endpoint`, `--instance-metadata-tags` | **NOT STARTED** — account-level; blocked on an `aws-sdk-go` bump, since the gateway's generic handler needs the typed input struct to route it | -| `get-instance-metadata-defaults` | — | `--dry-run` | **NOT STARTED** — account-level; blocked on an `aws-sdk-go` bump, as `InstanceMetadataDefaultsResponse` is absent from our version | - -### EC2 — VPC Core - -| Command | Implemented Flags | Missing Flags | Status | -|---------|-------------------|---------------|--------| -| `create-vpc` | `--cidr-block`, `--tag-specifications` | `--instance-tenancy`, `--dry-run` | **DONE** | -| `delete-vpc` | `--vpc-id` | `--dry-run` | **DONE** | -| `describe-vpcs` | `--vpc-ids`, `--filters` (vpc-id, state, cidr-block, is-default, owner-id, tag:*) | `--max-results`, `--dry-run` | **DONE** | -| `modify-vpc-attribute` | `--vpc-id`, `--enable-dns-hostnames`, `--enable-dns-support`, `--enable-network-address-usage-metrics` | `--dry-run` | **DONE** | -| `describe-vpc-attribute` | `--vpc-id`, `--attribute` (enableDnsHostnames, enableDnsSupport, enableNetworkAddressUsageMetrics) | `--dry-run` | **DONE** | -| `associate-vpc-cidr-block` | — | `--vpc-id`, `--cidr-block` | **NOT STARTED** | -| `disassociate-vpc-cidr-block` | — | `--association-id` | **NOT STARTED** | -| `create-subnet` | `--vpc-id`, `--cidr-block`, `--availability-zone`, `--tag-specifications` | `--dry-run` | **DONE** | -| `delete-subnet` | `--subnet-id` | `--dry-run` | **DONE** | -| `describe-subnets` | `--subnet-ids`, `--filters` (vpc-id, subnet-id, availability-zone, cidr-block, state, default-for-az, tag:*) | `--max-results`, `--dry-run` | **DONE** | -| `modify-subnet-attribute` | `--subnet-id`, `--map-public-ip-on-launch` | `--assign-ipv6-address-on-creation`, `--dry-run` | **DONE** | -| `associate-subnet-cidr-block` | — | `--subnet-id`, `--ipv6-cidr-block` | **NOT STARTED** | -| `disassociate-subnet-cidr-block` | — | `--association-id` | **NOT STARTED** | - -### EC2 — Security Groups - -| Command | Implemented Flags | Missing Flags | Status | -|---------|-------------------|---------------|--------| -| `create-security-group` | `--group-name`, `--description`, `--vpc-id`, `--tag-specifications` | `--dry-run` | **DONE** | -| `delete-security-group` | `--group-id` | `--dry-run` | **DONE** | -| `describe-security-groups` | `--group-ids`, `--filters` (vpc-id, group-name, group-id, description, ip-permission.cidr, tag:*) | `--group-names`, `--max-results`, `--dry-run` | **DONE** | -| `authorize-security-group-ingress` | `--group-id`, `--ip-permissions` | `--dry-run` | **DONE** | -| `authorize-security-group-egress` | `--group-id`, `--ip-permissions` | `--dry-run` | **DONE** | -| `revoke-security-group-ingress` | `--group-id`, `--ip-permissions` | `--dry-run` | **DONE** | -| `revoke-security-group-egress` | `--group-id`, `--ip-permissions` | `--dry-run` | **DONE** | -| `describe-security-group-rules` | `--filters` (group-id, security-group-rule-id, tag:*, tag-key), `--security-group-rule-ids` | `--max-results`, `--next-token`, `--dry-run` | **DONE** | - -### EC2 — Internet Gateway - -| Command | Implemented Flags | Missing Flags | Status | -|---------|-------------------|---------------|--------| -| `create-internet-gateway` | `--tag-specifications` | `--dry-run` | **DONE** | -| `attach-internet-gateway` | `--internet-gateway-id`, `--vpc-id` | `--dry-run` | **DONE** | -| `detach-internet-gateway` | `--internet-gateway-id`, `--vpc-id` | `--dry-run` | **DONE** | -| `delete-internet-gateway` | `--internet-gateway-id` | `--dry-run` | **DONE** | -| `describe-internet-gateways` | `--internet-gateway-ids`, `--filters` (internet-gateway-id, attachment.vpc-id, attachment.state, tag:*) | `--max-results`, `--dry-run` | **DONE** | - -### EC2 — Egress-Only Internet Gateway - -KV CRUD only — no OVN/OVS integration. EIGWs are stored but have no effect on network topology. Implementation is blocked on platform-wide IPv6 support. - -| Command | Implemented Flags | Missing Flags | Status | -|---------|-------------------|---------------|--------| -| `create-egress-only-internet-gateway` | `--vpc-id`, `--tag-specifications` | `--client-token`, `--dry-run` | **STARTED** (KV only, no OVN) | -| `delete-egress-only-internet-gateway` | `--egress-only-internet-gateway-id` | `--dry-run` | **STARTED** (KV only, no OVN) | -| `describe-egress-only-internet-gateways` | `--egress-only-internet-gateway-ids`, `--filters` (egress-only-internet-gateway-id, tag:*) | `--max-results`, `--next-token`, `--dry-run` | **STARTED** (KV only, no OVN) | - -### EC2 — Route Tables - -| Command | Implemented Flags | Missing Flags | Status | -|---------|-------------------|---------------|--------| -| `create-route-table` | `--vpc-id`, `--tag-specifications` | `--dry-run` | **DONE** | -| `delete-route-table` | `--route-table-id` | `--dry-run` | **DONE** | -| `describe-route-tables` | `--route-table-ids`, `--filters` (vpc-id, route-table-id, association.main, association.route-table-association-id, association.subnet-id, route.destination-cidr-block, route.gateway-id) | `--max-results`, `--next-token`, `--dry-run` | **DONE** | -| `create-route` | `--route-table-id`, `--destination-cidr-block`, `--gateway-id`, `--nat-gateway-id` | `--egress-only-internet-gateway-id`, `--vpc-peering-connection-id`, `--dry-run` | **DONE** | -| `delete-route` | `--route-table-id`, `--destination-cidr-block` | `--dry-run` | **DONE** | -| `replace-route` | `--route-table-id`, `--destination-cidr-block`, `--gateway-id` | `--nat-gateway-id`, `--dry-run` | **DONE** | -| `associate-route-table` | `--route-table-id`, `--subnet-id` | `--gateway-id`, `--dry-run` | **DONE** | -| `disassociate-route-table` | `--association-id` | `--dry-run` | **DONE** | -| `replace-route-table-association` | `--association-id`, `--route-table-id` | `--dry-run` | **DONE** | - -### EC2 — Network Interfaces (ENIs) - -| Command | Implemented Flags | Missing Flags | Status | -|---------|-------------------|---------------|--------| -| `create-network-interface` | `--subnet-id`, `--private-ip-address`, `--description`, `--tag-specifications` | `--groups`, `--dry-run` | **DONE** | -| `delete-network-interface` | `--network-interface-id` | `--dry-run` | **DONE** | -| `describe-network-interfaces` | `--network-interface-ids`, `--filters` (subnet-id, vpc-id, attachment.instance-id) | `--max-results`, `--dry-run` | **DONE** | -| `modify-network-interface-attribute` | — | `--network-interface-id`, `--description`, `--groups` | **DONE** | -| `attach-network-interface` | `--network-interface-id`, `--instance-id`, `--device-index` (all required) | `--dry-run`, `--network-card-index`, `--ena-srd-specification` | **DONE** — hot-plugged into a running instance | -| `detach-network-interface` | `--attachment-id` (required), `--force` | `--dry-run` | **DONE** | -| `assign-private-ip-addresses` | — | `--network-interface-id`, `--private-ip-addresses`, `--secondary-private-ip-address-count` | **NOT STARTED** | -| `unassign-private-ip-addresses` | — | `--network-interface-id`, `--private-ip-addresses` | **NOT STARTED** | - -### EC2 — Elastic IP - -EIP handlers are always registered. Without a public IPAM pool (external mode disabled, or `nat` without a public pool), `describe-addresses` returns an empty list and mutating commands return `UnsupportedOperation`. In `nat` mode a public pool (`--external-pool` or `--external-source=dhcp` at init) enables the full EIP surface with host-delivered ingress. - -| Command | Implemented Flags | Missing Flags | Status | -|---------|-------------------|---------------|--------| -| `allocate-address` | `--public-ipv4-pool`, `--tag-specifications` | `--domain`, `--dry-run` | **DONE** | -| `release-address` | `--allocation-id` | `--dry-run` | **DONE** | -| `associate-address` | `--allocation-id`, `--network-interface-id`, `--instance-id`, `--private-ip-address` | `--dry-run`, `--allow-reassociation` | **DONE** | -| `disassociate-address` | `--association-id` | `--dry-run` | **DONE** | -| `describe-addresses` | `--allocation-ids`, `--public-ips`, `--filters` (allocation-id, public-ip, instance-id, association-id, domain, tag:*) | `--dry-run` | **DONE** | -| `describe-addresses-attribute` | `--allocation-ids` | `--attribute`, `--dry-run`, `--max-results`, `--next-token` | **DONE** | - -### EC2 — NAT Gateway - -| Command | Implemented Flags | Missing Flags | Status | -|---------|-------------------|---------------|--------| -| `create-nat-gateway` | `--subnet-id`, `--allocation-id`, `--tag-specifications` | `--connectivity-type`, `--dry-run` | **DONE** | -| `delete-nat-gateway` | `--nat-gateway-id` | `--dry-run` | **DONE** | -| `describe-nat-gateways` | `--nat-gateway-ids`, `--filters` (vpc-id, state) | `--max-results`, `--next-token`, `--dry-run` | **DONE** | -| `assign-private-nat-gateway-address` | — | `--nat-gateway-id`, `--private-ip-addresses` | **NOT STARTED** | -| `associate-nat-gateway-address` | — | `--nat-gateway-id`, `--allocation-ids` | **NOT STARTED** | - -### EC2 — Placement Groups - -| Command | Implemented Flags | Missing Flags | Status | -|---------|-------------------|---------------|--------| -| `create-placement-group` | `--group-name`, `--strategy` (spread/cluster), `--tag-specifications` | `--partition-count`, `--spread-level`, `--dry-run` | **DONE** | -| `delete-placement-group` | `--group-name` | `--dry-run` | **DONE** | -| `describe-placement-groups` | `--group-names`, `--group-ids`, `--filters` (strategy, state, spread-level, group-name, tag:*, tag-key, tag-value) | `--dry-run` | **DONE** | - -### EC2 — VPC Peering - -| Command | Implemented Flags | Missing Flags | Status | -|---------|-------------------|---------------|--------| -| `create-vpc-peering-connection` | — | `--vpc-id`, `--peer-vpc-id`, `--peer-owner-id`, `--peer-region`, `--tag-specifications` | **NOT STARTED** | -| `accept-vpc-peering-connection` | — | `--vpc-peering-connection-id`, `--dry-run` | **NOT STARTED** | -| `reject-vpc-peering-connection` | — | `--vpc-peering-connection-id`, `--dry-run` | **NOT STARTED** | -| `delete-vpc-peering-connection` | — | `--vpc-peering-connection-id`, `--dry-run` | **NOT STARTED** | -| `describe-vpc-peering-connections` | — | `--vpc-peering-connection-ids`, `--filters`, `--max-results` | **NOT STARTED** | -| `modify-vpc-peering-connection-options` | — | `--vpc-peering-connection-id`, `--requester-peering-connection-options`, `--accepter-peering-connection-options` | **NOT STARTED** | - -### EC2 — VPC Endpoints - -| Command | Implemented Flags | Missing Flags | Status | -|---------|-------------------|---------------|--------| -| `create-vpc-endpoint` | — | `--vpc-id`, `--service-name`, `--vpc-endpoint-type`, `--route-table-ids`, `--subnet-ids`, `--tag-specifications` | **NOT STARTED** | -| `delete-vpc-endpoints` | — | `--vpc-endpoint-ids`, `--dry-run` | **NOT STARTED** | -| `describe-vpc-endpoints` | — | `--vpc-endpoint-ids`, `--filters`, `--max-results` | **NOT STARTED** | -| `describe-vpc-endpoint-services` | — | `--service-names`, `--filters`, `--max-results` | **NOT STARTED** | -| `modify-vpc-endpoint` | — | `--vpc-endpoint-id`, `--add-route-table-ids`, `--remove-route-table-ids`, `--add-subnet-ids`, `--remove-subnet-ids` | **NOT STARTED** | - -### EC2 — VPN & Customer Gateway - -| Command | Implemented Flags | Missing Flags | Status | -|---------|-------------------|---------------|--------| -| `create-customer-gateway` | — | `--type`, `--bgp-asn`, `--ip-address`, `--tag-specifications` | **NOT STARTED** | -| `delete-customer-gateway` | — | `--customer-gateway-id`, `--dry-run` | **NOT STARTED** | -| `describe-customer-gateways` | — | `--customer-gateway-ids`, `--filters` | **NOT STARTED** | -| `create-vpn-gateway` | — | `--type`, `--amazon-side-asn`, `--tag-specifications` | **NOT STARTED** | -| `delete-vpn-gateway` | — | `--vpn-gateway-id`, `--dry-run` | **NOT STARTED** | -| `attach-vpn-gateway` | — | `--vpn-gateway-id`, `--vpc-id` | **NOT STARTED** | -| `detach-vpn-gateway` | — | `--vpn-gateway-id`, `--vpc-id` | **NOT STARTED** | -| `describe-vpn-gateways` | — | `--vpn-gateway-ids`, `--filters` | **NOT STARTED** | -| `create-vpn-connection` | — | `--type`, `--customer-gateway-id`, `--vpn-gateway-id`, `--options`, `--tag-specifications` | **NOT STARTED** | -| `delete-vpn-connection` | — | `--vpn-connection-id`, `--dry-run` | **NOT STARTED** | -| `describe-vpn-connections` | — | `--vpn-connection-ids`, `--filters` | **NOT STARTED** | -| `modify-vpn-connection` | — | `--vpn-connection-id`, `--vpn-gateway-id`, `--customer-gateway-id` | **NOT STARTED** | -| `modify-vpn-connection-options` | — | `--vpn-connection-id`, `--local-ipv4-network-cidr`, `--remote-ipv4-network-cidr` | **NOT STARTED** | - -### EC2 — Network ACLs - -| Command | Implemented Flags | Missing Flags | Status | -|---------|-------------------|---------------|--------| -| `create-network-acl` | — | `--vpc-id`, `--tag-specifications` | **NOT STARTED** | -| `delete-network-acl` | — | `--network-acl-id`, `--dry-run` | **NOT STARTED** | -| `describe-network-acls` | — | `--network-acl-ids`, `--filters`, `--max-results` | **NOT STARTED** | -| `create-network-acl-entry` | — | `--network-acl-id`, `--rule-number`, `--protocol`, `--rule-action`, `--cidr-block`, `--ingress`/`--egress`, `--port-range` | **NOT STARTED** | -| `delete-network-acl-entry` | — | `--network-acl-id`, `--rule-number`, `--ingress`/`--egress` | **NOT STARTED** | -| `replace-network-acl-association` | — | `--association-id`, `--network-acl-id` | **NOT STARTED** | -| `replace-network-acl-entry` | — | `--network-acl-id`, `--rule-number`, `--protocol`, `--rule-action`, `--cidr-block`, `--ingress`/`--egress`, `--port-range` | **NOT STARTED** | - -### EC2 — Prefix Lists - -| Command | Implemented Flags | Missing Flags | Status | -|---------|-------------------|---------------|--------| -| `create-managed-prefix-list` | — | `--prefix-list-name`, `--address-family`, `--max-entries`, `--entries`, `--tag-specifications` | **NOT STARTED** | -| `delete-managed-prefix-list` | — | `--prefix-list-id`, `--dry-run` | **NOT STARTED** | -| `describe-managed-prefix-lists` | — | `--prefix-list-ids`, `--filters`, `--max-results` | **NOT STARTED** | -| `modify-managed-prefix-list` | — | `--prefix-list-id`, `--current-version`, `--add-entries`, `--remove-entries`, `--prefix-list-name` | **NOT STARTED** | -| `get-managed-prefix-list-entries` | — | `--prefix-list-id`, `--target-version`, `--max-results` | **NOT STARTED** | -| `get-managed-prefix-list-associations` | — | `--prefix-list-id`, `--max-results` | **NOT STARTED** | - -### EC2 — Launch Templates - -| Command | Implemented Flags | Missing Flags | Status | -|---------|-------------------|---------------|--------| -| `create-launch-template` | `--launch-template-name`, `--launch-template-data` (full nested RequestLaunchTemplateData), `--version-description`, `--tag-specifications` (launch-template-scoped), `--dry-run` (no-op) | `--client-token` (idempotency) | **DONE** | -| `create-launch-template-version` | `--launch-template-id`/`--launch-template-name`, `--launch-template-data`, `--source-version` (clone-and-override), `--version-description`, `--dry-run` (no-op) | `--client-token`, `--resolve-alias` | **DONE** | -| `delete-launch-template` | `--launch-template-id`/`--launch-template-name`, `--dry-run` (no-op) | — | **DONE** | -| `delete-launch-template-versions` | `--launch-template-id`/`--launch-template-name`, `--versions` (rejects the current default version), `--dry-run` (no-op) | — | **DONE** | -| `modify-launch-template` | `--launch-template-id`/`--launch-template-name`, `--default-version`, `--dry-run` (no-op) | — | **DONE** | -| `describe-launch-templates` | `--launch-template-ids`, `--launch-template-names`, `--filters` (launch-template-id, launch-template-name, create-time, tag:*, tag-key) | `--max-results`, `--next-token`, `--dry-run` | **DONE** | -| `describe-launch-template-versions` | `--launch-template-id`/`--launch-template-name`, `--versions` (`$Default`/`$Latest`/numeric), `--min-version`, `--max-version`, `--filters` (is-default-version, image-id, instance-type, kernel-id, ram-disk-id, ebs-optimized) | `--max-results`, `--next-token`, `--dry-run`, `--resolve-alias` | **DONE** | - -### EC2 — Dedicated Hosts, IPv4 Pools, DHCP, Capacity Reservations - -| Command | Implemented Flags | Missing Flags | Status | -|---------|-------------------|---------------|--------| -| `allocate-hosts` | — | `--availability-zone`, `--instance-type`, `--quantity`, `--auto-placement`, `--tag-specifications` | **NOT STARTED** | -| `describe-hosts` | — | `--host-ids`, `--filters`, `--max-results` | **NOT STARTED** | -| `release-hosts` | — | `--host-ids` | **NOT STARTED** | -| `create-public-ipv4-pool` | — | `--tag-specifications`, `--dry-run` | **NOT STARTED** | -| `delete-public-ipv4-pool` | — | `--pool-id`, `--dry-run` | **NOT STARTED** | -| `describe-public-ipv4-pools` | — | `--pool-ids`, `--filters`, `--max-results` | **NOT STARTED** | -| `create-dhcp-options` | — | `--dhcp-configurations`, `--tag-specifications` | **NOT STARTED** | -| `delete-dhcp-options` | — | `--dhcp-options-id`, `--dry-run` | **NOT STARTED** | -| `describe-dhcp-options` | — | `--dhcp-options-ids`, `--filters`, `--max-results` | **NOT STARTED** | -| `associate-dhcp-options` | — | `--dhcp-options-id`, `--vpc-id`, `--dry-run` | **NOT STARTED** | -| `create-capacity-reservation` | `--instance-type`, `--instance-count`, `--availability-zone`, `--instance-platform`, `--instance-match-criteria`, `--tenancy` (default only), `--dry-run` | `--end-date`, `--end-date-type` (unlimited only), `--availability-zone-id`, `--tag-specifications` | **DONE** | -| `cancel-capacity-reservation` | `--capacity-reservation-id`, `--dry-run` | — | **DONE** | -| `describe-capacity-reservations` | `--capacity-reservation-ids`, `--filters` | `--max-results`, `--next-token` | **DONE** | -| `modify-capacity-reservation` | — | `--capacity-reservation-id`, `--instance-count`, `--end-date`, `--end-date-type` | **NOT STARTED** | - -### EC2 — Misc - -| Command | Implemented Flags | Missing Flags | Status | -|---------|-------------------|---------------|--------| -| `delete-network-interface-permission` | — | `--network-interface-permission-id`, `--force` | **NOT STARTED** | -| `enable-address-transfer` | — | `--allocation-id`, `--transfer-account-id` | **NOT STARTED** | -| `disable-address-transfer` | — | `--allocation-id` | **NOT STARTED** | - -### EBS Direct API - -| Command | Implemented Flags | Missing Flags | Status | -|---------|-------------------|---------------|--------| -| `start-snapshot` | — | `--volume-size`, `--parent-snapshot-id`, `--description`, `--encrypted` | **NOT STARTED** | -| `put-snapshot-block` | — | `--snapshot-id`, `--block-index`, `--block-data`, `--checksum` | **NOT STARTED** | -| `get-snapshot-block` | — | `--snapshot-id`, `--block-index` | **NOT STARTED** | -| `complete-snapshot` | — | `--snapshot-id`, `--changed-blocks-count` | **NOT STARTED** | -| `list-snapshot-blocks` | — | `--snapshot-id`, `--max-results`, `--next-token` | **NOT STARTED** | -| `list-changed-blocks` | — | `--second-snapshot-id`, `--first-snapshot-id`, `--max-results` | **NOT STARTED** | - ---- - -## IAM - -All IAM operations are account-scoped. Root user (account `000000000000`) bypasses policy evaluation entirely. - -### IAM — Users - -| Command | Implemented Flags | Missing Flags | Status | -|---------|-------------------|---------------|--------| -| `create-user` | `--user-name`, `--path` | `--tags`, `--permissions-boundary` | **DONE** | -| `get-user` | `--user-name` | — | **DONE** | -| `list-users` | `--path-prefix` | `--max-items`, `--marker` | **DONE** | -| `delete-user` | `--user-name` | — | **DONE** | -| `update-user` | — | `--user-name`, `--new-path`, `--new-user-name` | **NOT STARTED** | -| `put-user-policy` | `--user-name`, `--policy-name`, `--policy-document` | — | **DONE** | -| `get-user-policy` | `--user-name`, `--policy-name` | — | **DONE** | -| `delete-user-policy` | `--user-name`, `--policy-name` | — | **DONE** | -| `list-user-policies` | `--user-name` | `--max-items`, `--marker` | **DONE** | -| `tag-user` | `--user-name`, `--tags` | — | **DONE** | -| `untag-user` | `--user-name`, `--tag-keys` | — | **DONE** | -| `list-user-tags` | `--user-name` | `--max-items`, `--marker` | **DONE** | -| `put-user-permissions-boundary` | — | `--user-name`, `--permissions-boundary` | **NOT STARTED** | -| `delete-user-permissions-boundary` | — | `--user-name` | **NOT STARTED** | -| `create-login-profile` | — | `--user-name`, `--password` | **NOT STARTED** | -| `get-login-profile` | — | `--user-name` | **NOT STARTED** | -| `update-login-profile` | — | `--user-name`, `--password` | **NOT STARTED** | -| `delete-login-profile` | — | `--user-name` | **NOT STARTED** | -| `change-password` | — | `--old-password`, `--new-password` | **NOT STARTED** | - -### IAM — Access Keys - -| Command | Implemented Flags | Missing Flags | Status | -|---------|-------------------|---------------|--------| -| `create-access-key` | `--user-name` | — | **DONE** | -| `list-access-keys` | `--user-name` | `--max-items`, `--marker` | **DONE** | -| `delete-access-key` | `--access-key-id`, `--user-name` | — | **DONE** | -| `update-access-key` | `--access-key-id`, `--user-name`, `--status` (Active/Inactive) | — | **DONE** | -| `get-access-key-last-used` | — | `--access-key-id` | **NOT STARTED** | - -### IAM — Policies - -| Command | Implemented Flags | Missing Flags | Status | -|---------|-------------------|---------------|--------| -| `create-policy` | `--policy-name`, `--policy-document`, `--path`, `--description` | `--tags` | **DONE** | -| `get-policy` | `--policy-arn` | — | **DONE** | -| `get-policy-version` | `--policy-arn`, `--version-id` | — | **DONE** | -| `list-policy-versions` | `--policy-arn` | `--max-items`, `--marker` | **DONE** | -| `list-policies` | — | `--scope`, `--only-attached`, `--path-prefix`, `--max-items`, `--marker` | **DONE** | -| `delete-policy` | `--policy-arn` | — | **DONE** | -| `attach-user-policy` | `--user-name`, `--policy-arn` | — | **DONE** | -| `detach-user-policy` | `--user-name`, `--policy-arn` | — | **DONE** | -| `list-attached-user-policies` | `--user-name` | `--path-prefix`, `--max-items`, `--marker` | **DONE** | -| `create-policy-version` | — | `--policy-arn`, `--policy-document`, `--set-as-default` | **NOT STARTED** | -| `delete-policy-version` | — | `--policy-arn`, `--version-id` | **NOT STARTED** | -| `set-default-policy-version` | — | `--policy-arn`, `--version-id` | **NOT STARTED** | -| `list-entities-for-policy` | — | `--policy-arn`, `--entity-filter`, `--path-prefix`, `--policy-usage-filter` | **NOT STARTED** | -| `tag-policy` | `--policy-arn`, `--tags` | — | **DONE** | -| `untag-policy` | `--policy-arn`, `--tag-keys` | — | **DONE** | -| `list-policy-tags` | `--policy-arn` | `--max-items`, `--marker` | **DONE** | -| `generate-service-last-accessed-details` | — | `--arn`, `--granularity` | **NOT STARTED** | -| `get-service-last-accessed-details` | — | `--job-id` | **NOT STARTED** | -| `get-service-last-accessed-details-with-entities` | — | `--job-id`, `--service-namespace` | **NOT STARTED** | -| `list-policies-granting-service-access` | — | `--arn`, `--service-namespaces` | **NOT STARTED** | - -### IAM — Roles - -| Command | Implemented Flags | Missing Flags | Status | -|---------|-------------------|---------------|--------| -| `create-role` | `--role-name`, `--assume-role-policy-document`, `--path`, `--description`, `--max-session-duration`, `--tags` | `--permissions-boundary` | **DONE** | -| `get-role` | `--role-name` | — | **DONE** | -| `list-roles` | `--path-prefix` | `--max-items`, `--marker` | **DONE** | -| `delete-role` | `--role-name` | — | **DONE** | -| `update-role` | `--role-name`, `--description`, `--max-session-duration` | — | **DONE** | -| `update-assume-role-policy` | `--role-name`, `--policy-document` | — | **DONE** | -| `attach-role-policy` | `--role-name`, `--policy-arn` | — | **DONE** | -| `detach-role-policy` | `--role-name`, `--policy-arn` | — | **DONE** | -| `list-attached-role-policies` | `--role-name`, `--path-prefix` | `--max-items`, `--marker` | **DONE** | -| `list-role-policies` | `--role-name` | `--max-items`, `--marker` | **DONE** | -| `put-role-policy` | `--role-name`, `--policy-name`, `--policy-document` | — | **DONE** | -| `get-role-policy` | `--role-name`, `--policy-name` | — | **DONE** (document returned as raw JSON, not URL-encoded) | -| `delete-role-policy` | `--role-name`, `--policy-name` | — | **DONE** | -| `put-role-permissions-boundary` | — | `--role-name`, `--permissions-boundary` | **NOT STARTED** | -| `delete-role-permissions-boundary` | — | `--role-name` | **NOT STARTED** | -| `tag-role` | `--role-name`, `--tags` | — | **DONE** | -| `untag-role` | `--role-name`, `--tag-keys` | — | **DONE** | -| `list-role-tags` | `--role-name` | `--max-items`, `--marker` | **DONE** | -| `update-role-description` | — | `--role-name`, `--description` | **NOT STARTED** | - -### IAM — Instance Profiles - -| Command | Implemented Flags | Missing Flags | Status | -|---------|-------------------|---------------|--------| -| `create-instance-profile` | `--instance-profile-name`, `--path`, `--tags` | — | **DONE** | -| `get-instance-profile` | `--instance-profile-name` | — | **DONE** | -| `list-instance-profiles` | `--path-prefix` | `--max-items`, `--marker` | **DONE** | -| `list-instance-profiles-for-role` | `--role-name` | `--max-items`, `--marker` | **DONE** | -| `delete-instance-profile` | `--instance-profile-name` | — | **DONE** | -| `add-role-to-instance-profile` | `--instance-profile-name`, `--role-name` | — | **DONE** | -| `remove-role-from-instance-profile` | `--instance-profile-name`, `--role-name` | — | **DONE** | -| `tag-instance-profile` | `--instance-profile-name`, `--tags` | — | **DONE** | -| `untag-instance-profile` | `--instance-profile-name`, `--tag-keys` | — | **DONE** | -| `list-instance-profile-tags` | `--instance-profile-name` | `--max-items`, `--marker` | **DONE** | - -### IAM — OIDC Providers - -| Command | Implemented Flags | Missing Flags | Status | -|---------|-------------------|---------------|--------| -| `create-open-id-connect-provider` | `--url`, `--client-id-list`, `--thumbprint-list`, `--tags` | — | **DONE** | -| `get-open-id-connect-provider` | `--open-id-connect-provider-arn` | — | **DONE** | -| `list-open-id-connect-providers` | — | — | **DONE** | -| `delete-open-id-connect-provider` | `--open-id-connect-provider-arn` | — | **DONE** | -| `add-client-id-to-open-id-connect-provider` | — | `--open-id-connect-provider-arn`, `--client-id` | **NOT STARTED** | -| `remove-client-id-from-open-id-connect-provider` | — | `--open-id-connect-provider-arn`, `--client-id` | **NOT STARTED** | -| `update-open-id-connect-provider-thumbprint` | — | `--open-id-connect-provider-arn`, `--thumbprint-list` | **NOT STARTED** | -| `tag-open-id-connect-provider` / `untag-open-id-connect-provider` | `--open-id-connect-provider-arn`, `--tags`/`--tag-keys` | — | **DONE** | -| `list-open-id-connect-provider-tags` | `--open-id-connect-provider-arn` | `--max-items`, `--marker` | **DONE** | - -### IAM — Groups - -| Command | Implemented Flags | Missing Flags | Status | -|---------|-------------------|---------------|--------| -| `create-group` | `--group-name`, `--path` | — | **DONE** | -| `get-group` | `--group-name` | — | **DONE** | -| `list-groups` | `--path-prefix` | `--max-items`, `--marker` | **DONE** | -| `delete-group` | `--group-name` | — | **DONE** | -| `update-group` | — | `--group-name`, `--new-path`, `--new-group-name` | **NOT STARTED** | -| `add-user-to-group` | `--group-name`, `--user-name` | — | **DONE** | -| `remove-user-from-group` | `--group-name`, `--user-name` | — | **DONE** | -| `list-groups-for-user` | `--user-name` | `--max-items`, `--marker` | **DONE** | -| `attach-group-policy` | `--group-name`, `--policy-arn` | — | **DONE** | -| `detach-group-policy` | `--group-name`, `--policy-arn` | — | **DONE** | -| `list-attached-group-policies` | `--group-name`, `--path-prefix` | `--max-items`, `--marker` | **DONE** | -| `put-group-policy` | `--group-name`, `--policy-name`, `--policy-document` | — | **DONE** | -| `get-group-policy` | `--group-name`, `--policy-name` | — | **DONE** | -| `delete-group-policy` | `--group-name`, `--policy-name` | — | **DONE** | -| `list-group-policies` | `--group-name` | `--max-items`, `--marker` | **DONE** | - -### IAM — Account - -| Command | Implemented Flags | Missing Flags | Status | -|---------|-------------------|---------------|--------| -| `get-account-summary` | — | — | **DONE** | - ---- - -## STS - -| Command | Implemented Flags | Missing Flags | Status | -|---------|-------------------|--------------------------------------|--------| -| `get-caller-identity` | — | — | **DONE** | -| `assume-role` | `--role-arn`, `--role-session-name`, `--duration-seconds` (900–min(role MaxSessionDuration, 43200)) | `--policy`, `--policy-arns` (→ `PackedPolicyTooLarge`); `--tags`, `--transitive-tag-keys` (→ `InvalidParameterValue`); `--serial-number`, `--token-code` (→ `InvalidParameterValue`); `--external-id`, `--source-identity` (accepted and logged, **not enforced** — no Condition evaluator in v1) | **DONE** | -| `get-session-token` | `--duration-seconds` (900–129600, default 43200 = 12h; clamped, not rejected) | `--serial-number`, `--token-code` (MFA → `InvalidParameterValue`) | **DONE** | -| `assume-role-with-web-identity` | `--role-arn`, `--role-session-name`, `--web-identity-token`, `--duration-seconds` (900–43200, default 3600) | `--provider-id`; `--policy`, `--policy-arns` (→ `PackedPolicyTooLarge`) | **DONE** | -| `assume-role-with-saml` | — | `--role-arn`, `--principal-arn`, `--saml-assertion`, `--policy`, `--policy-arns`, `--duration-seconds` | **NOT STARTED** | -| `get-access-key-info` | — | `--access-key-id` | **NOT STARTED** | -| `get-federation-token` | — | `--name`, `--policy`, `--policy-arns`, `--duration-seconds`, `--tags` | **NOT STARTED** | -| `decode-authorization-message` | — | `--encoded-message` | **NOT STARTED** | - -Trust policies (`AssumeRolePolicyDocument`) reject `NotPrincipal`, `NotAction`, empty-string `Action` elements, and empty `Principal` blocks at write time (`MalformedPolicyDocument`). `Condition` blocks are rejected except on `sts:AssumeRoleWithWebIdentity` with `StringEquals` (IRSA), which v1 evaluates at assume time (`{iss}:sub`, `{iss}:aud`); anything wider is rejected to avoid silent over-grant. - ---- - -## IMDS (Instance Metadata Service) - -Available at `169.254.169.254` from inside every running guest VM, matching AWS. The endpoint is reached from within a guest over plain HTTP, with no in-VM agent to install. - -**IMDSv2 by default.** Every read requires a session token unless the instance opted into IMDSv1. Obtain a token with a `PUT /latest/api/token` carrying `X-aws-ec2-metadata-token-ttl-seconds` (1–21600), then send it back in `X-aws-ec2-metadata-token` on every read. A tokenless (v1-style) `GET` returns `401 Unauthorized` with an empty body unless the requesting ENI's instance carries `MetadataOptions.HttpTokens=optional`. - -IMDSv1 is opt-in per instance via `--metadata-options HttpTokens=optional` on `run-instances` or `modify-instance-metadata-options`, on any platform, exactly as AWS does. The launch default is `required` everywhere except **Windows** images, which default to `optional` because cloudbase-init has no IMDSv2 token support in any release and would otherwise never read metadata at all. `--http-endpoint disabled`, `--http-protocol-ipv6 enabled` and `--instance-metadata-tags enabled` are still rejected with `UnsupportedOperation`. - -```bash -# Inside the guest VM: -TOKEN=$(curl -s -X PUT "http://169.254.169.254/latest/api/token" \ - -H "X-aws-ec2-metadata-token-ttl-seconds: 60") -curl -s -H "X-aws-ec2-metadata-token: $TOKEN" \ - http://169.254.169.254/latest/meta-data/instance-id - -# Tokenless GET → 401 Unauthorized (empty body) -curl -i http://169.254.169.254/latest/meta-data/instance-id -``` - -### IMDS — Deployment CA - -A guest that calls a Spinifex HTTPS endpoint with an AWS SDK needs the deployment CA in its trust -store. The CA is served from the IMDS responder at `/spinifex/ca.pem` — deliberately outside the -`/latest` tree, because the AWS-compatible surface stays byte-identical to EC2's and cloud-init must -never descend into a Spinifex-only path. - -The route is **token-free**: a CA certificate is public material (the console already serves it -unauthenticated at `/api/ca.pem`), and requiring the IMDSv2 handshake would push a token dance into -every bootstrap snippet. The `X-Forwarded-For` SSRF guard still applies, as on every other path. - -```yaml -#cloud-config -runcmd: - # Debian/Ubuntu - - curl -fsS http://169.254.169.254/spinifex/ca.pem -o /usr/local/share/ca-certificates/spinifex.crt - - update-ca-certificates -``` - -RHEL/Rocky write to `/etc/pki/ca-trust/source/anchors/spinifex.crt` and run `update-ca-trust`; stock -Alpine has no updater or anchor directory, so append the PEM to `/etc/ssl/certs/ca-certificates.crt`. -Rotating `ca.pem` on a node is served immediately — vpcd re-reads the file when it changes. - -### IMDS — Supported Paths - -| Path | Method | Source | Status | -|------|--------|--------|--------| -| `/latest/api/token` | PUT | Issues an ENI-bound IMDSv2 token; `X-aws-ec2-metadata-token-ttl-seconds` ∈ [1, 21600] required | **DONE** | -| `/` | GET | Supported API-version list (`2021-07-15`, `latest`); token-gated | **DONE** | -| `/latest` | GET | Top-level tree listing (`dynamic`, `meta-data`, `user-data`) | **DONE** | -| `//...` | GET/PUT | Any dated API version aliases to `/latest` (cloud-init parity) | **DONE** | -| `/latest/meta-data/` | GET | Directory listing of supported children | **DONE** | -| `/latest/meta-data/instance-id` | GET | `vm.ID` | **DONE** | -| `/latest/meta-data/instance-type` | GET | `vm.InstanceType` | **DONE** | -| `/latest/meta-data/ami-id` | GET | launch `ImageId` | **DONE** | -| `/latest/meta-data/ami-launch-index` | GET | Per-instance launch index (`0..n-1`), contiguous on partial failure | **DONE** | -| `/latest/meta-data/reservation-id` | GET | `DescribeInstances` `Reservation.ReservationId` | **DONE** | -| `/latest/meta-data/instance-life-cycle` | GET | `spot` for a spot-launched instance, else `on-demand`; defaults to `on-demand` on a resolution miss (never 404, the leaf is always advertised) | **DONE** | -| `/latest/meta-data/local-ipv4` | GET | `ENIRecord.PrivateIpAddress` (== request source IP) | **DONE** | -| `/latest/meta-data/public-ipv4` | GET | EIP, else instance public IP; empty body if none | **DONE** | -| `/latest/meta-data/public-hostname` | GET | Mirrors `public-ipv4`; 404 when no public IP | **DONE** | -| `/latest/meta-data/mac` | GET | `ENIRecord.MacAddress` | **DONE** | -| `/latest/meta-data/security-groups` | GET | `ENIRecord.SecurityGroupIds`, newline-separated | **DONE** | -| `/latest/meta-data/hostname`, `/local-hostname` | GET | Synthesised `ip-..compute.internal` | **DONE** | -| `/latest/meta-data/placement/availability-zone` | GET | `ENIRecord.AvailabilityZone` | **DONE** | -| `/latest/meta-data/placement/region` | GET | Derived from AZ (trailing letter stripped) | **DONE** | -| `/latest/meta-data/services/{domain,partition}` | GET | Static: `amazonaws.com` / `aws` | **DONE** | -| `/latest/meta-data/iam/info` | GET | `{InstanceProfileArn, InstanceProfileId}`; 404 if no profile | **DONE** | -| `/latest/meta-data/iam/security-credentials/` | GET | Role name(s) under the profile, one per line; empty body if none | **DONE** | -| `/latest/meta-data/iam/security-credentials/` | GET | STS `AssumeRoleForInstance` → ASIA-prefixed temporary credential JSON | **DONE** | -| `/latest/meta-data/public-keys/` | GET | `0=` from the launch key pair; 404 if none | **DONE** | -| `/latest/meta-data/public-keys/0/` | GET | `openssh-key` (format list for index 0) | **DONE** | -| `/latest/meta-data/public-keys/0/openssh-key` | GET | Launch SSH public key, live-fetched from the key store; 404 if the key was deleted, 500 on backend fault | **DONE** | -| `/latest/user-data` | GET | `vm.UserData`; 404 if none | **DONE** | -| `/spinifex/ca.pem` | GET | Deployment CA PEM (`application/x-pem-file`); token-free, outside the AWS tree; 404 when no CA is configured | **DONE** | -| `/latest/dynamic` | GET | Lists `instance-identity/` | **DONE** | -| `/latest/dynamic/instance-identity` | GET | Lists `document` (signed forms listed when the signing key lands) | **DONE** | -| `/latest/dynamic/instance-identity/document` | GET | Unsigned identity document from resolved ENI + instance facts | **DONE** | -| `/latest/dynamic/instance-identity/{signature,pkcs7,rsa2048}` | GET | Signed forms; need a per-cluster signing key | **NOT STARTED** (404; lands with EKS IRSA) | -| `/latest/meta-data/network/interfaces/macs//...` | GET | Primary ENI subtree: `mac`, `device-number`, `interface-id`, `owner-id`, `subnet-id`, `vpc-id`, `local-ipv4s`, `local-hostname`, `security-group-ids`, `security-groups`, `subnet-ipv4-cidr-block`, `vpc-ipv4-cidr-block(s)`, and `public-ipv4s`/`public-hostname` when an EIP is attached | **DONE** (single-NIC; multi-ENI deferred) | -| `/latest/meta-data/tags/instance/` | GET | Instance-tag metadata; gated on `InstanceMetadataTags` enablement | **NOT STARTED** (404) | -| `/latest/meta-data/block-device-mapping/...` | GET | `ami`/`root`/`ebsN`/`ephemeralN` device map | **NOT STARTED** (404) | -| `/latest/meta-data/placement/{group-name,partition-number,availability-zone-id,host-id}` | GET | Placement extras beyond `availability-zone`/`region` | **NOT STARTED** (404) | -| `/latest/meta-data/instance-action` | GET | `none` unless interruptible instances ship | **NOT STARTED** (404) | -| `/latest/meta-data/spot/{instance-action,termination-time}` | GET | 404 is the faithful steady state for a never-interrupted spot instance ("no action scheduled"); a 200 body would trigger interruption handling in pollers (AWS Node Termination Handler / Karpenter). Not advertised in the `spot/` listing | **DONE** (404 by contract) | - ---- - -## ELBv2 (Application & Network Load Balancer) - -The data plane uses a system-managed LB VM, launched automatically during `create-load-balancer`. Application Load Balancers run **HAProxy** (L7: rules, fixed-response, redirect, HTTP/HTTPS). Network Load Balancers run **nginx `stream`** (L4: TCP, UDP, TLS, TCP_UDP) — HAProxy cannot load-balance UDP. The agent selects the engine from the `Engine` field on the config-delivery response. - -### ELBv2 — Load Balancers - -| Command | Implemented Flags | Missing Flags | Status | -|---------|-------------------|---------------|--------| -| `create-load-balancer` | `--name`, `--subnets`, `--security-groups`, `--scheme` (internet-facing/internal), `--tags`, `--ip-address-type` (ipv4) | `--type` (hardcoded application), `--customer-owned-ipv4-pool`, `--dry-run` | **DONE** | -| `delete-load-balancer` | `--load-balancer-arn` | `--dry-run` | **DONE** | -| `describe-load-balancers` | `--load-balancer-arns`, `--names` | `--page-size`, `--marker`, `--dry-run` | **DONE** | - -### ELBv2 — Target Groups - -| Command | Implemented Flags | Missing Flags | Status | -|---------|-------------------|---------------|--------| -| `create-target-group` | `--name`, `--protocol` (HTTP), `--port`, `--vpc-id`, `--target-type` (instance), `--health-check-protocol`, `--health-check-port`, `--health-check-path`, `--health-check-interval-seconds`, `--health-check-timeout-seconds`, `--healthy-threshold-count`, `--unhealthy-threshold-count`, `--matcher`, `--tags` | `--health-check-enabled`, `--protocol-version`, `--ip-address-type`, `--dry-run` | **DONE** | -| `delete-target-group` | `--target-group-arn` | `--dry-run` | **DONE** | -| `describe-target-groups` | `--target-group-arns`, `--names`, `--load-balancer-arn` | `--page-size`, `--marker`, `--dry-run` | **DONE** | - -### ELBv2 — Targets - -| Command | Implemented Flags | Missing Flags | Status | -|---------|-------------------|---------------|--------| -| `register-targets` | `--target-group-arn`, `--targets` (Id, Port) | `--dry-run` | **DONE** | -| `deregister-targets` | `--target-group-arn`, `--targets` (Id, Port) | `--dry-run` | **DONE** | -| `describe-target-health` | `--target-group-arn`, `--targets` | `--include` | **DONE** | - -### ELBv2 — Listeners - -| Command | Implemented Flags | Missing Flags | Status | -|---------|-------------------|---------------|--------| -| `create-listener` | `--load-balancer-arn`, `--default-actions` (Type=forward, TargetGroupArn), `--protocol` (HTTP/HTTPS/TLS), `--port`, `--certificates` (HTTPS/TLS), `--ssl-policy` | `--alpn-policy`, `--mutual-authentication`, `--dry-run` | **DONE** | -| `modify-listener` | `--listener-arn`, `--protocol`, `--port`, `--default-actions`, `--certificates`, `--ssl-policy` | `--alpn-policy`, `--mutual-authentication`, `--dry-run` | **DONE** | -| `delete-listener` | `--listener-arn` | `--dry-run` | **DONE** | -| `describe-listeners` | `--load-balancer-arn`, `--listener-arns` | `--page-size`, `--marker`, `--dry-run` | **DONE** | - -### ELBv2 — Listener Rules - -| Command | Implemented Flags | Missing Flags | Status | -|---------|-------------------|---------------|--------| -| `create-rule` | `--listener-arn`, `--priority` (1–50000), `--conditions` (host-header, path-pattern, http-header, http-request-method, query-string, source-ip), `--actions` (forward, redirect, fixed-response), `--tags` | `--dry-run` | **DONE** | -| `modify-rule` | `--rule-arn`, `--conditions`, `--actions` | `--dry-run` | **DONE** | -| `delete-rule` | `--rule-arn` | `--dry-run` | **DONE** | -| `describe-rules` | `--listener-arn`, `--rule-arns` | `--page-size`, `--marker` (parsed, not enforced) | **DONE** | -| `set-rule-priorities` | `--rule-priorities` (RuleArn, Priority) | — | **DONE** | - -A synthetic `default` rule is derived from the listener's `DefaultActions`. - -### ELBv2 — Listener Certificates & SSL Policies - -| Command | Implemented Flags | Missing Flags | Status | -|---------|-------------------|---------------|--------| -| `add-listener-certificates` | `--listener-arn`, `--certificates` | `--dry-run` | **DONE** | -| `remove-listener-certificates` | `--listener-arn`, `--certificates` | `--dry-run` | **DONE** | -| `describe-listener-certificates` | `--listener-arn` | `--page-size`, `--marker` | **DONE** | -| `describe-ssl-policies` | `--names` | `--load-balancer-type`, `--page-size`, `--marker` | **DONE** (static catalog: `ELBSecurityPolicy-FS-1-2-Res-2019-08`, `ELBSecurityPolicy-TLS13-1-2-2021-06` — metadata only, no in-platform TLS termination) | - -The default certificate cannot be added/removed via these calls — set it on the listener. - -### ELBv2 — Attributes & Modify - -| Command | Implemented Flags | Missing Flags | Status | -|---------|-------------------|---------------|--------| -| `describe-load-balancer-attributes` | `--load-balancer-arn` | — | **DONE** (stored values over per-type defaults) | -| `modify-load-balancer-attributes` | `--load-balancer-arn`, `--attributes` | — | **DONE** (unknown keys → `ValidationError`) | -| `describe-target-group-attributes` | `--target-group-arn` | — | **DONE** | -| `modify-target-group-attributes` | `--target-group-arn`, `--attributes` (incl. `deregistration_delay.timeout_seconds`, `stickiness.*`) | — | **DONE** | -| `modify-target-group` | `--target-group-arn`, `--health-check-*`, `--matcher` | `--target-type`/`--protocol`/`--vpc-id` (immutable) | **DONE** | -| `describe-listener-attributes` | `--listener-arn` | — | **DONE** (stub — returns empty; not persisted) | -| `modify-listener-attributes` | `--listener-arn`, `--attributes` | — | **DONE** (stub — echoes input; not persisted) | - -### ELBv2 — Network & Security - -| Command | Implemented Flags | Missing Flags | Status | -|---------|-------------------|---------------|--------| -| `set-security-groups` | `--load-balancer-arn`, `--security-groups` | `--enforce-security-group-inbound-rules-on-private-link-traffic` | **DONE** (ALB only — NLB → `InvalidConfigurationRequest`) | -| `set-subnets` | `--load-balancer-arn`, `--subnets`, `--subnet-mappings` | `--ip-address-type` | **DONE** (live ENI add/remove with rollback) | -| `set-ip-address-type` | `--load-balancer-arn`, `--ip-address-type` (ipv4) | dualstack/IPv6 (rejected) | **DONE** | - -### ELBv2 — Tags - -| Command | Implemented Flags | Missing Flags | Status | -|---------|-------------------|---------------|--------| -| `describe-tags` | `--resource-arns` (loadbalancer, targetgroup, listener) | — | **DONE** | -| `add-tags` | `--resource-arns`, `--tags` | — | **DONE** | -| `remove-tags` | `--resource-arns`, `--tag-keys` | — | **DONE** | - -### ELBv2 — Not Yet Implemented - -| Feature | Priority | Status | -|---------|----------|--------| -| In-platform HTTPS/TLS termination (cert + SSL-policy APIs exist; data-plane TLS not terminated) | High | **NOT STARTED** | -| ALPN policy, mutual TLS (mTLS) | Medium | **NOT STARTED** | -| Listener attribute persistence (`Describe/ModifyListenerAttributes` are stubs) | Medium | **NOT STARTED** | -| Active health checking (API-driven, vs. HAProxy/nginx-only today) | Medium | **NOT STARTED** | -| IP and Lambda target types | Low | **NOT STARTED** | -| S3 access log delivery | Low | **NOT STARTED** | -| WAF integration | Low | **NOT STARTED** | - ---- - -## ACM (AWS Certificate Manager) - -Spinifex both stores externally-issued certificates (`import-certificate`) and issues its own (`request-certificate`) for ELBv2 listener references. Certs are account-scoped; `describe`/`delete` enforce ownership, and `delete-certificate` refuses with `ResourceInUseException` while any load balancer listener still references the ARN — no force flag, matching AWS. - -`request-certificate` mints a `CertificateArn` immediately and returns `PENDING_VALIDATION`; it never issues inline. The validation mode is derived from deployment state, never configured: - -| Mode | Who writes the DNS record | `ResourceRecord` returned | Renewal | Status | -| --- | --- | --- | --- | --- | -| `PROVIDER_API` | Spinifex, via the operator's DNS provider API | none | automatic | request accepted, `PENDING_VALIDATION` — the DNS-01 order is driven by a later worker | -| `MANUAL_TXT` | the operator, by hand or Terraform | TXT, rotates per order | manual — `INELIGIBLE` | request accepted, `PENDING_VALIDATION` — same as above | -| `CNAME_DELEGATION` | operator once, then Spinifex | CNAME, stable | automatic | deferred — never selected yet (northstar cannot serve public authoritative queries); an ARN-stable delegation token is minted on every managed certificate now so this lands as a non-breaking addition | -| `PRIVATE_CA` | nobody — no validation | none | automatic | **DONE** — issues synchronously against the tenant CA, no domain outside its name constraints | - -`PROVIDER_API` is selected when a DNS provider credential is configured; `MANUAL_TXT` when northstar hosts the zone; otherwise `PRIVATE_CA` — the only option for a deployment with no real, publicly delegated domain. Terraform's canonical `aws_acm_certificate` → `aws_route53_record` → `aws_acm_certificate_validation` → `aws_lb_listener` flow works unmodified in every mode: where Spinifex owns the record write, no `ResourceRecord` is emitted, so `for_each` over `domain_validation_options` yields zero records and `aws_acm_certificate_validation` still blocks correctly by polling until `ISSUED`. - -| Command | Implemented Flags | Missing Flags | Status | -|---------|-------------------|---------------|--------| -| `import-certificate` | `--certificate`, `--private-key`, `--certificate-chain`, `--certificate-arn` (re-import) | `--tags` | **DONE** | -| `describe-certificate` | `--certificate-arn` | — | **DONE** | -| `list-certificates` | — | `--certificate-statuses`, `--includes`, `--max-items`, `--next-token` | **DONE** | -| `get-certificate` | `--certificate-arn` | — | **DONE** — returns the leaf certificate and its chain | -| `delete-certificate` | `--certificate-arn` | — | **DONE** | -| `request-certificate` | `--domain-name`, `--subject-alternative-names`, `--tags` | `--validation-method`, `--certificate-authority-arn`, `--options`, `--idempotency-token` | **PARTIAL** — `PRIVATE_CA` issues synchronously; `PROVIDER_API`/`MANUAL_TXT` are accepted and correctly shaped but stay `PENDING_VALIDATION` until a later issuance worker lands | -| `add-tags-to-certificate` / `list-tags-for-certificate` / `remove-tags-from-certificate` | `--certificate-arn`, `--tags`/`--tag-keys` | — | **DONE** | -| `export-certificate` | — | `--certificate-arn`, `--passphrase` | **NOT STARTED** | - ---- - -## RDS (PostgreSQL and MariaDB) - -Each DB instance is one dedicated system-owned VM running the engine directly, launched from the `spinifex-rds-postgres` or `spinifex-rds-mariadb` AMI, tagged `spinifex:managed-by=rds` and therefore hidden from the customer's EC2 API. The engine is reached over a customer-account ENI injected into a subnet of the DB subnet group, so **the endpoint is private — reachable from inside the VPC only**, from any subnet of it rather than the endpoint ENI's own. `Endpoint.Address` is `{db-instance-identifier}.{account-id}.{region}.rds.{base-domain}` where northstar is configured, and the endpoint ENI's private IP where it is not; the IP is stable across VM replacement either way. - -**The endpoint is the only path to the engine.** The DB VM has two other NICs that no customer security group governs — a system NIC in a shared RDS system VPC, which is how the in-guest agent reaches the control plane, and a management NIC on the host's management bridge — and the engine binds neither. It binds the endpoint ENI's address alone, so the port is not open on them at all rather than open and gated. The system NIC additionally carries a dedicated region-wide security group that authorizes no ingress; agent traffic is outbound and its replies are matched by connection state. PostgreSQL's generated `pg_hba.conf` admits the customer VPC's address range and nothing wider, so a client outside the VPC is refused authentication even if it somehow reached the socket. MariaDB has no equivalent file: its analogue is the host pattern on a grant, which lives in the data volume and would follow a restore into another VPC, so for that engine the bind is the whole boundary. - -Everything below applies to both engines unless it names one. `Engine` is fixed at create — there is no in-place engine change, no cross-engine snapshot restore and no migration between the two. - -| | `postgres` | `mariadb` | -|---|---|---| -| Version | 18 | 11.8 | -| `EngineVersion` accepted | `18`, or omitted | `11.8`, or omitted | -| Default port | 5432 | 3306 | -| Parameter-group family | `postgres18` | `mariadb11.8` | -| Implicit default group | `default.postgres18` | `default.mariadb11.8` | -| `DBName` maximum | 63 characters | 64 characters | -| `MasterUsername` maximum | 63 characters | 80 characters | -| Reserved usernames | `postgres`, `rdsadmin`, `rds_superuser`, and the `pg_` prefix | `root`, `mysql`, `mariadb.sys`, `rdsadmin`, `PUBLIC`, and the `mysql.` and `mariadb.` prefixes | -| Catalog size | 53 parameters | 56 parameters | - -**`mysql` is not an accepted engine and is not an alias for `mariadb`.** MariaDB is offered under its own AWS engine name, exactly as AWS RDS offers it. Naming `mysql` fails with `InvalidParameterValue`; a client — including Terraform's `aws_db_instance` — must set `engine = "mariadb"`. Aliasing would report an engine and a version the instance is not running, and the discrepancy would propagate into `DescribeDBInstances`, parameter-group families and snapshot metadata. - -- **Engine version:** pinned per engine, and an `EngineVersion` naming anything but the pin is rejected. A minor version such as `18.4` or `11.8.8` is rejected as well: the AMI does not promise any particular minor, so accepting one would be a promise the platform cannot keep. There is no in-place upgrade. -- **Instance classes:** `db.t3.{micro,small,medium,large}` and `db.m5.{large,xlarge}` — a naming facade over the platform's EC2 sizing table. Any other class is rejected at create. **`db.X` is the EC2 instance type `X`**, so a client reads a class's vCPU count and memory from `ec2:describe-instance-types` for the identically named type; an orderable option carries neither, because AWS's own shape has no field for them. `describe-orderable-db-instance-options` reports only the classes the cluster's nodes can actually run, which on a Graviton-only cluster is none of the six — a class that would fail at launch is not offered. -- **Storage:** gp3 only, 20–65536 GiB, always encrypted with the cluster key. Grow-only, and a grow is **stop/start with downtime** — the volume cannot be resized while attached. -- **`DBName`:** optional; an omitted name creates no initial database. When supplied it must begin with a letter and hold only letters, digits and underscores, within the per-engine limit above. The rule is narrower than either engine's own, because the guest interpolates the name into a `CREATE DATABASE`. -- **TLS v1.3:** **required by default on both engines** — `rds.force_ssl` on `postgres18` and `require_secure_transport` on `mariadb11.8`, both boolean, modifiable and dynamic, both defaulting to `1`. Setting either to `0` in a parameter group restores plaintext without a reboot. Defaulting on is a **deliberate divergence** for MariaDB, which AWS leaves off. -- **What enforcement requires** is that the connection is encrypted, not that the client validates the certificate: `sslmode=require` satisfies it and does no validation at all. The engine serves a per-instance certificate signed by the cluster CA carrying both the ENI IP and the DNS name in its SAN set, so `sslmode=verify-full` — or MariaDB's `--ssl-ca` plus `--ssl-verify-server-cert` — verifies by name or by address; a client that wants to fetches the CA from the IMDS responder at `http://169.254.169.254/spinifex/ca.pem`. A deployment holding no cluster CA cannot serve TLS at all, so a group asking for enforcement is refused with `InvalidParameterCombination`, and the guest will not start an engine that could not honour it.**`go-sql-driver/mysql`** (no TLS without a `tls` DSN parameter) do not. -- **PostgreSQL master user:** administrative but **not a PostgreSQL superuser**, as on AWS. It gets `CREATEDB` and `CREATEROLE`, owns the initial database, and holds `rds_superuser` (`pg_monitor`, `pg_signal_backend`, `pg_checkpoint`) with `ADMIN OPTION`, so it can grant that set onward. It cannot `COPY ... FROM/TO PROGRAM`, touch server-side files, run `ALTER SYSTEM`, or install **untrusted** extensions — those need the cluster superuser, which no customer credential is. Trusted extensions install normally in a database it owns. -- **MariaDB master user:** created as `''@'%'` with global `RELOAD`, `PROCESS`, `SHOW DATABASES`, `REPLICATION SLAVE` and `REPLICATION CLIENT`, while application DML, DDL, routines, events, triggers and delegation are granted only on customer databases. MariaDB has no deny or partial-revoke mechanism, so granting those object privileges `ON *.*` would also grant them on `mysql.global_priv` and let the master acquire `SUPER`, `FILE` or `SHUTDOWN`. The initial `DBName` is granted automatically. Create another customer database with `CALL _spinifex_rds.create_database('name')`; plain `CREATE DATABASE`, arbitrary account administration and access to `mysql.*` are intentionally unavailable on the stock MariaDB build. -- **MariaDB storage engine:** `default_storage_engine` is platform-owned and pinned to **InnoDB**, and is absent from the parameter catalog — a deliberate divergence from AWS, which exposes it as modifiable. Only InnoDB keeps a redo log, so only InnoDB is covered by the snapshot guarantee. An explicit `ENGINE=Aria` or `ENGINE=MyISAM` on `CREATE TABLE` still works — the limitation is documented rather than prevented — but such a table has no redo log, so a snapshot taken without a successful quiesce can leave it inconsistent with no way back. Use InnoDB, as AWS also recommends. -- **Backups:** daily COW snapshots of the data volume inside `PreferredBackupWindow`. Retention defaults to 7 days and caps at 7; `0` disables automated backups. No point-in-time recovery, and MariaDB's binary log is off. -- **Availability:** single-AZ. Engine crashes restart in-guest and VM crashes on a live host restart via `ec2-health-restart`, but an instance whose host is lost is reported `failed` with a reason in `StatusInfos` and needs operator recovery. - -Statuses: `creating`, `available`, `modifying`, `backing-up`, `rebooting`, `stopping`, `stopped`, `starting`, `deleting`, `failed`. (`recovering` is defined in the state machine but unreachable until auto-recovery lands.) - -### RDS — DB Instances - -| Command | Implemented Flags | Missing Flags | Status | -|---------|-------------------|---------------|--------| -| `create-db-instance` | `--db-instance-identifier`, `--engine` (postgres, mariadb), `--engine-version` (the engine's pin, or omitted), `--db-instance-class`, `--allocated-storage` (20–65536 GiB), `--storage-type` (gp3), `--master-username`, `--master-user-password`, `--db-name` (letters, digits and underscores, beginning with a letter, max 63 on postgres and 64 on mariadb), `--port` (1150–65535), `--db-subnet-group-name` (unnamed → the account's default VPC subnet), `--vpc-security-group-ids`, `--db-parameter-group-name`, `--backup-retention-period` (0–7, default 7), `--preferred-backup-window`, `--preferred-maintenance-window` (unnamed → assigned from the identifier), `--deletion-protection`, `--tags`, `--storage-encrypted` (true only) | `--auto-minor-version-upgrade`, `--copy-tags-to-snapshot`, Performance Insights / Enhanced Monitoring flags (all accepted, no-op); see "Rejected Parameters" for those that fail loudly | **DONE** | -| `describe-db-instances` | `--db-instance-identifier` | `--filters`, `--max-records`, `--marker` (parsed, not applied) | **DONE** | -| `modify-db-instance` | `--db-instance-identifier`, `--master-user-password`, `--allocated-storage` (grow only, stop/start), `--db-instance-class` (VM replace), `--db-parameter-group-name`, `--vpc-security-group-ids`, `--deletion-protection`, `--backup-retention-period`, `--preferred-backup-window`, `--preferred-maintenance-window`, `--apply-immediately` | `--new-db-instance-identifier`, `--engine-version`, `--db-port-number`, `--db-subnet-group-name`, `--max-allocated-storage`, `--ca-certificate-identifier` (all rejected, not ignored) | **DONE** | -| `delete-db-instance` | `--db-instance-identifier`, `--skip-final-snapshot`, `--final-db-snapshot-identifier` (exactly one is required) | `--delete-automated-backups` (no-op — automated snapshots are always purged with the instance) | **DONE** — `DeletionProtection` blocks the call; a final snapshot **retains** the data volume until that snapshot is deleted | -| `reboot-db-instance` | `--db-instance-identifier` | `--force-failover` (rejected — single-AZ) | **DONE** — applies parameters marked `pending-reboot` | -| `stop-db-instance` | `--db-instance-identifier` | `--db-snapshot-identifier` (rejected) | **DONE** — the data volume and endpoint ENI are retained | -| `start-db-instance` | `--db-instance-identifier` | — | **DONE** — fresh VM, same data volume, same ENI and IP | - -### RDS — Snapshots & Restore - -| Command | Implemented Flags | Missing Flags | Status | -|---------|-------------------|---------------|--------| -| `create-db-snapshot` | `--db-snapshot-identifier`, `--db-instance-identifier`, `--tags` | — | **DONE** — the agent quiesces the engine first (`pg_backup_start` on postgres, `BACKUP STAGE` on mariadb); a failed quiesce falls back to a crash-consistent snapshot and writes a `DescribeEvents` warning naming what that engine does and does not recover | -| `describe-db-snapshots` | `--db-snapshot-identifier`, `--db-instance-identifier`, `--snapshot-type` (manual, automated) | `--filters`, `--dbi-resource-id`, `--include-shared`, `--include-public` (rejected), `--max-records`, `--marker` | **DONE** | -| `delete-db-snapshot` | `--db-snapshot-identifier` | — | **DONE** — refused while a restored volume still references the snapshot; the last snapshot released reclaims a retained data volume | -| `restore-db-instance-from-db-snapshot` | `--db-instance-identifier`, `--db-snapshot-identifier`, `--db-instance-class`, `--allocated-storage` (≥ the snapshot's), `--storage-type` (gp3), `--port`, `--db-subnet-group-name`, `--vpc-security-group-ids`, `--db-parameter-group-name`, `--deletion-protection`, `--tags`, `--engine` (must match the snapshot) | `--db-name` (rejected when it differs from the snapshot's), plus the create rejections | **DONE** — unnamed fields are inherited from the snapshot; the master password comes from the restored datadir | -| `copy-db-snapshot` | — | all | **NOT STARTED** (`InvalidAction`) | -| `modify-db-snapshot-attribute` / `describe-db-snapshot-attributes` | — | all | **NOT STARTED** (`InvalidAction`) — cross-account snapshot sharing | - -### RDS — Automated Backups - -| Command | Implemented Flags | Missing Flags | Status | -|---------|-------------------|---------------|--------| -| `describe-db-instance-automated-backups` | `--db-instance-identifier` | `--filters`, `--dbi-resource-id`, `--db-instance-automated-backups-arn` (rejected) | **DONE** — one entry per instance with backups enabled; the individual snapshots are listed by `describe-db-snapshots --snapshot-type automated` | - -`RestoreWindow` and `LatestRestorableTime` are deliberately absent: backups are discrete daily snapshots, and reporting a window would imply recovery to any instant inside it. - -### RDS — Subnet Groups - -| Command | Implemented Flags | Missing Flags | Status | -|---------|-------------------|---------------|--------| -| `create-db-subnet-group` | `--db-subnet-group-name`, `--db-subnet-group-description`, `--subnet-ids`, `--tags` | — | **DONE** (any subnet count — every subnet reports the single `spinifexz1` zone) | -| `describe-db-subnet-groups` | `--db-subnet-group-name` | `--filters`, `--max-records`, `--marker` | **DONE** | -| `delete-db-subnet-group` | `--db-subnet-group-name` | — | **DONE** — refused while any DB instance still names the group, including one that is deleting | -| `modify-db-subnet-group` | — | all | **NOT STARTED** (`InvalidAction`) | - -### RDS — Parameter Groups - -| Command | Implemented Flags | Missing Flags | Status | -|---------|-------------------|---------------|--------| -| `create-db-parameter-group` | `--db-parameter-group-name`, `--db-parameter-group-family` (`postgres18` or `mariadb11.8`), `--description`, `--tags` | — | **DONE** — names beginning with `default.` are reserved. **`--db-parameter-group-family` defaults to `postgres18` when omitted**, so a MariaDB group must name its family explicitly or the mismatch surfaces one call later, at `create-db-instance` | -| `describe-db-parameter-groups` | `--db-parameter-group-name` | `--filters`, `--max-records`, `--marker` | **DONE** — every engine's implicit default group is always listed, so both `default.postgres18` and `default.mariadb11.8` appear in every account | -| `modify-db-parameter-group` | `--db-parameter-group-name`, `--parameters` (ParameterName, ParameterValue, ApplyMethod) | — | **DONE** — the whole batch is validated before anything is written and propagated to attached instances; `immediate` on a static parameter is rejected, as AWS does | -| `describe-db-parameters` | `--db-parameter-group-name`, `--source` (user, engine-default) | `--filters`, `--max-records`, `--marker` | **DONE** — the catalog of the group's own family: 53 parameters on `postgres18`, 56 on `mariadb11.8`. Memory defaults are computed per instance class and reported as literals | -| `delete-db-parameter-group` | `--db-parameter-group-name` | — | **DONE** — refused for a default group and while any instance references it | -| `reset-db-parameter-group` | — | all | **NOT STARTED** (`InvalidAction`) | - -A group takes effect on an instance when `modify-db-instance --db-parameter-group-name` attaches it — immediately with `--apply-immediately`, otherwise at the next maintenance window. Later group edits propagate to every attached instance. Dynamic parameters are written into the engine's config and reloaded live; static ones are recorded `pending-reboot` and applied by `reboot-db-instance`. - -**A group's family must match the instance's engine.** A `postgres18` group cannot be attached to a MariaDB instance and a `mariadb11.8` group cannot be attached to a PostgreSQL one, on create, on modify, on a deferred apply or on a snapshot restore; the mismatch is refused with `InvalidParameterCombination`. The catalogs are per-family too, so `modify-db-parameter-group` will not store one engine's parameter name into the other's group. Each catalog is a curated, validated subset rather than the engine's full variable set, and the platform-owned settings — the port, the datadir, the socket, the bind address, the certificate and key paths, and on MariaDB `secure_file_priv`, `log_bin`, `default_storage_engine` and the InnoDB buffer-pool chunk settings — are absent from it rather than present-and-unmodifiable, because they are not the customer's to set. The exception is a setting AWS exposes as modifiable that this platform pins: the TLS floor is present as `ssl_min_protocol_version` and `tls_version` and reported as not modifiable, so a Terraform plan that sets it is refused as policy rather than reading as a platform gap. - -### RDS — Tags - -| Command | Implemented Flags | Missing Flags | Status | -|---------|-------------------|---------------|--------| -| `add-tags-to-resource` | `--resource-name` (db, snapshot, subgrp, pg ARNs), `--tags` | — | **DONE** | -| `remove-tags-from-resource` | `--resource-name`, `--tag-keys` | — | **DONE** | -| `list-tags-for-resource` | `--resource-name` | `--filters` | **DONE** — `describe-db-instances` reports the same tags in `TagList` | - -### RDS — Events - -| Command | Implemented Flags | Missing Flags | Status | -|---------|-------------------|---------------|--------| -| `describe-events` | `--source-type` (db-instance, db-snapshot), `--source-identifier`, `--event-categories`, `--duration`, `--start-time`, `--end-time`, `--max-records` | `--marker` | **DONE** — 100-event ring per resource, 14-day retention, one-hour default window | - -### RDS — Engine Versions & Orderable Options - -| Command | Implemented Flags | Missing Flags | Status | -|---------|-------------------|---------------|--------| -| `describe-db-engine-versions` | `--engine`, `--engine-version`, `--db-parameter-group-family`, `--filters` (`engine`, `engine-version`, `db-parameter-group-family`, `status`) | `--default-only`, `--include-all`, `--list-supported-character-sets`, `--list-supported-timezones` (accepted, provably no-ops), `--max-records` (accepted, no effect), `--marker` (rejected) | **DONE** — one row per engine | -| `describe-orderable-db-instance-options` | `--engine` (required), `--engine-version`, `--db-instance-class`, `--license-model`, `--vpc`, `--filters` (`engine`, `engine-version`, `db-instance-class`, `license-model`, `vpc`) | `--max-records` (accepted, no effect), `--marker`, `--availability-zone-group` (both rejected) | **DONE** — the engines crossed with the classes the cluster's nodes can run | - -Both are read from the tables the create path validates against, so an engine pin bump or a class-map change moves these answers with it. Neither paginates — at most 2 engine versions and 12 orderable options — so no `Marker` is ever returned, and one supplied is rejected rather than answered as page one, where the other RDS describes parse and ignore it. - -- **`AvailabilityZones` and `AvailableProcessorFeatures` are always empty**, and are gaps only in appearance: `--availability-zone` is rejected on create and `--processor-features` is ignored, so naming either here would advertise a knob that does nothing. -- **Only the classes the cluster's nodes can run are offered.** A cluster that answers nothing is `ServerInternal`, never the full class list; one that answers and runs none of them is an empty list. Free capacity is deliberately not consulted — exhausted capacity is a create-time failure, and filtering on it would make a Terraform data source return a different answer on every plan. - -Two further deliberate divergences: the four `describe-db-engine-versions` booleans are accepted as **provable identities** rather than the "parsed, not applied" the other describes document, because one version per engine and two empty lists leave them nothing to change; and `--filters` on `describe-orderable-db-instance-options` is **applied** where AWS documents it unsupported. Both actions reject an unrecognised filter name, and a non-boolean `vpc` value, with `InvalidParameterValue` rather than ignoring it — stricter than AWS rather than looser. - -### RDS — Rejected Parameters - -Policy: a parameter whose omission would create a false safety, security or availability guarantee is rejected with `InvalidParameterValue` rather than silently dropped. Parameters that are merely inert — `AutoMinorVersionUpgrade`, `CopyTagsToSnapshot`, `DeleteAutomatedBackups`, Performance Insights and Enhanced Monitoring fields — are accepted as no-ops. - -| Parameter | Why it is rejected | -|-----------|--------------------| -| `MultiAZ=true` | Single-AZ platform; a standby would not exist | -| `PubliclyAccessible=true` | The endpoint is a private VPC address | -| `StorageEncrypted=false` | Unencrypted storage is not offered | -| `EnableIAMDatabaseAuthentication` | IAM database authentication is not implemented | -| `Iops`, `StorageThroughput`, `StorageType` ≠ `gp3` | Provisioned performance classes are not implemented | -| `KmsKeyId`, `TdeCredentialArn` | Storage is encrypted with the cluster key, not a customer-managed one | -| `AvailabilityZone` | The platform exposes a single zone | -| `AvailabilityZoneGroup` (orderable options) | It selects a zone or local-zone group, and naming a zone is already refused | -| `DBSecurityGroups` | EC2-Classic security groups — use `VpcSecurityGroupIds` | -| `DBClusterIdentifier`, `DBClusterSnapshotIdentifier` | Clustered engines are not offered | -| `EnableCloudwatchLogsExports` | Log export is not implemented | -| `EngineVersion` other than the engine's pin, `Engine` on modify | No in-place engine or version change | -| `Engine=mysql` (and Aurora engines) | Oracle MySQL is not offered; `mariadb` is a distinct engine, not an alias for it | -| `NewDBInstanceIdentifier` | The identifier is the DNS label and the KV key | -| `DBPortNumber`, `DBSubnetGroupName` on modify | Both would move the endpoint | -| `MaxAllocatedStorage` | Storage autoscaling is not implemented | -| `ManageMasterUserPassword`, `RotateMasterUserPassword` | Secrets Manager integration is not offered | -| `CACertificateIdentifier` | The serving certificate is minted from the cluster CA | -| `Domain`, `DomainFqdn` | Active Directory domain join is not offered | -| `OptionGroupName` | Option groups are not offered | -| `CustomIamInstanceProfile` | The DB VM's instance profile is platform-owned | -| `EnableCustomerOwnedIp` | An Outposts feature | -| `ForceFailover` (reboot) | No standby to fail over to | -| `DBSnapshotIdentifier` (stop) | Snapshot-on-stop is not implemented | - -### RDS — Not Yet Implemented - -Recognised actions below return `OperationNotSupported`, so a client sees "not offered" rather than a typo'd action name. Everything else in the `rds` namespace returns `InvalidAction`. - -| Feature | Actions | Priority | Status | -|---------|---------|----------|--------| -| Oracle MySQL engine | — | Low | **NOT PLANNED** — MariaDB is offered instead, under its own `mariadb` engine name; see the note above on why it is not aliased onto `mysql` | -| Point-in-time recovery (WAL archiving to predastore on postgres, binlog on mariadb) | `restore-db-instance-to-point-in-time` | High | **NOT STARTED** | -| Auto-recovery from node loss (failure is detected, not repaired) | — | High | **NOT STARTED** | -| Read replicas | `create-db-instance-read-replica`, `promote-read-replica` | Medium | **NOT STARTED** | -| Aurora / DB clusters | `create-db-cluster`, `modify-db-cluster`, `delete-db-cluster`, `describe-db-clusters`, `failover-db-cluster` | Low | **NOT STARTED** | -| Option groups | `create-option-group`, `modify-option-group`, `delete-option-group`, `describe-option-groups` | Low | **NOT STARTED** | -| Multi-AZ standby, online (no-downtime) storage grow, storage autoscaling, IAM database auth, Performance Insights, Enhanced Monitoring, log exports, per-tenant private DNS zones, enforced TLS, cross-engine snapshot restore, in-place migration between the two engines | — | — | **NOT STARTED** | - -IAM: `AmazonRDSFullAccess` and `AmazonRDSReadOnlyAccess` are available as managed policies. They grant `rds:` verb prefixes rather than `rds:*`, because `rds:*` would also appear to grant the internal agent actions the gateway reserves for a DB VM's own role. - ---- - -## ECR (Elastic Container Registry) - -Repository metadata is served over the AWS API on the gateway endpoint; image data moves over the OCI Distribution `/v2/` endpoint on that same host, authenticated by the bearer token `get-login-password` mints. - -| Command | Status | -|---------|--------| -| `create-repository`, `delete-repository`, `describe-repositories` | **DONE** | -| `describe-images`, `list-images`, `batch-get-image`, `batch-delete-image`, `put-image` | **DONE** | -| `put-image-tag-mutability` | **DONE** | -| `get-authorization-token` | **DONE** — mints the short-lived bearer token used by `docker login` | -| `get-repository-policy`, `set-repository-policy`, `delete-repository-policy` | **DONE** | -| `get-lifecycle-policy`, `put-lifecycle-policy`, `delete-lifecycle-policy`, `get-lifecycle-policy-preview`, `start-lifecycle-policy-preview` | **DONE** | -| `list-tags-for-resource` | **DONE** | -| `tag-resource`, `untag-resource` | **NOT STARTED** (registered stub) | -| `batch-check-layer-availability`, `initiate-layer-upload`, `upload-layer-part`, `complete-layer-upload`, `get-download-url-for-layer` | **NOT STARTED** (registered stub) — layer transfer is served by the OCI `/v2/` endpoint | -| `describe-registry`, `get-registry-policy`, `put-registry-policy`, `put-replication-configuration`, `replicate-image` | **NOT STARTED** (registered stub) — single-registry deployment, no cross-region replication | -| `list-repositories` | **NOT STARTED** (registered stub) — use `describe-repositories` | -| `start-image-scan`, `describe-image-scan-findings`, `put-image-scanning-configuration`, `get-image-scanning-configuration`, `get-registry-scanning-configuration`, `put-registry-scanning-configuration`, `batch-get-repository-scanning-configuration` | **NOT STARTED** (`OperationNotSupported`) — vulnerability scanning is not offered | -| Pull-through cache rules, repository creation templates, image replication status | **NOT STARTED** (`InvalidAction`) | - ---- - -## ECS (Elastic Container Service) - -Clusters, services and tasks run on EC2 container instances; there is no Fargate launch type. - -| Command | Status | -|---------|--------| -| `create-cluster`, `delete-cluster`, `describe-clusters`, `list-clusters` | **DONE** | -| `create-service`, `update-service`, `delete-service`, `describe-services`, `list-services` | **DONE** | -| `register-task-definition`, `deregister-task-definition`, `describe-task-definition`, `list-task-definitions` | **DONE** | -| `run-task`, `start-task`, `stop-task`, `describe-tasks`, `list-tasks` | **DONE** | -| `register-container-instance`, `deregister-container-instance`, `describe-container-instances`, `list-container-instances`, `update-container-instances-state` | **DONE** | -| `create-capacity-provider`, `delete-capacity-provider`, `describe-capacity-providers`, `put-cluster-capacity-providers` | **DONE** | -| `submit-task-state-change` | **DONE** — reported by the in-guest agent | -| `tag-resource`, `untag-resource`, `list-tags-for-resource` | **DONE** | -| `update-cluster`, `list-account-settings`, `put-account-setting`, `list-services-by-namespace`, `list-task-definition-families` | **NOT STARTED** (registered stub) | -| Task sets (blue/green): `create-task-set`, `update-task-set`, `delete-task-set`, `describe-task-sets`, `update-service-primary-task-set` | **NOT STARTED** (`InvalidAction`) | -| `execute-command`, `get-task-protection`, `update-task-protection` | **NOT STARTED** (`InvalidAction`) | -| Attributes: `put-attributes`, `delete-attributes`, `list-attributes` | **NOT STARTED** (`InvalidAction`) | -| `update-capacity-provider`, `update-cluster-settings`, `update-container-agent` | **NOT STARTED** (`InvalidAction`) | -| `delete-account-setting`, `put-account-setting-default`, `delete-task-definitions` | **NOT STARTED** (`InvalidAction`) | -| `discover-poll-endpoint`, `submit-container-state-change`, `submit-attachment-state-changes` | **NOT STARTED** (`InvalidAction`) | - ---- - -## EKS (Elastic Kubernetes Service) - -REST-JSON, dispatched by HTTP method + path rather than by an action parameter, -so the routing table in `gateway/eks.go` is the authoritative list. Clusters run -K3s on control-plane VMs; nodegroups are EC2 instances joined to them. - -| Command | Status | -|---------|--------| -| `create-cluster`, `describe-cluster`, `list-clusters`, `delete-cluster` | **DONE** | -| `create-nodegroup`, `describe-nodegroup`, `list-nodegroups`, `delete-nodegroup`, `update-nodegroup-config`, `update-nodegroup-version` | **DONE** | -| `create-addon`, `describe-addon`, `describe-addon-versions`, `list-addons`, `update-addon`, `delete-addon` | **DONE** | -| `create-access-entry`, `describe-access-entry`, `list-access-entries`, `update-access-entry`, `delete-access-entry` | **DONE** | -| `associate-access-policy`, `disassociate-access-policy`, `list-associated-access-policies`, `list-access-policies` | **DONE** | -| `tag-resource`, `untag-resource`, `list-tags-for-resource` | **DONE for cluster ARNs**; other EKS resource ARNs return `NotImplemented` | -| `update-cluster-config`, `update-cluster-version` | **NOT STARTED** (`NotImplemented`) | -| Identity provider configs: `associate-identity-provider-config`, `describe-identity-provider-config`, `list-identity-provider-configs`, `disassociate-identity-provider-config` | **NOT STARTED** (`NotImplemented`) | - -Four routes on this surface are **internal, not AWS actions**, and are not -callable with an ordinary tenant credential: `PublishInternal` (the control-plane -VM broker, relaying bootstrap/state POSTs onto `eks.bus.*`/`eks.state.*`), -`WebhookTokenReview` (the `eks-token-webhook` posting bearer tokens for host-side -resolution), `ListInternalAddons` (the on-VM addon-sync agent fetching its staged -manifests) and `GetRecoveryDirective` (the on-VM k3s-recovery agent reading its -per-member directive at boot). They name the target account in the path rather -than taking it from the credential, so each requires a control-plane instance-role -session bound to the named cluster — a broad `eks:*` grant does not reach them. - -Disaster recovery for a lost single control plane is an operator command, not an -API call: see `spx admin eks restore-snapshot` above. - ---- - -## Resource Groups Tagging API (`tagging`) - -JSON-1.1, dispatched from the action suffix of -`X-Amz-Target: ResourceGroupsTaggingAPI_20170126.`. - -| Command | Status | -|---------|--------| -| `get-resources` | **DONE** — authorizes against `"*"`, which is correct here rather than a fail-open: the Resource Groups Tagging API defines no resource types of its own. A two-way completeness test pins that, so a later action cannot be added to this surface with a silent account-wide grant | -| `get-tag-keys`, `get-tag-values`, `tag-resources`, `untag-resources` | **NOT STARTED** (`InvalidAction`) | - ---- - -## CloudWatch (Basic Monitoring) - -| Command | Implemented Flags | Missing Flags | Status | -|---------|-------------------|---------------|--------| -| `put-metric-data` | — | `--namespace`, `--metric-data` | **NOT STARTED** | -| `get-metric-statistics` | — | `--namespace`, `--metric-name`, `--start-time`, `--end-time`, `--period`, `--statistics`, `--dimensions` | **NOT STARTED** | -| `list-metrics` | — | `--namespace`, `--metric-name`, `--dimensions`, `--recently-active` | **NOT STARTED** | -| `describe-alarms` | — | `--alarm-names`, `--alarm-name-prefix`, `--state-value`, `--action-prefix` | **NOT STARTED** | -| `put-metric-alarm` | — | `--alarm-name`, `--namespace`, `--metric-name`, `--statistic`, `--period`, `--evaluation-periods`, `--threshold`, `--comparison-operator`, `--alarm-actions`, `--dimensions` | **NOT STARTED** | -| `delete-alarms` | — | `--alarm-names` | **NOT STARTED** | - ---- - -## Auto Scaling - -| Command | Implemented Flags | Missing Flags | Status | -|---------|-------------------|---------------|--------| -| `create-auto-scaling-group` | — | `--auto-scaling-group-name`, `--launch-template`, `--min-size`, `--max-size`, `--desired-capacity`, `--vpc-zone-identifier`, `--target-group-arns`, `--health-check-type`, `--health-check-grace-period`, `--tags` | **NOT STARTED** | -| `update-auto-scaling-group` | — | `--auto-scaling-group-name`, `--min-size`, `--max-size`, `--desired-capacity`, `--launch-template`, `--health-check-type`, `--health-check-grace-period` | **NOT STARTED** | -| `delete-auto-scaling-group` | — | `--auto-scaling-group-name`, `--force-delete` | **NOT STARTED** | -| `describe-auto-scaling-groups` | — | `--auto-scaling-group-names`, `--filters`, `--max-records` | **NOT STARTED** | -| `set-desired-capacity` | — | `--auto-scaling-group-name`, `--desired-capacity`, `--honor-cooldown` | **NOT STARTED** | -| `describe-auto-scaling-instances` | — | `--instance-ids`, `--max-records` | **NOT STARTED** | -| `put-scaling-policy` | — | `--auto-scaling-group-name`, `--policy-name`, `--policy-type`, `--target-tracking-configuration`, `--scaling-adjustment`, `--cooldown` | **NOT STARTED** | -| `delete-scaling-policy` | — | `--auto-scaling-group-name`, `--policy-name` | **NOT STARTED** | diff --git a/docs/compatibility/acm-api-coverage/README.md b/docs/compatibility/acm-api-coverage/README.md index 3b3983e45..3d0f9191b 100644 --- a/docs/compatibility/acm-api-coverage/README.md +++ b/docs/compatibility/acm-api-coverage/README.md @@ -18,7 +18,7 @@ tags: ## Overview -Spinifex implements **9 of the 15** operations (60.0%) in the ACM `2015-12-08` API model. +Spinifex implements **9 of the 15** operations (**60.0%**) in the ACM `2015-12-08` API model. ### Import and issuance diff --git a/docs/compatibility/aws-api-coverage/README.md b/docs/compatibility/aws-api-coverage/README.md index f641ebf9b..747434bb7 100644 --- a/docs/compatibility/aws-api-coverage/README.md +++ b/docs/compatibility/aws-api-coverage/README.md @@ -19,14 +19,14 @@ tags: Spinifex serves the AWS APIs below. Every page counts the operations in the pinned `aws-sdk-go v1.55.8` `api-2.json` model for its service and reports, operation by operation, whether Spinifex implements it. -| Service | API version | Implemented | Modelled | Coverage | -|---|---|---:|---:|---:| -| [ACM](/docs/acm-api-coverage) | 2015-12-08 | 9 | 15 | 60.0% | -| [EC2](/docs/ec2-api-coverage) | 2016-11-15 | 121 | 625 | 19.4% | -| [ECR](/docs/ecr-api-coverage) | 2015-09-21 | 19 | 47 | 40.4% | -| [ECS](/docs/ecs-api-coverage) | 2014-11-13 | 31 | 56 | 55.4% | -| [EKS](/docs/eks-api-coverage) | 2017-11-01 | 34 | 56 | 60.7% | -| [ELBv2](/docs/elbv2-api-coverage) | 2015-12-01 | 33 | 46 | 71.7% | -| [IAM](/docs/iam-api-coverage) | 2010-05-08 | 75 | 159 | 47.2% | -| [RDS](/docs/rds-api-coverage) | 2014-10-31 | 26 | 162 | 16.0% | -| [STS](/docs/sts-api-coverage) | 2011-06-15 | 4 | 8 | 50.0% | +| Service | Implemented | Modelled | Coverage | +|---|---:|---:|---:| +| [ACM](/docs/acm-api-coverage) | 9 | 15 | 60.0% | +| [EC2](/docs/ec2-api-coverage) | 121 | 625 | 19.4% | +| [ECR](/docs/ecr-api-coverage) | 19 | 47 | 40.4% | +| [ECS](/docs/ecs-api-coverage) | 31 | 56 | 55.4% | +| [EKS](/docs/eks-api-coverage) | 34 | 56 | 60.7% | +| [ELBv2](/docs/elbv2-api-coverage) | 33 | 46 | 71.7% | +| [IAM](/docs/iam-api-coverage) | 75 | 159 | 47.2% | +| [RDS](/docs/rds-api-coverage) | 26 | 162 | 16.0% | +| [STS](/docs/sts-api-coverage) | 4 | 8 | 50.0% | diff --git a/docs/compatibility/ec2-api-coverage/README.md b/docs/compatibility/ec2-api-coverage/README.md index 222a98dec..74bba539a 100644 --- a/docs/compatibility/ec2-api-coverage/README.md +++ b/docs/compatibility/ec2-api-coverage/README.md @@ -18,7 +18,7 @@ tags: ## Overview -Spinifex implements **121 of the 625** operations (19.4%) in the EC2 `2016-11-15` API model. +Spinifex implements **121 of the 625** operations (**19.4%**) in the EC2 `2016-11-15` API model. ### Spot instances are a mock @@ -26,630 +26,634 @@ Spot Instance Requests are a mock over the on-demand `RunInstances` path. A requ ### Operations -| Operation | Status | Notes | -|---|---|---| -| `AcceptAddressTransfer` | ❌ Not implemented | | -| `AcceptReservedInstancesExchangeQuote` | ❌ Not implemented | | -| `AcceptTransitGatewayMulticastDomainAssociations` | ❌ Not implemented | | -| `AcceptTransitGatewayPeeringAttachment` | ❌ Not implemented | | -| `AcceptTransitGatewayVpcAttachment` | ❌ Not implemented | | -| `AcceptVpcEndpointConnections` | ❌ Not implemented | | -| `AcceptVpcPeeringConnection` | ❌ Not implemented | | -| `AdvertiseByoipCidr` | ❌ Not implemented | | -| `AllocateAddress` | ✅ Implemented | | -| `AllocateHosts` | ❌ Not implemented | | -| `AllocateIpamPoolCidr` | ❌ Not implemented | | -| `ApplySecurityGroupsToClientVpnTargetNetwork` | ❌ Not implemented | | -| `AssignIpv6Addresses` | ❌ Not implemented | | -| `AssignPrivateIpAddresses` | ❌ Not implemented | | -| `AssignPrivateNatGatewayAddress` | ❌ Not implemented | | -| `AssociateAddress` | ✅ Implemented | | -| `AssociateClientVpnTargetNetwork` | ❌ Not implemented | | -| `AssociateDhcpOptions` | ❌ Not implemented | | -| `AssociateEnclaveCertificateIamRole` | ❌ Not implemented | | -| `AssociateIamInstanceProfile` | ✅ Implemented | | -| `AssociateInstanceEventWindow` | ❌ Not implemented | | -| `AssociateIpamByoasn` | ❌ Not implemented | | -| `AssociateIpamResourceDiscovery` | ❌ Not implemented | | -| `AssociateNatGatewayAddress` | ❌ Not implemented | | -| `AssociateRouteTable` | ✅ Implemented | | -| `AssociateSubnetCidrBlock` | ❌ Not implemented | | -| `AssociateTransitGatewayMulticastDomain` | ❌ Not implemented | | -| `AssociateTransitGatewayPolicyTable` | ❌ Not implemented | | -| `AssociateTransitGatewayRouteTable` | ❌ Not implemented | | -| `AssociateTrunkInterface` | ❌ Not implemented | | -| `AssociateVpcCidrBlock` | ❌ Not implemented | | -| `AttachClassicLinkVpc` | ❌ Not implemented | | -| `AttachInternetGateway` | ✅ Implemented | | -| `AttachNetworkInterface` | ✅ Implemented | | -| `AttachVerifiedAccessTrustProvider` | ❌ Not implemented | | -| `AttachVolume` | ✅ Implemented | | -| `AttachVpnGateway` | ❌ Not implemented | | -| `AuthorizeClientVpnIngress` | ❌ Not implemented | | -| `AuthorizeSecurityGroupEgress` | ✅ Implemented | | -| `AuthorizeSecurityGroupIngress` | ✅ Implemented | | -| `BundleInstance` | ❌ Not implemented | | -| `CancelBundleTask` | ❌ Not implemented | | -| `CancelCapacityReservation` | ✅ Implemented | | -| `CancelCapacityReservationFleets` | ❌ Not implemented | | -| `CancelConversionTask` | ❌ Not implemented | | -| `CancelExportTask` | ❌ Not implemented | | -| `CancelImageLaunchPermission` | ❌ Not implemented | | -| `CancelImportTask` | ❌ Not implemented | | -| `CancelReservedInstancesListing` | ❌ Not implemented | | -| `CancelSpotFleetRequests` | ❌ Not implemented | | -| `CancelSpotInstanceRequests` | ✅ Implemented | | -| `ConfirmProductInstance` | ❌ Not implemented | | -| `CopyFpgaImage` | ❌ Not implemented | | -| `CopyImage` | ✅ Implemented | | -| `CopySnapshot` | ✅ Implemented | | -| `CreateCapacityReservation` | ✅ Implemented | | -| `CreateCapacityReservationFleet` | ❌ Not implemented | | -| `CreateCarrierGateway` | ❌ Not implemented | | -| `CreateClientVpnEndpoint` | ❌ Not implemented | | -| `CreateClientVpnRoute` | ❌ Not implemented | | -| `CreateCoipCidr` | ❌ Not implemented | | -| `CreateCoipPool` | ❌ Not implemented | | -| `CreateCustomerGateway` | ❌ Not implemented | | -| `CreateDefaultSubnet` | ❌ Not implemented | | -| `CreateDefaultVpc` | ❌ Not implemented | | -| `CreateDhcpOptions` | ❌ Not implemented | | -| `CreateEgressOnlyInternetGateway` | ✅ Implemented | | -| `CreateFleet` | ❌ Not implemented | | -| `CreateFlowLogs` | ❌ Not implemented | | -| `CreateFpgaImage` | ❌ Not implemented | | -| `CreateImage` | ✅ Implemented | | -| `CreateInstanceConnectEndpoint` | ❌ Not implemented | | -| `CreateInstanceEventWindow` | ❌ Not implemented | | -| `CreateInstanceExportTask` | ❌ Not implemented | | -| `CreateInternetGateway` | ✅ Implemented | | -| `CreateIpam` | ❌ Not implemented | | -| `CreateIpamExternalResourceVerificationToken` | ❌ Not implemented | | -| `CreateIpamPool` | ❌ Not implemented | | -| `CreateIpamResourceDiscovery` | ❌ Not implemented | | -| `CreateIpamScope` | ❌ Not implemented | | -| `CreateKeyPair` | ✅ Implemented | | -| `CreateLaunchTemplate` | ✅ Implemented | | -| `CreateLaunchTemplateVersion` | ✅ Implemented | | -| `CreateLocalGatewayRoute` | ❌ Not implemented | | -| `CreateLocalGatewayRouteTable` | ❌ Not implemented | | -| `CreateLocalGatewayRouteTableVirtualInterfaceGroupAssociation` | ❌ Not implemented | | -| `CreateLocalGatewayRouteTableVpcAssociation` | ❌ Not implemented | | -| `CreateManagedPrefixList` | ❌ Not implemented | | -| `CreateNatGateway` | ✅ Implemented | | -| `CreateNetworkAcl` | ❌ Not implemented | | -| `CreateNetworkAclEntry` | ❌ Not implemented | | -| `CreateNetworkInsightsAccessScope` | ❌ Not implemented | | -| `CreateNetworkInsightsPath` | ❌ Not implemented | | -| `CreateNetworkInterface` | ✅ Implemented | | -| `CreateNetworkInterfacePermission` | ❌ Not implemented | | -| `CreatePlacementGroup` | ✅ Implemented | | -| `CreatePublicIpv4Pool` | ❌ Not implemented | | -| `CreateReplaceRootVolumeTask` | ❌ Not implemented | | -| `CreateReservedInstancesListing` | ❌ Not implemented | | -| `CreateRestoreImageTask` | ❌ Not implemented | | -| `CreateRoute` | ✅ Implemented | | -| `CreateRouteTable` | ✅ Implemented | | -| `CreateSecurityGroup` | ✅ Implemented | | -| `CreateSnapshot` | ✅ Implemented | | -| `CreateSnapshots` | ❌ Not implemented | | -| `CreateSpotDatafeedSubscription` | ❌ Not implemented | | -| `CreateStoreImageTask` | ❌ Not implemented | | -| `CreateSubnet` | ✅ Implemented | | -| `CreateSubnetCidrReservation` | ❌ Not implemented | | -| `CreateTags` | ✅ Implemented | | -| `CreateTrafficMirrorFilter` | ❌ Not implemented | | -| `CreateTrafficMirrorFilterRule` | ❌ Not implemented | | -| `CreateTrafficMirrorSession` | ❌ Not implemented | | -| `CreateTrafficMirrorTarget` | ❌ Not implemented | | -| `CreateTransitGateway` | ❌ Not implemented | | -| `CreateTransitGatewayConnect` | ❌ Not implemented | | -| `CreateTransitGatewayConnectPeer` | ❌ Not implemented | | -| `CreateTransitGatewayMulticastDomain` | ❌ Not implemented | | -| `CreateTransitGatewayPeeringAttachment` | ❌ Not implemented | | -| `CreateTransitGatewayPolicyTable` | ❌ Not implemented | | -| `CreateTransitGatewayPrefixListReference` | ❌ Not implemented | | -| `CreateTransitGatewayRoute` | ❌ Not implemented | | -| `CreateTransitGatewayRouteTable` | ❌ Not implemented | | -| `CreateTransitGatewayRouteTableAnnouncement` | ❌ Not implemented | | -| `CreateTransitGatewayVpcAttachment` | ❌ Not implemented | | -| `CreateVerifiedAccessEndpoint` | ❌ Not implemented | | -| `CreateVerifiedAccessGroup` | ❌ Not implemented | | -| `CreateVerifiedAccessInstance` | ❌ Not implemented | | -| `CreateVerifiedAccessTrustProvider` | ❌ Not implemented | | -| `CreateVolume` | ✅ Implemented | | -| `CreateVpc` | ✅ Implemented | | -| `CreateVpcEndpoint` | ❌ Not implemented | | -| `CreateVpcEndpointConnectionNotification` | ❌ Not implemented | | -| `CreateVpcEndpointServiceConfiguration` | ❌ Not implemented | | -| `CreateVpcPeeringConnection` | ❌ Not implemented | | -| `CreateVpnConnection` | ❌ Not implemented | | -| `CreateVpnConnectionRoute` | ❌ Not implemented | | -| `CreateVpnGateway` | ❌ Not implemented | | -| `DeleteCarrierGateway` | ❌ Not implemented | | -| `DeleteClientVpnEndpoint` | ❌ Not implemented | | -| `DeleteClientVpnRoute` | ❌ Not implemented | | -| `DeleteCoipCidr` | ❌ Not implemented | | -| `DeleteCoipPool` | ❌ Not implemented | | -| `DeleteCustomerGateway` | ❌ Not implemented | | -| `DeleteDhcpOptions` | ❌ Not implemented | | -| `DeleteEgressOnlyInternetGateway` | ✅ Implemented | | -| `DeleteFleets` | ❌ Not implemented | | -| `DeleteFlowLogs` | ❌ Not implemented | | -| `DeleteFpgaImage` | ❌ Not implemented | | -| `DeleteInstanceConnectEndpoint` | ❌ Not implemented | | -| `DeleteInstanceEventWindow` | ❌ Not implemented | | -| `DeleteInternetGateway` | ✅ Implemented | | -| `DeleteIpam` | ❌ Not implemented | | -| `DeleteIpamExternalResourceVerificationToken` | ❌ Not implemented | | -| `DeleteIpamPool` | ❌ Not implemented | | -| `DeleteIpamResourceDiscovery` | ❌ Not implemented | | -| `DeleteIpamScope` | ❌ Not implemented | | -| `DeleteKeyPair` | ✅ Implemented | | -| `DeleteLaunchTemplate` | ✅ Implemented | | -| `DeleteLaunchTemplateVersions` | ✅ Implemented | | -| `DeleteLocalGatewayRoute` | ❌ Not implemented | | -| `DeleteLocalGatewayRouteTable` | ❌ Not implemented | | -| `DeleteLocalGatewayRouteTableVirtualInterfaceGroupAssociation` | ❌ Not implemented | | -| `DeleteLocalGatewayRouteTableVpcAssociation` | ❌ Not implemented | | -| `DeleteManagedPrefixList` | ❌ Not implemented | | -| `DeleteNatGateway` | ✅ Implemented | | -| `DeleteNetworkAcl` | ❌ Not implemented | | -| `DeleteNetworkAclEntry` | ❌ Not implemented | | -| `DeleteNetworkInsightsAccessScope` | ❌ Not implemented | | -| `DeleteNetworkInsightsAccessScopeAnalysis` | ❌ Not implemented | | -| `DeleteNetworkInsightsAnalysis` | ❌ Not implemented | | -| `DeleteNetworkInsightsPath` | ❌ Not implemented | | -| `DeleteNetworkInterface` | ✅ Implemented | | -| `DeleteNetworkInterfacePermission` | ❌ Not implemented | | -| `DeletePlacementGroup` | ✅ Implemented | | -| `DeletePublicIpv4Pool` | ❌ Not implemented | | -| `DeleteQueuedReservedInstances` | ❌ Not implemented | | -| `DeleteRoute` | ✅ Implemented | | -| `DeleteRouteTable` | ✅ Implemented | | -| `DeleteSecurityGroup` | ✅ Implemented | | -| `DeleteSnapshot` | ✅ Implemented | | -| `DeleteSpotDatafeedSubscription` | ❌ Not implemented | | -| `DeleteSubnet` | ✅ Implemented | | -| `DeleteSubnetCidrReservation` | ❌ Not implemented | | -| `DeleteTags` | ✅ Implemented | | -| `DeleteTrafficMirrorFilter` | ❌ Not implemented | | -| `DeleteTrafficMirrorFilterRule` | ❌ Not implemented | | -| `DeleteTrafficMirrorSession` | ❌ Not implemented | | -| `DeleteTrafficMirrorTarget` | ❌ Not implemented | | -| `DeleteTransitGateway` | ❌ Not implemented | | -| `DeleteTransitGatewayConnect` | ❌ Not implemented | | -| `DeleteTransitGatewayConnectPeer` | ❌ Not implemented | | -| `DeleteTransitGatewayMulticastDomain` | ❌ Not implemented | | -| `DeleteTransitGatewayPeeringAttachment` | ❌ Not implemented | | -| `DeleteTransitGatewayPolicyTable` | ❌ Not implemented | | -| `DeleteTransitGatewayPrefixListReference` | ❌ Not implemented | | -| `DeleteTransitGatewayRoute` | ❌ Not implemented | | -| `DeleteTransitGatewayRouteTable` | ❌ Not implemented | | -| `DeleteTransitGatewayRouteTableAnnouncement` | ❌ Not implemented | | -| `DeleteTransitGatewayVpcAttachment` | ❌ Not implemented | | -| `DeleteVerifiedAccessEndpoint` | ❌ Not implemented | | -| `DeleteVerifiedAccessGroup` | ❌ Not implemented | | -| `DeleteVerifiedAccessInstance` | ❌ Not implemented | | -| `DeleteVerifiedAccessTrustProvider` | ❌ Not implemented | | -| `DeleteVolume` | ✅ Implemented | | -| `DeleteVpc` | ✅ Implemented | | -| `DeleteVpcEndpointConnectionNotifications` | ❌ Not implemented | | -| `DeleteVpcEndpointServiceConfigurations` | ❌ Not implemented | | -| `DeleteVpcEndpoints` | ❌ Not implemented | | -| `DeleteVpcPeeringConnection` | ❌ Not implemented | | -| `DeleteVpnConnection` | ❌ Not implemented | | -| `DeleteVpnConnectionRoute` | ❌ Not implemented | | -| `DeleteVpnGateway` | ❌ Not implemented | | -| `DeprovisionByoipCidr` | ❌ Not implemented | | -| `DeprovisionIpamByoasn` | ❌ Not implemented | | -| `DeprovisionIpamPoolCidr` | ❌ Not implemented | | -| `DeprovisionPublicIpv4PoolCidr` | ❌ Not implemented | | -| `DeregisterImage` | ✅ Implemented | | -| `DeregisterInstanceEventNotificationAttributes` | ❌ Not implemented | | -| `DeregisterTransitGatewayMulticastGroupMembers` | ❌ Not implemented | | -| `DeregisterTransitGatewayMulticastGroupSources` | ❌ Not implemented | | -| `DescribeAccountAttributes` | ✅ Implemented | | -| `DescribeAddressTransfers` | ❌ Not implemented | | -| `DescribeAddresses` | ✅ Implemented | | -| `DescribeAddressesAttribute` | ✅ Implemented | | -| `DescribeAggregateIdFormat` | ❌ Not implemented | | -| `DescribeAvailabilityZones` | ✅ Implemented | | -| `DescribeAwsNetworkPerformanceMetricSubscriptions` | ❌ Not implemented | | -| `DescribeBundleTasks` | ❌ Not implemented | | -| `DescribeByoipCidrs` | ❌ Not implemented | | -| `DescribeCapacityBlockOfferings` | ❌ Not implemented | | -| `DescribeCapacityReservationFleets` | ❌ Not implemented | | -| `DescribeCapacityReservations` | ✅ Implemented | | -| `DescribeCarrierGateways` | ❌ Not implemented | | -| `DescribeClassicLinkInstances` | ❌ Not implemented | | -| `DescribeClientVpnAuthorizationRules` | ❌ Not implemented | | -| `DescribeClientVpnConnections` | ❌ Not implemented | | -| `DescribeClientVpnEndpoints` | ❌ Not implemented | | -| `DescribeClientVpnRoutes` | ❌ Not implemented | | -| `DescribeClientVpnTargetNetworks` | ❌ Not implemented | | -| `DescribeCoipPools` | ❌ Not implemented | | -| `DescribeConversionTasks` | ❌ Not implemented | | -| `DescribeCustomerGateways` | ❌ Not implemented | | -| `DescribeDhcpOptions` | ❌ Not implemented | | -| `DescribeEgressOnlyInternetGateways` | ✅ Implemented | | -| `DescribeElasticGpus` | ❌ Not implemented | | -| `DescribeExportImageTasks` | ❌ Not implemented | | -| `DescribeExportTasks` | ❌ Not implemented | | -| `DescribeFastLaunchImages` | ❌ Not implemented | | -| `DescribeFastSnapshotRestores` | ❌ Not implemented | | -| `DescribeFleetHistory` | ❌ Not implemented | | -| `DescribeFleetInstances` | ❌ Not implemented | | -| `DescribeFleets` | ❌ Not implemented | | -| `DescribeFlowLogs` | ❌ Not implemented | | -| `DescribeFpgaImageAttribute` | ❌ Not implemented | | -| `DescribeFpgaImages` | ❌ Not implemented | | -| `DescribeHostReservationOfferings` | ❌ Not implemented | | -| `DescribeHostReservations` | ❌ Not implemented | | -| `DescribeHosts` | ❌ Not implemented | | -| `DescribeIamInstanceProfileAssociations` | ✅ Implemented | | -| `DescribeIdFormat` | ❌ Not implemented | | -| `DescribeIdentityIdFormat` | ❌ Not implemented | | -| `DescribeImageAttribute` | ✅ Implemented | | -| `DescribeImages` | ✅ Implemented | | -| `DescribeImportImageTasks` | ❌ Not implemented | | -| `DescribeImportSnapshotTasks` | ❌ Not implemented | | -| `DescribeInstanceAttribute` | ✅ Implemented | | -| `DescribeInstanceConnectEndpoints` | ❌ Not implemented | | -| `DescribeInstanceCreditSpecifications` | ✅ Implemented | | -| `DescribeInstanceEventNotificationAttributes` | ❌ Not implemented | | -| `DescribeInstanceEventWindows` | ❌ Not implemented | | -| `DescribeInstanceStatus` | ✅ Implemented | | -| `DescribeInstanceTopology` | ❌ Not implemented | | -| `DescribeInstanceTypeOfferings` | ❌ Not implemented | | -| `DescribeInstanceTypes` | ✅ Implemented | | -| `DescribeInstances` | ✅ Implemented | | -| `DescribeInternetGateways` | ✅ Implemented | | -| `DescribeIpamByoasn` | ❌ Not implemented | | -| `DescribeIpamExternalResourceVerificationTokens` | ❌ Not implemented | | -| `DescribeIpamPools` | ❌ Not implemented | | -| `DescribeIpamResourceDiscoveries` | ❌ Not implemented | | -| `DescribeIpamResourceDiscoveryAssociations` | ❌ Not implemented | | -| `DescribeIpamScopes` | ❌ Not implemented | | -| `DescribeIpams` | ❌ Not implemented | | -| `DescribeIpv6Pools` | ❌ Not implemented | | -| `DescribeKeyPairs` | ✅ Implemented | | -| `DescribeLaunchTemplateVersions` | ✅ Implemented | | -| `DescribeLaunchTemplates` | ✅ Implemented | | -| `DescribeLocalGatewayRouteTableVirtualInterfaceGroupAssociations` | ❌ Not implemented | | -| `DescribeLocalGatewayRouteTableVpcAssociations` | ❌ Not implemented | | -| `DescribeLocalGatewayRouteTables` | ❌ Not implemented | | -| `DescribeLocalGatewayVirtualInterfaceGroups` | ❌ Not implemented | | -| `DescribeLocalGatewayVirtualInterfaces` | ❌ Not implemented | | -| `DescribeLocalGateways` | ❌ Not implemented | | -| `DescribeLockedSnapshots` | ❌ Not implemented | | -| `DescribeMacHosts` | ❌ Not implemented | | -| `DescribeManagedPrefixLists` | ❌ Not implemented | | -| `DescribeMovingAddresses` | ❌ Not implemented | | -| `DescribeNatGateways` | ✅ Implemented | | -| `DescribeNetworkAcls` | ❌ Not implemented | | -| `DescribeNetworkInsightsAccessScopeAnalyses` | ❌ Not implemented | | -| `DescribeNetworkInsightsAccessScopes` | ❌ Not implemented | | -| `DescribeNetworkInsightsAnalyses` | ❌ Not implemented | | -| `DescribeNetworkInsightsPaths` | ❌ Not implemented | | -| `DescribeNetworkInterfaceAttribute` | ❌ Not implemented | | -| `DescribeNetworkInterfacePermissions` | ❌ Not implemented | | -| `DescribeNetworkInterfaces` | ✅ Implemented | | -| `DescribePlacementGroups` | ✅ Implemented | | -| `DescribePrefixLists` | ❌ Not implemented | | -| `DescribePrincipalIdFormat` | ❌ Not implemented | | -| `DescribePublicIpv4Pools` | ❌ Not implemented | | -| `DescribeRegions` | ✅ Implemented | | -| `DescribeReplaceRootVolumeTasks` | ❌ Not implemented | | -| `DescribeReservedInstances` | ❌ Not implemented | | -| `DescribeReservedInstancesListings` | ❌ Not implemented | | -| `DescribeReservedInstancesModifications` | ❌ Not implemented | | -| `DescribeReservedInstancesOfferings` | ❌ Not implemented | | -| `DescribeRouteTables` | ✅ Implemented | | -| `DescribeScheduledInstanceAvailability` | ❌ Not implemented | | -| `DescribeScheduledInstances` | ❌ Not implemented | | -| `DescribeSecurityGroupReferences` | ❌ Not implemented | | -| `DescribeSecurityGroupRules` | ✅ Implemented | | -| `DescribeSecurityGroups` | ✅ Implemented | | -| `DescribeSnapshotAttribute` | ❌ Not implemented | | -| `DescribeSnapshotTierStatus` | ❌ Not implemented | | -| `DescribeSnapshots` | ✅ Implemented | | -| `DescribeSpotDatafeedSubscription` | ❌ Not implemented | | -| `DescribeSpotFleetInstances` | ❌ Not implemented | | -| `DescribeSpotFleetRequestHistory` | ❌ Not implemented | | -| `DescribeSpotFleetRequests` | ❌ Not implemented | | -| `DescribeSpotInstanceRequests` | ✅ Implemented | | -| `DescribeSpotPriceHistory` | ⛔ Not applicable | On owned hardware there is no spot-to-on-demand price differential, so any figure would be invented. | -| `DescribeStaleSecurityGroups` | ❌ Not implemented | | -| `DescribeStoreImageTasks` | ❌ Not implemented | | -| `DescribeSubnets` | ✅ Implemented | | -| `DescribeTags` | ✅ Implemented | | -| `DescribeTrafficMirrorFilterRules` | ❌ Not implemented | | -| `DescribeTrafficMirrorFilters` | ❌ Not implemented | | -| `DescribeTrafficMirrorSessions` | ❌ Not implemented | | -| `DescribeTrafficMirrorTargets` | ❌ Not implemented | | -| `DescribeTransitGatewayAttachments` | ❌ Not implemented | | -| `DescribeTransitGatewayConnectPeers` | ❌ Not implemented | | -| `DescribeTransitGatewayConnects` | ❌ Not implemented | | -| `DescribeTransitGatewayMulticastDomains` | ❌ Not implemented | | -| `DescribeTransitGatewayPeeringAttachments` | ❌ Not implemented | | -| `DescribeTransitGatewayPolicyTables` | ❌ Not implemented | | -| `DescribeTransitGatewayRouteTableAnnouncements` | ❌ Not implemented | | -| `DescribeTransitGatewayRouteTables` | ❌ Not implemented | | -| `DescribeTransitGatewayVpcAttachments` | ❌ Not implemented | | -| `DescribeTransitGateways` | ❌ Not implemented | | -| `DescribeTrunkInterfaceAssociations` | ❌ Not implemented | | -| `DescribeVerifiedAccessEndpoints` | ❌ Not implemented | | -| `DescribeVerifiedAccessGroups` | ❌ Not implemented | | -| `DescribeVerifiedAccessInstanceLoggingConfigurations` | ❌ Not implemented | | -| `DescribeVerifiedAccessInstances` | ❌ Not implemented | | -| `DescribeVerifiedAccessTrustProviders` | ❌ Not implemented | | -| `DescribeVolumeAttribute` | ❌ Not implemented | | -| `DescribeVolumeStatus` | ✅ Implemented | | -| `DescribeVolumes` | ✅ Implemented | | -| `DescribeVolumesModifications` | ✅ Implemented | | -| `DescribeVpcAttribute` | ✅ Implemented | | -| `DescribeVpcClassicLink` | ❌ Not implemented | | -| `DescribeVpcClassicLinkDnsSupport` | ❌ Not implemented | | -| `DescribeVpcEndpointConnectionNotifications` | ❌ Not implemented | | -| `DescribeVpcEndpointConnections` | ❌ Not implemented | | -| `DescribeVpcEndpointServiceConfigurations` | ❌ Not implemented | | -| `DescribeVpcEndpointServicePermissions` | ❌ Not implemented | | -| `DescribeVpcEndpointServices` | ❌ Not implemented | | -| `DescribeVpcEndpoints` | ❌ Not implemented | | -| `DescribeVpcPeeringConnections` | ❌ Not implemented | | -| `DescribeVpcs` | ✅ Implemented | | -| `DescribeVpnConnections` | ❌ Not implemented | | -| `DescribeVpnGateways` | ❌ Not implemented | | -| `DetachClassicLinkVpc` | ❌ Not implemented | | -| `DetachInternetGateway` | ✅ Implemented | | -| `DetachNetworkInterface` | ✅ Implemented | | -| `DetachVerifiedAccessTrustProvider` | ❌ Not implemented | | -| `DetachVolume` | ✅ Implemented | | -| `DetachVpnGateway` | ❌ Not implemented | | -| `DisableAddressTransfer` | ❌ Not implemented | | -| `DisableAwsNetworkPerformanceMetricSubscription` | ❌ Not implemented | | -| `DisableEbsEncryptionByDefault` | ✅ Implemented | | -| `DisableFastLaunch` | ❌ Not implemented | | -| `DisableFastSnapshotRestores` | ❌ Not implemented | | -| `DisableImage` | ❌ Not implemented | | -| `DisableImageBlockPublicAccess` | ❌ Not implemented | | -| `DisableImageDeprecation` | ❌ Not implemented | | -| `DisableImageDeregistrationProtection` | ❌ Not implemented | | -| `DisableIpamOrganizationAdminAccount` | ❌ Not implemented | | -| `DisableSerialConsoleAccess` | ✅ Implemented | | -| `DisableSnapshotBlockPublicAccess` | ❌ Not implemented | | -| `DisableTransitGatewayRouteTablePropagation` | ❌ Not implemented | | -| `DisableVgwRoutePropagation` | ❌ Not implemented | | -| `DisableVpcClassicLink` | ❌ Not implemented | | -| `DisableVpcClassicLinkDnsSupport` | ❌ Not implemented | | -| `DisassociateAddress` | ✅ Implemented | | -| `DisassociateClientVpnTargetNetwork` | ❌ Not implemented | | -| `DisassociateEnclaveCertificateIamRole` | ❌ Not implemented | | -| `DisassociateIamInstanceProfile` | ✅ Implemented | | -| `DisassociateInstanceEventWindow` | ❌ Not implemented | | -| `DisassociateIpamByoasn` | ❌ Not implemented | | -| `DisassociateIpamResourceDiscovery` | ❌ Not implemented | | -| `DisassociateNatGatewayAddress` | ❌ Not implemented | | -| `DisassociateRouteTable` | ✅ Implemented | | -| `DisassociateSubnetCidrBlock` | ❌ Not implemented | | -| `DisassociateTransitGatewayMulticastDomain` | ❌ Not implemented | | -| `DisassociateTransitGatewayPolicyTable` | ❌ Not implemented | | -| `DisassociateTransitGatewayRouteTable` | ❌ Not implemented | | -| `DisassociateTrunkInterface` | ❌ Not implemented | | -| `DisassociateVpcCidrBlock` | ❌ Not implemented | | -| `EnableAddressTransfer` | ❌ Not implemented | | -| `EnableAwsNetworkPerformanceMetricSubscription` | ❌ Not implemented | | -| `EnableEbsEncryptionByDefault` | ✅ Implemented | | -| `EnableFastLaunch` | ❌ Not implemented | | -| `EnableFastSnapshotRestores` | ❌ Not implemented | | -| `EnableImage` | ❌ Not implemented | | -| `EnableImageBlockPublicAccess` | ❌ Not implemented | | -| `EnableImageDeprecation` | ❌ Not implemented | | -| `EnableImageDeregistrationProtection` | ❌ Not implemented | | -| `EnableIpamOrganizationAdminAccount` | ❌ Not implemented | | -| `EnableReachabilityAnalyzerOrganizationSharing` | ❌ Not implemented | | -| `EnableSerialConsoleAccess` | ✅ Implemented | | -| `EnableSnapshotBlockPublicAccess` | ❌ Not implemented | | -| `EnableTransitGatewayRouteTablePropagation` | ❌ Not implemented | | -| `EnableVgwRoutePropagation` | ❌ Not implemented | | -| `EnableVolumeIO` | ❌ Not implemented | | -| `EnableVpcClassicLink` | ❌ Not implemented | | -| `EnableVpcClassicLinkDnsSupport` | ❌ Not implemented | | -| `ExportClientVpnClientCertificateRevocationList` | ❌ Not implemented | | -| `ExportClientVpnClientConfiguration` | ❌ Not implemented | | -| `ExportImage` | ❌ Not implemented | | -| `ExportTransitGatewayRoutes` | ❌ Not implemented | | -| `GetAssociatedEnclaveCertificateIamRoles` | ❌ Not implemented | | -| `GetAssociatedIpv6PoolCidrs` | ❌ Not implemented | | -| `GetAwsNetworkPerformanceData` | ❌ Not implemented | | -| `GetCapacityReservationUsage` | ❌ Not implemented | | -| `GetCoipPoolUsage` | ❌ Not implemented | | -| `GetConsoleOutput` | ✅ Implemented | | -| `GetConsoleScreenshot` | ❌ Not implemented | | -| `GetDefaultCreditSpecification` | ❌ Not implemented | | -| `GetEbsDefaultKmsKeyId` | ❌ Not implemented | | -| `GetEbsEncryptionByDefault` | ✅ Implemented | | -| `GetFlowLogsIntegrationTemplate` | ❌ Not implemented | | -| `GetGroupsForCapacityReservation` | ❌ Not implemented | | -| `GetHostReservationPurchasePreview` | ❌ Not implemented | | -| `GetImageBlockPublicAccessState` | ❌ Not implemented | | -| `GetInstanceMetadataDefaults` | ❌ Not implemented | | -| `GetInstanceTpmEkPub` | ❌ Not implemented | | -| `GetInstanceTypesFromInstanceRequirements` | ❌ Not implemented | | -| `GetInstanceUefiData` | ❌ Not implemented | | -| `GetIpamAddressHistory` | ❌ Not implemented | | -| `GetIpamDiscoveredAccounts` | ❌ Not implemented | | -| `GetIpamDiscoveredPublicAddresses` | ❌ Not implemented | | -| `GetIpamDiscoveredResourceCidrs` | ❌ Not implemented | | -| `GetIpamPoolAllocations` | ❌ Not implemented | | -| `GetIpamPoolCidrs` | ❌ Not implemented | | -| `GetIpamResourceCidrs` | ❌ Not implemented | | -| `GetLaunchTemplateData` | ❌ Not implemented | | -| `GetManagedPrefixListAssociations` | ❌ Not implemented | | -| `GetManagedPrefixListEntries` | ❌ Not implemented | | -| `GetNetworkInsightsAccessScopeAnalysisFindings` | ❌ Not implemented | | -| `GetNetworkInsightsAccessScopeContent` | ❌ Not implemented | | -| `GetPasswordData` | ✅ Implemented | | -| `GetReservedInstancesExchangeQuote` | ❌ Not implemented | | -| `GetSecurityGroupsForVpc` | ❌ Not implemented | | -| `GetSerialConsoleAccessStatus` | ✅ Implemented | | -| `GetSnapshotBlockPublicAccessState` | ❌ Not implemented | | -| `GetSpotPlacementScores` | ❌ Not implemented | | -| `GetSubnetCidrReservations` | ❌ Not implemented | | -| `GetTransitGatewayAttachmentPropagations` | ❌ Not implemented | | -| `GetTransitGatewayMulticastDomainAssociations` | ❌ Not implemented | | -| `GetTransitGatewayPolicyTableAssociations` | ❌ Not implemented | | -| `GetTransitGatewayPolicyTableEntries` | ❌ Not implemented | | -| `GetTransitGatewayPrefixListReferences` | ❌ Not implemented | | -| `GetTransitGatewayRouteTableAssociations` | ❌ Not implemented | | -| `GetTransitGatewayRouteTablePropagations` | ❌ Not implemented | | -| `GetVerifiedAccessEndpointPolicy` | ❌ Not implemented | | -| `GetVerifiedAccessGroupPolicy` | ❌ Not implemented | | -| `GetVpnConnectionDeviceSampleConfiguration` | ❌ Not implemented | | -| `GetVpnConnectionDeviceTypes` | ❌ Not implemented | | -| `GetVpnTunnelReplacementStatus` | ❌ Not implemented | | -| `ImportClientVpnClientCertificateRevocationList` | ❌ Not implemented | | -| `ImportImage` | ❌ Not implemented | | -| `ImportInstance` | ❌ Not implemented | | -| `ImportKeyPair` | ✅ Implemented | | -| `ImportSnapshot` | ❌ Not implemented | | -| `ImportVolume` | ❌ Not implemented | | -| `ListImagesInRecycleBin` | ❌ Not implemented | | -| `ListSnapshotsInRecycleBin` | ❌ Not implemented | | -| `LockSnapshot` | ❌ Not implemented | | -| `ModifyAddressAttribute` | ❌ Not implemented | | -| `ModifyAvailabilityZoneGroup` | ❌ Not implemented | | -| `ModifyCapacityReservation` | ❌ Not implemented | | -| `ModifyCapacityReservationFleet` | ❌ Not implemented | | -| `ModifyClientVpnEndpoint` | ❌ Not implemented | | -| `ModifyDefaultCreditSpecification` | ❌ Not implemented | | -| `ModifyEbsDefaultKmsKeyId` | ❌ Not implemented | | -| `ModifyFleet` | ❌ Not implemented | | -| `ModifyFpgaImageAttribute` | ❌ Not implemented | | -| `ModifyHosts` | ❌ Not implemented | | -| `ModifyIdFormat` | ❌ Not implemented | | -| `ModifyIdentityIdFormat` | ❌ Not implemented | | -| `ModifyImageAttribute` | ✅ Implemented | | -| `ModifyInstanceAttribute` | ✅ Implemented | | -| `ModifyInstanceCapacityReservationAttributes` | ❌ Not implemented | | -| `ModifyInstanceCreditSpecification` | ❌ Not implemented | | -| `ModifyInstanceEventStartTime` | ❌ Not implemented | | -| `ModifyInstanceEventWindow` | ❌ Not implemented | | -| `ModifyInstanceMaintenanceOptions` | ❌ Not implemented | | -| `ModifyInstanceMetadataDefaults` | ❌ Not implemented | | -| `ModifyInstanceMetadataOptions` | ✅ Implemented | | -| `ModifyInstancePlacement` | ❌ Not implemented | | -| `ModifyIpam` | ❌ Not implemented | | -| `ModifyIpamPool` | ❌ Not implemented | | -| `ModifyIpamResourceCidr` | ❌ Not implemented | | -| `ModifyIpamResourceDiscovery` | ❌ Not implemented | | -| `ModifyIpamScope` | ❌ Not implemented | | -| `ModifyLaunchTemplate` | ✅ Implemented | | -| `ModifyLocalGatewayRoute` | ❌ Not implemented | | -| `ModifyManagedPrefixList` | ❌ Not implemented | | -| `ModifyNetworkInterfaceAttribute` | ✅ Implemented | | -| `ModifyPrivateDnsNameOptions` | ❌ Not implemented | | -| `ModifyReservedInstances` | ❌ Not implemented | | -| `ModifySecurityGroupRules` | ❌ Not implemented | | -| `ModifySnapshotAttribute` | ❌ Not implemented | | -| `ModifySnapshotTier` | ❌ Not implemented | | -| `ModifySpotFleetRequest` | ❌ Not implemented | | -| `ModifySubnetAttribute` | ✅ Implemented | | -| `ModifyTrafficMirrorFilterNetworkServices` | ❌ Not implemented | | -| `ModifyTrafficMirrorFilterRule` | ❌ Not implemented | | -| `ModifyTrafficMirrorSession` | ❌ Not implemented | | -| `ModifyTransitGateway` | ❌ Not implemented | | -| `ModifyTransitGatewayPrefixListReference` | ❌ Not implemented | | -| `ModifyTransitGatewayVpcAttachment` | ❌ Not implemented | | -| `ModifyVerifiedAccessEndpoint` | ❌ Not implemented | | -| `ModifyVerifiedAccessEndpointPolicy` | ❌ Not implemented | | -| `ModifyVerifiedAccessGroup` | ❌ Not implemented | | -| `ModifyVerifiedAccessGroupPolicy` | ❌ Not implemented | | -| `ModifyVerifiedAccessInstance` | ❌ Not implemented | | -| `ModifyVerifiedAccessInstanceLoggingConfiguration` | ❌ Not implemented | | -| `ModifyVerifiedAccessTrustProvider` | ❌ Not implemented | | -| `ModifyVolume` | ✅ Implemented | | -| `ModifyVolumeAttribute` | ❌ Not implemented | | -| `ModifyVpcAttribute` | ✅ Implemented | | -| `ModifyVpcEndpoint` | ❌ Not implemented | | -| `ModifyVpcEndpointConnectionNotification` | ❌ Not implemented | | -| `ModifyVpcEndpointServiceConfiguration` | ❌ Not implemented | | -| `ModifyVpcEndpointServicePayerResponsibility` | ❌ Not implemented | | -| `ModifyVpcEndpointServicePermissions` | ❌ Not implemented | | -| `ModifyVpcPeeringConnectionOptions` | ❌ Not implemented | | -| `ModifyVpcTenancy` | ❌ Not implemented | | -| `ModifyVpnConnection` | ❌ Not implemented | | -| `ModifyVpnConnectionOptions` | ❌ Not implemented | | -| `ModifyVpnTunnelCertificate` | ❌ Not implemented | | -| `ModifyVpnTunnelOptions` | ❌ Not implemented | | -| `MonitorInstances` | ✅ Implemented | | -| `MoveAddressToVpc` | ❌ Not implemented | | -| `MoveByoipCidrToIpam` | ❌ Not implemented | | -| `ProvisionByoipCidr` | ❌ Not implemented | | -| `ProvisionIpamByoasn` | ❌ Not implemented | | -| `ProvisionIpamPoolCidr` | ❌ Not implemented | | -| `ProvisionPublicIpv4PoolCidr` | ❌ Not implemented | | -| `PurchaseCapacityBlock` | ❌ Not implemented | | -| `PurchaseHostReservation` | ❌ Not implemented | | -| `PurchaseReservedInstancesOffering` | ❌ Not implemented | | -| `PurchaseScheduledInstances` | ❌ Not implemented | | -| `RebootInstances` | ✅ Implemented | | -| `RegisterImage` | ✅ Implemented | | -| `RegisterInstanceEventNotificationAttributes` | ❌ Not implemented | | -| `RegisterTransitGatewayMulticastGroupMembers` | ❌ Not implemented | | -| `RegisterTransitGatewayMulticastGroupSources` | ❌ Not implemented | | -| `RejectTransitGatewayMulticastDomainAssociations` | ❌ Not implemented | | -| `RejectTransitGatewayPeeringAttachment` | ❌ Not implemented | | -| `RejectTransitGatewayVpcAttachment` | ❌ Not implemented | | -| `RejectVpcEndpointConnections` | ❌ Not implemented | | -| `RejectVpcPeeringConnection` | ❌ Not implemented | | -| `ReleaseAddress` | ✅ Implemented | | -| `ReleaseHosts` | ❌ Not implemented | | -| `ReleaseIpamPoolAllocation` | ❌ Not implemented | | -| `ReplaceIamInstanceProfileAssociation` | ✅ Implemented | | -| `ReplaceNetworkAclAssociation` | ❌ Not implemented | | -| `ReplaceNetworkAclEntry` | ❌ Not implemented | | -| `ReplaceRoute` | ✅ Implemented | | -| `ReplaceRouteTableAssociation` | ✅ Implemented | | -| `ReplaceTransitGatewayRoute` | ❌ Not implemented | | -| `ReplaceVpnTunnel` | ❌ Not implemented | | -| `ReportInstanceStatus` | ❌ Not implemented | | -| `RequestSpotFleet` | ❌ Not implemented | | -| `RequestSpotInstances` | ✅ Implemented | | -| `ResetAddressAttribute` | ❌ Not implemented | | -| `ResetEbsDefaultKmsKeyId` | ❌ Not implemented | | -| `ResetFpgaImageAttribute` | ❌ Not implemented | | -| `ResetImageAttribute` | ✅ Implemented | | -| `ResetInstanceAttribute` | ❌ Not implemented | | -| `ResetNetworkInterfaceAttribute` | ❌ Not implemented | | -| `ResetSnapshotAttribute` | ❌ Not implemented | | -| `RestoreAddressToClassic` | ❌ Not implemented | | -| `RestoreImageFromRecycleBin` | ❌ Not implemented | | -| `RestoreManagedPrefixListVersion` | ❌ Not implemented | | -| `RestoreSnapshotFromRecycleBin` | ❌ Not implemented | | -| `RestoreSnapshotTier` | ❌ Not implemented | | -| `RevokeClientVpnIngress` | ❌ Not implemented | | -| `RevokeSecurityGroupEgress` | ✅ Implemented | | -| `RevokeSecurityGroupIngress` | ✅ Implemented | | -| `RunInstances` | ✅ Implemented | | -| `RunScheduledInstances` | ❌ Not implemented | | -| `SearchLocalGatewayRoutes` | ❌ Not implemented | | -| `SearchTransitGatewayMulticastGroups` | ❌ Not implemented | | -| `SearchTransitGatewayRoutes` | ❌ Not implemented | | -| `SendDiagnosticInterrupt` | ❌ Not implemented | | -| `StartInstances` | ✅ Implemented | | -| `StartNetworkInsightsAccessScopeAnalysis` | ❌ Not implemented | | -| `StartNetworkInsightsAnalysis` | ❌ Not implemented | | -| `StartVpcEndpointServicePrivateDnsVerification` | ❌ Not implemented | | -| `StopInstances` | ✅ Implemented | | -| `TerminateClientVpnConnections` | ❌ Not implemented | | -| `TerminateInstances` | ✅ Implemented | | -| `UnassignIpv6Addresses` | ❌ Not implemented | | -| `UnassignPrivateIpAddresses` | ❌ Not implemented | | -| `UnassignPrivateNatGatewayAddress` | ❌ Not implemented | | -| `UnlockSnapshot` | ❌ Not implemented | | -| `UnmonitorInstances` | ✅ Implemented | | -| `UpdateSecurityGroupRuleDescriptionsEgress` | ❌ Not implemented | | -| `UpdateSecurityGroupRuleDescriptionsIngress` | ❌ Not implemented | | -| `WithdrawByoipCidr` | ❌ Not implemented | | +| Operation | Status | +|---|---| +| `AcceptAddressTransfer` | ❌ Not implemented | +| `AcceptReservedInstancesExchangeQuote` | ❌ Not implemented | +| `AcceptTransitGatewayMulticastDomainAssociations` | ❌ Not implemented | +| `AcceptTransitGatewayPeeringAttachment` | ❌ Not implemented | +| `AcceptTransitGatewayVpcAttachment` | ❌ Not implemented | +| `AcceptVpcEndpointConnections` | ❌ Not implemented | +| `AcceptVpcPeeringConnection` | ❌ Not implemented | +| `AdvertiseByoipCidr` | ❌ Not implemented | +| `AllocateAddress` | ✅ Implemented | +| `AllocateHosts` | ❌ Not implemented | +| `AllocateIpamPoolCidr` | ❌ Not implemented | +| `ApplySecurityGroupsToClientVpnTargetNetwork` | ❌ Not implemented | +| `AssignIpv6Addresses` | ❌ Not implemented | +| `AssignPrivateIpAddresses` | ❌ Not implemented | +| `AssignPrivateNatGatewayAddress` | ❌ Not implemented | +| `AssociateAddress` | ✅ Implemented | +| `AssociateClientVpnTargetNetwork` | ❌ Not implemented | +| `AssociateDhcpOptions` | ❌ Not implemented | +| `AssociateEnclaveCertificateIamRole` | ❌ Not implemented | +| `AssociateIamInstanceProfile` | ✅ Implemented | +| `AssociateInstanceEventWindow` | ❌ Not implemented | +| `AssociateIpamByoasn` | ❌ Not implemented | +| `AssociateIpamResourceDiscovery` | ❌ Not implemented | +| `AssociateNatGatewayAddress` | ❌ Not implemented | +| `AssociateRouteTable` | ✅ Implemented | +| `AssociateSubnetCidrBlock` | ❌ Not implemented | +| `AssociateTransitGatewayMulticastDomain` | ❌ Not implemented | +| `AssociateTransitGatewayPolicyTable` | ❌ Not implemented | +| `AssociateTransitGatewayRouteTable` | ❌ Not implemented | +| `AssociateTrunkInterface` | ❌ Not implemented | +| `AssociateVpcCidrBlock` | ❌ Not implemented | +| `AttachClassicLinkVpc` | ❌ Not implemented | +| `AttachInternetGateway` | ✅ Implemented | +| `AttachNetworkInterface` | ✅ Implemented | +| `AttachVerifiedAccessTrustProvider` | ❌ Not implemented | +| `AttachVolume` | ✅ Implemented | +| `AttachVpnGateway` | ❌ Not implemented | +| `AuthorizeClientVpnIngress` | ❌ Not implemented | +| `AuthorizeSecurityGroupEgress` | ✅ Implemented | +| `AuthorizeSecurityGroupIngress` | ✅ Implemented | +| `BundleInstance` | ❌ Not implemented | +| `CancelBundleTask` | ❌ Not implemented | +| `CancelCapacityReservation` | ✅ Implemented | +| `CancelCapacityReservationFleets` | ❌ Not implemented | +| `CancelConversionTask` | ❌ Not implemented | +| `CancelExportTask` | ❌ Not implemented | +| `CancelImageLaunchPermission` | ❌ Not implemented | +| `CancelImportTask` | ❌ Not implemented | +| `CancelReservedInstancesListing` | ❌ Not implemented | +| `CancelSpotFleetRequests` | ❌ Not implemented | +| `CancelSpotInstanceRequests` | ✅ Implemented | +| `ConfirmProductInstance` | ❌ Not implemented | +| `CopyFpgaImage` | ❌ Not implemented | +| `CopyImage` | ✅ Implemented | +| `CopySnapshot` | ✅ Implemented | +| `CreateCapacityReservation` | ✅ Implemented | +| `CreateCapacityReservationFleet` | ❌ Not implemented | +| `CreateCarrierGateway` | ❌ Not implemented | +| `CreateClientVpnEndpoint` | ❌ Not implemented | +| `CreateClientVpnRoute` | ❌ Not implemented | +| `CreateCoipCidr` | ❌ Not implemented | +| `CreateCoipPool` | ❌ Not implemented | +| `CreateCustomerGateway` | ❌ Not implemented | +| `CreateDefaultSubnet` | ❌ Not implemented | +| `CreateDefaultVpc` | ❌ Not implemented | +| `CreateDhcpOptions` | ❌ Not implemented | +| `CreateEgressOnlyInternetGateway` | ✅ Implemented | +| `CreateFleet` | ❌ Not implemented | +| `CreateFlowLogs` | ❌ Not implemented | +| `CreateFpgaImage` | ❌ Not implemented | +| `CreateImage` | ✅ Implemented | +| `CreateInstanceConnectEndpoint` | ❌ Not implemented | +| `CreateInstanceEventWindow` | ❌ Not implemented | +| `CreateInstanceExportTask` | ❌ Not implemented | +| `CreateInternetGateway` | ✅ Implemented | +| `CreateIpam` | ❌ Not implemented | +| `CreateIpamExternalResourceVerificationToken` | ❌ Not implemented | +| `CreateIpamPool` | ❌ Not implemented | +| `CreateIpamResourceDiscovery` | ❌ Not implemented | +| `CreateIpamScope` | ❌ Not implemented | +| `CreateKeyPair` | ✅ Implemented | +| `CreateLaunchTemplate` | ✅ Implemented | +| `CreateLaunchTemplateVersion` | ✅ Implemented | +| `CreateLocalGatewayRoute` | ❌ Not implemented | +| `CreateLocalGatewayRouteTable` | ❌ Not implemented | +| `CreateLocalGatewayRouteTableVirtualInterfaceGroupAssociation` | ❌ Not implemented | +| `CreateLocalGatewayRouteTableVpcAssociation` | ❌ Not implemented | +| `CreateManagedPrefixList` | ❌ Not implemented | +| `CreateNatGateway` | ✅ Implemented | +| `CreateNetworkAcl` | ❌ Not implemented | +| `CreateNetworkAclEntry` | ❌ Not implemented | +| `CreateNetworkInsightsAccessScope` | ❌ Not implemented | +| `CreateNetworkInsightsPath` | ❌ Not implemented | +| `CreateNetworkInterface` | ✅ Implemented | +| `CreateNetworkInterfacePermission` | ❌ Not implemented | +| `CreatePlacementGroup` | ✅ Implemented | +| `CreatePublicIpv4Pool` | ❌ Not implemented | +| `CreateReplaceRootVolumeTask` | ❌ Not implemented | +| `CreateReservedInstancesListing` | ❌ Not implemented | +| `CreateRestoreImageTask` | ❌ Not implemented | +| `CreateRoute` | ✅ Implemented | +| `CreateRouteTable` | ✅ Implemented | +| `CreateSecurityGroup` | ✅ Implemented | +| `CreateSnapshot` | ✅ Implemented | +| `CreateSnapshots` | ❌ Not implemented | +| `CreateSpotDatafeedSubscription` | ❌ Not implemented | +| `CreateStoreImageTask` | ❌ Not implemented | +| `CreateSubnet` | ✅ Implemented | +| `CreateSubnetCidrReservation` | ❌ Not implemented | +| `CreateTags` | ✅ Implemented | +| `CreateTrafficMirrorFilter` | ❌ Not implemented | +| `CreateTrafficMirrorFilterRule` | ❌ Not implemented | +| `CreateTrafficMirrorSession` | ❌ Not implemented | +| `CreateTrafficMirrorTarget` | ❌ Not implemented | +| `CreateTransitGateway` | ❌ Not implemented | +| `CreateTransitGatewayConnect` | ❌ Not implemented | +| `CreateTransitGatewayConnectPeer` | ❌ Not implemented | +| `CreateTransitGatewayMulticastDomain` | ❌ Not implemented | +| `CreateTransitGatewayPeeringAttachment` | ❌ Not implemented | +| `CreateTransitGatewayPolicyTable` | ❌ Not implemented | +| `CreateTransitGatewayPrefixListReference` | ❌ Not implemented | +| `CreateTransitGatewayRoute` | ❌ Not implemented | +| `CreateTransitGatewayRouteTable` | ❌ Not implemented | +| `CreateTransitGatewayRouteTableAnnouncement` | ❌ Not implemented | +| `CreateTransitGatewayVpcAttachment` | ❌ Not implemented | +| `CreateVerifiedAccessEndpoint` | ❌ Not implemented | +| `CreateVerifiedAccessGroup` | ❌ Not implemented | +| `CreateVerifiedAccessInstance` | ❌ Not implemented | +| `CreateVerifiedAccessTrustProvider` | ❌ Not implemented | +| `CreateVolume` | ✅ Implemented | +| `CreateVpc` | ✅ Implemented | +| `CreateVpcEndpoint` | ❌ Not implemented | +| `CreateVpcEndpointConnectionNotification` | ❌ Not implemented | +| `CreateVpcEndpointServiceConfiguration` | ❌ Not implemented | +| `CreateVpcPeeringConnection` | ❌ Not implemented | +| `CreateVpnConnection` | ❌ Not implemented | +| `CreateVpnConnectionRoute` | ❌ Not implemented | +| `CreateVpnGateway` | ❌ Not implemented | +| `DeleteCarrierGateway` | ❌ Not implemented | +| `DeleteClientVpnEndpoint` | ❌ Not implemented | +| `DeleteClientVpnRoute` | ❌ Not implemented | +| `DeleteCoipCidr` | ❌ Not implemented | +| `DeleteCoipPool` | ❌ Not implemented | +| `DeleteCustomerGateway` | ❌ Not implemented | +| `DeleteDhcpOptions` | ❌ Not implemented | +| `DeleteEgressOnlyInternetGateway` | ✅ Implemented | +| `DeleteFleets` | ❌ Not implemented | +| `DeleteFlowLogs` | ❌ Not implemented | +| `DeleteFpgaImage` | ❌ Not implemented | +| `DeleteInstanceConnectEndpoint` | ❌ Not implemented | +| `DeleteInstanceEventWindow` | ❌ Not implemented | +| `DeleteInternetGateway` | ✅ Implemented | +| `DeleteIpam` | ❌ Not implemented | +| `DeleteIpamExternalResourceVerificationToken` | ❌ Not implemented | +| `DeleteIpamPool` | ❌ Not implemented | +| `DeleteIpamResourceDiscovery` | ❌ Not implemented | +| `DeleteIpamScope` | ❌ Not implemented | +| `DeleteKeyPair` | ✅ Implemented | +| `DeleteLaunchTemplate` | ✅ Implemented | +| `DeleteLaunchTemplateVersions` | ✅ Implemented | +| `DeleteLocalGatewayRoute` | ❌ Not implemented | +| `DeleteLocalGatewayRouteTable` | ❌ Not implemented | +| `DeleteLocalGatewayRouteTableVirtualInterfaceGroupAssociation` | ❌ Not implemented | +| `DeleteLocalGatewayRouteTableVpcAssociation` | ❌ Not implemented | +| `DeleteManagedPrefixList` | ❌ Not implemented | +| `DeleteNatGateway` | ✅ Implemented | +| `DeleteNetworkAcl` | ❌ Not implemented | +| `DeleteNetworkAclEntry` | ❌ Not implemented | +| `DeleteNetworkInsightsAccessScope` | ❌ Not implemented | +| `DeleteNetworkInsightsAccessScopeAnalysis` | ❌ Not implemented | +| `DeleteNetworkInsightsAnalysis` | ❌ Not implemented | +| `DeleteNetworkInsightsPath` | ❌ Not implemented | +| `DeleteNetworkInterface` | ✅ Implemented | +| `DeleteNetworkInterfacePermission` | ❌ Not implemented | +| `DeletePlacementGroup` | ✅ Implemented | +| `DeletePublicIpv4Pool` | ❌ Not implemented | +| `DeleteQueuedReservedInstances` | ❌ Not implemented | +| `DeleteRoute` | ✅ Implemented | +| `DeleteRouteTable` | ✅ Implemented | +| `DeleteSecurityGroup` | ✅ Implemented | +| `DeleteSnapshot` | ✅ Implemented | +| `DeleteSpotDatafeedSubscription` | ❌ Not implemented | +| `DeleteSubnet` | ✅ Implemented | +| `DeleteSubnetCidrReservation` | ❌ Not implemented | +| `DeleteTags` | ✅ Implemented | +| `DeleteTrafficMirrorFilter` | ❌ Not implemented | +| `DeleteTrafficMirrorFilterRule` | ❌ Not implemented | +| `DeleteTrafficMirrorSession` | ❌ Not implemented | +| `DeleteTrafficMirrorTarget` | ❌ Not implemented | +| `DeleteTransitGateway` | ❌ Not implemented | +| `DeleteTransitGatewayConnect` | ❌ Not implemented | +| `DeleteTransitGatewayConnectPeer` | ❌ Not implemented | +| `DeleteTransitGatewayMulticastDomain` | ❌ Not implemented | +| `DeleteTransitGatewayPeeringAttachment` | ❌ Not implemented | +| `DeleteTransitGatewayPolicyTable` | ❌ Not implemented | +| `DeleteTransitGatewayPrefixListReference` | ❌ Not implemented | +| `DeleteTransitGatewayRoute` | ❌ Not implemented | +| `DeleteTransitGatewayRouteTable` | ❌ Not implemented | +| `DeleteTransitGatewayRouteTableAnnouncement` | ❌ Not implemented | +| `DeleteTransitGatewayVpcAttachment` | ❌ Not implemented | +| `DeleteVerifiedAccessEndpoint` | ❌ Not implemented | +| `DeleteVerifiedAccessGroup` | ❌ Not implemented | +| `DeleteVerifiedAccessInstance` | ❌ Not implemented | +| `DeleteVerifiedAccessTrustProvider` | ❌ Not implemented | +| `DeleteVolume` | ✅ Implemented | +| `DeleteVpc` | ✅ Implemented | +| `DeleteVpcEndpointConnectionNotifications` | ❌ Not implemented | +| `DeleteVpcEndpointServiceConfigurations` | ❌ Not implemented | +| `DeleteVpcEndpoints` | ❌ Not implemented | +| `DeleteVpcPeeringConnection` | ❌ Not implemented | +| `DeleteVpnConnection` | ❌ Not implemented | +| `DeleteVpnConnectionRoute` | ❌ Not implemented | +| `DeleteVpnGateway` | ❌ Not implemented | +| `DeprovisionByoipCidr` | ❌ Not implemented | +| `DeprovisionIpamByoasn` | ❌ Not implemented | +| `DeprovisionIpamPoolCidr` | ❌ Not implemented | +| `DeprovisionPublicIpv4PoolCidr` | ❌ Not implemented | +| `DeregisterImage` | ✅ Implemented | +| `DeregisterInstanceEventNotificationAttributes` | ❌ Not implemented | +| `DeregisterTransitGatewayMulticastGroupMembers` | ❌ Not implemented | +| `DeregisterTransitGatewayMulticastGroupSources` | ❌ Not implemented | +| `DescribeAccountAttributes` | ✅ Implemented | +| `DescribeAddressTransfers` | ❌ Not implemented | +| `DescribeAddresses` | ✅ Implemented | +| `DescribeAddressesAttribute` | ✅ Implemented | +| `DescribeAggregateIdFormat` | ❌ Not implemented | +| `DescribeAvailabilityZones` | ✅ Implemented | +| `DescribeAwsNetworkPerformanceMetricSubscriptions` | ❌ Not implemented | +| `DescribeBundleTasks` | ❌ Not implemented | +| `DescribeByoipCidrs` | ❌ Not implemented | +| `DescribeCapacityBlockOfferings` | ❌ Not implemented | +| `DescribeCapacityReservationFleets` | ❌ Not implemented | +| `DescribeCapacityReservations` | ✅ Implemented | +| `DescribeCarrierGateways` | ❌ Not implemented | +| `DescribeClassicLinkInstances` | ❌ Not implemented | +| `DescribeClientVpnAuthorizationRules` | ❌ Not implemented | +| `DescribeClientVpnConnections` | ❌ Not implemented | +| `DescribeClientVpnEndpoints` | ❌ Not implemented | +| `DescribeClientVpnRoutes` | ❌ Not implemented | +| `DescribeClientVpnTargetNetworks` | ❌ Not implemented | +| `DescribeCoipPools` | ❌ Not implemented | +| `DescribeConversionTasks` | ❌ Not implemented | +| `DescribeCustomerGateways` | ❌ Not implemented | +| `DescribeDhcpOptions` | ❌ Not implemented | +| `DescribeEgressOnlyInternetGateways` | ✅ Implemented | +| `DescribeElasticGpus` | ❌ Not implemented | +| `DescribeExportImageTasks` | ❌ Not implemented | +| `DescribeExportTasks` | ❌ Not implemented | +| `DescribeFastLaunchImages` | ❌ Not implemented | +| `DescribeFastSnapshotRestores` | ❌ Not implemented | +| `DescribeFleetHistory` | ❌ Not implemented | +| `DescribeFleetInstances` | ❌ Not implemented | +| `DescribeFleets` | ❌ Not implemented | +| `DescribeFlowLogs` | ❌ Not implemented | +| `DescribeFpgaImageAttribute` | ❌ Not implemented | +| `DescribeFpgaImages` | ❌ Not implemented | +| `DescribeHostReservationOfferings` | ❌ Not implemented | +| `DescribeHostReservations` | ❌ Not implemented | +| `DescribeHosts` | ❌ Not implemented | +| `DescribeIamInstanceProfileAssociations` | ✅ Implemented | +| `DescribeIdFormat` | ❌ Not implemented | +| `DescribeIdentityIdFormat` | ❌ Not implemented | +| `DescribeImageAttribute` | ✅ Implemented | +| `DescribeImages` | ✅ Implemented | +| `DescribeImportImageTasks` | ❌ Not implemented | +| `DescribeImportSnapshotTasks` | ❌ Not implemented | +| `DescribeInstanceAttribute` | ✅ Implemented | +| `DescribeInstanceConnectEndpoints` | ❌ Not implemented | +| `DescribeInstanceCreditSpecifications` | ✅ Implemented | +| `DescribeInstanceEventNotificationAttributes` | ❌ Not implemented | +| `DescribeInstanceEventWindows` | ❌ Not implemented | +| `DescribeInstanceStatus` | ✅ Implemented | +| `DescribeInstanceTopology` | ❌ Not implemented | +| `DescribeInstanceTypeOfferings` | ❌ Not implemented | +| `DescribeInstanceTypes` | ✅ Implemented | +| `DescribeInstances` | ✅ Implemented | +| `DescribeInternetGateways` | ✅ Implemented | +| `DescribeIpamByoasn` | ❌ Not implemented | +| `DescribeIpamExternalResourceVerificationTokens` | ❌ Not implemented | +| `DescribeIpamPools` | ❌ Not implemented | +| `DescribeIpamResourceDiscoveries` | ❌ Not implemented | +| `DescribeIpamResourceDiscoveryAssociations` | ❌ Not implemented | +| `DescribeIpamScopes` | ❌ Not implemented | +| `DescribeIpams` | ❌ Not implemented | +| `DescribeIpv6Pools` | ❌ Not implemented | +| `DescribeKeyPairs` | ✅ Implemented | +| `DescribeLaunchTemplateVersions` | ✅ Implemented | +| `DescribeLaunchTemplates` | ✅ Implemented | +| `DescribeLocalGatewayRouteTableVirtualInterfaceGroupAssociations` | ❌ Not implemented | +| `DescribeLocalGatewayRouteTableVpcAssociations` | ❌ Not implemented | +| `DescribeLocalGatewayRouteTables` | ❌ Not implemented | +| `DescribeLocalGatewayVirtualInterfaceGroups` | ❌ Not implemented | +| `DescribeLocalGatewayVirtualInterfaces` | ❌ Not implemented | +| `DescribeLocalGateways` | ❌ Not implemented | +| `DescribeLockedSnapshots` | ❌ Not implemented | +| `DescribeMacHosts` | ❌ Not implemented | +| `DescribeManagedPrefixLists` | ❌ Not implemented | +| `DescribeMovingAddresses` | ❌ Not implemented | +| `DescribeNatGateways` | ✅ Implemented | +| `DescribeNetworkAcls` | ❌ Not implemented | +| `DescribeNetworkInsightsAccessScopeAnalyses` | ❌ Not implemented | +| `DescribeNetworkInsightsAccessScopes` | ❌ Not implemented | +| `DescribeNetworkInsightsAnalyses` | ❌ Not implemented | +| `DescribeNetworkInsightsPaths` | ❌ Not implemented | +| `DescribeNetworkInterfaceAttribute` | ❌ Not implemented | +| `DescribeNetworkInterfacePermissions` | ❌ Not implemented | +| `DescribeNetworkInterfaces` | ✅ Implemented | +| `DescribePlacementGroups` | ✅ Implemented | +| `DescribePrefixLists` | ❌ Not implemented | +| `DescribePrincipalIdFormat` | ❌ Not implemented | +| `DescribePublicIpv4Pools` | ❌ Not implemented | +| `DescribeRegions` | ✅ Implemented | +| `DescribeReplaceRootVolumeTasks` | ❌ Not implemented | +| `DescribeReservedInstances` | ❌ Not implemented | +| `DescribeReservedInstancesListings` | ❌ Not implemented | +| `DescribeReservedInstancesModifications` | ❌ Not implemented | +| `DescribeReservedInstancesOfferings` | ❌ Not implemented | +| `DescribeRouteTables` | ✅ Implemented | +| `DescribeScheduledInstanceAvailability` | ❌ Not implemented | +| `DescribeScheduledInstances` | ❌ Not implemented | +| `DescribeSecurityGroupReferences` | ❌ Not implemented | +| `DescribeSecurityGroupRules` | ✅ Implemented | +| `DescribeSecurityGroups` | ✅ Implemented | +| `DescribeSnapshotAttribute` | ❌ Not implemented | +| `DescribeSnapshotTierStatus` | ❌ Not implemented | +| `DescribeSnapshots` | ✅ Implemented | +| `DescribeSpotDatafeedSubscription` | ❌ Not implemented | +| `DescribeSpotFleetInstances` | ❌ Not implemented | +| `DescribeSpotFleetRequestHistory` | ❌ Not implemented | +| `DescribeSpotFleetRequests` | ❌ Not implemented | +| `DescribeSpotInstanceRequests` | ✅ Implemented | +| `DescribeSpotPriceHistory` | ⛔ Not applicable [1](#notes) | +| `DescribeStaleSecurityGroups` | ❌ Not implemented | +| `DescribeStoreImageTasks` | ❌ Not implemented | +| `DescribeSubnets` | ✅ Implemented | +| `DescribeTags` | ✅ Implemented | +| `DescribeTrafficMirrorFilterRules` | ❌ Not implemented | +| `DescribeTrafficMirrorFilters` | ❌ Not implemented | +| `DescribeTrafficMirrorSessions` | ❌ Not implemented | +| `DescribeTrafficMirrorTargets` | ❌ Not implemented | +| `DescribeTransitGatewayAttachments` | ❌ Not implemented | +| `DescribeTransitGatewayConnectPeers` | ❌ Not implemented | +| `DescribeTransitGatewayConnects` | ❌ Not implemented | +| `DescribeTransitGatewayMulticastDomains` | ❌ Not implemented | +| `DescribeTransitGatewayPeeringAttachments` | ❌ Not implemented | +| `DescribeTransitGatewayPolicyTables` | ❌ Not implemented | +| `DescribeTransitGatewayRouteTableAnnouncements` | ❌ Not implemented | +| `DescribeTransitGatewayRouteTables` | ❌ Not implemented | +| `DescribeTransitGatewayVpcAttachments` | ❌ Not implemented | +| `DescribeTransitGateways` | ❌ Not implemented | +| `DescribeTrunkInterfaceAssociations` | ❌ Not implemented | +| `DescribeVerifiedAccessEndpoints` | ❌ Not implemented | +| `DescribeVerifiedAccessGroups` | ❌ Not implemented | +| `DescribeVerifiedAccessInstanceLoggingConfigurations` | ❌ Not implemented | +| `DescribeVerifiedAccessInstances` | ❌ Not implemented | +| `DescribeVerifiedAccessTrustProviders` | ❌ Not implemented | +| `DescribeVolumeAttribute` | ❌ Not implemented | +| `DescribeVolumeStatus` | ✅ Implemented | +| `DescribeVolumes` | ✅ Implemented | +| `DescribeVolumesModifications` | ✅ Implemented | +| `DescribeVpcAttribute` | ✅ Implemented | +| `DescribeVpcClassicLink` | ❌ Not implemented | +| `DescribeVpcClassicLinkDnsSupport` | ❌ Not implemented | +| `DescribeVpcEndpointConnectionNotifications` | ❌ Not implemented | +| `DescribeVpcEndpointConnections` | ❌ Not implemented | +| `DescribeVpcEndpointServiceConfigurations` | ❌ Not implemented | +| `DescribeVpcEndpointServicePermissions` | ❌ Not implemented | +| `DescribeVpcEndpointServices` | ❌ Not implemented | +| `DescribeVpcEndpoints` | ❌ Not implemented | +| `DescribeVpcPeeringConnections` | ❌ Not implemented | +| `DescribeVpcs` | ✅ Implemented | +| `DescribeVpnConnections` | ❌ Not implemented | +| `DescribeVpnGateways` | ❌ Not implemented | +| `DetachClassicLinkVpc` | ❌ Not implemented | +| `DetachInternetGateway` | ✅ Implemented | +| `DetachNetworkInterface` | ✅ Implemented | +| `DetachVerifiedAccessTrustProvider` | ❌ Not implemented | +| `DetachVolume` | ✅ Implemented | +| `DetachVpnGateway` | ❌ Not implemented | +| `DisableAddressTransfer` | ❌ Not implemented | +| `DisableAwsNetworkPerformanceMetricSubscription` | ❌ Not implemented | +| `DisableEbsEncryptionByDefault` | ✅ Implemented | +| `DisableFastLaunch` | ❌ Not implemented | +| `DisableFastSnapshotRestores` | ❌ Not implemented | +| `DisableImage` | ❌ Not implemented | +| `DisableImageBlockPublicAccess` | ❌ Not implemented | +| `DisableImageDeprecation` | ❌ Not implemented | +| `DisableImageDeregistrationProtection` | ❌ Not implemented | +| `DisableIpamOrganizationAdminAccount` | ❌ Not implemented | +| `DisableSerialConsoleAccess` | ✅ Implemented | +| `DisableSnapshotBlockPublicAccess` | ❌ Not implemented | +| `DisableTransitGatewayRouteTablePropagation` | ❌ Not implemented | +| `DisableVgwRoutePropagation` | ❌ Not implemented | +| `DisableVpcClassicLink` | ❌ Not implemented | +| `DisableVpcClassicLinkDnsSupport` | ❌ Not implemented | +| `DisassociateAddress` | ✅ Implemented | +| `DisassociateClientVpnTargetNetwork` | ❌ Not implemented | +| `DisassociateEnclaveCertificateIamRole` | ❌ Not implemented | +| `DisassociateIamInstanceProfile` | ✅ Implemented | +| `DisassociateInstanceEventWindow` | ❌ Not implemented | +| `DisassociateIpamByoasn` | ❌ Not implemented | +| `DisassociateIpamResourceDiscovery` | ❌ Not implemented | +| `DisassociateNatGatewayAddress` | ❌ Not implemented | +| `DisassociateRouteTable` | ✅ Implemented | +| `DisassociateSubnetCidrBlock` | ❌ Not implemented | +| `DisassociateTransitGatewayMulticastDomain` | ❌ Not implemented | +| `DisassociateTransitGatewayPolicyTable` | ❌ Not implemented | +| `DisassociateTransitGatewayRouteTable` | ❌ Not implemented | +| `DisassociateTrunkInterface` | ❌ Not implemented | +| `DisassociateVpcCidrBlock` | ❌ Not implemented | +| `EnableAddressTransfer` | ❌ Not implemented | +| `EnableAwsNetworkPerformanceMetricSubscription` | ❌ Not implemented | +| `EnableEbsEncryptionByDefault` | ✅ Implemented | +| `EnableFastLaunch` | ❌ Not implemented | +| `EnableFastSnapshotRestores` | ❌ Not implemented | +| `EnableImage` | ❌ Not implemented | +| `EnableImageBlockPublicAccess` | ❌ Not implemented | +| `EnableImageDeprecation` | ❌ Not implemented | +| `EnableImageDeregistrationProtection` | ❌ Not implemented | +| `EnableIpamOrganizationAdminAccount` | ❌ Not implemented | +| `EnableReachabilityAnalyzerOrganizationSharing` | ❌ Not implemented | +| `EnableSerialConsoleAccess` | ✅ Implemented | +| `EnableSnapshotBlockPublicAccess` | ❌ Not implemented | +| `EnableTransitGatewayRouteTablePropagation` | ❌ Not implemented | +| `EnableVgwRoutePropagation` | ❌ Not implemented | +| `EnableVolumeIO` | ❌ Not implemented | +| `EnableVpcClassicLink` | ❌ Not implemented | +| `EnableVpcClassicLinkDnsSupport` | ❌ Not implemented | +| `ExportClientVpnClientCertificateRevocationList` | ❌ Not implemented | +| `ExportClientVpnClientConfiguration` | ❌ Not implemented | +| `ExportImage` | ❌ Not implemented | +| `ExportTransitGatewayRoutes` | ❌ Not implemented | +| `GetAssociatedEnclaveCertificateIamRoles` | ❌ Not implemented | +| `GetAssociatedIpv6PoolCidrs` | ❌ Not implemented | +| `GetAwsNetworkPerformanceData` | ❌ Not implemented | +| `GetCapacityReservationUsage` | ❌ Not implemented | +| `GetCoipPoolUsage` | ❌ Not implemented | +| `GetConsoleOutput` | ✅ Implemented | +| `GetConsoleScreenshot` | ❌ Not implemented | +| `GetDefaultCreditSpecification` | ❌ Not implemented | +| `GetEbsDefaultKmsKeyId` | ❌ Not implemented | +| `GetEbsEncryptionByDefault` | ✅ Implemented | +| `GetFlowLogsIntegrationTemplate` | ❌ Not implemented | +| `GetGroupsForCapacityReservation` | ❌ Not implemented | +| `GetHostReservationPurchasePreview` | ❌ Not implemented | +| `GetImageBlockPublicAccessState` | ❌ Not implemented | +| `GetInstanceMetadataDefaults` | ❌ Not implemented | +| `GetInstanceTpmEkPub` | ❌ Not implemented | +| `GetInstanceTypesFromInstanceRequirements` | ❌ Not implemented | +| `GetInstanceUefiData` | ❌ Not implemented | +| `GetIpamAddressHistory` | ❌ Not implemented | +| `GetIpamDiscoveredAccounts` | ❌ Not implemented | +| `GetIpamDiscoveredPublicAddresses` | ❌ Not implemented | +| `GetIpamDiscoveredResourceCidrs` | ❌ Not implemented | +| `GetIpamPoolAllocations` | ❌ Not implemented | +| `GetIpamPoolCidrs` | ❌ Not implemented | +| `GetIpamResourceCidrs` | ❌ Not implemented | +| `GetLaunchTemplateData` | ❌ Not implemented | +| `GetManagedPrefixListAssociations` | ❌ Not implemented | +| `GetManagedPrefixListEntries` | ❌ Not implemented | +| `GetNetworkInsightsAccessScopeAnalysisFindings` | ❌ Not implemented | +| `GetNetworkInsightsAccessScopeContent` | ❌ Not implemented | +| `GetPasswordData` | ✅ Implemented | +| `GetReservedInstancesExchangeQuote` | ❌ Not implemented | +| `GetSecurityGroupsForVpc` | ❌ Not implemented | +| `GetSerialConsoleAccessStatus` | ✅ Implemented | +| `GetSnapshotBlockPublicAccessState` | ❌ Not implemented | +| `GetSpotPlacementScores` | ❌ Not implemented | +| `GetSubnetCidrReservations` | ❌ Not implemented | +| `GetTransitGatewayAttachmentPropagations` | ❌ Not implemented | +| `GetTransitGatewayMulticastDomainAssociations` | ❌ Not implemented | +| `GetTransitGatewayPolicyTableAssociations` | ❌ Not implemented | +| `GetTransitGatewayPolicyTableEntries` | ❌ Not implemented | +| `GetTransitGatewayPrefixListReferences` | ❌ Not implemented | +| `GetTransitGatewayRouteTableAssociations` | ❌ Not implemented | +| `GetTransitGatewayRouteTablePropagations` | ❌ Not implemented | +| `GetVerifiedAccessEndpointPolicy` | ❌ Not implemented | +| `GetVerifiedAccessGroupPolicy` | ❌ Not implemented | +| `GetVpnConnectionDeviceSampleConfiguration` | ❌ Not implemented | +| `GetVpnConnectionDeviceTypes` | ❌ Not implemented | +| `GetVpnTunnelReplacementStatus` | ❌ Not implemented | +| `ImportClientVpnClientCertificateRevocationList` | ❌ Not implemented | +| `ImportImage` | ❌ Not implemented | +| `ImportInstance` | ❌ Not implemented | +| `ImportKeyPair` | ✅ Implemented | +| `ImportSnapshot` | ❌ Not implemented | +| `ImportVolume` | ❌ Not implemented | +| `ListImagesInRecycleBin` | ❌ Not implemented | +| `ListSnapshotsInRecycleBin` | ❌ Not implemented | +| `LockSnapshot` | ❌ Not implemented | +| `ModifyAddressAttribute` | ❌ Not implemented | +| `ModifyAvailabilityZoneGroup` | ❌ Not implemented | +| `ModifyCapacityReservation` | ❌ Not implemented | +| `ModifyCapacityReservationFleet` | ❌ Not implemented | +| `ModifyClientVpnEndpoint` | ❌ Not implemented | +| `ModifyDefaultCreditSpecification` | ❌ Not implemented | +| `ModifyEbsDefaultKmsKeyId` | ❌ Not implemented | +| `ModifyFleet` | ❌ Not implemented | +| `ModifyFpgaImageAttribute` | ❌ Not implemented | +| `ModifyHosts` | ❌ Not implemented | +| `ModifyIdFormat` | ❌ Not implemented | +| `ModifyIdentityIdFormat` | ❌ Not implemented | +| `ModifyImageAttribute` | ✅ Implemented | +| `ModifyInstanceAttribute` | ✅ Implemented | +| `ModifyInstanceCapacityReservationAttributes` | ❌ Not implemented | +| `ModifyInstanceCreditSpecification` | ❌ Not implemented | +| `ModifyInstanceEventStartTime` | ❌ Not implemented | +| `ModifyInstanceEventWindow` | ❌ Not implemented | +| `ModifyInstanceMaintenanceOptions` | ❌ Not implemented | +| `ModifyInstanceMetadataDefaults` | ❌ Not implemented | +| `ModifyInstanceMetadataOptions` | ✅ Implemented | +| `ModifyInstancePlacement` | ❌ Not implemented | +| `ModifyIpam` | ❌ Not implemented | +| `ModifyIpamPool` | ❌ Not implemented | +| `ModifyIpamResourceCidr` | ❌ Not implemented | +| `ModifyIpamResourceDiscovery` | ❌ Not implemented | +| `ModifyIpamScope` | ❌ Not implemented | +| `ModifyLaunchTemplate` | ✅ Implemented | +| `ModifyLocalGatewayRoute` | ❌ Not implemented | +| `ModifyManagedPrefixList` | ❌ Not implemented | +| `ModifyNetworkInterfaceAttribute` | ✅ Implemented | +| `ModifyPrivateDnsNameOptions` | ❌ Not implemented | +| `ModifyReservedInstances` | ❌ Not implemented | +| `ModifySecurityGroupRules` | ❌ Not implemented | +| `ModifySnapshotAttribute` | ❌ Not implemented | +| `ModifySnapshotTier` | ❌ Not implemented | +| `ModifySpotFleetRequest` | ❌ Not implemented | +| `ModifySubnetAttribute` | ✅ Implemented | +| `ModifyTrafficMirrorFilterNetworkServices` | ❌ Not implemented | +| `ModifyTrafficMirrorFilterRule` | ❌ Not implemented | +| `ModifyTrafficMirrorSession` | ❌ Not implemented | +| `ModifyTransitGateway` | ❌ Not implemented | +| `ModifyTransitGatewayPrefixListReference` | ❌ Not implemented | +| `ModifyTransitGatewayVpcAttachment` | ❌ Not implemented | +| `ModifyVerifiedAccessEndpoint` | ❌ Not implemented | +| `ModifyVerifiedAccessEndpointPolicy` | ❌ Not implemented | +| `ModifyVerifiedAccessGroup` | ❌ Not implemented | +| `ModifyVerifiedAccessGroupPolicy` | ❌ Not implemented | +| `ModifyVerifiedAccessInstance` | ❌ Not implemented | +| `ModifyVerifiedAccessInstanceLoggingConfiguration` | ❌ Not implemented | +| `ModifyVerifiedAccessTrustProvider` | ❌ Not implemented | +| `ModifyVolume` | ✅ Implemented | +| `ModifyVolumeAttribute` | ❌ Not implemented | +| `ModifyVpcAttribute` | ✅ Implemented | +| `ModifyVpcEndpoint` | ❌ Not implemented | +| `ModifyVpcEndpointConnectionNotification` | ❌ Not implemented | +| `ModifyVpcEndpointServiceConfiguration` | ❌ Not implemented | +| `ModifyVpcEndpointServicePayerResponsibility` | ❌ Not implemented | +| `ModifyVpcEndpointServicePermissions` | ❌ Not implemented | +| `ModifyVpcPeeringConnectionOptions` | ❌ Not implemented | +| `ModifyVpcTenancy` | ❌ Not implemented | +| `ModifyVpnConnection` | ❌ Not implemented | +| `ModifyVpnConnectionOptions` | ❌ Not implemented | +| `ModifyVpnTunnelCertificate` | ❌ Not implemented | +| `ModifyVpnTunnelOptions` | ❌ Not implemented | +| `MonitorInstances` | ✅ Implemented | +| `MoveAddressToVpc` | ❌ Not implemented | +| `MoveByoipCidrToIpam` | ❌ Not implemented | +| `ProvisionByoipCidr` | ❌ Not implemented | +| `ProvisionIpamByoasn` | ❌ Not implemented | +| `ProvisionIpamPoolCidr` | ❌ Not implemented | +| `ProvisionPublicIpv4PoolCidr` | ❌ Not implemented | +| `PurchaseCapacityBlock` | ❌ Not implemented | +| `PurchaseHostReservation` | ❌ Not implemented | +| `PurchaseReservedInstancesOffering` | ❌ Not implemented | +| `PurchaseScheduledInstances` | ❌ Not implemented | +| `RebootInstances` | ✅ Implemented | +| `RegisterImage` | ✅ Implemented | +| `RegisterInstanceEventNotificationAttributes` | ❌ Not implemented | +| `RegisterTransitGatewayMulticastGroupMembers` | ❌ Not implemented | +| `RegisterTransitGatewayMulticastGroupSources` | ❌ Not implemented | +| `RejectTransitGatewayMulticastDomainAssociations` | ❌ Not implemented | +| `RejectTransitGatewayPeeringAttachment` | ❌ Not implemented | +| `RejectTransitGatewayVpcAttachment` | ❌ Not implemented | +| `RejectVpcEndpointConnections` | ❌ Not implemented | +| `RejectVpcPeeringConnection` | ❌ Not implemented | +| `ReleaseAddress` | ✅ Implemented | +| `ReleaseHosts` | ❌ Not implemented | +| `ReleaseIpamPoolAllocation` | ❌ Not implemented | +| `ReplaceIamInstanceProfileAssociation` | ✅ Implemented | +| `ReplaceNetworkAclAssociation` | ❌ Not implemented | +| `ReplaceNetworkAclEntry` | ❌ Not implemented | +| `ReplaceRoute` | ✅ Implemented | +| `ReplaceRouteTableAssociation` | ✅ Implemented | +| `ReplaceTransitGatewayRoute` | ❌ Not implemented | +| `ReplaceVpnTunnel` | ❌ Not implemented | +| `ReportInstanceStatus` | ❌ Not implemented | +| `RequestSpotFleet` | ❌ Not implemented | +| `RequestSpotInstances` | ✅ Implemented | +| `ResetAddressAttribute` | ❌ Not implemented | +| `ResetEbsDefaultKmsKeyId` | ❌ Not implemented | +| `ResetFpgaImageAttribute` | ❌ Not implemented | +| `ResetImageAttribute` | ✅ Implemented | +| `ResetInstanceAttribute` | ❌ Not implemented | +| `ResetNetworkInterfaceAttribute` | ❌ Not implemented | +| `ResetSnapshotAttribute` | ❌ Not implemented | +| `RestoreAddressToClassic` | ❌ Not implemented | +| `RestoreImageFromRecycleBin` | ❌ Not implemented | +| `RestoreManagedPrefixListVersion` | ❌ Not implemented | +| `RestoreSnapshotFromRecycleBin` | ❌ Not implemented | +| `RestoreSnapshotTier` | ❌ Not implemented | +| `RevokeClientVpnIngress` | ❌ Not implemented | +| `RevokeSecurityGroupEgress` | ✅ Implemented | +| `RevokeSecurityGroupIngress` | ✅ Implemented | +| `RunInstances` | ✅ Implemented | +| `RunScheduledInstances` | ❌ Not implemented | +| `SearchLocalGatewayRoutes` | ❌ Not implemented | +| `SearchTransitGatewayMulticastGroups` | ❌ Not implemented | +| `SearchTransitGatewayRoutes` | ❌ Not implemented | +| `SendDiagnosticInterrupt` | ❌ Not implemented | +| `StartInstances` | ✅ Implemented | +| `StartNetworkInsightsAccessScopeAnalysis` | ❌ Not implemented | +| `StartNetworkInsightsAnalysis` | ❌ Not implemented | +| `StartVpcEndpointServicePrivateDnsVerification` | ❌ Not implemented | +| `StopInstances` | ✅ Implemented | +| `TerminateClientVpnConnections` | ❌ Not implemented | +| `TerminateInstances` | ✅ Implemented | +| `UnassignIpv6Addresses` | ❌ Not implemented | +| `UnassignPrivateIpAddresses` | ❌ Not implemented | +| `UnassignPrivateNatGatewayAddress` | ❌ Not implemented | +| `UnlockSnapshot` | ❌ Not implemented | +| `UnmonitorInstances` | ✅ Implemented | +| `UpdateSecurityGroupRuleDescriptionsEgress` | ❌ Not implemented | +| `UpdateSecurityGroupRuleDescriptionsIngress` | ❌ Not implemented | +| `WithdrawByoipCidr` | ❌ Not implemented | + +### Notes + +1. On owned hardware there is no spot-to-on-demand price differential, so any figure would be invented. diff --git a/docs/compatibility/ecr-api-coverage/README.md b/docs/compatibility/ecr-api-coverage/README.md index 464aec220..a03f2af34 100644 --- a/docs/compatibility/ecr-api-coverage/README.md +++ b/docs/compatibility/ecr-api-coverage/README.md @@ -18,7 +18,7 @@ tags: ## Overview -Spinifex implements **19 of the 47** operations (40.4%) in the ECR `2015-09-21` API model. +Spinifex implements **19 of the 47** operations (**40.4%**) in the ECR `2015-09-21` API model. ### Two endpoints, one registry diff --git a/docs/compatibility/ecs-api-coverage/README.md b/docs/compatibility/ecs-api-coverage/README.md index 21fec652d..9bc2084d6 100644 --- a/docs/compatibility/ecs-api-coverage/README.md +++ b/docs/compatibility/ecs-api-coverage/README.md @@ -18,7 +18,7 @@ tags: ## Overview -Spinifex implements **31 of the 56** operations (55.4%) in the ECS `2014-11-13` API model. +Spinifex implements **31 of the 56** operations (**55.4%**) in the ECS `2014-11-13` API model. ### No Fargate diff --git a/docs/compatibility/eks-api-coverage/README.md b/docs/compatibility/eks-api-coverage/README.md index d5c19f320..e6d4e2462 100644 --- a/docs/compatibility/eks-api-coverage/README.md +++ b/docs/compatibility/eks-api-coverage/README.md @@ -18,7 +18,7 @@ tags: ## Overview -Spinifex implements **34 of the 56** operations (60.7%) in the EKS `2017-11-01` API model. +Spinifex implements **34 of the 56** operations (**60.7%**) in the EKS `2017-11-01` API model. ### Routing diff --git a/docs/compatibility/elbv2-api-coverage/README.md b/docs/compatibility/elbv2-api-coverage/README.md index 3edaefa65..d82cb29bf 100644 --- a/docs/compatibility/elbv2-api-coverage/README.md +++ b/docs/compatibility/elbv2-api-coverage/README.md @@ -18,7 +18,7 @@ tags: ## Overview -Spinifex implements **33 of the 46** operations (71.7%) in the ELBv2 `2015-12-01` API model. +Spinifex implements **33 of the 46** operations (**71.7%**) in the ELBv2 `2015-12-01` API model. ### Two data planes diff --git a/docs/compatibility/iam-api-coverage/README.md b/docs/compatibility/iam-api-coverage/README.md index ef7eba6c0..c72e9ad4b 100644 --- a/docs/compatibility/iam-api-coverage/README.md +++ b/docs/compatibility/iam-api-coverage/README.md @@ -18,7 +18,7 @@ tags: ## Overview -Spinifex implements **75 of the 159** operations (47.2%) in the IAM `2010-05-08` API model. +Spinifex implements **75 of the 159** operations (**47.2%**) in the IAM `2010-05-08` API model. ### Scope @@ -26,164 +26,171 @@ All IAM operations are account-scoped. The root user of an account bypasses poli ### Operations -| Operation | Status | Notes | -|---|---|---| -| `AddClientIDToOpenIDConnectProvider` | ❌ Not implemented | | -| `AddRoleToInstanceProfile` | ✅ Implemented | | -| `AddUserToGroup` | ✅ Implemented | | -| `AttachGroupPolicy` | ✅ Implemented | | -| `AttachRolePolicy` | ✅ Implemented | | -| `AttachUserPolicy` | ✅ Implemented | | -| `ChangePassword` | ❌ Not implemented | | -| `CreateAccessKey` | ✅ Implemented | | -| `CreateAccountAlias` | ❌ Not implemented | | -| `CreateGroup` | ✅ Implemented | | -| `CreateInstanceProfile` | ✅ Implemented | | -| `CreateLoginProfile` | ❌ Not implemented | | -| `CreateOpenIDConnectProvider` | ✅ Implemented | | -| `CreatePolicy` | ✅ Implemented | | -| `CreatePolicyVersion` | ❌ Not implemented | | -| `CreateRole` | ✅ Implemented | | -| `CreateSAMLProvider` | ❌ Not implemented | | -| `CreateServiceLinkedRole` | ⛔ Not applicable | Service-linked roles exist for AWS service principals, which this platform has none of. | -| `CreateServiceSpecificCredential` | ⛔ Not applicable | CodeCommit credentials; the service does not exist here. | -| `CreateUser` | ✅ Implemented | | -| `CreateVirtualMFADevice` | ❌ Not implemented | | -| `DeactivateMFADevice` | ❌ Not implemented | | -| `DeleteAccessKey` | ✅ Implemented | | -| `DeleteAccountAlias` | ❌ Not implemented | | -| `DeleteAccountPasswordPolicy` | ❌ Not implemented | | -| `DeleteGroup` | ✅ Implemented | | -| `DeleteGroupPolicy` | ✅ Implemented | | -| `DeleteInstanceProfile` | ✅ Implemented | | -| `DeleteLoginProfile` | ❌ Not implemented | | -| `DeleteOpenIDConnectProvider` | ✅ Implemented | | -| `DeletePolicy` | ✅ Implemented | | -| `DeletePolicyVersion` | ❌ Not implemented | | -| `DeleteRole` | ✅ Implemented | | -| `DeleteRolePermissionsBoundary` | ❌ Not implemented | | -| `DeleteRolePolicy` | ✅ Implemented | | -| `DeleteSAMLProvider` | ❌ Not implemented | | -| `DeleteSSHPublicKey` | ⛔ Not applicable | CodeCommit SSH keys; the service does not exist here. | -| `DeleteServerCertificate` | ❌ Not implemented | | -| `DeleteServiceLinkedRole` | ⛔ Not applicable | Service-linked roles exist for AWS service principals, which this platform has none of. | -| `DeleteServiceSpecificCredential` | ⛔ Not applicable | CodeCommit credentials; the service does not exist here. | -| `DeleteSigningCertificate` | ⛔ Not applicable | X.509 signing certificates are an EC2-Classic SOAP credential, retired by AWS. | -| `DeleteUser` | ✅ Implemented | | -| `DeleteUserPermissionsBoundary` | ❌ Not implemented | | -| `DeleteUserPolicy` | ✅ Implemented | | -| `DeleteVirtualMFADevice` | ❌ Not implemented | | -| `DetachGroupPolicy` | ✅ Implemented | | -| `DetachRolePolicy` | ✅ Implemented | | -| `DetachUserPolicy` | ✅ Implemented | | -| `EnableMFADevice` | ❌ Not implemented | | -| `GenerateCredentialReport` | ❌ Not implemented | | -| `GenerateOrganizationsAccessReport` | ⛔ Not applicable | AWS Organizations is not offered, so there is no organization to report on. | -| `GenerateServiceLastAccessedDetails` | ❌ Not implemented | | -| `GetAccessKeyLastUsed` | ❌ Not implemented | | -| `GetAccountAuthorizationDetails` | ❌ Not implemented | | -| `GetAccountPasswordPolicy` | ❌ Not implemented | | -| `GetAccountSummary` | ✅ Implemented | | -| `GetContextKeysForCustomPolicy` | ❌ Not implemented | | -| `GetContextKeysForPrincipalPolicy` | ❌ Not implemented | | -| `GetCredentialReport` | ❌ Not implemented | | -| `GetGroup` | ✅ Implemented | | -| `GetGroupPolicy` | ✅ Implemented | | -| `GetInstanceProfile` | ✅ Implemented | | -| `GetLoginProfile` | ❌ Not implemented | | -| `GetMFADevice` | ❌ Not implemented | | -| `GetOpenIDConnectProvider` | ✅ Implemented | | -| `GetOrganizationsAccessReport` | ⛔ Not applicable | AWS Organizations is not offered, so there is no organization to report on. | -| `GetPolicy` | ✅ Implemented | | -| `GetPolicyVersion` | ✅ Implemented | | -| `GetRole` | ✅ Implemented | | -| `GetRolePolicy` | ✅ Implemented | | -| `GetSAMLProvider` | ❌ Not implemented | | -| `GetSSHPublicKey` | ⛔ Not applicable | CodeCommit SSH keys; the service does not exist here. | -| `GetServerCertificate` | ❌ Not implemented | | -| `GetServiceLastAccessedDetails` | ❌ Not implemented | | -| `GetServiceLastAccessedDetailsWithEntities` | ❌ Not implemented | | -| `GetServiceLinkedRoleDeletionStatus` | ⛔ Not applicable | Service-linked roles exist for AWS service principals, which this platform has none of. | -| `GetUser` | ✅ Implemented | | -| `GetUserPolicy` | ✅ Implemented | | -| `ListAccessKeys` | ✅ Implemented | | -| `ListAccountAliases` | ❌ Not implemented | | -| `ListAttachedGroupPolicies` | ✅ Implemented | | -| `ListAttachedRolePolicies` | ✅ Implemented | | -| `ListAttachedUserPolicies` | ✅ Implemented | | -| `ListEntitiesForPolicy` | ❌ Not implemented | | -| `ListGroupPolicies` | ✅ Implemented | | -| `ListGroups` | ✅ Implemented | | -| `ListGroupsForUser` | ✅ Implemented | | -| `ListInstanceProfileTags` | ✅ Implemented | | -| `ListInstanceProfiles` | ✅ Implemented | | -| `ListInstanceProfilesForRole` | ✅ Implemented | | -| `ListMFADeviceTags` | ❌ Not implemented | | -| `ListMFADevices` | ❌ Not implemented | | -| `ListOpenIDConnectProviderTags` | ✅ Implemented | | -| `ListOpenIDConnectProviders` | ✅ Implemented | | -| `ListPolicies` | ✅ Implemented | | -| `ListPoliciesGrantingServiceAccess` | ❌ Not implemented | | -| `ListPolicyTags` | ✅ Implemented | | -| `ListPolicyVersions` | ✅ Implemented | | -| `ListRolePolicies` | ✅ Implemented | | -| `ListRoleTags` | ✅ Implemented | | -| `ListRoles` | ✅ Implemented | | -| `ListSAMLProviderTags` | ❌ Not implemented | | -| `ListSAMLProviders` | ❌ Not implemented | | -| `ListSSHPublicKeys` | ⛔ Not applicable | CodeCommit SSH keys; the service does not exist here. | -| `ListServerCertificateTags` | ❌ Not implemented | | -| `ListServerCertificates` | ❌ Not implemented | | -| `ListServiceSpecificCredentials` | ⛔ Not applicable | CodeCommit credentials; the service does not exist here. | -| `ListSigningCertificates` | ⛔ Not applicable | X.509 signing certificates are an EC2-Classic SOAP credential, retired by AWS. | -| `ListUserPolicies` | ✅ Implemented | | -| `ListUserTags` | ✅ Implemented | | -| `ListUsers` | ✅ Implemented | | -| `ListVirtualMFADevices` | ❌ Not implemented | | -| `PutGroupPolicy` | ✅ Implemented | | -| `PutRolePermissionsBoundary` | ❌ Not implemented | | -| `PutRolePolicy` | ✅ Implemented | | -| `PutUserPermissionsBoundary` | ❌ Not implemented | | -| `PutUserPolicy` | ✅ Implemented | | -| `RemoveClientIDFromOpenIDConnectProvider` | ❌ Not implemented | | -| `RemoveRoleFromInstanceProfile` | ✅ Implemented | | -| `RemoveUserFromGroup` | ✅ Implemented | | -| `ResetServiceSpecificCredential` | ⛔ Not applicable | CodeCommit credentials; the service does not exist here. | -| `ResyncMFADevice` | ❌ Not implemented | | -| `SetDefaultPolicyVersion` | ❌ Not implemented | | -| `SetSecurityTokenServicePreferences` | ❌ Not implemented | | -| `SimulateCustomPolicy` | ❌ Not implemented | | -| `SimulatePrincipalPolicy` | ❌ Not implemented | | -| `TagInstanceProfile` | ✅ Implemented | | -| `TagMFADevice` | ❌ Not implemented | | -| `TagOpenIDConnectProvider` | ✅ Implemented | | -| `TagPolicy` | ✅ Implemented | | -| `TagRole` | ✅ Implemented | | -| `TagSAMLProvider` | ❌ Not implemented | | -| `TagServerCertificate` | ❌ Not implemented | | -| `TagUser` | ✅ Implemented | | -| `UntagInstanceProfile` | ✅ Implemented | | -| `UntagMFADevice` | ❌ Not implemented | | -| `UntagOpenIDConnectProvider` | ✅ Implemented | | -| `UntagPolicy` | ✅ Implemented | | -| `UntagRole` | ✅ Implemented | | -| `UntagSAMLProvider` | ❌ Not implemented | | -| `UntagServerCertificate` | ❌ Not implemented | | -| `UntagUser` | ✅ Implemented | | -| `UpdateAccessKey` | ✅ Implemented | | -| `UpdateAccountPasswordPolicy` | ❌ Not implemented | | -| `UpdateAssumeRolePolicy` | ✅ Implemented | | -| `UpdateGroup` | ❌ Not implemented | | -| `UpdateLoginProfile` | ❌ Not implemented | | -| `UpdateOpenIDConnectProviderThumbprint` | ❌ Not implemented | | -| `UpdateRole` | ✅ Implemented | | -| `UpdateRoleDescription` | ❌ Not implemented | | -| `UpdateSAMLProvider` | ❌ Not implemented | | -| `UpdateSSHPublicKey` | ⛔ Not applicable | CodeCommit SSH keys; the service does not exist here. | -| `UpdateServerCertificate` | ❌ Not implemented | | -| `UpdateServiceSpecificCredential` | ⛔ Not applicable | CodeCommit credentials; the service does not exist here. | -| `UpdateSigningCertificate` | ⛔ Not applicable | X.509 signing certificates are an EC2-Classic SOAP credential, retired by AWS. | -| `UpdateUser` | ❌ Not implemented | | -| `UploadSSHPublicKey` | ⛔ Not applicable | CodeCommit SSH keys; the service does not exist here. | -| `UploadServerCertificate` | ❌ Not implemented | | -| `UploadSigningCertificate` | ⛔ Not applicable | X.509 signing certificates are an EC2-Classic SOAP credential, retired by AWS. | +| Operation | Status | +|---|---| +| `AddClientIDToOpenIDConnectProvider` | ❌ Not implemented | +| `AddRoleToInstanceProfile` | ✅ Implemented | +| `AddUserToGroup` | ✅ Implemented | +| `AttachGroupPolicy` | ✅ Implemented | +| `AttachRolePolicy` | ✅ Implemented | +| `AttachUserPolicy` | ✅ Implemented | +| `ChangePassword` | ❌ Not implemented | +| `CreateAccessKey` | ✅ Implemented | +| `CreateAccountAlias` | ❌ Not implemented | +| `CreateGroup` | ✅ Implemented | +| `CreateInstanceProfile` | ✅ Implemented | +| `CreateLoginProfile` | ❌ Not implemented | +| `CreateOpenIDConnectProvider` | ✅ Implemented | +| `CreatePolicy` | ✅ Implemented | +| `CreatePolicyVersion` | ❌ Not implemented | +| `CreateRole` | ✅ Implemented | +| `CreateSAMLProvider` | ❌ Not implemented | +| `CreateServiceLinkedRole` | ⛔ Not applicable [3](#notes) | +| `CreateServiceSpecificCredential` | ⛔ Not applicable [1](#notes) | +| `CreateUser` | ✅ Implemented | +| `CreateVirtualMFADevice` | ❌ Not implemented | +| `DeactivateMFADevice` | ❌ Not implemented | +| `DeleteAccessKey` | ✅ Implemented | +| `DeleteAccountAlias` | ❌ Not implemented | +| `DeleteAccountPasswordPolicy` | ❌ Not implemented | +| `DeleteGroup` | ✅ Implemented | +| `DeleteGroupPolicy` | ✅ Implemented | +| `DeleteInstanceProfile` | ✅ Implemented | +| `DeleteLoginProfile` | ❌ Not implemented | +| `DeleteOpenIDConnectProvider` | ✅ Implemented | +| `DeletePolicy` | ✅ Implemented | +| `DeletePolicyVersion` | ❌ Not implemented | +| `DeleteRole` | ✅ Implemented | +| `DeleteRolePermissionsBoundary` | ❌ Not implemented | +| `DeleteRolePolicy` | ✅ Implemented | +| `DeleteSAMLProvider` | ❌ Not implemented | +| `DeleteSSHPublicKey` | ⛔ Not applicable [1](#notes) | +| `DeleteServerCertificate` | ❌ Not implemented | +| `DeleteServiceLinkedRole` | ⛔ Not applicable [3](#notes) | +| `DeleteServiceSpecificCredential` | ⛔ Not applicable [1](#notes) | +| `DeleteSigningCertificate` | ⛔ Not applicable [4](#notes) | +| `DeleteUser` | ✅ Implemented | +| `DeleteUserPermissionsBoundary` | ❌ Not implemented | +| `DeleteUserPolicy` | ✅ Implemented | +| `DeleteVirtualMFADevice` | ❌ Not implemented | +| `DetachGroupPolicy` | ✅ Implemented | +| `DetachRolePolicy` | ✅ Implemented | +| `DetachUserPolicy` | ✅ Implemented | +| `EnableMFADevice` | ❌ Not implemented | +| `GenerateCredentialReport` | ❌ Not implemented | +| `GenerateOrganizationsAccessReport` | ⛔ Not applicable [2](#notes) | +| `GenerateServiceLastAccessedDetails` | ❌ Not implemented | +| `GetAccessKeyLastUsed` | ❌ Not implemented | +| `GetAccountAuthorizationDetails` | ❌ Not implemented | +| `GetAccountPasswordPolicy` | ❌ Not implemented | +| `GetAccountSummary` | ✅ Implemented | +| `GetContextKeysForCustomPolicy` | ❌ Not implemented | +| `GetContextKeysForPrincipalPolicy` | ❌ Not implemented | +| `GetCredentialReport` | ❌ Not implemented | +| `GetGroup` | ✅ Implemented | +| `GetGroupPolicy` | ✅ Implemented | +| `GetInstanceProfile` | ✅ Implemented | +| `GetLoginProfile` | ❌ Not implemented | +| `GetMFADevice` | ❌ Not implemented | +| `GetOpenIDConnectProvider` | ✅ Implemented | +| `GetOrganizationsAccessReport` | ⛔ Not applicable [2](#notes) | +| `GetPolicy` | ✅ Implemented | +| `GetPolicyVersion` | ✅ Implemented | +| `GetRole` | ✅ Implemented | +| `GetRolePolicy` | ✅ Implemented | +| `GetSAMLProvider` | ❌ Not implemented | +| `GetSSHPublicKey` | ⛔ Not applicable [1](#notes) | +| `GetServerCertificate` | ❌ Not implemented | +| `GetServiceLastAccessedDetails` | ❌ Not implemented | +| `GetServiceLastAccessedDetailsWithEntities` | ❌ Not implemented | +| `GetServiceLinkedRoleDeletionStatus` | ⛔ Not applicable [3](#notes) | +| `GetUser` | ✅ Implemented | +| `GetUserPolicy` | ✅ Implemented | +| `ListAccessKeys` | ✅ Implemented | +| `ListAccountAliases` | ❌ Not implemented | +| `ListAttachedGroupPolicies` | ✅ Implemented | +| `ListAttachedRolePolicies` | ✅ Implemented | +| `ListAttachedUserPolicies` | ✅ Implemented | +| `ListEntitiesForPolicy` | ❌ Not implemented | +| `ListGroupPolicies` | ✅ Implemented | +| `ListGroups` | ✅ Implemented | +| `ListGroupsForUser` | ✅ Implemented | +| `ListInstanceProfileTags` | ✅ Implemented | +| `ListInstanceProfiles` | ✅ Implemented | +| `ListInstanceProfilesForRole` | ✅ Implemented | +| `ListMFADeviceTags` | ❌ Not implemented | +| `ListMFADevices` | ❌ Not implemented | +| `ListOpenIDConnectProviderTags` | ✅ Implemented | +| `ListOpenIDConnectProviders` | ✅ Implemented | +| `ListPolicies` | ✅ Implemented | +| `ListPoliciesGrantingServiceAccess` | ❌ Not implemented | +| `ListPolicyTags` | ✅ Implemented | +| `ListPolicyVersions` | ✅ Implemented | +| `ListRolePolicies` | ✅ Implemented | +| `ListRoleTags` | ✅ Implemented | +| `ListRoles` | ✅ Implemented | +| `ListSAMLProviderTags` | ❌ Not implemented | +| `ListSAMLProviders` | ❌ Not implemented | +| `ListSSHPublicKeys` | ⛔ Not applicable [1](#notes) | +| `ListServerCertificateTags` | ❌ Not implemented | +| `ListServerCertificates` | ❌ Not implemented | +| `ListServiceSpecificCredentials` | ⛔ Not applicable [1](#notes) | +| `ListSigningCertificates` | ⛔ Not applicable [4](#notes) | +| `ListUserPolicies` | ✅ Implemented | +| `ListUserTags` | ✅ Implemented | +| `ListUsers` | ✅ Implemented | +| `ListVirtualMFADevices` | ❌ Not implemented | +| `PutGroupPolicy` | ✅ Implemented | +| `PutRolePermissionsBoundary` | ❌ Not implemented | +| `PutRolePolicy` | ✅ Implemented | +| `PutUserPermissionsBoundary` | ❌ Not implemented | +| `PutUserPolicy` | ✅ Implemented | +| `RemoveClientIDFromOpenIDConnectProvider` | ❌ Not implemented | +| `RemoveRoleFromInstanceProfile` | ✅ Implemented | +| `RemoveUserFromGroup` | ✅ Implemented | +| `ResetServiceSpecificCredential` | ⛔ Not applicable [1](#notes) | +| `ResyncMFADevice` | ❌ Not implemented | +| `SetDefaultPolicyVersion` | ❌ Not implemented | +| `SetSecurityTokenServicePreferences` | ❌ Not implemented | +| `SimulateCustomPolicy` | ❌ Not implemented | +| `SimulatePrincipalPolicy` | ❌ Not implemented | +| `TagInstanceProfile` | ✅ Implemented | +| `TagMFADevice` | ❌ Not implemented | +| `TagOpenIDConnectProvider` | ✅ Implemented | +| `TagPolicy` | ✅ Implemented | +| `TagRole` | ✅ Implemented | +| `TagSAMLProvider` | ❌ Not implemented | +| `TagServerCertificate` | ❌ Not implemented | +| `TagUser` | ✅ Implemented | +| `UntagInstanceProfile` | ✅ Implemented | +| `UntagMFADevice` | ❌ Not implemented | +| `UntagOpenIDConnectProvider` | ✅ Implemented | +| `UntagPolicy` | ✅ Implemented | +| `UntagRole` | ✅ Implemented | +| `UntagSAMLProvider` | ❌ Not implemented | +| `UntagServerCertificate` | ❌ Not implemented | +| `UntagUser` | ✅ Implemented | +| `UpdateAccessKey` | ✅ Implemented | +| `UpdateAccountPasswordPolicy` | ❌ Not implemented | +| `UpdateAssumeRolePolicy` | ✅ Implemented | +| `UpdateGroup` | ❌ Not implemented | +| `UpdateLoginProfile` | ❌ Not implemented | +| `UpdateOpenIDConnectProviderThumbprint` | ❌ Not implemented | +| `UpdateRole` | ✅ Implemented | +| `UpdateRoleDescription` | ❌ Not implemented | +| `UpdateSAMLProvider` | ❌ Not implemented | +| `UpdateSSHPublicKey` | ⛔ Not applicable [1](#notes) | +| `UpdateServerCertificate` | ❌ Not implemented | +| `UpdateServiceSpecificCredential` | ⛔ Not applicable [1](#notes) | +| `UpdateSigningCertificate` | ⛔ Not applicable [4](#notes) | +| `UpdateUser` | ❌ Not implemented | +| `UploadSSHPublicKey` | ⛔ Not applicable [1](#notes) | +| `UploadServerCertificate` | ❌ Not implemented | +| `UploadSigningCertificate` | ⛔ Not applicable [4](#notes) | + +### Notes + +1. CodeCommit credentials and SSH keys; the service does not exist here. +2. AWS Organizations is not offered, so there is no organization to report on. +3. Service-linked roles exist for AWS service principals, which this platform has none of. +4. X.509 signing certificates are an EC2-Classic SOAP credential, retired by AWS. diff --git a/docs/compatibility/pages.json b/docs/compatibility/pages.json index dabbe4c2c..e00581fe3 100644 --- a/docs/compatibility/pages.json +++ b/docs/compatibility/pages.json @@ -45,7 +45,10 @@ "vpc" ], "notApplicable": { - "DescribeSpotPriceHistory": "On owned hardware there is no spot-to-on-demand price differential, so any figure would be invented." + "DescribeSpotPriceHistory": "spot-price" + }, + "notes": { + "spot-price": "On owned hardware there is no spot-to-on-demand price differential, so any figure would be invented." } }, "ecr": { @@ -123,25 +126,31 @@ "policies" ], "notApplicable": { - "CreateServiceLinkedRole": "Service-linked roles exist for AWS service principals, which this platform has none of.", - "CreateServiceSpecificCredential": "CodeCommit credentials; the service does not exist here.", - "DeleteSSHPublicKey": "CodeCommit SSH keys; the service does not exist here.", - "DeleteServiceLinkedRole": "Service-linked roles exist for AWS service principals, which this platform has none of.", - "DeleteServiceSpecificCredential": "CodeCommit credentials; the service does not exist here.", - "DeleteSigningCertificate": "X.509 signing certificates are an EC2-Classic SOAP credential, retired by AWS.", - "GenerateOrganizationsAccessReport": "AWS Organizations is not offered, so there is no organization to report on.", - "GetOrganizationsAccessReport": "AWS Organizations is not offered, so there is no organization to report on.", - "GetSSHPublicKey": "CodeCommit SSH keys; the service does not exist here.", - "GetServiceLinkedRoleDeletionStatus": "Service-linked roles exist for AWS service principals, which this platform has none of.", - "ListSSHPublicKeys": "CodeCommit SSH keys; the service does not exist here.", - "ListServiceSpecificCredentials": "CodeCommit credentials; the service does not exist here.", - "ListSigningCertificates": "X.509 signing certificates are an EC2-Classic SOAP credential, retired by AWS.", - "ResetServiceSpecificCredential": "CodeCommit credentials; the service does not exist here.", - "UpdateSSHPublicKey": "CodeCommit SSH keys; the service does not exist here.", - "UpdateServiceSpecificCredential": "CodeCommit credentials; the service does not exist here.", - "UpdateSigningCertificate": "X.509 signing certificates are an EC2-Classic SOAP credential, retired by AWS.", - "UploadSSHPublicKey": "CodeCommit SSH keys; the service does not exist here.", - "UploadSigningCertificate": "X.509 signing certificates are an EC2-Classic SOAP credential, retired by AWS." + "CreateServiceLinkedRole": "service-linked-roles", + "CreateServiceSpecificCredential": "codecommit", + "DeleteSSHPublicKey": "codecommit", + "DeleteServiceLinkedRole": "service-linked-roles", + "DeleteServiceSpecificCredential": "codecommit", + "DeleteSigningCertificate": "signing-certificates", + "GenerateOrganizationsAccessReport": "organizations", + "GetOrganizationsAccessReport": "organizations", + "GetSSHPublicKey": "codecommit", + "GetServiceLinkedRoleDeletionStatus": "service-linked-roles", + "ListSSHPublicKeys": "codecommit", + "ListServiceSpecificCredentials": "codecommit", + "ListSigningCertificates": "signing-certificates", + "ResetServiceSpecificCredential": "codecommit", + "UpdateSSHPublicKey": "codecommit", + "UpdateServiceSpecificCredential": "codecommit", + "UpdateSigningCertificate": "signing-certificates", + "UploadSSHPublicKey": "codecommit", + "UploadSigningCertificate": "signing-certificates" + }, + "notes": { + "codecommit": "CodeCommit credentials and SSH keys; the service does not exist here.", + "organizations": "AWS Organizations is not offered, so there is no organization to report on.", + "service-linked-roles": "Service-linked roles exist for AWS service principals, which this platform has none of.", + "signing-certificates": "X.509 signing certificates are an EC2-Classic SOAP credential, retired by AWS." } }, "rds": { diff --git a/docs/compatibility/rds-api-coverage/README.md b/docs/compatibility/rds-api-coverage/README.md index c22879702..c9a4d3e59 100644 --- a/docs/compatibility/rds-api-coverage/README.md +++ b/docs/compatibility/rds-api-coverage/README.md @@ -19,7 +19,7 @@ tags: ## Overview -Spinifex implements **26 of the 162** operations (16.0%) in the RDS `2014-10-31` API model. +Spinifex implements **26 of the 162** operations (**16.0%**) in the RDS `2014-10-31` API model. ### Engines @@ -41,7 +41,34 @@ Enforcement requires that the connection is encrypted, not that the client valid ### Rejected parameters -A parameter whose omission would create a false safety, security or availability guarantee is rejected rather than silently dropped — `MultiAZ=true` on a single-AZ platform, `PubliclyAccessible=true` against a private endpoint, `StorageEncrypted=false` where unencrypted storage is not offered. Parameters that are merely inert are accepted as no-ops. +A parameter whose omission would create a false safety, security or availability guarantee is rejected with `InvalidParameterValue` rather than silently dropped. Parameters that are merely inert — `AutoMinorVersionUpgrade`, `CopyTagsToSnapshot`, `DeleteAutomatedBackups`, Performance Insights and Enhanced Monitoring fields — are accepted as no-ops. + +| Parameter | Why it is rejected | +|-----------|--------------------| +| `MultiAZ=true` | Single-AZ platform; a standby would not exist | +| `PubliclyAccessible=true` | The endpoint is a private VPC address | +| `StorageEncrypted=false` | Unencrypted storage is not offered | +| `EnableIAMDatabaseAuthentication` | IAM database authentication is not implemented | +| `Iops`, `StorageThroughput`, `StorageType` ≠ `gp3` | Provisioned performance classes are not implemented | +| `KmsKeyId`, `TdeCredentialArn` | Storage is encrypted with the cluster key, not a customer-managed one | +| `AvailabilityZone` | The platform exposes a single zone | +| `AvailabilityZoneGroup` (orderable options) | It selects a zone or local-zone group, and naming a zone is already refused | +| `DBSecurityGroups` | EC2-Classic security groups — use `VpcSecurityGroupIds` | +| `DBClusterIdentifier`, `DBClusterSnapshotIdentifier` | Clustered engines are not offered | +| `EnableCloudwatchLogsExports` | Log export is not implemented | +| `EngineVersion` other than the engine's pin, `Engine` on modify | No in-place engine or version change | +| `Engine=mysql` (and Aurora engines) | Oracle MySQL is not offered; `mariadb` is a distinct engine, not an alias for it | +| `NewDBInstanceIdentifier` | The identifier is the DNS label and the KV key | +| `DBPortNumber`, `DBSubnetGroupName` on modify | Both would move the endpoint | +| `MaxAllocatedStorage` | Storage autoscaling is not implemented | +| `ManageMasterUserPassword`, `RotateMasterUserPassword` | Secrets Manager integration is not offered | +| `CACertificateIdentifier` | The serving certificate is minted from the cluster CA | +| `Domain`, `DomainFqdn` | Active Directory domain join is not offered | +| `OptionGroupName` | Option groups are not offered | +| `CustomIamInstanceProfile` | The DB VM's instance profile is platform-owned | +| `EnableCustomerOwnedIp` | An Outposts feature | +| `ForceFailover` (reboot) | No standby to fail over to | +| `DBSnapshotIdentifier` (stop) | Snapshot-on-stop is not implemented | ### Operations diff --git a/docs/compatibility/rds-api-coverage/intro.md b/docs/compatibility/rds-api-coverage/intro.md index 280cb133b..03e2d8c35 100644 --- a/docs/compatibility/rds-api-coverage/intro.md +++ b/docs/compatibility/rds-api-coverage/intro.md @@ -18,4 +18,31 @@ Enforcement requires that the connection is encrypted, not that the client valid ### Rejected parameters -A parameter whose omission would create a false safety, security or availability guarantee is rejected rather than silently dropped — `MultiAZ=true` on a single-AZ platform, `PubliclyAccessible=true` against a private endpoint, `StorageEncrypted=false` where unencrypted storage is not offered. Parameters that are merely inert are accepted as no-ops. +A parameter whose omission would create a false safety, security or availability guarantee is rejected with `InvalidParameterValue` rather than silently dropped. Parameters that are merely inert — `AutoMinorVersionUpgrade`, `CopyTagsToSnapshot`, `DeleteAutomatedBackups`, Performance Insights and Enhanced Monitoring fields — are accepted as no-ops. + +| Parameter | Why it is rejected | +|-----------|--------------------| +| `MultiAZ=true` | Single-AZ platform; a standby would not exist | +| `PubliclyAccessible=true` | The endpoint is a private VPC address | +| `StorageEncrypted=false` | Unencrypted storage is not offered | +| `EnableIAMDatabaseAuthentication` | IAM database authentication is not implemented | +| `Iops`, `StorageThroughput`, `StorageType` ≠ `gp3` | Provisioned performance classes are not implemented | +| `KmsKeyId`, `TdeCredentialArn` | Storage is encrypted with the cluster key, not a customer-managed one | +| `AvailabilityZone` | The platform exposes a single zone | +| `AvailabilityZoneGroup` (orderable options) | It selects a zone or local-zone group, and naming a zone is already refused | +| `DBSecurityGroups` | EC2-Classic security groups — use `VpcSecurityGroupIds` | +| `DBClusterIdentifier`, `DBClusterSnapshotIdentifier` | Clustered engines are not offered | +| `EnableCloudwatchLogsExports` | Log export is not implemented | +| `EngineVersion` other than the engine's pin, `Engine` on modify | No in-place engine or version change | +| `Engine=mysql` (and Aurora engines) | Oracle MySQL is not offered; `mariadb` is a distinct engine, not an alias for it | +| `NewDBInstanceIdentifier` | The identifier is the DNS label and the KV key | +| `DBPortNumber`, `DBSubnetGroupName` on modify | Both would move the endpoint | +| `MaxAllocatedStorage` | Storage autoscaling is not implemented | +| `ManageMasterUserPassword`, `RotateMasterUserPassword` | Secrets Manager integration is not offered | +| `CACertificateIdentifier` | The serving certificate is minted from the cluster CA | +| `Domain`, `DomainFqdn` | Active Directory domain join is not offered | +| `OptionGroupName` | Option groups are not offered | +| `CustomIamInstanceProfile` | The DB VM's instance profile is platform-owned | +| `EnableCustomerOwnedIp` | An Outposts feature | +| `ForceFailover` (reboot) | No standby to fail over to | +| `DBSnapshotIdentifier` (stop) | Snapshot-on-stop is not implemented | diff --git a/docs/compatibility/sts-api-coverage/README.md b/docs/compatibility/sts-api-coverage/README.md index edbb6157f..287d3db76 100644 --- a/docs/compatibility/sts-api-coverage/README.md +++ b/docs/compatibility/sts-api-coverage/README.md @@ -18,7 +18,7 @@ tags: ## Overview -Spinifex implements **4 of the 8** operations (50.0%) in the STS `2011-06-15` API model. +Spinifex implements **4 of the 8** operations (**50.0%**) in the STS `2011-06-15` API model. ### Trust policies diff --git a/docs/terraform-workbooks/rds-quickstart/README.md b/docs/terraform-workbooks/rds-quickstart/README.md index eb5eedad7..1b9b61255 100644 --- a/docs/terraform-workbooks/rds-quickstart/README.md +++ b/docs/terraform-workbooks/rds-quickstart/README.md @@ -16,8 +16,8 @@ sections: - instructions - troubleshooting resources: - - title: "RDS CLI Reference" - url: "https://github.com/mulgadc/spinifex/blob/main/docs/COMMANDS.md#rds-postgresql-and-mariadb" + - title: "RDS API Coverage" + url: "/docs/rds-api-coverage" - title: "Terraform AWS Provider — aws_db_instance" url: "https://registry.terraform.io/providers/hashicorp/aws/latest/docs/resources/db_instance" - title: "Spinifex Repository" @@ -30,7 +30,7 @@ resources: > The smallest end-to-end RDS example on Spinifex: a VPC with a public client subnet and a private DB subnet, a DB subnet group, a parameter group, a PostgreSQL DB instance, and a client VM with `psql` already pointed at the endpoint. -This workbook is **PostgreSQL throughout** — the engine, the `postgres18` parameter group, port `5432`, the client package and the `~/.pgpass` credential are all PostgreSQL's. Spinifex also serves MariaDB 11.8 under `engine = "mariadb"`; running this workbook against it means changing `engine`, `engine_version`, the parameter-group `family` to `mariadb11.8`, the security-group port to `3306` and the client to `mariadb-client`. See the [RDS command reference](https://github.com/mulgadc/spinifex/blob/main/docs/COMMANDS.md#rds-postgresql-and-mariadb) for both engines' pins, families and limits. Note that `mysql` is not an accepted engine and is not an alias for `mariadb`. +This workbook is **PostgreSQL throughout** — the engine, the `postgres18` parameter group, port `5432`, the client package and the `~/.pgpass` credential are all PostgreSQL's. Spinifex also serves MariaDB 11.8 under `engine = "mariadb"`; running this workbook against it means changing `engine`, `engine_version`, the parameter-group `family` to `mariadb11.8`, the security-group port to `3306` and the client to `mariadb-client`. See the [RDS API coverage page](/docs/rds-api-coverage) for both engines' pins, families and limits. Note that `mysql` is not an accepted engine and is not an alias for `mariadb`. ## Overview diff --git a/internal/awsmodel/page.go b/internal/awsmodel/page.go index 63b3aa2c4..2434add26 100644 --- a/internal/awsmodel/page.go +++ b/internal/awsmodel/page.go @@ -5,6 +5,7 @@ import ( "encoding/json" "fmt" "regexp" + "sort" "strconv" "strings" "unicode/utf8" @@ -31,11 +32,12 @@ const ( var slugPattern = regexp.MustCompile(`^[a-z0-9]+(-[a-z0-9]+)*$`) -// OperationStatus is one row of a published coverage table. +// OperationStatus is one row of a published coverage table. NoteKey names the +// shared explanation behind the row's status, where one is declared. type OperationStatus struct { Operation string Status string - Note string + NoteKey string } // ImplementedPercent is the share of modelled operations bound to a real @@ -51,18 +53,18 @@ func (c OperationCoverage) ImplementedPercent() float64 { // followed by the registered operations the pinned model does not describe. // // notApplicable declares operations the platform will never serve, mapped to -// the reason why. A refusing handler is the same fact reached mechanically, so -// both publish as StatusNotApplicable; the declaration only adds the reason. +// the note key explaining why. A refusing handler is the same fact reached +// mechanically, so both publish as StatusNotApplicable. func (c OperationCoverage) OperationStatuses(notApplicable map[string]string) ([]OperationStatus, error) { registered := toSet(c.Registered) stubbed := toSet(c.Stubbed) unsupported := toSet(c.Unsupported) modelled := toSet(c.Modelled) - for operation, reason := range notApplicable { + for operation, noteKey := range notApplicable { switch { - case reason == "": - return nil, fmt.Errorf("awsmodel: %s operation %q is declared not applicable with no reason", c.Service, operation) + case noteKey == "": + return nil, fmt.Errorf("awsmodel: %s operation %q is declared not applicable with no note", c.Service, operation) case !modelled[operation]: return nil, fmt.Errorf("awsmodel: %s operation %q is declared not applicable but is not in the pinned model", c.Service, operation) case registered[operation] && !unsupported[operation]: @@ -81,8 +83,8 @@ func (c OperationCoverage) OperationStatuses(notApplicable map[string]string) ([ case registered[operation]: status = StatusImplemented } - if reason, ok := notApplicable[operation]; ok { - statuses = append(statuses, OperationStatus{Operation: operation, Status: StatusNotApplicable, Note: reason}) + if noteKey, ok := notApplicable[operation]; ok { + statuses = append(statuses, OperationStatus{Operation: operation, Status: StatusNotApplicable, NoteKey: noteKey}) continue } statuses = append(statuses, OperationStatus{Operation: operation, Status: status}) @@ -104,9 +106,14 @@ type PageMetadata struct { Description string `json:"description"` Tags []string `json:"tags"` - // NotApplicable maps an operation the platform will never serve to the - // reason why. Checked against the model and the dispatch tables at render, - // so a typo or a later implementation fails the build rather than lying. + // Notes are the shared explanations a page footnotes, keyed by a short + // name. One note covers every operation that shares a reason. + Notes map[string]string `json:"notes,omitempty"` + + // NotApplicable maps an operation the platform will never serve to the key + // of the note explaining why. Checked against the model, the notes and the + // dispatch tables at render, so a typo or a later implementation fails the + // build rather than publishing a claim that has quietly become false. NotApplicable map[string]string `json:"notApplicable,omitempty"` } @@ -182,6 +189,42 @@ func validatePage(owner string, page PageMetadata, slugs map[string]bool) error return nil } +// noteOrder returns the note keys in the order they are published. Sorted by +// key rather than by first use, so adding an operation cannot renumber a note +// that is already published. +func noteOrder(notes map[string]string) []string { + keys := make([]string, 0, len(notes)) + for key := range notes { + keys = append(keys, key) + } + sort.Strings(keys) + return keys +} + +// numberNotes assigns each note its published footnote number, rejecting a note +// nothing references and a reference to a note that does not exist. +func numberNotes(page PageMetadata) (map[string]int, error) { + referenced := map[string]bool{} + for operation, key := range page.NotApplicable { + if _, ok := page.Notes[key]; !ok { + return nil, fmt.Errorf("awsmodel: coverage page %s: operation %q references undefined note %q", page.Slug, operation, key) + } + referenced[key] = true + } + + numbering := make(map[string]int, len(page.Notes)) + for index, key := range noteOrder(page.Notes) { + if !referenced[key] { + return nil, fmt.Errorf("awsmodel: coverage page %s: note %q is never referenced", page.Slug, key) + } + if page.Notes[key] == "" { + return nil, fmt.Errorf("awsmodel: coverage page %s: note %q is empty", page.Slug, key) + } + numbering[key] = index + 1 + } + return numbering, nil +} + // RenderServicePage renders one publishable coverage page. intro is optional // hand-written prose emitted above the table; it may not open a new page // section, so its headings must be level three or deeper. @@ -203,7 +246,7 @@ func RenderServicePage(coverage OperationCoverage, pages PageSet, intro string) writeFrontmatter(&body, page, pages.Category) fmt.Fprintf(&body, "# %s\n\n## Overview\n\n", page.Title) - fmt.Fprintf(&body, "Spinifex implements **%d of the %d** operations (%.1f%%) in the %s `%s` API model.\n\n", + fmt.Fprintf(&body, "Spinifex implements **%d of the %d** operations (**%.1f%%**) in the %s `%s` API model.\n\n", len(coverage.Implemented), len(coverage.Modelled), coverage.ImplementedPercent(), page.Name, coverage.APIVersion) if intro != "" { @@ -214,18 +257,25 @@ func RenderServicePage(coverage OperationCoverage, pages PageSet, intro string) if err != nil { return "", err } - - body.WriteString("### Operations\n\n") - if len(page.NotApplicable) == 0 { - body.WriteString("| Operation | Status |\n|---|---|\n") - for _, status := range statuses { - fmt.Fprintf(&body, "| `%s` | %s |\n", status.Operation, status.Status) - } - return body.String(), nil + numbering, err := numberNotes(page) + if err != nil { + return "", err } - body.WriteString("| Operation | Status | Notes |\n|---|---|---|\n") + + body.WriteString("### Operations\n\n| Operation | Status |\n|---|---|\n") for _, status := range statuses { - fmt.Fprintf(&body, "| `%s` | %s | %s |\n", status.Operation, status.Status, status.Note) + if number, ok := numbering[status.NoteKey]; ok { + fmt.Fprintf(&body, "| `%s` | %s [%d](#notes) |\n", status.Operation, status.Status, number) + continue + } + fmt.Fprintf(&body, "| `%s` | %s |\n", status.Operation, status.Status) + } + + if len(numbering) > 0 { + body.WriteString("\n### Notes\n\n") + for index, key := range noteOrder(page.Notes) { + fmt.Fprintf(&body, "%d. %s\n", index+1, page.Notes[key]) + } } return body.String(), nil } @@ -240,14 +290,14 @@ func RenderIndexPage(coverages []OperationCoverage, pages PageSet, intro string) writeFrontmatter(&body, pages.Index, pages.Category) fmt.Fprintf(&body, "# %s\n\n## Overview\n\n", pages.Index.Title) fmt.Fprintf(&body, "Spinifex serves the AWS APIs below. Every page counts the operations in the pinned `aws-sdk-go %s` `api-2.json` model for its service and reports, operation by operation, whether Spinifex implements it.\n\n", SourceSDKVersion) - body.WriteString("| Service | API version | Implemented | Modelled | Coverage |\n|---|---|---:|---:|---:|\n") + body.WriteString("| Service | Implemented | Modelled | Coverage |\n|---|---:|---:|---:|\n") for _, coverage := range sortedCoverages(coverages) { page, ok := pages.Services[coverage.Service] if !ok { continue } - fmt.Fprintf(&body, "| [%s](/docs/%s) | %s | %d | %d | %.1f%% |\n", - page.Name, page.Slug, coverage.APIVersion, len(coverage.Implemented), len(coverage.Modelled), coverage.ImplementedPercent()) + fmt.Fprintf(&body, "| [%s](/docs/%s) | %d | %d | %.1f%% |\n", + page.Name, page.Slug, len(coverage.Implemented), len(coverage.Modelled), coverage.ImplementedPercent()) } if intro != "" { diff --git a/internal/awsmodel/page_test.go b/internal/awsmodel/page_test.go index 86457f94a..532d40f40 100644 --- a/internal/awsmodel/page_test.go +++ b/internal/awsmodel/page_test.go @@ -77,7 +77,7 @@ func TestRenderServicePageCarriesEveryStatus(t *testing.T) { `category: "Coverage"`, "sections:\n - overview\n", "# STS API Coverage\n\n## Overview\n", - "Spinifex implements **1 of the 8** operations (12.5%) in the STS `2011-06-15` API model.", + "Spinifex implements **1 of the 8** operations (**12.5%**) in the STS `2011-06-15` API model.", "### Scope\n\nHand-written prose.", "| `AssumeRole` | " + StatusImplemented + " |", "| `GetSessionToken` | " + StatusStub + " |", @@ -164,13 +164,13 @@ func TestOperationStatusesRejectsStaleNotApplicableClaims(t *testing.T) { } } -func TestOperationStatusesPublishesDeclaredReasons(t *testing.T) { +func TestOperationStatusesCarriesTheNoteKey(t *testing.T) { coverage, err := CompareOperations(STS, DispatchInventory{Registered: []string{"AssumeRole"}}) if err != nil { t.Fatal(err) } - statuses, err := coverage.OperationStatuses(map[string]string{"GetFederationToken": "No federation broker."}) + statuses, err := coverage.OperationStatuses(map[string]string{"GetFederationToken": "no-broker"}) if err != nil { t.Fatal(err) } @@ -178,14 +178,77 @@ func TestOperationStatusesPublishesDeclaredReasons(t *testing.T) { if status.Operation != "GetFederationToken" { continue } - if status.Status != StatusNotApplicable || status.Note != "No federation broker." { - t.Fatalf("status = %q, note = %q", status.Status, status.Note) + if status.Status != StatusNotApplicable || status.NoteKey != "no-broker" { + t.Fatalf("status = %q, note key = %q", status.Status, status.NoteKey) } return } t.Fatal("declared operation is missing from the table") } +// A footnote reused across operations is written once, and both directions of +// the reference are checked so neither side can rot. +func TestRenderServicePageFootnotesSharedNotes(t *testing.T) { + pages := testPageSet(t) + iam := pages.Services[IAM] + if len(iam.Notes) == 0 { + t.Skip("no notes are declared for IAM") + } + coverage, err := CompareOperations(IAM, DispatchInventory{Registered: []string{"CreateUser"}}) + if err != nil { + t.Fatal(err) + } + + page, err := RenderServicePage(coverage, pages, "") + if err != nil { + t.Fatal(err) + } + if !strings.Contains(page, "\n### Notes\n\n1. ") { + t.Errorf("page has no numbered notes section:\n%s", page) + } + if !strings.Contains(page, "| `UploadSSHPublicKey` | "+StatusNotApplicable+" [") { + t.Errorf("a declared operation carries no footnote reference:\n%s", page) + } + for _, text := range iam.Notes { + if strings.Count(page, text) != 1 { + t.Errorf("note %q is not written exactly once", text) + } + } +} + +func TestRenderServicePageRejectsBrokenNoteReferences(t *testing.T) { + pages := testPageSet(t) + coverage, err := CompareOperations(STS, DispatchInventory{Registered: []string{"AssumeRole"}}) + if err != nil { + t.Fatal(err) + } + sts := pages.Services[STS] + + for name, mutate := range map[string]func(*PageMetadata){ + "undefined note": func(p *PageMetadata) { + p.NotApplicable = map[string]string{"GetFederationToken": "nonexistent"} + }, + "unreferenced note": func(p *PageMetadata) { + p.Notes = map[string]string{"orphan": "Nothing points at this."} + }, + "empty note": func(p *PageMetadata) { + p.Notes = map[string]string{"blank": ""} + p.NotApplicable = map[string]string{"GetFederationToken": "blank"} + }, + } { + t.Run(name, func(t *testing.T) { + broken := sts + mutate(&broken) + pages.Services[STS] = broken + defer func() { pages.Services[STS] = sts }() + + if _, err := RenderServicePage(coverage, pages, ""); err == nil { + t.Fatal("RenderServicePage accepted a broken note reference") + } + }) + } +} + // An opaque service has no dispatch table to count, so publishing a page for it // would report 0% where the truth is that the surface is served elsewhere. func TestRenderServicePageRefusesOpaqueCoverage(t *testing.T) {