I am using FastApI and dependency-injetor below is the project structure
-app - api/v1/endpoints - repository - service main.py
When I am injecting the dependencies to the endpoints I always gets Provide object not actual class object due to this code always throws
AttributeError: 'Provide' object has no attribute 'test' However if I inject the dependencies in normal function it works well.
Here is below code snippet that I am using -
users.py as endpoint
@router.get('/u/{name}/{id}')
def add_user(name:str, id:int, strategy_service:StrategyService = Depends(Provide[Container.strategy_service])):
strategy_service.test(Test(name, id))
Container - class
class Container(DeclarativeContainer):
#Define configuration
config = providers.Configuration()
#Database
db = providers.Singleton(Database, db_url=config.db_url)
#All the repositories Configuration
strategy_repository = providers.Factory(
StrategyRepository,
session_factory = db.provided.session
)
#All the services configured
strategy_service = providers.Factory(
StrategyService,
strategy_repository = strategy_repository
)
main.py
def create_app() -> FastAPI:
container = Container()
container.config.from_yaml('../config.yml')
container.wire(packages=[api])
app = FastAPI()
app.container = container
#Here configure all your routes
app.include_router(api_v1.router, prefix='/api/v1')
#Return the final app
return app
app = create_app()
if __name__ == '__main__':
#We can get this host and port number from config files
uvicorn.run(app, host = '127.0.0.1', port = 8080)
Getting this exception -
result = self.fn(*self.args, **self.kwargs) File "/Users/manpr06/driveE/AlgoBot/algotradersbot-service/app/api/v1/endpoints/users.py", line 21, in add_user strategy_service.test(Test(name, id)) AttributeError: 'Provide' object has no attribute 'test'
Can someone please help one this?
Seems in your main.py, your wiring configuration is wrong,
def create_app() -> FastAPI:
container = Container()
container.config.from_yaml('../config.yml')
container.wire(packages=[api])
you need to write the correct path like this:
container.wire(packages=["api.v1.endpoints"])
FYI:
I faced the same issue but resolved with above way, let me share the summary of my codes:
├── core
│ └── di
│ └── __init__.py
└── handler
└── cluster
└── v1
└── cluster.py
__init__.py
class Container(containers.DeclarativeContainer):
wiring_config = containers.WiringConfiguration(modules=["handler.cluster.v1.cluster"])
cluster_repo = providers.Factory(***)
cluster_service = providers.Factory(
ClusterService,
cluster_repo=cluster_repo
)
cluster.py
cluster_router = APIRouter()
@cluster_router.get(
"/",
response_model=List[ClusterSummaryResponse],
responses={"404": {"model": ExceptionResponseSchema}},
summary="List Cluster",
)
@inject
async def list_cluster(cluster_service: ClusterService = Depends(Provide[Container.cluster_service]), type = None):
return await cluster_service.list(type=type)
You need setup wiring
class Container(DeclarativeContainer):
wiring_config = containers.WiringConfiguration(
modules=["src.routes.v1.users"] # or "users" in your case
)
# Define configuration
config = providers.Configuration()
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With