尧图网站建设 尧图网络
  • 首页
  • 关于我们
  • 服务项目
  • 案例展示
  • 建站流程
  • 资讯中心
  • 联系我们
首页/资讯中心/详情

一个完整的 AWS 无服务器架构教程 - 教程

一个完整的 AWS 无服务器架构教程 - 教程
📅 发布时间:2026/6/20 12:28:09

一个完整的 AWS 无服务器架构教程 - 教程

2025-11-27 14:22  tlnshuju  阅读(0)  评论(0)    收藏  举报

下面是一个完整的 AWS 无服务器架构教程,用于实现一个 OTA(Over-The-Air)固件更新服务。该服务提供两个 HTTP 接口:

  • GET /check:设备请求当前是否有可用更新(返回预签名 S3 URL)
  • POST /report:设备上报更新结果(成功/失败等)

组件说明:

  • API Gateway:暴露 REST API
  • Lambda:处理业务逻辑(鉴权、查询 DynamoDB、生成 S3 预签名 URL、写入回执)
  • S3:存储固件文件(如 firmware-v1.2.3.bin)
  • DynamoDB:存储设备信息、当前版本、目标版本、任务状态等

一、准备工作

1.1 AWS 账户与权限

确保你有权限创建以下资源:

  • API Gateway
  • Lambda
  • S3 Bucket
  • DynamoDB Table
  • IAM Roles/Policies

建议使用 AWS CLI + SAM(Serverless Application Model) 或 Terraform/CDK,但本教程以 控制台 + 手动配置 为主,便于理解。


二、创建 S3 存储桶(用于固件)

  1. 进入 S3 控制台
  2. 创建新存储桶,例如:my-ota-firmware-bucket-12345(全局唯一)
  3. 不要启用“阻止所有公共访问”以外的公开访问(固件通过预签名 URL 访问,无需公开)
  4. 记下存储桶名称

✅ 固件示例路径:s3://my-ota-firmware-bucket-12345/firmware/device-type-a/v1.2.3.bin


三、创建 DynamoDB 表

表名:OtaDevices

主键设计:

  • 分区键(Partition Key):deviceId(字符串,如 device-001)

其他属性(可选,根据业务扩展):

字段名类型说明
currentVersionstring当前固件版本
targetVersionstring目标固件版本(若为空则无更新)
deviceTypestring设备类型(用于选择固件)
lastCheckstring最后一次检查时间(ISO8601)
updateStatusstringpending / downloaded / applied / failed
firmwareKeystringS3 中的固件对象键(如 firmware/device-type-a/v1.2.3.bin)

创建步骤:

  1. 进入 DynamoDB 控制台
  2. 点击“创建表”
  3. 表名:OtaDevices
  4. 分区键:deviceId(类型:字符串)
  5. 其他保持默认,点击“创建表”

示例数据:

{
"deviceId": "device-001",
"currentVersion": "v1.1.0",
"targetVersion": "v1.2.3",
"deviceType": "sensor-x1",
"firmwareKey": "firmware/sensor-x1/v1.2.3.bin",
"updateStatus": "pending"
}

四、创建 Lambda 函数

我们将创建一个 Lambda 函数,处理 /check 和 /report 逻辑。

4.1 创建 Lambda

  1. 进入 Lambda 控制台
  2. 点击“创建函数” → “从头开始创作”
  3. 名称:OtaHandler
  4. 运行时:Python 3.12(或 Node.js 18.x,本教程用 Python)
  5. 权限:创建新角色(稍后手动添加权限)

4.2 编写代码(Python)

import json
import boto3
import os
from datetime import datetime, timedelta
from botocore.exceptions import ClientError
# 初始化客户端
dynamodb = boto3.resource('dynamodb')
s3_client = boto3.client('s3')
table = dynamodb.Table(os.environ['DYNAMODB_TABLE'])
BUCKET_NAME = os.environ['S3_BUCKET']
def lambda_handler(event, context):
print("Event:", json.dumps(event))
# 获取 HTTP 方法和路径
http_method = event['httpMethod']
resource_path = event['resource']
# 简单鉴权:检查 header 中的 token(实际应使用更安全机制,如 JWT、API Key)
auth_token = event['headers'].get('Authorization') or event['headers'].get('authorization')
if not auth_token or not auth_token.startswith("Bearer "):
return {
'statusCode': 401,
'body': json.dumps({'error': 'Missing or invalid Authorization header'})
}
device_id = auth_token.split(" ")[1]  # 假设 token 是 "Bearer <deviceId>"try:if resource_path == '/check' and http_method == 'GET':return handle_check(device_id)elif resource_path == '/report' and http_method == 'POST':body = json.loads(event['body']) if event.get('body') else {}return handle_report(device_id, body)else:return {'statusCode': 404, 'body': json.dumps({'error': 'Not found'})}except Exception as e:print("Error:", str(e))return {'statusCode': 500, 'body': json.dumps({'error': 'Internal error'})}def handle_check(device_id):# 1. 查询设备信息response = table.get_item(Key={'deviceId': device_id})if 'Item' not in response:return {'statusCode': 404, 'body': json.dumps({'error': 'Device not found'})}item = response['Item']# 2. 检查是否有待更新if not item.get('targetVersion') or item.get('currentVersion') == item.get('targetVersion'):return {'statusCode': 200,'body': json.dumps({'updateAvailable': False})}# 3. 生成预签名 URL(有效期 10 分钟)firmware_key = item['firmwareKey']try:presigned_url = s3_client.generate_presigned_url('get_object',Params={'Bucket': BUCKET_NAME, 'Key': firmware_key},ExpiresIn=600  # 10 分钟)except ClientError as e:return {'statusCode': 500, 'body': json.dumps({'error': 'Failed to generate URL'})}# 4. 更新 lastCheck 时间table.update_item(Key={'deviceId': device_id},UpdateExpression="SET lastCheck = :t",ExpressionAttributeValues={':t': datetime.utcnow().isoformat()})return {'statusCode': 200,'body': json.dumps({'updateAvailable': True,'version': item['targetVersion'],'downloadUrl': presigned_url,'firmwareKey': firmware_key})}def handle_report(device_id, report_data):# 报告内容示例:{"status": "success", "message": "Applied v1.2.3"}status = report_data.get('status', 'unknown')message = report_data.get('message', '')# 更新设备状态table.update_item(Key={'deviceId': device_id},UpdateExpression="SET updateStatus = :s, currentVersion = :v, lastReport = :t",ExpressionAttributeValues={':s': status,':v': report_data.get('version', 'unknown'),':t': datetime.utcnow().isoformat()})return {'statusCode': 200,'body': json.dumps({'message': 'Report received'})}

4.3 配置环境变量

在 Lambda 函数的“配置” → “环境变量”中添加:

键值
DYNAMODB_TABLEOtaDevices
S3_BUCKETmy-ota-firmware-bucket-12345

4.4 添加 IAM 权限

编辑 Lambda 的执行角色(在“配置” → “权限”中点击角色名),附加以下策略:

{
"Version": "2012-10-17",
"Statement": [
{
"Effect": "Allow",
"Action": [
"dynamodb:GetItem",
"dynamodb:UpdateItem"
],
"Resource": "arn:aws:dynamodb:YOUR_REGION:YOUR_ACCOUNT:table/OtaDevices"
},
{
"Effect": "Allow",
"Action": [
"s3:GetObject"
],
"Resource": "arn:aws:s3:::my-ota-firmware-bucket-12345/*"
}
]
}

替换 YOUR_REGION 和 YOUR_ACCOUNT(或直接使用控制台 ARN)


五、配置 API Gateway

5.1 创建 REST API

  1. 进入 API Gateway 控制台
  2. 点击“创建 API” → “REST API” → “构建”
  3. 选择“新建 API”,名称:OtaApi,端点类型:Regional

5.2 创建资源和方法

创建 /check 资源
  • 在“资源”中点击“操作” → “创建资源”
    • 资源名称:check
    • 资源路径:check
  • 选中 /check,点击“操作” → “创建方法” → 选择 GET → 勾选“使用 Lambda 代理集成”
  • Lambda 函数:选择 OtaHandler
  • 点击“保存”,确认权限
创建 /report 资源
  • 同样创建资源 report
  • 添加 POST 方法,同样指向 OtaHandler,启用 Lambda 代理集成

5.3 部署 API

  1. 点击“操作” → “部署 API”
  2. 新建阶段(如 prod)
  3. 记下调用 URL,例如:
    https://abc123.execute-api.us-east-1.amazonaws.com/prod

六、测试流程

6.1 上传固件到 S3

aws s3 cp firmware/sensor-x1/v1.2.3.bin s3://my-ota-firmware-bucket-12345/firmware/sensor-x1/v1.2.3.bin

6.2 在 DynamoDB 插入测试设备

{
"deviceId": "device-001",
"currentVersion": "v1.1.0",
"targetVersion": "v1.2.3",
"deviceType": "sensor-x1",
"firmwareKey": "firmware/sensor-x1/v1.2.3.bin",
"updateStatus": "pending"
}

6.3 调用 /check

curl -H "Authorization: Bearer device-001" \
https://abc123.execute-api.us-east-1.amazonaws.com/prod/check

✅ 响应示例:

{
"updateAvailable": true,
"version": "v1.2.3",
"downloadUrl": "https://my-ota-firmware-bucket-12345.s3.amazonaws.com/...?X-Amz-Signature=..."
}

6.4 调用 /report

curl -X POST \
-H "Authorization: Bearer device-001" \
-H "Content-Type: application/json" \
-d '{"status": "success", "version": "v1.2.3"}' \
https://abc123.execute-api.us-east-1.amazonaws.com/prod/report

✅ 响应:{"message": "Report received"}


七、安全增强建议(生产环境)

  1. 鉴权升级:

    • 使用 API Gateway 的 自定义授权方(Custom Authorizer) 或 Cognito
    • 或使用 API Key + Usage Plan
  2. 输入验证:

    • 在 Lambda 中校验 deviceId 格式
    • 防止路径遍历(如 firmwareKey 不应包含 ../)
  3. 日志与监控:

    • 启用 CloudWatch Logs
    • 设置告警(如大量 401 请求)
  4. S3 安全:

    • 确保 S3 存储桶策略禁止公开读取
    • 启用服务器端加密(SSE-S3)
  5. Lambda 超时与内存:

    • 设置合理超时(如 10 秒)
    • 内存 128MB 足够

八、清理(避免产生费用)

  • 删除 API Gateway
  • 删除 Lambda 函数
  • 清空并删除 S3 存储桶
  • 删除 DynamoDB 表

✅ 至此,你已成功搭建一个基于 AWS 的 OTA 固件分发服务!

相关新闻

  • 工业自动化航空发动机零部件加工发那科 CNC 与贝加莱 PLC Modbus 协议转换方案
  • 口碑好的治疗白带异常品牌解析与推荐
  • 小学与幼儿园研学基地哪个好?为你推荐广州文搏科普小镇

最新新闻

  • 终极指南:如何在Windows 11上安装免费Bili.UWP客户端享受原生B站体验
  • 抖音有实力的直播公会推荐 - 速递信息
  • 使用acme.sh获取免费泛域名SSL证书:从DNS验证到自动化部署
  • 2026年6月最新天梭中国官方售后热线服务电话客户地址网点 - 天梭服务中心
  • 2026上海黄金变现去哪靠谱?本地5家正规回收渠道深度拆解,第1家真的全能无短板 - 速递信息
  • 基于ACME协议的SSL证书自动化管理:从原理到实践

日新闻

  • 信任的进化:技术实现详解——如何用JavaScript构建博弈论模拟器
  • Terrakube自定义工作流:如何集成OPA、Infracost等工具扩展IaC能力
  • grunt-concurrent快速入门:5分钟学会并行运行Grunt任务

周新闻

  • 3步解锁iOS设备:applera1n激活锁绕过完全指南
  • 39 2026 人工智能证书终极盘点,普通人选 AI 证书可以从这些方向入手
  • Redis 暴露公网有多危险?从端口检查到补救步骤

月新闻

  • 【总结】入门篇:50句话让你记住架构核心概念
  • WeChatMsg技术方案解析:实现Mac微信数据自主管理的完整解决方案
  • WeChatMsg:革新性微信数据备份方案,打造你的专属数字记忆库

关于尧图

  • 公司简介
  • 团队介绍
  • 企业文化
  • 荣誉资质

服务项目

  • 定制开发
  • 电商建站
  • UI 设计
  • 运维服务

快速链接

  • 案例展示
  • 建站流程
  • 常见问题
  • 资讯中心

联系方式

  • 📍北京市朝阳区互联网产业园 A 座 10 层
  • 📞400-888-8888
  • ✉️contact@rkmt.cn
  • 🕐周一至周日 9:00-21:00

© 2024 北京尧图网络科技有限公司 版权所有 | 京 ICP 备 XXXXXXXX 号