Azure 静态 Web 应用非常棒
我们需要讨论无服务器
Azure 静态 Web 应用程序到底是什么?
创建你的第一个静态 Web 应用程序
那起了什么作用?
这仅仅是网站托管吗?有什么特别之处?
添加 API
我很喜欢它,但我可以在本地运行它吗?
添加一些有用的脚本
哦不!构建失败!
“但是 David!你是 TDD 专家吧?你怎么测试这个!”
你提到了 TypeScript?
但是让我们更大胆一点,C# 怎么样!
我认为这真的很棒
在过去三个月左右的时间里,我一直在网络上开发很多实验性的软件。有的很傻,有的很有趣。与此同时,我也一直在尝试各种托管现代 Web 内容的方法。
我经历过托管事物的艰辛Glitch
,因为它具有交互性,Heroku
可以获得 Node 后端,甚至Azure App Services
运行我的节点进程。
但每次把一件小事发布到互联网上,我都感觉需要付出努力和成本。
一切都是在努力、复杂性或功能方面做出的妥协。
因此,当微软几个月前推出静态 Web 应用程序测试版时,我非常渴望尝试一下。
它们仍处于测试阶段,文档有点少,代码还很粗糙,但它们是 2020 年构建 Web 应用程序的绝佳方式,并且运行成本几乎为零(实际上,在此测试版期间它们是免费的)。
我想向您解释它们为什么很棒,如何设置它们,以及如何针对不同的编程语言定制它们,同时涉及如何处理本地开发和调试。
我们需要讨论无服务器
这是一个经常被提及的笑话——云只是其他人的计算机,而无服务器,打个比方,只是其他人的应用服务器。
虽然这种说法有一定的道理——在云供应商的某个地方,有一台“计算机”——但它看起来肯定和你想象的完全不一样。
您上次将这样的台式电脑浸入海底是什么时候?
虽然云是“别人的计算机”,无服务器是“别人的服务器”——它也是别人的硬件抽象,需要管理团队和 SLA 来满足,由别人的专家操作——但云和无服务器都使计算机和服务器成为别人的问题,从而使您的生活变得更加轻松。
2020 年,随着像Netlify
和这样的平台Vercel
采用 PaaS 抽象并在其基础上迭代产品,我们很高兴看到微软多年来一直在 Azure 中提供出色的 PaaS 产品,现在开始将目光瞄准为“普通 Web 开发者”提供易于使用的产品。
一旦你删除听起来很愚蠢的 JAMSTACK 首字母缩略词,运送依赖 API 进行交互的 HTML 和 JavaScript Web 应用程序,这是一种非常常见的情况,并且在这个领域构建低摩擦工具的人越多越好。
让我们首先看看 Azure 静态 Web 应用程序如何以常规的“jamstack-ey”方式工作,然后我们将看到它们如何变得更加神奇。
Azure 静态 Web 应用程序到底是什么?
Azure Static Web Apps
目前是产品中的测试版新托管选项Azure-WebApps family
。
它们是一种在 URL 上快速托管一些静态文件(HTML 和 JavaScript)的简单方法,并且可以为您处理所有的扩展和内容分发。
它们的工作原理是将 GitHub 中的存储库连接到 Azure 门户的“静态 Web 应用”产品,然后门户会配置你的存储库以实现持续交付。这是一种良好的端到端体验,让我们来了解一下它是什么样子的。
创建你的第一个静态 Web 应用程序
我们将首先在 GitHub 上创建一个新的存储库 -
index.html
并向其中添加一个文件...
太棒了,你的第一个静态网站就建好了,是不是很棒?根目录下的 HTML 文件就是我们完整的用户体验。
完美!我太喜欢了。
我们现在需要跳转到 Azure 门户并将我们的新存储库添加为静态站点。
这个过程的妙处在于,Azure 门户将在我们的存储库中配置 GitHub 操作,并添加安全密钥,以为我们配置部署。
我们只是为新站点提供一个资源组(如果您以前没有使用过 Azure,则创建一个资源组 - 资源组只是 Azure 中一堆东西的标签)并选择我们的 GitHub 存储库。
一旦我们点击“Review + Create”,我们就会看到最终配置。
我们可以继续创建我们的应用程序。
创建过程完成后(令人困惑的消息是“部署已完成”) - 您可以单击“转到资源”按钮来查看新的静态 Web 应用程序。
您已在线!
我确实认为这可能是当今将 HTML 上传到互联网的最简单的方法。
首先假设您设法击败 Microsoft Active Directory Boss Monster 并登录 Azure ;)
那起了什么作用?
如果我们现在刷新我们的 GitHub 页面,您将看到当您授予 Azure Create 进程提交到您的存储库的权限时,它使用了它们。
在 Azure 门户中创建静态 Web 应用时,它会执行两项操作:
- 创建了一个构建脚本,并将其提交到你的存储库
- 向您的存储库设置添加了部署机密
生成的构建脚本相对较长,但您不必亲自触及它。
它配置 GitHub 操作,以便在您每次提交到主分支时构建和推送您的代码,并在您打开拉取请求时创建特殊的预览环境。
每次修改此构建脚本以引用 Azure 门户生成的部署机密。
您将注意到密钥在您的存储库中排列。
这仅仅是网站托管吗?有什么特别之处?
到目前为止,这很简单,但也完全没有什么令人兴奋的——然而,Azure Static Web Apps 的特别之处在于它们与 Azure Functions 的无缝集成。
传统上,如果您想为静态 Web 应用程序添加一些交互性,则必须在某处建立一个 API -Static Web Apps
将这两件事结合在一起,并允许您在同一个存储库中定义 Azure 静态 Web 应用程序和它将调用的一些 Azure 函数。
这真是太酷了,因为你还没有服务器!
但你可以运行服务器端代码!
它特别出色,因为您的应用程序所依赖的服务器端代码是与依赖它的代码一起进行版本控制和部署的。
让我们为静态应用程序添加一个 API!
添加 API
默认情况下,为您的应用程序生成的配置需要在 /api 目录中找到一个 Azure Functions 应用程序,因此我们将使用 npm 和 Azure Functions SDK 来创建一个。
在撰写本文时,Functions 运行时仅支持最高 Node 12(Node 的最新 LTS 版本),并跟踪该版本进行更新。
您需要安装节点并将其放在您的路径中,以便本教程的下一部分能够正常工作。
首先,让我们检查一下我们的存储库
确保已通过运行安装Azure Functions Core Tools
npm install -g azure-functions-core-tools\@3
现在我们将运行一些命令来创建 Azure 函数应用程序。
mkdir api
cd api
func init --worker-runtime=node --language=javascript
这会在 API 目录中生成一个默认的 JavaScript+Node 函数应用,我们只需要创建一个函数供 Web 应用调用即可。回到命令行,输入(仍然在 /api 目录中)
func new --template "Http Trigger" --name HelloWorld
这将在您的 API 目录中添加一个名为 HelloWorld 的新函数
这些绑定会告诉 Azure Functions 运行时如何处理你的代码。SDK 将生成一些实际运行的代码……
让我们编辑 HTML 来调用这个函数。
我们正在使用浏览器的 Fetch API 来调用“/api/HelloWorld”——Azure Static Web Apps 将按照该模式提供我们的功能。
让我们将这些更改推送到 git,然后等待一两分钟以运行我们的部署。
如果我们现在加载我们的网页,我们将看到以下内容:
这真是太棒了——一个服务器端 API,无需服务器,只需来自目录中的几个静态文件。
如果再次打开 Azure 门户并选择“函数”,您将看到 HelloWorld 函数现在显示出来:
我很喜欢它,但我可以在本地运行它吗?
当然!
微软建议使用 npm 包live-server
来运行应用程序的静态部分进行开发,您只需输入
npx 实时服务器
从你的仓库根目录开始。现在就来试试吧
哦不!这是怎么回事?
嗯,live-server
这就像把目录当成内容一样处理/api
,并在本地提供索引页,这不是我们想要的。为了让它像在生产环境中一样运行,我们还需要运行 Azure Functions 运行时,并告诉 Live Server 将所有调用代理到/api
正在运行的实例上。
听起来有点拗口,但我们还是尝试一下吧。
cd api
npm i
func start
这将在本地运行 Azure Functions 运行时。
您将看到类似以下内容
现在,在另一个控制台选项卡中,让我们再次启动 live-server,这次告诉它代理调用/api
npx live-server --proxy=/api: http://127.0.0.1:7071/api
如果我们现在访问 8080 上的本地主机,您会看到我们的行为与在 Azure 中的行为完全相同。
很棒,但对于本地开发来说,这一切似乎有点……繁琐。
如果您在 Visual Studio Code 中打开根目录,它将提示它具有用于调试和开发的浏览器扩展支持,但我更喜欢将这些内容捕获到我的存储库中,以便任何人都可以轻松地从命令行运行这些站点。
添加一些有用的脚本
我不知道你怎么样,但我总是忘记一些事情,所以让我们在一些脚本中捕捉一些内容,npm
这样我就不用再记住它们了。
我们/api/package.json
将添加两个有用的 npm 任务
这只是意味着我们可以调用npm run start
该目录来启动我们的函数运行时。
接下来,我们将添加package.json
到我们的存储库的根目录,以便我们可以在一个地方捕获所有与实时服务器相关的命令。
从命令提示符类型:
npm init
并在默认选项之后按几次回车键——你最终会得到类似这样的结果
最后,添加npm-run-parallel
包
npm 安装 npm-run-all –save-dev
我们将在这个默认设置中添加更多脚本package.json
这里我们设置了一个dev:api
,dev:server
和一个start
任务来自动执行上面我们必须执行的命令行工作。
所以现在对于本地开发我们只需输入
npm 运行启动
我们的环境的工作方式与在 Azure 上完全一样,我们无需记住所有这些东西,而且我们可以在工作时看到我们的更改被热加载。
让我们提交它并确保它仍然可以在 Azure 上运行!
哦不!构建失败!
好的,我想这就是我们的油漆滴落得有点湿的地方。
添加该根package.json
可以使我们的生活更轻松,但实际上破坏了我们的 GitHub Actions 部署管道中的某些东西。
如果我们深入研究日志,就会发现名为“Oryx”的程序无法找到构建脚本,并且不知道如何处理自己
事实证明,Azure 静态 Web 应用程序中蕴含的智慧是一种名为 Oryx 的工具,它需要它能够理解的框架,并运行某种语言检测。
发生的事情是,它发现了我们的package.json
,假定我们将指定我们自己的构建作业,并且我们不再是一个静态站点,但是当我们没有提供构建任务时,它就放弃了,因为它不知道
该做什么。
我发现能够使用节点工具并且仍然可以与 Azure 的自动部署引擎很好地配合的最简单方法是做两件事:
- 将我们的静态资产移动到“app”目录中
- 更新我们的部署脚本以反映这一点。
首先,让我们创建一个应用程序目录,并将我们的 index.html 文件移动到其中。
现在我们需要编辑 Azure 生成的 YAML 文件.github/workflows
这听起来可能有点吓人,但我们实际上只改变了一件事——在作业部分,在当前生成的示例的第 30 行有三个配置设置——
我们只需要更新app_location
为“应用程序”。
最后,我们需要更新添加的 npm 脚本,以确保live-server
从正确的位置为我们的应用程序提供服务。
在我们的根目录中package.json
,我们需要将“app”添加到我们的dev:server
构建任务中
我们还将添加一项名为build:azure
“-”的任务,并将其留空。
总的来说,我们只对几个文件进行了细微的更改。
您可能希望现在再次运行您的npm run start
任务以确保一切仍然正常(应该如此!)并提交您的代码并将其推送到 GitHub。
精彩的。
一切又恢复正常了。
“但是 David!你是 TDD 专家吧?你怎么测试这个!”
我想这真的很酷——现在我们已经配置了一个构建任务,并且知道我们可以在哪里配置app_artifact_location
——我们几乎可以做任何我们想做的事情。
- 想用 Jest 吗?绝对管用!
- 想用 Wallaby 之类的好东西吗?也来试试!
为什么不同时进行呢!
您只需要 npm 安装您想要的东西,然后您就可以在静态站点和 API 中测试 JavaScript。
您可以安装 webpack 并生成不同的捆绑输出,使用 svelte 等任何东西,Microsoft 的工具将确保托管和扩展您的 API 和 Web 应用程序。
我处理静态网站的标准“开发”配置是
- 添加一些开发依赖项
- 将此默认
babel.config.js
文件添加到我的存储库的根目录
这允许jest
使用我当前版本node
支持的任何语言功能,并且可以与我的所有 Visual Studio Code 插件很好地兼容。
我还将使用此默认Wallaby.conf.js
配置*进行连续测试运行器Wallaby.js
- 它类似于 NCrunch,但适用于 JavaScript 和 TypeScript 代码库。
你提到了 TypeScript?
啊,是的,Azure Functions 运行时完全支持 TypeScript。
创建 API 时,你只需要
func init --worker-runtime=node --language=typescript
生成的 API 将是 TypeScript——真的就这么简单。
同样,您可以为常规静态 Web 应用程序配置 TypeScript,您可能希望配置 WebPack 来执行编译和捆绑到资产文件夹中,但它运行得非常好。
当使用 TypeScript 创建函数时,每个函数旁边都会创建一些额外的 .json 元数据,这些元数据指向已编译的“dist”目录,该目录是在 Azure 函数运行时部署代码时构建的,并附带源映射,开箱即用。
但是让我们更大胆一点,C# 怎么样!
您也可以完全使用 C# 和 .NET Core!
如果您func init
使用 worker dotnet,SDK 将生成与 JavaScript 和 TypeScript 完全相同工作的 C# 函数代码。
您可以真正运行静态 Web 应用程序,并使用自动缩放的 C# .NET Core API 支持它。
Azure Functions 运行时支持的任何内容在这里都是有效的(python 也是如此)。
我认为这真的很棒
我希望通过将其分解为微小的步骤,并解释 GitHub Actions 如何构建、如何与 Functions 运行时和Oryx
驱动的部署引擎进行交互Azure Static Web Apps
,为您提供一些灵感,让您可以免费构建各种可轻松扩展的 Web 应用程序。
如果您是一家 C# 商店,稍微偏离了 ASP.NET MVC 的舒适区,为什么不使用 Statiq.Web 作为构建过程的一部分来生成使用 C# 并由 C# 和 .NET Core API 驱动的静态 WebApps?
只熟悉 Python?您可以使用 Pelikon 或 Lector来做同样的事情。
背后的 Oryx 构建过程非常灵活,并提供了大量的钩子来定制存储库拉取和站点服务和扩展之间的构建行为。
这些强大的无服务器抽象让我们能够用更少的资源做更多的事情,而不用担心中断、停机或扩展。
您真的可以在五到十分钟内从零开始在 Azure 静态站点上工作,而且我真诚地认为这是当今在互联网上托管内容的最佳方式之一。
文章来源:https://dev.to/david_whitney/azure-static-web-apps-are-awesome-4dn2