fizz.today

s3 is porcelain, s3api is the real service

I always assumed aws s3 and aws s3api were two different APIs to the same storage system — one high-level, one low-level. That’s how the CLI presents them. Two commands, two help pages, two sets of subcommands.

While building a replacement for the AWS CLI completer, I had to map every CLI service name to its botocore data directory. Botocore is the Python SDK’s data layer — every AWS service has a directory under botocore/data/ with a service-2.json containing the full API model.

There is no s3api directory. There is exactly one s3 directory.

aws s3api is the CLI namespace that exposes botocore’s s3 operations directly — 102 raw API verbs like put-object, list-buckets, get-bucket-acl. These are the actual S3 API calls, one verb per operation, kebab-cased from botocore’s PascalCase names.

aws s3 is porcelain. Nine hand-written commands:

cp  ls  mb  mv  presign  rb  rm  sync  website

Each one wraps multiple s3api calls. s3 cp handles multipart uploads, retries, progress bars, and parallel transfers. s3 sync does diffing, checksums, and delete tracking. These aren’t in botocore at all — they live in awscli/customizations/s3/, a few thousand lines of Python that sit on top of the API.

The two namespaces were always one service model with a friendlier doorman. s3api is the plumbing. s3 is the porcelain.

The other aliases

s3api is not the only CLI service name with no botocore directory. There are nine total. Three are aliases to different botocore directories:

CLI nameBotocore directory
s3apis3
configserviceconfig
ddbdynamodb

The other six are pure CLI inventions — configure, deploy, history, login, logout, cli-dev. No botocore model behind them at all.

The entire delta between botocore’s API contract and the CLI’s user-facing vocabulary fits in a 12-line JSON file.

#aws #cli #platformengineering