【问题标题】:Is there a way to run initial SQL when creating an RDS database instance using CloudFormation?使用 CloudFormation 创建 RDS 数据库实例时,是否可以运行初始 SQL?
【发布时间】:2013-01-01 07:58:58
【问题描述】:

我正在使用 CloudFormation 创建一个 RDS 实例:

“资源”: { “我的数据库”:{ "类型": "AWS::RDS::DBInstance", “特性”: { “分配存储”:“5”, "DBInstanceClass": "db.m1.small", “引擎”:“MySQL”, “引擎版本”:“5.5”, "DBName": "mydb", “主用户名”:{ “参考”:“数据库用户” }, “主用户密码”:{ “参考”:“数据库密码” }, “DBParameterGroupName”:{ “参考”:“myRDSParamGroup” } } }

一切正常。但是我需要在创建数据库时在数据库上运行初始 SQL,以设置我的应用程序架构。我目前的方法是让应用程序自行迁移,但我想在 CloudFormation 定义中进行。这可能吗?

【问题讨论】:

    标签: amazon-web-services amazon-rds amazon-cloudformation


    【解决方案1】:

    不,这是不可能的。但是,您可以让 EC2 实例连接到您的 RDS 实例来执行此操作。我可能会在 S3 中存储一个 .sql 文件并在 EC2 实例上使用 cloud-init 脚本来下载该文件并执行它。

    【讨论】:

    • 今天,使用 Lambda 函数 + CustomResource 比 EC2 实例更有意义
    • @OdedNiv 我正在尝试做同样的事情。您介意分享 lambda 函数和自定义资源吗?
    • @RishiGoel 我没有,但 Lambda 非常简单,文档也很简单。我可能很快会创建一个,在这种情况下我会在这里发布
    • 我尝试过的一件事是将 SNS 主题连接到 cloudformation 模板具有的 NotificationARN。从那里,有一个 lambda 函数通过 NotificationARNS 监听所有事件。当事件为 CREATE_FINISHED 时,启动您想要的任何行为。更多信息 => mbejda.com/handling-aws-cloudformation-events
    • 太糟糕了,这不是 RDS 的常规功能。无论您是通过 CLI、控制台、SDK、CloudFormation 还是 Beanstalk 创建数据库实例,都应该有一个运行指定脚本的选项。就像您可以在 EC2 实例上运行用户数据脚本一样。
    【解决方案2】:

    也可以创建 CloudFormation 自定义资源。关于如何使用 SNS here 构建一个的讨论很好;也可以使用 Lambda 构建一个。自定义资源本质上只是 RPC,因此创建一个以使用模式初始化数据库并不难。

    【讨论】:

    • 我想避免让我的 beanstalk/EC2 资源负责在 init 上加载数据库模式/数据。我希望数据库初始化模式/数据将通过另一种方式管理以分离关注点,并且不要将应用程序中心的应用程序与配置内容混合在一起。一个负责获取 sql 脚本并将模式/数据插入 RDS 数据库的自定义 cloudformation 资源似乎不错,也许使用 lambda,然后我们需要找到一种方法,在无用时删除这个额外的自定义资源。如果有人找到一种标准方法来完成这种经典要求,那就太酷了:init DB
    • 我同意你所说的一切——架构是一个部署问题。 “标准”不存在的一个原因可能是访问限制。对于用于初始化数据库的自定义资源,它必须具有写入权限,这是不可取的。不过,我自己也面临着类似的问题;如果我最终构建了一个自定义资源,我会回来分享我所做的以供参考,希望对您有用。
    • 你想出解决方案了吗?我面临同样的问题。我正在考虑为此使用 ansible playbook,但我想知道是否有可以在 cloudformation 领域完成的适当解决方案
    • 我没有。我最终只是解决了它,这并不难,因为在我的用例中我们很少上下旋转新堆栈。对于更大容量的用例,这种方法显然是行不通的。如果我今天必须解决问题,我会按照上面的链接设置一个自定义资源。
    【解决方案3】:

    CloudFormation 仍然没有为我们提供任何解决方案,但希望他们能尽快添加 Database Migration Service 支持。

    与此同时,如果您使用 CodePipeline,有一个很好的解决方案:创建一个迁移阶段,调用 Lambda 函数来运行您的迁移。我偶然发现了 this guide 从 CodePipeline 调用 Lambda,这可能对那些不熟悉的人有所帮助。

    【讨论】:

      【解决方案4】:

      另一种选择是对 AWS::RDS::DBInstance 资源使用 DBSnapshotIdentifier 属性。唯一需要注意的是,您首先需要在 AWS 中加载一个数据库才能创建快照。从那时起,您可以自动化您的 cloudformation 堆栈以使用它。

      DBSnapshot 标识符: 用于还原数据库实例的数据库快照的名称 (ARN)。

      如果属性包含一个值(不是空字符串),AWS CloudFormation 会从指定的快照创建一个数据库。

      使用 DBSnapshotIdentifier 属性还原数据库实例后,您必须为将来对数据库实例的任何更新指定相同的 DBSnapshotIdentifier 属性。当您为更新指定此属性时,数据库实例不会再次从数据库快照中恢复,数据库中的数据也不会更改。但是,如果您不指定 DBSnapshotIdentifier 属性,则会创建一个空数据库实例,并删除原始数据库实例。

      从更多信息中查看文档: https://docs.aws.amazon.com/AWSCloudFormation/latest/UserGuide/aws-properties-rds-database-instance.html#cfn-rds-dbinstance-dbsnapshotidentifier

      【讨论】:

        猜你喜欢
        • 2020-09-24
        • 2020-11-02
        • 2020-12-13
        • 2021-07-21
        • 1970-01-01
        • 1970-01-01
        • 2015-02-10
        • 2017-02-14
        • 2020-05-29
        相关资源
        最近更新 更多