专业编程教程与实战项目分享平台

网站首页 > 技术文章 正文

老司机教你构建Python微服务

ins518 2024-09-16 21:32:51 技术文章 64 ℃ 0 评论

前面为大家剖析了为什么微服务越来越受到企业的青睐。在微服务的框架选型上,我们最终锁定了FastAPI——一个先进、快速的、基于Python 3.9+ 的web框架。今天,我们就来亲手搭建一个FastAPI微服务!

在本章中,我们将深入研究如何使用FastAPI构建自己的Python微服务。FastAPI是一个快速,先进且易于使用的Web框架,它可以帮助您轻松地构建高性能的API和微服务。无论是创建简单的RESTful API还是构建复杂的Web应用程序,FastAPI都是一个强大的工具。如图4-1所示,思维导图显示的是构建Python微服务的基础步骤

如上图所见,本章分为以下四个主要部分,每个部分都是构建Python微服务的关键步骤。现在让我们逐一介绍每个部分,从快速上手FastAPI开始。

1 快速上手FastAPI

那么,怎样才能走上使用FastAPI的正轨呢?其实,和你想的一样简单。

首先,我们得确保机器上已经有了Python和pip环境。还没准备好环境的小伙伴可以参考第三章的内容。

准备好了?那就动手吧!

1.1 安装FastAPI

打开终端或命令行,我们来安装FastAPI。键入如下指令,轻轻一敲回车键,整个宇宙的能量都集中在这一刹那:

pip install fastapi

接下来,安装完FastAPI后,我们并没有完全准备好。一个Web框架还需要一个服务器来配合运行,这就像车没油怎么开?在FastAPI的世界里,我们常常使用一个叫做ASGI的伺服器,而其中的佼佼者就是uvicorn。

1.2 安装uvicorn

“uvicorn”是啥?简单说,它就像是FastAPI的点火器,能让我们的应用跑起来,速度还特别快。

那怎么安装它呢?一如既往的简单!

打开终端,然后键入下面的指令,这就是咱们的点火密钥:

pip install uvicorn

弄完这一切之前,我得提个重要的建议,这可是老司机的经验之谈哦!

你知道,Python中有个叫虚拟环境的东西,它就像是一个隔离的小盒子,能帮你避免各种版本和依赖的冲突。我这里强烈建议,在你开始安装上面的套件前,先弄一个虚拟环境出来。在这个隔离的环境里,你可以放心地装各种东西,不怕影响其他项目。

1.3 第一个FastAPI程序

安装依赖完毕之后,我们的FastAPI大门就打开了,心跳是不是加速了呢?来,跟着我一起迈出第一步!

首先,找到你最喜欢的代码编辑器,不知道选择哪个?那就试试VS Code吧,它简洁高效,非常受开发者喜爱。打开VS Code,然后创建一个新的Python文件,取个响亮的名字如“main.py”。

接着,在这个刚刚创建的“main.py”中,输入以下神奇的代码:

# main.py

from fastapi import FastAPI

app = FastAPI()

@app.get("/")
def read_root():
    return {"Hello": "FastAPI"}

看这段代码,是不是觉得眼前一片清新?其实,这只是一个FastAPI应用的"Hello, World!"版本。每次我们在编程世界中迈出新的一步,都从简单开始,逐步探索,最后达到精通。这段代码正体现了这样的哲理:所有看似复杂的大事,都从简单小事做起。

想看看这段代码的魔法吗?只要启动服务器,打开你的浏览器,访问应用的根目录网址( / ),你就会被迎接一个简洁而美丽的JSON格式回应,内容就是那句熟悉的问候:“Hello, FastAPI”。

好了,现在我们进入正题,如何将这段代码跑起来?答案就是利用uvicorn这个神奇的工具。拿起你的命令行大锤,敲入以下指令:

uvicorn main:app --reload

先停一停,我们来解密这段代码。

首先,“main”这个名字,不是随便来的哦,它其实应该对应你的Python文件的名字。接下来的“app”,是不是觉得有点眼熟?没错,那就是我们之前在文件中创建的FastAPI实例的名字,也就是那行简单又清晰的代码:app = FastAPI()。

再往后看,“--reload”,这个选项可谓是开发者的小助手。为什么呢?它的功能很简单但又非常强大:只要你修改了代码,服务器就会自动重新加载。这样,你可以马上看到自己代码的效果,非常适合开发的时候使用。

好了,准备好了吗?输入这段指令,深呼吸,然后大胆地按下enter键。你会看到终端里弹出的消息,那就是你成功启动的证明。如图4-2所示,显示uvicorn启动服务成功

你的第一个FastAPI应用程序,就像一个新生婴儿,已经成功地跑起来啦!感觉是不是既兴奋又有点小骄傲?

不要等了,快打开浏览器,输入这个熟悉的地址:http://127.0.0.1:8000。如果你是个喜欢简单的人,也可以输入:http://localhost:8000。进去后,你将会看到你的第一个fastAPI程序了。如图4-3所示,浏览器启动第一个python微服务

哈哈,是不是觉得小菜一碟?这正是FastAPI想给你的感觉!它的设计初衷,就是为了让每一个像你我这样的开发者都能轻松掌握,并能快速地展开开发之旅。

不过,现在只是个开始。你可以像玩乐高一样,随心所欲地加入更多的路由,定义各种你需要的函数,使你的应用程序像一棵大树,不断生长、茁壮。

记住,编程就像绘画,只有想象力是你的界限。FastAPI为你准备了丰富的色彩,等你来描绘你心中的那幅画。接下来我们看看怎么创建一个GET API吧!

1.4 FastAPI的GET请求解析

GET请求,简单的名字背后其实藏着不少奥秘。在FastAPI中,我们可以将GET请求分成三大类来详细讲解。

  1. 路径参数(Path parameters):这就像是一套精确的坐标,能够精确地指向某个地点。
  2. 预定义值(Predefined values):可以想象成一本既定的菜单,用户从中选择他们想要的。
  3. 查询参数(Query parameters):好比是在搜索引擎里输入关键词,按照特定的需求获取信息。

接下来,我们会逐一深入了解这三种类型,并探索各自的使用方法

路径参数,一个“小小”的玩意,却蕴含着大大的能量!

首先,让我们明确一下:什么是路径参数?它有一个更“正式”的名字——URL参数。简单来说,这玩意就是可以直接嵌套在URL路径中的参数,让我们的应用更具灵活性。

以URL /items/{item_id} 为例,你看到大括号中的item_id了吗?没错,这就是路径参数的魔法。在FastAPI的世界里,你可以轻松地在路由函数中通过使用同名参数来接收这个值。

如果你还觉得有点悬而未决,没关系,我们一起看代码。想象一下,在我们之前创建的main.py文件中,增加以下这段代码:

@app.get("/mobot/{id}")
def get_mobot(id):
    return {"data":f"Mobot的 id 是:{id}"}

在这段代码里,咱们设定了一个路径参数,那就是 id。假如你在浏览器的地址栏中输入了下边这样的路径:「http://127.0.0.1:8000/mobot/5」,那接下来就会呈现出下面的效果,如图4-3-2所示,浏览器启动第一个python微服务。如图4-4所示,GET请求赋值

约束路径参数的类型

若想让使用者所输入的路径参数 id 属于某特定数据类型,该如何妥善应对?就拿前面的案例来瞧,假设咱只希望用户仅仅输数字当作路径参数,其他货色统统拒之门外,那咱可以这样去布置:

@app.get("/mobot/{id}")
def get_mobot(id: int):
    return {"data": f"Mobot的 id 是:{id}"}

由于我们在 id 后面添加了 int(id: int),代码会对输入的参数 id 进行审查。这里的 int 代表整数。换句话说,如果 id 不是整数的话,就会跳出错误警告。比如,如果我们在浏览器地址栏键入了「http://127.0.0.1:8000/mobot/fun」,那就会呈现出以下报错信息,如图4-5所示,约束类型判断

慎重安排路由函数的次序

当我们手头有一个函数,该把它安置在何处,就需要谨慎地加以考虑。以下面的例子来看,想象一下,咱们有这么一个函数叫作 get_mobots_all,那它最适合放在何处呢?也就是说,函数 index、get_mobots 以及 get_mobots_all 这三者,应当何种次序才能够得心应手?

@app.get("/mobot/all")
def get_mobots_all():
    return {"message": "所有的 mobots"}

纵然输入了 http://127.0.0.1:8000/ 和 http://127.0.0.1:8000/mobot/5 两者皆能得出正确之答案,但是,若我们尝试输入 http://127.0.0.1:8000/mobot/all,这时将会失之交臂、搞砸一地(如图4-6 所示)。因为在次序方面,路由函数 get_mobot 排在 get_mobots_all 前面,根据原则,应当会先执行/mobot/{id}的函数,其次才会跳至/mobot/all的函数处。

若将这三个函数的排列,微调为下文所示之序,如此,便可轻松地实现正常执行,如图4-7 所示

在这般情况之下,当输入 http://127.0.0.1:8000/mobot/all 时,就再也不会出现错误。这是因为当初原本安排在第 14 行的函数已然移步至第 19 行之处,从而使得 get_mobots_all 得以执行,照单全收。言归正传,便是说 mobot/all 这一条件得以满腔而行,得偿所愿,称心如意。

1.5 预定义值 Predefined values

这一特性允许你为路径参数或查询参数设定预定义的合法值。当用户端传送的请求中,其参数值不在你事先定义的合法值之列时,FastAPI 将会自动作出反应,回应一则错误,向客户端明确可接受哪些值。

要使用此功能,首先得引入 Enum,并借由 Enum(枚举)设立一个类。通过此类来界定咱们所需的预定义值。以下举个例子来说明:

接下来的 MobotType 类,承袭了 Enum,且明确规定了咱们所需要的三个预定值。

class MobotType(str, Enum):
    business = "business"
    story = "story"
    qa = "qa"

从上方的代码可一睹为快,内里精心确立了三种合法值:business、story、qa。随后,就如同前文在判断路径参数类型时所采取的手法一模一样,在路由函数 get_mobot_type 内,将 type 的验证方式设置为 MobotType 类的类型。

@app.get("/mobot/type/{type}")
def get_mobot_type(type: MobotType):
    return {"message": f"Mobot 的类型是 {type}"}

用户输入 MobotType 里的任何一个数值,都是实打实的、合法的。而函数 get_mobot_type 将在这种情况下被执行,如图4-8所示

不过,如果使用者的请求超越了 business、story、qa 这三个正当范围,那将会引来一道错误讯息,如图4-9所示

底下是这个部分的完整代码呢:

from enum import Enum

class MobotType(str, Enum):
    business = "business"
    story = "story"
    qa = "qa"


@app.get("/mobot/type/{type}")
def get_mobot_type(type: MobotType):
    return {"message": f"Mobot 的类型是 {type}"}

1.6 查询参数 Query parameters

所谓查询参数,即在URL中使用问号,并在问号( ? )之后,通过「与符号」( & )进行分隔的一系列键值( key=value )对。浏览的网址形态,看起来就像下边这模样:

http://127.0.0.1:8000/mobot/all?page=3&pageSize=10

要明确,查询参数本身并不算作路径的构成部分。以下列的代码为例,路径的部分是 /mobot/all(http://127.0.0.1:8000/mobot/all ),而 page 和 pageSize 就属于查询参数( page=2&pageSize=10 )。因此,可谓以「与符号」( & )为分界点,拓展而开。

@app.get("/mobot/all")
def get_mobots_all(page, pageSize):
    return {"message": f"所有的 mobots: 來自第 {page} 页, 总共有 {pageSize} 页"}

于是你就能够获得如图4-10所示的收获

再举个例子,在 URL /items?skip=0&limit=10 里,skip 和 limit 都是查询参数。在 FastAPI 应用程序的路由函数里,你可以以相同的名称作为参数来接收这些值。而在 FastAPI 的世界中,查询参数常被应用于诸如排序、过滤等诸多操作之中。

1.7 查询参数的验证方式:Optional

查询参数亦能以 Optional 来进行验证。首先,咱们引入 Optional 包裹:

from typing import Optional

接下来,在函数 get_mobots_all 内,将 pageSize 从原本的固定数值变更为 Optional。并且在 Optional 之后添加上数据类型,在此处,咱们采用了 int 并将其默认值赋值为 None,当url没传pageSize值时,默认为None。

@app.get("/mobot/all")
def get_mobots_all(page=1, pageSize: Optional[int] = None):
    return {"message": f"所有的 mobots: 來自第 {page} 页, 总共有 {pageSize} 页"}

1.8 Swagger UI

FastAPI 已经预装了 Swagger UI。Swagger UI 是一个用于构建、记录和测试 API 的开源工具,它供应一个互动式的界面,可以便利地查看和检验你的 API。当你运用 FastAPI 打造 API 的时候,只要打开你应用的根路径(比如 http://localhost:8000/docs,如图4-11所示),你就能够在浏览器中观赏 Swagger UI 界面,这样一来,你的 API 各个端点、参数和响应就会呈现在你眼前。这个界面不仅仅是一份文档,还是一个能够用来试验 API 的地方,因为你可以在这个界面上直接输入参数,发送请求,然后查看响应。总之,Swagger UI 是一个特别实用的工具,能够协助开发者更轻松地理解和与 API 进行互动。

随后,点开 /mobot/all,如图4-12所示。您将看到以下画面:

点击页面上的 "试一下" 按钮,便可投入测试之中。

只要在字段中输入数字(比如说10,如图4-13所示),您将能够获得准确之结果。

然而,若在 pageSize 的栏位输入字串(比如:abc),就会爆出错误来。故此,运用 Optional 亦能用来处理查询参数的验证。如图4-14所示

简而言之,就是使用 Optional 这把钥匙,能够让我们更好地验证查询参数的可靠性。

1.8 FastAPI的实际应用

通过之前的阐述,相信您对于FastAPI已经有了基本的理解。接下来,我们将深入探讨FastAPI在实际开发中的威力与用途。

首先,FastAPI的快速与简便特质使其在API开发领域表现出色。您可以迅速构建各种RESTful API,并且由于FastAPI具备自动生成文档的能力,API的管理和使用都变得非常方便。

而且,FastAPI还支持OAuth2认证、跨域请求等功能,为您的API增添了更多的安全性和可用性。此外,FastAPI出色的异步处理能力,使其在开发实时应用(如聊天室、游戏等)方面拥有巨大优势。您可以利用Python的async/await语法来编写API。

最后,值得一提的是,由于FastAPI采用了现代Python的类型提示,您的代码将更具可读性和可维护性。无论是团队协作还是长期项目,这都是非常宝贵的优势。

从基础特性到实际应用,FastAPI展现出惊人的优势。其简洁易懂的语法、高速的执行效率、自动生成的文档,以及对异步处理的强大支持,使FastAPI成为当今Python网络框架的热门之选。无论您是Python的爱好者,还是初涉编程的新手,都值得探索FastAPI的精彩世界。愿本文能轻松引领您进入FastAPI,为您的python微服务开发之旅提供帮助。

本文暂时没有评论,来添加一个吧(●'◡'●)

欢迎 发表评论:

最近发表
标签列表