Skip to content
体验新版
项目
组织
正在加载...
登录
切换导航
打开侧边栏
镜像
Containers
Podman Compose
比较版本
f75d12af21d54cdbc783d59a0663e3f95df48720...06587c1dca031c51932ba1a8673eb93a09a37c5d
P
Podman Compose
项目概览
镜像
/
Containers
/
Podman Compose
9 个月 前同步成功
通知
9
Star
0
Fork
0
代码
文件
提交
分支
Tags
贡献者
分支图
Diff
Issue
0
列表
看板
标记
里程碑
合并请求
0
DevOps
流水线
流水线任务
计划
Wiki
0
Wiki
分析
仓库
DevOps
项目成员
Pages
P
Podman Compose
项目概览
项目概览
详情
发布
仓库
仓库
文件
提交
分支
标签
贡献者
分支图
比较
Issue
0
Issue
0
列表
看板
标记
里程碑
合并请求
0
合并请求
0
Pages
DevOps
DevOps
流水线
流水线任务
计划
分析
分析
仓库分析
DevOps
Wiki
0
Wiki
成员
成员
收起侧边栏
关闭侧边栏
动态
分支图
创建新Issue
流水线任务
提交
Issue看板
前往新版Gitcode,体验更适合开发者的 AI 搜索 >>
源分支
06587c1dca031c51932ba1a8673eb93a09a37c5d
选择Git版本
...
目标分支
f75d12af21d54cdbc783d59a0663e3f95df48720
选择Git版本
比较
Commits (7)
https://gitcode.net/awesome-mirrors/containers/podman-compose/-/commit/280f1770bf10731a842ed15a9cfe50bdbca5d84f
Add a test to extend using an empty service (placeholder)
2023-07-26T17:32:14+03:00
Natanael Arndt
arndtn@gmail.com
Signed-off-by: <span data-trailer="Signed-off-by:"><a href="mailto:arndtn@gmail.com" title="arndtn@gmail.com"></a><a href="javascript:void(0)" class="avatar s16 avatar-inline identicon bg2" style="text-decoration: none">N</a><a href="mailto:arndtn@gmail.com" title="arndtn@gmail.com">Natanael Arndt</a> <<a href="mailto:arndtn@gmail.com" title="arndtn@gmail.com">arndtn@gmail.com</a>></span>
https://gitcode.net/awesome-mirrors/containers/podman-compose/-/commit/e5cdce4e7d6b9b73528237346f43b5fe3b8bfd01
default to an empty dict for the from service if the service is None
2023-07-26T17:32:14+03:00
Natanael Arndt
arndtn@gmail.com
Signed-off-by: <span data-trailer="Signed-off-by:"><a href="mailto:arndtn@gmail.com" title="arndtn@gmail.com"></a><a href="javascript:void(0)" class="avatar s16 avatar-inline identicon bg1" style="text-decoration: none">N</a><a href="mailto:arndtn@gmail.com" title="arndtn@gmail.com">Natanael Arndt</a> <<a href="mailto:arndtn@gmail.com" title="arndtn@gmail.com">arndtn@gmail.com</a>></span>
https://gitcode.net/awesome-mirrors/containers/podman-compose/-/commit/0164c1db56f5e30d454451fa0c02156f81c07609
Simplify the fix using `or`.
2023-07-26T17:32:14+03:00
Natanael Arndt
arndtn@gmail.com
Signed-off-by: <span data-trailer="Signed-off-by:"><a href="mailto:arndtn@gmail.com" title="arndtn@gmail.com"></a><a href="javascript:void(0)" class="avatar s16 avatar-inline identicon bg1" style="text-decoration: none">N</a><a href="mailto:arndtn@gmail.com" title="arndtn@gmail.com">Natanael Arndt</a> <<a href="mailto:arndtn@gmail.com" title="arndtn@gmail.com">arndtn@gmail.com</a>></span>
https://gitcode.net/awesome-mirrors/containers/podman-compose/-/commit/d1f5ac9edc8473e45202f0737fb2a05cf04b9edb
convert build context path to absolute during final normalisation
2023-08-02T14:19:15+03:00
Sergei Biriukov
svbiriukov@gmail.com
Signed-off-by: <span data-trailer="Signed-off-by:"><a href="mailto:svbiriukov@gmail.com" title="svbiriukov@gmail.com"></a><a href="javascript:void(0)" class="avatar s16 avatar-inline identicon bg4" style="text-decoration: none">N</a><a href="mailto:svbiriukov@gmail.com" title="svbiriukov@gmail.com">Sergei Biriukov</a> <<a href="mailto:svbiriukov@gmail.com" title="svbiriukov@gmail.com">svbiriukov@gmail.com</a>></span>
https://gitcode.net/awesome-mirrors/containers/podman-compose/-/commit/57c527c2c982dfa2fdaa114bc6fe8856ba68db7e
add edits from review
2023-08-02T14:19:15+03:00
Sergei Biriukov
svbiriukov@gmail.com
Signed-off-by: <span data-trailer="Signed-off-by:"><a href="mailto:svbiriukov@gmail.com" title="svbiriukov@gmail.com"></a><a href="javascript:void(0)" class="avatar s16 avatar-inline identicon bg6" style="text-decoration: none">N</a><a href="mailto:svbiriukov@gmail.com" title="svbiriukov@gmail.com">Sergei Biriukov</a> <<a href="mailto:svbiriukov@gmail.com" title="svbiriukov@gmail.com">svbiriukov@gmail.com</a>></span>
https://gitcode.net/awesome-mirrors/containers/podman-compose/-/commit/bc9168b03927ff48120fa89cbebf5d1a47f1c74f
add no-normalize flag
2023-08-02T14:19:15+03:00
Evedel
svbiriukov@gmail.com
Signed-off-by: <span data-trailer="Signed-off-by:"><a href="mailto:svbiriukov@gmail.com" title="svbiriukov@gmail.com"></a><a href="javascript:void(0)" class="avatar s16 avatar-inline identicon bg3" style="text-decoration: none">N</a><a href="mailto:svbiriukov@gmail.com" title="svbiriukov@gmail.com">Evedel</a> <<a href="mailto:svbiriukov@gmail.com" title="svbiriukov@gmail.com">svbiriukov@gmail.com</a>></span>
https://gitcode.net/awesome-mirrors/containers/podman-compose/-/commit/06587c1dca031c51932ba1a8673eb93a09a37c5d
rm redundant tests
2023-08-02T14:19:15+03:00
Evedel
svbiriukov@gmail.com
Signed-off-by: <span data-trailer="Signed-off-by:"><a href="mailto:svbiriukov@gmail.com" title="svbiriukov@gmail.com"></a><a href="javascript:void(0)" class="avatar s16 avatar-inline identicon bg1" style="text-decoration: none">N</a><a href="mailto:svbiriukov@gmail.com" title="svbiriukov@gmail.com">Evedel</a> <<a href="mailto:svbiriukov@gmail.com" title="svbiriukov@gmail.com">svbiriukov@gmail.com</a>></span>
隐藏空白更改
内联
并排
Showing
7 changed file
with
374 addition
and
3 deletion
+374
-3
podman_compose.py
podman_compose.py
+31
-2
pytests/test_can_merge_build.py
pytests/test_can_merge_build.py
+4
-1
pytests/test_can_merge_cmd_ent.py
pytests/test_can_merge_cmd_ent.py
+1
-0
pytests/test_normalize_final_build.py
pytests/test_normalize_final_build.py
+298
-0
tests/extends_w_empty_service/common-services.yml
tests/extends_w_empty_service/common-services.yml
+7
-0
tests/extends_w_empty_service/docker-compose.yml
tests/extends_w_empty_service/docker-compose.yml
+10
-0
tests/test_podman_compose.py
tests/test_podman_compose.py
+23
-0
未找到文件。
podman_compose.py
浏览文件 @
06587c1d
#!
/usr/bin/
python3
#!
/usr/bin/env
python3
# -*- coding: utf-8 -*-
# https://docs.docker.com/compose/compose-file/#service-configuration-reference
...
...
@@ -1297,6 +1297,30 @@ def normalize(compose):
return
compose
def
normalize_service_final
(
service
:
dict
,
project_dir
:
str
)
->
dict
:
if
"build"
in
service
:
build
=
service
[
"build"
]
context
=
build
if
is_str
(
build
)
else
build
.
get
(
"context"
,
"."
)
context
=
os
.
path
.
normpath
(
os
.
path
.
join
(
project_dir
,
context
))
dockerfile
=
(
"Dockerfile"
if
is_str
(
build
)
else
service
[
"build"
].
get
(
"dockerfile"
,
"Dockerfile"
)
)
if
not
is_dict
(
service
[
"build"
]):
service
[
"build"
]
=
{}
service
[
"build"
][
"dockerfile"
]
=
dockerfile
service
[
"build"
][
"context"
]
=
context
return
service
def
normalize_final
(
compose
:
dict
,
project_dir
:
str
)
->
dict
:
services
=
compose
.
get
(
"services"
,
None
)
or
{}
for
service
in
services
.
values
():
normalize_service_final
(
service
,
project_dir
)
return
compose
def
clone
(
value
):
return
value
.
copy
()
if
is_list
(
value
)
or
is_dict
(
value
)
else
value
...
...
@@ -1375,7 +1399,7 @@ def resolve_extends(services, service_names, environ):
content
=
content
[
"services"
]
subdirectory
=
os
.
path
.
dirname
(
filename
)
content
=
rec_subs
(
content
,
environ
)
from_service
=
content
.
get
(
from_service_name
,
{})
from_service
=
content
.
get
(
from_service_name
,
{})
or
{}
normalize_service
(
from_service
,
subdirectory
)
else
:
from_service
=
services
.
get
(
from_service_name
,
{}).
copy
()
...
...
@@ -1603,6 +1627,8 @@ class PodmanCompose:
compose
.
get
(
"services"
,
{}),
set
(
args
.
profile
)
)
compose
[
"services"
]
=
resolved_services
if
not
getattr
(
args
,
"no_normalize"
,
None
):
compose
=
normalize_final
(
compose
,
self
.
dirname
)
self
.
merged_yaml
=
yaml
.
safe_dump
(
compose
)
merged_json_b
=
json
.
dumps
(
compose
,
separators
=
(
","
,
":"
)).
encode
(
"utf-8"
)
self
.
yaml_hash
=
hashlib
.
sha256
(
merged_json_b
).
hexdigest
()
...
...
@@ -3057,6 +3083,9 @@ def compose_build_parse(parser):
@
cmd_parse
(
podman_compose
,
"config"
)
def
compose_config_parse
(
parser
):
parser
.
add_argument
(
"--no-normalize"
,
help
=
"Don't normalize compose model."
,
action
=
"store_true"
)
parser
.
add_argument
(
"--services"
,
help
=
"Print the service names, one per line."
,
action
=
"store_true"
)
...
...
pytests/test_can_merge_build.py
浏览文件 @
06587c1d
...
...
@@ -138,7 +138,9 @@ def test__parse_compose_file_when_multiple_composes() -> None:
if
actual_compose
!=
expected_result
:
print
(
"compose: "
,
test_input
)
print
(
"override: "
,
test_override
)
print
(
"result: "
,
expected_result
)
print
(
"expected: "
,
expected_result
)
print
(
"actual: "
,
actual_compose
)
compose_expected
=
expected_result
assert
compose_expected
==
actual_compose
...
...
@@ -151,6 +153,7 @@ def set_args(podman_compose: PodmanCompose, file_names: list[str]) -> None:
podman_compose
.
global_args
.
env_file
=
None
podman_compose
.
global_args
.
profile
=
[]
podman_compose
.
global_args
.
in_pod
=
True
podman_compose
.
global_args
.
no_normalize
=
True
def
dump_yaml
(
compose
:
dict
,
name
:
str
)
->
None
:
...
...
pytests/test_can_merge_cmd_ent.py
浏览文件 @
06587c1d
...
...
@@ -107,6 +107,7 @@ def set_args(podman_compose: PodmanCompose, file_names: list[str]) -> None:
podman_compose
.
global_args
.
env_file
=
None
podman_compose
.
global_args
.
profile
=
[]
podman_compose
.
global_args
.
in_pod
=
True
podman_compose
.
global_args
.
no_normalize
=
None
def
dump_yaml
(
compose
:
dict
,
name
:
str
)
->
None
:
...
...
pytests/test_normalize_final_build.py
0 → 100644
浏览文件 @
06587c1d
# pylint: disable=protected-access
import
argparse
import
copy
import
os
import
yaml
from
podman_compose
import
(
normalize_service
,
normalize
,
normalize_final
,
normalize_service_final
,
PodmanCompose
,
)
cwd
=
os
.
path
.
abspath
(
"."
)
test_cases_simple_normalization
=
[
({
"image"
:
"test-image"
},
{
"image"
:
"test-image"
}),
(
{
"build"
:
"."
},
{
"build"
:
{
"context"
:
cwd
,
"dockerfile"
:
"Dockerfile"
},
},
),
(
{
"build"
:
"../relative"
},
{
"build"
:
{
"context"
:
os
.
path
.
normpath
(
os
.
path
.
join
(
cwd
,
"../relative"
)),
"dockerfile"
:
"Dockerfile"
,
},
},
),
(
{
"build"
:
"./relative"
},
{
"build"
:
{
"context"
:
os
.
path
.
normpath
(
os
.
path
.
join
(
cwd
,
"./relative"
)),
"dockerfile"
:
"Dockerfile"
,
},
},
),
(
{
"build"
:
"/workspace/absolute"
},
{
"build"
:
{
"context"
:
"/workspace/absolute"
,
"dockerfile"
:
"Dockerfile"
,
},
},
),
(
{
"build"
:
{
"dockerfile"
:
"Dockerfile"
,
},
},
{
"build"
:
{
"context"
:
cwd
,
"dockerfile"
:
"Dockerfile"
,
},
},
),
(
{
"build"
:
{
"context"
:
"."
,
},
},
{
"build"
:
{
"context"
:
cwd
,
"dockerfile"
:
"Dockerfile"
,
},
},
),
(
{
"build"
:
{
"context"
:
"../"
,
"dockerfile"
:
"test-dockerfile"
},
},
{
"build"
:
{
"context"
:
os
.
path
.
normpath
(
os
.
path
.
join
(
cwd
,
"../"
)),
"dockerfile"
:
"test-dockerfile"
,
},
},
),
(
{
"build"
:
{
"context"
:
"."
,
"dockerfile"
:
"./dev/test-dockerfile"
},
},
{
"build"
:
{
"context"
:
cwd
,
"dockerfile"
:
"./dev/test-dockerfile"
,
},
},
),
]
#
# [service.build] is normalised after merges
#
def
test_normalize_service_final_returns_absolute_path_in_context
()
->
None
:
project_dir
=
cwd
for
test_input
,
expected_service
in
copy
.
deepcopy
(
test_cases_simple_normalization
):
actual_service
=
normalize_service_final
(
test_input
,
project_dir
)
assert
expected_service
==
actual_service
def
test_normalize_returns_absolute_path_in_context
()
->
None
:
project_dir
=
cwd
for
test_input
,
expected_result
in
copy
.
deepcopy
(
test_cases_simple_normalization
):
compose_test
=
{
"services"
:
{
"test-service"
:
test_input
}}
compose_expected
=
{
"services"
:
{
"test-service"
:
expected_result
}}
actual_compose
=
normalize_final
(
compose_test
,
project_dir
)
assert
compose_expected
==
actual_compose
#
# running full parse over single compose files
#
def
test__parse_compose_file_when_single_compose
()
->
None
:
for
test_input
,
expected_result
in
copy
.
deepcopy
(
test_cases_simple_normalization
):
compose_test
=
{
"services"
:
{
"test-service"
:
test_input
}}
dump_yaml
(
compose_test
,
"test-compose.yaml"
)
podman_compose
=
PodmanCompose
()
set_args
(
podman_compose
,
[
"test-compose.yaml"
],
no_normalize
=
None
)
podman_compose
.
_parse_compose_file
()
actual_compose
=
{}
if
podman_compose
.
services
:
podman_compose
.
services
[
"test-service"
].
pop
(
"_deps"
)
actual_compose
=
podman_compose
.
services
[
"test-service"
]
if
actual_compose
!=
expected_result
:
print
(
"compose: "
,
test_input
)
print
(
"result: "
,
expected_result
)
assert
expected_result
==
actual_compose
test_cases_with_merges
=
[
(
{},
{
"build"
:
"."
},
{
"build"
:
{
"context"
:
cwd
,
"dockerfile"
:
"Dockerfile"
}},
),
(
{
"build"
:
"."
},
{},
{
"build"
:
{
"context"
:
cwd
,
"dockerfile"
:
"Dockerfile"
}},
),
(
{
"build"
:
"/workspace/absolute"
},
{
"build"
:
"./relative"
},
{
"build"
:
{
"context"
:
os
.
path
.
normpath
(
os
.
path
.
join
(
cwd
,
"./relative"
)),
"dockerfile"
:
"Dockerfile"
,
}
},
),
(
{
"build"
:
"./relative"
},
{
"build"
:
"/workspace/absolute"
},
{
"build"
:
{
"context"
:
"/workspace/absolute"
,
"dockerfile"
:
"Dockerfile"
}},
),
(
{
"build"
:
"./relative"
},
{
"build"
:
"/workspace/absolute"
},
{
"build"
:
{
"context"
:
"/workspace/absolute"
,
"dockerfile"
:
"Dockerfile"
}},
),
(
{
"build"
:
{
"dockerfile"
:
"test-dockerfile"
}},
{},
{
"build"
:
{
"context"
:
cwd
,
"dockerfile"
:
"test-dockerfile"
}},
),
(
{},
{
"build"
:
{
"dockerfile"
:
"test-dockerfile"
}},
{
"build"
:
{
"context"
:
cwd
,
"dockerfile"
:
"test-dockerfile"
}},
),
(
{},
{
"build"
:
{
"dockerfile"
:
"test-dockerfile"
}},
{
"build"
:
{
"context"
:
cwd
,
"dockerfile"
:
"test-dockerfile"
}},
),
(
{
"build"
:
{
"dockerfile"
:
"test-dockerfile-1"
}},
{
"build"
:
{
"dockerfile"
:
"test-dockerfile-2"
}},
{
"build"
:
{
"context"
:
cwd
,
"dockerfile"
:
"test-dockerfile-2"
}},
),
(
{
"build"
:
"/workspace/absolute"
},
{
"build"
:
{
"dockerfile"
:
"test-dockerfile"
}},
{
"build"
:
{
"context"
:
"/workspace/absolute"
,
"dockerfile"
:
"test-dockerfile"
}},
),
(
{
"build"
:
{
"dockerfile"
:
"test-dockerfile"
}},
{
"build"
:
"/workspace/absolute"
},
{
"build"
:
{
"context"
:
"/workspace/absolute"
,
"dockerfile"
:
"test-dockerfile"
}},
),
(
{
"build"
:
{
"dockerfile"
:
"./test-dockerfile-1"
}},
{
"build"
:
{
"dockerfile"
:
"./test-dockerfile-2"
,
"args"
:
[
"ENV1=1"
]}},
{
"build"
:
{
"context"
:
cwd
,
"dockerfile"
:
"./test-dockerfile-2"
,
"args"
:
[
"ENV1=1"
],
}
},
),
(
{
"build"
:
{
"dockerfile"
:
"./test-dockerfile-1"
,
"args"
:
[
"ENV1=1"
]}},
{
"build"
:
{
"dockerfile"
:
"./test-dockerfile-2"
}},
{
"build"
:
{
"context"
:
cwd
,
"dockerfile"
:
"./test-dockerfile-2"
,
"args"
:
[
"ENV1=1"
],
}
},
),
(
{
"build"
:
{
"dockerfile"
:
"./test-dockerfile-1"
,
"args"
:
[
"ENV1=1"
]}},
{
"build"
:
{
"dockerfile"
:
"./test-dockerfile-2"
,
"args"
:
[
"ENV2=2"
]}},
{
"build"
:
{
"context"
:
cwd
,
"dockerfile"
:
"./test-dockerfile-2"
,
"args"
:
[
"ENV1=1"
,
"ENV2=2"
],
}
},
),
]
#
# running full parse over merged
#
def
test__parse_compose_file_when_multiple_composes
()
->
None
:
for
test_input
,
test_override
,
expected_result
in
copy
.
deepcopy
(
test_cases_with_merges
):
compose_test_1
=
{
"services"
:
{
"test-service"
:
test_input
}}
compose_test_2
=
{
"services"
:
{
"test-service"
:
test_override
}}
dump_yaml
(
compose_test_1
,
"test-compose-1.yaml"
)
dump_yaml
(
compose_test_2
,
"test-compose-2.yaml"
)
podman_compose
=
PodmanCompose
()
set_args
(
podman_compose
,
[
"test-compose-1.yaml"
,
"test-compose-2.yaml"
],
no_normalize
=
None
,
)
podman_compose
.
_parse_compose_file
()
actual_compose
=
{}
if
podman_compose
.
services
:
podman_compose
.
services
[
"test-service"
].
pop
(
"_deps"
)
actual_compose
=
podman_compose
.
services
[
"test-service"
]
if
actual_compose
!=
expected_result
:
print
(
"compose: "
,
test_input
)
print
(
"override: "
,
test_override
)
print
(
"result: "
,
expected_result
)
compose_expected
=
expected_result
assert
compose_expected
==
actual_compose
def
set_args
(
podman_compose
:
PodmanCompose
,
file_names
:
list
[
str
],
no_normalize
:
bool
)
->
None
:
podman_compose
.
global_args
=
argparse
.
Namespace
()
podman_compose
.
global_args
.
file
=
file_names
podman_compose
.
global_args
.
project_name
=
None
podman_compose
.
global_args
.
env_file
=
None
podman_compose
.
global_args
.
profile
=
[]
podman_compose
.
global_args
.
in_pod
=
True
podman_compose
.
global_args
.
no_normalize
=
no_normalize
def
dump_yaml
(
compose
:
dict
,
name
:
str
)
->
None
:
# Path(Path.cwd()/"subdirectory").mkdir(parents=True, exist_ok=True)
with
open
(
name
,
"w"
,
encoding
=
"utf-8"
)
as
outfile
:
yaml
.
safe_dump
(
compose
,
outfile
,
default_flow_style
=
False
)
def
test_clean_test_yamls
()
->
None
:
test_files
=
[
"test-compose-1.yaml"
,
"test-compose-2.yaml"
,
"test-compose.yaml"
]
for
file
in
test_files
:
if
os
.
path
.
exists
(
file
):
os
.
remove
(
file
)
tests/extends_w_empty_service/common-services.yml
0 → 100644
浏览文件 @
06587c1d
services
:
webapp_default
:
webapp_special
:
image
:
busybox
volumes
:
-
"
/data"
tests/extends_w_empty_service/docker-compose.yml
0 → 100644
浏览文件 @
06587c1d
version
:
"
3"
services
:
web
:
image
:
busybox
extends
:
file
:
common-services.yml
service
:
webapp_default
environment
:
-
DEBUG=1
cpu_shares
:
5
tests/test_podman_compose.py
浏览文件 @
06587c1d
...
...
@@ -59,3 +59,26 @@ def test_podman_compose_extends_w_file_subdir():
out
,
_
,
returncode
=
capture
(
command_check_container
)
assert
0
==
returncode
assert
out
==
b
""
def
test_podman_compose_extends_w_empty_service
():
"""
Test that podman-compose can execute podman-compose -f <file> up with extended File which
includes an empty service. (e.g. if the file is used as placeholder for more complex configurations.)
:return:
"""
main_path
=
Path
(
__file__
).
parent
.
parent
command_up
=
[
"python3"
,
str
(
main_path
.
joinpath
(
"podman_compose.py"
)),
"-f"
,
str
(
main_path
.
joinpath
(
"tests"
,
"extends_w_empty_service"
,
"docker-compose.yml"
)
),
"up"
,
"-d"
,
]
_
,
_
,
returncode
=
capture
(
command_up
)
assert
0
==
returncode