CORBA拦截器操作远程对象参数报错求助:NO_RESOURCES异常处理
解决CORBA拦截器访问参数时的NO_RESOURCES错误
这个错误的核心原因是你使用的Sun/Oracle CORBA ORB默认没有启用Portable Interceptor(PI)的参数访问支持,而且send_request拦截点调用arguments()需要ORB提前开启相关配置。我来帮你一步步解决这个问题:
1. 错误原因解析
org.omg.CORBA.NO_RESOURCES: piOperationNotSupported1 明确表示ORB不支持在当前拦截阶段执行参数访问操作。CORBA PI规范中,arguments()方法并非在所有拦截点都默认可用,对于Sun的ORB实现,必须显式启用PI的参数捕获能力才能在send_request阶段访问参数。
2. 关键配置步骤
首先在初始化ORB时,必须添加PI启用的配置参数:
import java.util.Properties; import org.omg.CORBA.ORB; public class ClientMain { public static void main(String[] args) { Properties props = new Properties(); // 指定Sun的ORB实现类 props.put("org.omg.CORBA.ORBClass", "com.sun.corba.se.impl.orb.ORBImpl"); // 启用PI支持 props.put("com.sun.corba.se.ORB.PIEnable", "true"); // 指定自定义ORB初始化器(用于注册拦截器) props.put("org.omg.CORBA.ORBInitializers", "your.package.MyORBInitializer"); ORB orb = ORB.init(args, props); // 后续客户端初始化逻辑... } }
3. 实现ORB初始化器(注册拦截器)
拦截器必须通过ORBInitializer接口注册到ORB中,而不是直接创建:
import org.omg.PortableInterceptor.ORBInitializer; import org.omg.PortableInterceptor.ORBInitInfo; public class MyORBInitializer implements ORBInitializer { @Override public void pre_init(ORBInitInfo info) { try { // 注册自定义客户端拦截器 info.add_client_request_interceptor(new CustomClientInterceptor()); } catch (Exception e) { e.printStackTrace(); } } @Override public void post_init(ORBInitInfo info) {} }
4. 修正后的拦截器代码(支持参数加密)
修改拦截器,确保能安全访问并加密参数:
import org.omg.CORBA.*; import org.omg.PortableInterceptor.*; public class CustomClientInterceptor extends ClientRequestInterceptor { private final String interceptorName = "CustomEncryptionInterceptor"; @Override public String name() { return interceptorName; } @Override public void destroy() {} @Override public void send_request(ClientRequestInfo ri) throws ForwardRequest { try { // 获取方法参数列表 NVList argsList = ri.arguments(); if (argsList != null && argsList.count() > 0) { for (int i = 0; i < argsList.count(); i++) { NamedValue param = argsList.item(i); // 根据实际参数类型处理,这里以StringHolder为例 if (param.value() instanceof StringHolder) { StringHolder holder = (StringHolder) param.value(); // 替换为你的实际加密逻辑(比如AES/RSA) holder.value = encryptString(holder.value); System.out.println("加密参数[" + i + "]: " + holder.value); } // 如果是其他类型(如IntegerHolder),同理处理 } } logger(ri, "send_request - 参数加密完成"); } catch (Exception e) { e.printStackTrace(); throw new ForwardRequest(null); } } // 其他拦截方法实现(空实现即可) @Override public void send_poll(ClientRequestInfo ri) {} @Override public void receive_reply(ClientRequestInfo ri) {} @Override public void receive_exception(ClientRequestInfo ri) throws ForwardRequest {} @Override public void receive_other(ClientRequestInfo ri) throws ForwardRequest {} // 示例加密方法,替换为你的实际加密算法 private String encryptString(String plainText) { // 这里仅做演示,实际使用标准加密库 return new StringBuilder(plainText).reverse().toString(); } private void logger(ClientRequestInfo ri, String stage) { System.out.println("[" + interceptorName + "] " + stage + " - 操作名: " + ri.operation()); } }
5. 注意事项
- 确保所有类都在ORB能扫描到的包路径下,尤其是
ORBInitializers参数指定的类 - 不同CORBA实现的PI配置参数可能不同,如果你切换到其他ORB(如JacORB),需要调整对应的启用参数
- 单向调用(oneway)的方法可能无法访问参数,这类场景需要提前判断
内容的提问来源于stack exchange,提问作者Juliyanage Silva
相关产品推荐
相关产品推荐

