Moto

raw JSON →
5.1.22 verified Tue May 12 auth: no python install: verified quickstart: verified

Moto is a Python library that allows developers to easily mock AWS services for testing purposes. It intercepts Boto3 calls and routes them to an in-memory mock, simulating AWS API behavior locally without actual AWS interaction. The current version is 5.1.22, and it typically sees new releases every 1-2 weeks, ensuring continuous updates for AWS service support.

pip install moto[all]
error ModuleNotFoundError: No module named 'moto'
cause The 'moto' library is not installed in the Python environment where the code is being run.
fix
Install the moto library using pip. If you need specific AWS service mocks, install them with extras (e.g., [all] or [s3,dynamodb]).
pip install moto[all]
# Or for specific services:
pip install moto[s3,dynamodb]
error ImportError: cannot import name 'mock_s3' from 'moto'
cause This error typically occurs when upgrading Moto to version 5.0 or later, as the individual service decorators (like `mock_s3`, `mock_dynamodb2`) have been replaced by a single `@mock_aws` decorator.
fix
Replace individual service decorators with the unified @mock_aws decorator.
from moto import mock_aws

@mock_aws
def test_my_aws_function():
    # Your test code here
    pass
error botocore.exceptions.NoCredentialsError: Unable to locate credentials
cause This error happens when `boto3` attempts to make an AWS call but cannot find valid credentials, often because the `moto` mock was not correctly activated before the `boto3` client/resource was initialized, or no dummy credentials were provided.
fix
Ensure that the moto decorator (@mock_aws) or context manager (with mock_aws():) is applied *before* any boto3 clients or resources are created in your test. Also, it's good practice to set dummy AWS credentials for tests.
import os
import boto3
from moto import mock_aws

# Set dummy credentials (optional, but good practice)
os.environ['AWS_ACCESS_KEY_ID'] = 'testing'
os.environ['AWS_SECRET_ACCESS_KEY'] = 'testing'
os.environ['AWS_SECURITY_TOKEN'] = 'testing'
os.environ['AWS_SESSION_TOKEN'] = 'testing'
os.environ['AWS_DEFAULT_REGION'] = 'us-east-1'

@mock_aws
def test_s3_operation():
    s3_client = boto3.client('s3', region_name='us-east-1')
    # Your S3 operations
    s3_client.create_bucket(Bucket='my-test-bucket')
error botocore.errorfactory.NoSuchBucket: An error occurred (NoSuchBucket) when calling the ListObjects operation: The specified bucket does not exist.
cause Within a `moto` mock, AWS resources like S3 buckets or DynamoDB tables do not automatically exist; they must be explicitly created in the mock environment before your code attempts to access them.
fix
Create the necessary AWS resource (e.g., S3 bucket, DynamoDB table) within your moto decorated test function or fixture before making calls to it.
import boto3
from moto import mock_aws

@mock_aws
def test_list_s3_buckets():
    s3_client = boto3.client('s3', region_name='us-east-1')
    s3_client.create_bucket(Bucket='my-test-bucket') # Create the bucket in the mock environment
    response = s3_client.list_buckets()
    assert 'my-test-bucket' in [b['Name'] for b in response['Buckets']]
breaking Moto v5.x introduced a significant breaking change: all individual service decorators (e.g., `@mock_s3`, `@mock_dynamodb`, `@mock_sqs`) have been removed and replaced by a single, unified `@mock_aws` decorator.
fix Replace specific decorators like `@mock_s3` with `@mock_aws`. If you need to specify specific services for the mock, pass them as arguments to `@mock_aws` (though often not necessary for basic usage, it mocks all by default). For example: `@mock_aws(config={'s3': {'use_docker': False}})`.
gotcha Boto3 clients/resources must be created *after* the `moto` mock has been established. If a Boto3 client is initialized globally (e.g., at the module level) before the `@mock_aws` decorator or context manager is activated, `moto` will not intercept those calls, and they may hit real AWS.
fix Create `boto3` clients/resources inside the `@mock_aws` decorated function, within the `with mock_aws():` block, or within a `setUp` method of a `unittest.TestCase` where the class is decorated. For Pytest, ensure fixtures that create clients are decorated or called within the mock's scope. Using local imports for modules that create `boto3` clients can also help.
gotcha Always specify `region_name` explicitly when creating `boto3` clients and resources (e.g., `boto3.client('s3', region_name='us-east-1')`). Moto can sometimes exhibit inconsistent behavior or default to unexpected regions if `region_name` is omitted, potentially leading to hard-to-debug test failures.
fix Include `region_name='your-desired-region'` in all `boto3.client()` and `boto3.resource()` calls within your mocked tests.
breaking In Moto v3.x, the behavior of class decorators changed: the mock state is now reset before *every* test method within a decorated class. Previously, the state was global and shared across methods in the same class.
fix If your tests relied on shared state between methods in a class, refactor them to ensure each test method sets up its required state independently, or use alternative mechanisms (e.g., pytest fixtures with appropriate scope) to manage state if shared setup is truly necessary.
gotcha For Pytest users, ensure that any `boto3` client-creating fixtures are correctly integrated with Moto's mocking. If a fixture creates a client before `mock_aws` is active, it won't be mocked.
fix Decorate your pytest fixtures with `@mock_aws` if they provision AWS clients, or use the `mock_aws` context manager within the fixture's setup phase. Example: `@pytest.fixture @mock_aws def s3_client(): return boto3.client('s3', region_name='us-east-1')`.
gotcha Moto intercepts HTTP requests and requires dummy AWS credentials to be set (either via environment variables or `~/.aws/credentials`). Without them, `botocore` might attempt to resolve actual credentials or hit real AWS endpoints, leading to errors or unintended side effects.
fix Before running tests, set environment variables like `AWS_ACCESS_KEY_ID=testing`, `AWS_SECRET_ACCESS_KEY=testing`, `AWS_SECURITY_TOKEN=testing`, `AWS_SESSION_TOKEN=testing`, and `AWS_DEFAULT_REGION=us-east-1`. These can be exported in your test runner or set programmatically.
pip install 'moto[s3,dynamodb]'
python os / libc variant status wheel install import disk
3.10 alpine (musl) s3,dynamodb wheel - 1.62s 116.2M
3.10 alpine (musl) all wheel - 1.69s 291.4M
3.10 alpine (musl) s3,dynamodb - - 1.76s 115.5M
3.10 alpine (musl) all - - 1.74s 285.8M
3.10 slim (glibc) s3,dynamodb wheel 8.7s 1.18s 117M
3.10 slim (glibc) all wheel 23.0s 1.19s 292M
3.10 slim (glibc) s3,dynamodb - - 1.26s 117M
3.10 slim (glibc) all - - 1.24s 286M
3.11 alpine (musl) s3,dynamodb wheel - 2.04s 125.6M
3.11 alpine (musl) all wheel - 2.10s 333.5M
3.11 alpine (musl) s3,dynamodb - - 2.42s 125.2M
3.11 alpine (musl) all - - 2.43s 328.4M
3.11 slim (glibc) s3,dynamodb wheel 8.3s 1.79s 127M
3.11 slim (glibc) all wheel 22.0s 2.09s 334M
3.11 slim (glibc) s3,dynamodb - - 1.88s 126M
3.11 slim (glibc) all - - 1.92s 329M
3.12 alpine (musl) s3,dynamodb wheel - 2.10s 115.6M
3.12 alpine (musl) all wheel - 2.20s 324.6M
3.12 alpine (musl) s3,dynamodb - - 2.34s 115.1M
3.12 alpine (musl) all - - 2.35s 319.4M
3.12 slim (glibc) s3,dynamodb wheel 7.6s 2.19s 117M
3.12 slim (glibc) all wheel 21.0s 2.29s 325M
3.12 slim (glibc) s3,dynamodb - - 2.23s 116M
3.12 slim (glibc) all - - 2.41s 320M
3.13 alpine (musl) s3,dynamodb wheel - 2.04s 115.5M
3.13 alpine (musl) all wheel - 2.12s 323.9M
3.13 alpine (musl) s3,dynamodb - - 2.28s 114.9M
3.13 alpine (musl) all - - 2.35s 318.7M
3.13 slim (glibc) s3,dynamodb wheel 7.0s 1.93s 117M
3.13 slim (glibc) all wheel 20.0s 2.17s 324M
3.13 slim (glibc) s3,dynamodb - - 2.38s 116M
3.13 slim (glibc) all - - 2.30s 319M
3.9 alpine (musl) s3,dynamodb wheel - 1.55s 116.8M
3.9 alpine (musl) all wheel - 1.62s 285.8M
3.9 alpine (musl) s3,dynamodb - - 1.63s 115.7M
3.9 alpine (musl) all - - 1.64s 284.7M
3.9 slim (glibc) s3,dynamodb wheel 10.4s 1.54s 118M
3.9 slim (glibc) all wheel 27.1s 1.49s 286M
3.9 slim (glibc) s3,dynamodb - - 1.35s 117M
3.9 slim (glibc) all - - 1.36s 285M

This quickstart demonstrates how to mock an S3 service using the `@mock_aws` decorator. It creates a Boto3 S3 client within the mocked context, creates a bucket, and then verifies its existence, all without interacting with actual AWS infrastructure. Dummy AWS credentials are set to prevent botocore from attempting real AWS calls.

import boto3
from moto import mock_aws
import os

@mock_aws
def test_s3_bucket_creation():
    # Ensure dummy AWS credentials are set for botocore to not attempt real calls
    os.environ['AWS_ACCESS_KEY_ID'] = 'testing'
    os.environ['AWS_SECRET_ACCESS_KEY'] = 'testing'
    os.environ['AWS_SECURITY_TOKEN'] = 'testing'
    os.environ['AWS_SESSION_TOKEN'] = 'testing'
    os.environ['AWS_DEFAULT_REGION'] = 'us-east-1'

    s3_client = boto3.client('s3', region_name='us-east-1')
    bucket_name = 'my-test-bucket-123'
    
    # Create a bucket in the mocked AWS environment
    s3_client.create_bucket(Bucket=bucket_name)
    
    # List buckets and verify the new bucket exists
    response = s3_client.list_buckets()
    buckets = [b['Name'] for b in response['Buckets']]
    
    assert bucket_name in buckets
    print(f"Successfully created and verified bucket: {bucket_name}")

if __name__ == '__main__':
    test_s3_bucket_creation()