容器中缺乏永久性存储的问题该如何解决?

在容器中运行应用并不是一个全新的理念。是的,这是一个热门话题,其中许多人在讨论中为了提升话题的热度,或者是为了抛出新奇的观点,往往都会提到容器,仿佛他们为这一棘手问题找到了良策一样。听上去似乎是这样的——容器是万能的,它能解决所有的问题。

容器的起源实际上可以追溯至大型机时代,因此它并不是新的东西。这一技术已经开始逐渐成熟,并以极快的速度获得了用户的关注与认可。

容器可让应用同时运行在一个单一操作系统中,既可以将其直接部署在物理服务上,也可以作为一个虚拟实例部署。

这是通过提供了执行“用户空间”多个拷贝的功能实现的。在这里,应用可以运行在平台上,系统或是特殊代码可以运行在内核上。

容器在存储领域的短板:默认情况下没有永久性存储

容器当前的吸引力来自与运行虚拟实例相关的问题和日常开支方面,即每个实例必须要有专用内存和存储资源。这些东西通常要么太多,要么太少,在需要快速扩展时,往往要花费很长的时间。

虚拟实例的设计存在孤立性,每个实例的升级都具有独特性,但是在运行相似或相同操作系统版本的大环境中,每个都运行着一套相同的程序以消费内存,保持近乎相同的启动卷。

在向“大规模计算转型”这一目标进发的征途中,传统的虚拟化被认为效率低下,浪费内存、CPU、存储、机架空间、电力、冷却等物理资源,以及浪费管理、IP地址等逻辑资源。由于它们与邻近的看起来好像容器拥有整个操作系统的组件相互隔离,因此容器带有一定程度的分离性。这种分离性允许它们与外部世界进行互动。

由于在2014年呈现指数增长,容器及其生态系统2015年在企业环境中获得了一些推动力,但是还远未达到大规模部署的程度。目前已经有少量的备份软件提供商开始提供容器备份支持,但是目前是否已经有了一种可以通过备份软件备份容器的方法呢?

与虚拟实例相比,这可能是非常短暂的,并且只适用于分配给它们的存储。与以前所使用的原始镜像相比,容器可以使用重叠式文件系统等功能执行写入时复制程序,以存储所有升级信息到容器的根文件系统。如果容器被删除了,那么这些变更也通常会丢失。因此,容器在默认情况下没有永久存储。

Docker在存储领域的改进:使用卷和数据容器时仍存在问题

然而,Docker提供了Docker卷和数据容器两个功能,这两个功能可以实现对更多永久存储资源的访问。

Docker卷允许数据被存储在启动卷外的容器中,根文件系统内,并且可以通过多种方式被执行。通过提供一个传递至“-v”交换机参数的共享名,容器能够被创建在一个或多个卷内。

这拥有在Docker配置文件夹(/var/lib/docker)中创建一个实体,以展现卷中内容的效果。卷中的配置数据被存储在/var /lib/docker/volumes文件夹内,通过每个子目录展现基于通用唯一标识符(UUID)的卷名。数据本身将被存储在以UUID名称为基础的 /var/lib/docker/vfs/dir文件夹中。

任何卷中的数据都能够通过主机操作系统和标准权限申请被浏览和编辑。卷的使用既有优势也有劣势。由于数据被存储在标准文件系统中,它们可以通过操作系统被备份、拷贝或是移入/移出。

不足之处是卷名采用的是UUID格式,这让人难以将它们与容器名称联系在一起。Docker让许多工作变得更加轻松,它通过提供“docker cp”命令,让文件和文件夹能够从主机目录拷贝至指定容器名称的容器目录路径。这与rsync很相似。

这为提供对在NFS共享上的外部共享存储或LUN的访问带来了可能。LUN使用卷选项访问创建在外部存储上的主机共享,不过这种方式并不推荐使用。

Docker卷也可以与主机目录联系在一起。这在“-v”交换机中被进行了详细说明,它使用了一个通过冒号将主机与容器分隔起来的格式,即:“-v /host:/container”。这种方法允许容器访问主机上的持久性数据。

因此,这使得访问存储在NFS共享上的外部共享存储,或者使用卷选项访问创建在外部存储上的主机共享的LUN成为了可能。这种方式也可用于备份由容器访问的数据。

对于管理Docker中数据的另一个选项是使用Docker数据容器。这一概念实质上是一个不活跃容器,其中创建有一个或多个卷。在启动额外容器时,这些卷能够被导出到一个或多个使用“-volumes-from”交换机的容器中。

数据卷容器实际上是作为一个内部的Docker NFS服务器,提供对来自中央挂载点的容器的访问。

这种方法的好处是它抽象了原始数据的位置,让数据容器成为了一个逻辑挂载点。在保持数据长久保存一个专用容器的同时,它们还允许访问数据容器卷的“应用”容器被创建和被破坏。

在使用卷和数据容器时我们会发现,其中存在许多问题。

孤立的存储

目前,在不删除相关卷的情况下,删除容器已经成为了可能。实际上,这是一种默认行为,除非明确进行重写。这使得终结没有相关容器的孤立卷变得更加容易。

清理孤立存储是一项艰巨的任务,这需要查找与容器匹配的容器配置文件和与它们相关的卷。

安全性

除了标准文件权限和配置只读或读写访问选项外,卷或数据容器没有额外的安全保证。这意味着容器中的用户文件访问权限需要与主机设置相匹配。

数据完整性

共享使用卷和数据容器的数据没有任何数据完整性保护措施。文件锁定等功能需要由容器自身进行管理。这是一项必须要加入到应用当中的额外开销。

容器不提供数据保护工具,例如快照或复制,因此数据管理必须要由主机或是容器负责。

目前还缺乏对外部存储的支持。除了主机操作系统提供的功能外,Docker内部也没有对外部存储的一些特殊支持。

容器卷默认存储在/var/lib/dockerdirectory下,这将成为容量和性能瓶颈。目前,在Docker后台程序启动中使用交换机改变这一位置已经变成了可能。

容器和存储目前存在的问题之一是,无法管理运行在独立物理主机上的容器之间的数据共享。

容器卷可位于外部存储上,但是目前的设计并不便于将来自一台主机的卷用在另一台主机上。为了解决这一问题,开始出现了类似ClusterHQ的 Flocker等解决方案,以解决卷的可移植性问题。目前,还有一些建议对Docker进行调整,增加一些关于对卷进行管理的功能。

虽然许多问题有望被快速解决,但是数据管理在短期内仍将是一个棘手的问题。

编者注:本文编译自superuser.openstack.org,作者为Nick Gerasimotos,编译者Frank Chan。Nick Gerasimotos是FICO云服务工程高级总监,目前正致力于研究容器中缺乏永久性存储的问题,以及如何通过Docker卷和数据容器解决这一问题。

本文作者:Frank Chan

来源:51CTO

时间: 2024-10-28 22:12:51

容器中缺乏永久性存储的问题该如何解决?的相关文章

你的应用什么时候该拆分到多个容器中?

Docker的最佳实践提出了"一个容器内只运行一个进程"之后,是否需要将应用拆分到多个容器中就成了一个热门话题.本文以一个普通的Java应用作为讨论,从软件设计的角度来介绍为什么要将其拆分到多个容器中. 假设一个标准的Java Web应用包含以下两部分: 基于Struts框架的前端应用; 基于Java EE的后端REST API服务; 这两部分通常运行在同一个容器(如Tomcat)中,相互之间基于REST接口进行交互.类似这种应用,我们应该将其拆分到不同的容器中运行吗? 简单的回答:我

C++中如何在容器中使用继承和虚函数

容器不支持混合类型, 如果直接把派生类对象, 存入基类容器中, 则无法使用派生-基转换(derived-base conversion); 因为转换只能发生在指针和引用 过程中, 不能发生在 对象直接赋值, 如果是直接转换, 则会产生截断(sliced down); 即派生类部分被切除, 只留下基类部分; 所以存入容器中的派生类 输出为基类部分 的虚函数; 如果想在容器中, 进行继承, 则需要使用指针, 包括智能指针(如:shared_ptr<>), 则会输出派生类的覆写(override)版

Spring源代码解析(二):IOC容器在web容器中的启动

以下引用自博客:http://jiwenke-spring.blogspot.com/ 上面我们分析了IOC容器本身的实现,下面我们看看在典型的web环境中,Spring IOC 容器是怎样被载入和起作用的. 简单的说,在web容器中,通过ServletContext为Spring的IOC容器提供宿主环境,对 应的建立起一个IOC容器的体系.其中,首先需要建立的是根上下文,这个上下文持有的 对象可以有业务对象,数据存取对象,资源,事物管理器等各种中间层对象.在这个上下 文的基础上,和web MV

远程部署-使用jenkins发布maven项目到远程的jetty容器中

问题描述 使用jenkins发布maven项目到远程的jetty容器中 27C 如题(就这点币了)使用jenkins发布maven项目到远程的jetty容器中 解决方案 jenkins只是打包吧! 还能远程部署到jetty里吗? 这个没试过还真不知道.

如何在Ubuntu14.04的Docker容器中运行OpenVPN?

本文讲的是如何在Ubuntu14.04的Docker容器中运行OpenVPN?,[编者的话]本文来自DigitalOcean,DigitalOcean是美国的虚拟专用服务器提供商,本文主要介绍了如何在Ubuntu14.04上创建使用OpenVPN Docker容器. 介绍 本教程将介绍如何使用Docker来设置和运行OpenVPN容器. OpenVPN提供了一种方法来创建TLS加密(SSL的演进)的虚拟专用网络(VPN).它可以防止网络流量被窃取和中间人(MITM)攻击.专用网络可以用来安全地连

.NET程序在Linux容器中的演变

本文讲的是.NET程序在Linux容器中的演变[编者的话]Linux容器技术已被开发人员所熟知,现在.NET程序可以跑在Docker容器中,这为以Windows中心的开发人员带来了好处. [上海站|3天烧脑式微服务架构训练营]培训内容包括:DevOps.微服务.Spring Cloud.Eureka.Ribbon.Feign.Hystrix.Zuul.Spring Cloud Config.Spring Cloud Sleuth等. 本文将首先讨论镜像的构建时间和启动时间,接着会将一个简单的.N

Spring容器中Bean的作用域

    当通过Spring容器创建一个Bean实例时,不仅可以完成Bean实例的实例化,还可以为Bean指定特定的作用域.Spring支持如下5种作用域: singleton:单例模式,在整个Spring IoC容器中,使用singleton定义的Bean将只有一个实例 prototype:原型模式,每次通过容器的getBean方法获取prototype定义的Bean时,都将产生一个新的Bean实例 request:对于每次HTTP请求,使用request定义的Bean都将产生一个新实例,即每次

去除arraylist容器中的相同的对象元素的方法_Android

<span class="keyword" style="background-color: rgb(250, 250, 250); font-size: 1em; font-family: Monaco, 'DejaVu Sans Mono', 'Bitstream Vera Sans Mono', Consolas, 'Courier New', monospace;">boolean</span><span style="

c++builder如何将容器中的组件坐标转化为相对空间相对与窗体的坐标

问题描述 c++builder如何将容器中的组件坐标转化为相对空间相对与窗体的坐标 5C c++builder设计窗体时,用了个多页窗体PageControl,在PageControl中加了个Stringgrid1我需要在stringgrid1的第二列加上combobox,但是怎么设置坐标运行结果都错,我是拿stringgrid1的屏幕坐标减去窗体的屏幕坐标在加上单元格相对于stringgrid1的位置,但是运行的位置总是不对,拜托各位大神帮个忙,我这一直弄不出来,下面工作没法继续!刚注册的账号