`
holdbelief
  • 浏览: 696763 次
  • 性别: Icon_minigender_1
  • 来自: 北京
社区版块
存档分类
最新评论

java.naming.factory.url.pkgs 的用途

阅读更多

HTML clipboard

    因笔者最近实现一个JavaEE jndi的实现,对jndi的相关属性的学习和自己的理解给大家一个分享。

在创建Jndi上下文时,使用Context.INITIAL_CONTEXT_FACTORY("java.naming.factory.initial")属性,用来指定创建jndi上下文的工厂类,例如以下代码是我们很熟悉的代码使用jboss jndi的示例代码:

 

 

final Hashtable environment = new Hashtable();
environment.put(Context. INITIAL_CONTEXT_FACTORY "org.jnp.interfaces.NamingContextFactory" );
environment.put(Context. URL_PKG_PREFIXES "org.jboss.naming:org.jnp.interfaces" );

final
 
InitialContext ctx = new 
InitialContext(environment); 
ctx.lookup("
 java:/jdbc/test1");


但上述代码中,很多人对于Context.URL_PKG_PREFIXES("java.naming.factory.url.pkgs")的用途不是很了解,其实,这个属性主要用在查询url中包括scheme方法id时的创建对应的jndi上下文上,例如查询"java:/jdbc/test1"等类似查询上,即以冒号(":")标识的shceme。

Context.URL_PKG_PREFIXES属性值由多个java 包(package)路径,其中以冒号(":")分隔各个包路径,这些包路径中包括jndi相关实现类。当在jndi上下文中查找"java:"这类包括scheme方案ID的url时,InitialContext类将优先查找Context.URL_PKG_PREFIXES属性指定的包路径中是否存在 scheme+"."+scheme + "URLContextFactory"工厂类(需要实现ObjectFactory接口),如果存在此工厂类,则调用此工厂类的getObjectInstance方法获得此scheme方案ID对应的jndi上下文,再在此上下文中继续查找对应的url,仍以上述示例代码为例,当执行ctx.lookup("java:/jdbc/test1")时,InitialContext类将调用"org.jnp.interfaces.java.javaURLContextFactory"类创建jndi上下文,再在此上下文中查找"jdbc/test1"。

上述执行逻辑主要在NamingManager.getURLContext方法中实现,其javadoc api文档内容如下:

getURLContext

public static Context

  getURLContext

 (String

  scheme,  Hashtable

<?,?> environment)  throws NamingException

为给定的 URL 方案 id 创建一个上下文。

得到的上下文用于解析 scheme 方案的 URL。得到的上下文没有绑定到特定 URL。它能够使用指定方案处理任意 URL。

创建所得上下文的工厂的类名称包含命名约定方案 id URLContextFactory(例如,用于 "ftp" 方案 id 的 "ftpURLContextFactory"),所在的包指定如下。Context.URL_PKG_PREFIXES 环境属性(可能包含从 applet 参数、系统属性或应用程序资源文件中获得的值)包含以冒号分隔的包前缀列表。按指定的顺序尝试该属性中的每个包前缀来加载工厂类。默认包前缀是 "com.sun.jndi.url"(如果指定的包前缀都无效,则尝试使用此默认前缀)。完整的包名称是使用包前缀构造的,并与方案 id 连接在一起。

例如,如果方案 id 为 "ldap",而 Context.URL_PKG_PREFIXES 属性包含 "com.widget:com.wiz.jndi",则命名管理器将尝试加载以下类,直到成功实例化其中的一个:

  • com.widget.ldap.ldapURLContextFactory
  • com.wiz.jndi.ldap.ldapURLContextFactory
  • com.sun.jndi.url.ldap.ldapURLContextFactory
如果没有包前缀有效,则返回 null。

如果某一工厂被实例化,则使用以下参数调用该工厂来产生结果上下文。

factory.getObjectInstance(null, environment);

例如,按上述方式对 LDAP URL 上下文工厂调用 getObjectInstance() 将返回一个可以解析 LDAP url(例如 "ldap://ldap.wiz.com/o=wiz,c=us"、"ldap://ldap.umich.edu/o=umich,c=us" 等等)的上下文。

注意,对象工厂(实现 ObjectFactory 接口的对象)必须是公共的,并且必须有一个不接受任何参数的公共构造方法。


参数:
scheme - 上下文支持的 URL 的非 null 方案 id。
environment - 将在创建对象和对象工厂时使用的环境属性(可能为 null)。
返回:
使用方案 id scheme 解析 URL 的上下文;如果没有找到用于创建该上下文的工厂,则返回 null 。
抛出:
NamingException - 如果在创建上下文时发生命名异常。
 

其实现代码如下:

 

private static Object getURLObject(String scheme, Object urlInfo, Name name, Context nameCtx, Hashtableenvironment) throws NamingException {


    ObjectFactory factory = (ObjectFactory) ResourceManager.getFactory (Context. URL_PKG_PREFIXES , environment, nameCtx, "." + scheme + "." + scheme + "URLContextFactory" ,defaultPkgPrefix );


    if (factory == null )

        return null ;


    .......

}

分享到:
评论

相关推荐

Global site tag (gtag.js) - Google Analytics