简体   繁体   English

如何构建调用其他 API 的 FastAPI 应用程序

[英]How to structure a FastAPI app that calls other API's

I've seen this post: What are the best practices for structuring a FastAPI project?我看过这篇文章: What are the best practices for structuring a FastAPI project?

Which lays out a good baseline, but I was wondering where calling 3rd party API's would fall into place.这是一个很好的基线,但我想知道调用第 3 方 API 的位置在哪里。 Would creating a services folder inside the v1 folder here make sense.在此处的 v1 文件夹中创建一个服务文件夹是否有意义。 And then throwing modules in there for dealing with 3rd party API's.然后将模块放入其中以处理第 3 方 API。

There isn't really the best approach.没有真正最好的方法。 It all depends on your use case and individual preferences/practices.这完全取决于您的用例和个人偏好/实践。 With that said, I can give you a few options:话虽如此,我可以给你几个选择:

Implementation within the app应用内实现

Develop a class, method, or whatever you might need in a separate submodule inside your application root directory.在应用程序根目录内的单独子模块中开发 class、方法或您可能需要的任何内容。 Name this submodule however you'd like (services, utils, 3rdparty, etc.).根据需要命名此子模块(服务、实用程序、第 3 方等)。 In the end, it doesn't really matter that much as long it's a meaningful name to you and other people involved in the project.最后,只要它对您和参与该项目的其他人来说是一个有意义的名称,它并没有那么重要。

If this implementation is static, then you're good to go and can utilize it inside a particular controller by just doing a simple import.如果此实现是 static,那么您可以使用 go,只需执行简单的导入即可在特定的 controller 中使用它。

If, on the other hand, you'll require to create a class object instance that should be accessible across the whole application, and you don't want to create a new object each time you'll execute it in the controller (For instance, you wouldn't want to have X HTTP client sessions opened).另一方面,如果您需要创建一个 class object 实例,它应该可以在整个应用程序中访问,并且您不希望每次在 controller 中执行它时都创建一个新的 object(例如,您不希望打开 X HTTP 客户端会话)。 Then FastAPI event handlers can come in handy:那么FastAPI 事件处理程序就可以派上用场了:

You can define event handlers (functions) that need to be executed before the application starts up, or when the application is shutting down.您可以定义需要在应用程序启动之前或应用程序关闭时执行的事件处理程序(函数)。 These functions can be declared with async def or normal def.这些函数可以用 async def 或 normal def 声明。

To give you a better example in my fastapi-mvc-template on startup event, I'm creating Redis and Aiohttp class object instance:为了在我的fastapi-mvc-template启动事件中给你一个更好的例子,我创建了 Redis 和 Aiohttp class object 实例:

async def on_startup():
    RedisClient.open_redis_client()
    AiohttpClient.get_aiohttp_client()


async def on_shutdown():
    await RedisClient.close_redis_client()
    await AiohttpClient.close_aiohttp_client()

which then can be used inside any controller without the need of creating them each time API method gets called:然后可以在任何 controller 中使用,而无需在每次调用 API 方法时都创建它们:

from fastapi_mvc_template.app.utils.redis import RedisClient
from fastapi_mvc_template.app.utils.aiohttp_client import AiohttpClient

response = RedisClient.get("Key")
response = AiohttpClient.get("http://foo.bar")

Separate package单独package

If the implementation for dealing with 3rd party APIs is bigger than a few files/classes.如果用于处理 3rd 方 API 的实现大于几个文件/类。 Then maybe it's worth considering writing it as a separate Python package, or using 3rd party implementation for your language, if there is any.那么也许值得考虑将其作为单独的 Python package 编写,或者使用适用于您的语言的第 3 方实现(如果有的话)。 However, then you should be careful with this dependency version in requirements.但是,您应该在需求中注意这个依赖版本。 Ideally hardcoded or locked to patch version (ex. 1.1.x).理想情况下硬编码或锁定到补丁版本(例如 1.1.x)。

Remote Procedure Call远程过程调用

IMHO an API calling another API may not be the best approach.恕我直言,一个 API 调用另一个 API 可能不是最好的方法。 Each time you implement a change to an API, you should version it for backward compatibility sake.每次对 API 进行更改时,为了向后兼容,您应该对其进行版本控制。 I'd reckon 3rd party API providers will do the same as they improve theirs.我估计第 3 方 API 供应商会在改进他们的供应商时做同样的事情。 And now, if you start to grow and scale rapidly, you might end up with a compatibility matrix web so complex that even spiderman would get a headache:).而现在,如果你开始快速增长和扩展,你可能会得到一个兼容性矩阵 web ,它非常复杂,甚至蜘蛛侠都会头疼:)。

A what is called Remote Procedure Call (RPC) + protocol buffers might be a better approach.所谓的远程过程调用 (RPC) + 协议缓冲区可能是更好的方法。 There is currently one major framework in CNCF incubation : gRPC目前CNCF孵化的主要框架有一个: gRPC

Benefits of gRPC: gRPC 的好处:

  • Binary on the wire线上的二进制文件
  • Bi-directional streaming and integrated auth双向流和集成身份验证
  • High performance高性能
  • Works across languages and platforms (built-in code generation)跨语言和平台工作(内置代码生成)
  • Simple service definition and backward compatibility with using protocol buffers简单的服务定义和使用协议缓冲区的向后兼容性

Of course, 3rd party services may not provide that option.当然,第三方服务可能不提供该选项。 N.netheless, it's worth researching the topic since its benefits and increasing popularity nowadays. N.netheless,值得研究这个话题,因为它的好处和现在越来越受欢迎。

暂无
暂无

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

相关问题 FastApi 与其他 Api 通信 - FastApi communication with other Api 如何在 FastAPI 的同一应用程序中从不同的 API 调用 API? - How to call an API from a different API in the same app in FastAPI? 是什么破坏了 FastAPI 的 Swagger UI? - 它停止工作并在名为“default”的组下显示 API 调用 - What broke FastAPI's Swagger UI? - It stopped working and shows API calls under a group named “default” 如何以 json 格式获取我的 fastAPI 应用程序的控制台日志,具有不同的结构和不同的字段? - How do I get my fastAPI application's console log in json format with a different structure and different fields? FastAPI 以串行方式而不是并行方式运行 api 调用 - FastAPI runs api-calls in serial instead of parallel fashion 如何在 fastapi 中从另一个 api 调用一个 api? - How to call an api from another api in fastapi? 如何将变量从 FastAPI 传递到其他 class - How to pass variable from FastAPI to other class 如何从我的 FastAPI 应用程序向另一个站点 (API) 发送 HTTP 请求? - How can I send an HTTP request from my FastAPI app to another site (API)? 如何使 Pydantic 的 BaseModel 接受 fastapi 应用程序中的一些特殊情况输入类型 - How to make Pydantic's BaseModel accept some special case input types in fastapi app Fastapi 如何使用 sqlalchemy 管理对数据库的并发调用 - How does Fastapi manage concurrent calls to the database with sqlalchemy
 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM