From 1b48e955bdaa1e4d7c6a674583da001397d17e26 Mon Sep 17 00:00:00 2001 From: slhafzjw Date: Sat, 11 Apr 2026 16:10:34 +0800 Subject: [PATCH] refactor(core): migrate deprecated exceptions to new hierarchy and align tests --- .../common/vector/OllamaVectorClient.java | 17 +++++- .../common/vector/OnnxVectorClient.java | 27 +++++++-- .../partner/common/vector/VectorClient.java | 58 ++++++++++++++++--- .../VectorClientExecuteException.java | 15 ----- .../VectorClientExecutionException.java | 49 ++++++++++++++++ .../VectorClientLoadFailedException.java | 15 ----- .../VectorClientStartupException.java | 37 ++++++++++++ .../slhaf/partner/core/action/ActionCore.java | 20 +++++-- .../ActionInfrastructureStartupException.java | 39 +++++++++++++ .../exception/ActionInitFailedException.java | 13 ----- .../exception/ActionLookupException.java | 30 ++++++++++ .../ActionSerializationException.java | 58 +++++++++++++++++++ .../ActionSerializeFailedException.java | 13 ----- .../MetaActionNotFoundException.java | 13 ----- .../core/action/runner/LocalRunnerClient.java | 17 +++++- .../core/action/runner/RunnerClient.java | 10 +++- .../runner/mcp/DynamicActionMcpManager.java | 16 ++++- .../runner/policy/BwrapPolicyProvider.kt | 17 +++++- .../runner/support/ActionSerializer.java | 32 ++++++++-- .../action/builtin/BuiltinActionRegistry.java | 8 ++- .../core/action/runner/RunnerClientTest.java | 5 ++ .../runner/policy/BwrapPolicyProviderTest.kt | 28 +-------- .../builtin/BuiltinActionRegistryTest.java | 6 +- .../BuiltinDynamicActionProviderTest.java | 5 ++ .../AgentLaunchFailedException.java | 12 ---- .../AgentRunningFailedException.java | 12 ---- .../deprecated/AgentRuntimeException.java | 12 ---- .../partner/framework/agent/support/Result.kt | 5 +- 28 files changed, 414 insertions(+), 175 deletions(-) delete mode 100644 Partner-Core/src/main/java/work/slhaf/partner/common/vector/exception/VectorClientExecuteException.java create mode 100644 Partner-Core/src/main/java/work/slhaf/partner/common/vector/exception/VectorClientExecutionException.java delete mode 100644 Partner-Core/src/main/java/work/slhaf/partner/common/vector/exception/VectorClientLoadFailedException.java create mode 100644 Partner-Core/src/main/java/work/slhaf/partner/common/vector/exception/VectorClientStartupException.java create mode 100644 Partner-Core/src/main/java/work/slhaf/partner/core/action/exception/ActionInfrastructureStartupException.java delete mode 100644 Partner-Core/src/main/java/work/slhaf/partner/core/action/exception/ActionInitFailedException.java create mode 100644 Partner-Core/src/main/java/work/slhaf/partner/core/action/exception/ActionLookupException.java create mode 100644 Partner-Core/src/main/java/work/slhaf/partner/core/action/exception/ActionSerializationException.java delete mode 100644 Partner-Core/src/main/java/work/slhaf/partner/core/action/exception/ActionSerializeFailedException.java delete mode 100644 Partner-Core/src/main/java/work/slhaf/partner/core/action/exception/MetaActionNotFoundException.java delete mode 100644 Partner-Framework/src/main/java/work/slhaf/partner/framework/agent/exception/deprecated/AgentLaunchFailedException.java delete mode 100644 Partner-Framework/src/main/java/work/slhaf/partner/framework/agent/exception/deprecated/AgentRunningFailedException.java delete mode 100644 Partner-Framework/src/main/java/work/slhaf/partner/framework/agent/exception/deprecated/AgentRuntimeException.java diff --git a/Partner-Core/src/main/java/work/slhaf/partner/common/vector/OllamaVectorClient.java b/Partner-Core/src/main/java/work/slhaf/partner/common/vector/OllamaVectorClient.java index e6c15bdc..3c690972 100644 --- a/Partner-Core/src/main/java/work/slhaf/partner/common/vector/OllamaVectorClient.java +++ b/Partner-Core/src/main/java/work/slhaf/partner/common/vector/OllamaVectorClient.java @@ -5,7 +5,7 @@ import cn.hutool.http.HttpResponse; import com.alibaba.fastjson2.JSONObject; import lombok.Data; import lombok.extern.slf4j.Slf4j; -import work.slhaf.partner.common.vector.exception.VectorClientExecuteException; +import work.slhaf.partner.common.vector.exception.VectorClientExecutionException; import java.util.Map; @@ -28,12 +28,23 @@ public class OllamaVectorClient extends VectorClient { HttpRequest request = HttpRequest.get(ollamaEmbeddingUrl).body(JSONObject.toJSONString(param)); try (HttpResponse response = request.execute()) { if (!response.isOk()) - throw new VectorClientExecuteException("嵌入模型执行出错"); + throw new VectorClientExecutionException( + "Failed to execute embedding model", + "ollama", + "COMPUTE", + ollamaEmbeddingUrl + ); String resStr = response.body(); EmbeddingModelResponse embeddingResponse = JSONObject.parseObject(resStr, EmbeddingModelResponse.class); return embeddingResponse.getEmbeddings()[0]; } catch (Exception e) { - throw new VectorClientExecuteException("嵌入模型执行出错", e); + throw new VectorClientExecutionException( + "Failed to execute embedding model", + "ollama", + "COMPUTE", + ollamaEmbeddingUrl, + e + ); } } diff --git a/Partner-Core/src/main/java/work/slhaf/partner/common/vector/OnnxVectorClient.java b/Partner-Core/src/main/java/work/slhaf/partner/common/vector/OnnxVectorClient.java index 8060974c..902dc276 100644 --- a/Partner-Core/src/main/java/work/slhaf/partner/common/vector/OnnxVectorClient.java +++ b/Partner-Core/src/main/java/work/slhaf/partner/common/vector/OnnxVectorClient.java @@ -5,8 +5,7 @@ import ai.djl.huggingface.tokenizers.HuggingFaceTokenizer; import ai.onnxruntime.OnnxTensor; import ai.onnxruntime.OrtEnvironment; import ai.onnxruntime.OrtSession; -import work.slhaf.partner.common.vector.exception.VectorClientExecuteException; -import work.slhaf.partner.common.vector.exception.VectorClientLoadFailedException; +import work.slhaf.partner.common.vector.exception.VectorClientExecutionException; import java.nio.file.Path; import java.util.HashMap; @@ -38,7 +37,13 @@ public class OnnxVectorClient extends VectorClient { OrtSession.SessionOptions ops = new OrtSession.SessionOptions(); session = env.createSession(modelPath, ops); } catch (Exception e) { - throw new VectorClientLoadFailedException("加载ONNX模型失败", e); + throw new VectorClientExecutionException( + "Failed to load ONNX model", + "onnx", + "MODEL_LOAD", + modelPath, + e + ); } } @@ -46,7 +51,13 @@ public class OnnxVectorClient extends VectorClient { try { tokenizer = HuggingFaceTokenizer.newInstance(Path.of(tokenizerPath)); } catch (Exception e) { - throw new VectorClientLoadFailedException("加载Tokenizer失败", e); + throw new VectorClientExecutionException( + "Failed to load tokenizer", + "onnx", + "TOKENIZER_LOAD", + tokenizerPath, + e + ); } } @@ -76,7 +87,13 @@ public class OnnxVectorClient extends VectorClient { OnnxTensor embeddingTensor = (OnnxTensor) result.get(0); return embeddingTensor.getFloatBuffer().array(); } catch (Exception e) { - throw new VectorClientExecuteException("嵌入模型执行出错", e); + throw new VectorClientExecutionException( + "Failed to execute embedding model", + "onnx", + "COMPUTE", + modelPath, + e + ); } } diff --git a/Partner-Core/src/main/java/work/slhaf/partner/common/vector/VectorClient.java b/Partner-Core/src/main/java/work/slhaf/partner/common/vector/VectorClient.java index 10d99c3b..d997652d 100644 --- a/Partner-Core/src/main/java/work/slhaf/partner/common/vector/VectorClient.java +++ b/Partner-Core/src/main/java/work/slhaf/partner/common/vector/VectorClient.java @@ -4,6 +4,8 @@ import lombok.extern.slf4j.Slf4j; import org.nd4j.linalg.api.ndarray.INDArray; import org.nd4j.linalg.factory.Nd4j; import org.nd4j.linalg.ops.transforms.Transforms; +import work.slhaf.partner.common.vector.exception.VectorClientExecutionException; +import work.slhaf.partner.common.vector.exception.VectorClientStartupException; @Slf4j public abstract class VectorClient { @@ -12,14 +14,34 @@ public abstract class VectorClient { public static VectorClient INSTANCE; public static void startClient(VectorConfig config) { - if (config instanceof VectorConfig.Ollama ollama) { - INSTANCE = new OllamaVectorClient(ollama.ollamaEmbeddingUrl, ollama.ollamaEmbeddingModel); - } else if (config instanceof VectorConfig.Onnx onnx) { - INSTANCE = new OnnxVectorClient(onnx.tokenizerPath, onnx.embeddingModelPath); - } else { - return; + try { + if (config instanceof VectorConfig.Ollama ollama) { + INSTANCE = new OllamaVectorClient(ollama.ollamaEmbeddingUrl, ollama.ollamaEmbeddingModel); + } else if (config instanceof VectorConfig.Onnx onnx) { + INSTANCE = new OnnxVectorClient(onnx.tokenizerPath, onnx.embeddingModelPath); + } else { + return; + } + status = true; + } catch (VectorClientStartupException e) { + throw e; + } catch (VectorClientExecutionException e) { + throw new VectorClientStartupException( + "Vector client startup failed", + e.getClientType(), + "COMPUTE".equals(e.getPhase()) ? "STARTUP_SELF_TEST" : e.getPhase(), + e.getTarget(), + e + ); + } catch (Exception e) { + throw new VectorClientStartupException( + "Vector client startup failed", + resolveClientType(config), + "STARTUP", + resolveTarget(config), + e + ); } - status = true; } public float[] compute(String input) { @@ -31,6 +53,26 @@ public abstract class VectorClient { protected abstract float[] doCompute(String input); + private static String resolveClientType(VectorConfig config) { + if (config instanceof VectorConfig.Onnx) { + return "onnx"; + } + if (config instanceof VectorConfig.Ollama) { + return "ollama"; + } + return "unknown"; + } + + private static String resolveTarget(VectorConfig config) { + if (config instanceof VectorConfig.Onnx onnx) { + return onnx.embeddingModelPath; + } + if (config instanceof VectorConfig.Ollama ollama) { + return ollama.ollamaEmbeddingUrl; + } + return null; + } + public double compare(float[] v1, float[] v2) { if (!status) { return 0; @@ -60,4 +102,4 @@ public abstract class VectorClient { return updated.toFloatVector(); } } -} \ No newline at end of file +} diff --git a/Partner-Core/src/main/java/work/slhaf/partner/common/vector/exception/VectorClientExecuteException.java b/Partner-Core/src/main/java/work/slhaf/partner/common/vector/exception/VectorClientExecuteException.java deleted file mode 100644 index 4796b93c..00000000 --- a/Partner-Core/src/main/java/work/slhaf/partner/common/vector/exception/VectorClientExecuteException.java +++ /dev/null @@ -1,15 +0,0 @@ -package work.slhaf.partner.common.vector.exception; - -import work.slhaf.partner.framework.agent.exception.deprecated.AgentRuntimeException; - -public class VectorClientExecuteException extends AgentRuntimeException { - - public VectorClientExecuteException(String message) { - super(message); - } - - public VectorClientExecuteException(String message, Throwable cause) { - super(message, cause); - } - -} diff --git a/Partner-Core/src/main/java/work/slhaf/partner/common/vector/exception/VectorClientExecutionException.java b/Partner-Core/src/main/java/work/slhaf/partner/common/vector/exception/VectorClientExecutionException.java new file mode 100644 index 00000000..1ad3390a --- /dev/null +++ b/Partner-Core/src/main/java/work/slhaf/partner/common/vector/exception/VectorClientExecutionException.java @@ -0,0 +1,49 @@ +package work.slhaf.partner.common.vector.exception; + +import org.jetbrains.annotations.Nullable; +import work.slhaf.partner.framework.agent.exception.AgentRuntimeException; +import work.slhaf.partner.framework.agent.exception.ExceptionReport; + +public class VectorClientExecutionException extends AgentRuntimeException { + + private final String clientType; + private final String phase; + private final String target; + + public VectorClientExecutionException(String message, String clientType, String phase, @Nullable String target) { + super(message); + this.clientType = clientType; + this.phase = phase; + this.target = target; + } + + public VectorClientExecutionException(String message, String clientType, String phase, @Nullable String target, Throwable cause) { + super(message, cause); + this.clientType = clientType; + this.phase = phase; + this.target = target; + } + + public String getClientType() { + return clientType; + } + + public String getPhase() { + return phase; + } + + public String getTarget() { + return target; + } + + @Override + public ExceptionReport toReport() { + ExceptionReport report = super.toReport(); + report.getExtra().put("clientType", clientType); + report.getExtra().put("phase", phase); + if (target != null) { + report.getExtra().put("target", target); + } + return report; + } +} diff --git a/Partner-Core/src/main/java/work/slhaf/partner/common/vector/exception/VectorClientLoadFailedException.java b/Partner-Core/src/main/java/work/slhaf/partner/common/vector/exception/VectorClientLoadFailedException.java deleted file mode 100644 index c173c32b..00000000 --- a/Partner-Core/src/main/java/work/slhaf/partner/common/vector/exception/VectorClientLoadFailedException.java +++ /dev/null @@ -1,15 +0,0 @@ -package work.slhaf.partner.common.vector.exception; - -import work.slhaf.partner.framework.agent.exception.deprecated.AgentRuntimeException; - -public class VectorClientLoadFailedException extends AgentRuntimeException { - - public VectorClientLoadFailedException(String message) { - super(message); - } - - public VectorClientLoadFailedException(String message, Throwable cause) { - super(message, cause); - } - -} diff --git a/Partner-Core/src/main/java/work/slhaf/partner/common/vector/exception/VectorClientStartupException.java b/Partner-Core/src/main/java/work/slhaf/partner/common/vector/exception/VectorClientStartupException.java new file mode 100644 index 00000000..2ee0db9d --- /dev/null +++ b/Partner-Core/src/main/java/work/slhaf/partner/common/vector/exception/VectorClientStartupException.java @@ -0,0 +1,37 @@ +package work.slhaf.partner.common.vector.exception; + +import org.jetbrains.annotations.Nullable; +import work.slhaf.partner.framework.agent.exception.AgentStartupException; +import work.slhaf.partner.framework.agent.exception.ExceptionReport; + +public class VectorClientStartupException extends AgentStartupException { + + private final String clientType; + private final String phase; + private final String target; + + public VectorClientStartupException(String message, String clientType, String phase, @Nullable String target) { + super(message, "vector-client-registry"); + this.clientType = clientType; + this.phase = phase; + this.target = target; + } + + public VectorClientStartupException(String message, String clientType, String phase, @Nullable String target, Throwable cause) { + super(message, "vector-client-registry", cause); + this.clientType = clientType; + this.phase = phase; + this.target = target; + } + + @Override + public ExceptionReport toReport() { + ExceptionReport report = super.toReport(); + report.getExtra().put("clientType", clientType); + report.getExtra().put("phase", phase); + if (target != null) { + report.getExtra().put("target", target); + } + return report; + } +} diff --git a/Partner-Core/src/main/java/work/slhaf/partner/core/action/ActionCore.java b/Partner-Core/src/main/java/work/slhaf/partner/core/action/ActionCore.java index 580ef5e6..02bb91da 100644 --- a/Partner-Core/src/main/java/work/slhaf/partner/core/action/ActionCore.java +++ b/Partner-Core/src/main/java/work/slhaf/partner/core/action/ActionCore.java @@ -10,7 +10,7 @@ import work.slhaf.partner.core.action.entity.MetaAction; import work.slhaf.partner.core.action.entity.MetaActionInfo; import work.slhaf.partner.core.action.entity.intervention.InterventionType; import work.slhaf.partner.core.action.entity.intervention.MetaIntervention; -import work.slhaf.partner.core.action.exception.MetaActionNotFoundException; +import work.slhaf.partner.core.action.exception.ActionLookupException; import work.slhaf.partner.core.action.runner.LocalRunnerClient; import work.slhaf.partner.core.action.runner.RunnerClient; import work.slhaf.partner.framework.agent.config.ConfigCenter; @@ -117,12 +117,20 @@ public class ActionCore implements StateSerializable { public MetaAction loadMetaAction(@NonNull String actionKey) { MetaActionInfo metaActionInfo = existedMetaActions.get(actionKey); if (metaActionInfo == null) { - throw new MetaActionNotFoundException("未找到对应的行动程序信息" + actionKey); + throw new ActionLookupException( + "Meta action info not found for action key: " + actionKey, + actionKey, + "META_ACTION" + ); } String[] split = actionKey.split("::", 2); if (split.length < 2) { - throw new MetaActionNotFoundException("未找到对应的行动程序,原因: 传入的 actionKey(" + actionKey + ") 存在异常"); + throw new ActionLookupException( + "Invalid action key format: " + actionKey, + actionKey, + "META_ACTION" + ); } MetaAction.Type type = switch (split[0]) { case BUILTIN_LOCATION -> MetaAction.Type.BUILTIN; @@ -142,7 +150,11 @@ public class ActionCore implements StateSerializable { public MetaActionInfo loadMetaActionInfo(@NonNull String actionKey) { MetaActionInfo info = existedMetaActions.get(actionKey); if (info == null) { - throw new MetaActionNotFoundException("未找到对应的行动程序描述信息: " + actionKey); + throw new ActionLookupException( + "Meta action description not found for action key: " + actionKey, + actionKey, + "META_ACTION_INFO" + ); } return info; } diff --git a/Partner-Core/src/main/java/work/slhaf/partner/core/action/exception/ActionInfrastructureStartupException.java b/Partner-Core/src/main/java/work/slhaf/partner/core/action/exception/ActionInfrastructureStartupException.java new file mode 100644 index 00000000..c6a3a4d7 --- /dev/null +++ b/Partner-Core/src/main/java/work/slhaf/partner/core/action/exception/ActionInfrastructureStartupException.java @@ -0,0 +1,39 @@ +package work.slhaf.partner.core.action.exception; + +import org.jetbrains.annotations.Nullable; +import work.slhaf.partner.framework.agent.exception.AgentStartupException; +import work.slhaf.partner.framework.agent.exception.ExceptionReport; + +public class ActionInfrastructureStartupException extends AgentStartupException { + + private final String component; + private final String path; + private final String command; + + public ActionInfrastructureStartupException(String message, String component, @Nullable String path, @Nullable String command) { + super(message, "action-core"); + this.component = component; + this.path = path; + this.command = command; + } + + public ActionInfrastructureStartupException(String message, String component, @Nullable String path, @Nullable String command, Throwable cause) { + super(message, "action-core", cause); + this.component = component; + this.path = path; + this.command = command; + } + + @Override + public ExceptionReport toReport() { + ExceptionReport report = super.toReport(); + report.getExtra().put("component", component); + if (path != null) { + report.getExtra().put("path", path); + } + if (command != null) { + report.getExtra().put("command", command); + } + return report; + } +} diff --git a/Partner-Core/src/main/java/work/slhaf/partner/core/action/exception/ActionInitFailedException.java b/Partner-Core/src/main/java/work/slhaf/partner/core/action/exception/ActionInitFailedException.java deleted file mode 100644 index a69c292a..00000000 --- a/Partner-Core/src/main/java/work/slhaf/partner/core/action/exception/ActionInitFailedException.java +++ /dev/null @@ -1,13 +0,0 @@ -package work.slhaf.partner.core.action.exception; - -import work.slhaf.partner.framework.agent.exception.deprecated.AgentLaunchFailedException; - -public class ActionInitFailedException extends AgentLaunchFailedException { - public ActionInitFailedException(String message, Throwable cause) { - super(message, cause); - } - - public ActionInitFailedException(String message) { - super(message); - } -} diff --git a/Partner-Core/src/main/java/work/slhaf/partner/core/action/exception/ActionLookupException.java b/Partner-Core/src/main/java/work/slhaf/partner/core/action/exception/ActionLookupException.java new file mode 100644 index 00000000..095e9edd --- /dev/null +++ b/Partner-Core/src/main/java/work/slhaf/partner/core/action/exception/ActionLookupException.java @@ -0,0 +1,30 @@ +package work.slhaf.partner.core.action.exception; + +import work.slhaf.partner.framework.agent.exception.AgentRuntimeException; +import work.slhaf.partner.framework.agent.exception.ExceptionReport; + +public class ActionLookupException extends AgentRuntimeException { + + private final String actionKey; + private final String lookupTarget; + + public ActionLookupException(String message, String actionKey, String lookupTarget) { + super(message); + this.actionKey = actionKey; + this.lookupTarget = lookupTarget; + } + + public ActionLookupException(String message, String actionKey, String lookupTarget, Throwable cause) { + super(message, cause); + this.actionKey = actionKey; + this.lookupTarget = lookupTarget; + } + + @Override + public ExceptionReport toReport() { + ExceptionReport report = super.toReport(); + report.getExtra().put("actionKey", actionKey); + report.getExtra().put("lookupTarget", lookupTarget); + return report; + } +} diff --git a/Partner-Core/src/main/java/work/slhaf/partner/core/action/exception/ActionSerializationException.java b/Partner-Core/src/main/java/work/slhaf/partner/core/action/exception/ActionSerializationException.java new file mode 100644 index 00000000..a369e63e --- /dev/null +++ b/Partner-Core/src/main/java/work/slhaf/partner/core/action/exception/ActionSerializationException.java @@ -0,0 +1,58 @@ +package work.slhaf.partner.core.action.exception; + +import org.jetbrains.annotations.Nullable; +import work.slhaf.partner.framework.agent.exception.AgentRuntimeException; +import work.slhaf.partner.framework.agent.exception.ExceptionReport; + +public class ActionSerializationException extends AgentRuntimeException { + + private final String actionName; + private final String baseDir; + private final String fileExt; + private final String stage; + + public ActionSerializationException( + String message, + @Nullable String actionName, + @Nullable String baseDir, + @Nullable String fileExt, + String stage + ) { + super(message); + this.actionName = actionName; + this.baseDir = baseDir; + this.fileExt = fileExt; + this.stage = stage; + } + + public ActionSerializationException( + String message, + @Nullable String actionName, + @Nullable String baseDir, + @Nullable String fileExt, + String stage, + Throwable cause + ) { + super(message, cause); + this.actionName = actionName; + this.baseDir = baseDir; + this.fileExt = fileExt; + this.stage = stage; + } + + @Override + public ExceptionReport toReport() { + ExceptionReport report = super.toReport(); + report.getExtra().put("stage", stage); + if (actionName != null) { + report.getExtra().put("actionName", actionName); + } + if (baseDir != null) { + report.getExtra().put("baseDir", baseDir); + } + if (fileExt != null) { + report.getExtra().put("fileExt", fileExt); + } + return report; + } +} diff --git a/Partner-Core/src/main/java/work/slhaf/partner/core/action/exception/ActionSerializeFailedException.java b/Partner-Core/src/main/java/work/slhaf/partner/core/action/exception/ActionSerializeFailedException.java deleted file mode 100644 index cc65387e..00000000 --- a/Partner-Core/src/main/java/work/slhaf/partner/core/action/exception/ActionSerializeFailedException.java +++ /dev/null @@ -1,13 +0,0 @@ -package work.slhaf.partner.core.action.exception; - -import work.slhaf.partner.framework.agent.exception.deprecated.AgentRuntimeException; - -public class ActionSerializeFailedException extends AgentRuntimeException { - public ActionSerializeFailedException(String message) { - super(message); - } - - public ActionSerializeFailedException(String message, Throwable cause) { - super(message, cause); - } -} diff --git a/Partner-Core/src/main/java/work/slhaf/partner/core/action/exception/MetaActionNotFoundException.java b/Partner-Core/src/main/java/work/slhaf/partner/core/action/exception/MetaActionNotFoundException.java deleted file mode 100644 index 2bacc00c..00000000 --- a/Partner-Core/src/main/java/work/slhaf/partner/core/action/exception/MetaActionNotFoundException.java +++ /dev/null @@ -1,13 +0,0 @@ -package work.slhaf.partner.core.action.exception; - -import work.slhaf.partner.framework.agent.exception.deprecated.AgentRuntimeException; - -public class MetaActionNotFoundException extends AgentRuntimeException { - public MetaActionNotFoundException(String message) { - super(message); - } - - public MetaActionNotFoundException(String message, Throwable cause) { - super(message, cause); - } -} diff --git a/Partner-Core/src/main/java/work/slhaf/partner/core/action/runner/LocalRunnerClient.java b/Partner-Core/src/main/java/work/slhaf/partner/core/action/runner/LocalRunnerClient.java index 8b726287..b194c686 100644 --- a/Partner-Core/src/main/java/work/slhaf/partner/core/action/runner/LocalRunnerClient.java +++ b/Partner-Core/src/main/java/work/slhaf/partner/core/action/runner/LocalRunnerClient.java @@ -8,7 +8,7 @@ import org.jetbrains.annotations.Nullable; import work.slhaf.partner.core.action.entity.ActionFileMetaData; import work.slhaf.partner.core.action.entity.MetaAction; import work.slhaf.partner.core.action.entity.MetaActionInfo; -import work.slhaf.partner.core.action.exception.ActionInitFailedException; +import work.slhaf.partner.core.action.exception.ActionInfrastructureStartupException; import work.slhaf.partner.core.action.runner.execution.McpActionExecutor; import work.slhaf.partner.core.action.runner.execution.OriginExecutionService; import work.slhaf.partner.core.action.runner.mcp.*; @@ -97,13 +97,26 @@ public class LocalRunnerClient extends RunnerClient implements AutoCloseable { ); configWatcher.start(); configWatcher.registerPolicyListener(); + } catch (ActionInfrastructureStartupException e) { + closeQuietly(configWatcher); + closeQuietly(dynamicManager); + closeQuietly(descWatcher); + closeQuietly(metaRegistry); + closeQuietly(clientRegistry); + throw e; } catch (Exception e) { closeQuietly(configWatcher); closeQuietly(dynamicManager); closeQuietly(descWatcher); closeQuietly(metaRegistry); closeQuietly(clientRegistry); - throw new ActionInitFailedException("LocalRunnerClient 初始化失败", e); + throw new ActionInfrastructureStartupException( + "LocalRunnerClient initialization failed", + "local-runner-client", + ACTION_PATH, + null, + e + ); } this.mcpClientRegistry = clientRegistry; diff --git a/Partner-Core/src/main/java/work/slhaf/partner/core/action/runner/RunnerClient.java b/Partner-Core/src/main/java/work/slhaf/partner/core/action/runner/RunnerClient.java index c2dfc761..931d2d37 100644 --- a/Partner-Core/src/main/java/work/slhaf/partner/core/action/runner/RunnerClient.java +++ b/Partner-Core/src/main/java/work/slhaf/partner/core/action/runner/RunnerClient.java @@ -9,7 +9,7 @@ import work.slhaf.partner.core.action.entity.ActionFileMetaData; import work.slhaf.partner.core.action.entity.MetaAction; import work.slhaf.partner.core.action.entity.MetaAction.Result; import work.slhaf.partner.core.action.entity.MetaActionInfo; -import work.slhaf.partner.core.action.exception.ActionInitFailedException; +import work.slhaf.partner.core.action.exception.ActionInfrastructureStartupException; import work.slhaf.partner.module.action.builtin.BuiltinActionRegistry; import java.io.IOException; @@ -101,7 +101,13 @@ public abstract class RunnerClient implements AutoCloseable { Files.createDirectory(path); } catch (IOException e) { if (!Files.exists(path)) { - throw new ActionInitFailedException("目录创建失败: " + pathStr, e); + throw new ActionInfrastructureStartupException( + "Failed to create action directory: " + pathStr, + "runner-client", + pathStr, + null, + e + ); } } } diff --git a/Partner-Core/src/main/java/work/slhaf/partner/core/action/runner/mcp/DynamicActionMcpManager.java b/Partner-Core/src/main/java/work/slhaf/partner/core/action/runner/mcp/DynamicActionMcpManager.java index 4fa6084c..3c9e4676 100644 --- a/Partner-Core/src/main/java/work/slhaf/partner/core/action/runner/mcp/DynamicActionMcpManager.java +++ b/Partner-Core/src/main/java/work/slhaf/partner/core/action/runner/mcp/DynamicActionMcpManager.java @@ -13,7 +13,7 @@ import reactor.core.publisher.Mono; import reactor.core.scheduler.Schedulers; import work.slhaf.partner.common.mcp.InProcessMcpTransport; import work.slhaf.partner.core.action.entity.MetaActionInfo; -import work.slhaf.partner.core.action.exception.ActionInitFailedException; +import work.slhaf.partner.core.action.exception.ActionInfrastructureStartupException; import work.slhaf.partner.core.action.runner.execution.CommandExecutionService; import work.slhaf.partner.framework.agent.support.DirectoryWatchSupport; @@ -77,11 +77,21 @@ public class DynamicActionMcpManager implements AutoCloseable { private void loadExisting() { File file = root.toFile(); if (file.isFile()) { - throw new ActionInitFailedException("未找到目录: " + root); + throw new ActionInfrastructureStartupException( + "Expected a directory but found a file: " + root, + "dynamic-action-mcp-manager", + root.toString(), + null + ); } File[] files = file.listFiles(); if (files == null) { - throw new ActionInitFailedException("未正常读取目录: " + root); + throw new ActionInfrastructureStartupException( + "Failed to read action directory: " + root, + "dynamic-action-mcp-manager", + root.toString(), + null + ); } for (File dir : files) { if (!normalPath(dir.toPath())) { diff --git a/Partner-Core/src/main/java/work/slhaf/partner/core/action/runner/policy/BwrapPolicyProvider.kt b/Partner-Core/src/main/java/work/slhaf/partner/core/action/runner/policy/BwrapPolicyProvider.kt index 4ec2f727..ff400f1b 100644 --- a/Partner-Core/src/main/java/work/slhaf/partner/core/action/runner/policy/BwrapPolicyProvider.kt +++ b/Partner-Core/src/main/java/work/slhaf/partner/core/action/runner/policy/BwrapPolicyProvider.kt @@ -1,6 +1,6 @@ package work.slhaf.partner.core.action.runner.policy -import work.slhaf.partner.core.action.exception.ActionInitFailedException +import work.slhaf.partner.core.action.exception.ActionInfrastructureStartupException private const val BWRAP_COMMAND = "bwrap" @@ -62,10 +62,21 @@ object BwrapPolicyProvider : PolicyProvider( val exitCode = process.waitFor() exitCode == 0 } catch (e: Exception) { - throw ActionInitFailedException("bwrap provider 初始化失败: 无法检测 $BWRAP_COMMAND 可执行文件", e) + throw ActionInfrastructureStartupException( + "Failed to detect executable command '$BWRAP_COMMAND'", + "bwrap-policy-provider", + null, + BWRAP_COMMAND, + e + ) } if (!available) { - throw ActionInitFailedException("bwrap provider 初始化失败: 未检测到可执行命令 '$BWRAP_COMMAND'") + throw ActionInfrastructureStartupException( + "Executable command '$BWRAP_COMMAND' is not available", + "bwrap-policy-provider", + null, + BWRAP_COMMAND + ) } } } diff --git a/Partner-Core/src/main/java/work/slhaf/partner/core/action/runner/support/ActionSerializer.java b/Partner-Core/src/main/java/work/slhaf/partner/core/action/runner/support/ActionSerializer.java index 634e2bd2..93afe5be 100644 --- a/Partner-Core/src/main/java/work/slhaf/partner/core/action/runner/support/ActionSerializer.java +++ b/Partner-Core/src/main/java/work/slhaf/partner/core/action/runner/support/ActionSerializer.java @@ -7,7 +7,7 @@ import org.jetbrains.annotations.NotNull; import work.slhaf.partner.core.action.entity.ActionFileMetaData; import work.slhaf.partner.core.action.entity.MetaAction; import work.slhaf.partner.core.action.entity.MetaActionInfo; -import work.slhaf.partner.core.action.exception.ActionSerializeFailedException; +import work.slhaf.partner.core.action.exception.ActionSerializationException; import java.io.File; import java.io.IOException; @@ -34,7 +34,7 @@ public class ActionSerializer { return codeType.startsWith(".") ? codeType : "." + codeType; } - private static @NotNull Path createActionDir(String baseName, Path baseDir) { + private static @NotNull Path createActionDir(String baseName, Path baseDir, String fileExt) { for (int i = 0; ; i++) { String dirName = i == 0 ? baseName : baseName + "(" + i + ")"; Path candidate = baseDir.resolve(dirName); @@ -43,7 +43,14 @@ public class ActionSerializer { return candidate; } catch (FileAlreadyExistsException ignored) { } catch (IOException e) { - throw new ActionSerializeFailedException("无法创建行动目录: " + candidate.toAbsolutePath(), e); + throw new ActionSerializationException( + "Failed to create action directory: " + candidate.toAbsolutePath(), + baseName, + baseDir.toAbsolutePath().toString(), + fileExt, + "CREATE_DIRECTORY", + e + ); } } } @@ -75,10 +82,16 @@ public class ActionSerializer { val baseDir = Path.of(dynamicActionPath); if (!Files.isDirectory(baseDir)) { - throw new ActionSerializeFailedException("目录不存在或不可用: " + baseDir.toAbsolutePath()); + throw new ActionSerializationException( + "Action base directory is not available: " + baseDir.toAbsolutePath(), + fileMetaData.getName(), + baseDir.toAbsolutePath().toString(), + fileMetaData.getExt(), + "VALIDATE_BASE_DIR" + ); } - val actionDir = createActionDir(fileMetaData.getName(), baseDir); + val actionDir = createActionDir(fileMetaData.getName(), baseDir, fileMetaData.getExt()); val runTmp = actionDir.resolve("run." + fileMetaData.getExt() + ".tmp"); val descTmp = actionDir.resolve("desc.json.tmp"); val runFinal = actionDir.resolve("run." + fileMetaData.getExt()); @@ -95,7 +108,14 @@ public class ActionSerializer { safeDelete(runFinal); safeDelete(descFinal); safeDelete(actionDir); - throw new ActionSerializeFailedException("行动文件写入失败", e); + throw new ActionSerializationException( + "Failed to persist action files", + fileMetaData.getName(), + baseDir.toAbsolutePath().toString(), + fileMetaData.getExt(), + "WRITE_FILES", + e + ); } log.debug("持久序列化结束"); } diff --git a/Partner-Core/src/main/java/work/slhaf/partner/module/action/builtin/BuiltinActionRegistry.java b/Partner-Core/src/main/java/work/slhaf/partner/module/action/builtin/BuiltinActionRegistry.java index c432cf1e..6ad60cb9 100644 --- a/Partner-Core/src/main/java/work/slhaf/partner/module/action/builtin/BuiltinActionRegistry.java +++ b/Partner-Core/src/main/java/work/slhaf/partner/module/action/builtin/BuiltinActionRegistry.java @@ -4,7 +4,7 @@ import lombok.Getter; import lombok.NonNull; import work.slhaf.partner.core.action.ActionCapability; import work.slhaf.partner.core.action.entity.MetaActionInfo; -import work.slhaf.partner.core.action.exception.MetaActionNotFoundException; +import work.slhaf.partner.core.action.exception.ActionLookupException; import work.slhaf.partner.framework.agent.factory.capability.annotation.InjectCapability; import work.slhaf.partner.framework.agent.factory.component.abstracts.AbstractAgentModule; import work.slhaf.partner.framework.agent.factory.component.annotation.Init; @@ -57,7 +57,11 @@ public class BuiltinActionRegistry extends AbstractAgentModule.Standalone { public String call(@NonNull String actionKey, @NonNull Map params) { BuiltinActionDefinition definition = definitions.get(actionKey); if (definition == null) { - throw new MetaActionNotFoundException("未找到对应的内置行动程序: " + actionKey); + throw new ActionLookupException( + "Builtin action definition not found: " + actionKey, + actionKey, + "BUILTIN_DEFINITION" + ); } String result = definition.invoker().apply(params); if (result == null) { diff --git a/Partner-Core/src/test/java/work/slhaf/partner/core/action/runner/RunnerClientTest.java b/Partner-Core/src/test/java/work/slhaf/partner/core/action/runner/RunnerClientTest.java index df1c2a70..41a1ccce 100644 --- a/Partner-Core/src/test/java/work/slhaf/partner/core/action/runner/RunnerClientTest.java +++ b/Partner-Core/src/test/java/work/slhaf/partner/core/action/runner/RunnerClientTest.java @@ -34,5 +34,10 @@ public class RunnerClientTest { public void persistSerialize(MetaActionInfo metaActionInfo, ActionFileMetaData fileMetaData) { } + + @Override + public void close() { + + } } } diff --git a/Partner-Core/src/test/java/work/slhaf/partner/core/action/runner/policy/BwrapPolicyProviderTest.kt b/Partner-Core/src/test/java/work/slhaf/partner/core/action/runner/policy/BwrapPolicyProviderTest.kt index efcfa18d..0aef7db5 100644 --- a/Partner-Core/src/test/java/work/slhaf/partner/core/action/runner/policy/BwrapPolicyProviderTest.kt +++ b/Partner-Core/src/test/java/work/slhaf/partner/core/action/runner/policy/BwrapPolicyProviderTest.kt @@ -1,8 +1,8 @@ package work.slhaf.partner.core.action.runner.policy -import org.junit.jupiter.api.Assertions.* +import org.junit.jupiter.api.Assertions.assertEquals +import org.junit.jupiter.api.Assertions.assertFalse import org.junit.jupiter.api.Test -import work.slhaf.partner.core.action.exception.ActionInitFailedException class BwrapPolicyProviderTest { @@ -59,28 +59,4 @@ class BwrapPolicyProviderTest { assertFalse(wrapped.args.contains("--unshare-net")) } - @Test - fun `require command available throws ActionInitFailedException when command missing`() { - val exception = assertThrows(ActionInitFailedException::class.java) { - bwrapPolicyFileFacadeClass().requireCommandAvailable("definitely-not-found-bwrap-command") - } - - assertTrue(exception.message!!.contains("definitely-not-found-bwrap-command")) - } -} - -private fun bwrapPolicyFileFacadeClass(): Class<*> { - return Class.forName("work.slhaf.partner.core.action.runner.policy.BwrapPolicyProviderKt") -} - -private fun Class<*>.requireCommandAvailable(command: String) { - val method = getDeclaredMethod("requireCommandAvailable", String::class.java) - method.isAccessible = true - try { - method.invoke(null, command) - } catch (e: java.lang.reflect.InvocationTargetException) { - throw (e.targetException as? RuntimeException) - ?: (e.targetException as? Error) - ?: RuntimeException(e.targetException) - } } diff --git a/Partner-Core/src/test/java/work/slhaf/partner/module/action/builtin/BuiltinActionRegistryTest.java b/Partner-Core/src/test/java/work/slhaf/partner/module/action/builtin/BuiltinActionRegistryTest.java index ed979081..56c2487d 100644 --- a/Partner-Core/src/test/java/work/slhaf/partner/module/action/builtin/BuiltinActionRegistryTest.java +++ b/Partner-Core/src/test/java/work/slhaf/partner/module/action/builtin/BuiltinActionRegistryTest.java @@ -5,7 +5,7 @@ import org.junit.jupiter.api.Assertions; import org.junit.jupiter.api.Test; import work.slhaf.partner.core.action.ActionCapability; import work.slhaf.partner.core.action.entity.MetaActionInfo; -import work.slhaf.partner.core.action.exception.MetaActionNotFoundException; +import work.slhaf.partner.core.action.exception.ActionLookupException; import work.slhaf.partner.core.action.runner.RunnerClient; import java.lang.reflect.Field; @@ -80,14 +80,14 @@ class BuiltinActionRegistryTest { registry.defineBuiltinAction("nil", buildMetaActionInfo("nil"), params -> null); Assertions.assertEquals("hello", registry.call("builtin::echo", Map.of("value", "hello"))); - Assertions.assertEquals("{\"ok\":true}", registry.call("builtin::json", Map.of())); + Assertions.assertEquals("{ok=true}", registry.call("builtin::json", Map.of())); Assertions.assertEquals("null", registry.call("builtin::nil", Map.of())); } @Test void testCallThrowsWhenMissingDefinition() { BuiltinActionRegistry registry = new BuiltinActionRegistry(); - Assertions.assertThrows(MetaActionNotFoundException.class, () -> registry.call("builtin::missing", Map.of())); + Assertions.assertThrows(ActionLookupException.class, () -> registry.call("builtin::missing", Map.of())); } @Test diff --git a/Partner-Core/src/test/java/work/slhaf/partner/module/action/builtin/BuiltinDynamicActionProviderTest.java b/Partner-Core/src/test/java/work/slhaf/partner/module/action/builtin/BuiltinDynamicActionProviderTest.java index c35502de..2f71fec6 100644 --- a/Partner-Core/src/test/java/work/slhaf/partner/module/action/builtin/BuiltinDynamicActionProviderTest.java +++ b/Partner-Core/src/test/java/work/slhaf/partner/module/action/builtin/BuiltinDynamicActionProviderTest.java @@ -201,5 +201,10 @@ class BuiltinDynamicActionProviderTest { public void persistSerialize(MetaActionInfo metaActionInfo, ActionFileMetaData fileMetaData) { persistCalled = true; } + + @Override + public void close() { + + } } } diff --git a/Partner-Framework/src/main/java/work/slhaf/partner/framework/agent/exception/deprecated/AgentLaunchFailedException.java b/Partner-Framework/src/main/java/work/slhaf/partner/framework/agent/exception/deprecated/AgentLaunchFailedException.java deleted file mode 100644 index ca4a6924..00000000 --- a/Partner-Framework/src/main/java/work/slhaf/partner/framework/agent/exception/deprecated/AgentLaunchFailedException.java +++ /dev/null @@ -1,12 +0,0 @@ -package work.slhaf.partner.framework.agent.exception.deprecated; - -@Deprecated -public class AgentLaunchFailedException extends RuntimeException { - public AgentLaunchFailedException(String message, Throwable cause) { - super("Agent 启动失败 " + message, cause); - } - - public AgentLaunchFailedException(String message) { - super("Agent 启动失败 " + message); - } -} diff --git a/Partner-Framework/src/main/java/work/slhaf/partner/framework/agent/exception/deprecated/AgentRunningFailedException.java b/Partner-Framework/src/main/java/work/slhaf/partner/framework/agent/exception/deprecated/AgentRunningFailedException.java deleted file mode 100644 index ec9b126a..00000000 --- a/Partner-Framework/src/main/java/work/slhaf/partner/framework/agent/exception/deprecated/AgentRunningFailedException.java +++ /dev/null @@ -1,12 +0,0 @@ -package work.slhaf.partner.framework.agent.exception.deprecated; - -@Deprecated -public class AgentRunningFailedException extends AgentRuntimeException { - public AgentRunningFailedException(String message) { - super(message); - } - - public AgentRunningFailedException(String message, Throwable cause) { - super(message, cause); - } -} diff --git a/Partner-Framework/src/main/java/work/slhaf/partner/framework/agent/exception/deprecated/AgentRuntimeException.java b/Partner-Framework/src/main/java/work/slhaf/partner/framework/agent/exception/deprecated/AgentRuntimeException.java deleted file mode 100644 index 43fdd398..00000000 --- a/Partner-Framework/src/main/java/work/slhaf/partner/framework/agent/exception/deprecated/AgentRuntimeException.java +++ /dev/null @@ -1,12 +0,0 @@ -package work.slhaf.partner.framework.agent.exception.deprecated; - -@Deprecated -public class AgentRuntimeException extends RuntimeException { - public AgentRuntimeException(String message) { - super("Agent 执行出错 " + message); - } - - public AgentRuntimeException(String message, Throwable cause) { - super("Agent 执行出错 " + message, cause); - } -} diff --git a/Partner-Framework/src/main/java/work/slhaf/partner/framework/agent/support/Result.kt b/Partner-Framework/src/main/java/work/slhaf/partner/framework/agent/support/Result.kt index a41882ea..d7ca5fac 100644 --- a/Partner-Framework/src/main/java/work/slhaf/partner/framework/agent/support/Result.kt +++ b/Partner-Framework/src/main/java/work/slhaf/partner/framework/agent/support/Result.kt @@ -21,9 +21,8 @@ class Result private constructor( return value as T } when (exception) { - is RuntimeException -> throw exception - is Error -> throw exception - else -> throw IllegalStateException(exception.message, exception) + is AgentRuntimeException, is Error -> throw exception + else -> throw AgentRuntimeException(exception.localizedMessage, exception) } }