fix(system-update): 用 compose label 查询容器,修复 isRunning 和自更新助手镜像
- isRunning() 改用 docker ps --filter label=com.docker.compose.service 兼容 Compose v1 (xuqm_svc_1) 和 v2 (xuqm-svc-1) 命名格式 - 自更新助手镜像改用 getCurrentImage() 从运行中容器的 label 获取, 不再依赖容器环境变量 REGISTRY/IMAGE_TAG(容器内未注入这两个变量) Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
这个提交包含在:
父节点
cc132c7ce7
当前提交
aece1fd08d
@ -51,9 +51,14 @@ public class SystemUpdateService {
|
|||||||
// 解决方案:先用 docker run -d 启动一个独立助手容器,它不依附于 tenant-service,
|
// 解决方案:先用 docker run -d 启动一个独立助手容器,它不依附于 tenant-service,
|
||||||
// 能在 tenant-service 停止后继续完成重建。
|
// 能在 tenant-service 停止后继续完成重建。
|
||||||
emit.accept(">>> 启动自更新助手容器...");
|
emit.accept(">>> 启动自更新助手容器...");
|
||||||
String registry = System.getenv().getOrDefault("REGISTRY", "");
|
// Resolve the image by inspecting the running container via compose labels,
|
||||||
String imageTag = System.getenv().getOrDefault("IMAGE_TAG", "latest");
|
// so we don't depend on REGISTRY/IMAGE_TAG being present in the container env.
|
||||||
String selfImage = registry.isEmpty() ? "alpine" : (registry + "/tenant-service:" + imageTag);
|
String selfImage = getCurrentImage();
|
||||||
|
if (selfImage == null) {
|
||||||
|
emit.accept(">>> [错误] 无法获取当前 tenant-service 镜像名,请检查容器标签或手动执行更新。");
|
||||||
|
emit.accept("DONE");
|
||||||
|
return;
|
||||||
|
}
|
||||||
boolean helperStarted = spawnSelfUpdater(composeFile, selfImage);
|
boolean helperStarted = spawnSelfUpdater(composeFile, selfImage);
|
||||||
|
|
||||||
if (helperStarted) {
|
if (helperStarted) {
|
||||||
@ -100,19 +105,39 @@ public class SystemUpdateService {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// Use compose labels instead of container name — works with both Compose v1 (xuqm_svc_1)
|
||||||
|
// and Compose v2 (xuqm-svc-1) naming conventions.
|
||||||
private boolean isRunning(String service) {
|
private boolean isRunning(String service) {
|
||||||
String containerName = "xuqm-" + service;
|
|
||||||
try {
|
try {
|
||||||
Process p = new ProcessBuilder("docker", "inspect", "--type=container", containerName)
|
Process p = new ProcessBuilder(
|
||||||
.redirectErrorStream(true)
|
"docker", "ps", "-q",
|
||||||
.start();
|
"--filter", "label=com.docker.compose.project=xuqm",
|
||||||
p.getInputStream().transferTo(java.io.OutputStream.nullOutputStream());
|
"--filter", "label=com.docker.compose.service=" + service
|
||||||
return p.waitFor() == 0;
|
).redirectErrorStream(true).start();
|
||||||
|
String out = new String(p.getInputStream().readAllBytes()).trim();
|
||||||
|
p.waitFor();
|
||||||
|
return !out.isEmpty();
|
||||||
} catch (Exception e) {
|
} catch (Exception e) {
|
||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
private String getCurrentImage() {
|
||||||
|
try {
|
||||||
|
Process p = new ProcessBuilder(
|
||||||
|
"docker", "ps",
|
||||||
|
"--filter", "label=com.docker.compose.project=xuqm",
|
||||||
|
"--filter", "label=com.docker.compose.service=tenant-service",
|
||||||
|
"--format", "{{.Image}}"
|
||||||
|
).redirectErrorStream(true).start();
|
||||||
|
String out = new String(p.getInputStream().readAllBytes()).trim();
|
||||||
|
p.waitFor();
|
||||||
|
return out.isEmpty() ? null : out;
|
||||||
|
} catch (Exception e) {
|
||||||
|
return null;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
private void exec(Consumer<String> emit, String... cmd) {
|
private void exec(Consumer<String> emit, String... cmd) {
|
||||||
try {
|
try {
|
||||||
Process p = new ProcessBuilder(cmd)
|
Process p = new ProcessBuilder(cmd)
|
||||||
|
|||||||
正在加载...
在新工单中引用
屏蔽一个用户