【问题标题】:How can I use conditional configuration in serverless.yml for lambda?如何在 serverless.yml 中为 lambda 使用条件配置?
【发布时间】:2021-08-17 21:34:32
【问题描述】:

我需要通过serverless.yml 配置一个 lambda,以便为不同的环境使用不同的配置并发。下面是我的 lambda 配置:

 myLambda:
   handler: src/lambdas
   name: myLambda
   provisionedConcurrency: ${self:custom.pc}

...

custom:
  pc: ${env:PC}

值 PC 是从环境变量中加载的。它适用于大于 0 的值,但我无法在一个环境中设置值 0。我想要做的是在dev 环境中禁用配置并发。

我已通读此文档https://forum.serverless.com/t/conditional-serverless-yml-based-on-stage/1763/3,但对我的情况似乎没有帮助。

如何根据环境设置provisionedConcurrency

【问题讨论】:

    标签: amazon-web-services aws-lambda serverless-framework


    【解决方案1】:

    方法一:基于阶段的变量通过默认值

    这是一个使用级联值变量的相当简单的技巧。第一个值是您想要的值,第二个是默认值或备用值。也称为级联变量。

    // serverless.yml
    provider:
      stage: "dev"
    
    custom:
      provisionedConcurrency:
        live: 100
        staging: 50
        other: 10
    
     myLambda:
       handler: src/lambdas
       name: myLambda
       provisionedConcurrency: ${self:custom.provisionedConcurrency.${self:provider.stage}, self:custom.provisionedConcurrency.other}
    

    上面设置为 dev 的阶段将默认为“其他”值 10,但如果您通过 serverless deploy --stage live 设置阶段,那么它将使用实时值 100。

    更多详情请看这里:https://www.serverless.com/framework/docs/providers/aws/guide/variables#syntax

    方法2:通过Javascript异步值

    您可以使用 js 包含并将您的条件逻辑放在那里。它被称为“异步值支持”。基本上,这允许您将逻辑放入您包含的 javascript 文件中,并且它可以根据各种情况返回不同的值(例如,您使用的 AWS 帐户,或者是否设置了某些变量,等等)。基本上,它允许你这样做......

    provisionedConcurrency: ${file(./detect_env.js):get_provisioned_concurrency}
    

    如果您在此文件夹中创建一个名为 detect_env.js 的 javascript 文件,并且其内容类似于...

    module.exports.get_provisioned_concurrency = () => {
      if ("put logic to detect which env you are deploying to, eg for live") {
        return Promise.resolve('100');
      } else {
        // Otherwise fallback to 10
        return Promise.resolve('10');
      }
    }
    

    欲了解更多信息,请参阅:https://www.serverless.com/framework/docs/providers/aws/guide/variables#with-a-new-variables-resolver

    尽管几个月前有人问过这个问题,但我觉得我必须在这里回复,因为没有一个答案与正确答案相差甚远,我真的为作者或任何来到这里的人感到难过。

    【讨论】:

      【解决方案2】:

      对于真正棘手的问题,我发现转到 Cloudformation 脚本并使用 Cloudformation 内在函数很有用。

      对于这种情况,如果您知道所有可以使用的环境Fn::FindInMap

      https://docs.aws.amazon.com/AWSCloudFormation/latest/UserGuide/intrinsic-function-reference-findinmap.html

      或者如果只是生产需要 0,那么您可以在 Cloudformation 模板中使用条件 Fn::If 和布尔值 Condition 测试来测试环境是否等于生产,使用 0,否则使用来自 SLS 的模板化值。

      潜在的 SLS:

      resources:
        Conditions:
          UseZero: !Equals ["production", ${provider.stage}]
        Resources:
          myLambda:
            ProvisionedConcurrency: !If [UseZero, 0, ${self:custom.pc}]
      

      如果需要,您也可以显式删除 ProvisionedConcurrency 属性:

      resources:
        Conditions:
          UseZero: !Equals ["production", ${provider.stage}]
        Resources:
          myLambda:
            ProvisionedConcurrency: !If [UseZero, AWS::NoValue, ${self:custom.pc}]
      

      编辑:您仍然可以使用 SLS 进行部署;它只是编译成一个 Cloudformation JSON 模板,您可以使用 SLS resources 字段显式修改该模板。

      【讨论】:

      • 这意味着我不能使用serverless 来部署 lambda?这可能是一个很大的变化
      • 我已经尝试过这种方法,但它编译了大约The CloudFormation template is invalid: Invalid template resource property 'provisionedConcurrency'。它在function 部分使用相同的语法吗?
      • 启动 CLI 时 SLS 是否在抱怨?还是部署时符合 CF 标准?
      • 请注意:闯入 CloudFormation 来解决这种情况是非常疯狂的。 Serverless 在其框架中有很多方法来处理这个权利。
      【解决方案3】:

      无服务器框架提供了一个非常有用的仪表板工具,具有称为参数的功能。本质上,它可以让您将服务连接到它,然后您可以为不同阶段设置不同的值,然后在 serverless.yml 中使用 ${param:VARAIBLE_NANE_HERE} 等语法使用这些值,并在部署时将其替换为正确的您当前正在部署的任何阶段的价值。超级好用。仪表板中还有许多其他功能,例如监控和故障排除。

      您可以在此处的官方文档中找到有关参数的更多信息:https://www.serverless.com/framework/docs/guides/parameters/

      以及如何在此处开始使用仪表板:https://www.serverless.com/framework/docs/guides/dashboard#enabling-the-dashboard-on-existing-serverless-framework-services

      【讨论】:

      • 我没有使用无服务器仪表板。我只有命令行。有解决办法吗?
      【解决方案4】:

      在部署/打包期间仅在开发环境中使用具有空值的变量,SLS 将跳过此属性:

      provisionedConcurrency: ${self:custom.variables.provisionedConcurrency}
      

      【讨论】:

      • 仅供参考:这不是作者要求的。他们要求为不同的环境提供不同的值。如果不是没有,也可能不是一个值。
      猜你喜欢
      • 1970-01-01
      • 2021-08-01
      • 1970-01-01
      • 2018-11-11
      • 2020-05-07
      • 2017-12-20
      • 2020-01-11
      • 2020-09-11
      • 1970-01-01
      相关资源
      最近更新 更多