前后端部署:服务器、容器与 Serverless 分别解决什么问题
从一个普通的前端、API 和数据库应用出发,梳理部署方式的责任边界,以及什么时候需要容器编排。
机器翻译,未经作者审校。代码、公式与图片保留原样;可随时返回原文并与 AI 讨论。
目录
学习部署时,我把 Docker、Kubernetes、Serverless 和几个托管平台放在了一起。但这些名字其实不在同一个层次:有的是打包应用的方法,有的是管理应用运行的系统,有的是把一部分运维责任交给平台的服务方式。
我当时想弄清楚的问题很实际:如果我的项目只是一个前端、一个调用外部 API 的后端,再加上数据库,到底需要多复杂的部署?
这篇笔记始于 2025 年 11 月。整理时修正了原稿中的服务兼容性判断,并移除了已经停止服务的 MongoDB Data API 部署方案。它是一份概念梳理,不是某个平台的最新配置教程。
先把三个问题分开
部署首先要回答:代码在哪里运行?依赖怎么保持一致?程序出问题时由谁恢复?
服务器提供运行程序的机器环境。租一台云服务器后,可以直接在上面安装运行时,启动后端进程。域名、反向代理、证书、进程守护和系统更新,需要自己安排。
容器把应用和运行所需的文件、依赖封装在一起,让环境更容易重复。它可以运行在自己的服务器上,也可以交给托管平台。容器本身不会替我完成备份、监控和扩容。Docker 文档
Serverless描述的是一种服务与运维边界:我提交代码或工作负载,由平台管理底层计算资源。在函数式服务中,代码通常由请求或其他事件触发。我仍然要处理业务逻辑、权限、数据和错误,也需要适应平台的运行时与资源限制。
因此,服务器、容器和 Serverless 不是三个互斥的技术选项。用容器封装的服务也可以由平台按需运行;在自己租的机器上运行容器,也依然需要自己管理那台机器。
一个前后端应用,可以分别部署
前端和后端没有必要部署在一起。如果前端生成的是静态文件,可以交给静态托管服务和 CDN;需要服务端渲染的前端,则还需要相应的计算环境。
后端负责接收请求、检查权限、调用外部服务、读写数据库。数据库则有自己的持久化、备份和访问控制要求,不能因为后端用了容器就忽略这些工作。
浏览器 ──→ 前端页面
│
└────→ 后端 API ──→ 数据库
└─→ 外部 API
这个结构不要求特定的平台组合。关键是每一部分的地址、权限和生命周期清楚:浏览器访问公开接口,后端保存服务端凭据,数据库只接受允许的访问。
自己运行,还是交给平台
| 方式 | 主要负责什么 | 需要留意什么 |
|---|---|---|
| 自己管理服务器 | 系统、运行时、进程、网络和应用 | 更新、监控、备份、恢复是否有人维护 |
| 托管容器服务 | 镜像、配置和应用行为;基础设施由平台承担一部分 | 平台提供哪些恢复与扩缩容能力,持久化数据放在哪里 |
| 托管函数服务 | Handler、业务逻辑、权限和外部依赖 | 运行时兼容性、执行限制、连接方式与调用成本 |
容器对我的一个直接价值,是减少环境差异。如果程序需要特定系统依赖,例如媒体处理工具,镜像可以明确记录这些依赖。部署到自己的机器还是托管平台,是下一层选择。
函数式服务则适合把一些围绕请求展开的逻辑交给平台运行。但“REST API”这个标签本身还不足以决定部署方式:一个 API 可能很快返回,也可能在请求里运行很久的任务。要看真实工作负载,而不能只看接口形式。
Docker 后面不一定要接 Kubernetes
原来我画过这样的结构:应用代码 → Docker 容器 → Kubernetes → 云服务器集群。它描述了一种部署方式,但容易让人误以为每个项目都必须走完这几层。
Kubernetes 主要解决容器化工作负载的部署与管理,包括调度、扩缩容和故障恢复等问题。它也需要配置与维护,并不是加上之后所有运维工作就会自动消失。Kubernetes 概述
对于一个规模不大、服务数量有限的项目,可以先在一台服务器上运行进程或容器,也可以使用托管服务。是否引入编排系统,要看是否已经出现了多服务管理、可用性和团队协作方面的具体需求。高并发也不是唯一判断条件。
我从这份学习笔记里得到的一个判断是:先说清楚现在要解决哪一个运行问题,再增加相应的基础设施。
两个需要修正的判断
原稿把 Serverless 简化成“不能维持 TCP 连接”,又把 WebSocket 单独划到了容器一侧。这个分法不准确,能力取决于具体平台。例如 Cloudflare Workers 提供出站 TCP Socket API,也支持 WebSocket。是否能使用某个数据库驱动,还要继续核对运行时和连接管理方式,不能从“支持 TCP”直接推出“所有驱动都兼容”。TCP 文档、WebSocket 文档
原稿还推荐用 MongoDB Atlas Data API 连接数据库。该服务已于 2025 年 9 月 30 日结束生命周期,因此不应继续把它列为新项目的部署路径。这是整理时纠正的一处原始笔记错误。MongoDB 官方说明
真正开始部署之前
对一个“前端 + API + 数据库”的小应用,我会先回答这些问题:
- 前端是静态页面,还是需要服务端运行?
- 后端每次请求需要多久,是否依赖本地文件、原生库或后台任务?
- 数据库驱动能否在目标运行时里工作,连接和凭据如何管理?
- 出错后如何查看日志、恢复服务、回滚版本?
- 随着访问量增长,费用和资源限制会怎样变化?
回答这些问题之后,再决定是直接运行服务、制作容器镜像,还是适配函数式运行时,会比先选一套听起来完整的技术栈更清楚。