Common docker compose items as yaml fragments

huangapple go评论74阅读模式
英文:

Common docker compose items as yaml fragments

问题

I want to clean up my docker-compose.yml with yaml fragments.

x-common: &common
  restart: unless-stopped
  security_opt: 
    - no-new-privileges:true
  volumes:
    - /etc/localtime:/etc/localtime:ro

services:

  myapp1:
    <<: *common
    image: app1
    volumes:
      - ./foo:/foo

  myapp2:
    <<: *common
    image: app2
    volumes:
      - ./bar:/bar

When I run docker compose config to show the final result, the common restart and security_opt items are applied. But the common volumes item is not - I assume this is because the services are overwriting it.

Is there a way to do this?

英文:

I want to clean up my docker-compose.yml with yaml fragments.

x-common: &amp;common
  restart: unless-stopped
  security_opt: 
    - no-new-privileges:true
  volumes:
    - /etc/localtime:/etc/localtime:ro

services:

  myapp1:
    &lt;&lt;: *common
    image: app1
    volumes:
      - ./foo:/foo

  myapp2:
    &lt;&lt;: *common
    image: app2
    volumes:
      - ./bar:/bar

When I run docker compose config to show the final result, the common restart and security_opt items are applied. But the common volumes item is not - I assume this is because the services are overwriting it.

Is there a way to do this?

答案1

得分: 1

这是您提供的代码示例的中文翻译:

这个问题没有一个很好的解决方式。复杂的因素在于`volumes`是一个*列表*,而不是一个字典,而YAML没有合并列表的语法。

你可以尝试像这样做:

```yaml
x-common: &common
  restart: unless-stopped
  security_opt: 
    - no-new-privileges:true

x-common-volume: &volume /etc/localtime:/etc/localtime:ro

services:

  myapp1:
    <<: *common
    image: app1
    volumes:
      - *volume
      - ./foo:/foo

  myapp2:
    <<: *common
    image: app2
    volumes:
      - *volume
      - ./bar:/bar

这可以让你完成一半的工作 - 你需要记得将共同的卷添加到每个服务中,但你不必每次都重新输入完整的条目。


根据这个问题的严重程度,你可以考虑使用某种模板机制生成你的docker-compose.yml文件 - 例如,使用jsonnet

local Common = {
  restart: 'unless-stopped',
  security_opt: ['no-new-privileges:true'],
  volumes: [
    '/etc/localtime:/etc/localtime:ro',
  ]
};

{
  services: {
    myapp1: Common {
      image: 'app1',
      volumes+: [
        './foo:/foo',
      ],
    },
    myapp2: Common {
      image: 'app2',
      volumes+: [
        './bar:/bar',
      ],
    },
  },
}

通过运行jsonnet docker-compose.jsonnet > docker-compose.yaml生成你的docker-compose.yml文件,你就可以得到你想要的内容。

英文:

There's not really a great way to do this. The complicating factor is that volumes is a list, rather than a dictionary, and YAML doesn't have a syntax for merging lists.

You could do something like this:

x-common: &amp;common
  restart: unless-stopped
  security_opt: 
    - no-new-privileges:true

x-common-volume: &amp;volume /etc/localtime:/etc/localtime:ro

services:

  myapp1:
    &lt;&lt;: *common
    image: app1
    volumes:
      - *volume
      - ./foo:/foo

  myapp2:
    &lt;&lt;: *common
    image: app2
    volumes:
      - *volume
      - ./bar:/bar

Which gets you halfway there -- you need to remember to add the common volume to each service, but you don't have to retype the full entry each time.


Depending on how much this bothers you, you could look into generating your docker-compose.yml files with some sort of templating mechanism -- e.g., using jsonnet:

local Common = {
  restart: &#39;unless-stopped&#39;,
  security_opt: [&#39;no-new-privileges:true&#39;],
  volumes: [
    &#39;/etc/localtime:/etc/localtime:ro&#39;,
  ]
};

{
  services: {
    myapp1: Common {
      image: &#39;app1&#39;,
      volumes+: [
        &#39;./foo:/foo&#39;,
      ],
    },
    myapp2: Common {
      image: &#39;app2&#39;,
      volumes+: [
        &#39;./bar:/bar&#39;,
      ],
    },
  },
}

Generating your docker-compose.yml by running jsonnet docker-compose.jsonnet &gt; docker-compose.yaml and you've got what you want.

huangapple
  • 本文由 发表于 2023年6月12日 21:54:31
  • 转载请务必保留本文链接:https://go.coder-hub.com/76457369.html
匿名

发表评论

匿名网友

:?: :razz: :sad: :evil: :!: :smile: :oops: :grin: :eek: :shock: :???: :cool: :lol: :mad: :twisted: :roll: :wink: :idea: :arrow: :neutral: :cry: :mrgreen:

确定