社会焦点

使用 Docker 让传统 .NET 应用程序现代化(2)

字号+ 作者: 来源: 2017-05-05

这会在后台启动具有拆离标记的容器,并发布端口 1433,以便我可以从外部连接容器中的 SQL 实例(可能在主机上使用 SQL Server Management Studio)。env 选项是键值对,Docker 在容器内将其公开为系统环境变量。SQL

  这会在后台启动具有拆离标记的容器,并发布端口 1433,以便我可以从外部连接容器中的 SQL 实例(可能在主机上使用 SQL Server Management Studio)。env 选项是键值对,Docker 在容器内将其公开为系统环境变量。SQL Server 映像使用这些值来确认许可协议是否已被接受,并为 sa 用户设置密码。

  Docker 必须先在本地复制映像,然后才能运行容器。分发内容会在 Docker 平台中生成。因此,如果在运行此命令时没有本地 SQL Server Express 映像,Docker 将会从 Hub 下载。Docker Hub 上有超过 50 万个映像,这些映像已被下载超过 90 亿次。Docker 始于 Linux,其中大部分映像是 Linux 应用程序,但优质的 Windows 应用程序也越来越多,可供你下载并直接应用到解决方案中。

  现在,SQL Server 在 Docker 容器中运行,我的 Web 应用程序在连接字符串中将 sql-server 指定为主机名,以便连接在 Docker 中运行的数据库。我可以在后台启动 WebForms 应用程序,并发布端口 80,让网站可供访问:

  docker run --detach ` --publish 80:80 ` sixeyed/msdn-web-app:v1

  如果外部计算机在端口 80 上向我的主机发送请求,Docker 会接收请求,并透明地将请求转发给容器中运行的 ASP.NET 应用程序。如果我使用的是主机,则需要运行“docker inspect”获取容器的 IP 地址,然后转到容器即可显示网站(这是一个简单的产品发布微站)。图 1展示了在 Docker 中运行的网站的数据捕获页面。

  使用 Docker 让传统 .NET 应用程序现代化

  图 1:在 Docker 中运行的网站的注册页

  运行“docker ps”将列出所有正在运行的容器。一个是数据库,另一个是 Web 应用程序,但可以相同方式对两者进行管理:运行“docker top”可以查看在容器中运行的进程;运行“docker logs”可以查看应用程序的日志输出;运行“docker inspect”可以查看公开的端口以及有关容器的其他许多信息。一致性是 Docker 平台的主要优势。可以相同方式打包、分发和管理应用程序,无论其使用什么技术。

拆分整个应用程序的功能

  至此,应用程序已在新式平台上运行,我可以开始让应用程序本身现代化了。虽然将整个应用程序细分成较小服务的工作量非常浩大,但可以采取更有针对性的方法,将重点放在关键功能(如定期变化的功能)上,这样就可以部署有变化的功能的更新,而无需对整个应用程序执行回归测试。具有非功能性要求的功能可以受益于另一种设计(即无需对应用程序进行完全的体系结构重建),也是合适之选。

  我将从修复性能问题入手。在现有代码中,应用程序同步连接数据库来保存用户数据。这种方法的扩展性不佳。也就是说,如果有许多并发用户,就会造成 SQL Server 瓶颈。与消息队列进行异步通信是更具扩展性的设计。对于此功能,我可以将 Web 应用程序中的事件发布到消息队列,然后将数据暂留代码移到用于处理此事件消息的新组件中。

  此设计确实也具有很好的扩展性。如果出现网站流量高峰,我可以在更多主机上运行更多容器,以处理传入的请求。在消息处理程序处理事件消息前,它们会一直保留在队列中。对于没有特定 SLA 的功能,可以在一个容器中运行一个消息处理程序,并依赖消息队列的保证,即所有事件最终都会得到处理。对于 SLA 驱动型功能,可以通过运行更多的消息处理程序容器来扩展暂留层。

  本文随附的源代码包含应用程序版本 1、2 和 3 的文件夹。在版本 2 中,SignUp.aspx 页面在用户提交详细信息表单时发布事件:

  vareventMessage = newProspectSignedUpEvent{ Prospect = prospect, SignedUpAt = DateTime.UtcNow};MessageQueue.Publish(eventMessage);

  此外,在版本 2 中,有一个共享的消息传送项目,用于提取消息队列的详细信息;还有一个控制台应用程序,用于侦听 Web 应用程序发布的事件,并将用户数据保存到数据库。控制台应用程序中的暂留代码直接取自 Web 应用程序中的版本 1 代码,所以实现代码是一样的,不同之处在于功能设计已经过现代化。

  应用程序的新版本是包含许多工作部件的已分发解决方案,如图 2所示。

  使用 Docker 让传统 .NET 应用程序现代化

  图 2:经过现代化的应用程序包含许多工作部件

  组件之间有依赖项,必须以正确的顺序启动,这样解决方案才能正常运行。这是安排跨许多容器运行的应用程序的业务流程时面临的问题之一,而为了解决此问题,Docker 平台将已分发的应用程序视作“一等公民”。

使用 Docker Compose 安排应用程序的业务流程

  Docker Compose 属于 Docker 平台,主要处理对象是已分发的应用程序。在简单文本文件中将应用程序的所有部分定义为各个服务,包括组件之间的依赖项及其需要的所有配置值。下面展示了部分版本 2 Docker Compose 文件,仅包含 Web 应用程序的配置:

  product-launch-web: image: sixeyed/msdn-web-app:v2 ports: - "80:80" depends_on: - sql-server - message-queue networks: - app-net

  此时,我要指定要对 Web 应用程序使用的映像版本。我发布端口 80,然后显式声明 Web 应用程序依赖 SQL Server 和消息队列容器。Web 容器必须位于同一虚拟 Docker 网络中,才能访问这些容器。因此,Docker Compose 文件中的所有容器都会联接到同一虚拟网络 app-net 中。

  在 Docker Compose 文件中的其他位置,我使用 Docker Hub 上的 Microsoft 映像定义 SQL Server 服务,并使用 NATS 消息传送系统定义消息队列服务(这是性能卓越的开放源代码消息队列)。NATS 是 Docker Hub 上的官方映像。最终定义的是消息处理程序服务,这是使用简单的 Dockerfile 打包成 Docker 映像的 .NET 控制台应用程序。

  现在,我可以使用以下 Docker Compose 命令行运行应用程序:

  docker-compose up -d

  Docker Compose 会按正确的顺序启动每个组件的容器,只需一个命令就可以为我提供有效的解决方案。有权访问 Docker 映像和 Docker Compose 文件的任何人都可以运行应用程序,且行为方式是相同的,无论是在 Windows 10 笔记本电脑上,还是在数据中心或 Azure 中运行的 Windows Server 2016 计算机上。

转载请注明出处。


1.本站遵循行业规范,任何转载的稿件都会明确标注作者和来源;2.本站的原创文章,请转载时务必注明文章作者和来源,不尊重原创的行为我们将追究责任;3.作者投稿可能会经我们编辑修改或补充。

相关文章
  • 在Apache Spark 2.0中使用DataFrames和SQL

    在Apache Spark 2.0中使用DataFrames和SQL

  • 京东宣布启动618 变革玩法并开放使用618标识

    京东宣布启动618 变革玩法并开放使用618标识

  • HTC Link 是一台与 U11 配套使用的 VR 眼镜

    HTC Link 是一台与 U11 配套使用的 VR 眼镜

  • OPPO R11使用全新人像优化功能,比你更懂自己的美

    OPPO R11使用全新人像优化功能,比你更懂自己的美