Day 30 - 实作 Amazon API GateWay 整合 AWS Lambda 与 Dynamodb

Day 30 - 实作 Amazon API GateWay 整合 AWS Lambda 与 Dynamodb

Amazon API GateWay 简介

Amazon API Gateway 是由 AWS 提供的完全托管服务,使开发者可以创建、发布、维护、监控和保护任意规模的 API,可以使用它来创建充当应用程序前门的 RESTful 和 WebSocket API。这样,应用程序可以从後端服务访问数据、业务逻辑或功能,例如在 Amazon Elastic Compute Cloud (Amazon EC2)上运行的应用程序、在 AWS Lambda 上运行的代码、任何 Web 应用程序或即时通信应用程序。

API Gateway 负责处理所有任务,涉及接受和处理成千上万个并发 API 调用,包括流量管理、授权和访问控制、监控,以及 API 版本管理。更重要的是,API Gateway 没有最低费用或启动成本,只需为收到的 API 调用以及传出的数据量付费。

下图说明 Amazon API Gateway 的架构,在此架构图中,前端用户端应用程序和应用程序服务通过网际网路向API Gateway 发送 API 请求。API Gateway 负责管理所有这些请求并将其发送到 EC2 实例上运行的服务器、Virtual Private Cloud (VPC)中或网际网路上的任何位置。
使用 API Gateway 与其他 AWS 托管服务就可以为我们的应用程序构建无服务器後端,这意味着开发者无需维护任何服务器。比方说,API Gateway 可以将请求代理到 Lambda 函数,该函数运行代码并生成回应。

https://ithelp.ithome.com.tw/upload/images/20210930/20129510nnFqgmYMGV.png
图 1、Amazon API Gateway 架构

一般的 API 介面,直接面对的就是服务器後端,所以直接就是以 HTTP 请求/回应 (Request/Response) 格式,作为前後端沟通的协定,但因为 Amazon API Gateway 对应到的後端可能是各式各样的 AWS 服务(终端节点),所以 Amazon API Gateway 提供了多一层的转换对应,以方便将 HTTP 请求/回应 转换成不同的 AWS 服务可以接受的格式,这一层称之为整合请求/回应,也就是内部介面所涵盖的部份。Amazon API Gateway 和 AWS 服务的整合图形如下。

https://ithelp.ithome.com.tw/upload/images/20210930/20129510FwjmzjYm0G.png
图 2、Amazon API Gateway 和 AWS 服务的整合

考虑构建的 Amazon API Gateway 要提供服务的对象,我们可以把 API 终端节点分为以下三类:

  • 边缘优化 (Edge):边缘优化的 API 终端节点是公开可用的终端节点,旨在降低部署到距用户端地理位置更近的 Amazon CloudFront 分布上的 API 的延迟。
  • 区域性 (Region):区域性 API 终端节点是公开可用的终端节点,旨在当 API 请求和您的 REST API 源自相同的 AWS 区域时降低延迟。
  • 私有 (Private):私有 API 终端节点旨在将 API 仅公开给您的 Virtual Private Cloud (VPC) 中的服务和资源。

https://ithelp.ithome.com.tw/upload/images/20210930/20129510coy56JxceS.png
图 3、Amazon API Gateway 终端节点类型

Amazon API Gateway 开发和部署步骤:

  • 创建 API。
  • 控制对 API 的访问。
  • 测试 API 方法。
  • 部署和配置 API。
  • 调用 API。
  • 监控 API 执行。

实作 Amazon API GateWay 整合

接着要将 Day 29 - AWS Lambda 接收参数查询 Dynamodb 所设计的 AWS Lambda 整合到 Amazon API GateWay,需要完成的事情如下:

  • 修改 Lambda 函式的执行角色,使其取得写入 CloudWatch 日志群组 (Log groups) 的许可权。
  • 建立 Amazon API GateWay 与 Lambda 函式的整合
  • 使用 curl 来测试 Restfule API
  • 使用 CloudWatch 日志群组除错
  • 使用 Advanced Rest Client 来测试 GET 与 POST 方法

整合最大的问题 Amazon API GateWay 最大的问题是执行出现问题,看不到报错的讯息,所以在整合之前一定要先把除错功能先打开,而 CloudWatch 就是 AWS 提供最重要的除错服务之一 (Cloud Trail也是不错的选择),所以要先把 Day 29 - AWS Lambda 接收参数查询 Dynamodb 所设计的 Lambda 函数 getDataFromDynamoDB,把它所属的执行角色 LambdaDynamoDB,新增写入 CloudWatch 日志群组 (Log groups) 的许可权。

打开 AWS Lambda 控制台,选择 getDataFromDynamoDB Lambda 函数,在下方的操作视窗中,选择 组态 页签,单击 许可 功能,就可以看到本函数的执行角色 LambdaDynamoDB,如下图所示。

https://ithelp.ithome.com.tw/upload/images/20210930/20129510BAMEdpC5oA.png
图 4、Lambda 函数的执行角色

点击 LambdaDynamoDB 会打开 Identity and Access Management (IAM) 控制台,在 许可 页签中,单击 连接政策,如下图所示。

https://ithelp.ithome.com.tw/upload/images/20210930/20129510io90XdbKQ2.png
图 5、IAM 控制台进行角色连接政策

在连接许可画面中,在查询文字框中输入 AWSLambdaBasicExecutionRole ,选取後,点击下方的 连接政策

https://ithelp.ithome.com.tw/upload/images/20210930/20129510ieDjJCvN6X.png
图 6、IAM 角色连接 AWSLambdaBasicExecutionRole 许可政策

回到图 5的角色进行连接政策画面,这时候会看到 Permissions policies 变成是 Permissions policies (2 套用的多个政策),点击 AWSLambdaBasicExecutionRole 许可政策,可以看到许可政策内容,都是针对 CloudWatch Logs 的存取权限,如下图所示。

https://ithelp.ithome.com.tw/upload/images/20210930/20129510m0FM0HEwWV.png
图 7、检视 AWSLambdaBasicExecutionRole 许可政策的内容

打开 API Gateway 控制台,点选左侧功能选单的 API,接着在右手边的主画面点击 建立API,如下图所示。

https://ithelp.ithome.com.tw/upload/images/20210930/201295105N97WNlcCk.png
图 8、建立新的 API

在选择 API 类型画面中,要选第一个 REST API,後一个是针对私有的 REST API,选择完毕後,点击 建置,如下图所示。

https://ithelp.ithome.com.tw/upload/images/20210930/20129510SHevFWf9jK.png
图 9、选择 API 类型

在选择通讯协定画面中,配置设定如下:

  • 选取您想要建立 REST API 还是 WebSocket API: REST
  • 建立新的 API: 新 API
  • API 名称: dynamodb
  • 描述: 读取dynamodb
  • 端点类型: 区域性

结果如下图所示。

https://ithelp.ithome.com.tw/upload/images/20210930/20129510ztBXsnbLvp.png
图 10、选择 API 通讯协定设定画面

进入 API: dynamodb 设定画面,在资源窗格中,选择资源根,其以一条正斜线表示 (/),然後点击 操作 按钮,选择 建立资源。在右手边的操作 新的子资源 设定介面中,设定如下:

  • 设定为代理资源: 不勾选
  • 资源名称: fish
  • 资源路径: /fish
  • 启用 API 闸道 CORS: 不勾选

结果如下图所示。

https://ithelp.ithome.com.tw/upload/images/20210930/20129510L2seazMW0V.png
图 11、建立 API: dynamodb 新资源

在 资源窗格中,选择 /fish,然後点击 操作 按钮,选择 建立方法,对於 HTTP 方法,选择 ANY,然後储存,ANY 方法表示它可以接受任何的 HTTP 请求,不论是 GET, POST, PUT 还是其他,主要的判断是在接受这个请求的 AWS 服务,以这个案例来说,就是 Lambda 函数。操作画面如下图所示。

https://ithelp.ithome.com.tw/upload/images/20210930/20129510CfAVoIh2er.png
图 12、建立 API: dynamodb 新方法

在方法设定画面中,设定如下:

  • 整合类型: Lambda 函数
  • 使用 Lambda 代理整合: 勾选
  • Lambda 区域: ap-southeast-1
  • Lambda 函数: getDataFromDynamoDB
  • 使用预设逾时: 勾选

确认後,点击 储存,操作画面如下。

https://ithelp.ithome.com.tw/upload/images/20210930/20129510h3kWFXljFr.png
图 13、建立 API: dynamodb 新方法的设定
此时会弹出一个 新增Lambda函数的许可 画面,只要是要授权给 API Gateway 允许它调用 Lambda 函数,画面如下图所示。

https://ithelp.ithome.com.tw/upload/images/20210930/20129510eCXQlvFO2i.png
图 14、新增 API: dynamodb 调用 Lambda 的许可权

完成了 API Gateway 的所有设定,最後要做的就是部署 API,透过部署让其他使用者可以调用,部署阶段为 新阶段,阶段名称为 v1 (自行决定),画面如下图所示。

https://ithelp.ithome.com.tw/upload/images/20210930/20129510KLQsUeEUBf.png
图 15、部署 API: dynamodb

部署 API 完成後,会出现给外部使用者呼叫用的 URL,使用者可以透过这个网址,来调用 Lambda 函数的服务,画面如下图所示。

https://ithelp.ithome.com.tw/upload/images/20210930/20129510PbflguzHSj.png
图 16、v1 的部署组态

最简单的测试方式是使用 curl 的命令列方式直接呼叫,这种方式最大的好处是可以看到传输中的所有请求跟回应讯息。以下指令是透过 curl 发出 get 请求,对象是先前部署好的 API [APIGATEWAY_DEPLOY],并传递参数 key=1 ,希望能让 Lambda 函数可以回传编号为 1 的观赏鱼讯息。

curl -v -X GET 'https://[APIGATEWAY_DEPLOY]/fish?key=1' -H 'content-type: application/json' 

执行命令後,我们得到一连串的输出,前面有 * 号的讯息可以不用理会,出现句首有 > 符号的才是实际的请求跟回应,透过 curl 发出 HTTP 2.0 格式的请求,而 API Gateway 回传的讯息是 502,服务器内部错误,通常这种错误都是後端程序执行失败所造成,详细输出可以检视下图。

https://ithelp.ithome.com.tw/upload/images/20210930/20129510C5lDDbAM5N.png
图 17、使用 curl 检验 API

很幸运的,Lambda 函数执行错误了,但问题是我们看不到错误讯息,到底是哪一行导致的,於是,来到 AWS Lambda 的控制台,进到 getDataFromDynamoDB 这个 Lambda 函数的主画面中,再下方找到 监控 页签,并点击 日志 按钮,可以在下方的列表中找到最近的几笔记录讯息,点击该笔记录,或是点击 检视 CloudWatch 中的日志 按钮,就可以进入 CloudWatch logs 控制台。请参照下图。

https://ithelp.ithome.com.tw/upload/images/20210930/201295105sVWuVmmSV.png
图 18、检验 AWS Lambda 监控的日志功能

在 CloudWatch 控制台中,找到左手边导览功能列中的 日志群组,找到对应到 getDataFromDynamoDB 这个 Lambda 函数的纪录,通常都是 /aws/lambda/[函数名称],接着确认一下记录的日期时间,再看看发生错误的讯息,原来是第 14 行中的 qry = event['Mark'] 发生错误,因为传递参数的方式不同了,所以 event['Mark'] 变成是无效的变数,导致出错。

https://ithelp.ithome.com.tw/upload/images/20210930/20129510kFWaGJXdRj.png
图 19、使用 CloudWatch Logs 进行除错

将 Lambda 函数的内容修改如下,透过 event['httpMethod'] 取得呼叫的方法是 GET 还是 POST,如果是 get 使用 event['queryStringParameters']来取得传递过来的参数,如果是 post ,则用 event['body']

import json
import boto3
from boto3.dynamodb.conditions import Key

dynamodb = boto3.resource('dynamodb')

def lambda_handler(event, context):
  print("Received event: " + json.dumps(event, indent=2))
  if  event['httpMethod']=='POST':
    key = json.loads(event['body'])['key'] 
  else:
    key = event['queryStringParameters']['key']
  qry = key # event['Mark']
  table = dynamodb.Table('fishInfoTbl')
  data = table.query(
    IndexName='Mark-index',
    KeyConditionExpression = Key('Mark').eq(qry)
  )
  print('data=',data['Items'][0])
  if key:
    data['Items'][0]['key']=key
  response = {
      'statusCode': 200,
      'body': json.dumps(data['Items'][0]),
      'headers': {
        'Content-Type': 'application/json',
        'Access-Control-Allow-Origin': '*'
      },
  }
  
  return response

下图是使用 ARC 来检验 API GET 功能,主要是这样可以看到中文,因为 ARC 会做解码回来。

https://ithelp.ithome.com.tw/upload/images/20210930/20129510dUwUArS01M.png
图 20、使用 ARC 检验 API GET 功能

下图是使用 ARC 来检验 API POST 功能,记得 POST 的请求内容会放在主体内 (BODY),所以需要在主体内写,而请还需要指定编码格式,这样後端才能理解内容为何。

https://ithelp.ithome.com.tw/upload/images/20210930/20129510ldT5E0J5Jc.png
图 21、使用 ARC 检验 API POST 功能

参考资料


<<:  Day14 - 【概念篇】OAuth flows: Implicit (Legacy)

>>:  Day16 跟着官方文件学习Laravel-初写测试

DAY20 这边先帮你上一个按钮喔~(二)

昨天把骰子的程序逻辑都先完成了,这次我们将这个逻辑应用在 Android Studio 里。但我们今...

Rstudio

Shift+Ctrl+R 分段 可缩 Shift+Ctrl+C 多行注解 Shift+Ctrl+M ...

【设计+切版30天实作】|Day23 - Pros区块 - 看似无边框的三栏式卡片,到底要对准哪条栏位?

前面完成了小广告区块,今天来完成「平台好处 - pros」的区块。 数据收集 card标题的样式 ...

【Docker】02 使用CentOS系统安装Apache+PHP+MySQL

1.下载centos的印像档 开启 Windows cmd 视窗 docker pull cento...

DAY15 - [JS] 倒数计时

今日文章目录 需求说明 事前准备 重点说明 参考资料 需求说明 输入框:使用者可以输入时间 显示:...