WEBKT

Serverless Framework 进阶:深入剖析 serverless.yml 配置文件

265 0 0 0

Serverless Framework 作为一款流行的 Serverless 框架,极大地简化了 Serverless 应用的开发和部署。而 serverless.yml 文件,作为 Serverless Framework 的核心配置文件,承载着定义服务、函数、资源以及各种配置的重任。今天,咱们就来深入剖析一下 serverless.yml,聊聊它的配置项、最佳实践和一些进阶技巧,希望能帮助你更好地驾驭 Serverless Framework。

初识 serverless.yml: 配置文件概览

serverless.yml 文件通常位于 Serverless 项目的根目录下,采用 YAML 格式编写。它描述了整个 Serverless 服务的配置信息,Serverless Framework 会根据这个文件来构建、部署和管理你的应用。

一个典型的 serverless.yml 文件结构如下:

service: my-service # 服务名称

provider:
  name: aws # 云服务提供商
  runtime: nodejs16.x # 运行环境
  region: ap-southeast-1 # 部署区域
  # ... 其他 provider 相关配置

functions:
  hello:
    handler: handler.hello # 函数入口
    events:
      - http:
          path: /hello
          method: get
    # ... 其他函数相关配置

resources:
  Resources:
    MyS3Bucket:
      Type: AWS::S3::Bucket
      Properties:
        BucketName: my-unique-bucket-name
    # ... 其他资源定义

# ... 其他全局配置,如 plugins, custom 等

从上面的示例可以看出,serverless.yml 主要包含以下几个核心部分:

  • service: 定义服务名称,它是整个 Serverless 应用的标识。
  • provider: 定义云服务提供商(如 AWS、Azure、Google Cloud 等)以及与提供商相关的配置,如运行时环境、部署区域、IAM 角色等。
  • functions: 定义 Serverless 函数,包括函数的入口文件、触发事件、环境变量等。
  • resources: 定义云服务资源,如 S3 存储桶、DynamoDB 表、API Gateway 等。这部分通常使用 CloudFormation 语法(AWS)或其他云厂商的资源描述方式。
  • plugins: 插件配置,用于拓展 Serverless Framework 的功能。
  • custom: 自定义配置,用户可以在这里添加一些自定义的变量或配置。

接下来,咱们就来详细聊聊这些核心配置项。

provider:云服务提供商配置

provider 部分是 serverless.yml 中至关重要的一部分,它决定了你的 Serverless 应用将部署到哪个云平台上,以及使用哪些基础设置。

name:云服务提供商

name 属性指定了云服务提供商。常见的选项包括:

  • aws:亚马逊云服务(AWS)
  • azure:微软 Azure
  • google:谷歌云平台(GCP)
  • tencentcloud: 腾讯云
  • aliyun: 阿里云

runtime:运行时环境

runtime 属性指定了函数的运行环境。不同的云服务提供商支持的运行时环境有所不同。例如,对于 AWS,常见的运行时环境包括:

  • nodejs16.xnodejs18.x
  • python3.8python3.9
  • java11java17
  • go1.x
  • ruby2.7
  • .NET Core 3.1.NET 6

region:部署区域

region 属性指定了 Serverless 应用部署的地理区域。选择合适的区域可以降低延迟、提高可用性,并满足合规性要求。例如,对于 AWS:

  • us-east-1 (弗吉尼亚北部)
  • us-west-2 (俄勒冈)
  • ap-southeast-1 (新加坡)
  • eu-central-1 (法兰克福)

IAM 角色配置 (以 AWS 为例)

在 AWS 上,Serverless 函数需要具有相应的 IAM 角色才能访问其他 AWS 资源。provider 部分可以配置 IAM 角色相关的设置。

  • iamRoleStatements: 用于定义 IAM 角色的权限策略。你可以直接在这里定义权限,也可以引用已有的 IAM 角色。

    provider:
      iamRoleStatements:
        - Effect: Allow
          Action:
            - s3:GetObject
            - s3:PutObject
          Resource: "arn:aws:s3:::my-bucket/*"
    
  • role: 引用已有的 IAM 角色。如果你已经创建了 IAM 角色,可以直接在这里指定角色的 ARN。

     provider:
       role: arn:aws:iam::123456789012:role/my-serverless-role
    

其他 provider 配置

provider 部分还可以包含其他特定于云服务提供商的配置,如:

  • stage: 部署阶段(如 dev、test、prod),默认为 dev
  • profile: 使用的 AWS 配置文件(如果使用多个 AWS 账户)。
  • environment: 全局环境变量,会被所有函数继承。
  • memorySize: 函数的默认内存大小(AWS Lambda)。
  • timeout: 函数的默认超时时间(AWS Lambda)。
  • vpc: 如果你的函数需要访问 VPC 内的资源,可以在这里配置 VPC。

functions:函数配置

functions 部分定义了你的 Serverless 应用中的各个函数。每个函数都是一个独立的执行单元,可以由不同的事件触发。

handler:函数入口

handler 属性指定了函数的入口文件和处理函数。例如:

functions:
  myFunction:
    handler: src/handlers/myFunction.handler

上面的配置表示,当 myFunction 被触发时,Serverless Framework 会执行 src/handlers/myFunction.js 文件中的 handler 函数。

events:触发事件

events 属性定义了触发函数的事件。Serverless Framework 支持多种事件类型,常见的包括:

  • http: HTTP 请求事件,通常与 API Gateway 集成。

    events:
      - http:
          path: /users/{id}
          method: get
          cors: true # 启用 CORS
    
  • schedule: 定时任务事件,类似于 Cron 表达式。

    events:
      - schedule: rate(5 minutes) # 每 5 分钟执行一次
      - schedule: cron(0 12 * * ? *) # 每天中午 12 点执行
    
  • s3: S3 对象存储事件。

    events:
      - s3:
          bucket: my-bucket
          event: s3:ObjectCreated:*
          rules:
            - prefix: uploads/
            - suffix: .jpg
    
  • sns: SNS 消息通知事件。

    events:
      - sns: my-topic
    
  • sqs: SQS 消息队列事件。

    events:
      - sqs: arn:aws:sqs:region:account-id:queue-name
    
  • dynamodb: DynamoDB 数据流事件。

  • stream: Kinesis 数据流事件

  • websocket: WebSocket 事件

其他 functions 配置

functions 部分还可以包含其他函数级别的配置,如:

  • environment: 函数级别的环境变量,会覆盖 provider 中定义的全局环境变量。
  • memorySize: 函数的内存大小(覆盖 provider 中的默认值)。
  • timeout: 函数的超时时间(覆盖 provider 中的默认值)。
  • layers: AWS Lambda 层,用于共享代码和依赖。
  • package: 函数的打包配置。

resources:资源配置

resources 部分用于定义 Serverless 应用所需的云服务资源。对于 AWS,这部分通常使用 CloudFormation 语法来描述资源。

示例:创建一个 S3 存储桶

resources:
  Resources:
    MyS3Bucket:
      Type: AWS::S3::Bucket
      Properties:
        BucketName: my-unique-bucket-name-${self:provider.stage} # 使用变量

上面的示例创建了一个名为 my-unique-bucket-name 的 S3 存储桶。注意,这里使用了 ${self:provider.stage} 变量来引用 provider 部分定义的 stage

示例:创建一个 DynamoDB 表

resources:
  Resources:
    MyDynamoDBTable:
      Type: AWS::DynamoDB::Table
      Properties:
        TableName: my-table
        AttributeDefinitions:
          - AttributeName: id
            AttributeType: S
        KeySchema:
          - AttributeName: id
            KeyType: HASH
        ProvisionedThroughput:
          ReadCapacityUnits: 5
          WriteCapacityUnits: 5

上面的示例创建了一个名为 my-table 的 DynamoDB 表,其中 id 作为主键。

资源引用

functions 或其他地方,你可以使用 CloudFormation 的 RefFn::GetAtt 函数来引用 resources 部分定义的资源。

functions:
  myFunction:
    environment:
      BUCKET_NAME: !Ref MyS3Bucket # 引用 S3 存储桶名称
      TABLE_NAME:
        Fn::GetAtt: [ MyDynamoDBTable, Arn ] # 引用 DynamoDB 表的 ARN

plugins: 插件

plugins配置,允许你添加各种插件来扩展 Serverless Framework 的功能。 比如常用的serverless-offline(本地模拟运行环境)、 serverless-webpack(打包优化)等。

plugins:
  - serverless-offline
  - serverless-webpack

custom:自定义配置

custom 部分允许你定义一些自定义的变量或配置,这些变量可以在 serverless.yml 文件的其他地方引用。

custom:
  myVariable: myValue
  apiGatewayName: my-api-${self:provider.stage}

functions:
  myFunction:
    environment:
      MY_VAR: ${self:custom.myVariable} # 引用自定义变量

最佳实践和进阶技巧

1. 使用变量

serverless.yml 支持多种变量引用方式,可以帮助你实现配置的复用和动态化。

  • self: 引用 serverless.yml 文件自身的内容。
  • opt: 引用命令行选项。
  • env: 引用环境变量。
  • file: 引用外部文件中的变量。
  • AWS CloudFormation 变量
custom:
  bucketName: my-bucket-${opt:stage, self:provider.stage} # 优先使用命令行选项

resources:
  Resources:
    MyS3Bucket:
      Type: AWS::S3::Bucket
      Properties:
        BucketName: ${self:custom.bucketName}

2. 模块化配置

serverless.yml 文件变得庞大时,可以考虑将其拆分为多个模块化的配置文件,然后使用 file 变量引用。

# serverless.yml
service: my-service

provider:
  # ...

functions:
  ${file(./functions.yml)}

resources:
  ${file(./resources.yml)}
# functions.yml
myFunction1:
  handler: ...

myFunction2:
  handler: ...

3. 使用 Serverless Framework Variables

Serverless Framework Variables 提供了一种更强大和灵活的方式来引用变量,不仅可以从本地文件、环境变量、命令行选项中获取变量,还可以从 AWS SSM Parameter Store、S3 等地方获取。

# 从 SSM Parameter Store 获取变量
custom:
  secret: ${ssm:/my-app/my-secret}

functions:
  myFunction:
    environment:
      MY_SECRET: ${self:custom.secret}

4. 条件配置

你可以使用 Fn::IfFn::Equals 等 CloudFormation 条件函数来实现条件配置。

resources:
  Conditions:
    CreateDevResources: !Equals [ ${self:provider.stage}, dev ]

  Resources:
    MyS3Bucket:
      Type: AWS::S3::Bucket
      Condition: CreateDevResources # 仅在 dev 阶段创建
      Properties:
        BucketName: my-dev-bucket

5. 优化函数打包

Serverless Framework 默认会将整个项目目录打包上传。你可以通过 package 配置来优化打包过程,排除不必要的文件,减小部署包的大小。

functions:
  myFunction:
    package:
      individually: true # 每个函数单独打包
      exclude:
        - node_modules/**
        - .git/**
        - .vscode/**
      include:
        - src/handlers/myFunction.js

6. 使用 serverless-webpackserverless-esbuild 插件

对于 Node.js 项目,可以使用 serverless-webpackserverless-esbuild 插件来优化代码打包,进一步减小部署包的大小,并利用 Tree Shaking 等技术移除未使用的代码。

7. 使用 serverless-offline 插件

serverless-offline 插件可以在本地模拟 AWS Lambda 和 API Gateway 的运行环境,方便你在本地进行开发和测试。

8. 监控和日志

Serverless 应用的监控和日志非常重要。你可以使用 AWS CloudWatch、Azure Monitor、Google Cloud Operations Suite 等云服务提供的监控和日志服务,也可以集成第三方工具,如 Datadog、New Relic 等。

9. 安全性

  • 遵循最小权限原则,为每个函数配置独立的 IAM 角色,只授予必要的权限。
  • 使用环境变量或 Secrets Manager 等服务来存储敏感信息,不要将敏感信息硬编码在代码或配置文件中。
  • 定期审查和更新依赖项,避免使用存在安全漏洞的组件。
  • 对于 API Gateway,可以配置 Web Application Firewall (WAF) 来防御常见的 Web 攻击。
  • 启用 API Gateway 的访问日志记录,监控 API 的调用情况。

10. CI/CD

将 Serverless Framework 与 CI/CD 工具集成,可以实现自动化的构建、测试和部署。常见的 CI/CD 工具包括:

  • Jenkins
  • GitLab CI
  • GitHub Actions
  • AWS CodePipeline
  • Azure DevOps

通过 CI/CD,你可以实现:

  • 自动化测试:在每次代码提交时运行单元测试、集成测试等。
  • 自动化部署:将应用部署到不同的环境(dev、test、prod)。
  • 回滚:在部署失败时自动回滚到上一个版本。

总结

serverless.yml 文件是 Serverless Framework 的核心,掌握它的配置和使用技巧对于构建高效、可靠、安全的 Serverless 应用至关重要。希望通过今天的分享,你对 serverless.yml 有了更深入的理解。如果你在使用 Serverless Framework 过程中遇到任何问题,欢迎随时交流,咱们一起探讨!

Serverless 的世界变化很快,新的特性和最佳实践层出不穷。保持学习的热情,不断探索,你一定能成为 Serverless 领域的专家!

技术老炮儿 ServerlessServerless FrameworkYAML

评论点评