A small project with bash scripts for testing S3 API compability:
test_put_if_match.sh- testsIf-Matchtest_put_if_not_match.sh- testsIf-None-Matchtest_list_order.sh- tests globalLISTorder across pagination for WAL keystest_list_perf.sh- uploads many objects in parallel and measures 3 plainLISTcalls speedtest_put_perf.sh- uploads many small objects in parallel and measures average PUT time per filetest_put_perf_large.sh- sequentially uploads5x10 MiBand5x100 MiBfiles and measures average upload speed
Works with both AWS S3 and S3-compatible providers (MinIO, Ceph RGW, etc.).
awsCLI v2- S3 access (access key, secret key, region)
AWS CLI installation:
- Official install guide (all platforms): https://docs.aws.amazon.com/cli/latest/userguide/getting-started-install.html
- Linux: https://docs.aws.amazon.com/cli/latest/userguide/getting-started-install.html#cliv2-linux-install
- macOS: https://docs.aws.amazon.com/cli/latest/userguide/getting-started-install.html#cliv2-mac-install
- Windows: https://docs.aws.amazon.com/cli/latest/userguide/getting-started-install.html#cliv2-windows-install
- Create
.envfrom the example:
cp .env.example .env- Fill required fields in
.env:
AWS_ACCESS_KEY_IDAWS_SECRET_ACCESS_KEYAWS_DEFAULT_REGION
ENDPOINT_URL:
- keep empty for AWS S3
- set URL for S3-compatible service, for example
http://127.0.0.1:9000
Using make:
make test-if-match
make test-if-not-match
make test-list-order
make test-list-perf
make test-put-perf
make test-put-perf-large
make s3-delete-bucketOr directly:
bash test_put_if_match.sh
bash test_put_if_not_match.sh
bash test_list_order.sh
bash test_list_perf.sh
bash test_put_perf.sh
bash test_put_perf_large.sh
bash ./remove_bucket.shmake s3-delete-bucket or direct bash ./remove_bucket.sh deletes a bucket in 4 steps:
- removes current objects
- removes all object versions and delete markers
- aborts unfinished multipart uploads
- deletes the bucket itself
This is safer than plain aws s3 rb --force, because versioned buckets and unfinished multipart uploads often block bucket deletion.
test_list_order.sh creates WAL objects with lexicographic keys:
wal/0000001...wal/0000201
Then it lists objects with page size 100 (list-objects-v2 --max-keys 100) and checks:
- pagination is real (
page_count >= 2) - first key on each next page is strictly greater than the previous page last key
- global last key from paginated traversal is exactly
wal/0000201
This verifies that the last WAL key is found globally across pages, not only inside one page.
test_list_perf.sh loads a large amount of objects (default: 10000) with parallel PUT (default workers: 16) and then runs 3 regular LIST requests (list-objects-v2 without pagination loop).
If you want to measure only LIST on existing data, set SKIP_PUT_STAGE=true.
For each LIST run it prints:
- listed objects count from the single response page
- elapsed time in seconds
- speed in objects/sec
IsTruncatedflag
This helps detect if LIST latency grows noticeably when bucket prefix contains many objects.
test_put_perf.sh uploads many small objects in parallel and prints average PUT time per file.
test_put_perf_large.sh runs two sequential series:
5files by10 MiB5files by100 MiB
For each series it prints per-file progress, average time per file and average throughput in MiB/s. Payload files are generated once using sparse zero-filled files when supported, which is the fastest local preparation path.
See in .env.example.
Key variables for list tests:
CATALOG_PREFIXOBJECTS_COUNTOBJECT_KEY_WIDTHPUT_PARALLELISMLIST_RUNSSKIP_PUT_STAGECREATE_BUCKETCLEANUP_BUCKET