Elastic Beanstalk、Docker 和持续集成
Posted
技术标签:
【中文标题】Elastic Beanstalk、Docker 和持续集成【英文标题】:Elastic Beanstalk, Docker and Continuous integration 【发布时间】:2015-01-26 22:28:50 【问题描述】:我有一个使用 Docker 的 beanstalk 环境。
每次我推送一些东西时,jenkins 都会构建我的新快照并将其上传到 S3。 (我使用 S3 来存储我的版本)。每个版本都是一个 zip,其中包含我的应用程序和我的 Dockerfile。
然后我用我刚刚上传的版本更新我的BS环境。(BS用上传到S3的版本创建一个新版本,如果版本存在则替换它,它对快照有用)。
我第一次部署该版本时一切正常。 但是当我第二次这样做时,它继续工作,但似乎我的最后一个版本没有使用。 Docker 不会重新构建我刚刚更新的应用程序。
为什么会这样?我错过了什么吗?这是我的Dockefile
【问题讨论】:
我不确定我是否理解您在 S3 和您的 docker 容器之间的链接。你的代码是如何移动的?您是在 EB 上部署 docker 容器还是使用特定语言的部署? ? 如果您正在部署 docker 容器,EB 无法检测到更改。因为 Docker 文件没有改变。通过 VOLUME 挂载的卷绕过联合文件系统。 EB 看不到那里的变化 我更新了帖子以更清晰。那么,我如何告诉 EB 我的应用发生了变化? 但是 EB 实例如何知道实例上的 /root/wisdom 和 /repository 是什么。这些与您的构建环境有关吗?还是这些部署在 EC2 实例上?如果是后者,怎么办?我仍然想念这里。对不起 另一种方式来问我的问题:容器建在哪里?在 CI 服务器上还是在 EB 实例上? 【参考方案1】:基本上,update-environment 调用似乎拒绝更新相同的版本号——这就是为什么我们总是依赖$maven.build.timestamp
和朋友。这是你修饰过的 pom :]
注意我正在使用属性 - 这是最新版本的建议样式(糟糕,有人忘记更新文档了)。
我决定尝试使用最新的 1.4.0-SNAPSHOT。以下是您应该添加到个人资料中的内容:
<profiles>
<profile>
<id>awseb</id>
<properties>
<maven.deploy.skip>true</maven.deploy.skip>
<beanstalker.region>eu-west-1</beanstalker.region>
<beanstalk.applicationName>wisdom-demo</beanstalk.applicationName>
<beanstalk.cnamePrefix>wisdom-demo</beanstalk.cnamePrefix>
<beanstalk.environmentName>$beanstalk.cnamePrefix</beanstalk.environmentName>
<beanstalk.artifactFile>$project.basedir/target/$project.build.finalName.zip</beanstalk.artifactFile>
<beanstalk.environmentRef>$beanstalk.cnamePrefix.elasticbeanstalk.com</beanstalk.environmentRef>
<maven.build.timestamp.format>yyyyMMddHHmmss</maven.build.timestamp.format>
<beanstalk.s3Key>apps/$project.artifactId/$project.version/$project.artifactId-$project.version-$maven.build.timestamp.zip</beanstalk.s3Key>
<beanstalk.useLatestVersion>true</beanstalk.useLatestVersion>
<beanstalk.versionLabel>$project.artifactId-$project.version-$maven.build.timestamp</beanstalk.versionLabel>
<beanstalk.applicationHealthCheckURL>/ping</beanstalk.applicationHealthCheckURL>
<beanstalk.instanceType>m1.small</beanstalk.instanceType>
<beanstalk.keyName>aldrin@leal.eng.br</beanstalk.keyName>
<beanstalk.iamInstanceProfile>aws-elasticbeanstalk-ec2-role</beanstalk.iamInstanceProfile>
<beanstalk.solutionStack>64bit Amazon Linux 2014.* running Docker 1.*</beanstalk.solutionStack>
<beanstalk.environmentType>SingleInstance</beanstalk.environmentType>
</properties>
<build>
<plugins>
<plugin>
<groupId>br.com.ingenieux</groupId>
<artifactId>beanstalk-maven-plugin</artifactId>
<version>1.4.0-SNAPSHOT</version>
<executions>
<execution>
<id>default-deploy</id>
<phase>deploy</phase>
<goals>
<goal>upload-source-bundle</goal>
<goal>create-application-version</goal>
<goal>put-environment</goal>
</goals>
</execution>
</executions>
</plugin>
</plugins>
</build>
</profile>
从上面的示例中,只需调整您的 cnamePrefix 和最新的三个属性。这是一个纲要:
所以如果你想部署,只需:
$ mvn -Pawseb 部署
或者,如果你想启动它
从头开始部署最新版本(因此使用 useLatestVersion),只需执行以下操作:
$ mvn -Pawseb -Dbeanstalk.versionLabel= beanstalk:create-environment
通过将versionLabel设置为空白,它有效地激活了useLatestVersion行为:当没有版本时,使用最新的。
哦,部署失败了?
简单易懂:
$ mvn -Pawseb beanstalk:rollback-version
【讨论】:
我最终选择了它可能是最好的时间戳解决方案。我像你一样配置了我的 pom,它工作正常,所以谢谢你的帮助。你们会很快发布 1.4.0 吗? 事实上它适用于 1.3.5 - 除了刚刚添加的 .artifactFile :) 还有一件事:如果你在 eu-central-1 以外的任何地方,你可以使用 git 增量部署,这使得配置更容易(有点)和更快。【参考方案2】:感谢您的解释和博客文章的链接。 我按照这些分步说明,成功地将我的第一个 Wisdom 应用程序部署在 AWS Elastic Beanstalk 上的 Docker 容器中。
然后我升级 Java 源代码,使用 mvn package
编译,在本地测试并使用 AWS 控制台再次部署新的 ZIP 文件。
我的 AWS Elastic BeansTalk 环境已正确更新。
因此,您观察到的部署问题似乎在于部署代码的maven AWS Elastic Beanstalk plugin。 手动部署工作正常。由于此 maven 插件是第三方开源项目,因此我不适合对此进行调查。我建议您联系项目维护人员和/或在他们的Issue Tracking System 中打开一个问题
作为一种解决方法,您可以手动部署(或在 CI/CD 环境中编写此过程的脚本):
-
将您的人工制品复制到您的 AWS Elastic Beanstalk 存储桶中
aws s3 --region <REGION_NAME> cp ./target/YOUR_ARTIFACTID-1.0-SNAPSHOT.zip s3://<YOUR_BUCKET_NAME>/20141128-210900-YOUR_ARTIFACTID-1.0-SNAPSHOT.zip
-
使用您的 zip 文件创建应用程序版本
aws elasticbeanstalk create-application-version --region <REGION_NAME> --application-name <YOUR_APPLICATION_NAME> --version-label 20141128-212100 --source-bundle S3Bucket=<YOUR_BUCKET_NAME>,S3Key=20141128-210900-YOUR_ARTIFACTID-1.0-SNAPSHOT.zip
-
部署该版本
aws elasticbeanstalk update-environment --region <YOUR_REGION_NAME> --environment-name <YOUR_ENVIRONMENT_NAME> --version-label 20141128-212100
这三个步骤可能会从 maven 或 jenkins 自动完成,我将让您将此作为练习:-)
【讨论】:
很酷,感谢您的出色回答,我会尽快尝试并给您回报。 嘿@Stormacq,让我看看 :) 如果应用程序版本具有不同的名称似乎可以工作,但如果您上传 1.0-SNAPSHOT.zip,则创建将其部署为版本 1.0-SNAPSHOT,并删除此版本,然后以相同的名称重新创建它,它不工作 在我上一条评论之后,我明确指出它在 AWS 控制台和插件中不起作用。也许这是正常行为 那是因为您使用了相同的版本号 - API 在版本相同时拒绝更新。另外,upload-source-bundle 拒绝上传任何不类似于 .zip 文件的内容,因此可能存在一些不匹配。无论如何,我“刚刚”修饰了你的个人资料,我正在发布它。以上是关于Elastic Beanstalk、Docker 和持续集成的主要内容,如果未能解决你的问题,请参考以下文章
AWS Elastic Beanstalk - 多容器 Docker
AWS Elastic Beanstalk Docker 环境变量
Elastic Beanstalk、Docker 和持续集成
Elastic Beanstalk 上的 WebSockets 与 Docker