Windows上的最佳做法Docker卷

Windows上的最佳做法Docker卷,docker,docker-compose,docker-volume,Docker,Docker Compose,Docker Volume,我正在运行Windows 10,我想使用docker compose将主机的一些目录装载到docker容器中 假设我有一个包含图片的文件夹: D:\MyPictures 我想在Docker中创建一个卷,并将该卷装载到不同的容器中,以便能够访问图片。 最好我只需要定义一次我的卷,这样我就可以通过名称或类似的方式引用它(如果我想在将来移动图片文件夹,我只有一个地方可以更新路径)。 如果我可以为每个容器指定该容器是具有读/写访问权限还是仅具有读访问权限,那就太好了 如果我直接在服务下指定卷,我知道如何

我正在运行Windows 10,我想使用docker compose将主机的一些目录装载到docker容器中

假设我有一个包含图片的文件夹:
D:\MyPictures

我想在Docker中创建一个卷,并将该卷装载到不同的容器中,以便能够访问图片。 最好我只需要定义一次我的卷,这样我就可以通过名称或类似的方式引用它(如果我想在将来移动图片文件夹,我只有一个地方可以更新路径)。 如果我可以为每个容器指定该容器是具有读/写访问权限还是仅具有读访问权限,那就太好了

如果我直接在服务下指定卷,我知道如何执行此操作:

myservice:
  volumes:
    - /c/MyPictures:/mount/path/in/container
但是如果我移动我的图片,我会有多个地方来更新路径

当阅读有关使用
docker volume create
创建卷的内容时,我似乎无法指定每个容器的读/写访问权限

在Windows上实现这一点的最佳和最简单的方法是什么

  • 指定一个卷一次
  • 把它装在不同的容器里
  • 每个容器的访问粒度
  • 最佳答案(由orderlyfashion找到):

    使用环境变量

  • 使用变量
    MY_PICTURES=/c/MyPictures
  • docker compose.yml
    中,容器的卷部分下,装载为:
    -${MY_PICTURES}:/MY_PICTURES:ro
  • docker compose--env file global.env up开始

  • 如果使用
    docker volume create
    创建卷,则可以在compose的顶级
    volume
    部分中指定该卷,然后使用卷名,后跟每个容器中的路径和访问权限,这样就不会阻止您指定访问权限

    具体来看

    简短语法使用通用的[SOURCE:]TARGET[:MODE]格式,其中SOURCE可以是主机路径或卷名。TARGET是装入卷的容器路径。标准模式为只读的ro模式和读写的rw模式(默认)


    执行此操作时的下一个问题是,与绑定装载相反,无法将命名卷绑定到特定文件夹

    当您执行
    -v:
    时,您将创建一个绑定挂载。它是主机文件系统中的一个特定文件夹,安装在容器文件系统中,这很好,但它有一个缺点:无法共享

    添加
    顶级选项或执行
    docker卷创建
    时,将创建一个命名卷。命名卷是可以跨容器共享的空间,但不能绑定到主机上的特定文件夹。但如果您将数据写入此卷,它将保留在其中,这是一个持久卷

    所以问题是:如何用数据初始化这个卷?答案是将该卷装入一个容器中,该容器将在卷中写入数据。这并不优雅,而且有点复杂,但这就是解决方案

    如何做到这一点:

    在docker-compose.yml中,添加此服务和卷:

    services:
      initializer:
        image: <someimage> #I use python:3.9-slim, could be a simple busybox
        command: cp -R /mnt/. /media/
        volumes:
          - ./somefolder:/mnt
          - data_volume:/media
        service_you_want_to_attach_volume_to:
          ...
          volumes:
            - data_volume:<some path>:ro #or rw, you can set the rights per container
          depends_on:
            - initializer
    
    volumes:
      data_volume:
    
    服务:
    初始值设定项:
    图片:#我使用python:3.9-slim,可以是一个简单的busybox
    命令:cp-R/mnt//媒体/
    卷数:
    -/somefolder:/mnt
    -数据卷:/media
    要将卷附加到的服务:
    ...
    卷数:
    -data_volume::ro或rw,您可以设置每个容器的权限
    取决于:
    -初始值设定项
    卷数:
    数据量:
    
    容器初始值设定项将启动,装载文件夹和/mnt中所需的数据,装载/media中的命名卷,将数据从/mnt(因此要共享的数据)复制到/media(要共享的命名卷),然后停止(因为它已完成其主进程)

    命名卷现在已初始化,可以共享给任何具有所需访问权限(
    ro
    rw
    )的容器

    正面:所有内容都在docker卷中,易于备份
    负面影响:数据将在卷内复制。您将获得两倍于相同数据量的数据,并且除非您重新进行初始化,否则数据将不会更新。所以有三个步骤。1)
    创建docker卷
    。2) 列出docker compose中的卷。3) 请参阅docker compose中服务配置中的卷。我不明白的是,我应该在哪里指定主机上的路径?对于步骤1,它说Windows上的内置本地驱动程序不支持任何选项。
    ,因此我不知道如何在那里指定路径。对于步骤2,我尝试了
    my-pictures://c/MyPictures
    我的-pictures://c/MyPictures:/my-图片
    和一堆不同的东西,但都是无效的。对不起,花了这么长时间,我在回答中解释了这个过程。这对你有用吗?对不起,我有个主意,直到现在才有时间测试。我通过使用变量提出了另一个解决方案。1) 使用变量
    MY_PICTURES=/c/MyPictures
    创建一个文件
    globals.env
    。2) 在
    docker compose.yml
    中,容器的卷部分下,装载为:
    -${MY_PICTURES}:/MY_PICTURES:ro
    。3) 从
    docker compose--env file global.env up开始
    。这似乎满足了我的要求,并且奏效了。你认为这种方法有什么问题吗?在您的解决方案中,数据是否以某种方式重复?我不确定我是否完全理解复制步骤的工作原理。您的解决方案非常好:)在我的解决方案中,创建了一个容器并在其中装入了卷。然后将数据复制到此卷中。之后,卷可以由多个容器共享(无数据复制)。它比一个简单的变量要昂贵得多!