Container - InjectQ Documentation
Author: InjectQ Contributors
Description: Modern Python dependency injection library

Skip to content

# Container API

::: injectq.core.container

## Overview

The `InjectQ` container is the central component of the dependency injection system. It manages service registrations, resolves dependencies, and handles scope lifecycle.

## Basic Usage

    from injectq import InjectQ, inject

    # Create container
    container = InjectQ()

    # Register services
    container.bind(UserService, UserService).singleton()

    # Resolve services
    user_service = container.get(UserService)

## Container Methods

The container provides several methods for service management:

### Registration Methods

- `bind()` - Register a service binding
- `bind_instance()` - Register a specific instance
- `bind_factory()` - Register a factory function
- `install()` - Install a module

### Resolution Methods

- `get()` - Get service instance
- `get_optional()` - Get optional service instance
- `try_get()` - Try to get service with fallback

### Scope Management

- `create_scope()` - Create new scope
- `create_async_scope()` - Create async scope
- `with_scope()` - Execute with temporary scope

## Configuration Options

The container can be configured with various options:

    container = InjectQ(
        auto_wire=True,          # Enable automatic wiring
        validate_bindings=True,   # Validate bindings on registration
        thread_safe=True         # Enable thread safety
    )

## Advanced Features

### Custom Resolvers

    # Register custom resolver
    container.set_resolver(CustomResolver())

### Event Hooks

    # Register lifecycle hooks
    container.on_instance_created(lambda instance: print(f"Created: {instance}"))
    container.on_scope_created(lambda scope: print(f"Scope created: {scope}"))

### Validation

    # Validate container configuration
    validation_results = container.validate()
    for error in validation_results.errors:
        print(f"Validation error: {error}")

## Thread Safety

The container is thread-safe by default when configured appropriately:

    # Thread-safe container
    container = InjectQ(thread_safe=True)

    # Use from multiple threads
    import threading

    def worker():
        service = container.get(MyService)
        # Use service...

    threads = [threading.Thread(target=worker) for _ in range(10)]
    for thread in threads:
        thread.start()

## Performance Considerations

- Singleton services are resolved once and cached
- Scoped services are cached within their scope
- Transient services are created fresh each time
- Use `get_optional()` for services that might not be registered

## Error Handling

The container raises specific exceptions for different error conditions:

    try:
        service = container.get(UnregisteredService)
    except ServiceNotFoundError as e:
        print(f"Service not found: {e}")

    try:
        container.bind(ServiceA, ServiceA)
        container.bind(ServiceB, ServiceB)  # Circular dependency
        service = container.get(ServiceA)
    except CircularDependencyError as e:
        print(f"Circular dependency: {e}")