杜克大学大规模云计算基础笔记-全-
杜克大学大规模云计算基础笔记(全)
001:讲师介绍
在本节课中,我们将认识本课程的讲师,了解他的学术背景、行业经验以及专业成就,这有助于我们理解课程内容的知识来源和权威性。
讲师背景
我的名字是诺亚·吉夫特,我将担任本课程的讲师。
我在世界多所顶尖大学任教,包括杜克大学的数据科学项目、西北大学的研究生数据科学项目。我也曾在加州大学伯克利分校和加州大学戴维斯分校授课。
著作与行业经验
我的著书经验包括一本名为 《Python for DevOps》 的畅销书,以及 《Pragmatic AI》、《Cloud Computing for Data》 和 《Practical MLOps》。这些书籍中的许多已被翻译成中文。
我的行业经验涉及游戏、电影、软件即服务和机器学习工程领域。我曾多次按时、按预算交付产品。
专业理念与成就
如果你在过去20年里真正涉足软件行业,你就会知道对自动化的强调是当前的一个关键重点,而这正是我职业生涯中投入大量精力的领域。
我认为,如果一件事没有实现自动化,那么它就是有缺陷的。我的大部分经验都涉及构建服务器、进行测试、建立安全机制,以确保公司能够按时交付产品。
我近年来的荣誉包括获得 AWS 机器学习英雄 称号。我也参与了AWS、GCP和Azure的教育机构合作项目,并为包括Udacity、Coursera、O‘Reilly和Datacamp在内的顶级内容制作商开发了许多课程。同时,我也是 Python 软件基金会研究员。
因此,你将在优秀的指导下学习。我期待与你分享我的知识。让我们开始吧。
本节课中,我们一起认识了讲师诺亚·吉夫特,了解了他深厚的学术背景、丰富的行业实践经验以及在自动化与云计算领域的专业成就,这为我们后续学习构建大规模云计算解决方案奠定了信任基础。
002:课程介绍 🚀

在本节课中,我们将概述《云计算基础》课程的核心学习目标。你将了解本课程涵盖的关键主题,包括技术沟通、项目管理、持续交付管道构建、多种云服务模型的应用,以及DevOps原则和基础设施即代码的实践。
课程学习目标
上一段我们介绍了课程的整体框架,接下来,我们将详细拆解本课程的具体学习目标。以下是你在完成本课程后将掌握的核心技能:
- 应用沟通原则:你将学习在技术讨论中应用相关的沟通原则、概念和方法。
- 执行技术项目管理:你将学习使用多种工具来规划和执行有效的技术项目管理。
- 构建持续交付管道:你将在三大主流云平台(AWS、Azure和GCP)上,使用Python为数据工程和机器学习项目构建持续交付管道。
- 创建多种云服务网站:你将学习使用多种不同的云服务模型创建网站,包括:
- 使用S3创建静态网站。
- 使用Lambda创建无服务器架构网站。
- 使用Azure App Services、AWS Elastic Beanstalk和GCP App Engine创建平台即服务(PaaS)网站。
- 评估与选择云服务模型:你将学习评估不同的云服务模型,以便有效地选择正确的抽象层级,包括基础设施即服务(IaaS)、裸机即服务(MaaS)、平台即服务(PaaS)和无服务器(Serverless)。
- 应用DevOps原则:你将学习将DevOps原则应用于云计算、数据工程和机器学习领域。
- 实践基础设施即代码:你将学习结合使用基础设施即服务(IaaS)和基础设施即代码(IaC)来以可重复且幂等的方式管理和配置云资源。
- 评估最佳实践:你将学习评估在云计算中实施解决方案的最佳实践。
总结


本节课中,我们一起学习了《云计算基础》课程的完整学习路径。从技术沟通与项目管理的基础,到在三大云平台上构建实际的数据与机器学习管道,再到深入理解和应用从IaaS到Serverless的各种服务模型,最后通过DevOps和基础设施即代码实现高效、可靠的云运维。现在,让我们正式开始学习之旅。
003:课程先修要求 📚

在本节课中,我们将要学习成功学习本课程所需具备的先修知识与技能。了解这些要求将帮助你评估自己是否已做好准备,并明确在课程开始前可能需要补充学习的领域。
先修知识概述
为了能够顺利地跟随本课程并充分理解其内容,学员需要具备以下几方面的基础知识。这些技能是构建后续复杂云计算解决方案的基石。
以下是本课程的核心先修要求列表:
- Python编程能力:需要具备中级水平的Python知识。这意味着你需要能够构造语句、理解变量,并能够编写小型脚本。
- Linux基础知识:需要掌握基本的Linux操作技能,包括在文件系统中导航以及运行Shell命令。
- IT基础设施概念:需要理解关键的IT基础设施组件,例如虚拟机(Virtual Machine) 和数据库(Database) 的基本概念。
- 数据格式理解:需要能够理解JSON和YAML文件格式及其结构。这是控制云生态系统的关键,因为传递JSON(本质上类似于Python字典)或YAML数据是云操作中的常见任务。
学习本课程的意义
上一节我们介绍了课程的技术先修要求,本节中我们来看看为什么值得投入时间学习这门课程。掌握云计算技能在当今的科技行业中具有重要价值。
以下是学习本课程的主要意义:
- 满足数据科学需求:大多数数据科学项目最终都需要云平台。虽然可以在笔记本电脑上进行小型项目,但笔记本不具备近乎无限的计算和存储扩展能力,而云服务正好提供了这种可扩展性。
- 巨大的职业机会:根据亚马逊云科技(AWS)的研究,市场上有数十万个未填补的云计算相关职位。行业存在巨大的人才需求缺口,快速接受相关培训至关重要。
- 获取认证的基础:本课程可以作为考取三大主流云平台(AWS、GCP、Azure)认证的基础。你可以先通过本课程打下坚实基础,再决定向哪个平台深入发展。
- 构建实际系统:本课程非常注重职业技能培养,你将学习如何构建可工作的系统,范围涵盖从命令行工具、Web应用程序到完整的可运行机器学习模型。

本节课中我们一起学习了本课程所需的先修技能以及学习它的重要意义。确认你已掌握或计划学习这些先修知识,将帮助你更好地开启构建大规模云计算解决方案的旅程。
构建大规模云计算解决方案:P4:04_01_01:实验环境入门 🚀

在本节课中,我们将介绍本课程所需的实验环境与资源。你将了解如何免费使用三大主流云平台(AWS、GCP、Azure)的服务来完成所有课程任务,并获取额外的教育资源。
课程实验资源概述
本课程提供了针对AWS、GCP和Azure的实验。这些平台均设有免费套餐,足以支持你完成全部课程内容。此外,如果你是教育机构成员,还可以获取更多专为学习设计的实验资源。
AWS 实验环境
上一节我们概述了可用的云平台,本节中我们来看看AWS的具体资源。
AWS提供免费套餐。使用该套餐,你基本可以完成本课程的所有需求。
以下是获取AWS实验资源的途径:
- AWS免费套餐:推荐使用,可满足大部分实验要求。
- AWS Academy:如果你是教育机构成员,可以访问许多免费的实验,这些实验非常有帮助,并能为你考取AWS认证做准备。
- 教师授课:我本人也使用这些实验进行教学。
GCP 实验环境
了解了AWS的资源后,我们转向Google Cloud Platform。
GCP平台提供慷慨的免费套餐。使用免费套餐,你可以完成整个课程的所有作业。
以下是获取GCP实验资源的途径:
- GCP免费套餐:足以支持完成全部课程任务。
- Quicklabs:可以访问可选的Quicklabs。
- Google教育优惠:如果你是学生,可以申请Google教育优惠来获取一些Quicklabs积分,并进行试用。
Azure 实验环境
最后,我们来了解Microsoft Azure的实验环境。
Azure平台同样提供非常慷慨的免费套餐。作为学生,你可以访问该套餐。
以下是获取Azure实验资源的途径:
- Azure免费套餐:学生可以免费使用。
- Microsoft Learn:如果你想自行完成一些实验,可以通过Microsoft Learn平台进行。

总结

本节课中,我们一起学习了如何搭建本课程的实验环境。总而言之,通过利用AWS、GCP和Azure的免费套餐能力,你可以免费完成本课程涵盖的所有内容。此外,如果你是像杜克大学这样的教育机构的一员,还可以获取那些专门为教育环境设计的实验资源。
005:项目概览

在本节课中,我们将介绍课程一的最终项目。该项目将引导你构建一个基于AWS的静态网站,并为其配置一个持续交付流水线。通过完成这个项目,你将能够展示在AWS云环境中部署和交付代码的实际操作能力。
项目简介
上一节我们介绍了课程的整体目标,本节中我们来看看具体的实践项目。该项目的核心是创建一个基于Hugo框架的静态网站。
这个网站将由AWS S3托管,并通过AWS CodePipeline实现持续交付。你的源代码将存放在GitHub仓库中。
项目架构与流程
你的网站将被静态部署到一个名为Amazon S3的云原生环境中。当你通过GitHub进行推送或更改时,此事件将触发一个在AWS CodePipeline持续交付系统上运行的持续交付流程。
不必担心这些术语可能让你感到困惑,我们将在课程中逐步深入讲解。
你将如何构建
接下来,我们谈谈你将如何构建这个项目。你将运用本课程中涵盖的最佳实践,以及构建持续交付系统的技能。
以下是项目完成后你将获得的具体成果:
- 一个包含你源代码的GitHub仓库,证明你能够交付可在亚马逊云中运行的代码。
- 一段展示部署过程和可运行网站的演示视频。
我们设计这个项目的目的,是帮助你构建一个丰富的作品集,以展示你具备成为一名云架构师所需的实践技能。
总结


本节课中我们一起学习了课程一最终项目的概览。我们了解到,该项目将结合Hugo静态网站生成器、GitHub、AWS S3和AWS CodePipeline,构建一个完整的持续交付流水线。在接下来的课程中,我们将逐步深入每个环节,帮助你掌握构建云解决方案的核心技能。
构建大规模云计算解决方案:1-2:技术讨论介绍
在本节课中,我们将学习如何开展有效的技术讨论。所涵盖的技巧能立即帮助你在个人或团队项目中产生更大的影响力。
接下来,让我们深入了解具体的学习目标。
首先,我们将探讨如何实施包含可复现代码的技术讨论。例如,GitHub本身可以托管Notebook、Markdown语言文件等多种内容。这使你能够清晰地展示你的意图,而其他用户可以检出代码并逐步运行它。这是技术讨论中的一个关键点。
以下是实现可复现讨论的几个要点:
- GitHub等平台支持托管Jupyter Notebook和Markdown文件。
- 这些格式允许清晰地展示代码、逻辑和步骤。
- 其他用户可以轻松获取并复现整个流程,确保讨论基于共同的事实基础。
上一节我们提到了可复现的代码,本节中我们来看看如何创建简短的演示视频。
我们还将学习如何制作一个30秒到2分钟的演示视频,用以传达手头问题的技术细节。在我们所处的后疫情时代,通过电子方式进行异步沟通的能力至关重要。这是本课程将涵盖的一个关键点,我们也会在后续许多课程中继续强化这一技能。
以下是创建有效演示视频的关键:
- 时长控制在30秒至2分钟,聚焦核心。
- 清晰地展示问题、解决方案或关键发现。
- 使用屏幕录制工具捕捉代码运行、界面操作或图表变化。
- 添加简短的语音或文字说明,引导观看者理解重点。
除了动态演示,清晰、可重用的技术文档同样重要。
我们还将深入探讨如何创建高质量、可在多个平台间复用的技术笔记。一个很好的例子是,如果你用Markdown创建文档,之后可以将其转换成书籍、用于版本控制的注释,或者以多种形式(包括网页)使用。当你能够一次创建、多次复用时,你便真正发挥了有效技术沟通的力量。
以下是创建可复用技术笔记的建议:
- 使用Markdown等轻量级标记语言编写文档。
- 确保内容结构清晰,包含必要的代码块(使用
代码格式)和解释。 - 这样的文档可以轻松转换为PDF、网页、或集成到Wiki和版本控制系统中。


在本节课中,我们一起学习了开展有效技术讨论的三个核心技能:使用可复现的代码(如GitHub Notebook)、制作简短的演示视频,以及编写可跨平台重用的高质量技术笔记(如使用Markdown)。掌握这些技能将显著提升你在异步协作和技术沟通中的影响力。
007:使用Markdown、GitHub和Jupyter Colab进行技术讨论 📝
在本节课中,我们将学习四种快速进入有效技术讨论的方法。我们将重点介绍如何使用GitHub、Markdown、Gist和Jupyter Colab来创建可重复、结构清晰的技术文档和讨论。这些工具能帮助你清晰地分享代码、想法和项目进展。
使用GitHub和Markdown创建技术讨论
上一节我们介绍了课程目标,本节中我们来看看第一种技术:使用GitHub和Markdown。
GitHub是一个用于进行源代码版本控制并与他人共享代码的平台,它内置了强大的协作功能。Markdown是一种轻量级标记语言,能让你轻松地编写格式化的文档。
以下是创建GitHub仓库和Markdown文档的步骤:
- 创建新仓库:在GitHub上创建一个新的仓库(Repository),用于存储你的工作。例如,可以将其命名为“technical discussion”。
- 添加描述:为仓库添加描述,例如“A demo repo for sharing ideas around communication”。
- 初始化文件:创建时,建议勾选“Add a README file”选项,这样就能立即开始基于Markdown的文档编写。同时,可以添加一个
.gitignore文件(例如选择Python模板),以避免将编译产生的临时文件(如.pyc)提交到仓库中。 - 编辑文档:在仓库中,点击README文件旁的铅笔图标进行编辑。你可以使用Markdown语法来格式化内容。
- 使用
#创建标题。 - 使用
##创建二级标题。 - 使用
*或-创建项目符号列表。
- 使用
- 预览与保存:编辑时,可以随时预览渲染后的效果。完成后提交更改。
Markdown的优点是直观且可移植。你编写的原始Markdown文本可以轻松地放入书籍、网站或其他支持Markdown的平台中,因此它是进行技术讨论的理想格式。
使用Gist分享代码片段
我们已经学会了如何创建README文件来进行技术讨论。接下来,让我们看看第二种方法:使用Gist分享小型代码片段。
Gist是GitHub提供的一项功能,专门用于分享单文件或少量文件的代码片段。它的优势在于能自动进行语法高亮,并且易于嵌入或链接到其他讨论中。
以下是使用Gist的步骤:
- 访问Gist:在GitHub主页或通过
gist.github.com访问Gist功能。 - 创建Gist:输入代码片段描述、文件名(如
hello.py)和代码内容。def hello(x, y): return x + y - 选择可见性:你可以创建公开(Public)或秘密(Secret)的Gist。公开Gist可以被任何人查看。
- 分享链接:创建后,你会获得一个唯一的URL。你可以将这个链接复制到你的技术讨论文档中。
- 例如,在Markdown中:
[这是一个Gist示例](https://gist.github.com/your-gist-id)
- 例如,在Markdown中:
使用Gist分享代码,能确保对方看到正确的语法高亮和格式,避免了因直接粘贴代码到聊天工具(如Slack)可能引入的乱码或格式错误问题。此外,其他人还可以在你的Gist上添加评论。
使用Jupyter Colab创建交互式笔记本
接下来,让我们深入了解第三种强大的工具:Jupyter Colab。

Jupyter Colab是Google提供的托管版Jupyter Notebook服务。它允许你创建包含可执行代码、可视化结果和格式化文本的交互式文档,非常适合进行复杂的数据分析、机器学习项目演示或技术教程。
以下是使用Colab的核心步骤:
- 访问与创建:访问 colab.research.google.com 并创建一个新的笔记本。使用Google账号即可免费使用。
- 混合编写:在单元格(Cell)中,你可以编写代码并直接运行。
你也可以将单元格类型切换为“文本”,使用Markdown编写格式化的说明文档。def greet(name): return f"Hello, {name}!" print(greet("World")) - 结构化项目:你可以用Markdown标题将笔记本组织成清晰的章节,例如:
## 1. 数据获取## 2. 探索性数据分析## 3. 模型构建## 4. 结论
- 利用硬件加速:在“运行时”菜单中,你可以选择使用GPU或TPU来加速计算密集型任务。
- 分享与保存:
- 分享链接:点击右上角的“共享”按钮,可以生成链接,像共享Google文档一样与他人协作。
- 保存至GitHub:通过“文件” -> “在GitHub中保存副本”,可以将笔记本直接保存到你的GitHub仓库中。这会将
.ipynb文件提交到仓库,他人不仅可以查看代码,还可以通过Colab链接打开并运行它。
将Colab笔记本保存到GitHub,结合了交互式编程和版本控制的优点,是进行可复现技术讨论最有效的方式之一。
在Markdown中嵌入图片的技巧

最后,我们来学习一个实用的小技巧:如何在Markdown文档中便捷地嵌入图片。
这个方法适用于GitHub README、Jupyter Notebook的Markdown单元格以及任何支持Markdown的平台。核心是利用GitHub Issues作为免费的图床。
以下是具体操作步骤:
- 在GitHub仓库中新建Issue:进入你的仓库,点击“Issues”标签页,然后点击“New issue”。
- 拖拽上传图片:在Issue的编辑框中,直接将本地截图或图片文件拖拽进去。GitHub会自动上传图片并生成一个Markdown格式的图片链接,例如:
 - 提交Issue:提交这个Issue,图片链接就会永久生效(只要该Issue存在)。
- 在文档中引用:复制生成的图片链接,粘贴到你的README文件或Colab笔记本的Markdown单元格中。
通过这种方式,你可以轻松地在技术文档中插入图表、截图或示意图,使说明更加直观。
总结
本节课中我们一起学习了四种进行有效技术讨论的工具和方法:
- GitHub与Markdown:用于创建结构化、可版本控制的文档。
- Gist:用于分享和讨论独立的代码片段,并保证格式正确。
- Jupyter Colab:用于创建交互式、可执行且易于分享的代码笔记本,是实现复杂项目演示和可复现研究的利器。
- 图片嵌入技巧:利用GitHub Issues作为图床,在Markdown文档中方便地插入图片。


综合运用这些工具,你可以构建出清晰、专业且易于他人理解和参与的技术讨论内容。
008:创建技术演示视频 🎬
在本节课中,我们将学习如何制作一个有效的技术演示视频。这项技能在当今世界至关重要,能显著提升你的职业竞争力。
想象一下,当你的简历中包含一个视频链接,清晰展示你的项目成果时,这很可能成为你获得理想工作的关键。接下来,我们将从软件选择、视频格式、时长与表现力等方面,详细探讨如何制作高质量的技术演示视频。
软件选择 🛠️
首先,我们来了解制作技术演示视频所需的软件。幸运的是,有许多免费选项可供选择。
以下是几种可用的软件工具:
- Zoom:许多人已在使用,它具备录制功能。
- Loom:另一个免费的录制选项。
- Panopto 和 Warwire:这两种工具通常在教育环境中提供。
- QuickTime:预装在 macOS 机器上。
如果你希望使用更专业的商业软件,Camtasia 是一个不错的付费选择。
视频格式与清晰度 📹
上一节我们介绍了可用的软件工具,本节我们来看看视频的格式标准。为了确保最佳观看体验,选择合适的清晰度至关重要。
我推荐的视频格式是 1080p 或更高分辨率。720p 虽然可以接受,但有时会显得模糊。实际上,从 1080p 一直到 4K 都是制作此类视频的理想范围。
视频时长与表现力 ⏱️
确定了视频格式后,我们接下来探讨视频的时长以及如何有效地进行展示。掌握好时长能最大程度地吸引观众的注意力。
一般来说,将技术演示视频控制在 30秒到2分半钟 之间会产生最佳效果。这样能让你快速抓住观众注意力,展示必要内容,然后结束。这确实是技术演示视频的理想格式。

本节课中,我们一起学习了创建有效技术演示视频的核心要点。我们了解到,技术演示视频是当今世界一项必不可少的技能,投入少量努力即可获得巨大回报。通过选择合适的软件、采用高清格式并控制好时长,你就能制作出令人印象深刻的技术演示视频,为你的职业发展增添重要筹码。
009:有效批判性思维 🧠
在本节课中,我们将要学习有效批判性思维的核心概念及其在云计算和技术管理中的重要性。批判性思维是评估众多技术方案并做出明智决策的关键能力。
概述
有效批判性思维是学习云计算和技术管理时最重要的技能之一。原因在于,面对众多可选择的方案时,区分并选择最佳方案的唯一方法就是运用批判性思维。
麻省理工学院作者乔纳森·哈伯曾著有一本关于批判性思维的优秀著作。他在书中讨论了由一家研究批判性思维的非营利组织所阐述的批判性思维的多个方面。
批判性思维的构成要素
以下是批判性思维的一些关键构成要素。理解这些要素有助于我们在技术决策中更系统、更客观地思考。
1. 理智谦逊
理智谦逊意味着你能够意识到自己并非总是正确的,并且时常可能存在盲点或某种偏见。你需要持续警惕自己可能犯错的情况。这是批判性思维中经常缺失的一种特质。你可能在自己的工作场所中观察到这一点。
2. 勇气
如果你已经深入研究、科学地分析了问题,并且知道存在一个特定的解决方案,但绝大多数人并不相信它,那么你就需要有勇气去为你基于推理得出的信念而奋斗。这是批判性思维中一个非常重要的方面。
3. 同理心
同理心是指你能否设身处地,从理智上与你观点相左的人的角度思考,并理解他们为何要求你相信他们的观点。一旦你理解了对方的想法并对他们的观点产生同理心,就更容易达成妥协或找到双方都能接受的共同前进方向。
4. 自主性
自主性是指你能否独立提出自己的想法。你是仅仅在复述社交媒体、新闻或其他观点的内容,还是能够通过自己的反思、独处以及阅读自己的信息来源,独立形成自己的观点?在我们所处的时代,这是批判性思维的一个至关重要的方面。
5. 正直
正直意味着,当你想赢得一场辩论时,你是否在公平竞争?你是否在使用技巧或故意误导他人?这不是秉持正直的批判性思维,而是使用伎俩让他人接受你的观点,这确实是应该避免的。
6. 毅力
毅力是指你是否具备这样的能力:假设你知道某个问题存在正确的解决方案(我们可以将其带入技术领域,即存在一个正确的技术方案),你是否能坚持不懈地、有条不紊地记录为何这是最佳方案,并真正将其付诸实施?很多时候,人们容易简单地说“我是对的,你是错的”,也许你确实是对的,但你是否有能力坚持不懈,确保你所在的公司或实体完全实施你所建议的解决方案?
7. 对理性的信心
对理性的信心是指你是否真正相信科学事实?你是否能够逐步向人们证明事实,并最终让理性获胜?这是一个非常重要的哲学观点。
8. 公正
公正是指你是否能本着诚意,接受在解决问题过程中收到的每一条不同的批评或赞扬?如果你不能真正接受所有不同的观点,如果你是一名管理者,这可能会导致管理问题;在评估最佳解决方案时,也可能引发问题。
批判性思维在技术领域的应用
所有这些批判性思维的方面在技术意义上都非常重要,它们在其他生活领域也同样重要。但擅长云计算和擅长技术的一个关键组成部分,就是运用理性和批判性思维来评估所有不同的解决方案。
盲目接受某一条路径是行不通的。唯一的办法是逐步运用批判性思维,根据手头的问题得出最佳解决方案。这个过程可以概括为以下核心步骤:
- 识别问题与假设:明确要解决的核心问题,并审视自己可能存在的偏见或假设。
- 收集与分析信息:科学地研究问题,从多个可靠来源收集信息。
- 评估方案:运用理智谦逊、同理心和公正性,客观评估每个方案的优缺点。
- 得出结论并沟通:基于推理和证据得出结论,并有勇气和毅力去清晰地阐述和推动它。
- 反思与调整:保持开放心态,接受反馈,并根据新信息或不同观点调整方案。
总结

本节课中,我们一起学习了有效批判性思维的八个核心要素:理智谦逊、勇气、同理心、自主性、正直、毅力、对理性的信心以及公正。我们探讨了这些要素如何帮助我们避免偏见、独立分析、客观评估,并最终在云计算等复杂技术领域做出更明智、更可靠的决策。掌握批判性思维,是成为一名优秀技术专家和问题解决者的基石。
010:高效技术全能人才
概述
在本节课中,我们将探讨如何成为一名高效的“技术全能人才”。这个概念借鉴自篮球运动中的“三双”表现,旨在说明在技术职业生涯中,通过培养多方面的能力组合,可以显著提升你的竞争力和成功机会。
什么是“全能人才”?
上一节我们介绍了课程背景,本节中我们来看看“全能人才”这个概念的具体含义。
在篮球这项全球流行的运动中,有一个常用术语叫“三双”。它指的是球员在一场比赛中,在得分、篮板和助攻这三项主要统计数据上都达到两位数(例如,得分超过10分,抢下10个篮板,送出10次助攻)。这体现了球员在球场上的全面能力。此外,球员也可以通过其他方式展现全面性,例如完成10次抢断或10次盖帽,这些同样是高难度且宝贵的贡献。
这个概念同样适用于你的职业生涯。许多人之所以在求职或拓展人脉时遇到困难,是因为他们只专注于单一技能,就像篮球运动员只练习投篮或抢篮板一样。
如何构建你的“技术全能”组合
理解了全能人才的概念后,接下来我们看看如何将这一理念应用到技术领域,构建你自己的能力组合。
在技术领域,你可以通过培养一个“三威胁”组合来提升自己的全面性。以下是构建这个组合的三种核心方式:
- 学历:获得一个相关的学位是基础方式之一。
- 作品集:建立一个作品集,例如一个GitHub项目,并可以辅以展示项目功能的YouTube视频。
- 认证:考取行业认可的认证,例如基于云计算的认证。
本课程的一个关键内容,就是教你如何成为这样的全能人才,并学会综合利用这三种能力,使自己始终处于有利位置。这并不意味着其中单一一项总能奏效,或者你必须同时拥有全部三项,但拥有多种能力可以让你总能处在正确的位置,抓住机会。
其他形式的“技术全能”
除了上述核心组合,还有其他方式可以体现你在技术领域的全面性。
例如,拥有强大的人脉网络,或者拥有丰富且出色的工作经验,也是非常重要的能力维度。核心思想在于:不要只专注于一件事。如果你能展现出多方面的交付能力,这将是你在技术领域获得卓越职业生涯和成功求职的最佳途径。
给学生的关键建议
对于学生而言,以下是一条关键建议:
学历固然重要,但仅凭学历,你可能需要更多地依赖运气。然而,如果你同时拥有学历、作品集和认证,你就将自己置于了获得工作的最佳可能位置。
总结
本节课中,我们一起学习了“技术全能人才”的概念及其重要性。我们探讨了如何通过结合学历、实践作品集和行业认证来构建你的核心竞争力组合,并了解了强大人脉和工作经验的补充价值。记住,培养多方面的能力,是你在快速发展的技术领域立足和脱颖而出的关键。
011:高效技术团队协作介绍 🚀
在本节课中,我们将探讨如何培养高效的技术团队协作。我们将详细介绍一个用于评估和提升团队效能的检查清单,帮助你判断团队是否在最高水平上运作。
核心学习目标 🎯
上一节我们讨论了团队协作的重要性,本节中我们来看看如何通过具体方法实现高效协作。本节课的核心目标是学习如何通过透明和及时的沟通,来培养积极的团队动态。
理想的场景是拥有一个检查清单,你可以逐一核对,以判断你的团队是否在最高水平上运作。
让我们开始吧。
高效团队协作检查清单 📋
以下是构建高效技术团队所需的关键要素检查清单。你可以使用它来评估和改善团队的协作状态。
-
明确的目标与愿景
- 团队是否对项目的最终目标有清晰、统一的理解?
- 每个成员是否都清楚自己的工作如何贡献于整体目标?
-
透明与及时的沟通
- 团队是否建立了开放、无惧提出问题的沟通文化?
- 信息(如项目进展、障碍、决策)是否能及时传达给所有相关成员?
- 是否定期举行高效的站会或同步会议?
-
清晰的角色与职责
- 每个团队成员的角色和职责是否明确界定?
- 是否存在职责重叠或模糊地带?
-
信任与相互尊重
- 团队成员之间是否相互信任,能够依赖彼此完成工作?
- 讨论中是否尊重不同意见,并基于事实进行建设性辩论?
-
有效的冲突解决机制
- 当出现分歧时,团队是否有既定的、健康的解决流程?
- 冲突是否能被引导为促进创新的机会,而非破坏性内耗?
-
持续的学习与改进
- 团队是否定期回顾工作流程(如举行复盘会),并寻求改进?
- 是否鼓励知识分享和技能提升?
-
合适的工具与流程
- 团队是否使用了合适的协作工具(如Jira、Git、Slack)?
- 开发、部署、监控等流程是否清晰且高效?

总结 ✨

本节课中,我们一起学习了如何通过一个具体的检查清单来构建和评估高效的技术团队。我们强调了透明与及时的沟通是培养积极团队动态的基石,并逐一分析了从目标设定到工具使用的七个关键维度。
记住,高效的团队协作不是自然发生的,它需要通过有意识的培养和持续的维护。定期使用这份检查清单进行团队健康度诊断,是迈向高性能团队的重要一步。
012:高效技术团队协作 🧑💻
在本节课中,我们将探讨如何构建一个高效的技术团队。我们将超越单纯寻找“天才”的思维,深入了解科学研究所揭示的、真正驱动团队成功的核心要素。
概述
团队协作是任何技术项目成功的基石。然而,什么造就了一个高效的团队?许多人首先想到的是“人才”,但研究表明,这并非最重要的因素。本节将基于拉尔森和拉法斯托的研究,系统性地介绍高效团队的八个关键特征,并分享一个关于“人才”与“团队”权衡的个人故事。
高效团队的八大要素
上一节我们概述了团队协作的重要性,本节中我们来看看构成高效团队的具体要素。以下是构建高效团队必须关注的八个方面:
-
清晰且崇高的目标
团队需要一个明确且能激励人心的共同目标。例如:“解决贫困问题”、“普及某地区教育”或“实现清洁能源”。如果缺乏目标,团队将难以保持高效。 -
以结果为导向的结构
团队结构必须围绕结果来构建,而非人际关系或办公室政治。核心在于设定目标,衡量成员为实现目标所采取的步骤及取得的成果。 -
称职的团队成员
团队成员必须具备基本的能力。无论是在政治、体育还是工业领域,缺乏称职成员的团队都可能引发严重后果,导致团队失效。 -
统一的承诺
团队成员必须齐心协力,共同致力于解决问题。如果有人“出工不出力”或心怀异志,将对团队造成巨大损害,因为部分成员的不满或离职意向会产生毒性影响。 -
协作的氛围
团队需要一种支持性的协作环境。上层领导和团队成员应相互支持,并奖励团队合作行为。反之,如果环境充满毒性,成员相互对立,基层员工可能因害怕而隐瞒关键信息,最终导致糟糕的结果。 -
卓越的标准
团队必须对“优秀”达成共识。例如:“我们每天要为疫情进行四次检测”。如果缺乏卓越的标准,无人知晓何为“好”,这将严重阻碍高效团队的建立。 -
外部的支持与认可
高层管理者需要认可成员的额外付出,并支持他们实现目标。这类似于体育比赛中通过传球为队友创造机会,是高效团队的关键组成部分。 -
有原则的领导力
团队领导者必须具备品格,行事合法、道德且有原则。这样,团队成员才会受到鼓舞,并相信领导者在困境中也能做出正确抉择。
人才与团队:一个经验教训
在了解了高效团队的框架后,我们来看看一个常见的误区。在我的职业生涯中,关于人才与团队协作,我学到了深刻的一课。
作为管理者,我招聘过数百人,早期犯下的最大错误就是过分强调“人才”。在硅谷,人们常说“必须雇佣最好的开发者”、“必须雇佣最聪明的人”。当然,你希望团队拥有才华,这无可厚非。
但我通过艰难的方式认识到,过分强调人才是被高估的。你确实需要基础的能力(即“称职的团队成员”),但如果你只优化“才华”而忽视品格,就可能创造一个毒性环境。例如,某个成员可能总是自以为是或非常傲慢。
这会对你的团队产生极具破坏性的影响。因此,核心总结是:必须全面考量所有因素,而不是过分侧重“寻找天才”这件看似简单的事。真正为组织创造最佳成果的是团队协作,而非孤立的个人才华。
总结
本节课中,我们一起学习了构建高效技术团队的八大核心要素:清晰崇高的目标、结果导向的结构、称职的成员、统一的承诺、协作的氛围、卓越的标准、外部的支持与认可,以及有原则的领导力。同时,我们也认识到,虽然人才重要,但过度追求个人才华而忽视团队整体健康与协作,反而可能损害团队效能。如果你的组织正面临团队效率问题,不妨对照这份清单,逐步检视并改进。
013:技术项目管理介绍 🚀

在本节课中,我们将学习如何开展有效的技术项目管理。我们将深入探讨一些能极大简化工作流程的高效工具,并了解影响项目成败的关键因素。
上一节我们介绍了课程的整体目标,本节中我们来看看技术项目管理的具体内容。
识别影响技术项目成功的主要因素
首先,我们需要明确哪些是决定技术项目成败的核心要素。成功的项目通常优化了这些方面,而失败的项目则往往在这些方面存在不足。

通过透明及时的沟通培养积极的团队动力
其次,我们将学习如何通过透明和及时的沟通来建立积极的团队协作氛围。这意味着要利用最佳的异步协作技术和高效的软件工具,而非低效、粗糙的沟通方式。
接下来,我们将介绍几个具体的工具和方法。
以下是本课程将涵盖的三个核心工具与实践:
- 使用 Trello 进行工单跟踪:Trello 是一个极简的工单跟踪系统。我们将展示如何使用它来建立一个简单的工作流,从而消除许多无用的沟通(如临时打扰或本可异步进行的周会)。
- 使用电子表格进行项目管理:电子表格是一项古老的技术,自20世纪80年代初就已存在,但在项目管理中依然极其有效。我们将用它来构建项目结构。这是一个在许多百万美元级别的项目中都被验证过的高效工具。
- 识别并避免项目管理中的反模式:我们将讨论如何避开那些可能导致项目脱轨的陷阱。这些做法可能在当时看起来不错,但一旦实施却可能带来灾难性后果。


本节课中我们一起学习了技术项目管理的基础,包括影响项目成功的关键因素、促进团队协作的沟通原则,以及 Trello、电子表格等实用工具的介绍。在接下来的课程中,我们将逐一深入这些工具的具体使用方法。
014:高效技术项目管理 🚀
在本节课中,我们将学习如何成为一名高效的技术项目经理。我们将探讨一系列实用的策略和原则,帮助你规划项目、跟踪进度并建立可持续的工作流程,从而确保项目成功。
概述
技术项目管理不仅关乎截止日期,更关乎建立可预测、可持续的工作系统。我们将从制定季度计划开始,逐步介绍建立有效节奏、实施现代开发实践以及培养持续改进心态的方法。
制定季度计划 📅
上一节我们介绍了课程目标,本节中我们来看看项目规划的起点。一个有效的方法是构建一个季度计划,逐周明确你将构建的内容。
- 季度技术计划:在计划中,你可以逐周列出你认为会发生的事情。这并不意味着计划会一成不变,但它能促使想法流动,并让你深入思考将要构建的内容。这是最初规划某事的最佳方式之一。
建立每周演示节奏 🎯
仅仅有计划还不够,我们需要确保计划得以执行。以下是建立有效进度跟踪的方法。
- 每周演示:在团队中实施每周演示是推动进展、确保任务完成的最有效方式之一。其关键原因在于,你上周所做的工作很可能决定了你下周的工作内容。因此,这是一种展示构建进度的方式。如果你无法每周进行演示,很可能无法按时完成最终期限。
拥抱DevOps与持续交付 ⚙️
为了支撑快速的迭代节奏,我们需要强大的工程实践作为基础。项目管理的一个关键方面是理解DevOps。
- 持续交付:DevOps的一个关键因素是持续交付。它意味着你的代码始终处于可部署状态。这可以避免出现“我还没设置好这些复杂的环节,现在必须匆忙完成”的意外情况。如果从一开始就实践持续交付,你将为成功奠定坚实基础。
实施自动化测试 ✅
可靠的交付离不开质量保障。自动化测试是项目成功的另一个基石。
- 测试自动化:正如之前提到的,如果测试没有自动化,那么它就是无效的。这是思考项目测试的重要方式。从一开始就进行自动化,将在未来带来巨大回报,这很像一种投资。
合理拆分与管理任务 📋
有了良好的工程实践,我们还需要有效管理具体的工作项。当你使用工单系统拆分任务时,请遵循以下原则。
- 任务时长:将任务控制在4小时到3天的范围内是一个理想的“甜蜜点”。在一个为期一周或两周的周期内,你可以组合这些任务块,制定出切实可行的计划。
- 任务看板:使用简单的看板来沟通进度非常有效。你可以设置“待办列表”、“进行中列表”和“已完成列表”。保持简单,这样可以避免许多不必要的会议,因为工作状态一目了然——要么在做,要么没做,要么已完成。这实际上能消除组织中80%的会议需求。
避免“英雄式”流程 🦸
可持续的项目管理不应依赖个人英雄主义。另一个需要考虑的要点是,不要设计一个需要“英雄”在最后时刻拯救全场的流程。
- “英雄驱动”开发的危害:这是我在公司中见过的最有害的模式之一:依赖一位“英雄”在最后一刻熬夜完成所有奇迹般的工作。这实际上是一种“英雄驱动”的开发模式,从长远来看,这不是一种可持续的项目管理理念。一个关键问题是:如果那位“英雄”离开了怎么办?结果你会陷入大麻烦。因此,拥有一个可预测且不那么依赖“英雄”的流程更好。
践行“改善”哲学 🔄
以上讨论的许多理念都汇聚于一个词:改善。最后,我们来探讨驱动所有这些实践的核心心态。
- 持续改进:“改善”是源自日本汽车行业的哲学,旨在每日持续改进。这同样是构建成功云项目的一般方法。每天问自己:我是否在变得更好?我如何让事情变得更好、更快、质量更高?这种心态将驱动你在项目中取得最佳成果。
实践案例分享 🎬
让我分享一个故事来突出所有这些关键原则。在我职业生涯早期,我曾在一家大型电影工作室工作。他们投入了数亿美元制作一部电影。我记得当时是夏天,而我们有一部圣诞节电影要上映,情况非常糟糕。我刚加入公司,发现很多东西都无法运行,团队非常担心数亿美元会打水漂,因为广告牌已经立起来了,电影却无法完成。作为团队一员,我帮助解决问题的方法之一就是:我们定期进行清理和整顿。
- 逐步改进:我们一步一步来,一次只做一件正确的事。我们建立了每周节奏,设置了自动化的构建服务器,进行了一些测试。核心思想就是:每天我都要一点点地解决问题,让它变得更好,同时将工作变成可预测的、逐周的进展。这就是我职业生涯中解决大多数问题的方法,也成功解决了这个特定问题。
总结

本节课中我们一起学习了高效技术项目管理的核心原则。关键在于如何构建可预测的系统——就像为你的401k养老金定期储蓄一样,而不是寄希望于会出现“英雄”或奇迹来拯救你的“英雄式”场景。通过制定季度计划、建立每周演示节奏、实施DevOps与自动化测试、合理管理任务、避免依赖个人英雄主义,并践行每日“改善”的哲学,你就能实现最有效的技术项目管理。这才是确保项目长期成功与可持续发展的方式。
015:使用Trello进行工单跟踪 📋
在本节课中,我们将学习如何使用一个极简的工单跟踪系统来构建一个工具,以跟踪课程或组织内的项目进度。我们将以Trello为例,介绍其核心概念和基本操作流程。

创建看板与列表
首先,我们需要在Trello中创建一个看板。点击界面上的加号图标,选择“创建看板”。接着,你可以选择是否将其关联到某个团队,并设置看板的可见性(公开或私有)。这里我们创建一个名为“工单跟踪”的公开看板。

创建看板后,我们需要建立几个核心列表来代表任务的不同阶段。这是一种非常直观的流程设计,能帮助组织清晰地了解项目动态,从而减少不必要的会议。
以下是创建列表的步骤:
- 待办:用于存放所有已达成共识、等待开始的任务。
- 进行中:用于存放当前正在处理的任务。
- 已完成:用于存放已经完成的任务。
创建与管理工单卡片
上一节我们创建了任务流程的框架,本节中我们来看看如何向列表中添加具体的任务。
在“待办”列表中,我们可以创建代表具体任务的卡片。例如,我们可以创建名为“设置持续交付(CD)流水线”的卡片。在卡片内部,我们可以添加更多详细信息。
以下是管理工单卡片的关键操作:
- 添加备注:你可以在卡片内添加备注,例如预估完成时间“计划在本周末完成”。
- 使用标签:可以创建并使用标签对任务进行分类。例如,创建一个绿色的“DevOps”标签,并将其添加到相关卡片上。
- 使用Markdown:你可以在描述或备注中使用Markdown语法来格式化文本,例如添加代码块或加粗重点。
- 设置截止日期:为卡片设置一个明确的截止日期,以帮助跟踪进度。
- 分配成员:将卡片分配给特定的团队成员,明确责任人。
当任务状态发生变化时,只需将对应的卡片拖拽到相应的列表(如从“待办”拖到“进行中”),整个团队就能直观地看到进度更新。
最佳实践与总结
我们介绍了如何使用Trello创建看板和管理工单。最后,我们来探讨一下使用此类工具的最佳实践,以确保其长期有效。
一个常见的误区是过度复杂化工单系统。无论是Trello还是其他极简跟踪工具(GitHub的Projects也是一个好选择),其核心价值在于保持简单。你应该让看板一目了然,仅通过一次浏览就能掌握所有关键信息。
以下是使用Trello的核心建议:
- 保持简单:避免创建过多的列表、标签或自定义字段,以免系统变得难以维护。
- 及时归档:当任务移动到“已完成”列表并确认后,可以考虑将其归档,以保持看板的整洁和聚焦。
- 可视化沟通:利用看板的状态可视化特性,进行异步沟通,减少同步会议的需求。


本节课中,我们一起学习了如何使用Trello建立一个极简但高效的工单跟踪系统。关键步骤包括创建看板、设置“待办-进行中-已完成”的任务流程列表,以及通过创建卡片、添加标签、设置截止日期和分配成员来管理具体任务。记住,此类工具的成功秘诀在于保持简单和可视化状态,这能有效提升团队协作效率,减少不必要的会议。
016:使用电子表格进行项目规划 📊
在本节课中,我们将学习如何使用电子表格工具(如 Google Sheets)来制定初步的项目规划。这是一种经典且高效的项目管理方法,尤其适合在项目初期梳理思路、设定目标并规划时间线。
上一节我们介绍了项目规划的重要性,本节中我们来看看如何利用电子表格这一具体工具来落地执行。
创建季度计划模板
首先,我们打开一个电子表格(例如 Google Sheets)来创建一个季度计划模板。我们将这个工作表命名为 Q1,代表第一季度的计划。
接下来,我们设置表格的初始列。在 A列,我们可以将其定义为“周数”。随后的几列可以用来代表项目的不同交付部分,例如:
- B列:前端开发
- C列:后端开发
- D列:DevOps 任务
我们可以调整列宽,使表格看起来更清晰、更易于阅读。
规划时间线与关键目标
在设置好列标题后,我们可以在第一行填入时间线。例如,A2单元格可以是“第1周”,你可以填入具体日期,也可以使用“第1周”这样的占位符。我们的目标是规划出一个季度(通常是12周)的时间框架。
在时间线下方,我们可以构建一个灵活的结构来列出每个部分的关键目标。例如:
- 在前端部分,一个关键目标可能是:将应用转换为单页面应用(SPA)。
- 另一个目标可能是:尽量减少对第三方框架的依赖。
- 在后端部分,一个目标可能是:采用无服务器技术。
制定周度任务计划
有了关键目标后,我们就可以开始规划每周的具体任务了。这是一个逐步细化的过程。
以下是逐周规划任务的示例:
- 第1周(后端):建立持续交付(Continuous Delivery)流水线。
- 第2周(后端):创建增强型的基础设施即代码(Infrastructure as Code)模板。
- 第2周(前端):将 JavaScript 代码部署到 S3,让初始原型运行起来。
通过这种方式,你可以一步步地将宏观目标分解为可执行的周度任务。
电子表格规划的优势与价值
这种电子表格规划方法的核心价值在于,它允许你将想法可视化,并建立一个初步的行动路线图。它并不意味着计划会一成不变地发生,但远比没有任何规划要好得多。
根据我多年的项目管理经验,无论是管理5人的小团队还是遍布全球的数百人大型项目,我都是从这样一个季度计划开始的。它帮助我理清思路,估算可行性。
将计划写下来有诸多好处:
- 它帮助你在规划每周工作时保持清晰的方向。
- 它确保你对自己负责,避免尝试构建不可行的目标。
- 它能极大地辅助你进行项目估算。
因此,尽管电子表格已经存在了几十年,但它仍然是你可以使用的最有效的项目管理工具之一。完成这里的初步规划后,你可以将其中的任务逐步导入到 Trello、Jira 或其他专业的工单系统中进行跟踪管理。


本节课中我们一起学习了如何使用电子表格来创建项目季度计划。我们掌握了从建立模板、设定关键目标到分解周度任务的完整流程。记住,有效的规划是成功项目管理的基石,而电子表格是一个简单而强大的起点。
017:项目管理反模式 🚫
在本节课中,我们将探讨项目管理中常见的几种反模式。了解这些有害的模式,有助于我们提前识别并规避风险,从而更有效地推进项目。
上一节我们讨论了项目管理的正确做法,本节中我们来看看那些需要警惕的“反模式”。这些模式看似能解决问题,实则可能隐藏着巨大的隐患。
英雄驱动式开发 🦸
英雄驱动式开发是一种常见的反模式。我注意到在许多运作不良的公司里,总有一位“英雄”不断地在关键时刻拯救项目。他们经常加班,甚至在周末工作。
这实际上是一种导致失败的糟糕模式。因为这位“英雄”可能会精疲力竭并离职。更重要的是,这表明整个团队每周的工作方式缺乏严谨的规划和流程。这是一种需要避免的关键危险信号。
危机驱动式开发 🚨
另一种反模式是危机驱动式开发。我记得在硅谷的初创公司工作时,这常常是完成工作的方式。
你可能会在凌晨两点被叫醒,这可能是连续第十个晚上被叫醒,然后你开始尝试进行根本原因分析并修复问题。
久而久之,你完成任何开发工作的唯一方式,就是在某个巨大的危机之中。每个人都在追赶你上次犯的错误并试图修复,你疲于奔命,陷入恶性循环。这绝不是经营公司或生活的健康方式。
因此,如果你长期处于危机状态,重要的是退一步,解决你为何会陷入这种危机,而不是将其作为一种开发软件的方式。
最高薪者意见驱动式开发 💰
另一种非常普遍的反模式,我称之为“HIPo驱动式开发”。HIPo代表“最高薪者的意见”。
通常的情况是,团队可能已经制定了每周或每两周的计划,然后CEO、关键投资者或其他重要人物会突然介入并说:“听着,我想改这个,我想改那个。”
显然,高管提供意见很重要,但这应该事先完成,并融入到流程中。不应该出现这种每日或每周的随机变动,即人们即将完成某项工作时,却被拉去做别的事,仅仅因为CEO想要某个新功能。这是一种极具破坏性的模式,足以拖垮一家公司,我曾亲眼见过这种情况发生。
繁重的“仪式化”流程 📋
另一个有些反直觉的反模式是“繁重的仪式化流程”。这背后有一个关于“货物崇拜”的故事。
在二战期间,美军登上一些岛屿,给从未见过美国人的岛民带来了大量食物和飞机,由此形成了一种被称为“货物崇拜”的文化。美军离开后,岛民们会举行各种仪式,试图唤回那些物资。
项目管理中也常发生类似情况。很多时候,人们容易模仿那些看起来成功的东西,但这种模仿会逐渐走样,因为模仿者复制的是另一个模仿者,而后者又是另一个模仿者的复制品。最终,你做的只是一些毫无意义的事情。
我曾在一家公司见过这种情况,大家忙于开会、绘制燃尽图等等,结果发现所有时间都耗费在这个过程中,反而扼杀了所有潜在的生产力。因此,流程越轻量越好。事实上,这可能成为公司生产力的“毒瘤”,需要高度警惕。
过度依赖人而非流程 🤝
最后一个反模式是“过度依赖人,而非信任流程”。拥有一个精简而有效的流程是好的,但不能只相信人。
这一点与“英雄驱动式开发”紧密相关。如果有人只是说“嘿,相信我”或者“就按我的方式做,我一个月后给你”,或者“别担心,会完成的”,但从未展示任何进展,那么这是一种极具破坏性和适得其反的软件开发方式。
这并不意味着你不应该信任人。它的含义是,与你合作的个人或团队需要交付增量结果。在我的职业生涯中,我经历过很多成功,也经历过不少失败。一些失败正是发生在我完全信任对方,却没有看到任何实际进展,只是寄希望于对方会交付他们需要交付的东西。
有句话说得好:希望不是一种策略。这里的核心理念是,你应该建立一个能展示增量结果的流程。这样,你就不需要开无数的会议,也不会陷入“希望某事发生却最终落空”的境地。

本节课中我们一起学习了五种项目管理反模式:英雄驱动式开发、危机驱动式开发、最高薪者意见驱动式开发、繁重的仪式化流程以及过度依赖人而非流程。识别并避免这些模式,对于建立健康、可持续和高效的项目管理实践至关重要。记住,好的流程应该赋能于人,而不是束缚或替代他们。
018:AWS云开发环境搭建 🚀
在本节课中,我们将学习如何创建一个AWS云开发环境。我们将从理解持续集成的概念开始,逐步搭建一个基于AWS Cloud9的持续集成环境,并构建一个符合最佳实践的Python项目脚手架。
概述
我们将首先介绍持续集成的概念及其重要性。接着,我们会从零开始在AWS Cloud9上搭建一个持续集成环境。然后,我们将构建一个包含核心组件的Python项目脚手架,例如Makefile、测试、代码检查工具和依赖管理文件。最后,我们将探讨如何为AWS项目开发GitHub Actions测试。
理解核心概念
在开始动手之前,让我们先了解几个关键术语,确保你理解它们。
Makefile
Makefile 是构建软件的“配方”。它确保你的应用程序在任何环境中都能以相同的方式运行,并简化软件项目的构建步骤。本质上,它是一个在所有Linux系统上都可用的“配方”,你可以利用它来管理项目。
示例:
# 一个简单的Makefile示例
install:
pip install -r requirements.txt
test:
pytest
lint:
flake8
测试
测试的主要目的是确保你的软件正常工作。测试有多种类型:
- 功能测试:测试命令行工具或Web应用程序等,确保其基本功能正常。
- 集成测试:确保不同软件组件(例如Web前端和后端)能够协同工作。
- 负载测试:确保你的应用能够承受一定数量的用户(例如10,000名用户)同时访问。在云环境中进行负载测试至关重要。
总而言之,测试不是浪费时间,尤其是自动化测试,它实际上能为你节省大量时间,这是需要记住的关键点。
代码检查
代码检查 是Python等所有项目都应遵循的最佳实践。它可以检查不良语法,例如,如果你忘记为变量赋值,它能在代码部署到生产环境之前发现问题。
简而言之,代码检查的目的是在错误发生之前就捕获它们,并且可以自动执行。它还能增强自动化能力,当你在GitHub Actions或构建服务器上运行代码时,代码检查步骤能确保代码达到一定的质量标准。
Python虚拟环境
Python虚拟环境经常被误解,既然本节课会涉及,我们来简单讨论一下。
它们将Python隔离到一个特定的目录中。这允许Python解释器和相关库被安装在一个独立的目录里。以下是如何创建和使用虚拟环境的示例:
创建虚拟环境:
python3 -m venv ~/.your-project-venv
这条命令使用Python 3的venv模块,在你的主目录下创建一个名为.your-project-venv的隐藏目录(以点开头)。
激活虚拟环境:
source ~/.your-project-venv/bin/activate
activate脚本是一个Shell脚本,它告诉你的项目使用该目录下的Python环境。你将把所有代码和依赖安装在这个隔离的环境中,这能避免很多问题。
总而言之,使用Python虚拟环境是最佳实践,它能为你避免许多麻烦。虽然有很多复杂的理由推荐使用它,但总的来说,使用虚拟环境可以在问题出现之前就消除它们。
GitHub Actions简介
接下来,我们谈谈GitHub Actions。它是GitHub提供的一个基于SaaS的构建服务器,允许你进行持续集成。持续集成是一种自动化测试形式,当你提交代码时,这个基于SaaS的构建服务器会自动测试你的代码。如果你已经在使用GitHub,这将非常方便。
它基于YAML配置。YAML代表“YAML Ain‘t Markup Language”,它是一种高级、简单的配置文件格式,看起来非常易于人类阅读。你可以在其中定义一系列步骤,例如检查代码、测试代码、部署代码等。
简而言之,GitHub Actions是一个基于SaaS的持续集成服务器,我们将在课程后续部分深入探讨。
总结


本节课我们一起学习了搭建AWS云开发环境的基础。我们介绍了持续集成的概念,并解释了Makefile、自动化测试、代码检查以及Python虚拟环境等核心工具和最佳实践。我们还初步了解了GitHub Actions作为自动化构建和测试平台的作用。掌握这些概念是构建可靠、可扩展云解决方案的重要第一步。
019:持续集成介绍 🚀
在本节课中,我们将要学习持续集成(Continuous Integration, CI)的概念、重要性以及其基本工作原理。我们将通过类比和简单的技术流程,帮助你理解为什么CI是现代软件开发中不可或缺的一环。
什么是持续集成及其重要性
什么是持续集成,以及为什么你需要关心它?这是一个非常重要的问题。
在我教授学生构建软件或与公司进行咨询项目时,这个问题经常出现。很多时候,人们对此存在误解。他们认为进行自动化测试或编写测试是在浪费大量时间,但实际上,它能为你节省大量时间。
让我举几个例子。例如,为什么你的房子里要安装烟雾报警器?显然,你不想因为缺氧而在睡梦中无声无息地死去。所以,它是一种确保你生存的自动化方式。同样地,我们为什么要测试新药以确保其有效性?我们想确保为某种医疗状况提供的药物确实有益而非有害。再比如,你为什么要系安全带?安全带能确保在发生碰撞等突发事件时,防止你被抛出车外。
这些都是自动化测试和安全机制的形式,它们实际上拯救了你的生命。软件测试也是如此。持续集成是一种始终确保你的软件处于已知状态的方法,并且它实际上为你节省了时间。因此,关于持续集成,可能有两个重要的事情需要记住:你的软件状态始终是可知的(你知道它是正常工作还是出了问题),并且它实际上为你节省了时间,而不是耗费时间。
一旦你理解了这些概念,它就能真正让你以更快的速度开发软件。就像汽车的安全带类比一样,你知道有东西在保护你,因此可以随心所欲地加速。
持续集成的技术细节
上一节我们介绍了持续集成的核心价值,本节中我们来看看其技术实现细节。
很多时候,当你开始使用持续集成时,最好的步骤是从本地环境开始工作。
假设这是一个本地环境,它可以是Cloud9环境、台式机、笔记本电脑,或者任何你想要的机器。
以下是开始的基本步骤:
- 创建本地脚手架:你可以在这里创建一个Makefile,将测试文件放在你的项目中,或许还可以创建一个虚拟环境。
- 本地运行测试:然后,你可以执行例如
make test的命令,以确保代码正常工作。这会在本地得到一个表示成功的对勾标记。
一旦本地设置完成,下一步就是确保你的SaaS构建服务器(如GitHub Actions)已准备好自动测试你的代码。
我们假设这里是GitHub Actions。其内部发生的情况是,每次你对这个环境进行更改时,都会触发一个事件。这个事件本质上会检出(check out)你的代码,然后运行测试。就是这样。
所以,它实际上是一种将本地操作复制到云端SaaS构建服务器的方式。我们可以把这个服务器想象成云中的一个节点。
总而言之,所有持续集成所做的,就是以可重复的方式,自动化完成那些你手动重复执行的操作。在现实世界中,你可以看到很多这样的例子。例如,你不会想每次制造汽车时都手工打造,这就是为什么他们用工厂来制造。所以,持续集成就是一个自动测试你的代码并重复此过程的“测试工厂”,让你知道你的代码始终处于已知状态,并且它将为你节省时间。
核心概念与流程总结
本节课中我们一起学习了持续集成的核心概念。让我们用简单的公式和图示来总结其核心流程:
核心公式:
持续集成 (CI) = 本地自动化测试 + 云端自动验证
基本流程:
- 开发者在本地编写代码并运行测试(例如使用
make test)。 - 将代码提交到版本控制系统(如Git)。
- 提交操作触发云端CI服务器(如GitHub Actions)自动执行任务。
- CI服务器检出代码,运行与本地相同的测试套件。
- 根据测试结果,反馈构建状态(成功或失败)。


这个过程确保了软件质量的持续可控,正如我们之前讨论的,它像安全带和烟雾报警器一样,是一种重要的安全与效率保障机制。
020:使用AWS Cloud9进行云开发 🚀
概述
在本节课中,我们将学习AWS Cloud9,一个基于云的集成开发环境。我们将了解它如何解决云开发中的常见问题,并逐步演示如何创建和配置一个Cloud9环境,以及探索其核心功能。
什么是AWS Cloud9? ☁️
AWS Cloud9是一个基于云的集成开发环境。它解决了在云环境中开发时出现的许多问题。Azure云和GCP云也有类似的环境,它们都旨在解决同一个核心问题:你可以在代码将要运行的环境内部进行开发。
对于Cloud9而言,其工作原理是在AWS内部配置一台虚拟机。这台虚拟机相比你的个人笔记本电脑有几个优势。
Cloud9的优势
上一节我们介绍了Cloud9的基本概念,本节中我们来看看它具体解决了哪些开发痛点。
以下是使用Cloud9的几个主要优势:
- 权限管理:你可以为它分配基于角色的权限。这意味着你可以直接与AWS API通信,与其他服务交互,而无需管理访问密钥。从安全角度来看,这解决了许多问题。
- 网络性能:网络通信速度更快,因为你本质上是在实际的数据中心内部打开了一个终端。如果你的笔记本电脑连接着不稳定的无线网络,通信会遇到很多问题。但如果你在工作的实际环境中启动一个实例,你就能在数据所在的位置直接与其通信。
- 深度集成:这是Cloud9等工具的另一个关键方面,即能够与云服务深度集成。例如,你可以与无服务器计算服务AWS Lambda环境深度集成。你也可以深度集成命令行工具。
总而言之,如果你在为云环境进行开发,使用像AWS Cloud9这样的原生工具很可能会带来更好的体验。接下来,让我们实际操作一下。
创建Cloud9环境 🛠️
要开始使用AWS Cloud9,你需要登录你的AWS账户。
现在我们进入了AWS管理控制台,我将找到名为Cloud9的服务。我输入“cloud 9”,自动补全会给出结果。从这里,我可以创建一个新的Cloud9环境,所以我选择“Create environment”。
通常,给它起一个有意义的名称是个好主意。在这个例子中,我们将其命名为“cloud computing demo”。然后我会添加一个描述,例如“This is a demo environment”。点击下一步。
这里有几个关键点需要指出:对于大多数情况,尤其是学生用户,默认设置通常就足够了。尽管如此,我还是会指出几个关键功能。
这个部分显示“Create a new EC2 instance”,这允许你启动一个新的虚拟环境。这里还有一些其他高级选项,比如实例类型。
大多数时候,符合免费套餐资格的t2.micro实例类型是一个不错的选择,适合进行开发和完成教育项目。但Cloud9一个非常棒的功能是,如果我在这里选择“Other instance type”,我可以决定使用一台非常强大的机器。
例如,假设我想用一台72核、144GB内存的机器测试一些并行计算。大多数人没有机会接触这种硬件,但你可以实际启动一台,并且只按使用时长付费,从而测试一些计算密集型的操作。这也是Cloud9的一个关键特性:能够将你的实例扩展到多种不同的规格。
再次说明,我这里将选择默认设置。
关于平台,在大多数情况下保留默认设置可能是个好主意。有Amazon Linux、Amazon Linux 2可选,未来可能还会有Amazon Linux 3或Ubuntu Server。很多时候,默认设置会为你的项目开发提供最佳体验。在这个例子中,我将选择Amazon Linux 2,因为它包含的Python版本稍新一些。
另一个需要指出的点是“Cost-saving settings”。默认设置很好,因为如果你离开机器并关闭网页浏览器,它会自动休眠,保存所有设置,并且你不会被收取这些服务的费用。这也是一个很棒的功能。
这里还有一个关键点需要指出,就是“IAM role”。正如我之前提到的,使用AWS Cloud9的一个优势是,无论你登录哪个账户,相关角色都会自动关联。这样,你就不需要管理API调用的密钥,可以直接与S3等服务通信,来回拷贝数据。这是Cloud9环境免费提供的一个关键特性。

完成这些设置后,我点击“Next”。启动过程大约需要30到45秒。

探索Cloud9核心功能 🔍
现在AWS Cloud9已经启动,让我们来体验一下它的核心功能。
首先要注意的是左侧的“Environment”选项卡。如果你注意到它显示“~/environment”,这意味着如果我执行ls命令,这里只有一个README.md文件,这是驱动器的根目录。如果我输入pwd(打印工作目录)命令,你可以看到我的工作目录是/home/ec2-user/environment。
接下来,让我展示它已经预装了AWS命令行工具。例如,如果我输入aws s3 ls,我可以列出我账户中的所有存储桶。这非常有用。如果我还想拷贝数据,我可以直接在这里执行aws s3 cp命令。这确实是一个令人难以置信的功能:你免费获得了这个命令行工具,可以用它来与AWS的其他服务通信。


这里另一个需要注意的功能是,我也可以上传和下载文件。假设我想下载这里的README.md文件,我可以右键点击并选择“Download”,这允许我将其下载到本地机器。这是一个关键且非常有用的功能,可以让我在这个环境中处理数据。同样地,如果我想上传文件,比如一个CSV文件或一个想在此环境中运行的二进制文件,我也可以上传本地文件。


接下来,我要展示的另一个功能是,如果你点击右侧的这个选项卡,有几个非常有趣的功能。第一个是“Collaborate”(协作)。它的作用是允许你邀请其他人加入你的项目,并且你们可以实时聊天,进行结对编程。这对于课堂小组或公司里的团队合作非常有效。要做到这一点,你只需点击“Share”,然后邀请某人加入你的特定账户。这是一个非常棒的功能,我以前曾用它来调试生产环境中的问题。
如果我们接下来看“AWS Resources”选项卡,这是另一个令人难以置信的功能:我可以直接在Cloud9内部原生地创建AWS Lambda函数。如果我点击“Create a new Lambda function”,它允许我创建一个新函数,比如命名为“newLambda”或其他任何名称。点击“Next”,然后我可以从几个预装在此应用环境中的运行时中选择,例如Node.js、Python 3.6。从这里,我实际上可以选择不同的蓝图,然后配置应用程序。正如我之前谈到的,这种深度集成是Cloud9的关键特性之一。通常,从这里开始比从你的本地笔记本电脑开始更好。
另一个需要指出的点是,它有一个功能丰富的调试器,你可以设置断点并调试你的代码。
我们还将稍微了解另一个方面:假设我想在这里创建一个名为hello.py的基本Python文件,我可以使用touch命令,它会创建一个空文件。
touch hello.py
好的,让我们编辑这个hello.py文件。你可以看到它有语法高亮显示。我可以输入一些语句,比如def main(): return 1或其他任何我想做的,它会自动识别Python的正确语法。这里包含了许多非常强大的功能,使你能够直接构建云原生的应用程序,这就是Cloud9环境的关键优势。


总结 📝


本节课中,我们一起学习了AWS Cloud9云开发环境。我们了解了它如何通过提供基于角色的安全权限、优化的网络性能以及与AWS服务的深度集成来提升云开发体验。我们逐步演示了如何创建和配置一个Cloud9环境,并探索了其核心功能,包括内置的AWS命令行工具、文件上传下载、团队协作功能、原生Lambda函数创建以及强大的代码编辑器。掌握Cloud9将帮助你在云端更高效、更安全地进行开发和测试。
021:构建Python项目脚手架 🏗️
在本节课中,我们将学习如何为一个Python项目创建标准化的脚手架。这是一个可重复的流程,适用于你创建的每一个新项目。我们将从设置Git仓库开始,逐步创建项目所需的核心文件,并最终将其推送到GitHub。
创建Git仓库
首先,我们需要为项目创建一个新的Git仓库。这是管理代码版本和协作的基础。
以下是创建Git仓库的步骤:
- 访问GitHub网站。
- 点击“New repository”按钮创建一个新仓库。
- 将仓库命名为
scaffold。 - 添加描述,例如“This is a project scaffold for Python”。
- 务必勾选“Add a README file”选项。
- 在添加.gitignore文件的选项中,选择“Python”模板。这可以确保像
.pyc或.egg这类无关文件不会进入你的代码仓库。 - 点击“Create repository”完成创建。
配置SSH密钥并克隆仓库
上一节我们创建了远程Git仓库,本节中我们来看看如何在本地环境(如AWS Cloud9)中安全地连接并克隆它。我们将使用SSH密钥进行加密通信。
首先,我们需要生成SSH密钥对,并将公钥添加到GitHub账户。
以下是配置SSH连接的步骤:
- 在终端中运行命令生成RSA密钥对:
ssh-keygen -t rsa。 - 密钥对将默认保存在用户主目录的
.ssh文件夹中。 - 使用
cat命令打印出公钥文件(通常是~/.ssh/id_rsa.pub)的内容:cat ~/.ssh/id_rsa.pub。 - 复制输出的整个公钥字符串。
- 登录GitHub,进入“Settings” -> “SSH and GPG Keys”。
- 点击“New SSH key”,将复制的公钥粘贴进去,并为其命名(例如“scaffold”)。
- 保存后,即可在终端中使用SSH地址克隆仓库:
git clone git@github.com:你的用户名/scaffold.git。
创建项目基础文件
成功克隆仓库后,我们现在进入项目目录,开始创建脚手架所需的核心文件。
以下是需要创建的基础文件列表:
- Makefile:用于定义项目构建、测试、格式化等自动化任务。
- hello.py:项目的主脚本文件。
- test_hello.py:用于测试主脚本的测试文件。
- requirements.txt:列出项目所依赖的Python包。
在终端中,可以使用 touch 命令快速创建这些空文件:
touch Makefile hello.py test_hello.py requirements.txt
设置Python虚拟环境
为了隔离项目依赖,避免包冲突,最佳实践是使用Python虚拟环境。我们将创建一个与项目同名的虚拟环境。
运行以下命令创建虚拟环境:
python3 -m venv ~/.scaffold
此命令使用 venv 模块,在用户主目录下创建了一个名为 .scaffold 的隐藏虚拟环境。
创建后,需要激活它才能使用:
source ~/.scaffold/bin/activate
激活后,使用 which python 命令可以验证当前使用的Python解释器已指向虚拟环境内的路径。
编写Makefile
Makefile是项目的自动化指挥中心。我们将创建一个包含安装、代码检查、格式化和测试等任务的Makefile。
一个基础的Makefile内容如下,请注意,Makefile中的缩进必须使用制表符(Tab),而非空格:
install:
pip install --upgrade pip
pip install -r requirements.txt
format:
black hello.py
lint:
pylint --disable=R,C hello.py
test:
python -m pytest -vv --cov=hello test_hello.py
all: install lint test
install:升级pip并安装requirements.txt中列出的所有依赖包。format:使用black工具自动格式化hello.py代码。lint:使用pylint对hello.py进行代码风格和错误检查(此处禁用了部分冗余警告)。test:使用pytest运行测试,并输出详细结果和代码覆盖率。all:一个组合任务,可依次执行安装、代码检查和测试。
配置项目依赖
现在,我们来定义项目所需的第三方库。这些依赖将被记录在 requirements.txt 文件中。
以下是几个在Python项目中常用的工具库:
- pylint:代码静态分析工具,用于检查错误和代码风格。
- pytest:强大的测试框架。
- click:用于创建命令行界面的工具包。
- black:代码格式化工具,可自动调整代码格式。
- pytest-cov:生成测试覆盖率报告。
将这些库名称写入 requirements.txt 文件:
pylint
pytest
click
black
pytest-cov
你可以根据需要指定版本号,例如 pytest==7.0.0。首次搭建时,可以不固定版本以获取最新版。
保存文件后,即可运行 make install 来安装所有依赖。
编写示例代码与测试
脚手架搭建好后,我们开始编写实际的代码和对应的测试。这是验证我们设置是否正确的关键一步。
首先,在 hello.py 中编写一个简单的加法函数:
def add(x, y):
return x + y
if __name__ == "__main__":
result = add(1, 2)
print(f"This is the sum 1 and 2: {result}")
接着,在 test_hello.py 中为这个函数编写测试:
from hello import add
def test_add():
assert add(1, 2) == 3
现在,可以运行 make test 来执行测试。如果一切正常,你将看到测试通过和覆盖率报告。
代码质量检查与格式化
在提交代码之前,我们使用Makefile中定义的工具来保证代码质量。首先运行代码检查:
make lint
如果 pylint 提示有变量重定义等问题(例如在全局作用域定义了 x, y),你需要根据建议修改代码。例如,将 hello.py 中的直接赋值改为在函数调用中传入字面量值。
然后,运行代码格式化工具,让代码风格保持一致:
make format
black 工具会自动调整 hello.py 的格式(如缩进、空格),使其更规范、易读。
提交代码到GitHub

所有工作完成后,最后一步是将本地代码推送到远程GitHub仓库,为后续的持续集成做好准备。
以下是提交和推送代码的步骤:
- 使用
git status查看有哪些文件被修改或新增。 - 使用
git add .或git add *将所有变更添加到暂存区。 - 使用
git commit -m “添加初始项目结构”提交更改到本地仓库。首次提交时,Git可能会提示你配置用户名和邮箱。 - 使用
git push将本地提交推送到远程GitHub仓库。 - 刷新你的GitHub仓库页面,确认所有文件都已成功上传。
总结

本节课中我们一起学习了如何从零开始构建一个标准的Python项目脚手架。我们完成了从创建Git仓库、配置SSH、建立项目目录结构、设置虚拟环境,到编写自动化构建脚本(Makefile)、管理依赖、编写代码与测试,最后进行代码质量检查并推送到GitHub的完整流程。这个可重复的脚手架为后续实现持续集成和持续交付奠定了坚实的基础。
022:GitHub Actions 介绍 🚀
在本节课中,我们将学习如何为项目设置 GitHub Actions,以实现自动化测试和持续集成。我们将从零开始创建一个工作流,并了解其核心组成部分。
概述
上一节我们完成了项目的基础脚手架搭建。本节中,我们将进入最后一步:设置 GitHub Actions。这是一个自动化工作流工具,可以在代码推送时自动执行一系列任务,如安装依赖、代码检查、运行测试和格式化代码,从而确保代码质量。
创建工作流
以下是创建 GitHub Actions 工作流的步骤。
首先,在 GitHub 仓库中点击 Actions 图标。界面会显示一些预设的工作流模板,例如部署 Node.js 应用、容器或到 Google Cloud Kubernetes 服务。但我们选择从头开始设置。
我们选择设置一个默认工作流。系统会生成一个名为 main.yml 的 YAML 格式文件。这个文件定义了一个基本工作流。简单来说,它告诉 GitHub:当代码被推送到 master 或 main 分支时,执行一系列操作。如果你已经设置了 Makefile,这个过程会变得非常简单。
接下来,我将删除默认内容,并替换为一个我过去使用过的 GitHub Actions 配置。让我们看看其中的一些参数。
name: Python application test with Github actions
on: [push]
jobs:
build:
runs-on: ubuntu-latest
steps:
- uses: actions/checkout@v2
- name: Set up Python 3.8
uses: actions/setup-python@v2
with:
python-version: '3.8'
- name: Install dependencies
run: |
make install
- name: Lint with flake8
run: |
make lint
- name: Test with pytest
run: |
make test
- name: Format code
run: |
make format

工作流文件会被提交到 .github/workflows 目录下,文件名为 main.yml。你可以根据需要创建任意多个这样的文件,每个文件都会独立运行其定义的任务。例如,之后我们可以设置基于 Google Cloud 的部署或基于 Azure 的测试项目。
查看运行结果
要查看工作流的运行情况,可以返回 Actions 选项卡。你会看到最近运行的记录,例如“1分钟前”,耗时约29秒。点击记录可以查看详细步骤。
YAML 文件中的每一行都对应界面中的一个步骤。首先是设置任务,然后下载指定的虚拟环境(如 Ubuntu 18.04)。接着设置 Python 3.8,安装 CPython 3.8.6。之后,通过 make install 安装项目依赖。这一步验证了项目依赖是否正确。然后,通过 make lint 检查代码语法。每次代码变更都会自动验证项目是否正常工作。接着运行 make test 执行测试。最后,通过 make format 格式化代码。

添加状态徽章


为项目添加状态徽章是一个好做法。在构建主页面,点击“创建状态徽章”图标,然后复制徽章的 Markdown 代码。将其添加到项目的 README.md 文件中。

添加后,徽章会显示每次操作的结果(通过或失败)。这是基于 SaaS 的持续集成系统的一个非常有用的功能。
测试失败场景
为了测试工作流在代码出错时的反应,我们可以故意引入一个错误。首先,通过 git pull 拉取最新代码。然后,在代码文件(例如 hello.py)中添加错误的语法,比如一个未完成的变量定义。
# 这是一个错误的代码示例
bad_variable = # 缺少赋值


保存后,本地运行 make lint 会失败。我们提交这个错误代码以触发 GitHub Actions。
git add hello.py
git commit -m "添加错误代码以测试构建"
git push
推送后,GitHub Actions 会自动触发新的构建。在 Actions 选项卡中,可以看到构建状态变为橙色(运行中)。点击进入可以实时查看日志。构建会在 make lint 步骤失败,并给出具体错误信息(例如“第4行第5字符:无效语法”),这有助于调试。

要修复此问题,只需注释掉或更正错误的代码行,然后再次提交。提交后,工作流会重新运行,并通过所有检查。
核心价值与最佳实践


这个自动化构建步骤的核心价值在于它能自动确保项目代码的质量,并提供详细的输出信息。对于 Python 新手、数据科学初学者或编程新人来说,一个常见的误区是忽视自动化测试,认为它增加了额外工作量或看不到直接价值。然而,就像使用 Python 虚拟环境一样,设置持续集成只会帮助你产出更高质量的代码,并加快开发速度。因此,对于任何涉及 Python 的软件项目,这都是一项必需的最佳实践。
总结


本节课中,我们一起学习了如何为项目设置 GitHub Actions 工作流。我们创建了一个 YAML 配置文件,定义了在代码推送时自动执行的步骤(安装、检查、测试、格式化)。我们还学习了如何查看运行结果、添加状态徽章,以及如何通过引入和修复错误来测试工作流的有效性。掌握持续集成是保证代码质量和提升开发效率的关键实践。
023:设置 Amazon CodeCatalyst 🚀

在本节课中,我们将学习如何设置并使用 AWS 提供的一款令人兴奋的开发工具——Amazon CodeCatalyst。我们将从登录开始,逐步创建一个云端开发环境,并集成强大的 AI 编程助手 CodeWhisperer,让你体验无缝的云端开发流程。
登录与访问
首先,在 AWS 工具包中,我们可以看到包括 CDK、CodeWhisperer 以及 CodeCatalyst 在内的多个工具。要开始使用 CodeCatalyst,我们需要登录到构建者账户。
以下是具体步骤:
- 在工具包中选择 CodeCatalyst 并点击“开始”。
- 系统会提示我们连接 AWS 构建者 ID。点击“连接 AWS 构建者 ID 与 CodeCatalyst”。
- 这将打开一个配置文件页面,完成登录流程后,工具包中就会显示已登录状态。
登录成功后,我们便可以进行克隆代码仓库、打开或创建开发环境等操作。
创建开发环境
上一节我们完成了登录,本节中我们来看看如何创建一个全新的云端开发环境。
在 CodeCatalyst 界面中,点击创建新开发环境的按钮。系统会提供几个选项:
- 使用现有的 CodeCatalyst 代码仓库:如果你已有项目。
- 创建一个空的开发环境:这是探索和起步的推荐方式。
创建时,需要选择一个可用的“空间”和“项目”。我们可以将其作为一个临时项目,并为其设置一个别名(例如“delete-me”,以便后续识别和删除)。默认配置提供了 2 个 vCPU、4GB 内存、16GB 存储空间,并会在闲置 15 分钟后自动超时停止,这是一种节省成本的贴心设计。
注意:如果你为 CodeCatalyst 账户启用了计费,还可以选择启动配置更高的“大型环境”。为了演示,我们可以选择创建一个更大的环境。点击“创建开发环境”后,系统会自动打开一个新的 Visual Studio Code 窗口。
连接与验证
创建过程非常迅速和流畅。新窗口会自动建立 SSH 连接到远程机器。我们只需信任该连接即可。
环境准备就绪后,一个很好的习惯是打开终端进行验证。在终端中输入以下命令:
uname -a
此命令会显示系统信息,我们可以看到它运行的是 Amazon Linux。我们还可以输入:
whoami
来确认当前用户,它会显示与本地操作系统不同的云端用户身份。
集成 CodeWhisperer

现在我们已经有了一个可用的开发环境,接下来让我们集成 AWS 的 AI 编程助手 CodeWhisperer,以提升开发效率。
在 AWS 工具包中,找到 CodeWhisperer 并点击连接按钮。系统会再次引导我们完成登录授权流程:
- 点击“连接 AWS 构建者 ID 与 CodeWhisperer”。
- 在浏览器中确认并允许访问。
- 关闭授权窗口,回到开发环境。

完成设置后,工具包中 CodeWhisperer 的图标会显示为已激活状态。现在,我们就可以开始使用它了。
开始云端开发
一切就绪,让我们开始编写一些简单的代码来体验这个组合的强大功能。
首先,创建一个新文件,例如 hello.py。在文件中,我们可以尝试输入一些注释或代码开头,CodeWhisperer 会自动提供建议。
例如,输入:
# hello world python
def hello():
CodeWhisperer 很可能会自动补全一个 print("Hello World") 的函数体。这样,我们就快速得到了一个完整的 “Hello World” 示例。
同样,我们也可以尝试编写 Bash 脚本。新建一个文件,输入:
#!/bin/bash
# scan dynamodb table called customers
aws dynamodb scan
根据注释的上下文,CodeWhisperer 会帮助我们补全更具体的命令参数。
可以看到,CodeCatalyst 提供的云端开发环境与 CodeWhisperer 的 AI 辅助编程相结合,是一个强大的组合。它设置简单,在免费套餐中即可使用,同时也支持按需启动更强大的机器来满足大型项目的开发需求。

本节课中,我们一起学习了如何设置 Amazon CodeCatalyst 云端开发环境,从登录、创建环境到集成 CodeWhisperer AI 助手。这个工具组合让开发者能够快速获得一个配置好的、可随时访问的云端工作站,并借助 AI 提升编码效率,是进行现代云端应用开发的利器。
构建大规模云计算解决方案:1-2:AWS CodeWhisperer:自然语言转Bash CLI
在本节课中,我们将学习如何使用AWS CodeWhisperer工具,通过自然语言指令来生成并执行Bash命令行操作,从而提升在Shell环境中的工作效率。
AWS CodeWhisperer不仅是一个代码助手,它还能直接理解你的自然语言描述,并为你生成相应的Shell命令。这对于执行复杂查询或学习新命令非常有帮助。
接下来,我们将通过几个具体示例来演示其功能。
首先,我们可以在Shell中直接输入一个以#开头的自然语言问题。
例如,我们可以询问如何递归地统计当前目录下的所有文件数量。
输入指令后,按回车键,CodeWhisperer会提供一个命令建议。
我们可以执行它生成的命令:find . -type f | wc -l。
执行结果显示当前工作目录下共有256,000个文件。
这个工具的另一个优点是它具有教育意义。
你可以将生成的常用命令保存为别名(alias)或函数,集成到你的Shell配置文件中。
例如,你可以将统计文件的命令保存为一个别名,方便日后快速调用。
这样不仅能即时解决问题,还能帮助你系统地学习和积累Shell知识。
除了使用#提示符,CodeWhisperer还支持另一种更详细的提问方式。
你可以输入cw ai来启动一个更长的交互会话。
在这种模式下,你可以提出更复杂的问题。

例如,你可以询问如何查找所有CPU使用率超过10%的进程。

CodeWhisperer会生成一个相应的复杂命令,例如ps aux | awk ‘$3 > 10 {print $0}’。
执行该命令后,屏幕上会列出所有符合条件的进程信息。
在我看来,这个功能非常宝贵。
以下是使用AWS CodeWhisperer的几个主要优势:
- 直接生成命令:无需离开终端去搜索谷歌或Stack Overflow。
- 辅助学习:通过观察生成的命令,你可以逐步构建自己的命令行知识。
- 提升效率:它不仅仅是一个助手,更能实质性地让你变得更高效。
因此,如果你有机会,一定要尝试一下AWS CodeWhisperer这个工具。
它非常强大。其CLI功能可能是一个尚未被广泛认知的“隐形”利器。
你可以免费使用它,并在macOS等系统上通过原生扩展轻松安装。

本节课中,我们一起学习了如何利用AWS CodeWhisperer,通过自然语言指令来生成和执行Bash命令。我们看到了它如何将复杂的查询转化为可执行的命令行操作,以及如何通过保存别名来积累知识。这是一个能显著提升在Shell环境中工作效率和学习速度的强大工具。
025:Azure云开发介绍
在本节课中,我们将学习如何创建一个Azure云开发环境。我们将探讨测试和代码检查的重要性,构建基于Azure Cloud Shell的持续集成环境,并最终配置GitHub Actions来实现端到端的自动化测试流程。
学习目标
以下是本节课我们将要完成的主要任务:
- 评估测试与代码检查的优势:我们将深入了解软件测试和代码检查(Linting)带来的具体好处。
- 构建Azure Cloud Shell持续集成环境:我们将在Azure内部搭建一个完整的开发环境,并配置持续集成与测试流程。
- 开发用于Azure的GitHub Actions测试:我们将建立一个完整的端到端工作流水线,实现自动化测试。
在深入实践之前,让我们先系统地了解一下本课将涉及的测试类型。
测试类型概述
上一节我们明确了学习目标,本节中我们来看看软件测试有哪些不同的类型。我们已经简单讨论过测试,现在让我们更全面地了解它们。
软件测试包含多种类型,每种类型关注不同的层面:
- 单元测试:这是低层级的测试,针对代码中的最小可测试单元(如函数、方法)进行验证。
- 集成测试:这种测试用于验证不同的模块或服务是否能良好地协同工作。
- 功能测试:这种测试旨在验证应用程序的业务需求是否得到满足,例如,一个网络服务是否返回了正确的状态码。
- 端到端测试:这是一种模拟用户行为的方式。例如,一家游戏公司可以模拟游戏的实际玩法来进行测试。
- 验收测试:这是一种形式化的验证方式,用于确认系统是否符合预定的验收标准。例如,验证一个薪资应用程序是否能正确发出付款。
- 性能测试或负载测试:这种测试用于评估应用程序在负载下的性能表现。
- 基本健全性测试:这种测试用于快速验证应用程序的基本功能是否正常。结合一些探索性数据分析,可以确保系统运行正常。
总而言之,测试的类型多种多样,包括单元测试、集成测试、探索性测试、健全性测试等。当我们进入细节部分时,会对此进行更深入的探讨。




本节课中,我们一起学习了创建Azure云开发环境的整体目标,并系统回顾了软件测试的主要类型,为后续动手构建持续集成和自动化测试流水线打下了理论基础。
026:测试介绍 🧪

在本节课中,我们将要学习软件测试的核心概念、重要性以及如何制定一个“恰到好处”的测试策略。我们将通过一个真实的故事来理解测试如何帮助解决重大危机,并探讨测试的实践原则。
什么是测试?如何用它摆脱困境?
测试是什么?你如何利用它让自己摆脱大麻烦?我想分享一个职业生涯中期的故事。当时我在一家电影公司工作,我们遇到了一个非常严重的问题。事实上,整个价值数亿美元、拥有数百名员工的设施陷入了停滞,无法继续工作,而我们有一个不可更改的截止日期。一部电影将在圣诞节上映,海报已经贴出,迪士尼是背后的支持者。除了深入挖掘并找出解决方法,我们别无他法。
我们采取的第一步是:在一个模拟环境中让某种测试运行起来。这可能是你摆脱大麻烦可以做的第一件事:我能否将生产环境复制到某个地方?即使你没有设置持续交付类型的环境,通常也可以通过在某处运行模拟来摆脱困境。一旦你至少能运行它,你就可以验证某些事情是否按预期进行。
制定你的测试策略
上一节我们介绍了测试在危机中的作用,本节中我们来看看如何制定一个有效的日常测试策略。
正如之前提到的,“恰到好处”的策略是思考测试的重要方式。你既不想做得太多,也不想做得太少。你希望有足够的测试来确保你的工作有效。另一个需要牢记的是判断力。如果你怀疑应用程序的某个部分可能有问题,那就为此编写一个测试。这是你应对潜在麻烦的一种方式。
测试能为你节省时间,它们不是时间的浪费者。我认为这可能是最常见的初学者错误:人们因为忙于调试代码而不编写任何测试。但测试的本质是,它是你已经调试过的代码,并且你无需再次调试相同的东西。为什么你要日复一日、年复一年地反复添加打印语句并将变量传入函数,而不是直接编写一个测试来验证你的代码是否工作呢?我认为这是我看到的最常见的错误之一。
最后是自动化。一旦你的测试开始运行,你必须将其自动化,以便构建服务器(或在 GitHub Actions 的情况下)能够自动运行测试。这真正为你提供了持续改进的机会。你可以不断地、每日甚至多日地确保你的代码正在变得更好,你了解正在发生的事情,并且它处于一种持续改进的状态。有一个词可以形容这个概念:改善。因此,改善或持续改进是测试的目标,也应该是你的策略。
总而言之,你希望的是“恰到好处”的策略。这里只需要一点,但不要太多。
本节课总结


本节课中我们一起学习了测试的核心价值。我们通过一个真实案例看到,在模拟环境中建立测试是解决重大生产问题的第一步。我们探讨了制定测试策略的关键:追求“恰到好处”的平衡,运用判断力针对怀疑点编写测试,理解测试是节省时间的调试代码,以及实现自动化以实现持续改进。最终,测试的目标是支持改善这一理念。
027:使用Azure Cloud Shell进行云开发 💻
在本节课中,我们将学习如何使用Azure Cloud Shell环境进行云开发。Azure Cloud Shell是一个基于浏览器的命令行体验,它直接运行在Azure云中,是开始云开发工作的理想起点。
上一节我们介绍了云开发的基本概念,本节中我们来看看Azure Cloud Shell这个核心工具。它本质上是一个运行在Azure数据中心内的“迷你云”环境。推荐从这里开始开发的主要原因是,这里就是云本身。在这个环境中,你可以访问高速网络连接、拥有适当的角色权限、访问存储,并可以直接部署平台即服务(PaaS)应用。因此,它是控制和编排一切的主要场所。
我的建议是,在云上进行开发时,应使用这种基于云的开发环境。这样,你就不必依赖不稳定的无线网络连接或在本地与云端之间来回复制数据。你可以直接进入云端环境进行应用开发。
接下来,让我们深入了解Azure Cloud Shell的一些功能特性。
启动与基础功能 🚀

要开始使用Azure Cloud Shell,你需要点击门户中的Cloud Shell图标。选择后,它将启动一个基于Bash的云环境。首次使用时,你需要创建一个订阅和一个存储位置,这个过程非常简单直接。
以下是Azure Cloud Shell环境的一些核心功能:
- Azure CLI命令:你可以直接使用内置的Azure CLI命令。输入
az命令可以获取帮助,查看可运行的各种命令。例如,你可以配置、升级、管理Web应用(如基于Flask的PaaS应用)等。所有操作都可通过命令行界面完成,这是该环境的关键优势之一。 - 运行Python:环境中预装了Python。输入
python --version可以查看当前运行的Python版本(例如Python 3.5.2),这为开发提供了良好的支持。
集成编辑器与高级功能 ✏️



除了命令行,Azure Cloud Shell还集成了一个功能齐全的代码编辑器。点击编辑器图标即可打开。
打开后,你可以调整界面大小,实现终端在下、代码在上的并排布局。在这个编辑器中进行的修改会直接与云环境交互。你可以通过菜单轻松关闭编辑器,回到纯终端界面。
这个环境提供了开发完整项目所需的许多功能:
- 文件操作:你可以使用图标进行文件上传、下载、创建新文件等操作。
- 会话管理:可以开启新的会话。
- Shell切换:你可以在Bash和PowerShell之间自由切换。


总结 📝



本节课中我们一起学习了Azure Cloud Shell。其主要优势在于它是一个功能完整的原生云开发环境。它直接运行在Azure基础设施上,提供了命令行工具、代码编辑器和项目开发所需的各种功能。因此,我强烈建议在初次开始云配置和开发时,将Azure Cloud Shell作为你的起点。
028:Azure Cloud Shell 从零开始持续集成 🚀
在本节课中,我们将学习如何在 Azure Cloud Shell 环境中设置一个 Python 项目,进行本地测试,并最终通过 GitHub Actions 实现自动化持续集成。我们将从创建虚拟环境开始,逐步配置项目,使其能在 Azure 的特定 Python 版本下运行,并利用 GitHub Actions 同时测试多个 Python 版本。
创建 Python 虚拟环境
上一节我们介绍了 Azure Cloud Shell 的基本设置,本节中我们来看看如何为项目创建独立的 Python 运行环境。
首先,我们需要创建一个 Python 虚拟环境。这能确保项目依赖与其他项目隔离。

以下是创建虚拟环境的命令:
python3 -m venv ~/scaffold
此命令使用 venv 模块,在用户主目录下创建了一个名为 scaffold 的虚拟环境。

接下来,我们需要激活这个虚拟环境:
source ~/scaffold/bin/activate
激活后,当前终端会话将使用虚拟环境中的 Python 解释器。可以使用 which python 命令来验证。

配置 SSH 密钥与克隆仓库
为了与 GitHub 仓库进行安全通信,我们需要生成并配置 SSH 密钥。
以下是生成 SSH 密钥的命令:
ssh-keygen -t rsa
连续按几次回车键接受默认设置即可。生成后,使用以下命令查看公钥内容:
cat ~/.ssh/id_rsa.pub
复制输出的公钥内容。
然后,请按照以下步骤在 GitHub 上添加 SSH 密钥:
- 登录 GitHub,进入 Settings。
- 在侧边栏找到 SSH and GPG keys。
- 点击 New SSH key,将复制的公钥粘贴进去,并为其命名(例如“Azure scaffold”)。
完成配置后,即可使用 SSH 方式克隆项目仓库。在 Cloud Shell 中执行:
git clone git@github.com:your-username/your-repo.git
调整项目以适应 Azure 环境
Azure Cloud Shell 默认可能使用较旧的 Python 版本(如 3.5),这可能导致项目代码或依赖不兼容。我们需要对项目进行适配。
首先,进入项目目录并创建一个专用于 Azure 环境的依赖文件:
cd scaffold
touch requirements-azure.txt
然后,编辑 requirements-azure.txt 文件,移除或替换那些不支持 Python 3.5 的包(例如特定版本的代码格式化工具 black)。
接着,检查项目代码。Python 3.5 不支持 f-string 语法,需要将其替换为旧式的字符串格式化方法。例如,将:
print(f"The result is {result}")
修改为:
print("The result is %s" % result)
为了便于管理,我们可以在 Makefile 中添加一个专门为 Azure 环境安装依赖的命令:
install-azure:
pip install -r requirements-azure.txt
这样,通过运行 make install-azure 即可安装适配后的依赖包。
完成代码修改和依赖调整后,运行 make lint 和 make test 在本地进行验证,确保一切正常。

提交代码并配置 Git
本地测试通过后,将修改提交到 GitHub 仓库。
以下是提交代码的标准步骤:
git add .
git commit -m "Adding Azure compatible version"
首次提交时,可能需要配置 Git 用户信息:
git config --global user.email "you@example.com"
git config --global user.name "Your Name"
配置完成后,推送代码到远程仓库:
git push


配置 GitHub Actions 进行多版本测试

上一节我们完成了代码的本地适配和提交,本节中我们来看看如何利用 GitHub Actions 的强大功能,自动测试项目在多个 Python 版本下的兼容性。
目标是让 GitHub Actions 同时运行两个工作流:一个测试 Python 3.8(或其他较新版本),另一个专门测试 Python 3.5(模拟 Azure 环境)。
为此,我们需要在项目的 .github/workflows/ 目录下创建一个新的工作流文件,例如 azure.yml。
该工作流的核心是定义一个使用 Python 3.5 的作业。关键配置如下:
jobs:
build:
runs-on: ubuntu-latest
strategy:
matrix:
python-version: ["3.5"]
steps:
- uses: actions/checkout@v2
- name: Set up Python ${{ matrix.python-version }}
uses: actions/setup-python@v2
with:
python-version: ${{ matrix.python-version }}
- name: Install dependencies
run: |
make install-azure
- name: Lint with pylint
run: |
make lint
- name: Test with pytest
run: |
make test
请注意,安装依赖的步骤我们指定为运行 make install-azure,以确保使用为 Python 3.5 适配的 requirements-azure.txt 文件。
提交这个工作流文件后,GitHub Actions 会自动触发。在 Actions 页面,你可以看到两个作业在并行运行:一个是原有的 Python 3.8 测试,另一个是新添加的 Python 3.5 测试。


为了让界面更清晰,你可以将原有工作流中的作业名称从“Python application test”改为“Python 3.8 Test”。这样,不同版本的测试结果一目了然。



总结
本节课中我们一起学习了如何在 Azure Cloud Shell 中配置 Python 项目并实现持续集成。我们完成了以下关键步骤:
- 创建并激活虚拟环境,隔离项目依赖。
- 配置 SSH 密钥并克隆仓库,建立与 GitHub 的安全连接。
- 适配代码与依赖,解决因 Azure 环境 Python 版本较旧导致的兼容性问题。
- 提交代码并配置 Git,将修改推送到远程仓库。
- 配置 GitHub Actions,创建并行工作流来同时测试项目在 Python 3.8 和 Python 3.5 下的运行情况。


通过结合 Azure Cloud Shell 的便捷性与 GitHub Actions 的自动化能力,我们构建了一个能够跨不同云环境(如 Azure、AWS)进行一致性测试的稳健工作流。这确保了代码的可靠性和可移植性,是构建大规模云解决方案的重要实践。
029:GCP云开发介绍 🚀
在本节课中,我们将创建一个Google云开发环境。我们将探讨在云Shell中进行开发的一些关键组件,并构建一个从零开始的持续交付管道。
学习目标 🎯
首先,我们来明确本课的学习目标。我们将解释什么是持续交付,这是本节课将结合GCP(Google Cloud Platform)本身来介绍的一个核心概念。我们还将学习如何设置一个云Shell开发环境,它与其他云Shell环境有很多相似之处,但我们会特别介绍Google Cloud Shell的不同之处。最后,我们将从零开始构建一个持续交付管道,逐步构建一个项目并自动将其部署到Google Cloud Shell中。
持续交付的核心概念
上一节我们明确了学习目标,本节中我们来深入了解一下核心概念——持续交付。持续交付是一种软件开发实践,它确保代码可以随时被可靠地发布到生产环境。其核心思想是通过自动化的构建、测试和部署流程,来缩短软件交付周期并提高质量。
一个典型的持续交付流程可以用以下简化的代码流程来描述:
代码提交 -> 自动构建 -> 自动测试 -> 自动部署到预发布环境 -> 手动批准 -> 自动部署到生产环境
Google Cloud Shell 开发环境
了解了持续交付的概念后,我们来看看实现它的工具之一:Google Cloud Shell。Cloud Shell是一个基于浏览器的命令行环境,预装了Google Cloud SDK和其他开发工具,让你能快速开始在GCP上进行开发和管理。
以下是Google Cloud Shell的一些关键特性:
- 开箱即用:无需在本地安装任何软件,通过浏览器即可访问。
- 预配置环境:已预装
gcloud命令行工具、Docker、Kubernetes工具等。 - 持久化存储:你的
$HOME目录有5GB的持久化存储空间。 - 内置代码编辑器:包含一个基于Web的代码编辑器,方便你编辑文件。
构建持续交付管道
现在,我们已经熟悉了Cloud Shell环境,本节我们将动手实践,从零开始构建一个简单的持续交付管道。我们将创建一个基本的应用,并为其设置自动构建和部署流程。
以下是构建管道的主要步骤:
- 初始化项目:在Cloud Shell中创建一个新目录和项目文件。
- 编写应用代码:创建一个简单的Web应用(例如,使用Python Flask)。
- 创建构建配置文件:编写一个
cloudbuild.yaml文件,定义构建步骤。 - 配置触发器:在Google Cloud Build中设置触发器,使其在代码推送到代码仓库时自动运行构建。
- 部署应用:将构建好的应用容器部署到Cloud Run等托管服务。
通过以上步骤,我们就建立了一个基本的持续交付管道。当你将代码更改推送到仓库时,Cloud Build会自动执行构建和部署,实现快速迭代。

总结 📝

本节课中我们一起学习了Google Cloud Platform的云开发基础。我们首先介绍了持续交付的概念及其自动化流程。接着,我们探索了Google Cloud Shell这一强大的在线开发环境及其特性。最后,我们通过一个从零开始的实践,逐步构建了一个能够自动构建和部署应用的持续交付管道。掌握这些是开始在GCP上进行高效云开发的第一步。
030:GCP开发环境入门 🚀

在本节课中,我们将学习如何开始使用Google Cloud Platform(GCP)的免费套餐,并设置一个基础的开发环境。我们将涵盖从访问控制台、使用Cloud Shell,到配置Python和Rust开发环境,以及管理虚拟机实例的完整流程。
了解Google Cloud免费套餐
首先,我们来了解Google Cloud的免费套餐。注册免费套餐后,你可以访问20多种免费产品,并获得300美元的免费信用额度。这些信用额度需要在三个月内使用。免费套餐包含的部分产品有:Compute Engine、Cloud Storage、BigQuery、Kubernetes、App Engine、Cloud Run、Cloud Build、Stackdriver、Filestore、Pub/Sub、Cloud Functions、Vision AI、Speech-to-Text、Natural Language API、AutoML等。实际上,这里提供了非常丰富的免费服务。
访问云控制台
现在,让我们开始操作。首先进入云控制台仪表板。在这里,你可以看到所有内容的概览。首先是项目信息,在这里你可以决定如何添加项目成员、配置项目设置等。仪表板中间区域显示了你最近访问的一些服务。右侧还有一个资源选项卡,可以切换查看不同的资源,例如,如果你想启动一台虚拟机。右侧还显示了状态信息。当你使用GCP时,这个仪表板将是你最常使用的起点。请注意,我在这里选择了一个项目。如果我想创建一个新项目,可以点击“选择项目”并创建新项目。

启动Cloud Shell
对于GCP的初学者,我建议首先启动Cloud Shell。Cloud Shell非常方便,因为它允许你立即开始构建解决方案,并在这个环境中尝试各种想法。
上一节我们介绍了如何访问控制台,本节中我们来看看如何利用Cloud Shell搭建开发环境。
以下是启动Cloud Shell后的第一步操作:
-
创建Python虚拟环境:我喜欢做的第一件事是创建一个Python虚拟环境,以便在Cloud Shell中测试和运行Python项目。使用以下命令:
python3 -m venv .venv这将在主目录下创建一个隐藏的虚拟环境目录。
-
配置环境自动激活:接下来,我喜欢编辑我的
.bashrc文件。在文件底部添加一行,以便每次打开环境时自动激活Python虚拟环境:source .venv/bin/activate这是一个实用的小技巧,可以避免许多与Python相关的奇怪问题。


-
克隆代码仓库:如果我想访问一个包含代码的仓库(例如,这里有一些Python代码),并且不想推送更改回去,我可以直接在这个环境中使用
git clone命令。例如:git clone <仓库URL>克隆后,我可以进入该仓库目录。
-
使用Makefile:我喜欢使用Makefile,因为它能让我使用快捷命令。我们可以打开编辑器查看代码,这是GCP内部一个很好的资源。在目录中,我们可以看到Makefile,其中包含了
install、test、format、lint、container、refactor等常见操作命令。这在GCP环境中工作时非常普遍,教程中也会看到类似的内容。 -
测试环境:让我们通过运行
make install和make lint来测试一下。make install会根据requirements.txt文件安装所有必需的包。安装完成后,运行make lint来检查代码格式。如果成功,说明我们的环境配置正确。我们还可以查看main.py文件,了解这个简单应用程序的结构。


安装Rust开发环境
现在我们已经让Python正常运行了,接下来还能做什么呢?我们还可以安装Rust。Rust是一门系统编程语言,其性能根据任务不同,可能比Python快40倍到1000倍。因此,如果你需要进行高性能计算,Rust是一个非常好的选择。
以下是安装Rust的步骤:
- 访问
rustup.rs网站,复制安装命令。 - 在Cloud Shell中粘贴并运行该命令。这将下载并安装Rust环境,包括
cargo(Rust的包管理器)和clippy(代码检查工具)。安装程序会自动将其添加到系统路径中。 - 安装完成后,我们可以创建一个新的Rust项目来测试。使用命令:
这会在当前目录创建一个名为cargo new hellohello的示例项目目录。 - 进入项目目录,与Python不同,你几乎不需要任何额外步骤,直接运行:
程序会被编译并运行,输出“Hello, world!”。cargo run - 我们可以查看项目结构,里面有一个非常简单的
main.rs文件。如果需要添加依赖(例如GCP SDK),可以在Cargo.toml文件中进行配置。


管理虚拟机实例
最后,我们将学习如何启动和管理虚拟机实例。在GCP控制台中,我们可以进入Compute Engine部分。如果我想创建一个新实例,可以点击“创建实例”并选择机器类型。例如,启动一个微型实例时,界面会显示预估的月度费用(实际上按小时计费),这让你对成本有清晰的了解。如果选择一个大型机器(例如32核),月度费用可能高达500美元。因此,在启动机器时,务必注意查看不同的配置和费用指标。
由于我已经有一个正在运行的实例,我可以通过命令行来查看和管理它。在GCP教程中,使用命令行列出和管理机器是非常常见的操作。
以下是使用命令行管理实例的方法:
- 你可以通过运行
history命令查看最近使用过的命令,找到类似gcloud compute instances list的命令。 - 运行
gcloud compute instances list可以列出当前项目中的所有虚拟机实例。 - 你还可以使用
gcloud compute instances命令来执行更多操作,例如启动或停止实例。使用--help参数可以获取特定命令的更多信息。
GCP在很大程度上是一个面向命令行的服务,因此,如果你熟悉命令行操作,在使用Google Cloud时将获得极佳的体验。


本节课中我们一起学习了如何利用GCP免费套餐入门,包括访问控制台、设置Cloud Shell开发环境(配置Python和Rust),以及通过控制台和命令行两种方式管理Compute Engine虚拟机实例。这些是开始使用Google Cloud进行开发的基础步骤。
031:持续交付介绍 🚀
在本节课中,我们将要学习持续交付(Continuous Delivery)的核心概念。这是一种现代软件开发的最佳实践,旨在确保代码始终处于可部署状态,无论是应用程序本身还是运行它所需的基础设施。
什么是持续交付?
如果你曾接触过软件团队,你很可能听说过“持续交付”这个术语。这个术语意味着代码始终处于可部署状态,这既包括应用程序软件,也包括运行代码所需的基础设施。对于需要部署到云端的代码而言,这确实是一种现代最佳实践。
在过去,由于只有物理服务器,想要实现完全自动化的基础设施非常困难。如果你想拥有另一个版本的基础设施,就必须购买另一台服务器。而在云端,一切都是虚拟化的,因此你可以使用基础设施即代码来自动化并创建几乎无限数量的新环境。
如果构建服务器被设置为监听你的源代码控制仓库,代码就可以经历一系列操作:一个测试阶段、一个Lint阶段,可能还有一些负载测试。然后,你的基础设施即代码会检查基础设施,确保其设置正确,并最终部署该代码。
因此,这确实是云原生应用程序的现代软件工程最佳实践,所有公司都应该采用类似的方法。
持续交付的工作原理
上一节我们介绍了持续交付的理论概念,本节中我们来看看它的具体工作细节。
其工作方式如下:作为用户的你,可能在笔记本电脑上开发代码,然后将代码检入一个源代码控制仓库。通常,你会有一个主分支(例如 master),这是默认分支。GitHub(或类似平台)是将其连接到特定环境的地方。
这意味着当你做出更改时,一个构建服务器(这可以是多种类型,例如 GitHub Actions、Jenkins 或 AWS Code Build 等云原生服务)会开始工作。这里的核心思想是,所有工作都在这个构建服务器中完成。
以下是构建服务器执行的主要步骤序列:
- 检出代码:构建服务器检出你告知特定任务要监听的分支。
- 代码检查与测试:服务器对你的代码进行 Lint 检查(代码风格和质量检查)和测试。
- 基础设施即代码检查:服务器查看基础设施即代码配置(这可能是 Terraform、CloudFormation 或其他如 Pulumi 等工具)。
- 环境更新或创建:基础设施即代码允许你动态更新现有环境,甚至创建一个全新的环境。
通常,这个环境会直接映射到你源代码控制中的分支。例如:
- 开发分支:映射到开发环境。
- 预发布分支:映射到预发布环境。
- 生产分支:映射到生产环境。
这种做法的好处是,你可以将代码推送到开发分支(这可能是你大部分时间工作的地方)。当你准备好测试一个将来要上生产环境的变更时,可以将其合并到预发布分支。系统会自动执行 Lint 检查、测试代码,并将其部署到预发布环境。然后,你可以进行非常广泛的负载测试,以验证你的 Web 应用程序是否可以扩展到 10 万用户。
测试完成后,你可以决定将其合并到生产分支。合并后,系统会执行相同的流程:从预发布合并到生产的代码会经历 Lint 检查、测试,然后部署到生产环境。
核心思想与总结
本节课中我们一起学习了持续交付的机制。其核心思想是,你正在构建一个“软件工厂”。这个工厂就像任何其他工厂一样,你需要质量控制,需要自动化。只不过在这个案例中,工厂生产的是软件,而部署目标是云端的基础设施。
因此,持续交付意味着你的代码始终处于可部署状态。这并不一定意味着你必须自动将其推送到生产环境,因为你可以将其暂存在预发布环境中。但当确实需要推送到生产环境时,你可以通过将代码合并到生产分支来自动完成这一过程,使其经过一系列质量控制测试,然后实际部署出去。


简而言之,持续交付通过自动化构建、测试和部署流程,将软件发布变得可重复、可靠且高效,是云时代软件开发的关键实践。
032:使用Google Cloud Shell进行云开发 🚀
概述
在本节课中,我们将学习如何使用Google Cloud Shell进行云开发。Google Cloud Shell是一个基于浏览器的命令行环境,预装了开发工具,并直接集成在Google Cloud Console中,是开始云上项目的理想起点。
启动与探索Cloud Shell
上一节我们介绍了云平台的基本概念,本节中我们来看看如何启动并使用Google Cloud Shell。

这是Google Cloud Platform控制台。与其他云平台类似,它也提供了一个Cloud Shell环境。对于Python开发者,尤其是在该云平台上开始工作时,我推荐使用这个环境。你可以通过点击控制台右上角的图标并选择“激活Cloud Shell”来找到它。
点击后,系统将启动一个云端终端。该终端预装了一些非常有用的工具,例如特定版本的Python和一些Google Cloud Platform的命令行工具,这些工具可用于执行管理任务。这确实是云Shell环境如此重要的核心功能之一。可以说,这是大多数项目的默认起点。
激活并打开Shell后,我首先建议进行一些简单的探索。
以下是你可以尝试的几个步骤:
- 输入
which python命令,查看系统中Python的安装位置。 - 运行
python命令,启动Python解释器。注意,当前环境可能默认是Python 2。 - 运行
python3命令,检查是否安装了Python 3。

配置Python开发环境
了解了基本环境后,接下来我们需要配置一个独立的Python开发环境。
我建议创建一个虚拟环境。在Google Cloud Shell中,你可以通过两种方式之一来完成。系统已预装了名为 virtualenv 的工具。因此,我可以输入 virtualenv 命令来创建新环境。
以下是创建和激活虚拟环境的步骤:
- 运行命令
virtualenv ~/.gcp-cloud来创建一个名为.gcp-cloud的隐藏虚拟环境。 - 运行命令
source ~/.gcp-cloud/bin/activate来激活这个虚拟环境。

从GitHub克隆并运行项目
环境配置好后,我们就可以开始实际的开发工作了。下一步通常是获取代码并运行它。
我将开始处理一个GitHub仓库。我会导航到我已设置好的一个仓库,并克隆它。这个仓库包含了我所需的一切:用于测试代码的GitHub Actions工作流,以及一个非常简单的“hello”文件,它只是将一些数字相加。
以下是克隆和设置项目的流程:
- 在首次与GitHub通信前,你需要创建SSH密钥。可以使用命令
ssh-keygen -t rsa来生成,然后连续按回车键接受默认设置。生成公钥后,需要将其添加到你的GitHub账户中。 - 在GitHub仓库页面,点击“Code”按钮,确保选择“SSH”选项,复制仓库的SSH地址。
- 在Cloud Shell中,使用
git clone <仓库SSH地址>命令克隆仓库。 - 进入克隆的目录,使用
git pull命令检查并拉取任何更新。
现在,如何运行这些代码呢?因为我喜欢使用Makefile,所以可以输入 make install 命令。这个命令会检查并安装任何需要的新软件包。系统会开始安装这些更新。

使用云端集成开发环境
如果你不太喜欢在命令行中完成所有工作或使用命令行编辑器,Cloud Shell还提供了一个完整的IDE。
我可以点击“打开编辑器”图标,然后调整窗口,就能访问一个功能齐全的IDE。我可以在这里进行各种操作,构建完整的项目。
让我们找到我正在处理的项目。它叫做“GitHub actions demo”。如果我选择Makefile,就能看到它的内容。如果我打开“hello”文件,也能看到其中的代码。如果需要,我可以在这里直接修改文件。
这里的主要收获是:就像你的笔记本电脑一样,Google Cloud Platform中的云环境拥有你所需的一切。它既有编辑器,也有终端。此外,我还可以运行像 gcloud 这样的命令,这些是内置的、用于管理Google Cloud Platform的工具。
与云服务交互
真正的关键在于,与大多数云平台一样,你可以在一个项目中调整一切,进行探索和运行。我还想展示一个实用的小技巧。

如果我想登录我的账户以执行一些需要权限的操作,该怎么做呢?例如,我可以输入 gcloud auth list 来查看当前授权账户。要登录,系统会弹出一个授权窗口,允许我进行API调用。


授权完成后,我现在可以运行一个我之前构建的云函数。这个函数可以从维基百科获取文本并将其翻译成另一种语言。

你可以看到,我不仅可以在Cloud Shell中构建自己的项目,还能直接调用云环境中的服务。这正是基于云的环境的关键优势:它与所有其他云服务紧密集成。

总结
本节课中,我们一起学习了如何使用Google Cloud Shell进行云开发。我们从启动和探索Cloud Shell开始,接着配置了Python虚拟环境,然后从GitHub克隆并运行了一个示例项目。我们还体验了内置的云端IDE,并演示了如何通过命令行工具与Google Cloud服务进行交互。Cloud Shell提供了一个功能齐全、集成度高的开发环境,是快速开始在Google Cloud上构建项目的强大工具。
033:GCP Google App Engine从零开始持续交付 🚀
在本节课中,我们将通过一个实际项目,学习如何在Google Cloud Platform上为Google App Engine应用设置一个完整的持续交付流程。我们将从创建项目、部署应用到配置自动化部署,一步步构建一个自动化的发布管道。
概述
持续交付是一种软件开发实践,旨在通过自动化流程,确保代码变更可以快速、可靠地发布到生产环境。本节我们将利用GCP的核心服务,为一个小型Flask应用搭建这样的自动化流程。

核心组件
要理解GCP上的持续交付,首先需要了解几个核心配置文件。
以下是实现持续交付所需的关键文件:


-
app.yaml文件:此文件定义了应用的运行时环境。例如,对于Python应用,它会指定Python版本。runtime: python39 -
cloudbuild.yaml文件:此文件指示Cloud Build服务器如何构建和部署应用。一个最简单的部署命令如下:steps: - name: 'gcr.io/cloud-builders/gcloud' args: ['app', 'deploy'] -
应用源代码:一个简单的Web应用。我们使用一个Flask应用,它包含两个路由:一个返回“Hello World”,另一个回显传入的名称。
-
requirements.txt文件:此文件列出了应用所需的所有Python依赖包。
准备好这些文件,就完成了基础设置。
项目初始化与本地测试

上一节我们介绍了核心配置文件,本节中我们来看看如何初始化项目并在本地运行。
首先,我们需要在Google Cloud上创建一个新项目。

- 访问Google Cloud控制台,创建一个全新的项目,命名为
cloud-data-continuous-delivery。 - 创建完成后,在Cloud Shell中激活这个新项目。
- 将包含上述配置文件和源代码的Git仓库克隆到本地目录。
- 进入项目目录,创建一个Python虚拟环境以隔离依赖:
virtualenv ~/.cd_env source ~/.cd_env/bin/activate - 安装应用依赖:
pip install -r requirements.txt - 在本地运行应用进行测试:
应用将在本地端口8080启动。使用Cloud Shell的“网页预览”功能,可以访问python main.pyhttp://localhost:8080并看到“Hello World”的返回信息,这验证了应用在本地运行正常。

首次部署到Google App Engine
成功在本地运行应用后,下一步就是将其部署到Google App Engine的生产环境。


在Cloud Shell中,使用 gcloud 命令行工具进行部署:
gcloud app deploy
执行此命令后:
- 系统会提示选择部署区域(例如
us-central)。 gcloud工具会自动读取项目中的app.yaml文件,根据指定的运行时配置环境,并将应用部署上线。
部署完成后,命令行会提供一个生产环境的URL。访问该URL,即可看到线上运行的应用。我们还可以测试 /echo/<name> 路由,确认功能完整。
配置自动化持续交付管道
手动部署已经完成,但真正的威力在于自动化。本节我们将配置Cloud Build,实现代码变更后的自动部署。
目标是:每当向代码仓库的主分支推送新更改时,自动触发构建并将应用重新部署到App Engine。
以下是配置自动触发器的步骤:
- 在GCP控制台导航到 Cloud Build 服务。
- 点击 “触发器”,然后点击 “创建触发器”。
- 为触发器命名(例如
cloud-delivery-auto-deploy)。 - 选择触发条件为 “推送到分支”,并指定分支为
master(或您的主分支名称)。这意味着每次向该分支推送代码时都会触发构建。 - 连接到您的GitHub仓库,并选择对应的项目仓库。
- 在构建配置中,选择 “cloudbuild.yaml” 文件,它位于您的仓库根目录。
在创建触发器前,需要确保以下两项服务已启用:
- App Engine Admin API:允许Cloud Build服务代表您调用App Engine的部署API。
- Cloud Build 服务账户权限:需要确保Cloud Build使用的服务账户拥有部署到App Engine的权限。通常需要在IAM中为
[PROJECT_NUMBER]@cloudbuild.gserviceaccount.com账户添加“App Engine Deployer”角色。
完成这些设置后,自动化管道就配置完毕了。
测试持续交付流程
管道配置完成后,我们可以通过一个简单的修改来测试整个流程是否工作。
- 编辑
main.py文件中的“Hello World”消息,例如将其改为“Hello World! Testing Continuous Delivery.”。 - 将这次更改提交并推送到GitHub仓库的
master分支。 - 推送完成后,立即转到GCP控制台的 Cloud Build 历史记录页面。您将看到一个新的构建任务自动开始运行。
- Cloud Build会自动执行
cloudbuild.yaml中定义的步骤:拉取最新代码、执行部署命令。 - 等待构建状态显示“成功”。然后,刷新您的App Engine生产环境URL。页面上的问候语应该已经更新为您刚才提交的新消息。
这证明从代码提交到生产环境部署的整个流程已经完全自动化。
总结
本节课中我们一起学习了如何在Google Cloud Platform上为App Engine应用搭建持续交付管道。
我们首先了解了核心的配置文件(app.yaml, cloudbuild.yaml)。接着,我们从零开始创建项目、部署应用,并验证其功能。最后,我们配置了Cloud Build触发器,实现了代码推送后的自动构建与部署。


整个过程清晰展示了在云环境中设置自动化部署的简便性。对于使用Flask等框架的项目,这已成为一种最佳实践。您可以通过复刻示例仓库,快速在自己的GCP项目中体验这一流程。
034:使用GCP Cloud Run构建微服务 🚀

在本节课中,我们将学习如何使用Google Cloud Platform的Cloud Run服务来构建和部署一个容器化的微服务。我们将从零开始,在云端开发环境中创建应用,在本地模拟器中测试,最后将其部署到生产环境。
上一节我们介绍了Cloud Run作为运行容器的全托管平台。本节中,我们来看看如何从零开始创建一个Cloud Run应用。
在Google Cloud控制台中,你可以直接点击按钮开始使用Cloud Run。另一个有趣的选项是从头开始创建。我们可以激活Cloud Shell,它会提供一个专为构建容器应用而定制的完整IDE,并可以将应用推送到生产环境。
在Google Cloud编辑器中,有许多便捷功能,包括启动终端进行操作。这些基于云的开发环境更有趣的一点是,你可以通过菜单选择不同的服务并以原型化的方式构建它们。

我们选择Cloud Run并授权,它将为我们设置一个用于原型化Cloud Run应用的环境。

进入环境后,我们可以创建一个新的Cloud Run应用。
以下是创建步骤:
- 选择“创建新的Cloud Run应用”。
- 选择一个模板,例如“Python Cloud Run”。
- 点击“创建新应用”。
环境会为我们下载并设置好一切。在这个环境中,我们拥有文档、初步设置,甚至一个已经构建好的Dockerfile。这是学习如何构建应用的好方法,因为Google的专家展示了具体该怎么做。他们甚至使用了非常精简的Alpine容器。
我们还可以查看这里的样板代码,它是一个非常简单的服务,但之后会被推送到一个托管的容器编排服务中,我们无需进行任何运维工作。
上一节我们创建了应用的基础框架。本节中,我们来看看如何让这个应用运行起来。
首先,我们使用云模拟器在本地运行应用,然后将其部署到Cloud Run。这是入门的最佳方式之一。
具体操作是:点击云状态栏,选择“在云模拟器上运行”。这会在本地运行一个迷你版的Cloud Run环境。
我们转到状态栏,选择我们的Cloud Run应用,然后点击“在本地Cloud Run模拟器上运行应用”。让我们看看它是如何工作的。
它显示“构建环境:本地”。我们继续操作,它会询问一些设置。这个本地服务的酷炫之处在于,当我实际修改代码原型时,它可以自动重启。这是一种非常流畅的开发容器化应用的方式,我可以实时编辑,它会为我重建容器。如前所述,当我想部署时,它可以直接推送到生产环境。
加载需要一点时间。设置完成后,它会“监视更改”。一方面,我还可以预览它。将鼠标悬停其上,我们可以查看,非常酷,一个应用正在运行。
如果我想在本地调试,一个很酷的功能是:我可以看到它正在运行。如果我更改代码并保存,它会自动重启。我再次回到服务URL查看,更改已经生效。这是一个用于原型化云服务的绝佳环境。

上一节我们在本地成功运行并测试了应用。本节中,我们来看看如何将其部署到生产环境。
现在,让我们回到控制面板,停止本地服务。然后,我们可以将其部署到生产环境。

为此,我可以选择“部署到Cloud Run”。这将直接把应用推送到生产环境。实际上,一旦你拥有了一个容器,使用Cloud Run这样的服务来设置微服务就变得非常直接。你可以看到这里列出了部署其余代码的步骤。

本节课中,我们一起学习了使用GCP Cloud Run构建微服务的完整流程。我们从在云端开发环境中创建Python应用开始,接着使用本地模拟器进行测试和实时调试,最后将容器化应用一键部署到生产环境。这个过程展示了Cloud Run如何简化容器化微服务的开发、测试和部署,让开发者能够专注于代码本身。
035:使用Google Cloud Functions 🚀

在本节课中,我们将学习Google Cloud Functions(GCF)的基础知识。这是一种无服务器计算服务,允许你运行代码以响应事件,而无需管理服务器。我们将从架构概述开始,然后逐步学习如何创建、配置、测试和部署一个简单的云函数。
概述
Google Cloud Functions 是一种事件驱动的无服务器计算平台。它允许开发者编写单一用途的函数,这些函数在特定事件(如文件上传、消息发布或HTTP请求)发生时被触发执行。其核心优势在于无需管理基础设施,支持多种编程语言,并且可以轻松集成到Google Cloud生态系统中。
Google Cloud Functions 架构
理解Google Cloud Functions的架构是掌握其在Google Cloud平台上如何工作的最佳方式。
架构的第一步是事件触发器。在触发器系统中,你可以监听多种事件。例如,你可以监听存储事件,当有图像或文本文件被放入存储桶时,它会调用云函数。同样,你可以设置一个发布/订阅系统,当流数据作为消息传入时,也可以触发云函数。其中更简单的一种是HTTP触发器,即通过向一个URL发送POST请求并附带有效载荷来调用函数。
Google Cloud Functions 的一个显著优点是它支持多种语言,包括Go、Python、C#、Ruby、Node.js等几乎所有现代语言。这些函数可以通过命令行界面或HTTP请求轻松进行测试。
创建你的第一个云函数
上一节我们介绍了GCF的架构,本节中我们来看看如何在Google Cloud控制台中实际创建一个函数。
首先,进入Google Cloud Functions控制台,点击“创建函数”。你会注意到有两个版本:第一代和第二代。第二代提供了更多的触发器和事件类型,功能也更强大,但目前仍处于初步阶段。本教程将使用第一代进行演示。
以下是创建函数的主要步骤:
- 为函数命名:例如,可以命名为
hello-world。 - 选择触发器类型:对于初学者,从HTTP触发器开始是个好选择。当然,你也可以配置其他触发器,如发布/订阅、云存储、Firestore或数据库事件。一个良好的默认设置是要求调用者进行身份验证,除非你确定要创建一个公开的API。
- 选择运行时和编写代码:点击“下一步”后,选择你想要的编程语言。Google Cloud Functions 支持众多选项,包括 .NET、Go、Java、PHP、Python、Ruby等。选择
Python 3.11。对于所有语言,GCF都提供了包管理功能,允许你安装依赖项。你只需将依赖项名称列在指定区域即可。代码编辑区会提供一个入口函数。例如,函数名hello_world与入口点名称匹配。该函数接收一个请求对象,你可以解析其中的数据并返回响应。 - 部署函数:编写完代码后,点击“部署”按钮即可。部署完成后,函数就可以被调用了。
编写与测试函数代码
现在,让我们深入代码部分,并学习如何测试它。我们将创建一个稍微复杂一点的Python函数。
以下是一个示例函数,它检查HTTP请求体中是否包含特定的名字:
def hello_world(request):
request_json = request.get_json()
if request_json and ‘name’ in request_json:
name = request_json[‘name’]
if name.lower() == ‘marco’:
return ‘Polo!’
else:
return f‘I don‘t know you, {name}.’
else:
return ‘Please provide a “name” in the request body.’
部署此函数后,你可以直接在控制台进行测试。转到函数的“测试”标签页,这里提供了两种测试方式:
- 在控制台内测试:你可以直接在提供的JSON输入框中构造测试负载。例如,输入
{“name”: “Marco”},点击“测试函数”,应返回“Polo!”。输入{“name”: “Bob”},则会返回“I don‘t know you, Bob.”。 - 在Cloud Shell中测试:你也可以选择在Cloud Shell中使用
curl命令进行测试,这对于模拟真实HTTP调用非常有用。
使用其他语言(以Go为例)
Google Cloud Functions 的多语言支持使其非常灵活。让我们快速看一下用Go语言实现的相同功能。
以下是一个Go版本的“Marco Polo”函数:

package p
import (
“encoding/json”
“fmt”
“net/http”
)
// NameStruct 定义了期望的JSON结构
type NameStruct struct {
Name string `json:“name”`
}
// HelloWorld 是云函数的入口点
func HelloWorld(w http.ResponseWriter, r *http.Request) {
var d NameStruct
if err := json.NewDecoder(r.Body).Decode(&d); err != nil {
fmt.Fprint(w, “Error decoding JSON. Please provide a {‘name’: ‘value’} payload.“)
return
}
if d.Name == “Marco” {
fmt.Fprint(w, “Polo!”)
} else {
fmt.Fprintf(w, “I need another name. You provided: %s”, d.Name)
}
}
创建和测试Go函数的过程与Python类似:选择Go运行时,粘贴代码,部署,然后在测试标签页使用相同的JSON负载进行验证。

监控与管理函数
函数部署后,管理它同样重要。Google Cloud Functions 控制台提供了强大的工具。
- 指标:在“指标”标签页,你可以查看每秒调用次数、执行时间、错误率等图表,这对于监控函数性能和健康状况至关重要。
- 编辑与重新部署:如果需要修改代码,只需点击“编辑”,进入代码编辑页面进行更改,然后再次点击“部署”即可更新函数,无需重新配置触发器。
- 日志:“日志”标签页显示了函数的所有执行日志,包括标准输出、错误信息以及系统日志。这是调试和排查问题不可或缺的工具。
总结


本节课中,我们一起学习了Google Cloud Functions的核心概念和基本操作。我们了解了其基于事件触发的无服务器架构,逐步实践了如何创建、配置、编写代码、测试以及部署一个云函数。无论是使用Python还是Go,流程都清晰而直接。我们还探索了如何通过控制台监控函数指标、查看日志以及更新代码。Google Cloud Functions 提供了一个完整、易用且功能强大的计算环境,让你能够专注于业务逻辑,而无需操心底层基础设施。
036:云计算介绍 ☁️
在本节课中,我们将学习云计算的核心能力,并了解它与传统计算的区别。

概述
我们将首先探讨云计算的定义及其核心特征。接着,我们会详细介绍不同类型的云交付模型。通过本节内容,你将理解云计算的基本概念及其服务模式。

什么是云计算?
云计算是一种通过互联网按需提供计算资源(如服务器、存储、数据库、网络、软件等)的服务模式。它的核心在于按需自助服务、广泛的网络访问、资源池化、快速弹性以及可度量的服务。
云计算的核心特征
上一节我们定义了云计算,本节中我们来看看它的五个核心特征。
以下是云计算的五个核心特征:
- 按需自助服务:用户可以根据需要,无需与服务提供商人工交互,自动配置计算资源。
- 广泛的网络访问:功能通过网络提供,并通过标准机制访问,支持各种客户端设备。
- 资源池化:提供商的计算资源被集中起来,通过多租户模式服务多个用户,根据用户需求动态分配和再分配物理和虚拟资源。
- 快速弹性:资源可以快速、弹性地供应和释放,对于用户而言,可供应的资源近乎无限,并可在任何时间购买任何数量。
- 可度量的服务:云系统通过利用适用于服务类型的某种抽象级别的计量能力,自动控制和优化资源使用。资源使用情况可被监控、控制和报告,为提供商和用户提供透明度。
云计算服务模型
理解了核心特征后,我们来看看云计算是如何通过不同的服务模型交付给用户的。这些模型定义了用户管理和控制的范围。
以下是几种重要的云计算服务模型:
- 软件即服务:指可以“租用”的软件,并将其集成到自己的基础设施中。例如电子商务系统、薪资系统或监控系统。用户无需编写该软件,只需支付费用即可使用。
- 公式/代码示例:
SaaS = 租用的应用软件
- 公式/代码示例:
- 平台即服务:这是一个高级抽象层,允许软件开发团队只专注于业务逻辑,而基础设施提供商负责将其部署到生产环境的其余工作。
- 公式/代码示例:
PaaS = 开发平台 + 托管环境
- 公式/代码示例:
- 基础设施即服务:这很像大型仓储式商店,你可以批量获取资源(如虚拟机、存储、网络),但仍需负责配置和整合所有这些设备。
- 公式/代码示例:
IaaS = 虚拟化的计算、存储、网络资源
- 公式/代码示例:
- 裸机即服务:这是一个较新的术语,意味着许多云范式可以应用于物理硬件。这适用于需要处理特殊情况的场景,如GPU编程或大型存储系统。
- 公式/代码示例:
Bare-Metal-as-a-Service = 专用的物理服务器
- 公式/代码示例:
- 无服务器计算:这是较新的服务模型之一。“无服务器”指的是完全无需担心底层基础设施。它与平台即服务有许多相似之处和重叠。一个著名的例子是AWS Lambda,本质上是一个可以放入云中的函数,你可以将事件映射到它来执行。
- 公式/代码示例:
Serverless = 事件驱动的函数执行 (例如:AWS Lambda)
- 公式/代码示例:
总结

本节课中,我们一起学习了云计算的基本概念。我们首先定义了云计算,然后分析了其按需自助、广泛访问、资源池化、快速弹性和可度量服务这五个核心特征。最后,我们探讨了从软件即服务到无服务器计算等多种云服务模型,了解了每种模型为用户提供的不同抽象级别和管理责任。理解这些基础是构建大规模云解决方案的第一步。
037:什么是云计算 ☁️
在本节课中,我们将要学习云计算的核心概念。我们将探讨其四个关键特征,这些特征共同定义了云计算的本质,并使其成为现代技术基础设施的基石。
概述
云计算是什么?这是一个至关重要的问题。我们将避免使用大量术语,而是聚焦于四个核心特征:近乎无限的计算能力、消除前期成本、按使用付费的效用模型以及比较优势理论。理解这些特征,是掌握云计算价值的基础。
近乎无限的计算能力 💾
上一节我们概述了云计算的四个特征,本节中我们首先来看看第一个,也是最重要的概念:近乎无限的计算能力。
你的个人笔记本电脑无法存储PB级的数据。即使是企业自有的物理数据中心,要处理PB级数据也会面临挑战。但在云环境中,你拥有近乎无限的存储、近乎无限的计算能力和近乎无限的CPU资源。我们可以将其概括为:
资源 = CPU + 存储 + 内存
这个概念是云计算如此强大的根本原因。许多机制,例如一个消息队列系统,其处理能力可以远超你所能发送的流量上限。
消除前期成本 💰
了解了无限的计算资源后,我们来看看第二个特征:消除前期成本。
这对于初创公司尤其关键。如果你希望从一开始就构建一个全球规模的基础设施,你无需亲自处理。云服务已经为你搭建好了这个平台,你直接消除了构建全球基础设施的需求。通过使用云计算,你正在利用现成的可用资源。这一点非常重要,我们今天使用的许多服务和产品,如果没有这种消除前期成本的能力,可能根本无法被创造出来。
按使用付费的效用模型 ⚡
在消除了资本支出的障碍后,云计算的消费模式也与众不同。接下来我们探讨第三个特征:按使用付费的效用模型。
这就像家中的温控器。如果你将其设置为68华氏度以实现节能,在夏天使用空调时,你就不会支付过高的电费。云计算同理。如果你低效地使用资源,你将支付高昂的费用;但如果你高效地使用,它就更像一种公用事业。最擅长使用云计算的公司正是这样做的:将云资源视为可按需调节、按量付费的效用。
以下是实现高效使用的关键原则:
- 弹性伸缩:根据负载自动增加或减少资源。
- 资源优化:选择最适合工作负载的实例类型。
- 监控与成本分析:持续跟踪支出并识别浪费。
专注于核心业务的比较优势 🎯
最后,另一个关键组成部分是比较优势。这是微观经济学中的一个核心概念,指的是专注于你最擅长的事情,而将其他事情交给更专业的人。
一个很好的例子是迈克尔·乔丹。当他在芝加哥公牛队训练时,他应该花时间去修剪草坪,还是应该花钱请人来做?显然,他为公牛队打球赚的钱远多于修剪草坪。因此,他应该专注于篮球。
云计算也遵循类似的概念。如果你的公司专注于软件即服务或构建应用程序,那么你无需担心亲自驱车前往数据中心、安装硬件等事务。许多这类场景都会消失,你可以专注于你最擅长的事情——创造产品价值。
总结
本节课中,我们一起学习了云计算的四个核心特征:
- 近乎无限的计算能力:提供可弹性扩展的CPU、内存和存储资源。
- 消除前期成本:无需大量资本投入即可使用世界级的基础设施。
- 按使用付费的效用模型:像使用水电一样,为实际消耗的资源付费。
- 比较优势:让企业能够专注于自身核心业务,而将基础设施的复杂性交给云提供商。


理解这些特征,是有效利用云计算构建可扩展、高效且经济解决方案的第一步。
038:云计算服务模型 🏗️
在本节课中,我们将要学习云计算中几种主要的服务模型。理解这些模型是设计和构建云解决方案的基础,它们定义了用户与云服务提供商之间的责任划分和抽象层级。
概述
云计算提供了多种服务模型,每种模型在基础设施、平台和软件的管理责任上有所不同。从完全托管的应用程序到需要自行配置的物理硬件,不同的模型适用于不同的业务需求和技术能力。
软件即服务 (SaaS)
软件即服务是一种完全托管的应用程序交付模式。用户无需管理底层的基础设施、平台甚至应用程序本身,只需通过互联网访问和使用软件。
以下是软件即服务的常见示例:
- Gmail:用户无需自行搭建邮件服务器,只需注册账号即可使用邮件服务。
- Splunk 或 Datadog:这类监控服务替代了企业自行构建和维护监控系统的需求。
平台即服务 (PaaS)
上一节我们介绍了完全托管的SaaS,本节中我们来看看平台即服务。PaaS的核心在于抽象掉基础设施(如服务器、存储、网络),让开发者能够专注于应用程序的构建和部署,而无需操心运行环境的管理。
以下是平台即服务的核心特点与示例:
- 核心抽象:
PaaS = 基础设施抽象 + 应用部署平台 - 服务示例:Heroku、Google App Engine (GAE)、Amazon Elastic Beanstalk。
- 价值主张:开发者支付额外费用,云服务提供商负责管理一切底层运维,类似于加油站的全服务加油与自助加油的区别。
基础设施即服务 (IaaS)
如果说PaaS提供了“拎包入住”的便利,那么基础设施即服务则提供了“毛坯房”级别的控制权和灵活性。IaaS提供最基础的计算资源,如虚拟机、存储和网络,用户需要自行安装操作系统、配置网络并部署应用。
以下是基础设施即服务的关键点:
- 核心产品:例如亚马逊的EC2(弹性计算云),用户可以租用虚拟机。
- 成本优势:通过批量购买和竞价实例(如Spot Instances),成本可以降至典型价格的10%,类似于在Costco批发采购。
- 责任划分:用户(软件工程师或云架构师)需要负责从虚拟机到网络层的所有配置工作,以此换取显著的成本节约。对于拥有相应技术能力的组织,这是一个极具吸引力的选择。
其他服务模型
除了上述三种经典模型,云计算领域还涌现出一些更专门化的服务模型。
以下是另外两种重要的云服务模型:
- 硬件即服务 / 裸机即服务 (MaaS):此模型允许用户直接配置和控制物理服务器。它适用于需要专用硬件(如特定型号的多GPU集群用于机器学习,或专用数据库服务器)的场景,以实现对物理硬件的完全掌控。
- 无服务器计算 (Serverless / FaaS):无服务器计算在理念上与PaaS相似,但它进一步抽象,围绕“函数”这一概念构建,因此也可称为函数即服务。其开发范式不同,开发者将业务逻辑封装为函数单元,部署到云中,并由特定事件(如HTTP请求、文件上传)触发执行。这就像车库的灯泡,可以通过多种方式(定时器、门磁感应、手动开关)触发点亮,无服务器架构将业务逻辑抽象为可复用的工作单元,并在需要时执行。
总结


本节课中我们一起学习了云计算的主要服务模型。我们从完全托管的软件即服务开始,了解了用户如何直接使用应用。接着,我们探讨了平台即服务,它让开发者能专注于代码。然后,我们深入了提供基础计算资源的基础设施即服务,它提供了最大的控制权和成本优化空间。最后,我们还介绍了更专门的硬件即服务和对事件驱动的无服务器计算。理解这些模型的区别和适用场景,是设计高效、经济云解决方案的关键第一步。
039:构建多网站介绍 🚀
在本节课中,我们将学习如何在云环境中构建多种类型的网站。我们将涵盖静态网站、无服务器网站、虚拟化网站以及平台即服务(PaaS)网站。通过具体的AWS服务实践,你将理解每种方法的适用场景与核心概念。
上一节我们介绍了课程的整体目标,本节中我们来看看构建多网站的具体学习目标。
以下是本节课的学习目标:
- 在AWS S3上构建一个静态网站。
- 在AWS Lambda上构建一个无服务器网站。
- 在EC2虚拟机上构建一个网站。
- 使用AWS Beanstalk(PaaS)构建一个网站。
接下来,让我们逐一解析这些核心概念,以便更好地理解后续的实践操作。
静态网站是一个常见术语,它意味着你生成HTML文件,并将这些文件存放在类似Amazon S3的地方。这种方法的重要性在于,它消除了对中间服务器来渲染HTML的需求。这确实是现代开发Web应用,特别是内容管理类应用的主流方式。
S3是另一个关键术语,它代表对象存储,是亚马逊的对象存储系统,具有11个9的可靠性。这意味着其可靠性为99.999999999%,本质上每年可能只中断约一毫秒,这是S3的关键优势之一。
AWS Lambda是一项无服务器技术,允许你编写一个函数(我们将介绍Python版本)并将其与事件挂钩。这些事件可以是网站请求、来自队列的消息,或者是你需要处理的事件,例如一个文件被放入S3存储桶。
EC2代表虚拟机。亚马逊提供几种类型,一种是按需实例,价格稍高,但你可以随时启动虚拟机;另一种是竞价实例,允许你出价以获得更低价格,适合用于实验。
AWS Beanstalk是AWS提供的一项平台即服务产品。我们将结合Flask使用它来部署一个基于Python的Web应用。
现在,让我们开始实践。




本节课中我们一起学习了构建多种云网站的基础概念,包括静态网站、无服务器架构、虚拟机和平台即服务。我们明确了使用AWS S3、Lambda、EC2和Beanstalk这四项核心服务来实现这些网站类型的目标,为后续动手实践奠定了理论基础。
040:在AWS上构建静态S3网站 🚀
在本节课中,我们将深入探索亚马逊S3服务,并学习如何利用它来构建一个静态网站。我们将通过将index.html文件放入一个S3桶中来实现这一目标。
概述
S3可以被理解为一个文件夹,而其中的文件则是对象。通过启用静态网站托管功能,这个对象就能转变为一个网站。我们将要使用的技巧,就是创建一个能在全球范围内访问、具备极高可用性的网站。其背后的可靠性高达“11个9”(即99.999999999%),这是因为对象在后台被存储为多个副本。此外,这是一项无服务器技术,意味着你无需管理任何服务器。
现在,让我们开始动手构建。
准备工作
为了创建一个静态托管的网站,我们只需要两样东西:一个index.html文件和一个配置了正确权限的S3桶。
首先,我们将在Cloud9环境中创建一个空的index.html文件。
以下是创建基本HTML文件的步骤:
- 创建一个名为
index.html的空文件。 - 编辑该文件,添加HTML标签。
- 在
<title>标签中设置页面标题,例如“这是一个网站”。 - 在
<body>中添加一个段落,例如“这是我的新网站。我会把它做大。”
完成这些步骤后,我们就得到了一个可以托管的基本HTML文档。
创建并配置S3桶
上一节我们准备好了网站文件,本节中我们来看看如何创建和配置S3桶来托管它。
以下是创建和配置S3桶的步骤:
- 在AWS控制台中导航到S3服务,点击“创建桶”。
- 为桶设置一个全局唯一的名称,例如
hello-cloud-for-data。 - 为了创建公开网站,需要启用所有公共访问(请注意,仅在创建公共网站时这样做),并确认此更改。
- 点击“创建桶”。
桶创建完成后,我们需要对其进行配置以启用网站托管功能。
以下是配置静态网站托管的步骤:
- 在桶列表中,找到并点击你刚创建的桶。
- 切换到“属性”选项卡。
- 向下滚动到“静态网站托管”部分。
- 选择“启用”选项。
- 在“索引文档”字段中,输入你的主页文件名,即
index.html。 - 在“错误文档”字段中,可以输入一个错误页面文件名,例如
error.html(可选)。 - 点击“保存更改”。
设置桶策略
现在,我们需要为桶添加一个策略,以允许公众读取桶中的对象(即我们的网页文件)。
以下是添加桶策略的步骤:
- 切换到桶的“权限”选项卡。
- 向下滚动到“桶策略”部分,点击“编辑”。
- 将以下策略代码粘贴到编辑器中。请务必将
Resource值中的your-bucket-name替换为你实际的桶名。
{
"Version": "2012-10-27",
"Statement": [
{
"Sid": "PublicReadGetObject",
"Effect": "Allow",
"Principal": "*",
"Action": "s3:GetObject",
"Resource": "arn:aws:s3:::your-bucket-name/*"
}
]
}
- 点击“保存更改”。此策略将允许世界上任何人读取该桶中的文件。
上传文件并测试
最后一步是将我们之前创建的index.html文件上传到S3桶中,并测试网站是否正常工作。
以下是上传和测试的步骤:
- 从Cloud9环境下载
index.html文件到本地。 - 回到S3桶的“对象”选项卡。
- 点击“上传”,选择并上传刚才下载的
index.html文件。 - 上传完成后,返回桶的“属性”选项卡。
- 再次找到“静态网站托管”部分,此时你会看到一个“桶网站端点”的URL。
- 点击这个URL链接,它将在新标签页中打开你的网站。
如果一切配置正确,你将看到你创建的HTML页面成功显示。
总结


本节课中我们一起学习了如何在AWS S3上构建一个静态网站。我们首先创建了一个简单的HTML文件,然后创建并配置了一个S3桶,包括启用静态网站托管和设置公开读取的桶策略,最后上传文件并通过生成的URL访问了网站。整个过程无需管理服务器,即可获得一个高可用、全球分布的网站。
041:使用AWS Lambda控制台构建Python Lambda函数 🚀

在本节课中,我们将学习如何在AWS Lambda控制台上快速构建和测试Python函数。我们将创建两个简单的Lambda函数:一个用于加法运算,另一个用于除法运算,并了解如何对它们进行部署和测试。
概述
我们将构建两个Lambda函数。第一个函数将接收两个数字 x 和 y,并返回它们的和。第二个函数将接收第一个函数返回的结果,并将其除以2。最终,我们可以通过无服务器编排工具(如Step Functions)将它们组合起来。本节课将专注于在AWS控制台中使用Python进行快速原型开发。
构建加法Lambda函数
首先,我们进入AWS Lambda控制台创建第一个函数。选择使用ARM架构以节省成本,并选择最新的Python 3.11运行时环境。
以下是创建函数的步骤:
- 点击“创建函数”。
- 选择“从头开始创作”。
- 输入函数名称
add。 - 选择运行时为
Python 3.11。 - 在架构中选择
ARM64。 - 点击“创建函数”。
创建完成后,我们进入代码编辑器编写函数逻辑。该函数将从事件(event)中提取 x 和 y 参数,计算它们的和,并以JSON格式返回结果。
import json
def lambda_handler(event, context):
# 从传入的事件中获取参数
x = event['x']
y = event['y']
# 执行加法计算
total = x + y
# 构造并返回响应
return {
'statusCode': 200,
'body': json.dumps({
'total': total
})
}
编写代码后,点击“部署”按钮保存更改。接下来,我们需要配置一个测试事件来验证函数是否按预期工作。
测试加法函数
为了测试函数,我们需要创建一个测试事件来模拟输入。
以下是配置测试事件的步骤:
- 点击“测试”选项卡。
- 点击“创建新事件”。
- 输入事件名称,例如
addTest。 - 在JSON模板中,提供
x和y的值。{ "x": 10, "y": 20 } - 点击“保存”。
保存测试事件后,点击“测试”按钮执行函数。控制台将显示执行结果。如果代码正确,响应体(body)中应包含计算结果 {"total": 30}。如果遇到错误(例如缩进或语法问题),修正代码后重新部署并再次测试即可。
构建除法Lambda函数
成功创建并测试了加法函数后,接下来我们构建第二个函数。这个函数将接收一个包含 total 值的负载,并将其除以2。
我们返回函数列表页面,再次点击“创建函数”。重复之前的创建步骤,将函数命名为 divideBy2,运行时和架构选择保持不变。
创建完成后,在代码编辑器中输入以下逻辑:
import json
def lambda_handler(event, context):
# 解析传入事件中的负载
# 注意:事件结构取决于调用方式,这里假设负载在body中
body = json.loads(event['body'])
input_total = body['total']
# 执行除法计算
result = input_total / 2
# 构造并返回响应
return {
'statusCode': 200,
'body': json.dumps({
'calculated': result
})
}
同样,部署此函数后,我们需要为其创建一个测试事件。这次的事件负载需要模拟第一个函数的输出。
以下是配置除法函数测试事件的步骤:
- 点击“测试”选项卡。
- 创建新事件,命名为
divideTest。 - 在JSON模板中,模拟第一个函数的返回结构。
{ "body": "{\"total\": 30}" } - 点击“保存”并执行测试。
如果一切正常,测试结果将显示 {"calculated": 15.0}。这表明第二个函数能够正确接收并处理第一个函数的输出。
总结

本节课中,我们一起学习了如何在AWS Lambda控制台上使用Python构建和测试无服务器函数。我们创建了两个函数:一个执行加法(add),另一个执行除法(divideBy2)。我们了解了从创建函数、编写代码、部署到配置测试事件的完整流程。使用Python在控制台内进行原型开发非常快捷方便,适合快速验证想法。虽然对于长期运行的代码可能需要考虑其他语言(如Rust),但Python无疑是快速起步和测试的绝佳选择。在后续课程中,我们可以使用AWS Step Functions等编排服务将这些独立的函数连接起来,构建更复杂的工作流。
042:在AWS Lambda上构建无服务器网站 🚀
在本节课中,我们将学习如何使用AWS Lambda构建一个简单的无服务器网站。我们将创建一个Python函数,将其与HTTP触发器(API Gateway)连接,使其能够响应Web请求并返回HTML内容。
上一节我们介绍了无服务器计算的概念,本节中我们来看看如何具体实现一个基于AWS Lambda的网站。
AWS Lambda本质上是一个函数。它可以是Python或其他语言编写的函数。在本例中,我们将使用Python。这个Python函数会与一个触发器挂钩。触发器可以是任何能触发函数执行的事件。在本例中,我们将围绕Web构建触发器,即连接一个HTTP触发器。这意味着当我点击一个URL时,该请求会映射到这个函数并调用它。构建AWS Lambda函数就是如此简单。之后,如果我需要将此函数连接到其他类型的事件,例如S3文件上传事件或SQS队列消息,也可以进行配置。但总的来说,它只是一段逻辑代码,我将其挂接到一个事件上,然后就可以对外提供网站服务。现在,让我们开始构建。
我们将再次使用AWS Cloud9环境。我们可以在Cloud9环境中为Lambda构建解决方案。
以下是操作步骤:
- 在Cloud9界面中,选择“AWS Resources”选项卡。
- 找到并点击“创建新的Lambda函数”图标。
- 在弹出的窗口中,填写函数名称和应用程序名称。例如,可以输入
hello_cloud_lambda。 - 系统会自动填充应用程序名称。接着,选择运行时环境。Lambda支持多种运行时,Cloud9支持Node.js和Python。我们选择 Python 3.6。
- 选择函数模板为“空的Python函数”。
- 接下来配置触发器。由于我们要构建网站,因此选择 API Gateway 作为触发器。
- API Gateway会询问要映射的URL路径。我们输入根路径
/。 - 出于简化目的,安全性选择“无”。我们只想提供一个非常基础的Web请求。
- 无需配置特殊权限,因为它只是返回HTML。点击“完成”。
很好,现在我们已经完成了基本设置。系统会为我们在此项目中搭建好脚手架结构。你会看到它创建了整个项目结构,包括一个lambda函数文件、一个虚拟环境和其他文件。实际上,我们只需要修改Lambda函数本身(即处理器)。
在本例中,我们甚至不需要处理事件参数,只需构建返回原始HTML的逻辑。每当你获得这样的脚手架时,都可以将你的逻辑代码放入其中。
我将粘贴一段预先准备好的代码。请注意,我定义了一个变量 content,并在其中放入了一些HTML代码。我放置了一个HTML标签,并写入了“这是我的Lambda网站”段落。然后,我返回一个响应。响应的主体就是这个HTML内容。它返回状态码 200,表示Web服务成功获取了代码。在响应头中,我告诉Web浏览器我将提供HTML内容。这就是全部。
这与静态网站的区别在于,每次有人发起请求时,这个函数都会被调用。
现在我们已经设置好了代码,我将在本地运行它以进行测试。为此,我转到 hello_cloud_lambda 目录,右键点击并选择“运行” -> “在本地运行API Gateway”。这将允许我在本地环境中测试它。这是AWS Cloud9的一个关键优势。
注意,它填充了一个GET请求,这是从应用程序获取信息的一种方式。当我运行它时,它返回了我期望的结果,非常完美。
测试通过后,下一步是部署。我可以在这里右键点击项目,然后选择“部署”。这将把它部署到AWS控制台。我们继续操作。
部署完成后,我可以返回AWS控制台查看。你会看到它现在位于这个位置。这里需要指出的关键点是,它设置了API Gateway触发器。如果需要,我还可以通过选择相应图标来查看我的源代码,并进行编辑和修改。
但总的来说,主要需要关注的是这个API Gateway。如果我向下滚动并选择这个API端点,它将会响应我的HTML请求。让我们来试试看。
成功了!页面上显示了“这是我的Lambda网站”。
总而言之,构建此网站的关键组件是这个Lambda接口,以及我可以将其连接到API Gateway的能力。之后,我还可以添加不同的触发器,或者保留当前这个触发器。这是现代云计算的一项关键能力。


本节课中,我们一起学习了如何在AWS Lambda上构建无服务器网站。我们创建了一个Python函数,通过API Gateway配置了HTTP触发器,使其能够响应Web请求并返回动态HTML内容。这个过程展示了无服务器架构的简洁性和灵活性。
043:在EC2虚拟机上构建网站 🚀
在本节中,我们将学习如何在EC2 Spot实例上构建一个简单的网页服务器。我们将从设置开发环境开始,逐步完成创建密钥对、配置安全组、启动Spot实例、安装Web服务器软件,并最终部署一个测试网页的全过程。通过这个实践,你将掌握在云端使用虚拟机快速搭建和测试Web应用原型的基本方法。
准备工作
上一节我们介绍了云计算的基本概念,本节中我们来看看如何具体操作。首先,我们需要完成几项准备工作,包括创建密钥对和配置安全组,以便安全地连接到即将启动的虚拟机。


以下是创建密钥对和安全组的步骤:
- 创建密钥对:在AWS控制台中,导航至EC2服务,选择“密钥对”并点击“创建密钥对”。将其命名为
hello-web-service,保持默认设置并创建。下载生成的.pem私钥文件。 - 上传密钥对到Cloud9:在Cloud9开发环境中,通过“文件”->“上传本地文件”功能,将下载的
.pem文件上传至工作区。 - 创建安全组:在EC2控制台中,导航至“安全组”并点击“创建安全组”。将其命名为
hello-spot-web-service,描述为“用于Spot Web服务”。 - 添加入站规则:在新建的安全组中,添加两条入站规则:
- 类型:
SSH,端口:22,来源:0.0.0.0/0(允许所有IP进行SSH连接)。 - 类型:
HTTP,端口:80,来源:0.0.0.0/0(允许所有IP访问Web服务)。
- 类型:
启动Spot实例
准备工作完成后,我们现在可以启动一个EC2 Spot实例。Spot实例能提供显著的成本节约,非常适合用于原型开发和测试。
以下是启动Spot实例的步骤:
- 在EC2控制台中,导航至“Spot请求”并点击“请求Spot实例”。
- 选择一个合适的模板,例如“大数据工作负载”。
- 将Amazon Machine Image (AMI) 更改为 Amazon Linux 2。
- 在“密钥对”设置中,选择之前创建的
hello-web-service。 - 在“安全组”设置中,选择我们配置好的
hello-spot-web-service。 - 将目标容量设置为1,确认预估折扣(通常为70-80% off),然后提交请求。
- 请求提交后,状态会变为“已提交”。稍等片刻,可以在“实例”页面看到新实例进入“pending”然后“running”状态。
- 为实例添加一个易于识别的名称,例如
spot-web-service。
连接到实例并安装Web服务器
实例运行后,我们需要通过SSH连接到它,并安装Apache Web服务器。
以下是连接和安装的步骤:
- 连接实例:在EC2控制台的实例详情页,点击“连接”按钮。按照提供的SSH连接指令操作。
- 设置密钥权限:首先在Cloud9终端中,运行以下命令修改私钥文件的权限:
chmod 400 hello-web-service.pem - 建立SSH连接:复制并执行控制台提供的SSH连接命令,格式通常如下:
ssh -i "hello-web-service.pem" ec2-user@<你的实例公有DNS> - 更新系统与安装Apache:成功连接后,在实例的终端中依次执行以下命令:
sudo yum update -y # 更新系统软件包 sudo yum install httpd -y # 安装Apache HTTP服务器 sudo systemctl start httpd # 启动Apache服务 sudo systemctl enable httpd # 设置Apache开机自启
测试与部署网页
Web服务器安装并启动后,我们可以进行测试并部署自定义的网页内容。
以下是测试和部署的步骤:
- 测试默认页面:在浏览器中访问EC2实例的公有IPv4地址或公有DNS。如果看到Apache的测试页面,说明Web服务器运行正常。
- 准备Web目录权限:为了能够编辑网页文件,需要为默认的Web目录设置适当的权限。在实例终端中执行:
sudo usermod -a -G apache ec2-user # 将ec2-user加入apache组 sudo chown -R ec2-user:apache /var/www # 更改/var/www目录的所有者 sudo chmod 2775 /var/www && find /var/www -type d -exec sudo chmod 2775 {} \; # 设置目录权限 find /var/www -type f -exec sudo chmod 0664 {} \; # 设置文件权限 - 创建自定义网页:导航到Web根目录并创建一个简单的HTML文件:
使用文本编辑器(如cd /var/www/html touch index.htmlvi或nano)编辑index.html文件,输入以下内容:<html> <body> <p>Hi</p> </body> </html> - 重启服务并验证:保存文件后,重启Apache服务使更改生效:
再次在浏览器中刷新实例的公有IP地址,现在应该能看到显示“Hi”的自定义网页。sudo systemctl restart httpd
总结
本节课中我们一起学习了在AWS EC2 Spot实例上构建一个完整Web服务器原型的全过程。我们首先创建了密钥对和安全组以确保访问安全,然后启动了高性价比的Spot实例。接着,我们通过SSH连接到实例,安装并配置了Apache HTTP服务器。最后,我们通过修改权限和创建HTML文件,成功部署并测试了一个简单的自定义网页。


这种方法的优势在于你拥有对服务器的完全控制权,搭建过程相对直接。但需要注意的是,与S3托管静态网站相比,运行EC2实例需要持续付费,且需要自行维护服务器。这个流程为在云上使用虚拟机进行应用开发和测试提供了一个可重复使用的模板。
044:使用AWS Elastic Beanstalk平台即服务构建网站 🚀
在本节课中,我们将学习如何使用AWS的Elastic Beanstalk服务,这是一种平台即服务(PaaS)产品,来快速部署一个Flask Web应用。我们将从环境准备开始,一步步完成应用的本地开发、配置,并最终将其部署到云端。
Elastic Beanstalk的核心价值在于,它将部署和运维的复杂性抽象化。开发者只需专注于应用代码,而诸如服务器配置、负载均衡、自动扩展和监控等基础设施管理工作,均由AWS自动处理。这能显著提升开发效率,让团队能更快地构建和发布应用。
架构概述与准备工作 🏗️
在开始动手之前,我们先了解一下Elastic Beanstalk的运作架构。它作为一个PaaS产品,承担了所有繁重的部署和运维工作。其典型工作流程是:开发者使用一个命令行工具(EB CLI)来编排整个部署过程。这个工具会在后台自动创建并配置一个完整的生态系统,包括EC2实例、负载均衡器、安全组、自动扩展组等,然后将我们的应用代码部署到这个准备好的基础设施上。
以下是开始使用Elastic Beanstalk CLI的推荐步骤:
- 启动一个运行Cloud9的EC2实例:这提供了一个在线的集成开发环境。
- 安装EB CLI工具:按照官方指南,从GitHub仓库获取并安装最新的命令行工具。
我已经提前完成了这些准备工作。现在,在终端中输入 eb --help,如果看到帮助信息,说明工具已成功安装并运行。这正是PaaS工具的强大之处——它为我们构建了部署应用所需的强大基础设施。
创建并配置本地Flask应用 💻
上一节我们介绍了Elastic Beanstalk的架构和准备工作,本节中我们来看看如何创建一个简单的Flask应用,并为其部署做准备。
首先,我们遵循步骤来设置一个新的Elastic Beanstalk环境。
-
创建一个项目目录并进入:
mkdir eb_flask cd eb_flask -
创建一个Python虚拟环境。这里为了演示方便,我们将虚拟环境创建在项目目录内:
python3 -m venv venv -
激活虚拟环境:
source venv/bin/activate -
在虚拟环境中安装特定版本的Flask:
pip install flask==1.0.2 -
将已安装的包及其版本号导出到
requirements.txt文件中。这个文件对Elastic Beanstalk至关重要,因为它指明了需要安装的依赖:pip freeze > requirements.txt
编写Flask应用代码 📝
环境配置好后,接下来我们需要编写应用的核心代码。
-
创建一个名为
application.py的应用文件:touch application.py -
将以下Flask应用代码复制到
application.py文件中。这段代码非常简单,包含两个路由:一个返回“Hello World”,另一个接收URL参数并返回JSON格式的响应。from flask import Flask application = Flask(__name__) @application.route('/') def hello_world(): return 'Hello World!' @application.route('/echo/<name>') def echo(name): return {'echo': name}
本地测试应用 ✅
在部署到云端之前,最好先在本地测试应用是否能正常运行。
-
在终端中运行Flask应用:
python application.py应用启动后,默认会在本地服务器的5000端口监听。
-
打开另一个终端窗口,使用
curl命令测试我们的路由:# 测试根路由 curl http://localhost:5000/ # 输出:Hello World! # 测试echo路由 curl http://localhost:5000/echo/Bob # 输出:{"echo":"Bob"}如果测试成功,说明我们的应用在本地运行良好,可以准备部署了。
部署应用到Elastic Beanstalk ☁️
我们的应用在本地运行无误,现在可以将其部署到AWS Elastic Beanstalk了。
首先,我们需要确保不将虚拟环境目录上传到云端。为此,创建一个名为 .ebignore 的文件(类似于 .gitignore),并在其中添加 venv/ 以忽略虚拟环境目录。
接下来,使用EB CLI创建并部署环境。这个命令会在后台执行大量工作,包括创建EC2实例、安全组、负载均衡器、自动扩展组、S3存储桶、CloudWatch警报,并使用CloudFormation栈进行基础设施即代码管理。
eb init -p python-3.6 flask-cloud-demo
eb create flask-cloud-demo-env
命令执行后,EB CLI会自动处理所有基础设施的创建和配置。这个过程可能需要几分钟。我们可以通过以下命令在部署完成后在浏览器中打开应用:
eb open
或者,我们也可以直接登录AWS管理控制台,在Elastic Beanstalk服务中查看环境状态。当环境状态变为“OK”后,点击提供的URL即可访问我们部署的网站。同样,可以使用 curl 或浏览器测试 / 和 /echo/<name> 路由。
清理资源 🧹
在完成原型开发或测试后,及时清理资源非常重要,以避免产生不必要的费用。
要删除我们创建的整个Elastic Beanstalk环境及其所有关联资源(如EC2实例、负载均衡器等),只需运行以下命令:
eb terminate flask-cloud-demo-env
系统会要求你确认操作。确认后,Elastic Beanstalk将开始清理所有资源。我们可以在AWS控制台上看到环境状态变为“终止中”,直至最终消失。


本节课中我们一起学习了如何使用AWS Elastic Beanstalk这一PaaS服务来快速部署Flask应用。我们从理解其自动化部署的架构优势开始,逐步完成了本地应用开发、依赖管理、本地测试,最后通过简单的命令行操作将应用部署到高可用的云端环境中,并在最后清理了所有资源。Elastic Beanstalk极大地简化了从开发到上线的流程,是快速构建和迭代Web应用的强大工具。
045:使用Zola构建静态网站 🚀

在本节课中,我们将学习如何使用Zola这一静态网站生成器来构建网站。我们将了解其核心优势、基本工作原理以及快速上手的步骤。
Zola是一个用Rust语言编写的静态网站生成器。它是一个可以下载的Rust二进制文件。这使得它易于上手,并且可以跨多种不同平台移植,在不同环境中安装也非常简单。
速度优势 ⚡
首先我们来谈谈速度。由于内容被预构建成静态HTML文件,Zola能够极其快速地生成网站。这比动态内容管理系统的生成速度要快得多。
核心特性与优势 ✨
以下是Zola的一些核心特性和优势:
- 模块化模板:这些模板是可复用的,有许多优秀的模板可供直接使用或在其基础上构建。
- 基于Markdown:这是一个巨大的优势。你只需编写易于人类阅读的Markdown文件,它就能自动转换为外观精美的网站。
- 支持高级功能:它支持Sass和CSS等高级功能,这些Sass编译器能为设计师实现更复杂的效果。
- 易于发布和部署:你可以轻松地将网站部署到GitLab Pages、AWS或其他云环境中。
- 自由度高:这一点非常重要。许多公司提供“点击即用”的网站生成器,但你需要为此付费,并且需要赌这家公司能长久运营。如果你自己拥有静态网站,你可以将其迁移到任何地方,甚至可以将文件离线交给他人。
使用静态网站生成器有许多优点。Zola是一个“一体化”的静态站点引擎,没有外部依赖,速度极快,可扩展性强,并且非常易于使用。
快速入门指南 🛠️

上一节我们介绍了Zola的优势,本节中我们来看看如何快速开始使用它。文档中会指导你完成一些常见的必要步骤。

以下是开始构建网站的基本流程:
- 构建初始结构:创建网站的基本目录和文件结构。
- 构建网站:将你的静态文件(如Markdown)转换为最终的HTML网站。
- 本地服务:在本地启动一个服务器来预览网站效果。
- 检查:对网站进行语法或链接检查。
需要注意的是,大多数人可能希望从一个主题开始。你可以直接下载一个主题,然后就可以开始使用了。这使得Zola的入门变得非常简单。
总结 📝

本节课中我们一起学习了Zola静态网站生成器。它拥有速度快、基于Markdown、模板丰富、部署简单等诸多优点。在所有这些能力中,最重要的或许是它带来的自由——你不会被锁定在某个可能因资金撤出而关闭的平台上,你可以完全掌控自己的内容。使用静态网站生成器能带来许多基于自由度的优势。
046:自定义Zola主题 🎨

在本节课中,我们将学习如何使用静态网站生成器Zola,并为其应用一个自定义主题。我们将从初始化一个Zola站点开始,然后集成一个主题,最后进行简单的配置修改以验证我们的工作。
启动Zola并初始化站点
首先,我们在一台Ubuntu桌面机器上启动Zola。我们将打开一个代码工作空间,并确保有一个终端窗口来辅助我们的工作流程。
进入工作空间后,我们首先列出目录内容,确认Zola已安装。接着,我们使用 zola init 命令来初始化一个新的站点。
zola init my_site
在初始化过程中,我们通常选择所有默认选项以快速完成设置。初始化完成后,我们可以进入站点目录并运行Zola的本地服务器。
cd my_site
zola serve
服务器启动后,我们可以在浏览器中访问 http://localhost:1111 来查看默认的站点页面。

集成自定义主题
上一节我们成功运行了基础的Zola站点,本节中我们来看看如何为其添加一个自定义主题。
以下是集成主题的步骤:
- 复制主题文件:将准备好的主题文件夹复制到站点的
themes目录下。cp -r ../a80_idoks_theme ./themes/a80_idoks - 更新配置文件:将主题自带的示例配置文件复制为站点的主配置文件。
cp themes/a80_idoks/config.toml.example ./config.toml
完成这些步骤后,重新运行 zola serve,刷新浏览器页面,即可看到应用了新主题的网站。
验证与自定义修改
成功应用主题后,我们可以通过修改配置文件来验证一切工作正常,并进行简单的自定义。
例如,我们可以打开 config.toml 文件,找到 title 字段并将其修改为“Demo”。
title = "Demo"
保存文件后,Zola服务器会自动检测到更改并重新构建。刷新浏览器,可以看到浏览器标签页的标题已更新为“Demo”。这证明了我们的配置修改已生效。
使用Zola这类静态网站生成器的优势在于它们速度极快、易于使用,并且通常以二进制文件形式分发,可以快速部署。构建好的静态文件可以轻松部署到GitLab Pages、AWS S3或其他静态网站托管服务上。

本节课中我们一起学习了Zola静态网站生成器的基本使用流程。我们从初始化站点开始,接着集成并应用了一个自定义主题,最后通过修改站点标题验证了整个配置过程。这是一个开始使用静态网站生成技术的有效方式。
047:云计算经济学介绍 💰
在本节课中,我们将更详细地探讨云计算的经济学原理。我们将解释云计算的经济学基础,并深入介绍本课程将涵盖的一些核心概念与关键术语。
上一节我们介绍了课程的整体框架,本节中我们来看看云计算经济学中的几个核心概念。
关键术语解析
以下是理解云计算经济学必须掌握的几个关键术语。
- 弹性:指根据需求扩展和收缩资源的能力。其核心在于按需调整,避免资源闲置或不足。
- 可用性:指系统响应请求的能力,关键在于是否拥有足够的处理容量来满足需求。
- 自助服务:意味着用户可以自行获取资源,无需经过传统的IT采购流程。例如,插入信用卡即可启动虚拟机。
- 降低复杂性:由于云服务提供商处理了大量底层细节(如数据中心内的网络或安全),因此您公司需要应对的复杂性得以降低。
- 总体拥有成本:这与降低复杂性相关。它指的是在特定时期(例如五年)内,您在软件、IT和人员薪资上的花费,与租用云资源成本之间的比较。通常,使用云资源的总体拥有成本远低于维护自有物理数据中心。
在了解了这些基础术语后,我们接下来看看云计算如何从商业层面影响企业。
商业优势
除了技术术语,云计算还带来了重要的商业价值。
- 运营韧性:指您的公司能否承受冲击(例如自然灾害)。当您使用云服务时,云提供商内置的高韧性将成为您与云供应商关系的一部分,从而增强您公司的运营韧性。
- 业务敏捷性:企业很容易忽视一个事实:公司的核心是从事特定业务,而这通常与计算基础设施无关。通过利用云提供商日益增长的服务,您的公司可以更专注于快速构建产品并响应客户需求。


本节课中我们一起学习了云计算经济学的核心概念,包括弹性、可用性、自助服务等关键术语,以及云计算在降低总体拥有成本、增强运营韧性和提升业务敏捷性方面带来的商业优势。理解这些经济学原理是构建高效、经济云计算解决方案的基础。
048:一个案例
在本节课中,我们将通过一个真实的故事来探讨云计算经济学中的一个核心概念:自建解决方案与采用成熟商业/云服务的权衡。
概述
我们将分析一个发生在财富500强公司的真实案例,它揭示了当企业试图自行构建非核心业务功能时可能面临的风险与成本。这个故事将帮助我们理解云计算带来的商业敏捷性的真正价值。
案例故事
让我分享一个职业生涯中的故事。当时我在一家主要的财富500强公司工作。
我们团队中有一些非常出色的同事。我所在的团队拥有一项围绕日志文件搜索和信息检索的出色技术。开发者们非常喜爱这个由一位开发者自主创建的内部解决方案。
然而后来,那位开发者被湾区的一家顶级科技公司挖走了。他是一位非常杰出的开发者。
在大约两到三个月后,他为公司开发的这个纯内部产品开始崩溃。这正是公司构建非核心业务内容所面临的问题之一。
试图自行构建的后果是,你的顶尖人才可能会离开,前往其他地方。其他人将不得不接手这个项目,而这可能并非你公司的核心业务。
最终,我们采取的行动是彻底移除这个内部方案,并购买了一个商业解决方案。这个商业方案实际上要好得多,也更容易维护。
那位杰出工程师创建的“雪花”式或一次性解决方案,事后看来确实是一个需要反思的案例。
核心启示
我认为这是云计算的一个关键启示。如果你能够真正拥抱趋势,把握住人们所构建方案的商业敏捷性,你就能抓住云计算的本质。
与其辛苦地重新发明轮子,或者陷入“非我发明”综合症的思维,你可以专注于为公司构建最佳的解决方案,并聚焦于你的公司最具独特竞争力的领域。
总结

本节课中,我们一起学习了一个关于内部解决方案风险的案例。它说明了将资源集中在核心业务上,并利用云计算或成熟商业服务来处理非核心功能,往往是更经济、更可持续的策略。这有助于企业保持敏捷并专注于创造独特价值。
049:云经济学深度解析 💰

在本节课中,我们将深入探讨云经济学,理解其核心概念如何帮助企业优化成本、提升效率并实现业务敏捷性。我们将逐一解析弹性、可用性、自助服务、降低复杂性、总拥有成本、运营弹性和业务敏捷性这七个关键概念。
弹性 🧘
弹性是云经济学的核心概念之一。它意味着当公司拥有的网络服务器流量增加时,系统可以自动响应,获取一台或多台新的虚拟机。同样,当流量下降时,系统可以回收这些虚拟机资源,使其进入无需物理购买的状态。弹性概念的本质是根据需求进行向上扩展和向下缩减。
我们理解这个概念,是因为它与公用事业的工作原理类似。公用事业是弹性的一个绝佳例子:如果你需要更多空调,可以从电力公司获取更多电力;反之,如果你不需要,可以关闭恒温器,停止消耗电力。同样的概念适用于云计算。掌握这个概念至关重要:当更多流量涌入时,你可以扩展;当流量减少时,你可以缩减。这是实现巨大成本节约的方式。


你可以将其视为一种80/20法则。在传统数据中心,80%的成本源于必须预先购买所有硬件。但在云环境中,你可以更像一个20%的参与者,因为峰值时可以扩展,而无需在流量回落后继续保留这些实例。大多数情况下,许多技术网站的流量具有周期性。
可用性 ✅




云经济学中另一个重要概念是可用性。这指的是你的网站是否可用。具体含义是:当我发送一个请求时,是否能得到一个健康的响应?无论我试图访问的是何种网络服务,我是否总能得到回应?服务是99.9999%可靠,还是存在可用性问题?
这就是可用性的概念:你使用的服务是真正为可扩展性而设计的。对于一个独立的公司来说,仅仅因为购买所有基础设施的启动成本,几乎不可能自行构建类似的东西。
自助服务 🤖



云经济学的另一个关键概念是自助服务。你是否可以在不经过冗长的IT采购流程和涉及多人的官僚主义的情况下获取资源?或者,你是否能以更自助的方式进行操作?

自助服务的一个好例子是自动售货机。如果你想喝水或吃点零食,可以去自动售货机,付款后立即获得。虽然价格可能稍高,但它解决了不需要人工介入的问题。许多云技术正是为此而设计,自助服务可能是云计算的一个核心特性。这意味着公司中的个人用户真正被赋予了用信用卡解决问题的能力,而传统方式则需要一个冗长的流程来完成一般业务。
降低复杂性 🧩


云计算中一个不常被提及但非常重要的方面是降低复杂性的理念。这意味着你可以专注于解决业务问题,而不是去判断数据中心是否存在安全问题,或者网络是否正遭受外部攻击。云供应商能够为你解决所有这些问题,因为他们专门解决这些问题。
因此,我认为这是云计算一个常被忽视的方面:当你使用专家并利用你最擅长的技能时,事情会变得更简单。这是你应该使用云计算的一个比较优势的例子。


总拥有成本 📊



20世纪80年代和90年代最流行的术语之一是“总拥有成本”这个短语,至今仍是一个非常重要的术语,原因很充分。很多时候,人们很容易只关注某物的初始成本,而忽略了总成本。
例如,对于物理数据中心,如果有人只看到他们已经投入的初始或固定投资(也称为沉没成本),他们可能会想:“我们已经有了这些人员和设备,为什么还需要使用云计算?”很多时候,长期成本才是重要的。





因此,如果你开始从长远角度审视,也许最初没有收益,但最终这些成本会大大降低,因为在生命周期内,你无需支付更高的薪水,也无需支付固定成本。所以,当你考虑总拥有成本时,你关注的是长期影响。如果你的公司降低了维护这个生态系统的薪水和固定成本,会发生什么?很多时候,结果是你的公司会节省资金,因为从长远来看,你正在从前期成本转向可变成本,而可变成本是你可以控制和优化的。


运营弹性 🛡️
运营弹性真正回应了这个问题:当出现某种危机时,你的公司如何运作?假设你拥有一个物理数据中心,发生了自然灾害导致其离线。如果你把所有资源都投入到一个物理数据中心,那么你基本上就束手无策,无法解决问题。但当你使用云提供商或利用拥有比你更好资源的公司时,你就获得了这种内在的运营弹性。
因此,从第一天起你就拥有了全球规模。所以,如果出现某个数据中心离线的情况,这并不重要,因为你已经设计了你的应用程序来应对这种情况,并且你知道可以处理这种故障,因为你具备了内置的运营弹性。这是云经济学另一个非常重要但较少被理解的方面:除非你是一家规模极其庞大的软件公司,否则几乎不可能构建出这种弹性。





业务敏捷性 🏄

业务敏捷性很像冲浪。你驾驭着浪潮,这是一种极其强大的自然力量,如果你试图对抗它,它可能会摧毁你。但如果你能利用浪潮的能力,冲浪者就能驾驭这些巨浪,他们是顺应浪潮,而不是强迫浪潮做某事。
云计算的业务敏捷性非常相似。通过利用不断发展的云原生资源,你可以专注于公司真正关注的业务核心战略,无论是销售零售商品、提供机器学习应用还是构建移动应用。通过不专注于云提供商已经为你提供的事情,你就是在驾驭浪潮,能够更快地前进,并以更快的速度开发新功能。也许每周,你的公司都能开发新功能,因为你没有浪费时间去做那些别人已经以比你公司可能做到的好得多的方式为你完成的事情。




本节课中,我们一起学习了云经济学的七个核心概念:弹性、可用性、自助服务、降低复杂性、总拥有成本、运营弹性和业务敏捷性。理解这些概念有助于企业充分利用云计算的优势,实现成本优化、效率提升和快速创新。
050:DevOps介绍 🚀
在本节课中,我们将要学习DevOps的核心概念。我们将探讨DevOps的定义、关键实践以及相关术语,帮助你理解它如何弥合软件开发与IT运维之间的鸿沟。
什么是DevOps?🤔
上一节我们介绍了课程概述,本节中我们来看看DevOps究竟是什么。DevOps是一种集文化理念、实践与工具于一体的方法论,旨在提高组织高速交付应用程序和服务的能力。它强调软件开发(Dev)与IT运维(Ops)团队之间的协作与沟通,从而实现比传统流程更快速、更可靠的软件构建、测试和发布。
DevOps的关键实践 🔑
理解了DevOps的基本定义后,我们来深入探讨其核心实践。这些实践共同构成了DevOps方法论的基础。
以下是DevOps中一些关键的共享实践:
- 持续集成:这是一种开发实践,要求开发人员频繁地将代码变更合并到共享的主干分支中。每次合并都会触发自动化构建和测试流程,以便尽早发现集成错误。其核心公式可表示为:
代码提交 -> 自动构建 -> 自动测试。 - 持续交付:这是持续集成的延伸,确保代码在通过所有测试阶段后,始终处于可部署到生产环境的状态。它意味着任何时刻的代码库都是可发布的。
- 微服务:这是一种架构风格,将单个大型应用程序拆分为一组小型、松散耦合的服务。每个微服务都专注于完成一项特定的业务功能,并可以独立开发、部署和扩展。
- 基础设施即代码:这是一种通过代码(如YAML、JSON或特定领域语言)来管理和配置基础设施的方法,而不是手动设置。这些代码文件可以像应用程序代码一样进行版本控制、审查和维护。例如,使用Terraform定义云资源:
resource "aws_instance" "example" { ami = "ami-0c55b159cbfafe1f0" instance_type = "t2.micro" } - 监控与日志记录:为了确保系统健康并快速定位问题,需要对应用程序和基础设施进行全面的监控和日志记录。这就像飞行员依靠仪表盘驾驶飞机一样,运维和开发团队依靠监控数据来了解系统状态。
- 沟通与协作:这是DevOps文化的基石。它强调打破开发、运维及其他相关团队(如安全、测试)之间的壁垒,通过共享责任、工具和信息流来促进高效合作。
总结 📝


本节课中我们一起学习了DevOps的基本概念。我们了解到,DevOps不仅仅是工具或自动化,它更是一种促进开发与运维紧密协作的文化。其核心实践包括持续集成、持续交付、微服务架构、基础设施即代码、全面的监控与日志记录,以及最重要的——沟通与协作。掌握这些概念是构建高效、可扩展的云计算解决方案的重要基础。
051:现实世界中的DevOps 🚀
在本节课中,我们将探讨DevOps在现实世界中的应用。我们将了解为什么构建服务器是实现DevOps的核心,以及它如何帮助团队持续改进代码质量。
我的职业生涯大部分时间都在现实世界的公司中度过,包括社交媒体公司、游戏公司和社交网络公司。在这些公司中,我的主要职责通常是帮助建立持续交付流程。
作为工程经理或个人贡献者,建立一个能够自动测试和部署代码的构建系统,是我为所服务的每家公司所做的最重要的事情之一。我学到的一个关键要点是:DevOps的核心在于构建服务器这一核心资产,它负责建立测试和质量控制,并将此过程自动化。
这样做的目的是确保每次你对源代码进行更改时,系统都在变得更好,而不是更糟。这里有一个简单的经验法则:要么你每天都在变得更好,要么你每天都在变得更糟。如果你不知道自己是哪一种情况,那么你很可能正在变得更糟。
这正是构建服务器的作用所在。因此,构建服务器对于在你的组织中实施DevOps至关重要。
上一节我们介绍了构建服务器在DevOps中的核心地位,本节中我们来看看它的具体价值。
构建服务器通过自动化流程,确保了代码的每一次变更都能得到即时验证。以下是构建服务器带来的几个关键好处:
- 持续改进:自动化测试和部署确保每次提交都推动代码库向更好的方向发展。
- 质量保障:通过自动化的质量控制,及早发现并修复问题。
- 状态可知:团队可以清晰地了解当前构建是成功还是失败,避免了“未知即恶化”的情况。

本节课中我们一起学习了DevOps在现实世界的实践。我们认识到,构建服务器及其自动化流程是实施DevOps、保障代码质量并实现持续改进的基石。记住,一个健康的构建系统是团队高效交付和稳定运营的关键。
052:DevOps的优势 🚀

在本节课中,我们将要学习DevOps的核心优势。我们将详细探讨DevOps如何通过一系列实践,帮助团队和组织在软件开发与交付的各个方面实现显著提升。
首先,我们来定义什么是DevOps。它是一种旨在提升团队交付速度的实践。提升速度是DevOps的一个关键组成部分。如果一项实践不能带来改善,我们为何要采用它呢?DevOps确实能够提升软件部署的速度,并加快软件到达客户手中的速度,这正是其核心价值所在。
接下来,我们将详细剖析DevOps带来的具体优势。
优势详解
以下是DevOps带来的主要优势。
- 速度:通过运用DevOps原则,整个组织将能够更快地行动。这意味着所有环节都会加速:功能开发、软件上线生产、以及开发人员创造软件的周期。这是DevOps的核心组成部分之一,也是一个显著优势。
- 交付:正如之前提到的,能够更快地将新功能或缺陷修复直接交付给客户,是一个关键优势。在某些情况下,花费一年时间开发某个功能可能会让公司失去竞争力。而通过提升交付能力,你实际上囊括了DevOps的所有益处。
- 可靠性:DevOps原则的一大优点是,由于你实现了自动化并持续改进,通过测试、监控和日志记录等手段,你的系统将变得更加可靠。监控和日志记录是DevOps鼓励的最佳实践,它将确保你的系统具有高度的可靠性。
- 扩展性:为了进行大规模运营,方法之一是使用基础设施即代码来自动化管理基础设施。同时,通过采用更小的微服务,你能够将系统扩展到更大的规模。关于扩展性,一个不那么直观的关键点是:系统设计得越简单(例如这些小型服务),扩展就越容易。因为每个系统本身都易于理解和维护,你可以在此基础上不断构建,直至达到惊人的规模。
- 协作:协作是DevOps的一个关键方面。它意味着共享所有权和责任。不再是开发人员编写代码后交给别人,或者产品经理提出需求后强迫开发人员去实现。而是所有人共同努力,共享所有权和问责制。这意味着你减少了低效环节,节省了时间。
- 安全性:当今许多软件应用面临的一个关键问题是数据泄露,即无意中将数据提供给他人。实际上,你可以将策略即代码,从而大规模地定义和跟踪合规性。提升安全级别是DevOps的关键方面之一。从这个角度看,仅凭这一点,就可能成为你的组织选择采用DevOps的主要原因。


本节课中,我们一起学习了DevOps的六大核心优势:速度、交付、可靠性、扩展性、协作和安全性。理解这些优势有助于我们认识到DevOps实践如何从整体上提升软件开发和运维的效率与质量。
053:DevOps最佳实践 🚀
在本节课中,我们将学习DevOps的核心最佳实践。这些实践构成了一个组织成功实施DevOps文化的关键检查清单,旨在提升软件质量、加快交付速度并增强团队协作。
概述 📋
DevOps是一套结合了开发与运维的文化、实践与工具,旨在缩短系统开发生命周期,并提供高质量的持续交付。接下来,我们将逐一探讨构成DevOps核心的几项最佳实践。
持续集成(Continuous Integration)
上一节我们概述了DevOps的目标,本节中我们来看看第一项关键实践:持续集成。
持续集成是自动测试代码、确保软件质量并减少验证或发布新软件更新时间的过程。这是一个需要纳入检查清单的关键环节。
其核心流程通常通过代码来描述:
# 开发者提交代码到共享仓库
git commit -m "新功能"
git push origin main
# 持续集成服务器自动触发构建和测试
# 例如,运行测试套件
npm test
# 或
pytest
持续交付(Continuous Delivery)
理解了持续集成后,我们接下来探讨其自然延伸:持续交付。
持续交付是指代码变更能够被自动构建、测试,并准备好发布到生产环境的能力。这意味着你可以将所有变更部署到测试或预发布环境,且整个过程无需人工干预。
以下是实现持续交付的一个简化概念模型:
代码提交 -> 自动构建 -> 自动测试 -> 自动部署到预发布环境
微服务架构(Microservices)
除了集成与交付,系统架构本身也至关重要。以下是现代软件开发中一项关键的架构实践。
微服务是DevOps的关键组成部分。它允许你将一个单体应用构建为一组小型服务的集合。每个服务独立运行,并通过队列系统或其他接口进行通信。这种架构通过简化每个服务,极大地提升了系统的可扩展性。
基础设施即代码(Infrastructure as Code)
要实现高效的持续交付,基础设施的管理方式必须变革。以下是另一项组织必须拥有的最佳实践。
基础设施即代码允许你将基础设施本身(如服务器配置、网络设置)像应用程序代码一样,存入Git仓库进行版本管理。这使得你能够以自动化、可重复的方式编排基础设施,从而获得DevOps所带来的交付速度。
其核心思想可以用一个公式表达:
基础设施配置 = 可版本控制的代码文件
监控与日志(Monitoring and Logging)
在自动化部署之后,了解系统运行状况至关重要。以下是一项常被忽视但极其重要的实践。
监控与日志记录允许你查看应用程序指标和基础设施状态(如CPU负载、内存、磁盘使用情况),从而更快地定位问题根源。发现的问题可以通过持续交付流程进行修复,形成一个数据驱动的反馈闭环。这本质上是一个“观察-决策-部署”的循环。
沟通与协作(Communication and Collaboration)
最后,但同样重要的是,DevOps的成功离不开文化的支撑。以下是所有实践得以落地的基石。
沟通与协作意味着在组织文化层面,持续寻求更好的沟通方式。这可以通过工单系统、聊天工具让开发与运维人员讨论源代码管理的各个方面,或者在技术文档中添加详尽的注释来实现。将沟通与协作置于优先地位,是成功实施所有前述DevOps最佳实践的关键。
总结 🎯

本节课中我们一起学习了构成DevOps核心的六项最佳实践检查清单:
- 持续集成:自动测试,保障质量。
- 持续交付:自动化构建、测试与部署准备。
- 微服务架构:构建小型、独立、可扩展的服务。
- 基础设施即代码:以可编程、可版本控制的方式管理基础设施。
- 监控与日志:建立数据驱动的反馈闭环,快速定位问题。
- 沟通与协作:培育开放、透明的团队文化。

这些实践相辅相成,缺一不可。只有将它们全部融入组织的基础设施和文化中,才能真正实现DevOps的潜力。
构建大规模云计算解决方案:1-2:使用IaC管理云基础设施介绍 🚀
在本节课中,我们将学习如何利用基础设施即代码来管理云基础设施。
首先,我们将解释什么是基础设施即代码。然后,我们将探讨如何利用它来管理云基础设施。
核心概念与术语
上一节我们介绍了课程目标,本节中我们来看看几个关键术语。
基础设施即代码 本身就是一个核心术语。它指的是被检入代码仓库、用于部署基础设施的代码。其核心思想非常简单。
Terraform 是基础设施即代码的一种流行工具。它可以在包括GCP、AWS和Azure在内的多个云平台上运行。
环境漂移 是指环境进入一种你无法确切知晓其状态的情况。基础设施即代码所解决的正是这个问题——它通过每次部署时修正环境状态,来阻止环境发生漂移和意外变更。
雪花环境 是一个很好的例子,说明了不使用自动化来定义基础设施时会发生什么。一个人很容易做出更改,然后忘记它。接着另一个人又来做出更改。不知不觉中,你的环境就变得不可复现。这很像童话故事里的蛋头先生,摔碎之后没人能把他拼回原样。雪花环境就是如此,我们将在后面详细讨论。
总结


本节课中,我们一起学习了基础设施即代码的基本概念及其核心价值。我们了解了基础设施即代码是存储在仓库中的部署代码,认识了Terraform这一跨平台工具,并探讨了环境漂移和雪花环境这两个因缺乏自动化管理而导致的典型问题。理解这些概念是迈向自动化、可重复云基础设施管理的第一步。
055:现实世界中的基础设施即代码 (IaC) 🏗️

在本节课中,我们将通过一个真实的故事,来了解基础设施即代码在现实世界中的重要性、威力以及潜在的风险。
概述
我们将从一个真实的运维事故案例开始,这个故事展示了基础设施即代码如何成为一家公司的“救命稻草”,同时也揭示了错误使用它可能带来的问题。通过这个案例,我们将深入理解为什么基础设施即代码是现代软件工程的关键组成部分。
一个真实世界的 IaC 故事
上一节我们概述了本节课的主题,本节中我们来看看这个具体的故事。
我当时在湾区一家软件即服务公司担任工程主管。公司的创始人在凌晨两点打电话给我,告诉我一切都宕机了。他说,什么都不存在了,我们的整个基础设施都被删除了。
我们的服务托管在亚马逊云上。我查看了我们的仪表盘,确实没有任何服务器可用。那真是一段艰难的时期。我开车到办公室,试图弄清楚发生了什么。后来我们开始查明原因:发生的情况是,有一些关于即将退役的虚拟机的警告邮件被忽略了。这些邮件躺在公司创始人的垃圾邮件文件夹里。云服务商最终因为这些虚拟机是旧版本而将它们下线。实际上我们提前几个月就收到了通知,但直到它们最终被删除,我们才注意到。
因此,从零开始恢复我们整个公司的唯一方法,就是使用基础设施即代码。
恢复过程与挑战
上一节我们了解了事故的起因,本节中我们来看看具体的恢复过程与遇到的挑战。
我所做的是,去查看我们的构建系统,该系统使用了一个名为 Puppet 的基础设施即代码系统。这是一个较老的系统,在2010年左右非常流行。结果我发现我无法运行它。我试图找出问题所在,后来我们确定,那个版本的 Puppet 与我们使用的版本不同。我们对它进行了一些调整和修改。我必须找到我们使用的那个特定版本的 Puppet,它基本上能解锁我们的整个生态系统,并让我们从零开始重建公司。
幸运的是,我在一台机器上找到了它。之前的一位开发人员制作了他们自己的 Puppet 版本,并将其放在了一台机器上。我们找到了它,并重新创建了一切。
这个过程花了好几天,但我们没有倒闭。
经验教训与总结
上一节我们看到了如何使用 IaC 进行恢复,本节中我们来总结从这个故事中获得的经验教训。
这个故事的寓意,我认为有两点。第一点是,不要随意分叉或更改基础设施即代码系统,使用默认标准可能是最佳实践。第二点则是,基础设施即代码的力量有多么强大。一方面,我们能够通过重新执行其指令来重建整个基础设施乃至整个公司。
但另一方面,如果没有这样的能力,情况会多么危险。完全恢复一个基础设施可能需要数月时间。
因此,基础设施即代码是现代软件工程的一个关键组成部分,我们将在本课程的后续部分更详细地讨论它。
总结

本节课中,我们一起学习了一个关于基础设施即代码的真实案例。我们看到了 IaC 在灾难恢复中的决定性作用,也认识到遵循标准实践和维护 IaC 可重现性的重要性。这个故事生动地说明了为什么 IaC 是构建可靠、可扩展云解决方案的基石。
056:什么是基础设施即代码 (IaC) 🏗️

在本节课中,我们将学习基础设施即代码的核心概念。我们将了解它的定义、工作原理、优势以及为何它是现代云部署的必备实践。
概述
基础设施即代码字面意思是将基础设施与项目的源代码一同进行版本控制。这意味着你可以拥有一个可重复、幂等的流程,用于部署和配置你的云环境。
什么是基础设施即代码?
基础设施即代码是指将基础设施的定义以代码的形式,与项目源代码一同进行版本管理。这意味着部署和配置云环境的过程是可重复且幂等的。
在实践中,这意味着不仅代码本身会被部署,其运行环境也会被一同部署。这样做的好处是,你可以基于代码定义,构建出多个不同的环境。
工作原理与流程
上一节我们介绍了IaC的基本概念,本节中我们来看看它的典型工作流程。基础设施即代码的使用流程通常由一个事件触发。
这个触发事件通常是向主分支推送代码。推送代码后,构建服务器会执行标准的源代码管理流程,例如运行测试、代码检查和一些部署步骤。
与此同时,实际的物理基础设施也会被同步部署出去。这可以包括配置负载均衡器、正确设置存储或创建用户权限等。
核心优势
以下是采用基础设施即代码带来的主要好处:
- 可重复性与一致性:所有环境都通过代码模板定义,避免了手动配置的差异。
- 版本控制与审计:基础设施的变更像代码一样被记录和追踪,易于审计和回滚。
- 提升效率与自动化:环境创建和销毁可以完全自动化,加速开发和部署周期。
- 降低风险与保障业务连续性:消除了对特定人员(“关键员工”)手工操作的依赖。即使人员变动,环境也能被准确重建。
与传统方式的对比
传统部署方式就像是“雪花式部署”,即每个环境都是独特的。需要人工介入,点击各种按钮进行配置。
当你询问操作人员他们具体做了什么时,他们可能无法准确复现,因为过程过于复杂。这正是基础设施即代码要解决的核心问题。
总结
本节课中我们一起学习了基础设施即代码。它是进行云部署的最佳实践,如果你没有使用它,就不能算是在用现代方式进行部署。


它在可重复性和业务连续性方面解决了许多问题。没有基础设施即代码,可能会引发严重问题,例如关键员工离职后无人知晓其之前的配置操作。因此,基础设施即代码是所有云解决方案架构师都应采纳并在其组织中实施的最佳实践。
057:在GCP上使用Terraform启动虚拟机 🚀
在本节课中,我们将学习如何使用基础设施即代码工具Terraform,在Google Cloud Platform上启动一台虚拟机。我们将从激活Cloud Shell开始,逐步完成编写配置、初始化、规划和应用部署的完整流程。

激活Google Cloud Shell
首先,我们需要激活Google Cloud Shell。这是一个基于浏览器的命令行工具,允许我们直接在GCP控制台中交互式地构建解决方案。

验证与准备
在开始编写配置之前,最好先验证Terraform是否已正确安装。以下是验证步骤。
- 输入命令
terraform来检查安装情况。 - 该命令会显示所有可用选项,确认Terraform已就绪。

接下来,我们需要创建一个存储虚拟机配置的空文件。
- 创建一个名为
instance.tf的文件。 - 我们将使用内置的编辑器来编辑此文件,这对于不熟悉命令行工具的用户更为友好。

编写Terraform配置
现在,我们打开编辑器来编写配置。编辑器能识别.tf文件并提供语法支持。
我们将复制一段配置数据到 instance.tf 文件中。配置中唯一需要修改的是填入我们自己的GCP项目ID。
- 从GCP控制台顶部获取项目ID。
- 将项目ID粘贴到配置中
project = “YOUR_PROJECT_ID”的位置。
配置完成后,我们来解读一下这个文件的内容。
name = “terraform”: 这是虚拟机的名称。machine_type = “n1-standard-1”: 这是虚拟机的机器类型。zone = “us-central1-a”: 这是虚拟机将在GCP中部署的区域(美国中部)。boot_disk.initialize_params.image = “debian-cloud/debian-9”: 这指定了虚拟机要运行的操作系统镜像(Debian 9)。
基础设施即代码配置的优点在于,所有资源定义都声明在文件中。如果将此文件检入源代码仓库,其他人可以清晰地了解将要部署的内容。
确认无误后,保存文件。
初始化与规划

保存配置后,我们回到终端窗口。接下来,我们需要初始化Terraform工作目录。
- 执行命令
terraform init。

此命令会在后台下载所需的提供商插件(本例中是Google提供商),为后续步骤做好准备。
初始化完成后,在正式部署前,我们可以先执行规划操作来验证部署计划是否符合预期。
- 执行命令
terraform plan。
规划过程会列出Terraform将要执行的所有操作,例如创建虚拟机资源、配置启动盘等。这让我们有机会在真正改变基础设施之前进行确认。
应用配置
如果规划结果符合预期,我们就可以应用配置来实际创建资源了。
- 执行命令
terraform apply。
Terraform会再次显示执行计划,并询问是否继续。输入 yes 来批准执行。


系统可能会要求授权此次API调用。授权后,Terraform将通过GCP API在后台为我们创建资源。这体现了基础设施即代码在简化部署流程和确保可重复性方面的巨大价值。
虚拟机创建通常需要几分钟时间。完成后,终端会显示应用成功的消息。
验证部署结果
虚拟机创建成功后,我们如何找到它呢?


我们可以返回GCP控制台查看。
- 进入 Compute Engine -> VM instances 页面。


在实例列表中,可以看到名为“terraform”的虚拟机正在运行,其区域、IP地址等信息均与我们的配置一致。如果需要,我们还可以通过浏览器窗口SSH连接到该虚拟机进行操作。


总结


本节课中,我们一起学习了使用Terraform在GCP上启动虚拟机的完整过程。我们经历了激活Cloud Shell、编写声明式配置、初始化工作区、规划变更以及最终应用部署的关键步骤。Terraform提供了一种幂等、可重复且易于版本控制的方式来管理和配置云资源。本次实践只是Terraform强大功能的冰山一角,它为自动化和管理复杂云基础设施奠定了坚实基础。
058:AWS CDK for Python 入门示例 🚀
在本节课中,我们将学习如何使用 AWS CDK(Cloud Development Kit)和 Python 语言,通过基础设施即代码的方式,在几分钟内部署一个简单的 AWS Lambda 函数。我们将使用 AWS Cloud9 作为开发环境。

概述
我们将从设置 AWS Cloud9 环境开始,初始化一个 CDK 项目,编写一个简单的 Lambda 函数,并使用 CDK 命令将其部署到 AWS 云上。整个过程将展示基础设施即代码的核心工作流。
环境准备与 CDK 初始化
首先,我们位于 AWS Cloud9 环境中,这是一个非常适合使用 CDK 的工作环境。
第一步是运行官方文档中的命令,以确认我们安装了正确版本的 CDK。
cdk --version
确认版本无误后,接下来我们将参考一个官方的 AWS 研讨会内容来初始化项目结构。我们将复制相关命令来创建一个工作目录。


mkdir cdk-workshop && cd cdk-workshop
进入目录后,我们将创建一个示例 CDK 应用程序。
cdk init sample-app --language python
现在,我们已经生成了示例应用。根据终端提示,我们需要先创建一个 Python 虚拟环境并激活它。
python3 -m venv .venv
source .venv/bin/activate
激活虚拟环境后,下一步是安装项目 requirements.txt 文件中列出的所有依赖包。让我们先查看一下这个文件的内容。
requirements.txt 文件包含了运行 CDK Python 项目所需的核心库。
pip install -r requirements.txt
这些是关键的初始步骤。安装完成后,我们就可以运行其他 CDK 命令了。
验证 CDK 与创建 Lambda 函数
安装顺利结束后,我们可以通过输入 cdk ls 命令来验证 CDK 是否正常工作。

cdk ls
如果命令成功运行并列出栈(Stack)的信息,则说明 CDK 已准备就绪。
接下来,我们将回到官方文档,创建一个 Lambda 函数。文档要求我们在 cdk-workshop 目录下创建一个名为 lambda 的文件夹,并在其中创建一个 Python 文件。

mkdir lambda
touch lambda/hello.py
然后,我们将简单的 Lambda 函数代码粘贴到 hello.py 文件中。在 Python 中,Lambda 函数就是接收一个 event 参数的普通函数,它将在 AWS 环境中运行。
lambda/hello.py 文件内容:
def handler(event, context):
return {
'statusCode': 200,
'body': 'Hello from Lambda!'
}



集成 Lambda 到 CDK 栈
下一步是将 Lambda 函数集成到我们的 CDK 基础设施代码中。我们需要安装 AWS Lambda 的构造(Construct)库。一种方法是在项目的基础设施代码文件中直接引入。
在我们的项目中,基础设施代码位于 cdk_workshop/cdk_workshop_stack.py 文件中。我们将打开这个文件,用新的代码替换其内容,以部署我们刚刚创建的 Lambda 函数。
cdk_workshop/cdk_workshop_stack.py 文件更新后内容:
from aws_cdk import (
aws_lambda as _lambda,
core
)
class CdkWorkshopStack(core.Stack):
def __init__(self, scope: core.Construct, construct_id: str, **kwargs) -> None:
super().__init__(scope, construct_id, **kwargs)
# 定义 Lambda 函数资源
my_lambda = _lambda.Function(
self, 'HelloHandler',
runtime=_lambda.Runtime.PYTHON_3_8,
code=_lambda.Code.from_asset('lambda'),
handler='hello.handler',
)
更新栈文件后,我们可以运行 cdk diff 命令来查看本地代码与云端配置之间的差异。
cdk diff
由于这是我们第一次部署,应该会显示许多即将创建的变更。确认无误后,就可以进行部署了。

部署与测试
现在,我们使用 cdk deploy 命令将基础设施部署到 AWS。
cdk deploy
系统可能会提示需要先运行 cdk bootstrap 来初始化部署环境。这在首次使用 CDK 时很常见。
cdk bootstrap
在 Cloud9 环境中进行此操作非常方便,因为它通常已具备执行这些操作所需的角色权限。部署过程大约需要一分钟。
部署完成后,我们可以打开 AWS Lambda 控制台。在控制台中,使用“最后修改时间”过滤器,应该能看到我们刚创建的 Lambda 函数。
为了测试函数,我们可以在控制台中创建一个测试事件。根据我们的代码,Lambda 函数期望事件中包含 path 字段。因此,我们可以配置一个简单的测试事件。
测试事件示例:
{
"path": "hello"
}
保存测试事件后,点击“测试”。如果配置正确,函数将执行并返回成功的响应,而不会出现堆栈跟踪错误。
总结

本节课中,我们一起学习了使用 AWS CDK 和 Python 部署基础设施的基本流程。我们从设置 Cloud9 环境和初始化 CDK 项目开始,然后创建了一个简单的 Lambda 函数,并将其集成到 CDK 栈中。最后,我们通过 cdk diff 和 cdk deploy 命令完成了对 AWS 资源的部署和测试。这个流程展示了如何通过代码来定义、管理和更新云资源,是基础设施即代码的核心实践。
059:持续流水线介绍 🚀
在本节课中,我们将学习如何为软件开发构建持续流水线,即持续交付流水线。我们将首先理解持续交付的概念及其解决的问题,然后着手开发能够自动部署软件应用的流水线。
上一节我们介绍了课程的整体目标,本节中我们来看看本课涉及的一些核心术语和概念。
以下是本课将用到的一些关键技术:
- Flask:这是一个用 Python 编写的微服务 Web 框架。它是一个常用且流行的框架,用于构建微服务。
- Hugo:这是一种用 Go 语言构建的静态网站生成技术。它因生成 HTML 文件等静态资源的速度极快而非常流行。
- AWS CodePipeline:这是一个集成在 AWS 平台中的持续集成与持续交付系统。我们将在本课中使用它来部署一个 Hugo 网站。
接下来,我们探讨一下静态网站的概念。
静态网站是一种无服务器网站,其资源被生成并放置到一个可以在全球范围内访问的位置。因此,静态网站是一项非常流行的云原生技术。


本节课中我们一起学习了持续交付流水线的基本概念,并认识了构建此类流水线所需的关键工具与技术,包括 Flask、Hugo 和 AWS CodePipeline。我们还了解了静态网站作为云原生应用的特点。
060:持续交付概览


在本节课中,我们将要学习持续交付的核心概念。我们将通过一个真实案例来理解它是什么,以及为什么它在现代软件工程中至关重要。
什么是现实世界中的持续交付?
为了阐明持续交付的概念,我将分享我职业生涯中的几个故事。
其中一个故事发生在我任职于一家电影制片厂期间。这是一家由迪士尼资助的制片厂,当时我们面临着严重的交付问题。我们认为,如果无法解决技术问题,公司甚至可能倒闭。
我们如何实施持续交付
我们采取的措施之一是创建一个自动化流程。以下是该流程的核心步骤:
首先,我们建立了一个自动化流程,每当源代码被提交到版本控制系统时,就会自动触发检查。
其次,我们设置了一个包含数据库预发布版本的环境,所有变更都会首先在这个环境中进行验证。
持续交付的本质
一旦我们建立了这个自动化流程,我们就能将其应用到生产环境中,执行相同的步骤。
本质上,持续交付是一系列质量控制关卡的集合。通过这些关卡,你可以持续地改进产品。
我们正是这样做的。我们逐步推进,每天可能进行一两次小更新,持续地让生产环境中的产品变得更好一点。
持续改进的理念
这种“持续地变得更好一点”的理念被称为 Kaizen。这是一个源自日本汽车工业的持续改进过程。
所以,持续交付听起来很复杂,但实际上是许多人已经在做的事情:只是比你前一天做得更好一点。
不实施持续交付的后果
另一方面,如果你不实施持续交付,你实际上是在持续地让事情变得更糟。
如果没有一个自动化的流程来改进事物,那么参与其中的人虽然在做事情,但可能做得不好,并且会逐步地让事情变得越来越糟。
因此,持续交付是一种系统性的方法,旨在持续地让你的源代码控制变得更好。
持续交付的必要性
在现代软件工程基础设施中,这并非一个可选项。你必须进行持续交付,因为你要选择是持续地改进事物,还是持续地让事情恶化。
本节课中,我们一起学习了持续交付的基本概念。我们通过一个案例了解到,它是一套通过自动化质量关卡来持续改进软件的系统方法。其核心是 Kaizen 理念,即每日进行微小但持续的改进。我们认识到,在现代软件开发中,实施持续交付是必要的,因为它能系统性地提升质量,避免因手动、低效的操作而导致问题累积和恶化。
061:持续交付深度解析 🚀
在本节课中,我们将深入探讨持续交付的核心概念、解决的问题以及其具体的工作流程。我们将了解如何通过自动化实现持续改进,并确保软件始终处于可部署状态。
概述
持续交付是一种软件开发实践,旨在通过自动化流程,确保代码变更能够快速、可靠地发布到生产环境。它解决了手动部署过程中的低效和错误问题,实现了真正的持续改进。
持续交付解决的问题
一个可能浮现的问题是:我们为什么要实施持续交付?它解决了什么问题?本质上,它解决的是“改善”问题。我之前提到的“改善”是一个意味着持续改进的概念。为了持续改进你所做的事情并使其变得更好,你必须实现自动化。为了持续改进,你必须有一套质量控制措施。因此,你需要自动测试代码,需要一个幂等的或能够反复部署的基础设施,并且部署过程本身也必须是自动化的,以便你能将其部署到任何需要的环境中。
公式:持续改进 = 自动化 + 质量控制
持续交付的工作流程
在实践中,其工作方式如下:开发人员忙于工作,并将代码推送到源代码控制中。在这里,根据你将代码推送到哪个分支,它会触发构建服务器的变更。
以下是该流程的关键步骤:
- 代码提交与触发:开发人员将代码推送到特定的分支(如功能分支)。
- 自动化构建与测试:构建服务器被触发,执行代码测试以确保没有错误,并可能进行代码链接。
- 基础设施即代码:构建服务器使用 Terraform、Pulumi、CloudFormation 等工具查看并配置基础设施。
- 环境准备:云环境被配置完成后,环境就准备就绪,可以测试你的变更。
# 示例:一个简化的CI/CD流水线触发器配置
trigger:
branches:
include:
- main
- staging
向生产环境推进
当变更接近生产环境时,流程会进一步推进。例如,你可以将主分支合并到预发布分支。这同样会触发一个部署流程:测试代码、链接代码、执行基础设施即代码。如果有新的变更,比如需要配置一个更强大的数据库,系统就会执行此操作。
在预发布环境中,你可以进行某种负载测试。这里是你进行性能测试、确定你的应用能否承受10万用户的地方。完成这些后,你可以再次从预发布分支合并到生产分支,然后自动将这些变更部署给你的用户。
持续交付的本质

因此,持续交付的过程在某种程度上非常直观:你总是在让事情变得更好。这个过程是完全自动化的,完全不需要人工干预。唯一需要人工参与的地方是,最初由人将变更提交到源代码控制仓库。在此之后,就不再需要人工去按按钮或在其他地方进行修改了。
所以,这实际上是为持续交付建立质量控制清单的好方法。如果这个过程完全与人工分离,那么你就实现了持续交付。如果在这些步骤中的任何一步需要人工参与,例如需要运维人员配置机器,或者QA人员需要调整某些设置或配置,那么你还没有实现持续交付。
核心定义:持续交付意味着你的代码始终处于持续改进且可部署的状态。这并不一定意味着直接部署到生产环境,但你可以选择这样做。使用持续交付的真正优势在于,这种自动化方式能够持续改进,并以快速的方式将新变更交付给客户。
总结

本节课我们一起学习了持续交付的核心价值。我们了解到,持续交付通过将代码构建、测试和部署过程全面自动化,解决了手动流程的低效问题,实现了软件开发中的“持续改善”。关键在于确保从代码提交到潜在的生产部署,整个流程无需人工干预,从而保证软件始终处于高质量、可随时发布的状态。这是现代云原生应用快速、可靠迭代的基石。
062:使用Azure持续部署Flask机器学习应用 🚀
在本节课中,我们将学习如何使用Azure DevOps、Azure应用服务和Flask机器学习应用,完成一个端到端的持续交付流程。我们将从查看现有项目开始,通过修改代码触发自动部署,并最终验证部署结果。
概述
我们将演示一个完整的持续交付过程。首先,我们会查看一个已配置好的Azure DevOps项目及其关联的Flask机器学习应用。接着,我们将对应用代码进行一个小修改,观察Azure Pipelines如何自动检测到代码变更、触发构建和部署流程。最后,我们将验证修改后的应用是否成功上线并正常运行。
访问Azure DevOps项目
首先,我们进入Azure DevOps的组织界面。我选择了一个名为 flaskml-deploy 的预设项目。

接下来,查看“流水线”部分。可以看到最近运行过的应用记录。点击记录中的链接,可以跳转到关联的GitHub仓库。这证实了该应用已与Azure流水线服务成功连接。

验证应用运行状态
为了确认应用当前正在运行,我们可以打开Azure Cloud Shell。在Cloud Shell中,找到该应用的名称,并在新标签页中打开其URL。
可以看到,该服务正在运行,并且提供了一个预测API接口。我们可以通过一个名为 make_predict_azure_app.py 的脚本文件来调用这个API,执行机器学习预测。
运行该脚本,验证服务是否能正确处理请求。结果显示成功,证明服务运行正常。
触发持续交付
上一节我们验证了应用运行正常,本节我们来看看如何进行持续交付,即如何通过修改代码来触发自动部署。
由于Azure Pipelines已配置为自动监听代码仓库的变更,我们可以轻松地修改代码来验证这一流程。
具体操作是,进入GitHub仓库的应用代码目录,找到显示 psyt learn prediction home from Azure pipelines 的语句。我们将其修改为 continuous delivery,并添加一个额外的说明语句。


代码修改并提交后,将会触发一次新的部署事件。
观察部署流程
现在,我们回到Azure DevOps的流水线界面。在流水线列表中,应该能看到一个新的发布任务已被触发并进入队列。
点击该任务,可以逐步观察部署过程。首先,系统会构建应用程序。构建任务通常需要几分钟。
构建完成后,系统会自动部署应用程序。在部署日志中,可以找到验证部署是否成功的文件记录。



验证部署结果

部署完成后,我们需要验证修改是否已生效。在部署任务的日志中,找到“部署Web应用”的步骤,其中包含“下载构件”、“使用Python版本”等操作。
点击日志中的应用程序URL图标,在新标签页或终端中打开该URL。
以下是验证步骤:
- 访问应用的主页URL。
- 检查页面内容是否已更新为我们修改后的语句(即包含“continuous delivery”)。
- 再次运行预测API脚本,确保核心功能未受影响。


此外,也可以回到Azure Cloud Shell环境,进行最终的验证。但总而言之,我们已经成功地通过Azure Pipelines完成了端到端的持续交付,并验证了代码变更已生效。





总结

本节课中,我们一起学习了使用Azure平台实施持续交付的完整流程。我们从访问配置好的Azure DevOps项目开始,验证了Flask应用的初始运行状态。随后,我们通过修改GitHub仓库中的代码,触发了Azure Pipelines的自动构建和部署流程。最后,我们观察了部署过程,并成功验证了代码变更已应用到线上服务中。这个过程展示了如何利用Azure工具链实现高效、自动化的应用更新。
063:使用Azure构建含代码检查的持续交付流水线
在本节课中,我们将学习如何通过添加质量控制环节来改进Azure的持续交付流程。我们将重点关注在Python项目中集成代码检查工具。
概述
持续交付流程可以确保代码的快速、可靠部署。为了进一步提升代码质量,我们可以在部署流程中加入自动化的质量控制环节。本节将演示如何在Azure Pipelines中添加代码检查步骤。
添加代码检查环节
上一节我们介绍了基础的Azure持续交付流程。本节中我们来看看如何集成代码检查工具。
Azure官方文档提供了两种在Python项目中添加质量控制环节的简单方法:一种是代码检查,另一种是测试。我们当前将专注于代码检查部分。
以下是添加代码检查环节的步骤:
- 访问Azure官方文档,找到关于添加脚本步骤的示例。
- 在YAML配置文件的合适位置,添加一个执行代码检查的脚本步骤。

编辑Azure Pipelines配置文件
现在,我们回到Azure Cloud Shell环境,开始编辑配置文件。

在Cloud Shell中,选择编辑器图标,进入项目目录。

在项目中,找到并选择azure-pipelines.yml文件进行编辑。

向下滚动,找到一个合适的位置来插入新的步骤。一个理想的位置是在虚拟环境激活和依赖安装完成之后。
在该位置,我们可以添加一个新的步骤。我们将粘贴从文档中复制的脚本模板,但会对其进行一些调整。
自定义代码检查命令
为了简化操作并保持一致性,我们选择复现本地开发环境中使用的命令。使用Makefile可以很好地实现这一点。
在Shell中,运行make lint命令,可以看到它执行了一个带有特定选项的pylint命令。
我们希望在这个Azure环境中复现同样的行为。因此,我们将复制这个命令的语法,并将其放入配置文件的脚本部分。
实际上,我们可以直接使用make install和make lint这两个命令,这能极大地简化配置步骤。
同时,我们还需要为这个构建步骤设置一个清晰的显示名称,以便在流水线日志中轻松识别。
配置完成后,代码检查步骤的YAML配置大致如下:
- script: |
make install
make lint
displayName: 'Run Pylint Code Analysis'
提交更改并触发构建
编辑完成后,在终端中运行git status查看更改,然后提交这次修改。


提交更改会触发一次新的部署流程。我们可以点击提供的链接,实时观察构建任务的执行情况。
验证执行结果
进入构建任务详情页面,我们可以看到流水线正在执行。新添加的“Run Pylint Code Analysis”步骤会运行,并对代码进行检查。


这个步骤确保了代码检查环节被成功集成到部署流程中。它提供了一个强大的质量控制关口,帮助我们在部署前发现代码中的潜在问题,从而避免将有问题的代码部署到生产环境。
总结
本节课中我们一起学习了如何增强Azure持续交付流程。我们通过编辑azure-pipelines.yml配置文件,添加了一个执行pylint代码检查的脚本步骤。这个质量控制环节能自动运行,确保只有符合代码规范的更改才能进入后续的部署阶段,从而有效提升了代码质量和部署的可靠性。
064:为Hugo设置AWS Cloud9和GitHub初始环境 🚀
在本节课中,我们将学习如何为构建Hugo静态网站设置初始的开发环境。我们将使用AWS Cloud9作为云端集成开发环境(IDE),并将其与GitHub仓库连接,以便进行版本控制和协作。整个过程将展示如何结合基础设施即服务(IaaS)和无服务器(Serverless)架构来部署一个高可用的网站。

使用AWS Cloud9创建开发环境
首先,我们开始设置云端开发环境。使用AWS Cloud9是一个良好的实践模式,因为它提供了一个预配置的、可直接编码的环境。
以下是创建Cloud9环境的步骤:
- 在AWS Cloud9控制台中,选择“创建环境”。
- 将环境命名为
HugoForDuke107。 - 在描述中注明:“这是一个用于构建Hugo网站的临时环境”。
- 保持所有其他配置为默认值,以简化设置。
- 点击“创建”按钮,启动环境。
在环境创建的同时,我们可以并行进行下一步操作。
在GitHub上创建代码仓库
上一节我们启动了Cloud9环境,本节中我们来看看如何准备代码存储库。我们需要在GitHub上创建一个新的仓库,用于存放Hugo网站的源代码。
以下是创建GitHub仓库的步骤:

- 登录GitHub,点击“New repository”按钮。
- 将仓库命名为
HugoForDuke17。 - 在描述中填写:“Sample Hugo website for Duke class”。
- 选择“添加README文件”选项。
- 在“.gitignore”模板选择器中,暂时选择一个模板(例如“Node”)。我们稍后会回来修改这个文件,这是一个微妙但重要的细节。
- 点击“创建仓库”按钮。
至此,我们创建了一个空的代码仓库。现在,让我们回到正在启动的Cloud9环境。
理解背后的架构:IaaS与Serverless

在继续配置密钥之前,有必要简要了解我们将要使用的架构。虽然本教程以实践操作为主,但理解核心概念很重要。
我们将使用基础设施即服务(IaaS)和无服务器(Serverless) 架构来部署网站。
- IaaS层:我们将使用Amazon S3(一种对象存储服务)来托管Hugo生成的静态网站文件。S3提供了
99.999999999%(11个9)的持久性,这意味着数据几乎永远不会丢失,年故障时间仅为毫秒级。 - Serverless层:在IaaS之上,AWS提供了无服务器服务(如CloudFront、Lambda@Edge),使我们能够托管全球可扩展的网站。这意味着即使像《华尔街日报》或《纽约时报》这样规模的网站,也能通过此架构支撑。
本质上,无服务器是在基础设施即服务之上构建的更高层抽象,但本项目的核心是S3存储桶。
配置SSH密钥连接GitHub
现在,我们的Cloud9环境应该已经准备就绪。接下来,我们需要创建SSH密钥对,以便Cloud9环境能够安全地与GitHub仓库通信。
请注意:如果这是你第一次创建Cloud9环境,才需要执行此步骤。如果已有环境,可以跳过。
以下是生成并配置SSH密钥的步骤:
- 在Cloud9环境的终端中,运行以下命令生成密钥:
ssh-keygen -t rsa - 在提示保存位置和输入密码时,直接按五次回车键,接受所有默认值(空密码)。
- 生成后,使用以下命令显示公钥内容:
cat ~/.ssh/id_rsa.pub - 复制终端中显示的整个公钥字符串。这是可以公开分享的部分。
- 打开GitHub,点击右上角头像,进入“Settings”。
- 在侧边栏选择“SSH and GPG keys”。
- 点击“New SSH key”,将标题命名为“HugoKeys”,并将复制的公钥粘贴到“Key”字段中。
- 点击“Add SSH key”确认添加。
克隆GitHub仓库到本地环境
密钥配置完成后,我们就可以将之前在GitHub上创建的仓库克隆到Cloud9环境中,开始开发工作。
以下是克隆仓库的步骤:
- 在GitHub上,进入你刚创建的
HugoForDuke17仓库页面。 - 点击绿色的“Code”按钮,选择“SSH”选项卡,并复制提供的SSH链接(例如
git@github.com:username/HugoForDuke17.git)。 - 回到Cloud9环境的终端,使用
git clone命令和复制的链接来克隆仓库:git clone git@github.com:username/HugoForDuke17.git
这种从零开始设置开发环境并连接版本控制系统的流程,在你开始新项目或加入新团队时非常常见,是一个推荐的标准实践。

本节课中我们一起学习了如何为Hugo项目搭建初始的云端开发环境。我们完成了使用AWS Cloud9创建IDE、在GitHub建立代码仓库、理解IaaS与Serverless的基础架构概念、配置SSH密钥认证以及将远程仓库克隆到本地环境这一系列步骤。这为后续实际构建和部署Hugo网站奠定了坚实的基础。
065:在AWS Cloud9中构建Hugo目录

概述
在本节课中,我们将学习如何在AWS Cloud9环境中下载、安装和配置Hugo静态网站生成器,并创建一个基础的Hugo项目。我们将涵盖从获取Hugo二进制文件到生成可预览的静态网站的全过程。
下载Hugo二进制文件
上一节我们介绍了课程背景,本节中我们来看看如何获取Hugo工具。首先,我们需要从GitHub下载Hugo的最新版本二进制文件。
以下是下载步骤:
- 访问Hugo的GitHub发布页面。
- 找到适用于Linux 64位系统的
.tar.gz压缩包。 - 使用
wget命令下载该文件。wget是一个命令行下载工具,功能类似于在浏览器中点击下载链接。
执行下载命令:
wget [Hugo的tar.gz文件下载链接]
此命令会将文件下载到本地当前目录。
解压与安装Hugo
文件下载完成后,我们需要解压这个压缩包并将其安装到合适的位置。
.tar.gz 文件是Linux系统中常见的软件分发格式,它包含了一个经过压缩的文件夹。使用 tar 命令可以解压它。
执行解压命令:
tar -zxvf [下载的Hugo文件名].tar.gz
参数 -zxvf 表示:z 解压gzip压缩,x 解包,v 显示详细信息,f 指定文件名。
解压后,为了便于在任何位置使用Hugo命令,我们将其移动到用户主目录下的 ~/bin 文件夹中。这个目录通常包含在系统的PATH环境变量里。
创建目录并移动文件:
mkdir -p ~/bin
mv hugo ~/bin/
命令 mkdir -p 可以安全地创建目录,如果目录已存在则不会报错。
现在,我们可以验证安装是否成功:
which hugo
hugo version
如果返回了Hugo的路径和版本信息,说明安装成功。
创建Hugo网站项目
现在我们已经安装了Hugo,接下来可以创建一个新的网站项目。
使用 hugo new site 命令来生成项目脚手架:
hugo new site quickstart
此命令会创建一个名为 quickstart 的目录,其中包含Hugo网站的基本结构文件。
为了将项目纳入版本控制(例如Git),我们需要将这个新创建的项目内容移动到我们的源代码仓库根目录下。操作步骤如下:
- 进入
quickstart目录。 - 将其所有内容复制到上一级目录(即仓库根目录)。
- 删除空的
quickstart目录。
具体命令如下:
cd quickstart
cp -r * ../hugo-for-duke/
cd ..
rm -rf quickstart
现在,使用 git status 命令可以看到新的文件已被Git识别,但尚未被跟踪。
配置Hugo主题与项目
一个Hugo网站的核心配置位于 config.toml 文件中。我们需要配置网站的基本信息,特别是主题。
首先,为项目添加一个主题。我们可以使用Git子模块功能来链接一个主题仓库:
git submodule add [主题Git仓库地址] themes/[主题名]
接着,编辑 config.toml 文件,指定使用的主题:
baseURL = ‘http://example.org/‘
languageCode = ‘en-us’
title = ‘My New Hugo Site’
theme = “[主题名]”
配置完成后,将这些更改添加到Git暂存区:
git add config.toml
管理Git忽略文件
在开发过程中,Hugo会生成一个 public/ 目录来存放最终构建的HTML等静态资源。我们不应该将这些自动生成的文件提交到版本库。
因此,我们需要创建一个 .gitignore 文件来忽略它们:
echo “public/” > .gitignore
git add .gitignore
这样,每次运行Hugo生成站点时,public/ 目录下的文件都不会被Git跟踪。
创建内容与本地预览
现在,我们可以开始为网站创建内容了。使用Hugo命令创建一篇新文章:
hugo new posts/my-first-post.md
此命令会在 content/posts/ 目录下生成一个Markdown文件。你可以用任何文本编辑器打开它并撰写内容。
为了在本地预览网站,我们需要启动Hugo的开发服务器。但在AWS Cloud9中,需要先配置安全组以开放访问端口。
以下是配置步骤:
- 在AWS管理控制台,找到你的EC2实例。
- 进入该实例关联的安全组。
- 编辑“入站规则”,添加一条新规则:
- 类型:自定义TCP
- 端口范围:8080
- 来源:0.0.0.0/0 (允许所有IP访问,仅用于测试)
- 描述:Hugo预览
配置完成后,回到Cloud9终端,启动Hugo服务器并绑定到所有网络接口:
hugo server -D --bind 0.0.0.0 --port 8080
参数 -D 表示包含草稿文章,--bind 0.0.0.0 允许外部访问,--port 8080 指定端口。
现在,你可以在浏览器中访问 http://<你的EC2实例公有IP>:8080 来预览网站了。
生成静态站点文件
除了实时预览,Hugo的主要功能是生成静态文件。这些文件可以部署到任何Web服务器或云存储服务(如AWS S3)上。
生成静态站点的命令非常简单:
hugo
运行后,Hugo会快速地将所有文章和模板渲染成HTML文件,并输出到 public/ 目录中。这个过程通常非常快,适合构建大型静态网站。

总结
本节课中我们一起学习了在AWS Cloud9环境中搭建Hugo静态网站生成器的完整流程。我们从下载和解压Hugo二进制文件开始,然后创建了一个新的Hugo项目,并为其配置了主题和Git忽略规则。最后,我们学习了如何创建内容、在本地预览网站以及生成最终的静态站点文件。这些静态文件为后续部署到云存储服务(如S3)以实现无服务器架构奠定了基础。
066:将Hugo数据复制到AWS S3存储桶并配置静态网站托管 🚀

在本节课中,我们将学习如何将本地生成的Hugo网站文件上传到AWS S3存储桶,并通过配置S3的静态网站托管功能,快速部署一个高可用性的网站。整个过程展示了无服务器架构的简便与强大。

上一节我们介绍了Hugo静态网站生成器的基础使用,本节中我们来看看如何将生成的网站文件部署到云端。
创建S3存储桶
首先,我们需要在AWS S3服务中创建一个新的存储桶来存放网站文件。

以下是创建存储桶的步骤:
- 快速导航到AWS管理控制台的S3服务页面。
- 点击“创建存储桶”按钮。
- 为存储桶命名,例如
hugo-duke。 - 连续点击“下一步”,使用默认配置,直至完成创建。
注意:AWS账户有存储桶数量限制。如果遇到“存储桶数量超出允许范围”的错误,需要先删除一些不再使用的旧存储桶以释放配额。
配置静态网站托管
存储桶创建成功后,下一步是启用其静态网站托管功能。这是将S3转变为网站服务器的关键步骤。
以下是配置静态网站托管的步骤:
- 进入新创建的存储桶。
- 切换到“属性”选项卡。
- 找到并点击“静态网站托管”选项。
- 选择“使用此存储桶托管网站”。
- 在“索引文档”字段中输入
index.html。 - (可选)在“错误文档”字段中输入
error.html。 - 点击“保存”按钮。
此功能是一项无服务器技术,只需点击按钮即可获得一个具备高可靠性的网站托管环境。
设置存储桶策略
为了使公众能够访问我们托管的网站,必须配置存储桶策略,允许公开读取权限。
以下是设置存储桶策略的步骤:
- 切换到存储桶的“权限”选项卡。
- 找到“存储桶策略”部分并点击“编辑”。
- 在策略编辑器中,输入一个允许公开读取访问的策略。策略结构如下:
{ "Version": "2012-10-17", "Statement": [ { "Sid": "PublicReadGetObject", "Effect": "Allow", "Principal": "*", "Action": "s3:GetObject", "Resource": "arn:aws:s3:::您的存储桶名称/*" } ] } - 将策略中的
您的存储桶名称替换为实际的存储桶名称(例如hugo-duke)。 - 点击“保存”策略。
注意:如果保存策略时遇到错误,提示“阻止公共访问设置”,需要先修改存储桶的“阻止公共访问”设置,暂时允许公共访问,完成策略配置后再根据安全需求进行调整。这是云平台持续增强安全性的常见做法。
上传网站文件

策略配置完成后,即可将本地的Hugo网站文件上传至存储桶。

以下是上传文件的步骤:
- 在本地计算机上,进入Hugo项目的
public目录,该目录包含了生成的所有静态网站文件。 - 可以选择将整个
public目录压缩并下载到本地以便上传。 - 回到AWS S3控制台,进入目标存储桶。
- 点击“上传”按钮,选择或拖拽
public目录下的所有文件。 - 连续点击“下一步”,使用默认设置,直至完成上传。
这个过程演示了部署一个网站的核心流程,本质上非常简单。


访问网站

所有文件上传完毕后,网站即部署完成。
以下是访问网站的方法:
- 再次进入存储桶的“属性”选项卡。
- 找到“静态网站托管”部分。
- 其中会显示一个以
http://<bucket-name>.s3-website-<region>.amazonaws.com格式生成的端点URL。 - 点击或复制该URL到浏览器中,即可访问刚刚部署的网站。


本节课中我们一起学习了如何利用AWS S3存储桶托管静态网站。通过创建存储桶、启用静态网站托管、配置访问策略以及上传文件,我们成功部署了一个具备专业规模、高可用性且几乎不会宕机的网站。这充分展示了云计算在简化基础设施部署方面的强大能力。
067:在AWS Cloud9中实现Hugo自动更新 🚀

在本节课中,我们将学习如何使用Hugo静态网站生成器,结合AWS Cloud9开发环境和一系列AWS服务,构建一个能够自动更新、全球可访问的网站。我们将通过一个完整的持续交付流程,实现从代码修改到网站自动部署的全自动化。
概述
Hugo是一个开源的静态网站生成器,它快速、易用且无需数据库。通过将其与AWS的云服务结合,我们可以创建一个低成本、高可用性且能自动部署的网站发布系统。本节将逐步指导您完成在AWS Cloud9中设置Hugo开发环境,并配置AWS CodeBuild实现持续交付的整个过程。
开发环境设置与本地工作流
上一节我们介绍了课程的目标和Hugo的优势,本节中我们来看看如何搭建基础的开发环境。首先,我们需要一个与最终生产环境一致的开发环境,AWS Cloud9是一个理想的选择。
以下是设置Cloud9环境的步骤:
- 登录AWS控制台,进入Cloud9服务。
- 点击“创建环境”,为其命名(例如“Hugo”)。
- 选择实例类型。为了获得更好的响应速度,可以选择配置较高的实例,例如拥有16GB内存和8个vCPU的实例。
- 平台选择“Amazon Linux 2”,因为后续的AWS CodeBuild也将使用此平台。
- 保留其他默认设置(如30分钟无操作超时),然后创建环境。
环境创建完成后,您将获得一个基于Bash的终端,并且已经配置了基于角色的权限,可以直接与AWS生态系统进行交互。
安装与配置Hugo
现在,我们已经在Cloud9中拥有了一个开发环境。接下来,我们需要在这个环境中安装Hugo并创建一个示例网站。
以下是安装Hugo的步骤:


- 访问Hugo GitHub发布页面,找到最新的64位Linux压缩包(
hugo_extended_*_Linux-64bit.tar.gz),复制其链接地址。 - 在Cloud9终端中,使用
wget命令下载该文件。wget [复制的链接地址] - 解压下载的压缩包。
tar -xzf hugo_extended_*_Linux-64bit.tar.gz - 将可执行文件复制到系统路径(如
/usr/local/bin)。sudo cp hugo /usr/local/bin/ - 验证安装是否成功。
hugo version

安装完成后,我们可以按照Hugo官方快速入门指南创建一个新站点。

以下是创建Hugo站点的步骤:


- 使用
hugo new site命令创建一个新站点。hugo new site quickstart cd quickstart - 初始化Git仓库。
git init - 添加一个主题作为Git子模块。这里以
ananke主题为例。git submodule add https://github.com/theNewDynamic/gohugo-theme-ananke.git themes/ananke - 将主题配置写入站点配置文件。
echo 'theme = "ananke"' >> config.toml - 创建第一篇非草稿文章。
编辑hugo new posts/my-first-post.mdcontent/posts/my-first-post.md文件,将draft: true改为draft: false,并添加一些内容,例如“Hello World”。

本地测试与远程访问

我们已经创建了一个基本的Hugo站点。为了验证其能否正常运行,并允许从外部访问进行测试,我们需要启动本地服务器并配置安全组。



首先,在Cloud9终端中启动Hugo服务器。默认情况下,Hugo只绑定到本地回环地址(127.0.0.1),为了能从外部IP访问,需要指定绑定到所有网络接口。



hugo server -D --bind=0.0.0.0 --baseURL=http://[您的Cloud9实例公共IP]:1313
命令中的 -D 表示包含草稿文章,--bind=0.0.0.0 允许外部访问,--baseURL 用于设置正确的基础URL。

接下来,需要配置EC2实例的安全组以开放1313端口。

以下是配置安全组的步骤:


- 在AWS控制台进入EC2服务,找到您的Cloud9环境所使用的EC2实例。
- 点击该实例,在下方描述标签页中找到“安全组”并点击其链接。
- 在安全组页面,点击“编辑入站规则”。
- 添加一条新规则:类型选择“自定义TCP”,端口范围填写“1313”,来源选择“0.0.0.0/0”(允许任何IP访问)。
- 保存规则。


配置完成后,您就可以通过浏览器访问 http://[您的Cloud9实例公共IP]:1313 来查看您的Hugo网站了。在Cloud9中修改文章内容并保存,Hugo会自动重新构建,刷新浏览器即可看到更新,这演示了高效的本地开发工作流。
配置自动化持续交付流程
上一节我们完成了本地开发和测试,本节中我们来看看如何实现自动化部署,让每次代码提交都能自动更新生产环境网站。这需要用到AWS CodeBuild、S3和CloudFront等服务。
整个流程的核心是一个名为 buildspec.yml 的配置文件,它定义了CodeBuild在每次触发时需要执行的步骤。
以下是一个典型的 buildspec.yml 文件内容:
version: 0.2
phases:
install:
commands:
- wget https://github.com/gohugoio/hugo/releases/download/v0.88.1/hugo_extended_0.88.1_Linux-64bit.tar.gz
- tar -xzf hugo_extended_0.88.1_Linux-64bit.tar.gz
- sudo cp hugo /usr/local/bin/
build:
commands:
- hugo
post_build:
commands:
- aws s3 sync ./public s3://YOUR-BUCKET-NAME --delete
- aws s3 cp s3://YOUR-BUCKET-NAME s3://YOUR-BUCKET-NAME --recursive --metadata-directive REPLACE --cache-control max-age=31536000
- aws cloudfront create-invalidation --distribution-id YOUR-DISTRIBUTION-ID --paths "/*"

这个配置文件主要做了三件事:
- 安装阶段:下载并安装指定版本的Hugo。
- 构建阶段:运行
hugo命令,将Markdown等内容生成静态HTML文件到./public目录。 - 构建后阶段:
- 使用
aws s3 sync将./public目录下的文件同步到指定的S3存储桶。 - 使用
aws s3 cp递归地更新S3中所有文件的缓存控制头,设置较长的有效期。 - 使用
aws cloudfront create-invalidation命令使CloudFront CDN的缓存失效,确保用户立即看到新内容。
- 使用

要使用这个流程,您需要提前完成以下AWS资源配置:
- S3存储桶:创建一个存储桶并启用“静态网站托管”功能。同时,需要配置存储桶策略,允许公开读取对象。
- IAM角色:创建一个供CodeBuild使用的服务角色,该角色必须拥有向上述S3存储桶写入数据以及使特定CloudFront分发缓存失效的权限。
- CloudFront分发(可选但推荐):创建一个分发,将S3存储桶作为源站。这可以加速全球访问并启用HTTPS。
- Route 53(可选):如果您有自己的域名,可以在此配置,将域名指向CloudFront分发或S3网站端点。
最后,在AWS CodeBuild控制台创建一个新的构建项目,将其源代码指向您的GitHub仓库,选择“Amazon Linux 2”托管镜像,并指定使用我们创建的IAM角色和 buildspec.yml 文件。这样,每次向GitHub仓库推送代码时,CodeBuild都会自动执行构建和部署流程。

总结
本节课中我们一起学习了如何利用Hugo和AWS云服务搭建一个完整的持续交付静态网站系统。我们从在AWS Cloud9中设置开发环境开始,逐步完成了Hugo的安装、本地站点的创建与测试。接着,我们深入探讨了如何通过配置AWS CodeBuild、S3、CloudFront和IAM,实现从代码提交到网站全球自动部署的自动化流水线。

这套方案的优势在于:成本低廉(主要费用为S3存储和CloudFront流量),高度可扩展(能承载如纽约时报级别的流量),安全性高(静态文件只读),并且完全自动化,让开发者可以专注于内容创作。您可以使用这个系统来传播真实、有价值的信息,正如课程初衷所期望的那样。
068:讲师介绍
在本节课中,我们将认识本课程的讲师,了解他的背景、专业领域以及丰富的行业与教学经验。
讲师背景
大家好,我是诺亚·吉夫特,我将担任本课程的讲师。
我在世界多所顶尖大学任教,包括杜克大学的数据科学项目、西北大学的研究生数据科学项目。我也曾在加州大学伯克利分校和戴维斯分校授课。
著作与行业经验
上一节我们介绍了讲师的学术背景,本节中我们来看看他的著作与行业实践。
我的著书经验包括一本名为 Python for DevOps 的畅销书,以及 Pragmatic AI、Cloud Computing for Data 和 Practical MLOps。这些书籍中的许多已被翻译成中文。
我的行业经验涉及游戏、电影、软件即服务和机器学习工程领域。我曾多次在预算内按时交付产品。
专业理念与成就
了解了讲师的实践经验后,我们来看看他秉持的专业理念和取得的成就。
如果你在过去20年里真正涉足软件行业,你就会知道自动化是当前的一个关键重点,而这正是我职业生涯中投入大量精力的领域。
我认为,如果流程没有自动化,它就是有缺陷的。我的大量经验包括构建服务器、进行测试、建立安全机制,以确保公司能够按时交付产品。
我近些年获得的一些荣誉包括“AWS机器学习英雄”称号。我也曾参与AWS、GCP和Azure的教育机构合作项目,并为包括Udacity、Coursera、O‘Reilly和Datacamp在内的顶级内容提供商制作了许多课程。同时,我也是Python软件基金会的成员。
因此,你们将由经验丰富的讲师带领学习。我期待与你们分享我的知识。让我们开始吧。
本节课中我们一起学习了本课程讲师诺亚·吉夫特的背景。他拥有顶尖大学的丰富教学经验、多本畅销技术著作的撰写经历,以及在游戏、影视、SaaS和机器学习工程领域的深厚行业实践。他专注于自动化,并获得了包括“AWS机器学习英雄”在内的多项荣誉。
069:课程介绍 🚀

在本课程中,我们将学习构建复杂应用所需的云计算基础模块。为了更深入地了解这些模块,我们将探讨虚拟化与容器等技术。这些技术能帮助我们启动按需付费的虚拟机实例,或使用Docker格式的容器来封装应用并将其部署到Kubernetes。
上一节我们概述了课程内容,本节中我们来看看另一个核心概念:微服务。微服务是DevOps最佳实践的关键组成部分。本质上,一个微服务是一个映射到特定接口(例如Web接口)的独立功能,它专注于做好一件事。我们将学习如何构建高效、简洁的微服务。
此外,我们还将深入探讨云的操作特性,并介绍一些运维最佳实践,包括监控、日志记录等。确保在构建应用时,你也能拥有一个类似飞机仪表盘的监控面板,实时显示运行状态,如当前高度或航向。
现在,我们来谈谈本课程的学习目标。
以下是本课程的主要学习目标:
- 评估虚拟化与容器技术:你将能够根据现有解决方案组合的具体情况,做出合适的技术选择。例如,遗留应用可能更适合使用虚拟机,而数据科学项目则可能更适合容器。具体选择取决于上下文,我们将深入探讨这些不同的场景细节。
- 利用微服务开发高效技术方案:如前所述,微服务是DevOps最佳实践的一部分。我们将深入探讨如何通过构建有效的微服务来简化应用,从而提高生产力,并构建出高效、高可用的应用。
- 评估有效的技术运维策略:你应该对应用进行负载测试吗?应该如何设置告警和监控?我们将讨论不同的策略,以确保你部署的代码不仅能有效运行,团队中的其他成员也能协助维护。


本节课中,我们一起学习了构建大规模云计算解决方案的课程概述与核心学习目标,包括虚拟化、容器、微服务以及云运维等关键模块。在接下来的课程中,我们将逐一深入这些主题。
070:课程先修要求 📋

在本节课中,我们将介绍学习本课程所需的先修知识与技能,并阐述学习本课程的价值与意义。
先修知识要求
为了能更好地跟上课程进度并理解核心概念,建议学员在开始前具备以下基础。
以下是四项关键的先修知识:
- 中级Python知识:这意味着你需要具备构建语句、理解变量以及编写小型脚本的能力。
- Linux基础知识:包括在文件系统中导航、运行Shell命令的能力,这将非常有帮助。
- IT基础设施知识:这是一个关键要求,意味着你需要理解什么是虚拟机、数据库,并对IT基础设施有基本的了解。
- 理解JSON与YAML文件格式:你需要了解这两种格式及其包含的内容。这实际上非常容易掌握,但核心概念在于,通过传递本质上等同于Python字典的JSON数据,或传递YAML数据,你将能够控制云生态系统。这是你将要做的大量工作,因此了解这些基础知识很重要。
为何学习本课程
在了解了先修要求后,我们来看看为什么这门课程值得你投入时间学习。
以下是学习本课程的几个关键原因:
- 数据科学需要云:大多数数据科学项目都需要云计算。很多时候你会在自己的笔记本电脑上进行小型项目,但笔记本电脑不具备近乎无限的计算和存储扩展能力,这就是为什么大多数数据科学真正需要云的原因。
- 巨大的就业机会:根据亚马逊网络服务的研究,云计算领域存在数十万个未填补的职位空缺。确实存在未满足的需求和人才危机,需要快速培训人才。
- 三大云平台认证的基础:本课程可以作为在全部三大云平台上获得认证的基础。你不仅可以后续获得AWS认证,还可以在首先学习本课程、打下基础后,决定向哪个方向深入,进而获得GCP或Azure认证。
- 学习构建可运行的系统:本课程一个重要的组成部分是,你将学习构建可工作的系统。这非常注重职业技能,你将学习如何从命令行工具到Web应用程序,再到完整可运行的机器学习模型,一步步构建系统。

本节课中,我们一起学习了开始本课程所需的先修技能,包括Python、Linux、IT基础架构和文件格式知识,并探讨了学习云计算在数据科学、职业发展和技能认证方面的重要价值。准备好这些基础,你将能更顺利地开启云计算之旅。
071:实验环境准备 🛠️

在本节课中,我们将学习如何为后续的课程实验准备免费的云平台环境。我们将介绍AWS、GCP和Azure三大主流云服务商提供的免费资源,并指导你如何获取和使用它们。
课程概述
本课程包含一系列动手实验,这些实验将在AWS、GCP和Azure云平台上进行。为了帮助你顺利完成所有实验,我们将利用各平台提供的免费套餐或教育优惠。无论你选择哪个平台,都可以在不产生费用的情况下完成本课程的全部内容。
实验平台与免费资源
以下是三个主要云平台的免费资源获取方式。
AWS 平台资源
上一节我们介绍了课程的整体实验需求,本节中我们来看看AWS平台的具体准备方案。
AWS提供免费的套餐服务。使用AWS免费套餐,你基本可以完成本课程所需的所有操作。此外,如果你是教育机构AWS Academy的成员,还可以访问许多免费的实验资源,这些资源不仅有助于课程学习,也能为你考取AWS认证做好准备。我个人教学也使用这些实验。
以下是AWS资源的获取途径:
- AWS免费套餐:适用于所有新用户,提供一定额度的免费服务。
- AWS Academy:面向教育机构成员,提供丰富的免费实验模块。
GCP 平台资源
了解了AWS的资源后,我们接下来看看GCP平台。
GCP平台提供非常慷慨的免费套餐。仅使用免费套餐,你就可以完成整个课程的所有作业。此外,你还可以访问可选的Quicklabs。如果你是学生,可以通过Google教育申请获取一些Quicklabs积分,并进行试用。
以下是GCP资源的获取途径:
- GCP免费套餐:提供持续免费的特定产品使用额度。
- Google教育/Quicklabs:学生可申请积分,用于完成交互式实验。
Azure 平台资源
最后,我们来了解Azure平台的准备方案。
Azure平台同样提供非常慷慨的免费套餐,学生可以申请使用。如果你想自行完成更多实验,可以访问Microsoft Learn平台进行学习。
以下是Azure资源的获取途径:
- Azure免费套餐:包含12个月的免费热门服务和永久免费的25+项服务。
- Microsoft Learn:提供丰富的免费在线学习路径和交互式沙箱环境。

总结

本节课中我们一起学习了如何为AWS、GCP和Azure三大云平台准备免费的实验环境。总而言之,本课程所涵盖的所有内容,都可以通过利用AWS、GCP和Azure的免费功能来完成。如果你像杜克大学的学生一样是教育机构的一员,还可以获取那些专门为教育环境设计的实验资源。
072:项目概述 🚀

在本节课中,我们将一起学习课程二的最终项目。你将创建一个容器化的 Flask 微服务,并将其部署到一个托管的容器服务中。我们将逐步解析项目中的核心概念,确保你能清晰地理解每个部分。
项目简介

你将构建的项目是一个容器化的 Flask 微服务。这意味着你需要创建一个独立的、包含所有运行时和源代码的工作单元,并将其部署到云服务商提供的托管容器平台上。
核心概念解析
上一节我们介绍了项目的整体目标,本节中我们来详细看看其中涉及的关键术语。
容器
容器是一个独立的工作单元。它通常采用 Docker 格式,包含了部署应用所需的所有运行时环境和源代码。其核心公式可以表示为:
容器 = 运行时环境 + 应用程序源代码
这是容器与常规应用程序的一个关键区别。常规应用可能依赖外部环境,而容器将一切打包在一起,确保了环境的一致性。
微服务
关于微服务,我们将在后续课程中深入探讨。简单来说,微服务是一个单一用途的应用程序。它专注于做好一件事,就像一个厨房小刀或搅拌机,功能专一且高效。
托管容器服务
在云平台上,有多种托管的容器服务可供选择。每个主要的云服务提供商都提供此类服务。以下是几个例子:
- Cloud Run:这是谷歌云平台(GCP)上的一项全托管容器服务。你只需提供一个 Docker 格式的文件,将其推送到容器注册表(存放容器的地方),该服务就能自动将其转换为一个可用的 Web 服务。
- AWS EKS:这是亚马逊云科技(AWS)平台上的服务,用于在 Kubernetes 环境中管理容器。
你可以灵活选择最适合你工作流程的托管服务来部署你的容器。
总结

本节课中,我们一起学习了课程二最终项目的概述。我们明确了项目目标是构建一个容器化的 Flask 微服务,并解析了“容器”、“微服务”和“托管容器服务”这三个核心概念。在接下来的实践中,你将有机会亲手实现这个项目。
073:虚拟机简介 🖥️
在本节课中,我们将深入学习虚拟机。虚拟机是云计算的关键组成部分,它们允许你在一个主机操作系统内部运行一个客户操作系统。
我们将探讨几个核心主题,包括容器与虚拟机的对比、竞价实例的工作原理,以及如何在云平台上启动竞价实例和虚拟机。让我们先来看看本课的学习目标。
学习目标 🎯
首先,我们将评估不同的虚拟化抽象方法。这意味着要了解虚拟化应用程序的合适方式、其中的权衡取舍,以及需要注意的事项。
上一节我们介绍了学习目标,本节中我们来看看如何利用虚拟机构建解决方案。虚拟机在云环境中仍然被广泛使用,我们将讨论构建虚拟机的一些关键特性。
关键术语 📖
以下是本课程将涉及的一些关键术语。
容器
容器允许你构建云原生应用,包括那些使用Kubernetes编排服务的应用。使用容器构建应用也是DevOps的最佳实践。它的作用是将运行时环境与你的代码打包在一起。容器的另一个关键特性是它们可以在毫秒级时间内启动。
虚拟机
现在,我们来谈谈虚拟机的一些关键特性。首先,虚拟机适用于单体应用。例如,如果你有一个已经运行了10年的Web框架,将其迁移到虚拟机是一个合适的用例。虚拟机还允许你在一个操作系统内部运行另一个操作系统。例如,如果你正在运行macOS,并希望在其中运行Linux,虚拟机就是一个很好的选择。最后,与容器不同,虚拟机的启动时间可能从几秒到几分钟不等。这是虚拟机与容器的一个关键区别,也是某些场景下容器可能更合适的原因。
Docker格式容器详解 🐳
接下来,我们详细了解一下Docker格式的容器。一个Docker格式的容器本质上是一个包含关键指令的平面文件。请注意,这里的示例文件从Python 3.7.3继承,然后指定了存放代码的目录,并安装了所需的软件。Docker格式容器的关键区别在于,它是一个文件,你通过它来指定操作系统、代码或运行时环境应如何存在于你的源代码控制项目中。它是一种文件格式,可以继承其他依赖项。其启动时间也可以在秒到分钟级别。这就是Docker容器的关键特性。


总结 📝


本节课中,我们一起学习了虚拟机的基本概念及其在云计算中的核心作用。我们比较了容器与虚拟机的区别,了解了虚拟机的关键特性,如适用于单体应用、支持嵌套操作系统以及较长的启动时间。我们还深入探讨了Docker格式容器的构成和工作原理。理解这些基础知识是后续学习如何在云平台上实际启动和管理虚拟机的重要前提。
074:容器与虚拟机对比 🆚
在本节课中,我们将学习云计算中的两个核心概念:容器与虚拟机。我们将探讨它们的定义、架构差异以及各自适用的场景,帮助你理解在何时应选择容器,何时应选择虚拟机。
概述
容器和虚拟机是两种主流的应用部署与隔离技术。理解它们的区别对于设计高效、可扩展的云解决方案至关重要。本节将清晰地对比两者的架构和特点。
虚拟机详解
上一节我们概述了课程内容,本节中我们首先来深入了解虚拟机。
虚拟机模拟了一台完整的物理计算机。其核心架构包含一个宿主机操作系统和一个或多个客户机操作系统。例如,你可以在运行Ubuntu Linux的宿主机上,创建一个运行Red Hat Linux的客户机操作系统,并在其中运行应用程序。
关键公式/概念:虚拟机 = 宿主机操作系统 + 虚拟机管理程序(Hypervisor) + 客户机操作系统 + 应用程序
虚拟机本质上是一个完整的、可运行任何应用程序的操作系统克隆。
以下是虚拟机的主要适用场景:
- 单体应用:适合运行传统的、一体化的应用程序。
- 遗留系统迁移:非常适合“直接迁移”策略,将已在物理机上运行多年的旧系统(如一个老旧的PHP内容管理系统)完整地克隆并放入虚拟机中。
因此,虚拟机是处理遗留应用或需要完整操作系统环境场景的理想选择。
容器详解
了解了虚拟机之后,我们来看看容器技术有何不同。
容器与虚拟机的最大区别在于架构。容器同样运行在宿主机操作系统之上,但其核心是运行时环境,而非一个完整的操作系统。
关键公式/概念:容器 = 宿主机操作系统 + 容器引擎(如Docker) + 应用及其依赖(二进制文件、库)
容器更像是一个被隔离的进程,它只打包了运行特定应用程序所必需的文件和库,是操作系统的一个子集。
以下是容器的核心特点:
- 轻量级:由于不包含完整的操作系统,容器体积更小,启动速度更快。
- 符合DevOps最佳实践:容器与持续集成/持续交付流程天然契合。
- 适合微服务架构:其轻量、独立的特性非常适合构建和部署微服务。
核心对比与总结
现在,让我们将两者放在一起进行最终对比。
虚拟机的关键在于完全复制,它复制了整个操作系统环境。而容器的关键在于便携性,它打包了一个更小、更精简的应用运行环境,完美契合持续集成和持续交付的理念。

虚拟机架构示意图

容器架构示意图
本节课中,我们一起学习了容器与虚拟机的核心区别。总结如下:
- 虚拟机提供完整的操作系统隔离,适合遗留单体应用和直接迁移场景。
- 容器提供轻量级的应用层隔离,启动快、资源占用少,非常适合现代微服务架构和DevOps实践。


理解这些差异将帮助你在构建云解决方案时做出更合适的技术选型。
075:竞价实例工作原理 🏗️💡
在本节课中,我们将学习AWS竞价实例的工作原理及其核心架构组件。我们将通过一个具体的示例,了解如何设置和使用竞价实例,包括出价、安全组配置和SSH连接等关键步骤。
上一节我们介绍了云计算的基本概念,本节中我们来看看AWS竞价实例的具体工作流程。
首先,我们来看一个示例架构。在这个例子中,我们使用AWS Cloud 9作为控制台。Cloud 9是一个集成开发环境,可以作为我们执行命令、启动实例以及与AWS平台进行交互的“指挥中心”。你可以通过AWS API以编程方式启动竞价实例,也可以直接在AWS管理控制台中操作。
启动竞价实例有几个关键组件需要注意。以下是主要步骤:
首先,你需要对实例进行出价,这类似于参与拍卖。你可以设定你愿意为启动一台虚拟机支付的价格。竞价实例的价格折扣最高可达90%,对于在AWS平台上进行实验的用户来说,这是一个巨大的节省。
其次,除了虚拟机规格,安全组的配置至关重要。安全组决定了实例可以通信的端口。例如,如果你要运行Web服务,可能需要开放端口80;如果你想通过SSH连接来控制机器,则需要开放端口22。在本示例中,为了后续能通过SSH连接,我们必须在安全组中开放端口22。
另一个与SSH连接相关的组件是密钥对文件(PM文件)。这个SSH密钥将允许你安全地连接到启动的竞价实例。
最后,如果你希望该竞价实例能够调用其他AWS服务(例如进行自然语言处理或图像识别API调用),你需要为其分配一个IAM角色。这个角色赋予了实例进行这些连接和操作的权限。
综上所述,启动竞价实例需要关注的核心要素并不多,主要包括:出价、安全组规则以及SSH密钥对文件。
这就是为什么我推荐使用Cloud 9环境。你可以直接从Cloud 9实例建立SSH连接到竞价实例,这非常强大。相比于在个人笔记本电脑上管理一切,维护一个可随时启用的AWS Cloud 9实例作为控制中心更为便捷。当你不需要使用时,可以将其关闭以节省成本。它的优势在于,你可以通过这一个可靠的“中转站”,轻松控制AWS基础设施中的多个竞价实例。


本节课中我们一起学习了AWS竞价实例的启动流程和核心配置要素。我们了解了如何通过出价获得低成本计算资源,以及如何通过配置安全组、SSH密钥和IAM角色来确保实例的可访问性和功能性。同时,使用AWS Cloud 9作为集中管理工具可以极大地简化操作流程。接下来,我们就可以开始动手实践了。
076:启动AWS竞价实例 🚀
在本节课中,我们将学习如何在AWS上启动一个竞价实例。竞价实例是一种极具成本效益的计算资源,通常可以节省高达90%的费用,非常适合用于原型开发、批处理任务或深度学习等场景。我们将从设置Cloud9开发环境开始,逐步完成竞价实例的请求、配置和连接。
概述
我们将通过以下步骤完成竞价实例的启动:
- 设置一个AWS Cloud9环境作为操作平台。
- 通过EC2控制台配置并提交竞价实例请求。
- 配置关键的安全组和密钥对,以确保能够成功连接到实例。
- 从Cloud9环境通过SSH连接到已启动的竞价实例。
- 最后,学习如何清理和终止实例,以避免产生不必要的费用。
设置Cloud9环境
首先,我们需要一个操作基地。AWS Cloud9是一个基于云的集成开发环境,非常适合用来管理和连接我们的竞价实例。
以下是创建Cloud9环境的步骤:
- 在AWS控制台中搜索并进入Cloud9服务。
- 点击“创建环境”。
- 将环境命名为
spot-connector。 - 其余配置保持默认值,然后点击“创建”。

这个Cloud9环境非常有用,因为我们可以将SSH密钥文件上传到这里,之后便可以反复用它来连接多个竞价实例。
配置并启动竞价实例
上一节我们准备好了操作环境,本节中我们来看看如何配置并启动一个竞价实例。


首先,在AWS控制台中导航到EC2服务,然后在左侧菜单中找到“Spot Requests”(竞价请求)并点击“Request Spot Instances”(请求竞价实例)。
在配置界面中,有几个关键部分需要注意:
- AMI选择:你可以选择默认的Amazon Linux,也可以根据需求选择其他镜像,例如用于深度学习的AMI、Ubuntu或Windows。AMI代表Amazon Machine Image,你可以使用预配置的镜像来快速启动实例。
- 实例类型:你可以根据工作负载选择。对于本教程,选择“Big data workload”或其他任何类型均可。
- 密钥对:这是用于SSH连接的关键。点击“创建新的密钥对”,命名为
spot-connector并下载.pem文件。请务必妥善保存此文件。 - 网络设置:通常可以保持默认的VPC和子网设置。
- 安全组:这是一个常见的配置错误点。默认安全组可能不允许SSH连接。我们需要创建一个新的安全组。
- IAM实例配置文件:如果你的实例需要访问其他AWS服务(如S3或Rekognition),则需要在此处关联一个具有相应权限的IAM角色。否则,可以跳过。
- 用户数据:你可以在此处输入实例启动时自动运行的脚本,例如挂载文件系统或安装软件包。
配置安全组与上传密钥
配置竞价实例时,安全组和密钥对是确保能够成功连接的两个最重要环节。忘记配置它们是最常见的错误。
首先,我们来配置安全组。在“配置安全组”部分,点击“创建新的安全组”。
- 将安全组命名为
spot-connect。 - 添加一条入站规则:类型选择“SSH”,端口为
22,来源可以暂时设置为“任何位置”(0.0.0.0/0)以方便测试。在生产环境中,建议将来源限制为你的Cloud9环境IP或特定IP段。
接下来,处理密钥对。我们需要将之前下载的 spot-connector.pem 密钥文件上传到Cloud9环境中,以便后续连接。
- 在Cloud9环境中,点击菜单栏的 File -> Upload Local Files...。
- 选择你下载的
spot-connector.pem文件进行上传。
提交请求并连接实例
完成所有配置后,我们就可以提交竞价实例请求了。
在请求表单底部,设置你需要的实例数量(例如1个),然后查看预估的节省费用(通常可达70%以上)。确认无误后,点击“Launch”(启动)。
提交请求后,状态会显示为“pending fulfillment”(等待履行)。你可以在“Spot Requests”列表中点击该请求查看详细状态。当状态变为“fulfilled”(已履行)时,实例就启动成功了。
此时,在EC2的“Instances”(实例)列表中,你应该能看到一个处于“running”(运行中)状态的新实例。建议立即为它命名(例如 spot-connector),以便于管理。
要连接到这个实例,请执行以下步骤:
- 在实例列表中选中它,点击顶部的“Connect”(连接)按钮。
- 连接向导会给出具体的SSH命令。首先,它要求你设置密钥文件的权限。在你的Cloud9终端中运行:
chmod 400 spot-connector.pem - 然后,复制并运行向导提供的SSH命令,其格式通常如下:
ssh -i "spot-connector.pem" ec2-user@<你的实例公有DNS> - 首次连接时可能会询问是否信任主机,输入
yes即可。

如果一切顺利,你现在应该已经进入了竞价实例的命令行界面,可以开始运行你的命令了。

清理资源
使用完竞价实例后,及时清理资源非常重要,可以避免产生意外费用。
清理的正确步骤是:
- 返回EC2控制台的“Spot Requests”页面。
- 选中你创建的竞价请求。
- 点击“Actions”(操作),选择“Cancel request”(取消请求)。
- 关键:在弹出的对话框中,务必勾选“Terminate instances”(终止实例)选项。这样会同时取消请求并终止关联的实例。如果不勾选,仅取消请求,实例可能仍会运行。
- 确认操作后,实例状态会变为“shutting-down”(关闭中)并最终消失。
对于Cloud9环境,因为它采用按使用时间计费(当环境不活动时会自动休眠),你可以直接关闭浏览器标签页。如果需要彻底删除,可以回到Cloud9控制台删除该环境。
总结


本节课中我们一起学习了如何启动和连接AWS竞价实例。我们了解了从创建Cloud9环境、配置竞价请求(包括选择AMI、设置密钥对和安全组),到最终通过SSH连接实例的完整流程。同时,我们也强调了三个最常见的配置错误:忘记创建/上传密钥对、未配置允许SSH的安全组规则,以及未为需要访问AWS服务的实例分配IAM角色。最后,我们学习了如何正确地取消竞价请求并终止实例以进行资源清理。掌握这些步骤后,你就可以充分利用竞价实例的高性价比优势,进行原型开发、测试或运行批处理作业了。
077:通过终端创建GCP虚拟机 🖥️
在本节课中,我们将学习如何在Google Cloud Platform上启动一台虚拟机。我们将通过Cloud Shell环境,使用命令行来创建虚拟机实例,然后通过SSH连接到该实例,并安装一个名为Nginx的Web服务器。
启动Cloud Shell环境
首先,我们需要激活Cloud Shell环境。Cloud Shell是一个基于浏览器的命令行工具,它预装了Google Cloud SDK和其他实用程序,方便我们管理云资源。
在GCP控制台中,点击顶部的Cloud Shell图标即可激活它。
通过命令行创建虚拟机
上一节我们启动了Cloud Shell环境,本节中我们来看看如何使用gcloud命令行工具来创建虚拟机实例。
gcloud是Google Cloud SDK的主要命令行界面。以下是创建虚拟机的命令示例:
gcloud compute instances create gce-lab --machine-type n1-standard-2 --zone us-central1-a

gcloud compute instances create gce-lab: 这是创建虚拟机实例的核心命令,gce-lab是我们为实例指定的名称。--machine-type n1-standard-2: 此参数定义了虚拟机的规格,n1-standard-2代表一种标准配置的机型。--zone us-central1-a: 此参数指定了虚拟机将要部署的区域,us-central1-a是位于美国中部的一个可用区。
运行此命令后,系统可能会要求授权,之后便会以编程方式启动虚拟机。通过Cloud Shell执行此操作,无需在控制台界面中导航,这是一个关键优势。
连接到虚拟机并安装软件
虚拟机创建完成后,我们可以在GCP控制台的“VM实例”页面找到它。该页面提供了连接到虚拟机的选项。
我们可以通过SSH连接到这台机器。在实例列表中找到对应的机器,点击“SSH”按钮,并选择“在浏览器窗口中打开”。
成功连接后,我们会获得一个独立的终端窗口,可以在此对虚拟机执行操作。
首先,我们以root用户身份登录,并更新Ubuntu操作系统。更新系统的命令是:
apt-get update

接下来,我们安装Nginx Web服务器。在Ubuntu系统中,我们使用apt-get包管理器来安装软件。安装Nginx的命令是:
apt-get install nginx

安装完成后,我们可以验证Nginx服务是否正在运行。使用以下命令查看系统进程,并筛选出与Nginx相关的进程:
ps aux | grep nginx

如果命令输出中显示了nginx进程,则说明Web服务器已成功运行。
配置防火墙规则
现在,Web服务器已经在虚拟机上运行。我们尝试通过虚拟机的公网IP地址在浏览器中访问它。
然而,你可能会发现无法访问。这是一个在GCP中创建资源时的常见问题:默认的防火墙规则可能阻止了外部访问。

要解决这个问题,我们需要创建一个新的防火墙规则来允许HTTP流量。
以下是创建防火墙规则的步骤:
- 在GCP控制台中导航到“防火墙规则”页面。
- 点击“创建防火墙规则”。
- 为规则命名,例如
web-access。 - 将“流量方向”设置为“入站”。
- 在“目标”部分,可以选择“网络中的所有实例”。
- 在“来源IP地址范围”中,输入
0.0.0.0/0以允许所有IP地址访问(生产环境中建议限制为特定IP)。 - 在“协议和端口”部分,选择“TCP”,并指定端口
80。 - 点击“创建”。
创建防火墙规则后,返回浏览器并刷新虚拟机的公网IP地址页面。此时,你应该能看到Nginx的默认欢迎页面,这证明Web服务已可通过网络访问。



本节课中我们一起学习了通过GCP命令行工具创建虚拟机、连接实例、安装Nginx Web服务器以及配置防火墙规则以允许外部访问的完整流程。掌握这些步骤是构建和部署云上应用的基础。
078:在Azure机器学习工作室中创建计算集群 🚀
在本节课中,我们将学习Azure机器学习工作室中的核心计算选项,包括计算实例、计算集群和推理集群。我们将了解它们各自的用途、配置方法以及如何根据不同的工作负载选择合适的类型。
探索Azure计算选项
上一节我们介绍了Azure机器学习工作室的界面。本节中,我们来看看其中几种核心的计算资源类型。
在这个界面中,我们可以看到计算实例、计算集群,以及推理集群。那么它们之间有什么区别呢?
计算实例:用于交互式开发
计算集群是您可以启动并配置Jupyter Notebook环境的地方。我们可以直接创建一个。
如果我选择“新建”,并输入名称,例如“Jupyter-demo”。在这里,我可以在CPU和GPU之间进行选择,这取决于我要解决的问题类型。我还可以在不同规格的虚拟机大小之间切换。此外,如果需要,我还能通过SSH连接到该实例。配置完成后,我点击“创建”。
创建过程通常需要几分钟时间。
计算集群:用于弹性训练
现在,让我们也看看计算集群。如果进入计算集群部分并选择“新建”,操作类似。我可以将其命名为“demo-cluster-2”。同样,我可以在GPU和CPU之间切换。
例如,如果我打算进行自动化机器学习或深度学习,那么GPU对于这类特定工作负载来说就非常合适。这里还有一个重要的设置是虚拟机优先级。点击后可以看到,“专用”意味着它始终存在。但很多时候,对于实验任务,我认为“低优先级”是更好的选择,因为它实际上也能降低成本。我可以在这里切换不同规格的虚拟机大小。
然后,我可以选择节点的最小和最大数量。这里需要重点指出的是:如果您不希望在某些时段(例如夜间没有作业运行时)产生费用,您应该将最小节点数设置为0。然后,您可以设置它能够弹性扩展到某个数量,比如我想扩展到4个节点,之后就可以点击创建。
这样做的好处是,集群在不需要时会保持空闲状态,而当我需要时,它可以迅速准备就绪。
推理集群:用于大规模预测
接下来,我们看看第三种类型:基于Kubernetes的推理集群。如果我在这里创建它,您会看到它利用Kubernetes来执行大规模推理或预测。
创建推理集群的过程与其他类型(计算实例、计算集群)非常相似。您需要输入一个名称(我们称之为“k8s-cluster”),并选择一个区域(例如“美国中部”)。同样,我可以选择不同的虚拟机类型。我们可以保留默认的节点数量,然后点击“创建”。
附加集群:连接外部服务
最后一种计算实例类型是附加集群。例如,假设您正在使用Databricks(一个托管的Spark环境),我可以将其作为附加集群连接到Azure机器学习工作室。
总结与回顾
本节课中,我们一起学习了Azure机器学习工作室中的主要计算选项。
- 计算实例:主要用于交互式开发,例如运行Jupyter Notebook。
- 计算集群:用于弹性扩展,执行模型训练任务,支持按需启动以节省成本。
- 推理集群:专为大规模模型预测而优化的环境,基于托管的Kubernetes服务。
理解这些选项的区别,将帮助您根据开发、训练和部署的不同阶段,高效且经济地配置云计算资源。




079:AWS Cloud Shell 🐚

在本节课中,我们将要学习AWS Cloud Shell,这是一个在AWS控制台中可直接访问的、用于开发和配置的强大工具。我们将探索它的基本功能、如何利用它进行快速开发,以及如何通过自定义配置来提升工作效率。
上一节我们介绍了AWS控制台的基本界面,本节中我们来看看一个内置的、常被忽视的强大工具:AWS Cloud Shell。
AWS Cloud Shell是一个在AWS管理控制台中可直接访问的、基于浏览器的命令行终端。它预装了AWS CLI、Python、Git等常用开发工具,并已配置好您账户的访问权限,无需额外设置。
以下是AWS Cloud Shell的几个核心优势:
- 无需本地配置:您无需在本地计算机上安装或配置AWS CLI。
- 预认证环境:Shell启动时已自动使用您登录控制台的凭证,可直接操作AWS资源。
- 持久化存储:您的
/home/cloudshell-user目录下的文件会被保留,即使关闭Shell会话。
现在,让我们看看如何利用Cloud Shell进行实际开发。一个常见的用例是管理Python虚拟环境。
在Cloud Shell中,您可以像在本地终端一样操作。例如,您可以编辑~/.bashrc文件,以便在每次登录Shell时自动激活特定的Python虚拟环境。这通过source命令实现。
# 示例:在.bashrc中添加自动激活虚拟环境的命令
echo "source /path/to/your/venv/bin/activate" >> ~/.bashrc
source ~/.bashrc
执行上述命令后,您的Python虚拟环境将在Shell启动时自动激活,方便您立即开始使用特定的依赖库进行开发,例如安装并测试boto3库。
除了管理开发环境,Cloud Shell更强大的功能在于直接通过命令行与AWS服务进行交互。这比在图形界面中点击操作通常更快捷。
例如,您可以使用AWS CLI直接操作DynamoDB。以下命令用于创建一个名为customers的表:
aws dynamodb create-table \
--table-name customers \
--attribute-definitions AttributeName=CustomerID,AttributeType=S \
--key-schema AttributeName=CustomerID,KeyType=HASH \
--billing-mode PAY_PER_REQUEST
创建后,您可以使用list-tables命令来验证:
aws dynamodb list-tables
这种交互方式让您能够快速测试想法、验证命令,是开发初期进行原型设计和调试的高效手段。
如果您发现某些AWS CLI命令需要频繁重复输入,Cloud Shell支持通过别名(Alias)来简化操作。您可以将长命令定义为简短的别名,并保存在~/.bashrc文件中,使其永久生效。
以下是定义别名的方法:
- 使用文本编辑器(如
vi)打开~/.bashrc文件。 - 在文件末尾添加别名定义,格式为:
alias 简短命令='原始长命令'。 - 保存文件,并使用
source ~/.bashrc命令使更改立即生效。
例如,将列出DynamoDB表的命令定义为别名listtables:
# 在.bashrc文件中添加
alias listtables='aws dynamodb list-tables'
之后,您只需输入listtables,Shell就会自动执行完整的aws dynamodb list-tables命令。输入alias命令可以查看所有已定义的别名。

本节课中我们一起学习了AWS Cloud Shell的核心价值与应用。我们了解到它是一个开箱即用、已预认证的命令行环境,非常适合进行快速的开发测试、服务配置和资源管理。通过管理Python环境、直接使用AWS CLI操作服务以及创建命令别名来优化工作流,您可以显著提升在AWS上进行开发和运维的效率。对于开发者而言,在某些场景下,这可能是与AWS服务交互的最快捷方式。
080:13_02_12_Google Cloud Shell

概述
在本节课中,我们将学习如何开始使用Google Cloud Platform。我们将从了解免费套餐开始,然后重点探索一个核心工具——Google Cloud Shell。我们将学习如何在Cloud Shell中设置开发环境,运行Python和Rust代码,并初步了解如何通过命令行管理云资源。
Google Cloud 免费套餐
首先,我们来看看Google Cloud的免费套餐。
如果你从Google Cloud免费套餐开始,你可以访问20种免费产品。你还会获得$300的免费额度,但需要在三个月内使用完毕。免费套餐包含的部分产品有:
- Compute Engine
- Cloud Storage
- BigQuery
- Kubernetes
- App Engine
- Cloud Run
- Cloud Build
- Stackdriver
- Filestore
- Pub/Sub
- Cloud Functions
- Vision AI
- Speech-to-Text
- Natural Language API
- AutoML
这里确实提供了大量的免费服务。接下来,让我们开始实际操作。
进入云控制台
我将进入云控制台仪表板。你可以在这里看到所有内容的概览。首先,我们有项目信息。在项目信息中,你可以决定例如如何向项目添加人员、配置项目设置等。

此外,中间的仪表板显示了一些最近访问过的服务。右边还有一个资源标签页,显示你可以切换查看的不同资源,例如,如果你想启动一台虚拟机。右侧还会显示状态信息。
当你使用Google Cloud时,这里将是你最常使用的起点。请注意,我在这里选择了一个项目。如果我想创建一个新项目,我会点击“选择项目”并创建一个新项目。
启动Cloud Shell
当你初次接触Google Cloud Platform时,我建议你启动Cloud Shell。让我们开始操作。
Cloud Shell非常方便,因为你可以立即在这个环境中开始构建解决方案、尝试各种想法。
我喜欢做的第一件事是创建一个Python虚拟环境,以便测试Python项目并在Cloud Shell中运行它们。我将首先执行以下操作:
python3 -m venv .venv
这将在我的主目录下创建一个隐藏的虚拟环境目录。操作成功。
然后,我喜欢编辑我的.bashrc文件。在这里,我可以添加一行命令来自动激活Python虚拟环境:
source ~/.venv/bin/activate
这是一个实用的小技巧。现在,每次我打开这个环境时,Python虚拟环境都会自动激活,这解决了许多与Python相关的奇怪问题。
克隆并运行代码
如果我想进入一个存放代码的仓库,例如这里有一些Python代码,并且我不想推送更改回去,我可以进入这个环境并直接执行git clone。让我们开始操作:
git clone <你的仓库URL>


现在,我有了我的Python代码。如果我进入这个仓库目录,可以看到我有一个测试文件和其他一些内容。
我喜欢使用Makefile,因为它允许我使用快捷命令。我们甚至可以进入编辑器查看代码,这是Google Cloud平台内部一个很好的资源。
在这个目录中,我们有一个Makefile。你可以看到我可以执行install、test、format、lint、container、refactor等命令。这包含了在Google Cloud环境中工作时非常常见的一些操作。
让我们返回并测试一下,只需执行make install,然后执行make lint,看看是否有效。
make install
这将进入我的requirements.txt文件并安装所有包。安装完成后,我可以继续并检查我的代码:


make lint
看起来我们的代码检查成功了。你甚至可以查看这个文件,看看main函数里有什么,这是一个非常简单的应用程序。
安装Rust环境
现在Python可以工作了,我们还能做什么?我们还可以安装Rust。我将访问rustup.rs,复制安装命令,然后在这里粘贴执行。这将下载Rust环境,包括cargo和clippy(代码检查工具)。基本上,这提供了成为Rust开发者所需的一切。
我喜欢用Rust编程的原因之一是,根据你所做的事情,它的性能可能比Python好40倍到1000倍。因此,如果你想进行高性能计算,这通常是一个非常好的选择。
安装程序已经将其添加到了我的路径中。所以如果我在这里,实际上可以运行cargo。我可以创建另一个“Hello World”项目:
cargo new hello
这将在这里创建一个示例目录。进入目录后,与Python不同,我不需要执行任何额外步骤,可以直接运行:
cargo run


它编译并输出了我们的“Hello, world!”。如果我们想查看该项目的结构,可以看到这是一个非常简单的“Hello World”文件。如果我想要添加依赖项,例如GCP SDK,我可以在这里的Cargo.toml文件中完成。
这是一个开发者需要做的一些事情的很好概述。同样,我认为Python和Rust是两种非常理想的编程选择。
管理虚拟机实例
我要做的最后一件事是启动一台虚拟机并查看它。这里已经有一台正在运行的实例。如果我想创建一个新的,可以点击“创建实例”并启动某种类型的机器。
例如,如果我想启动一个微型实例,你可以看到我将花费的成本估算会显示在这里,包括月度估算。实际上它是按小时计费的。如果我选择一台非常大的机器,可以看到在这个特定环境中,一台32核的机器每月大约需要$500。因此,确保查看你启动的机器的不同指标非常重要。
由于我已经有一台正在运行的机器,我需要做的就是通过命令行来查询它。在Google Cloud的教程中,查看如何通过命令行列出机器是非常常见的操作。
我的历史命令中已经有一条相关记录。查看历史命令也是一个获得快捷方式的好方法:
history
如果我输入gcloud compute instances list,可以看到我实际上可以控制它。我甚至可以通过使用这个基础命令来启动东西:
gcloud compute instances
如果你需要更多关于特定命令的信息,可以随时运行help。Google Cloud确实是一个以命令行导向的服务。因此,如果你理解命令行,使用Google Cloud将会有很好的体验。
总结


本节课中,我们一起学习了如何开始使用Google Cloud Platform。我们首先了解了免费套餐的内容,然后深入探索了Cloud Shell这个强大的工具。我们学习了如何在其中设置Python虚拟环境、克隆代码仓库并使用Makefile运行项目。接着,我们安装了Rust开发环境并运行了简单的程序。最后,我们了解了如何通过云控制台和gcloud命令行工具来查看和管理虚拟机实例。希望你能亲自尝试这些命令,开始你的Google Cloud之旅。
081:容器技术简介 🐳
在本节课中,我们将学习容器技术。容器是一种将应用程序的运行时环境与源代码一起打包的强大方式。我们还将探讨什么是Docker,如何使用Docker Hub,以及如何利用容器注册表(包括亚马逊的ECR)来构建应用。让我们开始学习这些目标。
首先,我们将进入使用容器构建解决方案的部分。我会逐步展示如何基于源代码控制仓库构建一个容器,并将该代码推送到容器注册表。之后,我们将探讨如何将DevOps最佳实践(如持续集成和持续交付)应用于容器。
什么是容器?📦
上一节我们概述了课程内容,本节中我们来看看容器的核心概念。容器是一种轻量级、可移植的软件打包技术。它将应用程序及其所有依赖项(如库、配置文件)打包在一个标准化的单元中。这确保了应用程序在任何计算环境中都能以相同的方式运行。
容器与虚拟机不同。虚拟机模拟整个操作系统,而容器则共享主机操作系统的内核,这使得它们更加高效和快速启动。理解这一点对于掌握容器化至关重要。
Docker简介 🐋
在了解了容器的基础概念后,本节我们来认识Docker。Docker是目前最流行的容器化平台。它提供了一套工具,使得创建、部署和运行容器变得非常简单。
以下是Docker的核心组件:
- Docker镜像:一个只读的模板,包含了运行应用所需的代码、运行时、库和环境变量。镜像是通过一个名为
Dockerfile的文本文件定义的。 - Docker容器:是Docker镜像的一个运行实例。你可以使用
docker run命令从镜像启动一个或多个容器。 - Docker Hub:一个公共的镜像注册表,你可以从中拉取(下载)现成的镜像,也可以推送(上传)自己构建的镜像。
使用Docker Hub 🌐
上一节我们介绍了Docker的基本组件,本节中我们来看看如何使用Docker Hub。Docker Hub是一个云端的服务,用于存储和分发Docker镜像。你可以把它想象成容器镜像的“GitHub”。
以下是使用Docker Hub的基本步骤:
- 搜索镜像:你可以在Docker Hub网站上或使用
docker search命令查找你需要的软件镜像,例如nginx或python。 - 拉取镜像:找到镜像后,使用
docker pull [镜像名]命令将其下载到本地。 - 推送镜像:如果你构建了自己的镜像,可以登录Docker Hub后,使用
docker push [你的用户名]/[镜像名]命令将其分享到云端。
构建与推送容器镜像 🛠️
在熟悉了镜像仓库后,本节我们将动手实践如何构建和推送一个容器镜像。这个过程通常从编写一个 Dockerfile 开始。
以下是一个简单的示例,展示如何为一个Python应用构建镜像:
# 使用官方Python运行时作为父镜像
FROM python:3.9-slim
# 设置工作目录
WORKDIR /app
# 将当前目录内容复制到容器的/app目录下
COPY . /app
# 安装应用所需的依赖
RUN pip install --no-cache-dir -r requirements.txt
# 声明容器运行时监听的端口
EXPOSE 80
# 定义容器启动时执行的命令
CMD ["python", "app.py"]
构建好 Dockerfile 后,你可以使用 docker build -t my-python-app . 命令来构建镜像,然后使用 docker push 命令将其推送到你选择的容器注册表。
应用DevOps最佳实践 🔄
我们已经学会了如何构建和存储容器镜像,本节我们将探讨如何将DevOps理念融入容器化工作流。核心实践是持续集成和持续交付。
以下是关键实践点:
- 持续集成:每当有代码变更提交到源代码仓库时,自动触发构建新的Docker镜像并进行测试。
- 持续交付/部署:将通过测试的镜像自动部署到测试或生产环境。这可以通过与Amazon ECR、GitHub Actions、Jenkins等工具集成来实现。

将容器与CI/CD管道结合,可以实现快速、可靠且一致的软件发布流程。

总结 📝
本节课中我们一起学习了容器技术。我们从容器的基础概念讲起,介绍了Docker平台及其核心组件。我们学习了如何使用Docker Hub,并逐步演示了如何通过 Dockerfile 构建镜像并将其推送到注册表。最后,我们探讨了如何将DevOps的持续集成与持续交付实践应用于容器化项目,以实现高效的软件开发和部署。掌握这些知识是构建现代化、可扩展云解决方案的重要一步。
082:容器使用实践 🐳

在本节课中,我们将探讨何时应该使用容器技术。容器是现代云计算时代中一个非常相关的技术选择,我们将分析几个关键的应用场景和优势。
概述
容器技术为软件部署和运行提供了一种轻量级、可移植的解决方案。理解其适用场景,有助于我们更有效地设计和构建云原生应用。接下来,我们将逐一探讨使用容器的几个核心原因。
使用容器的关键场景
以下是几个选择使用容器技术的主要理由。
构建云原生环境 ☁️
上一节我们介绍了容器的基本概念,本节中我们来看看它在云原生环境中的应用。如果你希望构建一个云原生环境,容器通常是一个绝佳的选择。这得益于云计算的诸多进展,例如托管容器服务。这类服务允许你将容器作为服务进行部署,这可能是部署应用程序最简单的方式。
此外,在云原生生态中,存在许多云托管的Kubernetes服务,它们可以管理容器编排的复杂性。因此,追求云原生架构是使用容器的一个重要理由。
实现微服务架构 🔧
微服务是一种高效且简洁的解决问题的方式,其核心思想是让一个服务只专注于一件事。这种架构与容器技术配合得非常好。
容器允许你构建可复现的、独立的单元,完美契合微服务的工作流程。一个微服务可以被封装在一个容器中,确保其运行环境的一致性。
支持DevOps实践 ⚙️
你可能会问,什么是DevOps的最佳实践?其中之一就是像管理源代码一样,可编程地复现运行环境。
在DevOps实践中,容器允许你通过代码(Infrastructure as Code)来定义和构建容器镜像,同时也能以编程方式构建源代码,并将其部署到生态系统中。因此,DevOps工作流与容器技术能够很好地协同工作。
任务与作业管理 📋
另一个比较直观的应用场景是任务管理。当你需要反复构建和复现某些作业(例如持续集成中的构建任务)时,基于容器的工作流通常非常有效。
这就是为什么许多构建服务公司或软件即服务(SaaS)的构建平台都使用容器来管理他们的工作负载。容器确保了每次任务执行都在完全一致的环境中开始。
确保可移植性与可用性 📦
最后,可移植性和可用性是容器的另一个关键优势。在DevOps和数据科学这两个领域,可移植性尤其能带来巨大收益。
例如,假设你是一名数据科学家,拥有一个完整的、用于药物发现的工作流环境。如果你只将源代码交给别人,而源代码仓库中无法复现运行时环境,那么对方仍然无法运行你的程序。
但是,如果使用容器,运行时环境也被一同打包。这是一个关键要点:当你能够将运行时与项目一起打包时,它就变得完全可复现,而这正是科学可重复性的一个关键原则。
总结


本节课中我们一起学习了在哪些场景下应该考虑使用容器。我们探讨了五个主要理由:构建云原生环境、实现微服务架构、支持DevOps实践、高效管理作业任务,以及确保应用的可移植性与可用性。当然,使用容器的理由不止这些,但这几点是最核心的考量因素。理解这些场景,能帮助你在设计云计算解决方案时做出更合适的技术选型。
083:Docker概述 🐳

在本节课中,我们将要学习Docker是什么,了解其核心组件Docker Desktop和Docker Hub,并探索如何在本地开发环境中使用Docker。
什么是Docker?
Docker是一个由Docker Desktop和Docker Hub组成的特定产品。这是一个在初次接触容器技术时非常常见的问题。
Docker Desktop是一个安装在您电脑上的应用程序,用于本地开发工作流。它包含一个容器运行时,这是关键组件之一。它还包含开发者工具,允许您执行诸如启动Kubernetes、配置不同堆栈的启动和关闭等操作。此外,它还有一个图形用户界面应用程序,您可以用来控制各项功能。如前所述,它可以与Kubernetes交互,您实际上可以在Docker内部启动和管理集群。因此,它本质上是一个本地开发工作流。
Docker Hub则允许您将内容签入公共或私有仓库。您可以通过GitHub自动化容器的构建,可以拉取和使用经过认证的镜像。例如,您可以获取数据库的官方版本并拉取下来,并且知道创建该数据库的开发人员就是认证它的人。Docker Hub还支持团队和组织功能,这更像是一个协作环境,而Docker Desktop则是开发环境。
Docker工作流解析
上一节我们介绍了Docker的组成,本节中我们来看看一个典型的基于Docker的工作流是如何运作的。
当您使用基于Docker的工作流时,通常会从使用核心开发者提供的基础镜像开始。例如,尽管我有多年的Python经验,但Python核心开发者比我知识渊博得多。我可以通过在我的Dockerfile中拉取他们的基础镜像来利用他们的知识。
以下是一个示例:
FROM python:3.7.3
这个指令利用了Python核心开发者对Python的深厚知识,这远超过我个人所能掌握的。他们可能拥有我一生都无法复现的百年经验,他们已经运行了所有正确的Bash命令和构建命令,而我可以直接在我的项目中利用这一点。
接下来,我会基于那个原始的基础镜像创建一个新的复合项目,然后将这些更改推送到我的私有Docker Hub仓库。这意味着,如果我愿意,我可以拉取这个镜像,在云中测试并运行这个新项目,或者将其交给新开发者用于入职,新开发者可以使用我的代码并部署它。
这个理念非常类似于源代码控制,只不过控制的是运行时本身。就像人们经常利用专家开发者编写的库的力量一样,您也可以利用专家开发者构建的运行时环境的力量。
这就是Docker的核心理念。Dockerfile是其中的关键要点。

Docker Desktop界面导览
上一节我们解析了Docker的工作流理念,本节中我们来看看Docker Desktop本身,了解其图形用户界面工具如何工作。

让我们深入了解Docker在操作系统(以macOS为例,其他系统类似)上是如何工作的。在菜单栏上,可以看到Docker Desktop正在运行,Kubernetes也在运行。这是Docker安装的一部分。

如果我点击这个仪表板,它可以让我对Docker环境中运行的所有内容进行更详细的控制。例如,我可以看到Docker有一些可用的镜像。如果我愿意,可以拉取其中一个,查看和检查它,或者运行它。它提供了启动等控制选项。
此外,如果我回到Docker Desktop环境并进入设置菜单,我还可以配置不同的选项。例如,我可能希望登录时自动启动Docker Desktop(假设我正在做大量活跃开发),或者我的机器资源有限,所以不想自动启动它(这是我的典型做法)。
在资源设置下,我可以为我的机器配置所需的选项。我有一台性能相当强大的机器,所以我告诉Docker可以使用我32个可用CPU中的16个,以及我300GB可用RAM中的50GB。我还可以在这里更改其他参数,如交换空间或磁盘大小。这是一种定制本地开发环境的方式,让您拥有或多或少的控制权。
Docker还有其他一些功能。您可以将Docker容器映射到磁盘上的物理位置,也可以配置其他选项,比如如何启动Docker镜像,或者您希望启用哪些实验性功能(例如,更多云体验或FUSE文件系统)。对于包含在内的Kubernetes,您可以设置是否希望默认启用它,以及是否希望Docker部署到本地Kubernetes集群。
总而言之,它确实是一个开发环境加上一个图形用户界面,这个界面为您提供了许多不同的配置选项。
总结


本节课中我们一起学习了Docker的基础知识。我们了解到Docker是一个包含Docker Desktop(本地开发环境与GUI工具)和Docker Hub(镜像仓库与协作平台)的产品。我们探讨了如何通过Dockerfile利用专家制作的基础镜像来构建自己的应用,并初步浏览了Docker Desktop的界面和配置选项,它让容器的本地开发、管理和资源调配变得可视化且便捷。
084:从Docker Hub运行容器 🐳
在本节课中,我们将学习如何从Docker Hub获取并运行一个容器。Docker Hub是创建、管理和交付容器最便捷的平台。我们将以运行一个Jupyter Notebook容器为例,展示如何快速搭建一个复杂的数据科学工作环境,而无需在本地进行繁琐的配置。
访问Docker Hub
根据官方文档,Docker Hub是创建、管理和交付容器最简便的方式。我们可以访问Docker Hub网站,选择登录或直接浏览现有的容器镜像。
以下是访问Docker Hub的步骤:
- 打开浏览器,访问 Docker Hub 网站。
- 你可以选择登录账户,也可以直接浏览公共仓库。
- 在搜索栏中,可以查找你需要的容器镜像,例如 “jupyter”。
拉取容器镜像
一个很好的例子是Jupyter。如果想在macOS或Windows上搭建一个基于Jupyter的环境,过程可能相当复杂。但通过Docker,我们可以简化这一流程。
在Jupyter的Docker Hub页面向下滚动,可以找到docker pull命令。复制该命令,在终端中粘贴并执行,即可下载由Jupyter专家创建并维护的、功能完整的Jupyter Notebook环境镜像。
命令示例:
docker pull jupyter/scipy-notebook
执行此命令后,我们就下载了最新的Jupyter镜像。这个生态系统的强大之处在于,之后我们可以轻松尝试不同版本或更复杂的Jupyter配置,而完全不影响本地环境。
运行容器

现在,让我们看看如何实际使用这个镜像。我们可以使用docker run命令来启动容器。
如果想运行最新版本的镜像,可以使用以下命令:
docker run -p 8888:8888 jupyter/scipy-notebook:latest
其中,-p 8888:8888将容器内的8888端口映射到宿主机的8888端口,:latest指定拉取最新的镜像标签。
执行此命令后,Docker会启动一个包含了所有最新特性和依赖的Jupyter Notebook实例。这极大地简化了环境配置,避免了因环境差异导致的混乱。
启动后,你可以在终端看到Jupyter实例的运行日志。它默认在前台运行,并会输出一个带有令牌(token)的访问URL。
使用Jupyter Notebook
现在,Jupyter实例已经运行。如果你正在学习Python或数据科学,这可能是最推荐的工作流程之一,尤其适合初学者。
在浏览器中打开终端提供的URL(通常是 http://localhost:8888),即可进入Jupyter界面。
在Jupyter界面中,你可以点击“New”按钮,然后选择“Python 3”来创建一个新的Notebook,或者选择“Terminal”来打开一个终端。
让我们快速尝试一下。选择打开一个终端,输入命令uname -a,你会发现容器内部实际上运行着一个Linux系统。这是容器环境非常强大的一点。你甚至可以运行top命令来查看进程情况。
这是一种极其强大的本地开发方式,无需维护复杂的本地工作流。
在容器中进行数据分析
接下来,我们新建一个Python 3 Notebook,并尝试一些操作。这是一个常见的数据科学工作流。
首先,导入pandas库:
import pandas as pd
然后,创建一个DataFrame。这里我们使用一个关于糖消费量的研究数据URL:
df = pd.read_csv('你的数据CSV文件URL')
接着,我们可以使用df.describe()方法来查看数据的描述性统计信息。这个数据集展示了美国各州及不同教育水平的糖摄入量,其中存在教育水平与糖摄入量之间的负相关关系。
最后,我们可以进行简单的可视化。使用df.plot()即可生成图表。
核心概念:整个过程展示了如何在不触碰操作系统的情况下,开发复杂的应用程序。容器本身为你解决了环境依赖问题。
总结
本节课中,我们一起学习了如何从Docker Hub拉取并运行容器镜像。我们以Jupyter Notebook为例,演示了通过几条简单的Docker命令,就能快速获得一个功能完整、隔离的复杂应用运行环境。


无论是Jupyter Notebook、Postgres数据库还是大数据系统,使用容器都是简化系统搭建、快速入门系统工程的高效方式。它消除了环境配置的障碍,让开发者能更专注于应用本身。
085:从零构建Docker容器项目 🐳
在本节课中,我们将学习如何从零开始构建一个简单的Docker容器项目。我们将通过一个具体的例子,了解创建和运行Docker容器所需的核心文件和步骤。
项目概述
让我们来看一个非常简单的项目,它允许你从零开始构建一个容器。这个项目只需要几个必要的文件。
首先,我们来看看这个Dockerfile文件。在这个Dockerfile中,你可以看到我继承了Python 3的基础镜像。这是核心镜像,核心开发者拥有我所不具备的专业知识,我利用了他们的专业知识。我创建了一个应用目录,复制了一个应用程序文件,然后在这里安装第三方包。这就是Dockerfile。
那么应用程序文件呢?让我们继续看看它。如果你看这个应用程序文件,你会发现它是一个非常简单的命令行工具,它接受一个名字,然后打印出你的名字。所以它是一个“Hello World”命令行工具。
那么,我们如何将这个工具容器化并使其运行呢?
在云端环境中克隆项目
让我们继续将这个项目克隆到AWS Cloud9中,这是一个基于云的开发环境。我将复制这个命令,转到这个环境中,然后输入 git clone 命令。好了,现在我将使用 cd 命令进入该目录。
我们将在这里再次看到相同的项目结构。接下来,我将阅读这里的README文件,以了解如何实际运行这个项目。
README中的说明指出,为了运行它,我只需要运行这个命令。首先我们会运行它,然后我会解释它。你可以在这里看到,我运行了 docker run -it,后面跟着存储此镜像的仓库名称(该仓库位于外部的Docker Hub上),然后我像这样传入一些参数。让我们继续运行这个命令。
很好,你可以看到这里发生了什么:现在我已经运行了一次。我可以输入不同的参数并反复使用它,但核心思想是运行时现在位于其他地方。
本地构建与运行
现在,如果我想在本地运行它,我实际上可以输入一个Docker构建命令。让我们继续在这个代码仓库中执行这个操作。假设我运行 docker build --tag,我将这个标签命名为“app”,然后运行一个点号.。这个点号表示查看当前工作目录,并构建Dockerfile中的内容。让我们继续这样做。
好了,它正在本地运行。然后,如果我想查看并运行它,我实际上可以说 docker image ls,它会显示最新的镜像副本。在这里,这就是“app”镜像。
因此,如果我想在本地运行它,我可以稍微修改这个README文件,然后输入 docker run -it。在这种情况下,我不使用远程镜像,而是使用本地镜像。然后我会做同样的事情,输入这些命令,这将运行该镜像的本地版本。

好了,你可以看到,你可以使用托管在其他地方的Docker容器,也可以自己构建它,并实际定制它,然后将其推送到其他地方。
总结

本节课中,我们一起学习了如何从零开始构建一个Docker容器项目。我们了解了Dockerfile的结构和作用,学习了如何从远程仓库拉取镜像并运行,更重要的是,我们实践了如何在本地环境中构建自定义的Docker镜像并运行它。这个过程展示了Docker容器化的核心流程:定义依赖、构建镜像、运行容器。
086:推送项目至AWS ECR注册表 📦
在本节课中,我们将学习如何在AWS上使用容器化工作流。具体来说,我们将使用Cloud9环境作为核心开发场所,构建一个容器镜像,并将其推送到AWS的私有容器注册表——弹性容器注册表(ECR)。随后,我们将在另一个全新的Cloud9环境中拉取并运行该容器,从而体验容器化带来的“一次构建,随处运行”的强大能力。
上一节我们介绍了容器化开发的基本概念,本节中我们来看看如何将其应用于AWS云平台。
创建ECR仓库
首先,我们需要在AWS上创建一个容器注册表仓库来存储我们的镜像。
以下是创建ECR仓库的步骤:
- 登录AWS管理控制台,导航到“弹性容器注册表(ECR)”服务。
- 点击“创建仓库”。
- 为仓库命名,例如
container-scratch。 - 保持其他设置为默认,然后点击“创建仓库”。
仓库创建成功后,系统会显示用于推送镜像的命令。我们稍后会用到这些命令。
在开发环境中构建并推送镜像
接下来,我们回到最初的Cloud9开发环境。假设该环境中已有一个包含 Dockerfile 和应用程序源代码的项目。
以下是推送镜像到ECR的完整流程:
- 登录ECR:使用AWS CLI提供的命令进行身份验证,以便Docker客户端可以与ECR通信。
aws ecr get-login-password --region <region> | docker login --username AWS --password-stdin <account-id>.dkr.ecr.<region>.amazonaws.com - 构建Docker镜像:在项目根目录下,使用Docker构建镜像。
docker build -t container-scratch . - 为镜像打标签:为本地镜像打上符合ECR仓库地址的标签。
docker tag container-scratch:latest <account-id>.dkr.ecr.<region>.amazonaws.com/container-scratch:latest - 推送镜像:将打好标签的镜像推送到远程ECR仓库。
docker push <account-id>.dkr.ecr.<region>.amazonaws.com/container-scratch:latest
在云环境中执行此操作的一大优势是网络带宽。Cloud9实例与ECR注册表之间的数据传输发生在AWS云内部,速度极快。这比从本地慢速网络连接推送要高效得多,能显著节省容器开发时间。
在新环境中拉取并运行镜像
当镜像正在推送时,我们可以准备第二个环境。我们创建一个新的Cloud9环境,命名为“pull-container”。这是一个全新的、干净的环境,无需安装任何依赖。
镜像推送完成后,我们切换到新的Cloud9环境。
以下是拉取并运行镜像的步骤:
- 登录ECR:同样,在新环境中需要先登录ECR才能拉取私有镜像。可以使用命令行历史快速找回登录命令。
# 从历史记录中执行之前的登录命令 aws ecr get-login-password ... | docker login ... - 拉取镜像:从ECR仓库拉取我们刚刚推送的镜像。
docker pull <account-id>.dkr.ecr.<region>.amazonaws.com/container-scratch:latest - 运行容器:基于拉取的镜像启动一个容器。运行命令可能与开发时类似,但镜像来源变为ECR。
docker run -p 8080:8080 <account-id>.dkr.ecr.<region>.amazonaws.com/container-scratch:latest
执行后,应用程序将在新环境中成功运行。我们可以多次运行此命令,验证其可重复性。
核心概念与总结
回顾整个流程,其核心架构可以概括为以下模式:
[开发环境:构建镜像] --> [推送至ECR注册表] --> [任何环境:拉取并运行镜像]


本节课中我们一起学习了完整的AWS容器工作流。关键收获在于,你可以在一个位置(如Cloud9)进行开发并将变更推送至中央仓库(ECR),团队中的其他成员或生产服务器可以轻松地拉取这些变更,并精确复现你的开发环境。这为团队协作和应用部署提供了一种高效、一致的云原生开发方式。
构建大规模云计算解决方案:1-2:Distroless镜像解析


在本节课中,我们将要学习什么是Distroless容器镜像。我们将通过一个简单的类比来理解其核心概念、优势以及它如何为应用程序提供一个安全、高效的运行环境。
什么是Distroless容器?🍚
Distroless是一种精简、安全且一致的容器镜像。理解它的一种方式是将其类比为一顿有机餐,这顿饭只由米饭和豆子组成。米饭和豆子结合在一起时,能提供完整的蛋白质,同时非常健康,因为它包含了简单的成分,如纤维和完整蛋白质。
接下来,我们将逐一剖析这个类比,以理解Distroless容器的核心特性。
核心特性剖析
以下是Distroless容器的主要特性,我们将结合“米饭和豆子”的类比进行说明。
最小化运行时占用
就像一顿米饭豆子餐只包含最基本的营养元素一样,Distroless容器只包含运行应用程序所必需的最核心组件。它不需要花哨的“配料”,从而保持镜像的精简和高效。
聚焦安全性
一顿简单的米饭豆子餐降低了食物过敏的风险。类似地,Distroless容器通过剔除非必要的软件,减少了可能被利用的安全漏洞,从而提升了容器的安全性。
简单性与可维护性
烹饪和清理一顿米饭豆子餐非常简单直接。同样,Distroless容器因为组件少,所以更易于管理。出现问题时也更容易追踪根源,确保了运行的顺畅。
可重现性
复制一顿米饭豆子餐非常容易。Distroless容器因其简单性而具备高度的可重现性。这种一致性确保了所有开发者都在相同的运行时环境下工作,最大限度地减少了差异和混淆。
多语言支持
就像米饭豆子餐能为不同饮食偏好的人提供完整的蛋白质来源一样,Distroless容器可以托管用各种编程语言编写的应用程序,为开发者提供了一个多功能的平台。
总结

本节课中,我们一起学习了Distroless容器镜像。总而言之,Google的Distroless容器就像一顿简单而完整的米饭豆子餐,只提供所需,别无他物。它们为部署应用程序提供了一个安全、可维护、可重现且包容性强的环境,是您软件“食谱”中既营养又经济的选择。😊
088:Rust Distroless PyTorch 项目详解 🚀

在本节课中,我们将学习如何结合 Rust 编程语言与预训练的 PyTorch 模型,来构建一个高效、安全且易于部署的机器学习微服务。我们将探讨其架构优势、关键组件以及从本地开发到生产部署的完整工作流程。
架构概述
上一节我们介绍了课程背景,本节中我们来看看一个具体的架构图。这里展示的是一个使用 Rust 和预训练 PyTorch 模型的架构示意图。

该架构的核心优势在于,它将 Rust 语言的关键优点与预训练模型相结合,为机器学习运维(MLOps)构建了一个极具吸引力的解决方案。
核心组件与优势
以下是构成此解决方案的几个关键组件及其优势。
- Actix Web 框架:这是一个 Web 微服务框架,曾一度被评为全球最快的框架。可以说,它实际上是世界上最快的 Web 服务之一。
- tch-rs(PyTorch Rust 绑定):这些绑定非常完整,让你能够访问底层的 PyTorch C++ 基础设施。因此,你拥有一个真正底层的 PyTorch 库接口。
- 预训练模型:我们可以直接使用优秀的、为计算机视觉或自然语言处理任务准备好的预训练模型。
生产环境考量
在考虑生产环境时,还需要关注一些其他方面,例如日志记录。如果你要运行一个每月处理数百万请求的服务,并且可能涉及准确性、业务逻辑或其他需要监控的方面,那么信息级别、调试级别和异常级别的日志记录都将帮助你维护部署到生产环境的模型。
在处理微服务时,另外两个值得考虑的有趣方面是冒烟测试和单元测试。
- 单元测试:其理念是捕获业务逻辑问题。在开发应用程序时,我可能希望为应用程序中我担心的关键组件编写单元测试,并开发几个不同的单元测试。我甚至可能想构建一个测试 PyTorch 绑定本身的单元测试,以确保安装成功。
- 冒烟测试:这非常有趣,因为其理念是你可以自己调用 API 端点。例如,你可以调用 4、5、10 或 20 个不同的 API 端点,发送一张图片,并确保返回的预测符合预期且没有错误。当你构建一个端到端的模型(例如要投入生产的机器学习模型)时,这些都是非常好的实践。
本地环境与 Rust 优势
这就是本地环境。Rust 的另一个巨大优势是,与 Python 等脚本语言不同,你只需要二进制文件本身(除了需要访问底层的 PyTorch 动态链接库之外)。
一旦你设置好了 PyTorch 二进制文件,接下来为了使其更高效,你可以使用 Distroless Docker 镜像。Distroless 的优点是,这些镜像只包含应用程序及其运行时依赖。
这里至少有两个关键优势。
- 安全性更高:你只包含你的应用程序。在 Rust 的情况下,你只包含二进制文件,可能还有 PyTorch 和预训练模型。仅此而已。这减少了安全漏洞。
- 部署简便:你可以保持一个非常小的容器镜像,这使得在生产环境中部署到许多不同的云服务变得非常简单。
因此,这是一个非常理想的工作流程。让我们看一下这里的 Google 容器工具。你可以看到这被称为 Distroless 容器镜像,它可以从 Google 容器工具获取。
我们来看看这个。为什么要使用它?其理念在于它们只包含应用程序和运行时依赖。一些很酷的特点是这些镜像非常小。例如,对于一个基于 Rust 的命令行工具,你可以制作一个只有 3 或 4 MB 的镜像交给别人。同时,你也不必那么担心容器常见的一些问题,因为你只以非常精简的方式包含了二进制文件。
因此,这是在 Rust 中嵌入预训练模型的理想方案。
项目代码结构
现在让我们快速浏览一下代码。我们来看看这个 rusty-deploy 项目和这里的 rtorch-disk。
项目中包含的一些内容如下。
- Cargo.toml 文件:这里列出了所有的依赖项。
- Dockerfile 文件:你可以看到,与一些 Dockerfile 不同,这个非常小。它只是使用 Rust 作为构建环境,下载 PyTorch,在这里设置一些路径,复制二进制文件,然后将其放入 Distroless 镜像中。我这里只复制了预训练模型和一些用于测试的图片,然后设置了环境路径,就完成了。
- 代码量:这是 30.6 行代码。这是一个计算机视觉模型。这就是使用像 Rust 这样的语言的好处:当你将其部署到生产环境时,它非常小巧。
另外,如果我们看一下这里的源代码,我们有一个库,我们有逻辑代码。所以这些实际上是库类型的文件。我们有一个调用所有内容的主文件。在本例中,这将是 Actix Web 服务,每个路由都被注册。最后,我们还有路由本身,你可以看到它们在单元测试方面的实际作用。
在测试方面,我这里有一个测试目录,然后我有不同种类的测试。我还有一些夹具,也许是一张用于预测的图片。我可以再次包含我正在使用的库的绑定,以验证在部署时安装是否正确。
当你设置好这种结构时,安装就变得非常简单。在安装步骤中,我喜欢做的另一件事是,如果我点击这个,我实际上创建了一个小的安装脚本,允许我引导环境,这样设置新的生产部署也变得非常简单。
它只是执行一些设置命令,移动 PyTorch 文件。这样做的原因是,如果我在这个特定的代码仓库中创建许多不同版本的 PyTorch,我不必一遍又一遍地复制庞大的 PyTorch 库。我可以设置一次,然后就不用管了。
总结与适用场景
因此,这就是我们在考虑用 Rust 构建预训练模型时所关心的结构。许多需要部署大型语言模型的公司都应该认真考虑这个工作流程。
当然,我已经为你做了很多繁重的工作。你可以直接查看这个项目,访问 rusty-deploy 并尝试自己进行这种部署。


本节课中我们一起学习了如何利用 Rust 的高性能与安全性,结合 Distroless 容器和预训练的 PyTorch 模型,构建一个精简、高效且易于维护的机器学习微服务。这种架构特别适合对性能、安全性和资源效率有高要求的生产环境部署。
089:Rust Distroless PyTorch 运行演示 🚀

概述
在本节课中,我们将学习如何将一个预训练的 PyTorch 模型与一个 Rust Actix 微服务结合,并演示其构建、测试和容器化部署的全过程。我们将重点关注如何创建高效的微服务、添加日志记录、进行健康检查,以及利用 Distroless 容器镜像来优化部署大小。
代码结构与构建过程
首先,我们有一个包含预训练 PyTorch 模型的 Rust Actix 微服务项目。项目运行在 GitHub Codespaces 环境中,目录名为 R_torch_disk。
进入该目录后,我们使用 Makefile 来管理构建流程。Makefile 中定义了多个命令来简化操作。
以下是项目构建的关键步骤:
- 构建 Docker 容器:执行
make de-build命令。 - 构建项目发布版本:执行
make build命令。
现在,让我们执行 make build 来编译项目。该命令会显示具体的构建指令。
cargo build --release
由于之前已经构建过,所以这里主要是检查二进制文件是否已存在。如果想直接运行项目,可以使用 cargo run 命令。build 负责编译,run 负责运行。这种基于本地二进制文件的运行方式便于我们进行测试。
微服务测试与日志记录
在项目运行的同时,我们可以查看其“冒烟测试”(smoke test)。这个测试脚本会遍历并调用微服务的各个路由端点。
以下是测试涵盖的端点示例:
- 第一个路由端点。
- 第二个路由端点。
- 第三个路由端点。
- 第四个路由端点。
冒烟测试的强大之处在于,它会自动上传图像,从而允许我们使用不同的端点进行图像预测。
让我们打开一个新的终端,进入 R_torch_disk 目录并运行冒烟测试。
./smoke_test.sh
可以看到,测试脚本逐一调用了所有端点并执行了预测。在构建微服务时,创建一个便于测试不同预测功能并附带良好日志记录的工具是非常有价值的。
接下来,我们看看日志记录是如何设置的。查看 src/main.rs 源代码,可以发现我们使用了一个日志记录器(logger),并将其集成到了微服务中。
在业务逻辑代码中,我们添加了许多 info 级别的日志消息。这些消息帮助我们监控不同环节的操作,便于在生产环境中进行调试和问题排查。因此,在构建微服务时添加日志记录至关重要,它能让你清楚地了解系统内部的实际运行情况。
路由设计与健康检查
关于路由设计,有一个重要点需要指出:在生产环境中,可能只会暴露其中一个路由供外部使用。但在本例中,我设置了多个不同的路由用于内部检查。
例如:
- 一个路由用于检查 PyTorch 是否正常工作。
- 一个路由用于检查图像上传功能是否正常。
- 一个路由用于检查能否对本地磁盘上的图像进行预测。
通过将功能分解到不同的子路由,我们可以逐一验证微服务的各个组件是否正常工作。这构成了一套良好的健康检查(Health Check)系统。在生产环境中,我们可能只公开最后一个路由(用于实际预测),而其他路由则作为内部自检的监控点,用于验证安装、图像上传和图像预测等各个组件的状态。这是一个非常实用的小策略。
容器化部署与镜像优化
现在,让我们看看容器是如何工作的。首先停止当前运行的服务。查看项目中的 Dockerfile,其结构非常清晰。
Dockerfile 主要步骤包括:
- 使用基础镜像。
- 下载 PyTorch。
- 设置环境变量。
- 复制所有构建产物(包括 LibTorch 和预训练模型)。
- 运行编译好的二进制文件。
在 Makefile 中,docker-build 过程对应 docker build 命令,而运行则对应 docker run。我将执行 make run 命令来运行 Docker 镜像。
make run
我喜欢使用 Makefile 是因为 Docker 命令通常较长且容易输错,而 Makefile 可以将其简化。运行后,我们可以看到之前的所有功能在容器内同样正常工作,冒烟测试也能成功执行。这表明我们的应用程序可以轻松部署。
另一个值得关注的点是镜像的大小,这是本方法的一大优势。通过执行 docker image ls 命令,我们可以看到这个镜像大约有 3 GB。
对于这个特定的 PyTorch 安装来说,PyTorch 库本身就有数 GB 大小。因此,镜像中的绝大部分空间都被 PyTorch 占用。预训练模型本身很小(小于 100 MB),Rust 代码编译后的二进制文件大约只有 20 MB。所以,镜像体积主要来自 PyTorch 及其依赖。
尽管如此,这个镜像仍然比常规的、可能达到 6GB、8GB 或 10GB 的完整系统镜像要小得多。通过使用 Distroless 类型的精简基础镜像,我们有效地减小了最终镜像的体积。

项目测试与模型管理
在这个项目结构中,我还设置了多种测试。
例如:
- 模型测试 (
model_tests):运行一些针对模型本身的测试。 - 视觉测试 (
vision_tests):运行绑定库安装的测试。 - Web 功能测试 (
web_tests):例如,验证索引页面是否正常工作的功能测试。
了解这些测试步骤非常重要。此外,如果我们想查看模型本身,项目目录下实际存放着模型文件。在本例中,我使用了一个 ResNet 模型,但你可以替换成任何类型的预训练模型。项目支持放入多个不同的模型供构建过程选择。
总结
本节课我们一起学习了如何构建和部署一个结合了 PyTorch 与 Rust 的微服务。我们演示了从代码构建、本地测试(包括冒烟测试和日志记录)、到设计包含健康检查的路由,最后将其容器化并利用 Distroless 镜像优化部署大小的完整流程。
你看到了既可以使用本地二进制文件进行部署,也可以使用 Docker Distroless 镜像进行部署。一旦完成此设置,就可以轻松地将此服务部署到任何支持容器的云服务平台。
090:Kubernetes入门 🚀
在本节课中,我们将深入学习Kubernetes。Kubernetes是一个强大的容器编排服务,它允许你构建高可用性的解决方案,以及能够自动扩展和自我修复的解决方案。
我们将探讨一些关键的学习目标。首先,我们会了解Kubernetes究竟是什么,它存在的原因是什么,它是如何开发的,以及为什么谷歌要开源Kubernetes。我们还将学习如何使用Kubernetes开发一个解决方案,以便你能亲自动手,利用Kubernetes服务构建一个编排层。
什么是Kubernetes?🤔
上一节我们概述了课程目标,本节中我们来看看Kubernetes的核心定义。
Kubernetes是一个开源的容器编排平台,用于自动化部署、扩展和管理容器化应用程序。它最初由谷歌设计并开源,现在由云原生计算基金会(CNCF)维护。
Kubernetes将构成应用程序的容器分组为逻辑单元,以便于管理和发现。它旨在提供“以容器为中心的基础架构”。
为什么需要Kubernetes?🔍
了解了Kubernetes是什么之后,本节我们来探讨其产生的原因和必要性。
随着微服务架构和容器技术(如Docker)的普及,应用程序被分解为许多小型、独立的服务。手动管理这些容器的部署、网络连接、扩展和故障恢复变得极其复杂且容易出错。
Kubernetes解决了以下核心问题:
- 自动化部署与扩展:可以声明期望的应用程序状态,Kubernetes会自动将实际状态调整至期望状态。
- 服务发现与负载均衡:Kubernetes可以为容器组分配IP地址和DNS名称,并能在它们之间负载均衡流量。
- 自我修复:它会重启失败的容器、替换和重新调度容器,并杀死不响应用户定义健康检查的容器。
- 密钥与配置管理:可以存储和管理敏感信息(如密码)和应用程序配置,而无需将其嵌入容器镜像。
Kubernetes的核心架构 🏗️
现在我们已经知道了Kubernetes解决的问题,接下来我们剖析其核心架构组件。
一个Kubernetes集群由一组称为节点的机器组成。这些节点分为两类:控制平面和工作节点。
以下是主要组件及其功能:
控制平面组件(管理集群)
- kube-apiserver:公开Kubernetes API,是控制平面的前端。
- etcd:一个高可用的键值存储,用作Kubernetes所有集群数据的后备存储。
- kube-scheduler:监视新创建的、未指定运行节点的Pod,并选择节点让Pod在上面运行。
- kube-controller-manager:运行控制器进程,这些控制器处理集群级别的常规任务,例如节点故障、副本数量维护等。
工作节点组件(运行容器)
- kubelet:一个在集群中每个节点上运行的代理,它确保容器在Pod中运行。
- kube-proxy:维护节点上的网络规则,实现Kubernetes服务概念。
- 容器运行时:负责运行容器的软件,例如Docker、containerd。
关键概念与对象 📦
理解了架构,本节我们介绍一些你必须掌握的核心Kubernetes对象。
Pod
Pod是Kubernetes中可以创建和管理的最小可部署计算单元。一个Pod封装了一个或多个应用容器、存储资源、唯一的网络IP以及控制容器运行方式的选项。
apiVersion: v1
kind: Pod
metadata:
name: myapp-pod
spec:
containers:
- name: myapp-container
image: nginx:latest
Deployment
Deployment为Pod和ReplicaSet提供声明式更新。你描述一个期望状态,Deployment控制器就会以受控速率将实际状态更改为期望状态。它是管理无状态应用的标准方式。
apiVersion: apps/v1
kind: Deployment
metadata:
name: nginx-deployment
spec:
replicas: 3
selector:
matchLabels:
app: nginx
template:
metadata:
labels:
app: nginx
spec:
containers:
- name: nginx
image: nginx:1.14.2
Service
Service定义了一组Pod的逻辑集合和访问它们的策略。Service使Pod之间的相互发现和通信成为可能,并为外部访问提供稳定的IP地址和DNS名称。
apiVersion: v1
kind: Service
metadata:
name: my-service
spec:
selector:
app: MyApp
ports:
- protocol: TCP
port: 80
targetPort: 9376
动手实践:部署一个简单应用 🛠️
理论需要结合实践,本节我们将通过一个简单示例,体验如何使用Kubernetes部署一个Nginx应用。
-
创建Deployment:使用上面的Deployment YAML示例,创建一个运行3个Nginx副本的部署。
kubectl apply -f nginx-deployment.yaml -
查看部署状态:检查Deployment和它创建的Pod是否正常运行。
kubectl get deployments kubectl get pods -
创建Service:使用上面的Service YAML示例,创建一个Service来暴露这个Nginx部署。
kubectl apply -f nginx-service.yaml

- 访问应用:获取Service的外部访问地址(例如使用
kubectl get svc查看CLUSTER-IP或在云环境中查看EXTERNAL-IP),然后在浏览器中访问该IP地址,你应该能看到Nginx的欢迎页面。

总结 📝
本节课中我们一起学习了Kubernetes的基础知识。我们从了解Kubernetes作为容器编排平台的定义和必要性开始,然后深入探讨了其核心架构,包括控制平面和工作节点的各个组件。接着,我们学习了Pod、Deployment和Service这三个关键对象的概念和作用。最后,我们通过一个部署Nginx的简单示例,将理论知识付诸实践。
掌握这些基础概念是构建和管理大规模、高可用容器化应用的第一步。在后续课程中,我们将基于此,探索更高级的Kubernetes特性和实践。
091:Kubernetes架构概览 🚢
在本节课中,我们将要学习Kubernetes,一个用于容器的编排系统。我们将从它的基本概念开始,逐步深入到其核心架构、工作流程以及关键的自动扩缩容功能。
Kubernetes是一个容器编排系统,它于2014年由Google开发。它的核心作用是管理容器化的应用程序。与简单的容器运行时不同,Kubernetes提供了集群级别的编排能力。亚马逊、谷歌和微软都提供了各自的托管Kubernetes服务,分别是Amazon EKS、Google GKE和Microsoft AKS。
Kubernetes提供了多项强大的内置功能,包括高可用架构、自动扩缩容、丰富的生态系统、服务发现、健康管理以及密钥管理。这些功能使得管理和扩展容器化应用变得更加简单。
基本工作流程
以下是使用Kubernetes部署一个应用程序的基本步骤。
- 创建Kubernetes集群:这是第一步,你需要建立一个Kubernetes集群环境。
- 部署应用程序:将你的应用程序部署到刚刚创建的集群中。
- 暴露服务端口:将应用程序的内部端口暴露出来,以便外部(如网页浏览器或移动客户端)可以访问。
- 自动扩缩容:当流量增加,超出当前环境的处理能力时,可以配置应用程序自动横向扩展。
- 持续更新:通过持续交付流程,将代码变更自动推送到集群,实现应用更新。
集群架构解析
上一节我们介绍了基本工作流程,本节中我们来看看支撑这些流程的Kubernetes集群架构。一个Kubernetes集群由多个组件构成。
整体架构如下图所示,其中节点(Node) 是运行容器化应用的工作机器。

以下是架构中的核心概念:
- 容器(Container): 应用运行的基本单元,通常采用Docker格式。
- Pod: Kubernetes中最小的可部署单元。一个Pod可以包含一个或多个紧密相关的容器,这些容器共享网络和存储资源。
- 节点(Node): 一个物理机或虚拟机,用于运行Pod。一个节点上可以运行多个Pod。
- 控制平面(Master): 集群的大脑。它通过Kubernetes API来管理和编排所有节点上的工作。你可以将其理解为你系统的“指挥中心”,负责调度、启动、停止容器等任务。
运行环境与示例
Kubernetes可以在多种环境中运行。正如之前提到的,你可以在各大云服务商(AWS, GCP, Azure)的托管服务上运行。此外,你也可以在本地运行它。
例如,使用Docker Desktop可以在Windows或Mac上轻松安装一个本地Kubernetes环境。对于高级用户,可以使用kubectl命令行工具配合curl命令进行安装。
以下是一个简单的本地Kubernetes应用示例:你可以创建一个服务(Service)在端口8080上暴露你的应用,并在其后端配置端点(Endpoints)。你还可以部署一个独立的数据库。
部署命令可能类似于:
docker stack deploy -c docker-compose.yml myapp
这允许你在自己的笔记本电脑上运行复杂的Kubernetes应用。
核心特性:自动扩缩容
Kubernetes的一个杀手级特性是能够根据负载自动扩缩容。这是通过水平Pod自动扩缩器(Horizontal Pod Autoscaler, HPA) 实现的。
其工作原理如下图所示:

HPA控制循环会持续监控系统指标,例如CPU和内存使用率。当某个指标(如CPU利用率)达到预设的阈值时,HPA会自动增加Pod的副本数量,从而横向扩展应用。当负载降低时,它也会相应地减少副本数量。
这种基于健康指标动态调整资源的能力,是Kubernetes成为卓越任务管理系统的重要原因。


本节课中我们一起学习了Kubernetes的核心概念。简而言之,Kubernetes是一个容器编排系统,它将容器组织在由控制平面管理的集群架构中。容器被隔离运行在Pod里,而Kubernetes正是那个掌控全局、负责调度和扩缩容的“指挥家”。希望本节能帮助你揭开Kubernetes的神秘面纱,理解其底层是一个容器以及一个编排该容器的系统。
092:Kubernetes核心概念 🚢

在本节课中,我们将学习Kubernetes的几个核心概念。这些概念是理解和使用Kubernetes进行容器编排的基础。我们将逐一介绍集群、部署、探索、暴露、扩展和滚动更新,并解释它们如何协同工作以管理容器化应用。
集群(Cluster)
首先,我们来讨论集群。集群的核心概念是一组由API控制的节点集合。
这个集群可以运行在你的虚拟机上,也可以存在于基于云的环境中,或者在你自己的数据中心里。集群具备可扩展性,这意味着你可以根据需要增加或减少节点数量。
部署(Deployment)
上一节我们介绍了集群,本节中我们来看看如何将应用部署到集群中。部署是指将容器化应用程序移入集群并启动它的过程。
这是一种非常常见的实践。以下是部署的典型步骤:
- 你可以从一个公共容器注册中心(如DockerHub)获取容器镜像。
- 然后将该镜像移入你的部署系统,并在Kubernetes集群中启动它。
探索(Exploring)
一旦你的应用部署完成并运行起来,下一步就是探索和迭代。这意味着你可以对已部署的应用程序进行测试、调试和功能迭代,以不断改进它。
暴露(Exposing)
在应用部署并经过初步探索后,通常需要将其提供给外部用户使用。暴露的概念就是将你的应用程序公开到外部世界。
具体做法是通过一个公共端口来提供服务,使其他用户或系统能够访问你的应用。
扩展(Scaling)
当应用对外提供服务后,可能会面临流量增长的压力。扩展功能使你能够响应特定事件(如CPU使用率过高或内存不足)。
以下是扩展的机制:
- 监控到资源指标达到阈值。
- 自动或手动为已部署的应用程序提供更多资源(例如,增加Pod副本数)。
滚动更新(Rolling Update)
最后,一个非常常见的用例是为你的应用程序发布新版本,即进行滚动更新。
这个过程允许你迭代容器化应用程序的多个版本,实现不停机升级。以下是其工作方式:
- 逐步用新版本的Pod替换旧版本的Pod。
- 确保在更新过程中,服务始终可用。
这些是使用Kubernetes时最常见的一些场景。在接下来的课程中,我们将更深入地探讨其中一些场景。

本节课中,我们一起学习了Kubernetes的六大核心概念:集群、部署、探索、暴露、扩展和滚动更新。理解这些概念是掌握Kubernetes容器编排技术的第一步。
093:Kubernetes Pod与Node

在本节课中,我们将学习Kubernetes中的两个核心概念:Pod(容器组)和Node(节点)。理解它们之间的关系是掌握Kubernetes如何编排和管理容器化应用的基础。
概述
Kubernetes Pod和Node是重要的基础概念。通过理解它们,你将明白Kubernetes如何将你的应用部署到计算资源上。
Pod与Node的关系
上一节我们介绍了Kubernetes的基本架构,本节中我们来看看Pod和Node的具体定义及其关系。
从图中可以看到,一个节点(Node)可以包含多个Pod。节点可以运行在虚拟机、数据中心或云环境中。在这个节点内部,可以运行许多不同的Pod,而每个Pod又可以包含多个容器化的应用、存储卷和IP地址。通常,一个节点内部会运行多个Pod。
以下是关于Pod的几个关键点:
- Pod是一个应用的逻辑主机。
- 它可以包含多个紧密耦合的应用容器。例如,一个前端应用和一个后端应用可以配置在同一个Pod中。
Node的定义与类型
了解了Pod之后,我们来看看它运行的环境——Node。
一个Pod总是运行在一个节点上。在Kubernetes中,节点是工作机器,也称为Worker Machine。
以下是节点的两种类型:
- 它可以是物理机器。
- 也可以是虚拟机。具体类型取决于你所配置的集群类型。
总结

本节课中我们一起学习了Kubernetes的Pod和Node。我们了解到,Pod是容纳一个或多个紧密耦合容器的逻辑单元,而Node是运行Pod的物理或虚拟机。一个Node可以托管多个Pod,这是Kubernetes实现高效资源调度和应用部署的基础。理解这一关系是后续学习更高级Kubernetes概念的关键。
094:Kubernetes集群架构

在本节课中,我们将学习Kubernetes集群的基本架构,了解其核心组件及其协作方式。
概述
Kubernetes集群架构包含几种不同类型的资源。首先,有一个协调整个集群的控制平面。节点则是运行具体工作负载的工作者。
上一节我们介绍了云计算的基本概念,本节中我们来看看Kubernetes如何组织这些计算资源。
核心组件
以下是Kubernetes集群的两个主要组成部分:
- 控制平面:这是集群的大脑,负责协调所有活动。在上图中,它用紫色圆点表示。
- 节点:这些是实际运行应用程序的工作者。集群中有多个节点,它们通过Kubernetes API与控制平面进行通信。
架构详解
从集群示意图中可以看到,所有节点都处于控制平面的管理之下。它们处理不同类型的工作负载,具体取决于您所构建的Kubernetes架构。
一个节点可以运行在物理计算机、虚拟机或集群环境中。理解这一点很重要:Kubernetes集群是一个逻辑上的概念集群,而其物理节点可能分布在多种不同的地理位置或基础设施中。
总结

本节课中我们一起学习了Kubernetes集群的基础架构。我们了解到集群由控制平面和工作节点组成,控制平面负责协调,节点负责执行任务,它们共同通过Kubernetes API协作,形成一个统一的计算资源池。
095:在GKE上部署应用到Kubernetes 🚀
在本节课中,我们将学习如何在Google Kubernetes Engine上部署一个应用程序。我们将从创建集群开始,然后推送应用镜像,最后通过负载均衡器将应用暴露到互联网上。
上一节我们介绍了Kubernetes的基本概念,本节中我们来看看如何实际操作。首先,我们需要理解Kubernetes集群的基本架构。它是一个可以弹性伸缩的复杂系统,由主节点控制多个工作节点,每个工作节点包含多个Pod,而每个Pod又可以运行多个容器。
接下来,我们进入Google Cloud控制台开始设置。
设置计算区域与创建集群


在Google Cloud Shell上运行任何操作的第一步是设置正确的计算区域。这决定了我们的资源将在哪个地理位置被创建和运行。
以下是具体步骤:
- 使用以下命令设置计算区域(例如
us-central1-a):gcloud config set compute/zone us-central1-a - 使用以下命令创建一个名为
cloud-for-data的Kubernetes集群。这个过程可能需要几分钟时间。
此命令会在后台自动配置集群的所有组件,包括主节点和工作节点。gcloud container clusters create cloud-for-data
集群创建成功后,我们可以看到其详细信息,包括名称、位置、主节点版本、IP地址、机器类型、节点版本和节点数量(例如3个)。
认证集群与部署应用
现在集群已经运行,我们需要对其进行认证,以便能够通过 kubectl 命令控制它。
以下是具体步骤:

- 获取集群的认证凭据:
gcloud container clusters get-credentials cloud-for-data - 部署一个示例应用。我们将从Google Container Registry拉取一个名为
hello-server的镜像并创建部署。kubectl create deployment hello-server --image=gcr.io/google-samples/hello-app:1.0
创建服务与访问应用
应用部署完成后,我们需要创建一个Kubernetes服务来暴露它。这里我们将创建一个负载均衡器类型的服务,它将自动处理流量并具备伸缩能力。
以下是具体步骤:
- 将部署的应用通过负载均衡器在端口8080上暴露:
kubectl expose deployment hello-server --type=LoadBalancer --port 8080 - 检查服务的状态,以获取外部访问IP地址。初始状态可能为
Pending。
需要多次运行此命令,直到kubectl get service hello-serverEXTERNAL-IP字段从pending变为一个具体的IP地址(例如35.222.100.99)。 - 使用获得的外部IP地址和端口(
8080)在浏览器中访问应用,例如http://35.222.100.99:8080。此时应能看到应用成功运行的页面。

清理资源
在实验或开发环境完成后,及时清理资源以避免产生不必要的费用非常重要。但在生产环境中,删除集群需要格外谨慎。
以下是删除集群的步骤:
- 运行以下命令删除我们创建的集群:
gcloud container clusters delete cloud-for-data - 在提示确认时输入
y。集群及其所有相关资源将被删除。


本节课中我们一起学习了在Google Kubernetes Engine上部署和管理应用的完整流程。我们首先创建并配置了Kubernetes集群,然后部署了容器化应用,接着通过负载均衡服务将应用暴露给外部访问,最后清理了所有资源。这个过程展示了利用云平台的高级抽象能力,可以相对轻松地运行和管理复杂的Kubernetes应用,这正是云计算的关键优势之一。
096:Kubernetes 演示 🚢
在本节课中,我们将要学习 Kubernetes 的核心概念,并通过一个本地演示来理解其基本工作原理。我们将探讨 Kubernetes 的强大能力与复杂性,并动手运行一个简单的 Kubernetes 应用。
Kubernetes 功能强大,本质上是一个可以运行在“盒子”里的云。例如,在 Google,它每周可以运行数十亿个实例。然而,这种强大的能力也带来了相应的复杂性。接下来,我们来看看一个 Kubernetes 集群究竟是什么。
理解 Kubernetes 集群架构 🏗️
上一节我们介绍了 Kubernetes 的强大与复杂,本节中我们来看看它的基本架构。
一个 Kubernetes 集群可以运行在各种环境中。如果你安装了 Docker Desktop 并启用了 Kubernetes 功能,这便是在本地运行 Kubernetes 集群最简单的方式之一。
集群的核心是 Kubernetes 主节点,它包含了 Kubernetes API。所有操作都通过这个 API 进行,这也是 kubectl 命令行工具能与集群通信的原因。
在集群中,应用的基本调度单元是 Pod。一个集群中通常会有许多 Pod。更复杂的是,每个 Pod 可以包含多个不同的容器。到目前为止,我们主要与单个 Docker 容器打交道,但在大规模系统中,一个 Pod 内部经常会有多个容器协同工作。
以下是 Kubernetes 架构的层级关系:
- 容器:封装应用及其依赖。
- Pod:Kubernetes 中最小的可部署单元,包含一个或多个容器。
- 节点:一个物理机或虚拟机,可以运行多个 Pod。
- 集群:由多个节点组成的集合。
那么,为什么要设计如此复杂的结构?其意义何在?其中一个原因是为了实现职责分离和灵活伸缩。例如,在一个节点上,你可以有独立的 Pod:
- 一个 Pod 运行你的 Web 应用,可以根据其特定的 CPU 或内存需求进行独立伸缩。
- 另一个 Pod 可能专门负责监控,将数据发送到 Prometheus 或 Stackdriver 等监控系统。
- 还可以有一个 Pod 运行关系型数据库或专门的消息队列系统。

这实际上是一种根据功能或资源需求,将自然关联的组件组合在一起的方式。为了降低理解难度,让我们暂时抛开部分复杂性,直接看看如何在桌面上实际使用 Kubernetes。
动手运行本地 Kubernetes 集群 💻
上一节我们了解了集群的理论架构,本节中我们通过一个具体项目来实践。

我将展示一个最终项目的样子。以下是项目结构,包含了我们熟悉的部分:
DockerfileMakefileapp.py
当涉及一系列复杂命令时,我通常的做法是创建一个脚本文件。让我们查看其中一个脚本,例如 run_kubernetes.sh。
这个脚本用于在本地 Kubernetes 集群中运行应用。它的核心步骤如下:
- 设置 Docker 镜像路径。
- 使用
kubectl命令(即与 Kubernetes API 交互)部署应用。这里需要指定应用运行的端口和应用名称标签。 - 运行
kubectl get pods来列出正在运行的 Pod 及其内容。 - 最后,将容器端口转发到宿主机,以便我们能够访问和测试应用。
首先,让我们检查当前是否有 Pod 在运行。执行命令:
kubectl get pods
这个命令允许我们查询集群状态。如果看到有 Pod 在运行(本例中只包含一个容器),说明环境正常。
接下来,我们知道应用最终会监听端口 8000。让我们尝试用 curl 命令访问它,看看当前是否有服务运行。
curl localhost:8000
你会发现没有任何响应,因为端口尚未被转发。现在,让我们运行整个 run_kubernetes.sh 脚本。
脚本执行后,你可能会看到一些提示(例如,Pod 已存在),但关键的是它执行了端口转发命令。现在,我可以让这个转发进程在前台运行,然后打开一个新的终端标签页。
在这个新标签页中,再次尝试运行 curl 命令:
curl localhost:8000
这次,你将看到应用成功响应,端口已被正确暴露。在我看来,这是实验 Kubernetes 的最佳方式之一:将命令逐步写入 Shell 脚本,然后进行调试和把玩。
无法回避的是,Kubernetes 极其复杂,是一项不断发展的技术。掌握它需要技巧,需要一步一步地理解发生的事情。而最佳的学习环境就是尽可能小的本地环境,这样可以限制操作的整体复杂度。
总结 📝
本节课中我们一起学习了 Kubernetes 的基本概念和本地实践。我们了解到 Kubernetes 集群由主节点、节点、Pod 和容器等多个层级构成,其设计允许灵活的资源管理和应用编排。通过一个本地演示脚本,我们实践了如何使用 kubectl 部署应用、查看 Pod 状态以及进行端口转发,从而在最小化的复杂环境中体验 Kubernetes 的核心工作流程。记住,面对复杂技术时,从简单的本地环境开始实验是有效的学习路径。



现在,请尝试在你自己的环境中完成这个实践。
097:容器编排方案对比 🚢

在本节课中,我们将学习在云环境中部署和管理容器化应用的不同方案。我们将对比各种托管容器服务,并理解如何选择最适合生产环境的方案。
概述
在云原生开发中,容器化部署是核心环节。开发者有多种方案来管理基于容器的部署服务,这些方案虽然各有特点,但存在许多相似之处。
开发与构建流程
上一节我们概述了容器编排的整体概念,本节中我们来看看具体的开发和构建流程。典型的流程始于开发环境,经过构建系统,最终到达容器注册表。
以下是开发与构建流程的关键步骤:
- 开发环境:你可能在云端开发环境中工作,例如 AWS Cloud9、Google Cloud 开发环境、云工作站,或者在 GitHub 上进行开发。
- 本地测试与构建:在开发过程中,你可以在本地测试功能并构建容器。
- 生产部署:当应用准备就绪需要部署到生产环境时,你需要通过一个构建系统来推送它。
- 构建系统示例:在 GitHub 上,可以是 GitHub Actions;在 AWS 上,可以是 AWS 构建系统。
- 容器注册表:构建完成后,容器镜像被推送到一个容器注册表。通常,如果你使用某个云提供商,你会使用该提供商的容器注册表(如 AWS ECR、Google Container Registry)。当然,你也可以使用其他公共注册表,例如 Docker Hub。
托管容器服务选择
从容器注册表之后,下一步就是选择托管容器服务。市场上有多种不同的托管容器服务选项。
通常,用户希望使用尽可能高级别的服务,这样在成本和管理效率上更优。这意味着你应该优先考虑云提供商完全托管的服务,而不是自己搭建和维护底层基础设施。
以下是不同云平台上的托管服务示例:
- AWS 平台:与其在虚拟机上自行搭建和管理集群,不如使用 AWS 完全托管的 Kubernetes 服务 EKS。或者,你也可以选择 AWS 自研的容器编排服务 ECS。AWS 上还有许多其他服务能与这些容器服务协同工作。
- 其他云平台:其他云平台的情况类似。例如在 Google Cloud 上,你可以使用其托管的 Kubernetes 服务 GKE。将应用直接推送到这类托管服务中会简单得多,因为云提供商会为你管理服务本身。
- 高阶抽象服务:你甚至可以使用更高级别的服务,例如 Google Cloud Run。这类服务使得向 Kubernetes 部署应用变得极其简单:你只需要提供一个容器镜像,然后运行一条命令,它就能被推送到生产环境。其核心命令类似于:
gcloud run deploy --image [IMAGE_URL]
最佳实践总结
总而言之,这是处理基于云的系统时你应该预期的架构概览。通常,你不应该通过自行管理的 Kubernetes 集群来部署应用,而应该让云提供商的专业团队为你完成繁重的基础设施管理工作。

本节课中,我们一起学习了容器化应用从开发到生产的完整流程,对比了 AWS EKS/ECS 和 Google GKE/Cloud Run 等主流托管容器服务,并明确了利用云平台托管服务以提升效率和降低成本的最佳实践。
098:Minikube FastAPI 演示 🚀

在本节课中,我们将学习如何将一个使用 FastAPI 构建的微服务容器化,并在本地 Kubernetes 环境(Minikube)中部署和运行。我们将从代码结构开始,逐步完成本地运行、容器构建、推送到镜像仓库,最终在 Minikube 集群中部署和访问服务的全过程。
项目结构概述
首先,我们有一个包含 FastAPI 微服务的 GitHub 代码库。该项目包含一个 Dockerfile,用于将应用容器化。

以下是项目的主要组成部分:
main.py:这是微服务的主代码文件。logic目录:该目录包含一些业务逻辑函数。Dockerfile:用于构建应用容器镜像的文件。
深入代码与本地运行
上一节我们介绍了项目的整体结构,本节中我们来看看具体的代码实现,并学习如何在本地运行这个 FastAPI 应用。

在 main.py 文件中,我们首先进行了一些基本的导入和设置。代码定义了一个基础模型,用于端点请求。应用包含几个路由:
- 一个默认路由,返回“Hello World”。
- 一个获取随机水果的路由。
- 一个搜索维基百科的端点,允许通过 POST 请求查询关键词。
- 一个计算器功能,用于展示应用的可能性。

使用以下命令即可在本地运行此应用:
python main.py
应用启动后,将在本地 8080 端口运行。访问根路径 / 会看到“Hello World”。FastAPI 自动提供了 /docs 路径,这是一个 Swagger UI 界面,可用于查看和测试所有 API 端点,无需额外构建前端界面。

容器化应用
现在我们已经能在本地运行应用,接下来看看如何将其容器化,以便在任何支持容器的环境中运行。
项目中的 Dockerfile 使得将应用容器化变得简单。容器化后,我们可以:
- 将镜像推送到容器镜像仓库(如 Docker Hub)。
- 在本地使用 Kubernetes 运行。
- 推送到云端的构建系统,在云环境中运行。


例如,我们可以将构建好的镜像推送到 Docker Hub。之后,任何人都可以通过一条命令拉取并运行这个容器,而无需关心本地环境依赖。
docker run -p 8080:8080 <你的DockerHub用户名>/hello-fastapi

在 Minikube 中部署
虽然容器本身可以独立运行,但在生产环境中,我们通常使用 Kubernetes 来编排和管理容器。本节我们将学习如何在本地 Minikube 集群中部署这个应用。
首先,启动 Minikube 集群并启用指标服务器,以便获取运行指标。
minikube start
minikube addons enable metrics-server
启动 Minikube 仪表盘,可以直观地查看集群状态和应用运行情况。
minikube dashboard
接下来,使用 kubectl 命令基于 Docker Hub 中的镜像创建一个部署。
kubectl create deployment hello-fastapi --image=<你的DockerHub用户名>/hello-fastapi
创建部署后,需要将服务暴露出来,以便从集群外部访问。
kubectl expose deployment hello-fastapi --type=LoadBalancer --port=8080
最后,获取服务的访问 URL。
minikube service hello-fastapi --url
使用此 URL,即可在浏览器中访问运行在 Minikube 集群中的 FastAPI 应用。你也可以使用 curl 命令测试服务是否正常运行。
curl <服务URL>
清理资源
实验完成后,需要清理所创建的资源,这是一个好习惯。
以下是清理步骤:
- 删除服务。
kubectl delete service hello-fastapi - 删除部署。
kubectl delete deployment hello-fastapi - 停止 Minikube 集群。
minikube stop

总结

本节课中我们一起学习了微服务从开发到部署的完整流程。我们首先查看了 FastAPI 微服务的代码结构,并在本地成功运行。接着,我们使用 Dockerfile 将应用容器化,并推送到 Docker Hub 镜像仓库。最后,我们重点演示了如何在本地 Minikube Kubernetes 环境中部署这个容器化应用,包括创建部署、暴露服务以及访问应用。这个过程展示了现代云原生应用开发与部署的基本工作流。
099:微服务架构简介 🚀
在本节课中,我们将学习微服务架构。这是一种在现代云原生架构中非常流行的模式,由小型、专用且自治的服务组成。
上一节我们介绍了云计算的基础概念,本节中我们来看看微服务架构的具体内容。
学习目标
以下是本节课的主要学习目标:
- 应用DevOps最佳实践于微服务:微服务本身是一项重大进步,但它也是更广泛的DevOps实践的一部分。这包括持续交付、持续集成,以及围绕监控和告警的最佳实践。
- 评估不同类型的微服务架构:我们将了解事件驱动、Web服务等不同类型的架构。这些架构的选择可能直接导致项目的成功或失败,具体取决于实施方式。
核心概念:无服务器计算
现在,我们来谈谈一个关键术语:无服务器计算。
无服务器意味着你可以在无需预置服务器的情况下运行代码。这是现代计算时代最伟大的进步之一,因为你无需担心预置机器的底层细节。
一个很好的例子是 AWS Lambda。这是一项基于事件的服务,可以映射到对象创建事件、Web服务事件或AWS平台上的任何事件。
以下是其他类似服务的例子:
- Google Cloud Functions:其架构与AWS Lambda类似,可以映射到不同的事件。
- Azure Functions:也是一个很好的例子,是一项可以映射到不同事件的服务。
总而言之,无服务器是一种新的、事件驱动的、云原生的范式。




本节课中我们一起学习了微服务架构的基本概念及其核心组成部分——无服务器计算。我们了解了如何将DevOps实践应用于微服务,并初步认识了不同类型的微服务架构模式。
100:什么是微服务 🧩

在本节课中,我们将要学习微服务的核心概念、关键特征及其带来的主要优势。微服务是一种软件架构风格,它将应用程序构建为一套小型、独立的服务。
微服务的特征
微服务具备几个不同的特征,我们可以从其特征角度来审视它。
以下是微服务的关键特征:
- 小型化:一个微服务只做一件事,并且做得非常好。
- 自治性:微服务不会同时连接数据库、连接其他服务并将所有东西捆绑在一起。它执行一个特定任务,并且只专注于做好这一件事。例如,每个微服务可以独立地与认证系统通信,或独立地与数据库系统通信。
- 专门化:这些微服务以特定方式执行特定任务,即使与其他服务之间的连接失败,它们也不会因此崩溃,而是能够优雅地处理该错误。
微服务的优势
上一节我们介绍了微服务的特征,本节中我们来看看采用微服务架构能带来哪些好处。
以下是微服务的主要优势:
- 开发速度:很多时候,如果你在处理一个大型应用程序,你必须回溯大量代码,找出某个部分如何与另一部分交互。但如果是一个小型微服务,你可以立即查看它。假设它只有100或200行代码,你就能清楚地知道它的功能。
- 简单性:同样地,由于服务非常小,你能够确切地知道它在运行时发生了什么,并且可以将功能隔离到特定的服务中,例如认证服务、数据库服务或业务逻辑服务。
微服务的本质
简而言之,微服务所做的是将其逻辑映射到一个特定的URL上。因此,在其最简形式下,一个微服务就是一个函数。
这个函数可以用Python、Go或其他语言编写,并映射到一个URL或一个事件上。
微服务的意义
那么,这对我们实际意味着什么呢?这意味着系统具有高度的可靠性,因为每个微服务只做一件事并且做得很好。
总而言之,由于这些特征和优势,微服务是软件工程架构领域的一项巨大进步。


在本节课中,我们一起学习了微服务的定义、核心特征(小型化、自治性、专门化)以及它带来的主要优势(提升开发速度、增强简单性和可靠性)。微服务通过将应用拆分为映射到特定URL或事件的独立函数,实现了软件架构的重要演进。
101:微服务运行实践 🚀

在本节课中,我们将要学习微服务架构中一个核心的实践问题:在哪里运行微服务。这对于设计系统的架构师而言是一个关键决策。
概述
微服务架构将应用程序分解为一系列小型、独立的服务。每个服务都围绕特定业务能力构建,并可以独立开发、部署和扩展。然而,这种架构模式带来了一个新的挑战:如何高效地部署和运行这些分散的服务。本节将探讨几种主流的微服务运行环境。
运行环境的主要类别
微服务的运行环境主要可以分为几个大类。以下是几种常见的选择。
1. 容器环境 🐳
上一节我们介绍了微服务的基本概念,本节中我们来看看第一种运行方式:容器。容器为微服务提供了一个轻量级、可移植的运行环境。
- 容器即服务:你可以将微服务部署到云平台提供的容器托管服务中。例如,在Google Cloud中,有 Cloud Run 服务。这是一种“容器即服务”产品,你可以将微服务推送上去,而无需管理底层基础设施。
- 示例代码:部署命令可能类似于
gcloud run deploy SERVICE_NAME --image gcr.io/PROJECT_ID/IMAGE_NAME。
- 示例代码:部署命令可能类似于
- 容器编排平台:另一种选择是将微服务部署到更复杂的容器编排系统中,例如 Kubernetes。在这种环境下,微服务可以运行在由Kubernetes管理的容器集群内,获得强大的自动化部署、扩展和管理能力。
2. 云原生函数 🌩️
除了容器,云平台本身也提供了原生的事件驱动计算能力,这为运行特定类型的微服务提供了另一种思路。
- 函数即服务:目前所有主流云平台都支持编写一个函数来响应特定事件。这种模式通常被称为“函数即服务”或“无服务器函数”。
- 示例服务:例如,AWS的 Lambda、Google Cloud的 Cloud Functions 或 Azure的 Functions。你只需上传代码,平台会处理运行和扩展。
3. 一体化应用平台 🏗️
最后,我们来看一种更为一体化的部署方式,它简化了从开发到运行的许多环节。
另一种开发微服务的替代方案是使用更全面的平台。例如,Elastic Beanstalk,或者 Google App Engine,亦或是集成了身份验证等功能的更复杂的服务。所有这些平台都可以作为运行微服务的地方。
- 平台即服务:这类服务属于“平台即服务”范畴。它们抽象了基础设施和中间件的管理,让开发者可以更专注于代码本身。

总结

本节课中我们一起学习了微服务部署的几种主要实践路径。我们探讨了在容器环境(如Cloud Run或Kubernetes)中运行微服务,利用云原生函数(如Lambda或Cloud Functions)实现事件驱动架构,以及使用一体化应用平台(如App Engine或Elastic Beanstalk)来简化运维。每种选择都有其适用的场景,架构师需要根据服务的具体需求、团队的技术栈和运维成本来做出决策。
构建大规模云计算解决方案:P102:Flask框架入门 🚀
在本节课中,我们将学习如何使用Flask框架。Flask是一个轻量级的Web框架,也是目前Python中最流行的框架之一。它之所以受欢迎,是因为它专注于一件事并将其做得很好。在云环境中,Flask常用于构建微服务。其核心机制是将一段Python代码(一个函数)映射到一个Web URL路由上。例如,一个HTTP请求到 My domain/name 的路径,会被映射到一个名为 name 的路由,并执行与之关联的代码。
接下来,我们先明确本课的学习目标。我们将使用Python Flask构建微服务,并讨论相关的最佳实践。

同时,我们还需要了解什么是API,因为它在本次课程中会频繁出现。API是定义服务之间交互的一种方式,通常与JSON结合使用。你会经常听到JSON这个术语,它代表JavaScript对象表示法。
现在,让我们深入了解JSON。JSON是一种轻量级的数据交换格式,是API的常用格式。因此,构建微服务的核心组件将包括一个Flask应用程序、API以及JSON数据格式,这些元素共同构成了一个微服务。
核心概念与组件
上一节我们介绍了Flask和微服务的基本概念,本节中我们来看看构建微服务所需的核心组件。
Flask应用:一个Flask应用是Web服务的核心,它负责处理HTTP请求和响应。创建一个基本的Flask应用非常简单,只需几行代码。
from flask import Flask
app = Flask(__name__)
@app.route('/')
def hello_world():
return 'Hello, World!'
API(应用程序编程接口):API定义了不同软件组件之间相互通信的规则。在Web开发中,它通常指一组允许客户端(如浏览器或其他服务)与服务器交互的端点。
JSON(JavaScript对象表示法):JSON是一种用于传输结构化数据的文本格式。它易于人阅读和编写,也易于机器解析和生成。在Flask微服务中,我们经常以JSON格式发送和接收数据。
{
"name": "John Doe",
"age": 30,
"city": "New York"
}
构建你的第一个Flask微服务

了解了核心组件后,本节我们将动手构建一个简单的Flask微服务。
首先,确保你已经安装了Flask。可以通过以下命令安装:
pip install flask
以下是创建一个返回JSON数据的简单微服务的步骤:
- 导入Flask并创建应用实例:这是启动任何Flask项目的第一步。
- 定义路由和视图函数:路由决定了哪个URL会触发哪个函数。视图函数则处理请求并返回响应。
- 运行应用:启动开发服务器,使应用可以在本地访问。

以下是实现上述步骤的完整代码示例:
from flask import Flask, jsonify
app = Flask(__name__)
@app.route('/api/user', methods=['GET'])
def get_user():
# 模拟用户数据
user_data = {
"id": 1,
"name": "Alice",
"email": "alice@example.com"
}
# 使用jsonify将Python字典转换为JSON响应
return jsonify(user_data)
if __name__ == '__main__':
app.run(debug=True)
保存代码后运行它,访问 http://127.0.0.1:5000/api/user,你将看到返回的JSON格式的用户信息。
微服务最佳实践
构建出可运行的微服务只是第一步。为了确保服务的健壮性、可维护性和安全性,我们需要遵循一些最佳实践。以下是几个关键点:
1. 使用蓝图(Blueprints)组织代码
当应用规模增长时,将所有路由放在一个文件中会变得难以管理。Flask的蓝图功能允许你将应用模块化。
2. 配置管理
将配置(如数据库连接字符串、密钥)与代码分离,通常使用环境变量或配置文件来管理。
3. 错误处理
为应用添加适当的错误处理,例如捕获404(页面未找到)或500(服务器内部错误),并向客户端返回清晰的JSON错误信息。
4. 输入验证与序列化
对于接收数据的API端点,务必验证输入数据的有效性和安全性。可以使用库如 marshmallow 或 Pydantic 来简化此过程。
5. 日志记录
添加日志记录有助于调试和监控应用的运行状态。

总结
本节课中我们一起学习了Flask框架的基础知识及其在构建云原生微服务中的应用。我们从Flask的核心概念讲起,介绍了API和JSON的作用,然后一步步构建了一个简单的返回JSON数据的微服务。最后,我们探讨了组织代码、管理配置、处理错误等关键的最佳实践,这些是开发高质量、可扩展微服务的重要基础。掌握这些内容,你就迈出了使用Python和Flask构建大规模云计算解决方案的第一步。
103:Flask框架解析 🐍

在本节课中,我们将学习Flask框架的基础知识。Flask是一个轻量级的Python Web框架,它允许开发者快速构建Web应用和服务。我们将通过分析一个简单的示例应用,了解Flask的核心概念和基本用法。
什么是Flask以及如何使用它?
Flask是一个微框架,其核心设计理念是简洁和灵活。它不强制使用特定的项目结构或库,让开发者可以自由选择组件。
让我们查看官方文档中的一个最小化Flask应用示例。这个示例非常简短。
代码示例:一个最小的Flask应用
from flask import Flask
app = Flask(__name__)
@app.route('/')
def hello_world():
return 'Hello, World!'
在这个应用中,我们首先从flask模块导入Flask类,然后定义一个应用实例。@app.route()装饰器用于创建URL路由,其内部封装的函数包含了该路由的逻辑。
分析一个真实的Flask应用
上一节我们介绍了Flask的基本结构,本节中我们来看看一个更具体的真实世界Flask应用。这里有一个GitHub Codespace中的代码。
代码示例:一个包含更多功能的Flask应用
from flask import Flask
app = Flask(__name__)
@app.route('/')
def hello_world():
print(‘Debugging message’)
return ‘Hello, World!’
@app.route('/echo/<name>')
def echo_name(name):
return f‘Hello, {name}!’
if __name__ == '__main__':
app.run(host='127.0.0.1', port=8080, debug=True)
这段代码包含了Flask应用的样板代码。我们定义了两个路由:根路由‘/’和‘/echo/<name>’。在根路由中,我们可以打印调试信息并返回一条消息。
如果我想实现更复杂的功能(这在现实世界中很常见),比如接受参数,Flask可以轻松做到。
以下是Flask中处理参数的方法:在路由路径中使用尖括号< >包裹参数名,然后在对应的函数中捕获它。函数参数名必须与路由中的参数名匹配。
代码示例:带参数的路由
@app.route('/echo/<name>')
def echo_name(name):
return f‘Hello, {name}!’
当我在这里输出时,返回的字符串会回显我输入的任何名字。
应用启动与调试
另一个需要了解的重要部分是代码末尾的if __name__ == ‘__main__’:块(第16-17行)。这是一个快捷方式,它告诉你的Python代码:如果它作为脚本直接运行,则执行以下操作。
在这个块内部,我们调用app.run()。这指向第2行定义的应用实例。我们告诉它在本地主机(127.0.0.1)的8080端口上运行,并设置调试模式。
那么,我们如何运行这个应用呢?很简单,只需在命令行执行python hello.py(假设文件名为hello.py)。如果已经安装了Flask,它就会在本地运行。
在这个GitHub Codespace环境中,我可以在浏览器中打开它并进行测试。首先,我会测试根路由‘/’,然后测试‘/echo’路由。
第一步,访问根路径。很好,“Hello, World!”显示正常,说明它正在工作。
现在,如果我访问/echo路径,并在URL中输入一个名字,比如Bob。看,它返回了“Hello, Bob!”。我们再试试Sally,同样成功返回“Hello, Sally!”。
通过这个基于路由的方法,我可以快速构建功能完整的Web服务,而且非常简单。整个应用不到20行代码,结构清晰,易于理解。这就是使用像Flask这样的微框架的主要优势。
总结


本节课中我们一起学习了Flask框架的基础。我们了解了Flask是一个轻量级的Web框架,通过定义应用实例和使用@app.route()装饰器来创建路由。我们学习了如何构建一个简单的“Hello, World!”应用,以及如何创建能接受URL参数的路由。最后,我们掌握了使用app.run()方法在本地启动和调试Flask应用的基本流程。Flask的简洁性使得构建Web服务变得快速而高效。
104:Flask微服务改造 🛠️
在本节课中,我们将逐步剖析一个现实的微服务项目。我们将学习如何理解、设置、测试并运行一个基于Flask框架的简单微服务应用。
概述
我们将分析一个名为“flask-change-microservice”的项目。该项目包含一个Flask应用文件、一个测试文件、一个依赖清单和一个Makefile。我们将在一个云端开发环境(GitHub Codespaces)中设置并运行它,但请注意,这些步骤同样适用于任何云平台或本地计算机。
项目结构与设置
首先,我们来看看项目的核心文件。项目根目录下包含以下关键文件:
app.py: Flask应用的主文件。test_app.py: 用于测试应用逻辑的单元测试文件。requirements.txt: 列出项目所需的Python包依赖。Makefile: 包含用于安装、测试和代码检查的便捷命令。
为了运行此项目,我们将使用GitHub Codespaces。这是一个基于Docker容器的云端开发环境,类似于VS Code Online、AWS Cloud9或Google Cloud Shell。我们将在其中创建一个新的代码空间来执行后续操作。
核心应用逻辑解析
上一节我们介绍了项目结构,本节中我们来看看微服务的核心功能代码。
打开app.py文件,我们可以看到它执行一个非常具体的任务:计算找零。以下是核心代码片段:
from flask import Flask, jsonify
app = Flask(__name__)
def change(amount):
# 计算各种面额纸币和硬币的数量
result = {}
# ... (具体的找零计算逻辑)
return result
change函数接收一个金额(浮点数),并返回一个字典,其中包含组成该金额所需的各种纸币和硬币数量。这是一个典型微服务的特征:只做好一件事。
为了验证这个函数的逻辑,我们可以使用交互式Python环境(如IPython)进行测试。首先激活项目创建的虚拟环境,然后安装IPython并导入函数进行测试:
source .venv/bin/activate
pip install ipython
ipython
from app import change
print(change(5.13))
# 输出:{'quarters': 20, 'dimes': 1, 'nickels': 0, 'pennies': 3}
通过这种方式,我们可以快速验证核心业务逻辑是否正确。
构建Flask API端点
理解了核心函数后,我们需要将其包装成一个可以通过HTTP访问的API。Flask框架让这一切变得非常简单。
在app.py中,我们定义了两个路由:
-
根路由 (
/):一个简单的“Hello World”端点,用于验证服务是否运行。@app.route('/') def hello(): return “Change” -
找零路由 (
/change/<dollar>/<cent>):这是主要的API端点。它从URL路径中捕获dollar(美元)和cent(美分)参数,将它们组合成金额,调用change函数,并将结果以JSON格式返回。@app.route('/change/<int:dollar>/<int:cent>') def make_change(dollar, cent): amount = dollar + cent / 100.0 result = change(amount) return jsonify(result)
公式:URL中的参数被组合为最终金额:amount = dollar + cent / 100。
现在,我们可以运行这个Flask应用。在终端中执行:
python app.py
应用将在本地8080端口启动。在Codespaces环境中,我们可以使用“在浏览器中打开”功能来访问它。
访问根URL(例如https://your-codespace-url-8080.app.github.dev/)会看到“Change”。要测试找零功能,可以访问类似/change/5/89的URL,它将返回5.89美元的找零组合。API会返回一个JSON响应,例如:
{"quarters": 23, "dimes": 1, "nickels": 0, "pennies": 4}
测试与质量保证
一个健壮的微服务需要包含自动化测试。本项目提供了一个简单的单元测试文件test_app.py,用于验证change函数在不同输入下的行为是否符合预期。
此外,Makefile封装了常用的开发命令,使得执行测试和代码风格检查变得非常方便。以下是几个关键命令:
make install: 根据requirements.txt安装所有项目依赖。make test: 运行单元测试,并显示测试覆盖率报告。make lint: 运行代码风格检查工具(如Flake8),确保代码符合规范。
通过运行make test和make lint,我们可以快速确认代码逻辑正确且风格良好,这是持续集成和交付中的重要环节。

总结


本节课中我们一起学习了如何构建一个简单的Flask微服务。我们从分析项目结构开始,然后深入理解了核心业务逻辑(找零计算),接着将其封装成RESTful API端点,并通过交互式方式和浏览器进行了测试。最后,我们探讨了如何通过单元测试和代码检查来保证微服务的质量。这个不足50行代码的示例清晰地展示了微服务“单一职责”和“独立部署”的核心思想,为构建更复杂的大型云解决方案奠定了基础。
105:使用Flask在Azure部署微服务 🚀
在本节课中,我们将学习如何使用Flask框架和Python语言,通过Azure命令行界面,快速创建并部署一个简单的微服务。整个过程将涵盖从环境准备、本地测试到云端部署和更新的完整流程。


概述
我们将创建一个基础的“Hello World” Flask应用,并将其部署到Azure应用服务。随后,我们将修改应用代码,添加一个新功能,并学习如何将更新部署到云端。通过本教程,你将掌握使用Azure CLI部署和更新Python微服务的基本方法。
环境准备与代码获取
首先,我们需要在Azure Cloud Shell环境中进行操作。这是一个基于浏览器的命令行工具,预装了Azure CLI和其他必要的工具。
接下来,我们将克隆一个包含初始代码的Git仓库。这为我们提供了一个快速开始的脚手架。
git clone <仓库地址>
克隆完成后,我们进入项目目录。典型的Python项目最佳实践是从创建虚拟环境开始。
python3 -m venv venv
source venv/bin/activate
激活虚拟环境后,我们进入项目目录。可以看到项目结构包含一个应用文件(application.py)和一个依赖文件(requirements.txt)。
安装依赖与本地运行
以下是安装项目所需Python包的步骤。


我们使用pip根据requirements.txt文件安装所有依赖项。

pip install -r requirements.txt
安装完成后,我们需要运行Flask应用。直接运行python application.py可能不会启动Flask开发服务器。Flask提供了一个便捷的方法:设置环境变量。
export FLASK_APP=application.py
flask run
此时,应用将在本地运行。我们可以在Cloud Shell中点击“Web预览”图标,并配置端口为5000,即可在浏览器中预览运行的应用。此时,你将看到一个显示“Hello World”的简单网页。
部署应用到Azure

上一节我们完成了本地测试,本节中我们来看看如何将应用部署到Azure云平台。

我们将使用Azure CLI命令创建一个Azure应用服务。这里我们选择免费的F1定价层。
az webapp up --sku F1 --name <你的唯一应用名称>

注意:应用名称必须在整个Azure中保持唯一。如果名称已存在,命令会失败,需要更换一个名称。
命令执行后,Azure会在后台创建必要的资源组和应用服务环境。完成后,你将获得一个公开可访问的URL。访问该URL,即可看到你的应用已成功运行在云端。
修改应用与测试更新
我们的应用已成功上线。接下来,我们对其进行功能增强,并学习如何部署更新。
我们将打开Cloud Shell中的代码编辑器,编辑application.py文件。原始应用只有一个根路由。现在,我们添加一个新的路由。

@app.route('/marco/<polo>')
def marco_polo(polo):
return polo
这个新路由/marco/<polo>会接收URL路径中的<polo>参数,并将其作为响应返回。例如,访问/marco/hello将返回“hello”。

在部署到云端之前,最好在本地测试新功能。我们再次在本地运行Flask服务器,并通过Web预览测试新路由,确保其按预期工作。
测试无误后,停止本地服务器。现在,我们将本地修改部署到Azure。

az webapp up
此命令会检测本地代码的更改,并将其同步到已部署的Azure应用服务中。部署完成后,再次访问你的应用URL,并测试新的/marco/<polo>路由,确认更新已生效。

总结
本节课中我们一起学习了使用Flask和Azure CLI部署微服务的完整流程。我们从准备环境、安装依赖、本地运行开始,然后使用az webapp up命令将应用部署到Azure应用服务。最后,我们修改了应用代码,并再次使用同一命令将更新部署到了云端。



整个过程展示了Azure平台即服务(PaaS)的便捷性,使得部署和更新微服务变得非常简单直接,并能轻松集成到Azure Pipelines等云原生构建环境中。
106:无服务器微服务简介 🚀
在本节课中,我们将学习如何开发一个无服务器微服务。这是一种用于构建微服务的最新流行技术,它与云计算结合得非常好,因为你无需预置和管理服务器。让我们先了解一下本课的学习目标。
首先,我们将学习如何构建无服务器微服务,并讨论其中涉及的一些最佳实践,包括持续交付。我们还将评估适用于无服务器开发的DevOps最佳实践,这包括如何包含适量的代码、何时应该拆分代码仓库,以及其他有助于你交付高质量微服务的关键知识。
什么是无服务器微服务?🤔
上一节我们介绍了本课的目标,本节中我们来看看无服务器微服务的核心概念。
无服务器计算是一种云计算执行模型,云提供商动态管理机器资源的分配。开发者无需关心服务器,只需专注于编写和部署代码。当我们将这种模式应用于构建微服务时,就得到了“无服务器微服务”。
其核心思想是:每个微服务由一个或多个独立的、事件驱动的函数构成。这些函数通常被称为 Function as a Service。
一个简单的函数代码示例如下(以伪代码表示):
def handle_request(event, context):
# 处理传入的事件(例如HTTP请求)
data = process(event[‘data’])
# 返回响应
return {‘statusCode’: 200, ‘body’: data}
无服务器架构的优势 💪
了解了基本概念后,我们来看看采用无服务器架构来构建微服务有哪些主要优势。
以下是采用无服务器架构的关键优势:
- 无需服务器管理:开发者完全不用操心服务器的配置、扩展、打补丁或维护工作。
- 自动扩展:服务会根据负载(如请求数量)自动、即时地扩展或收缩。
- 按使用付费:你只需为代码实际执行时所消耗的计算资源付费,在空闲时段没有成本。
- 提高开发速度:开发者可以更专注于业务逻辑,而不是基础设施,从而加快开发和部署周期。
开发与部署最佳实践 🛠️
我们已经看到了无服务器架构的优势,但在实际开发和部署过程中,遵循一些最佳实践至关重要。
以下是构建和部署无服务器微服务时的一些核心最佳实践:
- 单一职责原则:每个函数应该只做一件事,并且把它做好。这有助于保持函数小巧、可测试且易于维护。
- 使用外部配置:不要将数据库连接字符串、API密钥等敏感信息硬编码在函数代码中。应使用环境变量或云服务提供的密钥管理服务。
- 实现持续交付:建立自动化的构建、测试和部署流水线。每次代码提交都能自动触发流程,确保快速、可靠地将更改交付到生产环境。
- 合理的代码仓库管理:通常建议为每个独立的无服务器微服务(或一组紧密相关的函数)使用单独的代码仓库。这有助于实现团队自治和独立部署。

总结 📚

本节课中,我们一起学习了无服务器微服务的基础知识。我们首先了解了无服务器计算如何免除服务器管理的负担,并探讨了其自动扩展和按量付费的核心优势。接着,我们回顾了在开发和部署无服务器微服务时应遵循的关键最佳实践,包括保持函数职责单一、管理好配置以及建立持续交付流程。
掌握这些概念,将帮助你利用无服务器技术高效、经济地构建可扩展的云原生微服务。
107:无服务器函数概述 🏠
在本节课中,我们将要学习无服务器架构中函数如何作为事件触发器来工作。我们将通过一个简单的比喻来理解其核心概念,并了解一个函数如何响应多种不同的事件。
核心概念:函数即事件触发器
上一节我们介绍了无服务器架构的基本思想,本节中我们来看看函数在其中扮演的具体角色。无服务器函数的核心工作方式,可以通过一个日常生活中的例子来直观理解。
想象一个带有车库的房子,车库里有一盏灯。这盏灯可以通过多种不同的方式被打开。
以下是三种不同的触发事件:
- 车库门打开事件:当你开车进入车库并按下按钮时,车库门打开,这个动作会同时触发车库灯亮起。这类似于一个事件(如文件上传、API调用)自动触发了函数的执行。
- 手动开关事件:你可以直接走到开关前,手动按下开关来打开灯。这相当于手动调用一个函数,例如通过控制台或命令行工具直接执行。
- 定时器事件:你可以设置一个定时器,让灯在每天午夜12点自动打开,以达到防盗的目的。这对应着定时调度事件,例如使用Cron作业来定期触发函数。


这三种完全不同的事件,最终都作用于同一个工作单元——即这盏灯泡。无服务器函数的工作方式与此完全相同。
关键直觉:单一代码,多种交互方式
这是理解如何构建无服务器函数的最佳直觉之一:你只需编写一段代码,这段代码可以通过多种不同的方式被触发和交互。
在代码层面,这可能体现为一个简单的函数定义,例如:
def garage_light_handler(event, context):
# 处理来自不同事件(开门、手动、定时)的逻辑
print("车库灯已打开")
return {"status": "light_on"}
无论触发事件是来自API网关(手动)、对象存储服务(开门)还是云定时器(定时),最终都会执行这段相同的 garage_light_handler 函数。函数内部的逻辑可以根据传入的 event 参数来判断事件的来源并做出相应处理。


本节课中我们一起学习了无服务器函数作为事件触发器的核心模型。我们通过车库灯的例子,理解了单一函数如何响应多种事件源,包括自动事件、手动调用和定时调度。掌握这种“一段代码,多种触发”的思维模式,是设计和构建高效无服务器应用的基础。
108:构建AWS Lambda Marco Polo函数
在本节课中,我们将学习如何在AWS Lambda上创建一个简单的函数。我们将通过一个名为“Marco Polo”的示例应用,了解Lambda函数的基本创建、代码编辑、部署和测试流程。
概述
AWS Lambda是一项无服务器计算服务,允许您运行代码而无需预置或管理服务器。本节将引导您完成创建第一个Lambda函数的全过程,从控制台搜索服务开始,到编写、部署和测试一个简单的响应函数。
创建Lambda函数
首先,我们需要在AWS管理控制台中创建函数。
- 在AWS管理控制台中搜索“Lambda”服务。
- 进入Lambda服务控制台,点击“创建函数”。
- 您有几个选项:从头开始创建、使用蓝图(学习构建函数的好方法)或查看包含更复杂示例的无服务器应用程序存储库。
- 我们将创建一个基础的Marco Polo应用示例。因此,选择“从头开始创作”。
- 为函数命名,例如
MarcoPolo9000。 - 选择运行时环境,这里我们选择 Python 3.8。
- 在权限设置部分,由于我们仅运行一些Python代码,不涉及调用其他AWS服务API,因此暂时无需设置特殊执行角色,使用默认角色即可。
- 点击“创建函数”。
编辑函数代码
函数创建完成后,我们可以在AWS Lambda控制台内直接编辑和构建代码。
上一节我们介绍了如何创建函数,本节中我们来看看如何编辑其代码逻辑。
- 在函数概览页面,向下滚动找到代码编辑器。
- 编辑器内是默认的示例代码,我们将修改它以实现Marco Polo逻辑。
- 删除默认代码,输入以下内容:
def lambda_handler(event, context):
# 打印接收到的event,便于调试
print(f"This was the event: {event}")
# 检查event中是否包含名为'name'的键,且其值为'Marco'
if event.get('name') == 'Marco':
# 如果匹配,返回 'Polo'
return 'Polo'
else:
# 如果不匹配,返回 'No'
return 'No'
代码解释:
lambda_handler是Lambda函数的入口点。event参数包含了触发函数的事件数据。- 我们使用
event.get('name')安全地获取事件中name字段的值。 - 核心逻辑是一个条件判断:如果
name等于"Marco",则返回"Polo";否则返回"No"。 print语句用于在日志中输出事件内容,有助于调试。
- 编辑完成后,点击“部署”按钮以保存并发布代码更改。
测试函数
代码部署后,我们需要测试其功能是否按预期工作。
以下是测试Lambda函数的步骤:
- 在函数控制台界面,点击“测试”选项卡。
- 首次测试需要配置一个测试事件。点击“创建新事件”。
- 为测试事件命名,例如
MarcoTest。 - 在事件JSON模板中,输入一个包含
name字段的JSON对象:{ "name": "Marco" } - 点击“创建”。
- 保存测试事件后,点击“测试”按钮来调用函数。
- 观察执行结果。在“执行结果”部分,您应该看到返回值为
"Polo",并且在“函数日志”中可以看到打印的event信息。
为了验证函数在非“Marco”输入下的行为,我们可以创建另一个测试事件。
- 再次点击“测试”,选择“配置测试事件”。
- 创建一个名为
BobTest的新事件。 - 在事件JSON中,将
name的值改为"Bob":{ "name": "Bob" } - 点击“测试”按钮。
- 这次,执行结果应返回
"No",因为输入不匹配条件。
配置触发器(进阶)
目前,我们通过控制台手动触发函数。Lambda的强大之处在于能够响应各种事件自动触发。
上一节我们介绍了如何手动测试函数,本节中我们来看看如何为其配置自动触发器。
- 在函数控制台,切换到“配置”选项卡。
- 在左侧导航栏中,选择“触发器”。
- 点击“添加触发器”。
- 您可以从多种触发器类型中选择,例如:
- API Gateway:用于创建HTTP API端点。
- S3:当S3存储桶中发生特定事件(如文件上传)时触发。
- DynamoDB:当DynamoDB表数据变更时触发。
- SNS(简单通知服务)或 SQS(简单队列服务):响应消息时触发。
- 选择所需的触发器类型并进行相应配置(此步骤因触发器类型而异,本基础教程不深入展开)。
核心概念:通过配置触发器,您的Lambda函数可以从被动执行转变为事件驱动的自动化部署。函数将监听特定事件源,并在事件发生时自动运行。
总结


本节课中我们一起学习了AWS Lambda的基础操作。我们完成了从创建函数、编写Python代码(实现一个简单的Marco Polo响应逻辑)、部署更改到手动测试函数的全过程。最后,我们还了解了如何通过配置触发器,将函数与AWS的其他服务(如S3、API Gateway等)连接起来,实现基于事件的自动执行。这为构建更复杂、自动化的大规模云应用奠定了基础。
109:构建Marco Polo状态机 🚀
在本节课中,我们将学习AWS Step Functions,这是一种编排不同Lambda函数以协同工作的服务。我们将通过一个简单的“Hello World”示例和一个更复杂的“Marco Polo”示例,来理解如何构建、运行和调试状态机。
概述
AWS Step Functions 是一种用于协调多个AWS服务(尤其是Lambda函数)的工作流服务。它允许您以可视化的方式设计复杂的工作流程,其中包含顺序执行、条件分支、错误处理等逻辑。本节将引导您创建并运行两个Step Functions示例,以掌握其核心概念。
理解Step Functions
上一节我们介绍了云计算的宏观概念,本节中我们来看看具体的编排工具。AWS Step Functions的核心是状态机。一个状态机由多个状态(步骤)组成,定义了工作流的执行逻辑。
您可以将它理解为一个流程图。例如,一个工作流可能先获取数据,然后根据不同的操作类型,选择不同的处理路径。这就是Step Functions的本质。
构建“Hello World”示例
现在,让我们通过一个“Hello World”示例来具体了解如何操作。我们将创建一个简单的状态机,并观察其逐步执行的过程。
首先,在AWS控制台中创建一个新的状态机。我们将其命名为“HelloWorld”,并创建一个新的执行角色。状态机的定义使用Amazon States Language (ASL),这是一种基于JSON的格式。
以下是一个简化的状态机定义代码示例,它包含一个等待状态和一个成功结束状态:
{
"Comment": "一个简单的Hello World示例",
"StartAt": "Hello",
"States": {
"Hello": {
"Type": "Task",
"Resource": "arn:aws:lambda:REGION:ACCOUNT_ID:function:HelloFunction",
"Next": "Wait"
},
"Wait": {
"Type": "Wait",
"Seconds": 3,
"Next": "World"
},
"World": {
"Type": "Succeed"
}
}
}
创建完成后,我们启动一个执行。初始输入载荷(payload)可以是简单的JSON,例如 {"message": "Hello World"}。启动执行后,您可以直观地看到每个步骤的状态变化(例如,“正在运行”、“成功”)。
Step Functions的一个强大功能是提供了详细的执行历史记录。对于每个步骤,您可以:
以下是您可以查看的调试信息:
- 输入:查看进入该步骤的确切数据。
- 输出:查看该步骤执行后产生的数据。
- 错误信息:如果步骤失败,可以查看具体的错误原因。
例如,在“Hello”步骤中,您可以看到输入的 {"message": "Hello World"},这为调试提供了极大的便利。
构建“Marco Polo”状态机
理解了基础示例后,我们来构建一个更复杂、能体现状态间数据传递的“Marco Polo”状态机。这个状态机将串联两个Lambda函数,实现一个简单的“喊话-回应”逻辑。
在AWS控制台中,我们找到名为“MarcoSimple”的状态机模板并编辑它。其工作流非常直观:
以下是“Marco Polo”状态机的步骤:
- Marco函数:第一个Lambda函数。它接收输入,检查其中是否包含特定的关键词。
- Polo函数:第二个Lambda函数。它接收上一个函数的输出作为输入,并进行处理。
- 结束:成功完成整个工作流。
现在,让我们运行它。首先,我们直接启动执行,但使用一个空的或无效的输入(例如 {})。不出所料,执行在“Marco”函数处失败了。通过可视化界面,我们可以清晰地看到失败发生在哪一步,并查看该步骤的输入。
为了深入排查,我们可以点击失败的Lambda函数链接,直接查看其代码。代码逻辑很简单:它检查输入事件中的 name 字段,如果值是 "marco",则返回 "polo";否则会抛出错误。
# Marco Lambda函数示例代码
def lambda_handler(event, context):
# 检查输入中是否有‘name’字段且值为‘marco’
if event.get('name') == 'marco':
return {'response': 'polo'}
else:
raise ValueError('Name must be "marco"')
了解了逻辑后,我们重新执行,这次提供正确的输入:{"name": "marco"}。启动执行后,我们可以看到流程成功运行:
以下是成功的执行流程:
- 步骤1:输入
{"name": "marco"}传递给Marco函数。函数识别出"marco",并输出{"response": "polo"}。 - 步骤2:上一步的输出
{"response": "polo"}作为输入传递给Polo函数。一个对应的Polo函数会接收"polo"并返回"marco",完成一次“对话”。 - 步骤3:状态机成功结束。
这个例子展示了如何将多个无服务器函数组合在一起,并让数据在它们之间流动。
总结
本节课中我们一起学习了AWS Step Functions的核心用法。我们了解到,Step Functions是编排Lambda函数构建复杂工作流的强大工具。通过“Hello World”示例,我们学会了创建、执行和调试状态机的基本方法。通过“Marco Polo”示例,我们进一步掌握了如何设计让数据在不同状态间传递的工作流,并利用可视化工具进行高效的故障排查。总之,Step Functions是学习Lambda函数组合和构建健壮无服务器应用的重要途径。




110:构建AWS S3存储桶触发器 🚀
在本节课中,我们将学习如何构建一个基于AWS S3存储桶的事件驱动工作流。具体来说,我们将了解如何配置S3存储桶,使其在对象被创建时自动触发一个AWS Lambda函数,并利用该函数调用Amazon Rekognition服务进行图像识别。
概述
事件驱动架构是现代云应用的核心模式之一。AWS S3触发器是实现这一模式的常见方式,它允许我们在存储桶中的对象发生变化(如上传新文件)时,自动执行一段代码逻辑。本节课将演示一个典型的计算机视觉工作流:当一张图片被上传到S3存储桶时,自动触发Lambda函数,该函数调用Amazon Rekognition服务识别图片内容并返回标签。
S3触发器与Lambda的工作流程
上一节我们介绍了课程目标,本节中我们来看看整个工作流的具体构成。
整个流程始于用户向指定的S3存储桶上传一个文件(例如一张图片)。这个上传操作会产生一个“对象创建”事件。该事件会被配置好的S3触发器捕获,并作为调用请求传递给一个预先定义好的AWS Lambda函数。
Lambda函数被触发后,会执行其内部的代码。在我们的案例中,这段代码的核心任务是调用Amazon Rekognition服务的图像识别功能。函数需要从事件参数中提取出刚上传文件所在的存储桶名称和文件名称,并将这两个参数传递给Rekognition服务。
以下是Lambda函数处理事件的关键步骤:
- 解析事件:Lambda函数接收到的
event参数包含了触发它的S3事件的所有详细信息。 - 提取文件信息:从
event记录中循环遍历,获取每个新增文件的存储桶名和对象键(文件名)。 - 调用识别服务:使用提取出的信息,调用
rekognition.detect_labelsAPI。 - 处理结果:接收Rekognition返回的识别标签(例如“狮子”、“熊”),并可根据业务需求进行后续处理,如将结果存入数据库或发送通知。
其核心逻辑可以用以下伪代码表示:
def lambda_handler(event, context):
for record in event[‘Records’]:
bucket = record[‘s3’][‘bucket’][‘name’]
key = record[‘s3’][‘object’][‘key’]
response = rekognition_client.detect_labels(
Image={‘S3Object’: {‘Bucket’: bucket, ‘Name’: key}}
)
labels = response[‘Labels’]
# 对识别出的标签进行后续处理
配置S3触发器
理解了工作流程后,我们需要在AWS控制台中完成实际配置。这个过程将把S3存储桶和Lambda函数关联起来。
以下是配置S3触发器的具体步骤:
- 打开目标Lambda函数的配置页面。
- 在函数概览页找到并点击“添加触发器”。
- 在触发器选择列表中,选择“Amazon S3”。
- 在配置界面中,指定要监听的S3存储桶。
- 选择事件类型,例如“所有创建事件”,这样任何形式的上传都会触发Lambda。
- 保存配置,完成触发器的添加。
配置成功后,在Lambda函数的触发器列表中可以查看到已添加的S3触发器,确认其状态为“启用”。
实战演示与验证
配置完成后,我们可以通过一个简单的测试来验证整个工作流是否正常运行。
首先,我们向配置了触发器的S3存储桶上传一张测试图片,例如一张狮子的照片。上传操作完成后,系统会自动触发关联的Lambda函数。
为了验证Lambda函数确实被调用并执行成功,我们需要查看其运行日志。在Lambda控制台,进入该函数的“监控”选项卡,点击“查看CloudWatch日志”。在日志流中,我们可以搜索到最近函数执行的记录。
成功的日志会显示函数被调用的时间戳,并打印出从Rekognition服务返回的识别标签,例如 ‘Labels’: [‘Lion’, ‘Animal’, …]。这证明从S3事件触发到图像识别完成的整个自动化链路已成功运行。
总结


本节课中我们一起学习了如何构建一个基于AWS S3触发器的事件驱动工作流。我们掌握了其核心概念:S3存储桶的事件如何自动触发Lambda函数执行。我们通过一个图像识别的实际案例,演示了在Lambda函数中解析事件参数、调用rekognition.detect_labels API以及处理返回结果的完整过程。最后,我们完成了从控制台配置触发器到上传文件测试验证的全流程。这个模式将复杂的后端逻辑变得简单可控,是构建无服务器应用和自动化工作流的强大工具。
111:通过CLI触发Lambda函数 🚀
在本节课中,我们将学习如何通过命令行界面(CLI)来调用AWS Lambda函数。虽然控制台提供了便捷的测试方式,但通过CLI调用能赋予脚本和自动化流程更强大的能力。
概述
上一节我们介绍了在AWS控制台中测试Lambda函数。本节中,我们来看看如何通过AWS命令行工具实现相同的调用功能,并将其集成到自动化脚本中。
通过CLI调用Lambda函数
首先,我们回顾一下示例Lambda函数的功能。该函数接收一个包含name字段的事件对象。如果name的值是“Marco”,函数将返回“Polo”。
在控制台中,我们可以通过配置测试事件来验证此功能。
以下是测试事件的JSON结构示例:
{
"name": "Marco"
}
运行测试后,函数应返回“Polo”。
使用AWS CLI进行调用
现在,我们转向命令行界面执行相同的操作。在Cloud9等集成开发环境中,AWS命令行工具通常已预装,这为开发提供了便利。
以下是调用Lambda函数的AWS CLI命令基本格式:
aws lambda invoke \
--function-name <你的函数名称> \
--payload '<JSON格式的事件数据>' \
output.txt
--function-name: 指定要调用的Lambda函数的名称。--payload: 提供传递给函数的JSON格式事件数据。output.txt: 指定一个文件名,命令会将函数的响应输出写入此文件。
为了立即查看结果,我们可以在命令后使用管道(|)和cat命令打印文件内容。
让我们看一个具体的调用示例。假设函数名为MyTestFunction。
使用“Marco”作为输入的调用命令如下:
aws lambda invoke --function-name MyTestFunction --payload '{"name":"Marco"}' output.txt && cat output.txt
执行后,终端应显示返回结果“Polo”。
接下来,我们尝试使用不同的输入值“Bob”进行调用:
aws lambda invoke --function-name MyTestFunction --payload '{"name":"Bob"}' output.txt && cat output.txt
根据函数逻辑,此次调用将不会返回“Polo”。通过对比不同输入的结果,我们可以验证函数的行为是否符合预期。
优势与应用场景
通过命令行调用Lambda函数的核心优势在于其可脚本化和自动化能力。
以下是几个典型的应用场景:
- 批量处理:在循环脚本中多次调用函数,处理大量数据。
- 集成测试:将Lambda调用作为持续集成/持续部署(CI/CD)流水线中的一个步骤。
- 系统集成:从其他命令行工具或脚本中触发Lambda函数,构建工作流。
总结


本节课中我们一起学习了通过AWS命令行界面调用Lambda函数的方法。我们回顾了函数逻辑,掌握了aws lambda invoke命令的基本用法,并通过不同输入验证了函数行为。最后,我们探讨了CLI调用方式在自动化脚本和分布式任务处理中的强大潜力。掌握此技能,能帮助你更灵活地将Lambda函数集成到各类自动化解决方案中。
112:Google Cloud Function 变更实践 💰
在本节课中,我们将学习如何使用 Google Cloud Functions 这一无服务器技术,创建一个名为“找零机”的函数,并通过多种方式触发和调用它。
Google Cloud Functions 是一种无服务器技术,它允许你将一段逻辑映射到一个函数,并通过触发器来调用它。在本例中,我们将在 Google Cloud Platform 内部创建一个函数。
创建函数
首先,在 Google Cloud Platform 中选择 Cloud Functions 服务。我们将创建一个新函数。
以下是创建函数的主要步骤:
- 命名函数:将函数命名为
change_machine。 - 选择区域:为函数选择一个部署区域。
- 选择触发器类型:选择 HTTP 触发器,这允许我们通过 Web 接口调用它。
- 设置身份验证:选择“允许未经身份验证的调用”,以便将其用作常规的、无需身份验证的 Web 服务。
- 保存并继续:点击“保存”,然后进入下一步。
配置运行时与代码
接下来,我们需要为函数选择运行时环境并编写代码。
以下是配置运行时和代码的步骤:
- 选择运行时:从多种运行时中选择,例如 .NET (C#)、Go、Java、Node.js 或 Python。这里我们选择 Python 3.8。
- 使用内联编辑器:平台提供了方便的内联编辑器,并允许安装第三方包。
- 编写函数代码:我们将实现一个简单的“找零机”逻辑。该函数接收一个包含
amount字段的 JSON 载荷,计算并返回最优的硬币找零组合(优先使用大面额硬币)。
我们将替换掉默认的样板代码。函数的入口点(即被调用时执行的函数)需要正确设置。代码如下所示:
import json
def make_change(request):
"""HTTP Cloud Function.
Args:
request (flask.Request): The request object.
Returns:
The response text, or any set of values that can be turned into a
Response object using `make_response`
<http://flask.pocoo.org/docs/1.0/api/#flask.Flask.make_response>.
"""
request_json = request.get_json(silent=True)
if request_json and 'amount' in request_json:
amount = float(request_json['amount'].replace('$', ''))
else:
return json.dumps({"error": "Please provide an 'amount' in JSON payload."})
cents = int(amount * 100)
quarters = cents // 25
cents %= 25
dimes = cents // 10
cents %= 10
nickels = cents // 5
cents %= 5
pennies = cents
result = {
"quarters": quarters,
"dimes": dimes,
"nickels": nickels,
"pennies": pennies
}
return json.dumps(result)
确认代码和入口点正确后,点击“部署”按钮。
在控制台测试函数
函数部署完成后,我们可以在 Google Cloud 控制台内对其进行测试。
以下是测试步骤:
- 转到函数的“测试”标签页。
- 在“触发事件”部分,提供一个 JSON 载荷,例如
{"amount": "$1.34"}。 - 点击“测试函数”。
测试成功后,函数将返回计算结果,例如 {"quarters": 5, "dimes": 0, "nickels": 1, "pennies": 4}。我们可以尝试输入不同的金额进行多次测试,以验证其功能。

通过命令行调用函数
除了在 Web 控制台测试,我们还可以通过命令行工具调用此函数。这展示了 Cloud Functions 如何集成到自动化工作流中。

以下是使用 gcloud 命令行工具调用函数的步骤:

- 打开 Cloud Shell。
- 使用以下命令格式调用函数,并传递
amount参数:gcloud functions call change_machine --data '{"amount":"$1.34"}' - 首次调用时,可能需要登录授权。按照提示完成登录流程。
调用成功后,你将在命令行中看到相同的 JSON 格式结果。这种方式使得该函数可以被用于数据处理、机器学习预处理或并行操作等自动化任务中。
通过外部 HTTP 请求调用函数
由于我们的函数配置了 HTTP 触发器且允许未经身份验证的调用,因此任何能访问互联网的设备都可以通过 HTTP POST 请求来调用它。

以下是使用 curl 命令从外部调用的方法:

- 在函数详情页找到并复制其触发 URL。
- 在命令行中使用
curl命令向该 URL 发送 POST 请求和 JSON 数据:
请将 URL 替换为你自己的函数 URL。curl -X POST https://YOUR_REGION-YOUR_PROJECT.cloudfunctions.net/change_machine \ -H "Content-Type: application/json" \ -d '{"amount": "$1.34"}'
调用成功后,你将收到来自函数的找零结果。这证明了 Cloud Functions 可以作为公开的 Web 服务使用。


本节课中我们一起学习了 Google Cloud Functions 的核心实践。我们创建了一个“找零机”函数,并通过三种方式成功调用:在云控制台测试、使用 gcloud 命令行工具、以及通过外部的 curl HTTP 请求。这充分展示了 Cloud Functions 响应事件、集成到命令行工作流以及作为简单 Web 服务使用的灵活性和强大能力。
113:使用AWS Lambda控制台

概述
在本节课中,我们将学习如何在AWS Lambda控制台中构建和测试两个简单的Lambda函数。第一个函数负责加法运算,第二个函数负责将结果除以2。我们将使用Python语言进行快速原型开发,并了解如何在控制台内编写、部署和测试代码。
构建第一个Lambda函数:加法运算
上一节我们介绍了课程目标,本节中我们来看看如何创建第一个执行加法运算的Lambda函数。
首先,我们需要进入AWS控制台并创建函数。为了节省成本,建议选择ARM架构,这是最经济的选项。运行时环境选择最新支持的Python 3.11版本。
我们将这个函数命名为 add,然后点击创建函数。
使用Python进行原型开发的一个优点是,即使你后续计划将代码转换为Rust等其他语言,也可以在控制台中直观地查看和测试逻辑。因此,Python非常适合作为快速原型设计的工具。
以下是 add 函数的代码实现:
import json
def lambda_handler(event, context):
x = event['x']
y = event['y']
total = x + y
return {
'statusCode': 200,
'body': json.dumps({
'total': total
})
}
代码逻辑非常直接:从传入的事件(event)中提取 x 和 y 的值,将它们相加,然后将结果以JSON格式返回。
测试第一个Lambda函数
代码编写完成后,我们需要部署并进行测试。
点击“部署”按钮来部署函数。接着,我们需要配置一个测试事件来验证函数逻辑。
以下是配置测试事件的步骤:
- 创建一个新的测试事件,命名为
add。 - 在事件负载(payload)中,提供
x和y的值。例如:{"x": 10, "y": 20}。 - 保存测试事件并执行测试。
测试时可能会遇到代码错误,例如缩进或语法问题。这是开发过程中的常见情况。如果测试失败,检查并修正代码后重新部署,再次测试即可。
当测试成功时,函数将返回计算结果:{"total": 30}。
构建第二个Lambda函数:除以2
现在,我们已经成功创建并测试了加法函数。接下来,我们将创建第二个函数,它接收第一个函数的输出,并将结果除以2。
让我们返回函数列表页面,创建第二个函数。
我们将这个函数命名为 divide_by_2。同样,为了节省成本,选择ARM架构和Python 3.11运行时。
以下是 divide_by_2 函数的代码:
import json
def lambda_handler(event, context):
# 假设输入是第一个函数返回的JSON字符串
body = json.loads(event['body'])
total = body['total']
result = total / 2
return {
'statusCode': 200,
'body': json.dumps({
'result': result
})
}
这个函数解析来自第一个函数的响应体,取出 total 值,执行除以2的运算,然后返回新的结果。
测试第二个Lambda函数
与测试第一个函数类似,我们需要为 divide_by_2 函数配置一个测试事件。
以下是配置测试事件的步骤:
- 创建一个新的测试事件,例如命名为
payload。 - 在事件负载中,模拟第一个函数的输出。例如:
{"body": "{\"total\": 30}"}。 - 保存测试事件,部署函数,然后执行测试。
测试成功后,函数将返回计算结果:{"result": 15.0}。

总结
本节课中,我们一起学习了如何在AWS Lambda控制台中构建和测试两个简单的函数。我们使用Python进行了快速原型开发,创建了执行加法运算的 add 函数和执行除法运算的 divide_by_2 函数。我们掌握了在控制台内编写代码、部署函数以及配置测试事件进行验证的完整流程。这些独立的函数为后续使用AWS Step Functions等无服务器编排工具进行组合调用奠定了基础。
114:使用 AWS Step Functions 编排无服务器函数

在本节课中,我们将学习如何使用 AWS Step Functions 来编排和协调多个 AWS Lambda 函数,构建一个简单的分布式应用程序。我们将通过一个具体的例子,演示如何将两个独立的 Lambda 函数连接成一个有序的工作流。
概述
AWS Step Functions 是一项无服务器编排服务,它允许您将多个 AWS 服务(如 Lambda)组合成可维护的工作流。本节我们将创建一个状态机,依次调用一个加法函数和一个除法函数,并观察数据如何在它们之间传递。
准备工作
首先,我们需要确认已经创建了两个 Lambda 函数。以下是这两个函数:
add:一个执行加法运算的函数。divide_by_2:一个将输入值除以 2 的函数。
创建 Step Functions 状态机
上一节我们介绍了所需的 Lambda 函数,本节中我们来看看如何将它们编排起来。
- 打开 AWS Step Functions 控制台,点击“创建状态机”。
- 选择“使用可视化编辑器设计工作流”选项,这是一个非常直观的原型设计工具。
- 从左侧的组件面板中,将一个 “任务” 状态拖拽到设计画布中。
- 将这个状态命名为
add。 - 在状态配置中,将“集成类型”设置为 AWS Lambda,并在“API 参数”下的“FunctionName”字段中,选择我们之前创建的
add函数。 - 重复步骤 3-5,添加第二个“任务”状态。将其命名为
divide_by2,并关联到divide_by2Lambda 函数。 - 使用箭头连接这两个状态,定义执行顺序:首先是
add,然后是divide_by2。
完成设计后,点击“下一步”,查看自动生成的 Amazon States Language (ASL) 定义代码。确认无误后,再次点击“下一步”。
为状态机命名,例如 AddAndDivide,然后点击“创建状态机”。
执行与验证
状态机创建完成后,我们可以立即测试它。
- 在状态机详情页,点击“开始执行”。
- 在输入对话框中,我们需要提供一个符合 Lambda 函数预期的 JSON 负载。对于我们的
add函数,它需要两个数字参数。因此,我们输入以下内容:{ "x": 10, "y": 20 } - 点击“开始执行”。
执行开始后,您可以实时观察工作流的进展。Step Functions 界面会显示每个步骤的输入和输出,这是其强大的调试功能。
- 第一步 (
add):输入是{"x": 10, "y": 20}。输出结果应为{"total": 30}。这个输出会自动成为下一步的输入。 - 第二步 (
divide_by2):输入是上一步的输出{"total": 30}。divide_by2函数处理这个输入,最终输出应为{"result": 15}。
通过这个流程,您可以清晰地看到数据如何从一个函数传递到另一个函数。
核心优势
使用 AWS Step Functions 进行编排的主要优势包括:
- 可视化与可维护性:工作流以图形化方式呈现,逻辑清晰,易于理解和修改。
- 内置调试:可以精确查看每一步的输入和输出,快速定位问题。
- 可重复性与可靠性:状态机管理着函数执行的状态、重试和错误处理,使整个流程更健壮。
- 灵活编排:您可以轻松地串联、并行运行或基于条件分支来组织 Lambda 函数,构建复杂的数据工程或机器学习工作流。
总结

本节课中我们一起学习了如何使用 AWS Step Functions 来协调多个 AWS Lambda 函数。我们创建了一个简单的状态机,将加法函数和除法函数串联起来,并通过具体的输入验证了整个工作流的执行过程。Step Functions 提供的可视化设计、状态管理和调试功能,使其成为构建下一代无服务器应用程序,特别是数据流水线和机器学习工作流的强大工具。
115:通过CLI调用Step Functions 🚀

在本节课中,我们将学习如何通过AWS命令行界面(CLI)来调用和运行Step Functions状态机。这是一种实现程序化控制、测试工作流的高效方法。
上一节我们介绍了Step Functions的基本概念和图形化控制台操作。本节中我们来看看如何通过命令行实现更灵活的执行与控制。
启动AWS Cloud Shell
首先,我们需要一个可以执行AWS命令的环境。AWS Cloud Shell是一个便捷的在线终端。
以下是启动Cloud Shell的步骤:
- 在AWS管理控制台中,找到并点击顶部导航栏的Cloud Shell图标。
- 系统将自动为您启动一个预配置好AWS CLI的终端环境。

使用CLI命令执行状态机

在Cloud Shell中,我们可以使用aws stepfunctions start-execution命令来触发一个状态机的执行。

该命令的核心结构如下:
aws stepfunctions start-execution --state-machine-arn <您的状态机ARN> --input <您的输入JSON>
命令包含两个关键参数:
--state-machine-arn:用于指定要执行的状态机。其值是一个唯一标识资源的ARN。--input:用于向状态机传递输入数据。其值是一个JSON格式的字符串。
实际操作演示

现在,让我们跟随操作步骤,实际执行一次状态机。
- 获取状态机ARN:在Step Functions控制台中找到目标状态机,复制其ARN。
- 构造输入数据:准备一个JSON字符串作为输入,例如
{"value1": 10, "value2": 16}。 - 执行命令:在Cloud Shell中粘贴并运行组合好的命令。例如:
aws stepfunctions start-execution --state-machine-arn arn:aws:states:us-east-1:123456789012:stateMachine:MyStateMachine --input '{"value1": 10, "value2": 16}' - 验证执行结果:命令执行成功后,会返回一个执行ARN。您可以回到Step Functions控制台刷新页面,查看新增的执行记录,并检查其输入、输出和每一步的执行详情。

进行迭代测试
CLI调用的优势在于便于快速进行迭代测试和修改。

例如,我们可以通过键盘的“上箭头”键调出刚才执行的命令,修改--input参数中的数值,然后再次运行命令。
# 修改输入值后再次执行
aws stepfunctions start-execution --state-machine-arn arn:aws:states:us-east-1:123456789012:stateMachine:MyStateMachine --input '{"value1": 13, "value2": 13}'
每次执行后,都可以在控制台中看到新的记录,从而形成一个“执行 -> 观察结果 -> 调整输入 -> 再次执行”的快速反馈循环。
方法优势总结
使用AWS CLI和Cloud Shell调用Step Functions,是一种非常高效的工作方式。
以下是其主要优点:
- 程序化控制:便于集成到脚本或自动化流程中。
- 快速测试:无需编写完整的SDK代码,即可快速验证工作流逻辑和输入输出。
- 即时反馈:结合控制台可视化界面,能立即查看每次执行的详细结果。


本节课中我们一起学习了如何通过AWS CLI在Cloud Shell中调用Step Functions状态机。我们掌握了获取ARN、构造命令、传递输入以及验证结果的全过程。这种方法为您提供了一种强大且灵活的方式来编排和测试您的无服务器应用程序工作流。
116:构建Rust AWS Lambda加法函数 🦀

在本节课中,我们将学习如何使用Rust语言构建一个简单的AWS Lambda函数。这个函数将实现两个数字相加的功能。我们将从项目创建开始,逐步完成本地开发、构建、部署和远程测试的全过程。
项目架构概述

这是一个非常简单的Lambda函数系列架构的起点,这些函数最终将被包装在一个Step Function中。首先,我们从Rust开始,构建一个加法函数。
这个函数接收一个x和一个y,然后返回它们的总和。选择Rust的原因是,它可能是构建高性价比Lambda函数最简单的方式之一。
创建Rust Lambda项目
以下是创建项目的步骤。我们使用cargo-lambda工具来初始化项目。
- 使用命令
cargo lambda new创建一个新项目。 - 项目生成后,其目录结构非常简单,主要包含一个
main.rs文件和一个Cargo.toml配置文件。 Cargo.toml文件已经预先配置好了所需的依赖项,如序列化、异步运行时和日志追踪库。
函数逻辑解析
现在,让我们深入查看Lambda函数内部的逻辑。以下是函数代码的详细说明。
- 请求与响应结构体:我们定义了两个结构体。
Request结构体代表传入的请求,包含x和y两个字段。Response结构体代表返回的响应,包含total字段。 - 主处理函数:核心逻辑是一个异步的Rust函数
function_handler。它接收一个Request对象,将x和y相加得到total,然后将其包装在Response对象中返回。 - 入口点:
main函数已经自动设置好,它会调用我们定义的function_handler。
本地开发与测试
为了高效开发,我们可以创建一个Makefile来简化常用命令。以下是本地开发和测试的流程。
- 本地监听:通过命令
make watch(对应cargo lambda watch)启动本地开发服务器,可以实时编译和测试。 - 本地调用:通过命令
make invoke可以调用本地构建的函数二进制文件进行测试。与Python等脚本语言不同,Rust Lambda的本地开发环境无需复杂配置。
构建与部署
完成本地测试后,下一步是构建并部署函数到AWS。以下是具体步骤。

- 构建发布版本:使用命令
make build(对应cargo lambda build --release)构建优化后的二进制文件。为了获得最佳成本效益,我们可以选择构建ARM64架构的版本。 - 部署到AWS:使用命令
make deploy(对应cargo lambda deploy)即可轻松将函数部署到指定的AWS区域。得益于Rust生成的精简二进制文件,部署过程非常快速。
远程调用与监控
函数部署后,我们可以在AWS控制台中进行测试和监控。以下是验证函数运行情况的方法。
- 远程调用:使用命令
make aws-invoke(对应cargo lambda invoke --remote)可以直接远程调用已部署的Lambda函数。 - 控制台测试:在AWS Lambda控制台的测试界面,可以创建测试事件并查看执行结果和详细指标。
- 性能优势:从监控数据可以看到,Rust Lambda函数的执行时间通常在毫秒级别,内存占用极低(例如15MB)。由于AWS Lambda按计算资源(内存和运行时间)计费,这种高效性使得用Rust实现复杂操作在成本上更具优势。
课程总结

本节课中,我们一起学习了使用Rust构建和部署AWS Lambda函数的完整流程。我们从创建项目开始,编写了简单的加法函数逻辑,并进行了本地测试。接着,我们构建了ARM64版本以优化成本,并将其部署到云端。最后,我们通过远程调用和控制台监控验证了函数的正确性与高性能表现。掌握这些步骤,你就具备了使用Rust开发高效、低成本云函数的基础能力。
117:构建Rust AWS Lambda除二函数 🦀

在本节课中,我们将学习如何使用Rust语言从头开始构建一个简单的AWS Lambda函数。这个函数的功能是接收一个数字载荷,并将其除以二后返回结果。
我们将从创建项目开始,逐步完成代码编写、本地测试、构建和部署到AWS的完整流程。

项目初始化
首先,我们需要创建一个新的Rust Lambda项目。我们将使用 cargo-lambda 工具来搭建项目基础结构。
以下是创建项目的命令:
cargo lambda new divide_by2
执行命令后,选择“否”以跳过模板中的额外配置,让项目开始初始化。
编写Makefile
为了简化后续的构建和部署流程,我们创建一个Makefile。这个文件将包含编译、测试和部署Lambda函数所需的常用命令。
定义函数逻辑
现在,我们进入代码部分。首先需要明确函数的意图:它接收一个名为 total 的数字,计算其一半,并返回计算结果。
我们需要修改Lambda函数的请求和响应结构体。将请求体中的字段改为 total,它是一个数字。将响应体中的字段改为 calculation,用于存放计算结果。

在主函数中,逻辑非常简单:从请求中提取 total 值,将其除以2,然后将结果赋值给响应体中的 calculation 字段。
核心计算代码如下:
let calculation = total / 2;
response.calculation = calculation;
本地测试
在部署之前,进行本地测试是一个好习惯。我们将使用 cargo lambda watch 命令来启动一个本地Lambda运行时环境,以便于测试。
为了测试,我们需要准备一个事件文件。创建一个JSON文件,其内容为 {"total": 10},模拟一个输入事件。
然后,我们可以使用 make invoke 命令(该命令会调用 cargo lambda invoke)来本地调用我们的函数,并验证其返回 {"calculation": 5}。
构建与部署
测试通过后,就可以构建并部署函数了。我们将为ARM64架构构建,因为这是性价比较高的计算选项。
使用以下命令进行构建和部署:
make build
make deploy
部署命令会将我们的函数代码打包并发布到AWS Lambda。
远程调用验证
部署完成后,我们还可以进行远程调用测试,以确保函数在云环境中也能正常工作。我们可以使用AWS CLI或通过控制台来触发函数,并传入测试事件。
本节课中,我们一起学习了如何使用Rust从零开始构建、测试和部署一个AWS Lambda函数。我们完成了从项目初始化、代码编写、本地测试到最终云部署的完整流程。这个“除二函数”虽然简单,但涵盖了构建无服务器函数的核心步骤。
118:通过CLI调用AWS Step Functions 🚀

在本节课中,我们将学习如何通过AWS命令行界面(CLI)来调用一个由Rust语言编写的AWS Step Functions工作流。我们将从确认已部署的Lambda函数开始,逐步创建并运行一个状态机,最后通过CLI执行它。
准备工作:确认Lambda函数 ✅
上一节我们介绍了AWS Step Functions的基本概念,本节中我们来看看如何实际操作。首先,我们需要确保用于构建工作流的Lambda函数已经成功部署。
以下是确认步骤:
- 导航至AWS管理控制台的Lambda服务页面。
- 在函数列表中,检查名为
rustadd和divide_by_two的函数是否存在。 - 确认这两个函数的运行时环境均为Rust。
完成确认后,我们就可以进入AWS Step Functions服务来创建状态机。


创建Step Functions状态机 🏗️
现在,我们将在AWS Step Functions中创建一个新的状态机。这个状态机将按顺序调用我们之前确认的两个Lambda函数。
以下是创建可视化工作流的步骤:
- 在Step Functions控制台,点击“创建状态机”。
- 选择“使用可视化工作流设计器”选项。
- 为状态机命名,例如
RustBasedWorkflow。 - 从左侧面板拖拽两个“任务”状态到设计画布中。
- 配置第一个任务,将其命名为
Add,并关联到rustaddLambda函数。 - 配置第二个任务,将其命名为
DivideBy2,并关联到divide_by_twoLambda函数。 - 按照执行顺序连接这两个任务。
- 点击“下一步”,预览工作流定义,然后创建状态机。
创建成功后,我们可以立即开始执行。
首次执行与测试 🔄
状态机创建完毕后,我们将进行首次手动执行以测试工作流是否按预期运行。
执行过程如下:
- 在新创建的状态机页面,点击“开始执行”。
- 在输入框中,提供一个JSON格式的输入。例如,要计算
(1+3)/2,输入为:{ "x": 1, "y": 3 } - 点击“开始执行”。工作流将首先调用
rustadd函数计算x+y,然后将结果传递给divide_by_two函数进行除以2的操作。 - 在执行详情页面,可以查看每个步骤的输入和输出,最终输出结果应为
2。

测试成功,验证了我们的工作流逻辑正确。
通过AWS CLI调用工作流 💻
上一节我们在控制台手动执行了工作流,本节中我们来看看如何通过命令行实现自动化调用。这是集成到CI/CD管道或其他自动化脚本中的关键步骤。

操作步骤如下:
- 首先,在终端中配置AWS CLI的输出格式为JSON,以便于解析结果:
aws configure set output json - 使用
aws stepfunctions start-execution命令来触发状态机。需要提供状态机的ARN和执行输入:
命令会返回一个包含执行ARN的响应。aws stepfunctions start-execution --state-machine-arn <您的状态机ARN> --input "{\"x\": 5, \"y\": 3}" - 可以通过以下命令查看特定执行的详细信息:
aws stepfunctions describe-execution --execution-arn <上一步返回的执行ARN> - 返回AWS Step Functions控制台,刷新执行列表,可以看到通过CLI触发的执行记录。检查其输入,确认与我们通过命令行传递的参数(例如
x=5, y=3)一致。
通过CLI调用,我们能够以编程方式、高效地驱动这个高性能、低成本的Rust计算工作流。
总结 📝

本节课中我们一起学习了通过AWS CLI调用Step Functions工作流的完整流程。我们首先确认了Rust Lambda函数的状态,然后创建了一个顺序执行“加法”和“除以2”任务的状态机。在手动测试成功后,我们最终使用AWS CLI命令实现了工作流的自动化执行,这为集成到更广泛的自动化体系中奠定了基础。
119:使用 Rust 构建 AWS Step Functions 实践 🦀

在本节课中,我们将学习如何使用 Rust 语言来构建和部署 AWS Step Functions。Step Functions 是一种强大的无服务器工作流服务,它允许你将多个 AWS Lambda 函数像乐高积木一样串联起来,构建复杂的业务流程。我们将通过一个简单的“Marco Polo”游戏示例,演示从创建 Lambda 函数到组装工作流的完整过程。
概述
AWS Step Functions 的核心优势在于其可视化的编排能力和强大的调试支持。你可以轻松地将一个 Lambda 函数的输出作为另一个 Lambda 函数的输入,并在控制台中直观地追踪每个步骤的执行详情。本教程将展示如何利用 Rust 和 cargo-lambda 工具链来实现这一流程。
创建 Rust Lambda 函数

首先,我们需要创建两个独立的 Rust Lambda 函数,它们将作为工作流中的两个步骤。
以下是创建第一个函数 rust-marco 的步骤:
- 使用
cargo-lambda工具初始化新项目。cargo lambda new rust-marco - 编写函数逻辑。函数接收一个包含
name字段的 JSON 输入。 - 在处理器(handler)中,判断输入的名字是否为 “Marco”。
- 根据判断结果,构造不同的响应体。
让我们查看 rust-marco 函数的核心代码逻辑:
// 定义输入数据结构
#[derive(Deserialize)]
struct Request {
name: String,
}
// 定义输出数据结构
#[derive(Serialize)]
struct Response {
body: String,
}
// Lambda 函数处理器
async fn function_handler(event: LambdaEvent<Request>) -> Result<Response, Error> {
// 从事件中提取 name 字段
let name = event.payload.name;
// 核心逻辑:判断并生成响应
let body = if name == "Marco" {
"Polo".to_string()
} else {
"Nobody".to_string()
};
// 记录日志用于调试
tracing::info!("Processed name: {}", name);
// 返回响应
Ok(Response { body })
}
接下来,我们以同样的方式创建第二个函数 rust-polo。
上一节我们创建了第一个 Lambda 函数,本节中我们来看看第二个函数 rust-polo 的实现。它的作用是接收第一个函数的输出,并做出响应。
rust-polo 函数的逻辑如下:
async fn function_handler(event: LambdaEvent<Request>) -> Result<Response, Error> {
// 从事件中提取上一个函数返回的 body 字段
let body = event.payload.body;
// 核心逻辑:判断 body 内容
let result = if body.contains("Polo") {
"You win".to_string()
} else {
"You lose".to_string()
};
tracing::info!("Received body: {}, Result: {}", body, result);
Ok(Response { body: result })
}

构建与部署函数
为了简化构建和部署流程,我们可以使用 Makefile 来定义常用命令。
以下是 Makefile 的示例内容:
release:
cargo lambda build --release
deploy:
cargo lambda deploy
invoke:
cargo lambda invoke --remote --data-ascii '{"name": "Marco"}' rust-marco-function
运行 make release 会编译 Rust 代码为 Lambda 可用的二进制文件。运行 make deploy 会将函数部署到 AWS 云端。运行 make invoke 可以远程测试已部署的函数。
在 AWS 控制台组装 Step Functions
函数部署完成后,我们可以在 AWS 管理控制台中像搭积木一样创建 Step Functions 工作流。
以下是创建状态机的步骤:
- 进入 Step Functions 控制台,点击“创建状态机”。
- 在可视化编辑器中,从左侧拖入一个“Lambda 调用”状态块。
- 将其配置为调用我们部署的
rust-marco函数。 - 再拖入第二个“Lambda 调用”状态块,将其配置为调用
rust-polo函数。 - 用箭头连接两个状态块,定义执行顺序。
- 为状态机命名(例如
rust-marco-polo-chain)并创建。
工作流的定义(ASL)本质上是一个 JSON 文件,它描述了状态的顺序和转换逻辑。
执行与调试工作流
状态机创建后,我们可以立即执行它并观察其运行过程。
执行工作流并观察结果的步骤如下:
- 在状态机详情页,点击“开始执行”。
- 为本次执行提供一个输入,例如:
{"name": "Marco"}。 - 点击“开始执行”后,控制台会进入可视化执行界面。
- 你可以看到执行流经
rust-marco和rust-polo两个步骤。 - 点击每个步骤,可以展开查看其详细的输入和输出,这对于调试至关重要。
如果输入 name 不是 “Marco”,第一个函数将返回 “Nobody”,导致第二个函数判断为 “You lose”,整个工作流会成功完成但结果不同。如果函数配置或权限有误,工作流会失败并显示清晰的错误信息,方便定位问题。
总结

本节课中我们一起学习了使用 Rust 构建 AWS Step Functions 的完整流程。我们首先利用 cargo-lambda 创建并部署了两个简单的 Lambda 函数,然后在 AWS 控制台中将它们组装成一个顺序执行的工作流。这个过程展示了 Step Functions 在编排无服务器任务、可视化流程和简化调试方面的强大能力。通过结合 Rust 的性能与安全性,以及 AWS 无服务器服务的弹性,你可以构建出高效、可靠且易于维护的大规模云解决方案。
120:App Engine Rust应用部署演示 🚀
在本节课中,我们将学习如何在Google App Engine的灵活环境中,使用Rust语言部署一个微服务应用。我们将从创建项目目录开始,逐步配置必要的文件,并最终将应用部署到生产环境。

配置App Engine环境
首先,我们有一个App Engine环境。我已将其配置为灵活环境,以便演示如何使用Rust语言和App Engine框架部署微服务。
以下是部署Rust应用到App Engine的具体步骤。
1. 创建项目目录与配置文件
首先,创建一个名为 web_docker 的目录并进入。
mkdir web_docker
cd web_docker
接下来,需要为App Engine创建配置文件。创建一个名为 app.yaml 的文件。

touch app.yaml
app.yaml 文件至关重要,它用于告知App Engine我们的部署配置。其基本内容如下:
runtime: custom
env: flex
这表示我们使用自定义运行时,并选择灵活环境。
2. 初始化Rust项目
现在,我们需要初始化一个Rust项目。使用 cargo init 命令。
cargo init
在提示中输入项目名称,例如 web_docker。此命令会生成 Cargo.toml 等文件。
接着,我们需要添加项目依赖。将以下内容添加到 Cargo.toml 文件的 [dependencies] 部分:
actix-web = "4"
rand = "0.8"
serde = { version = "1", features = ["derive"] }
3. 创建Dockerfile
由于我们使用自定义运行时,需要提供一个 Dockerfile 来定义构建和运行环境。
touch Dockerfile
Dockerfile 内容示例如下。它使用Rust构建器,并采用多阶段构建以生成更小的最终镜像。
FROM rust:1.68 as builder
WORKDIR /usr/src/app
COPY . .
RUN cargo build --release
FROM debian:buster-slim
COPY --from=builder /usr/src/app/target/release/web_docker /usr/local/bin/web_docker
CMD ["web_docker"]
4. 编写应用源代码
现在,我们来编写应用的核心代码。首先创建 src/lib.rs 文件。
// src/lib.rs
use actix_web::{get, web, App, HttpResponse, HttpServer, Responder};
use rand::Rng;
use serde::Serialize;
#[derive(Serialize)]
struct Fruit {
name: String,
}
#[get("/")]
async fn index() -> impl Responder {
let fruits = vec!["Apple", "Banana", "Cherry", "Date", "Elderberry"];
let mut rng = rand::thread_rng();
let random_fruit = fruits[rng.gen_range(0..fruits.len())];
HttpResponse::Ok().body(format!("Welcome! Random fruit: {}", random_fruit))
}
#[get("/health")]
async fn health() -> impl Responder {
HttpResponse::Ok().body("OK")
}
pub fn init_app(config: &mut web::ServiceConfig) {
config.service(index);
config.service(health);
}
然后,创建 src/main.rs 文件作为应用入口。
// src/main.rs
use actix_web::{web, App, HttpServer};
use web_docker;
#[actix_web::main]
async fn main() -> std::io::Result<()> {
HttpServer::new(|| {
App::new().configure(web_docker::init_app)
})
.bind(("0.0.0.0", 8080))?
.run()
.await
}
5. 添加Makefile(可选)
为了便于管理和记录构建步骤,可以添加一个 Makefile。
.PHONY: run build deploy clean


run:
cargo run
build:
cargo build --release
deploy:
gcloud app deploy
clean:
cargo clean
rm -rf target
6. 本地测试应用
在部署之前,先在本地运行应用以确保一切正常。


cargo run

应用启动后,可以通过Web预览功能访问 http://localhost:8080。页面应显示“Welcome! Random fruit: [随机水果名]”。访问 /health 路由应返回“OK”。
7. 部署到App Engine
确认应用在本地运行无误后,即可开始部署。首先,建议删除 target 目录以避免上传不必要的构建文件。
rm -rf target
由于Rust编译可能耗时较长,需要设置更长的构建超时时间。
gcloud config set app/cloud_build_timeout 1600
最后,执行部署命令。
gcloud app deploy

此过程需要一些时间。部署完成后,应用将在App Engine的生产环境中运行。
灵活环境的优势
通过以上步骤,我们成功在App Engine灵活环境中部署了一个Rust应用。App Engine的灵活性不仅限于Rust,它支持多种语言和部署方式。
例如,对于Python应用,你可以直接在 app.yaml 中指定官方运行时。
runtime: python37
若想实现自动化部署,可以添加 cloudbuild.yaml 文件来定义Cloud Build的各个构建步骤。
这种灵活性使得开发者可以轻松地在不同语言(如Rust、Python、Go)之间切换,并选择适合的部署策略。整个过程可以从简单的命令行开始,根据需求演变为一个完整的持续交付流程。

总结

本节课中,我们一起学习了如何将Rust应用部署到Google App Engine的灵活环境。我们从创建项目、编写配置文件(app.yaml 和 Dockerfile)、编写应用代码,到本地测试和最终部署,完成了完整的流程。App Engine提供了高度灵活的环境,支持多种编程语言和部署方式,是构建和扩展云应用的强大平台。
121:监控与告警简介 🚨
在本节课中,我们将学习监控与告警,这是运维工作中最关键的功能之一。我们将探讨如何通过有效的告警技术来确保业务连续性,并介绍如何构建一个可操作的监控系统。
概述
首先,我们将评估不同的基础设施配置,以优化云计算成本与性能。这是监控与告警的一个关键方面,对于任何面向客户的企业都至关重要。
接下来,我们将介绍如何构建一个有效且可操作的监控与告警系统。构建一个能产生大量“噪音”的系统是一回事,而能够对这些“噪音”采取行动则是另一回事。
学习目标
以下是本节课的主要学习目标:
- 评估优化云成本与性能的配置:理解如何通过监控数据来调整资源配置,实现成本与性能的最佳平衡。
- 构建可操作的监控系统:学习设计一个不仅能发现问题,还能指导团队采取具体行动的监控体系。
核心概念
上一节我们概述了课程内容,本节中我们来看看监控与告警的核心概念。
监控的核心在于持续收集系统各项指标。一个基础的监控公式可以表示为:
监控数据 = 收集(指标, 日志, 追踪)
而告警则是基于这些监控数据设定的规则。当某项指标超过预设的阈值时,系统便会触发告警。这个过程可以用伪代码简单描述:
if 监控指标 > 阈值:
触发告警(级别, 消息)
告警技术要点
理解了基本概念后,我们来看看实施有效告警的一些技术要点。以下是构建告警系统时需要考虑的几个关键步骤:
- 定义清晰的指标:明确需要监控什么,例如 CPU 使用率、内存消耗、请求延迟等。
- 设置合理的阈值:阈值设置过高可能漏报问题,设置过低则会产生过多无效告警。
- 分级告警:根据问题的严重程度(如 紧急、警告、信息)对告警进行分级,确保关键问题能被优先处理。
- 设置静默期与聚合:避免在短时间内因同一问题重复触发告警,将相关告警聚合后通知。
- 规划响应流程:确保每个告警都有明确的处理流程和负责人。

总结

本节课中我们一起学习了监控与告警的基础知识。我们了解到,监控是观察系统状态的窗口,而告警则是推动行动的信号。一个优秀的监控告警系统不仅能帮助优化云计算的成本与性能,更是保障业务连续性的重要基石。关键在于构建一个有效且可操作的系统,让团队能够快速响应并解决问题。
122:高效监控与告警策略 🚨
在本节课中,我们将探讨告警在组织中的重要性,并学习如何制定高效的告警策略,以避免无效告警带来的负面影响。
概述
告警是运维和监控系统中的关键组成部分。然而,不当的告警策略不仅无法帮助解决问题,反而可能损害团队的健康和生产力。本节将通过一个真实案例,分析告警的常见误区,并阐述构建有效、可操作的告警策略的核心原则。
一个关于告警的教训
上一节我们介绍了监控的基础概念,本节中我们来看看告警策略。告警在组织中扮演着极其重要的角色。在我职业生涯早期管理一家完全专注于云计算的软件即服务公司时,我们遇到了一些实际问题。
机器会无故消失。过了一段时间,我们开始创建一些告警来监控发生的情况。我们会利用这些告警在早上叫醒自己,然后稍后修复问题。逐渐地,我们的软件产品出现了越来越多的问题。
由于在风险投资公司中需要快速的开发周期,我们确实没有时间修复所有问题。因此,在接近一年的时间里,这个小团队的许多成员都睡眠不足。可以说,在接近一年的时间里,我很多个晚上都没睡好,因为我经常在凌晨两点、三点、四点被叫醒。
最终,凭借我的统计学背景,我开始思考:我们真的在对正确的事情发出告警吗?还是我们本质上只是在抛硬币,然后被叫醒?为此,我做了一件事:我查看了一整年的告警记录。
我注意到的一个事实是,除了看起来是随机的之外,这些告警没有任何可辨别的模式。在我得出这个结论并确定我们基本上白白失去了一年的睡眠、这些告警除了让我们疲惫之外毫无用处之后,我关闭了它们。
我决定尝试一个实验:在一年内不设置这些告警。结果证明,在一个月内,什么糟糕的事情都没有发生。实际情况是,我们只是陷入了一种关于告警的“货物崇拜”思维方式,这对我们造成了真正的损害。
事实上,甚至让公司里的人相信我们不需要被不断地叫醒,也花了很长时间。因此,我认为关于告警的一个重要启示是:就像生活中的许多事情一样,好事也可能过犹不及。
构建高效告警策略的核心原则
所以,关键在于告警的有效使用。如果你要设置一个告警,请确保它是可操作的并且是罕见的。以下是制定高效告警策略时需要遵循的几个关键点:
- 可操作性:告警必须明确指出发生了什么问题,并且接收告警的团队或个人有能力立即采取行动来修复或缓解它。模糊或无法行动的告警只会制造噪音。
- 罕见性:告警应该只在真正重要、紧急的情况下触发。高频的、无关紧要的告警会导致“告警疲劳”,使团队对真正的危机变得麻木。
- 明确模式:有效的告警应基于可识别的、非随机的模式或阈值。如果告警触发看起来完全是随机的,那么它很可能没有捕捉到根本原因。
总结

本节课中我们一起学习了高效监控与告警策略。我们通过一个案例了解到,无效的告警会严重消耗团队精力,破坏工作与生活的平衡。关键在于设置可操作的和罕见的告警,确保团队能够保持健康,维持工作与生活的平衡,从而将时间创造性地用于改进产品。记住,告警的目的是为了解决问题,而不是制造问题。
123:使用AWS CloudWatch实现监控触发与告警 📊
在本节课中,我们将学习AWS CloudWatch的核心功能。CloudWatch是一个强大的服务,可以帮助你监控在AWS上运行的几乎所有资源和应用程序。我们将通过一个Lambda函数的例子,探索如何设置监控、查看日志、配置告警以及创建定时触发器。
探索CloudWatch控制台
首先,我们进入AWS管理控制台,找到并打开CloudWatch服务。CloudWatch允许我们监控资源和应用程序。其功能主要分为几个大类:告警、事件、日志和指标。
为了全面了解这些功能,我们将回到之前创建的“Marco” Lambda函数,并以其为例进行演示。
查看CloudWatch日志 📝
上一节我们介绍了CloudWatch的概览,本节中我们来看看如何查看和分析日志。
Lambda函数每次被调用时,都会生成日志。在Lambda控制台的“监控”选项卡下,我们可以查看与函数相关的CloudWatch监控信息。
以下是查看日志的步骤:
- 确保Lambda函数的执行角色具有写入CloudWatch Logs的权限。如果之前修改过角色,可能需要将其恢复为默认角色或附加一个包含
CloudWatchLogsFullAccess策略的开发角色。 - 保存角色更改并刷新页面。
- 在“监控”选项卡下,点击“查看CloudWatch中的日志”。
- 在打开的CloudWatch Logs界面中,可以根据时间戳查看最新的日志流,这是调试Lambda函数的有效方法。




在代码中添加调试信息
除了查看自动生成的日志,我们还可以在Lambda函数代码中主动输出调试信息,这是一种常见的调试手段。
例如,在Python编写的Lambda函数中,我们可以使用print语句输出事件内容:
print(f"This is my event: {event}")
这段代码使用了Python的f-string格式化方法,将事件对象的内容打印到日志中。保存并多次测试函数后,这些自定义的“Bob”消息和函数原有的“Marco”消息都会出现在CloudWatch日志中。
回到CloudWatch监控界面,我们不仅可以查看调用次数、持续时间等指标,还可以深入查看具体的日志输出来排查问题。
配置CloudWatch事件触发器 ⏰
上一节我们学习了如何查看日志,本节中我们来看看如何配置自动触发器。
CloudWatch Events(现称为EventBridge)可以按计划或响应事件来触发Lambda函数。例如,如果我们希望“Marco”函数每分钟自动运行一次,可以设置一个规则。
以下是创建定时触发器的步骤:
- 在Lambda函数配置页面的“触发器”部分,点击“添加触发器”。
- 选择“CloudWatch Events/EventBridge”。
- 创建新规则,例如命名为“noisy-one-minute”。
- 选择“计划表达式”,并输入速率表达式:
rate(1 minute) - 保存后,规则将每分钟触发一次Lambda函数。
设置完成后,我们可以通过查看CloudWatch日志来验证函数是否被周期性调用。在CloudWatch控制台的“规则”部分,也可以管理已创建的事件规则。
注意:对于不执行实际任务的函数,应移除此类触发器以避免不必要的运行和成本。演示后,我们移除了这个“noisy-one-minute”触发器。



总结
本节课中我们一起学习了AWS CloudWatch的几个核心功能。我们通过一个Lambda函数实例,实践了如何查看和分析CloudWatch日志,如何在函数代码中添加调试信息,以及如何配置CloudWatch事件规则来定时触发函数。



总而言之,CloudWatch是AWS生态中监控和可观察性的核心,它集告警、事件、日志和指标于一体,从调试应用程序到构建自动化数据管道,都发挥着重要作用。确保资源配置正确的权限并及时清理不必要的资源,是使用CloudWatch时的最佳实践。
124:从零构建告警系统 🚨

在本节课中,我们将学习如何从零开始构建一个简单的告警系统。我们将通过编写一个Bash脚本来检查特定文件是否存在,并根据检查结果输出相应信息或返回错误状态码。这个过程模拟了在基础设施中验证关键组件是否按预期工作的基本方法。
上一节我们介绍了告警系统的基本概念,本节中我们来看看如何具体实现一个文件检查脚本。
首先,我们需要在Azure Cloud Shell环境中进行操作。打开Cloud Shell编辑器可以方便地创建和编辑文件。
以下是创建测试文件和检查脚本的步骤:

- 创建一个名为
config的测试文件,这个文件代表我们需要确保存在的目标文件。touch config - 创建一个名为
check.sh的Bash脚本文件,用于执行检查逻辑。
现在,让我们开始编辑 check.sh 脚本文件。
脚本的第一行是“shebang”行,它指定了脚本的解释器。
#!/usr/bin/env bash
接下来,我们定义要检查的文件路径,并使用 if 语句和 test -f 命令来检查文件是否存在。
FILE="./config"
if test -f "$FILE"; then
echo "Config file exists."
else
echo "Config file doesn‘t exist."
exit 2
fi
这段代码的逻辑是:如果文件存在,则打印成功信息;如果文件不存在,则打印错误信息并以状态码 2 退出,这通常用于表示“文件未找到”的错误。
脚本编写完成后,需要使其可执行。
chmod +x check.sh
现在,我们可以运行脚本来测试其功能。
./check.sh
如果 config 文件存在,脚本将输出“Config file exists.”。为了测试告警功能,我们可以重命名或删除 config 文件,然后再次运行脚本。
mv config config2
./check.sh
此时,脚本将输出“Config file doesn‘t exist.”并以状态码 2 退出。


本节课中我们一起学习了如何构建一个基础的告警检查脚本。我们创建了一个Bash脚本,用于检查关键文件是否存在,并在文件缺失时返回错误状态码。虽然这是一个简单的例子,但它展示了如何将验证逻辑嵌入基础设施中,以确保系统按预期运行,并在需要人工干预时触发告警。
125:Google App Engine Rust微服务监控与日志 📊

在本节课中,我们将学习如何为部署在Google App Engine上的Rust微服务进行监控与日志分析。我们将从查看一个实际部署的微服务仪表盘开始,了解其提供的各项监控指标,然后深入探讨如何使用日志查询功能进行更细致的调试。
微服务与仪表盘概览
我们有一个使用Actix Web框架的Rust微服务。该服务包含一个名为/fruit的路由,以及一个返回“Hello World”的函数。我们可以通过代码了解其部署到生产环境后的行为。该应用已容器化,非常适合在App Engine上运行。
上一节我们介绍了微服务的基本构成,本节中我们来看看其部署后的监控界面。
如果我们访问该服务在App Engine上的已部署版本,可以看到一个仪表盘。该仪表盘展示了此部分所有重要的摘要信息。
以下是仪表盘提供的主要监控视图:
- 请求:可以查看请求数量。
- 计费状态:查看服务的计费情况。
- 错误:查看是否存在任何错误。
- 按类型查看请求:例如,可以切换查看延迟情况。
- 流量:查看接收和发送的流量数据。
- 利用率:查看资源利用率。
- 实例:查看已部署的实例数量(例如,当前有两个)。
- 内存使用情况:这对微服务非常重要,甚至可以基于此创建警报策略。
- 缓存查询:查看各种不同的缓存查询情况。
访问应用本身非常简单。我们再次看到这个基于Rust的随机水果微服务,访问/fruit路由,并可以反复运行它。
因此,仅从这个仪表盘就能获得非常直观和全面的监控服务。我们还可以在这里查看版本,甚至了解哪些版本正在提供流量(当前是100%的流量)。我们也可以从这个仪表盘停止或启动服务。
所以,如果你有一个容器化的Rust微服务运行在Google App Engine上,这里就是一个一站式的监控管理平台。
深入日志分析


除了仪表盘,另一项非常实用的功能是日志分析。
我们可以进一步深入查看细节。其中一种方法是创建自定义查询。我们可以在这里切换,仅按资源类型筛选,从而很好地了解发生的一切。我们可以创建指标、创建警报,甚至执行SQL查询。
接下来,我将演示一个非常简单的操作:查询我们已知会被调用的/fruit这个URL。让我们运行一个查询。

查询结果应该会显示出来。我们可以看到应用延迟(以秒为单位)、项目名称以及调用发生的时间戳。
如果需要,我也可以基于此创建某种警报。例如,如果调用次数过多,我们可以据此采取一些行动。我们还可以切换查看不同的日志名称和严重级别。
因此,结合Google App Engine的仪表盘和日志显示功能,你便拥有了调试基于Rust的App Engine微服务所需的一切工具,足以应对生产环境中的应用调试。
课程总结
本节课中我们一起学习了如何利用Google App Engine的内置工具监控和调试Rust微服务。我们首先探索了App Engine仪表盘,它提供了从请求、错误、实例状态到内存使用率等全方位的运行概览。接着,我们深入使用了日志查询功能,通过自定义查询来追踪特定请求(如/fruit)的详细执行情况,包括延迟和时间戳,并了解了如何基于日志数据创建警报。这些工具共同为生产环境中的微服务提供了强大的可观测性支持。
126:负载测试入门 🧪
在本节课中,我们将学习负载测试的基础知识。负载测试是软件即服务公司、游戏公司或面向消费者的公司可以执行的最关键任务之一。其重要性在于,它能让你了解应用程序的性能极限。想象一下,建造旧金山海湾大桥或金门大桥,却不知道在特定交通流量下会发生什么,那将是灾难性的生命损失。负载测试的作用正是确保你的应用程序能够在最高水平上运行。
上一节我们介绍了负载测试的重要性,本节中我们来看看本课的具体学习目标。
以下是本课的主要学习目标:
- 首先,我们将评估负载测试的最佳实践。
- 其次,我们将介绍一个名为 Locust 的开源负载测试工具。
负载测试最佳实践 📊
负载测试的核心目标是模拟真实用户行为,以评估系统在高负载下的表现。为了有效进行负载测试,需要遵循一些关键实践。
以下是进行负载测试时应考虑的最佳实践列表:
- 定义明确的目标:在开始测试前,明确要测试的性能指标,例如每秒请求数、响应时间或并发用户数。
- 模拟真实场景:测试脚本应尽可能贴近真实用户的操作流程和行为模式。
- 循序渐进增加负载:不要一开始就施加最大压力,而应逐步增加负载,观察系统性能的变化曲线。
- 监控关键指标:在测试过程中,持续监控服务器资源使用率、应用错误率和数据库性能等。
- 分析结果并优化:测试结束后,分析瓶颈所在,并针对性地进行系统优化。
使用 Locust 进行负载测试 🐝
Locust 是一个易于使用的开源负载测试工具,它允许你使用 Python 代码定义用户行为,并模拟数百万并发用户。
以下是一个简单的 Locust 测试脚本示例,它定义了一个用户行为:访问网站首页。
from locust import HttpUser, task, between
class WebsiteUser(HttpUser):
wait_time = between(1, 5) # 用户等待1到5秒后执行下一个任务
@task
def index_page(self):
self.client.get("/") # 模拟用户访问根路径
在这个脚本中,WebsiteUser 类代表一个虚拟用户。wait_time 定义了用户执行任务间的等待时间,以模拟真实用户的思考或阅读时间。@task 装饰器标记的方法 index_page 代表用户要执行的具体任务,即向网站的根目录发起一个 HTTP GET 请求。
运行 Locust 测试后,你可以通过其 Web 界面实时查看请求数、失败率、响应时间等关键数据,并据此分析系统性能。


本节课中我们一起学习了负载测试的基础概念及其重要性,探讨了进行有效负载测试的最佳实践,并初步认识了如何使用 Locust 这一开源工具来编写和执行负载测试脚本。掌握这些知识是构建健壮、可扩展的云应用的基础。
127:高效负载测试方法 🧪
在本节课中,我们将学习负载测试的重要性及其在识别和预防复杂系统故障中的关键作用。通过一个真实案例,我们将了解负载测试如何帮助发现那些在常规条件下难以复现的深层问题。
负载测试的价值
上一节我们介绍了课程背景,本节中我们来看看负载测试的核心价值。负载测试是一种模拟高并发、高压力场景以验证系统稳定性的方法。它能够揭示系统在极限条件下的行为,帮助开发者在问题影响用户之前将其解决。
我曾多次依靠负载测试化解危机。事实上,它是我职业生涯中使用过的最有效的工具之一。
一个真实案例:日志分析服务的崩溃
有一个特别有趣的案例发生在我工作于一家提供日志分析的软件即服务公司时。我们的系统包含许多基于Java的搜索引擎机器,它们负责分析文件。但很多时候,这些机器会莫名其妙地消失。
这成了一个严重的缺陷,因为重建这些服务器需要很长时间。我们很难弄清楚到底发生了什么。
部分原因在于这些机器被配置为不使用交换空间。这意味着它们从不保存状态。因此,我们完全无法知晓故障发生时的情况。
问题的根源
最终,我们发现了一个非常复杂且隐蔽的问题:机器本身被过度分配了线程。它们被设定使用过多的内存和并发量。结果,它们实际上达到了一个负载极限,超出了机器所能使用的内存量。
除非机器处于极高的压力下,否则它们永远不会真正达到这些条件,而这种情况并不常见。并且,由于机器上没有交换空间,它们会立即触发内核恐慌。在Linux系统上,内核本身会进入内存不足处理程序,并开始终止进程。
不幸的是,由于存在一个监控进程会重启Java进程,这就导致了一种竞态条件,最终引发内核恐慌。这是一系列非常复杂的事件,如果我们没有进行负载测试,我们可能永远都不会想到去检查这些方面。
经验教训与解决方案
我没有通过负载测试发现这个问题,而是用传统方式检测到的。但从那次错误中我吸取了教训:不能仅仅相信我们的架构支持那种级别的并发,而必须进行验证。
通过构建一套全面的负载测试套件,我们本可以避免那些极其隐蔽的崩溃和难以调试的问题。这正是负载测试的作用:它着眼于最坏可能的情况,并反复进行验证,从而使你能够进行根本原因分析并修复缺陷。
核心概念总结
以下是负载测试方法的核心要点:
- 目的:在可控环境中模拟极端条件,主动发现系统瓶颈和缺陷。
- 关键实践:不要假设,要验证。通过测试来证明系统的健壮性。
- 价值:暴露那些在低负载或常规操作下永远不会出现的复杂、隐蔽问题。
本节课总结


本节课中,我们一起学习了负载测试的实践价值。通过一个具体的案例,我们看到了负载测试如何帮助诊断由过度分配资源(如内存和线程)引发的复杂系统崩溃。关键在于,负载测试迫使系统暴露其极限,为开发者提供了在问题影响生产环境前进行“根因分析”和修复的机会。记住,对于系统承载能力,验证远比信任更为可靠。
128:使用Flask与Locust进行负载测试 🚀

在本节课中,我们将学习如何对一个简单的Flask Web应用进行负载测试。我们将使用Locust工具来模拟多个并发用户访问我们的服务,并观察其性能表现。整个过程将在AWS Cloud9开发环境中完成。
概述
我们将创建一个基础的“Hello World” Flask应用,然后使用Locust编写一个负载测试脚本。通过配置安全组开放必要的端口,我们可以在本地浏览器中访问Flask应用和Locust的Web界面,从而实时监控测试结果。
准备Flask应用
首先,我们需要构建一个简单的Flask应用作为测试目标。
以下是一个基础的Flask应用代码,它只包含一个返回“Hello World”的路由:
from flask import Flask
app = Flask(__name__)
@app.route('/')
def hello_world():
return 'Hello World!'
if __name__ == '__main__':
app.run(host='0.0.0.0', port=8080)
在Cloud9终端中,我们可以使用命令 python app.py 来运行这个应用。应用将在端口8080上启动。
配置安全组
由于Cloud9环境运行在EC2实例上,我们需要确保测试所需的端口在安全组中是开放的。
以下是需要开放的端口及其用途:
- 端口 8080: Flask应用运行在此端口。
- 端口 8089: Locust的Web管理界面运行在此端口。
- 端口 9090: 可能用于其他开发用途。
配置完成后,我们可以通过EC2实例的公共DNS地址和相应端口(例如 http://<公共DNS>:8080)在浏览器中访问Flask应用,以验证其运行正常。
编写Locust负载测试脚本
上一节我们准备好了待测试的Flask应用,本节中我们来看看如何编写Locust测试脚本。
Locust测试脚本定义了模拟用户的行为。以下是一个针对我们Flask应用的简单测试脚本:
from locust import HttpUser, task, between
class WebsiteUser(HttpUser):
wait_time = between(1, 5) # 模拟用户等待1到5秒
@task
def hello_world(self):
self.client.get("/") # 访问Flask应用的根路径
这段代码创建了一个名为 WebsiteUser 的用户类,它会在每次任务执行后等待1到5秒,然后重复访问我们Flask应用的首页。
运行与监控负载测试
现在,我们已经有了待测应用和测试脚本,接下来让我们启动测试并观察结果。

首先,确保Flask应用正在运行(python app.py)。然后,在另一个终端标签页中,导航到项目目录并运行命令 locust。这将启动Locust,并默认在端口8089上提供Web界面。
在浏览器中访问Locust的Web界面(http://<公共DNS>:8089),我们需要配置测试参数。
以下是启动测试前需要填写的参数:
- Number of users (peak concurrency): 要模拟的最大并发用户数,例如10。
- Spawn rate (users started/second): 每秒启动的用户数,例如1。
- Host: 目标应用的地址,格式为
http://<公共DNS>:8080。
填写参数并点击“Start swarming”后,Locust将开始模拟用户请求。我们可以在Web界面上实时查看各种统计数据。
Locust的Web界面提供了多个监控视图,帮助我们分析应用性能:
- Statistics: 显示请求数、失败率、响应时间(平均、中位数、最小/最大值)等关键指标。
- Charts: 以图表形式实时展示每秒请求数(RPS)和响应时间的变化趋势。
- Failures: 列出所有失败的请求及其原因。
- Exceptions: 显示测试过程中抛出的异常。
总结



本节课中我们一起学习了如何使用Locust对Flask应用进行负载测试。我们首先创建了一个简单的Flask服务,然后编写了Locust测试脚本以定义用户行为。通过配置AWS安全组开放端口,我们能够在浏览器中访问并操作Locust的Web界面,从而轻松地启动测试并实时监控应用的性能表现,如吞吐量和响应时间。这套方法可以进一步扩展,用于测试容器化或部署在Kubernetes中的微服务。
129:在GitHub Codespaces中使用Locust进行负载测试 🚀

概述
在本节课中,我们将学习如何使用Locust这一开源负载测试工具。负载测试是验证生产系统行为的重要环节。我们将在一个GitHub Codespaces环境中,对一个简单的微服务应用进行负载测试,模拟多用户并发访问,并观察其性能表现。
准备工作
首先,我们有一个可以运行在Kubernetes上的简单微服务。为了演示,我们暂时在本地运行它。通过执行 python main.py 命令可以启动这个应用。
创建Locust测试文件
接下来,我们需要创建一个Locust测试文件。使用 touch 命令创建一个名为 locustfile.py 的文件。我们将在这个文件中编写负载测试代码。
以下是创建Locust测试文件的基本步骤:

- 导入必要的Locust模块。
- 定义一个继承自
HttpUser的用户类。 - 在该类中,使用
@task装饰器定义要测试的具体任务。
编写测试任务
我们的微服务有一个 /fruit 路由,它会随机返回一种水果。因此,我们的负载测试任务就是模拟用户访问这个端点。
我们编写的测试代码如下:
from locust import HttpUser, task
class WebsiteUser(HttpUser):
@task
def get_fruit(self):
self.client.get("/fruit")
这段代码定义了一个用户行为:反复向 /fruit 路径发起GET请求。

运行负载测试
编写好测试文件后,我们就可以运行Locust了。在终端中直接输入 locust 命令。Locust会启动一个Web管理界面。

为了进行测试,我们需要同时运行被测试的微服务。因此,我们打开一个新的终端,并执行 python main.py 来启动我们的应用。
配置并执行测试
在Locust的Web界面中,我们可以配置测试参数:


- Number of users:要模拟的用户总数。
- Spawn rate:每秒启动的用户数。
- Host:被测试应用的地址(例如
http://127.0.0.1:8080)。


配置完成后,点击“Start swarming”开始测试。
分析测试结果
测试开始后,Locust的仪表盘会实时显示关键指标:
- Requests/s:每秒处理的请求数,反映系统吞吐量。
- Response Time:响应时间,包括平均值、中位数和特定百分位数(如P95)。
- Failures:失败的请求数量及原因。
通过这些图表和数据,我们可以清晰地了解应用在负载下的性能表现,例如是否存在性能瓶颈或错误。
集成到开发流程
Locust测试可以非常方便地集成到持续集成/持续部署(CI/CD)流程中。我们可以在每次部署到生产环境之前自动运行负载测试,并设定性能指标阈值(例如,响应时间必须低于200毫秒)。只有测试通过,才能继续进行部署,这有助于保障生产系统的稳定性。


总结
本节课我们一起学习了如何使用Locust进行负载测试。我们完成了从创建测试文件、编写测试任务、运行测试到分析结果的全过程。Locust是一个强大且易用的工具,能够帮助我们模拟高并发场景,验证应用的性能与可靠性。将负载测试纳入自动化流程,是构建健壮生产系统的重要实践。
130:Prometheus监控系统入门 🚀

在本节课中,我们将学习如何设置和运行Prometheus,这是一个非常流行的指标收集与告警解决方案,常与容器和Kubernetes一起使用。我们将使用AWS Cloud9环境来快速搭建一个原型。
概述
我们将从下载Prometheus开始,配置它,并在AWS环境中运行,最后通过Web界面查看其收集的指标数据。整个过程将展示Prometheus的基本工作原理。
环境准备与Prometheus下载
首先,我们使用AWS Cloud9环境。Cloud9能简化环境配置,特别适合在云中进行原型开发。
以下是启动步骤:
- 在AWS控制台中找到并点击Cloud9服务。
- 选择一个已有的Cloud9环境(本例中使用了一个之前用于Docker工作的环境)。
- 在Cloud9的终端中,我们将下载Prometheus客户端。
接下来,我们访问Prometheus官方网站的下载页面,找到适用于Linux的可执行文件。使用 wget 命令下载它。
wget https://github.com/prometheus/prometheus/releases/download/v2.37.0/prometheus-2.37.0.linux-amd64.tar.gz
下载完成后,使用 tar 命令解压文件包。
tar xvzf prometheus-2.37.0.linux-amd64.tar.gz
配置Prometheus
解压后,我们进入Prometheus的目录。目录中已有一个默认的配置文件 prometheus.yml。
cd prometheus-2.37.0.linux-amd64
我们可以用文本编辑器查看这个默认配置。但为了演示,我们将创建一个自定义配置。Prometheus不仅能收集其他系统的指标,也会生成关于自身的指标。默认情况下,它的Web界面运行在端口 9090。
由于Cloud9环境默认有安全限制,我们需要在AWS EC2的安全组中手动开放9090端口。
以下是配置安全组的步骤:
- 回到AWS控制台,导航到EC2服务。
- 在左侧导航栏中找到“安全组”。
- 找到与你的Cloud9实例关联的安全组(名称中通常包含“cloud9”或本例中的“docker”)。
- 在“入站规则”标签页中,点击“编辑入站规则”。
- 添加一条新规则:类型选择“自定义TCP”,端口范围填写 9090,来源设置为“0.0.0.0/0”(或根据你的安全需求调整)。
- 保存规则。
运行Prometheus并访问界面
端口开放后,我们就可以运行Prometheus了。使用 --config.file 参数指定我们的配置文件。
./prometheus --config.file=prometheus.yml
服务器将在前台运行,我们可以在终端中看到它的日志输出。
要访问Prometheus的Web界面,我们需要知道Cloud9实例的公共IP地址或公共DNS。
查找地址的步骤如下:
- 在EC2控制台的“实例”页面,找到你的Cloud9实例。
- 复制“公共IPv4 DNS”或“公共IPv4地址”。
- 在浏览器中访问
http://<你的公共DNS>:9090。
查看与理解指标
成功访问Web界面后,我们可以探索Prometheus的功能。
首先,Prometheus会自动生成关于自身的指标。我们可以通过访问 http://<你的公共DNS>:9090/metrics 来查看这些原始的指标数据。每次刷新这个页面,都会产生新的指标数据点。
回到主界面(http://<你的公共DNS>:9090),我们可以使用“Graph”标签页下的表达式浏览器来查询和可视化指标。
例如,我们可以输入 prometheus_http_requests_total 来查看Prometheus服务处理的HTTP请求总数。点击“Execute”执行查询,结果会以表格形式展示。切换到“Graph”视图,可以看到该指标随时间变化的曲线图。
总结


本节课我们一起学习了Prometheus监控系统的基础操作。我们从在AWS Cloud9环境中下载和安装Prometheus开始,然后学习了如何配置安全组以开放必要的网络端口。接着,我们启动了Prometheus服务并通过Web界面访问它。最后,我们探索了如何查看Prometheus自动生成的指标,并使用表达式浏览器对指标进行简单的查询和图表展示。这为后续深入使用Prometheus进行应用监控打下了基础。
131:持续改进理念简介 🚀
在本节课中,我们将学习“改善”(Kaizen)这一核心理念。改善是一个源自日本汽车工业的术语,意指“持续改进”。它最初用于提升工厂日常的汽车生产质量,后来也完美融入了敏捷软件开发方法论中。敏捷开发正是通过不断优化小模块来改进软件的常用方法。

接下来,我们来看看本节课的学习目标。首先,我们将评估“改善”的最佳实践。改善是包括软件开发在内的众多领域的最佳实践。其次,我们将深入探讨一个名为“五个为什么”(Five Whys)的迭代过程,它与改善相关,能帮助你进行根本原因分析。
改善的核心原则 🎯
上一节我们介绍了改善的基本概念,本节中我们来看看其核心原则。改善强调从小处着手,通过持续的、渐进的改进来提升整体质量和效率,而非追求一次性的巨大变革。
以下是改善实践中的几个关键行动:
- 识别浪费:找出流程中所有不增加价值的活动。
- 标准化工作:为最佳实践建立清晰、可重复的步骤。
- 测量效率:使用关键指标来量化当前表现和改进效果。
- 鼓励参与:让团队每一位成员都参与到提出和改进想法的过程中。
“五个为什么”分析法 🔍
了解了改善的原则后,我们来看一个强大的辅助工具——“五个为什么”分析法。这是一个简单而有效的迭代提问技术,用于追溯问题的根本原因,而不仅仅是处理表面症状。
其操作公式可概括为:
对观察到的现象连续追问“为什么?”,通常重复五次,直至发现根本原因。
以下是应用“五个为什么”的步骤:
- 明确问题:清楚定义你要解决的问题。
- 首次提问:问第一个“为什么”会发生这个问题。
- 深入追问:针对上一步的答案,再次追问“为什么”。
- 重复过程:持续追问,通常进行四到五次。
- 制定对策:找到根本原因后,制定措施防止问题复发。

总结 📝

本节课中,我们一起学习了“改善”(Kaizen)这一持续改进理念。我们了解到它起源于制造业,并广泛应用于包括软件开发在内的现代领域。我们还探讨了“五个为什么”这一根本原因分析工具,它通过层层深入的提问,帮助我们找到问题的核心,从而实施有效的改善措施。掌握这些理念和工具,对于构建和维护高质量、可演进的大规模云计算解决方案至关重要。
132:高效持续改进实践 🚀
在本节课中,我们将学习什么是高效且持续的改进。我们将通过一个软件项目的具体例子,来理解为什么每日进行渐进式改进对于项目的长期成功至关重要。
什么是高效持续的改进?
上一节我们介绍了课程主题,本节中我们来看看“高效持续改进”的具体含义。
如果你思考一支运动队,那是一个人们希望持续改进的绝佳例子。他们希望提升举起的重量、能跑的距离或其他运动表现指标。你的源代码或基于云的项目也是如此,你总应该思考如何让它变得更好。如何让事情更透明,如何提高可靠性。在我职业生涯中参与的许多项目都没有这样做,这正是它们失败的原因之一,之后我不得不与他人合作介入并修复它。
一个项目失败的例子
理解了持续改进的概念后,我们来看一个因缺乏此实践而导致问题的具体案例。
我将给你一个例子。我曾在一家游戏公司工作,那里有一个项目,当我刚到那里时,它已经进行了大约一年,并且事实上已经被重写了好几次。当我真正开始接触这个项目并熟悉它时,我进行了检查。我查看了源代码,尝试在我的笔记本电脑上运行它。运行它花了大约一周时间,然后它导致我的整个笔记本电脑死机。我意识到这个特定的方法存在一个大问题。因此,我们必须做的是,系统地找出如何让事情变得更好,不是一次性修复所有问题,而是一点一点地来,找出错误,持续进行测试和持续改进。这个过程就是我修复许多问题的方法,包括那个特定的问题。
持续改进的核心原则
从上述案例中,我们可以看到持续改进的重要性。以下是其核心原则。
所以简而言之,持续改进是你的团队、你的公司可以做出的每日选择。事实上,你可以立即开始。很多时候,失败的原因在于没有一个每日持续尝试、每次只做一点点来解决问题的过程,以便你能找到根本原因,最终获得一个可靠的产品。
警惕持续退化
即使你做到了上述所有事情,了解这一点也很重要:虽然你可以持续改进,但你也可能持续退化。因此,即使你有一个出色的项目,一切都做对了,但如果你不每天努力让事情变得更好,这也会成为一个问题。有句俗话说:你要么在变得更好,要么在变得更糟。如果你不知道自己是哪一种,那你很可能在变得更糟。我想很多足球队会说这类话,但这在软件领域确实如此。你需要每天进行改进。
总结

本节课中,我们一起学习了高效持续改进的实践。我们了解到,持续改进是一个需要团队每日践行的选择,旨在通过渐进、系统化的方式提升代码和项目的质量与可靠性。我们通过一个反面案例看到了缺乏持续改进的后果,并认识到即使项目初期成功,若不坚持每日改进,也可能面临“持续退化”的风险。关键在于建立每日进行小幅度改进的习惯,以逐步解决问题并达成根本性的优化。
133:五问法解析 🕵️

在本节课中,我们将学习一种名为“五问法”的根因分析技术。这是一种通过连续提问来探究问题根本原因的互动方法,它常与“改善”(Kaizen)理念结合使用,以推动持续改进。
概述
五问法是一种迭代式的分析技术,旨在系统地找出问题的根本原因。它起源于与“改善”理念相近的时期,是持续改进生命周期中常用的工具。
五问法详解
上一节我们介绍了五问法的基本概念,本节中我们通过一个假设场景来具体看看它的应用过程。
假设你的组织总是延期交付产品。例如,你的移动应用发布不断被延迟。
以下是运用五问法进行分析的步骤:
-
第一问:为什么移动应用发布总是延迟?
回答:因为本周有一个新功能被临时加入了发布周期,导致了延迟。 -
第二问:为什么会有新功能被临时加入发布周期?
回答:通常我们执行两周的冲刺计划,但CEO临时要求必须立即加入这个功能。 -
第三问:为什么CEO会临时要求立即加入这个功能?
回答:因为CEO找不到项目经理,而项目经理当时正忙于和产品经理沟通。 -
第四问:为什么项目经理和产品经理无法妥善处理这个功能请求?
回答:他们未能就如何在合理时间内、通过正确规划来交付该功能达成一致。 -
第五问:为什么会出现这种沟通不畅的情况?
回答:根本原因在于存在轻微的沟通脱节。CEO不知道存在其他正式的功能请求途径。如果CEO知道直接联系开发人员会导致应用延迟,他就不会那么做。
这类细微的沟通错位问题时常发生。通过五问法,你可以触及问题根源,并找到永久性的解决方案。这种方法不仅适用于功能延期,也适用于分析软件缺陷、信息错误等任何你试图解决的问题。
总结

本节课中我们一起学习了五问法。五问法是“改善”理念的重要组成部分,其核心在于通过连续追问“为什么”来追溯问题根源。它是坚持正确做事并持续改进的关键方法,建议你在自己的环境中考虑使用它。

浙公网安备 33010602011771号