很多地方都会用到JNDI,一大堆的缩写加上一大堆不清不楚的概念描述,使得在看到的时候都不认识,更不要说使用了。
JNDI,Java Naming Directory Interface,J2EE的标准之一,所有的J2EE容器都必须提供一个JNDI的服务,但是,我一直都没用过,至少是没有刻意地去用过。因为,我也 曾经把数据源配置在Tomcat的JNDI服务中,但那时,我也只是刚刚涉足JAVA,有人告诉我应该这么干而已。后来,我开始使用自定义的数据库连接配 置文件,就再也没有跟JNDI打过交道了,直到今天。

现在之所以又想看一下,只是因为觉得这是J2EE的重要标准之一,如果不懂得的话,似乎有点说不过去。

JNDI 的主要功能可以这样描述,它使用一张哈希表存储对象(大多数的J2EE容器也的确是这样做的),然后,开发人员可以使用键值——也就是一个字符串——来获 取这个对象。这里就包括取JNDI的两个最主要操作,bind和lookup。bind操作负责往哈希表里存对象,存对象的时候要定义好对象的键值字符 串,lookup则根据这个键值字符串往外取对象。

JNDI的命称可能会让人产生混淆,似乎觉得这是一个用来操作目录的,事实上,我更愿 意把这个目录理解成为JNDI存放对象时使用的格式,也就是说,JNDI以目录的方式存储对象的属性。例如,用户通过JNDI存储一个汽车对象,那么,汽 车就是根目录,汽车的轮子、引擎之类的子对象就算是子目录,而属性,比如说汽车的牌子、重量之类,就算是汽车目录下的文件。

JNDI的功能既然就是根据一个字符串键值就可以取得一个想要得到的对象,我一开始就觉得这不是跟COM或CORBA一样吗?SUN也是有野心的企业啊,JNDI应该就是它要努力推行的JAVA下的分布式开发的标准吧。

JNDI 的出现应该就是为了分步式开发服务的,有人负责开发这种分布式对象,有人只需要使用这些分布式对象就可以了,这两组人不必属于同一个公司,而且这种开发通 常应该是不并行的,也不必是会了同一个项目服务。就如果数据源对象,它放在JNDI中,只要想要用的人,直接通过JNDI服务取来用就可以了,至于当初是 谁把它放进JNDI中的,还是不用操这份心了吧。而我一直没有使用JNDI,也就是这个原因,项目中的所有对象都在我控制之下,我不去使用别人的对象,也 没打算把我的对象贡献出来给别人使用,那自然也就没必要去跟JNDI打交道。我觉得是否使用JNDI,这应该是关键原因,至于什么方便性、安全性之类的考 虑,应该不是JNDI的主要目的,就如同你可以用JAVA来做网站,但JAVA并不是专门用来做网站的。

可能有人觉得这种功能跟IoC也 很象,这个我倒不觉得,虽然对于对象的使用人员来说的确是这种感觉,且不说IoC需要为对象定义接口,而JNDI并无此限制,先说这里有一个使用环境问 题,我觉得IoC是用来解决并行开发问题的,也就是说IoC主要是用于明确设计人员与实现/使用人员的分工,无论是设计的,还是使用的,通常是一个项目组 里的人,使用IoC,可以使得设计人员专注于设计,加快设计速度。因此,IoC的用途要比JNDI广泛的多,现在大型系统中,不使用IoC的,几稀矣。

JNDI 笔记(二) J2EE下使用JNDI

在J2EE环境下使用JNDI是非常简单的事,因为所有的J2EE容器都要实现JNDI服务,所以,在J2EE环境下使用JNDI,与使用 Hashtable也没有什么太大区别。只有一点限制,那就是绑定对象时,对象所属的类必须实现java.io.Serializable接口,这一点也 实在一点也不困难,几乎所有用到的Java类都实现了这个接口,对于自定义的类,在接口实现列表里把这个接口加进去也就是了。

下面,我将演示一下如何在J2EE环境下使用JNDI,为了保证代码的通用性,我不使用struts之类的框架,而是直接使用标准JSP和Servlet实现。我将该项目的名称定为jndi_test

要使用JNDI,需要先到SUN的网站上去下载jndi.jar。

 2.1 JSP

本项目包括5个JSP,功能说明如下:

  • index.jsp:首页
  • bind.jsp:用于在JNDI中绑定对象
  • bind_result.jsp:绑定对象后的返回页面
  • lookup.jsp:用于在JNDI中检索对象
  • lookup_result.jsp:用于显示检索对象

本节中用到的JSP代码如下,代码都简单地很,就不多做解释了。

2.1.1 index.jsp

> bind an object </ a >
> lookup the binded object </ a >
</ body >
</ html >

2.1.5 lookup_result.jsp

<% @ page language = " java "  contentType = " text/html; charset=GB18030 "
    pageEncoding = " GB18030 " %>
<! DOCTYPE html PUBLIC "-//W3C//DTD HTML 4.01 Transitional//EN" "http://www.w3.org/TR/html4/loose.dtd" >
< html >
< head >
< meta  http-equiv ="Content-Type"  content ="text/html; charset=GB18030" >
< title > JNDI Test - Lookup result </ title >
</ head >
< body >
<%
     Object  o  =  request.getAttribute( " found_jndi_obj " );
    out.println(o);
%>
</ body >
</ html >

2.2 Servlet

本例包括两个Servlet,功能说明如下:

  • BindServlet:用于在JNDI服务中绑定一个对象
  • LookupServlet:用于在JNDI服务中取出一个对象

2.2.1 BindServlet.java

package  lld.test.jndi;

import  java.io.IOException;
import  java.util.Date;

import  javax.naming.Context;
import  javax.naming.InitialContext;
import  javax.servlet.RequestDispatcher;
import  javax.servlet.ServletContext;
import  javax.servlet.ServletException;
import  javax.servlet.http. * ;

public   class  BindServlet  extends  HttpServlet
{

     private   static   final   long  serialVersionUID  =   5219969790998794367L ;

    @Override
     protected   void  doGet(HttpServletRequest req, HttpServletResponse resp)
             throws  ServletException, IOException
     {
         this .doPost(req, resp);
    }

    @Override
     protected   void  doPost(HttpServletRequest req, HttpServletResponse resp)
             throws  ServletException, IOException
     {
         try
         {
            Context jndi_ctx  =   new  InitialContext();
            String key  =   " jndi_object " ;
            jndi_ctx.rebind(key,  new  Date());
        } catch (Exception ex)
         {
            ex.printStackTrace();
        }
        
        ServletContext context  =   this .getServletContext();
        RequestDispatcher dispatcher  =  context.getRequestDispatcher( " /bind_result.jsp " );
        dispatcher.forward(req, resp);
    }
    
}

使用rebind而不是bind绑定对象是因为,使用bind时,如果已经有对象绑定到该键值上,则会抛出异常。

因为只是示例代码,所以我只是绑定了一个最简单的日期对象。

2.2.2 LookupServlet.java

package  lld.test.jndi;

import  java.io.IOException;

import  javax.naming.Context;
import  javax.naming.InitialContext;
import  javax.servlet.RequestDispatcher;
import  javax.servlet.ServletContext;
import  javax.servlet.ServletException;
import  javax.servlet.http.HttpServlet;
import  javax.servlet.http.HttpServletRequest;
import  javax.servlet.http.HttpServletResponse;

public   class  LookupServlet  extends  HttpServlet
{
     private   static   final   long  serialVersionUID  =   6677219828267184673L ;

    @Override
     protected   void  doGet(HttpServletRequest req, HttpServletResponse resp)
             throws  ServletException, IOException
     {
         this .doPost(req, resp);
    }

    @Override
     protected   void  doPost(HttpServletRequest req, HttpServletResponse resp)
             throws  ServletException, IOException
     {
         try
         {
            Context jndi_ctx  =   new  InitialContext();
            String key  =   " jndi_object " ;
            Object o  =  jndi_ctx.lookup(key);
            req.setAttribute( " found_jndi_obj " , o);
        } catch (Exception ex)
         {
            ex.printStackTrace();
        }
        
        ServletContext context  =   this .getServletContext();
        RequestDispatcher dispatcher  =  context.getRequestDispatcher( " /lookup_result.jsp " );
        dispatcher.forward(req, resp);
    }
    
}

2.3 web.xml

在web.xml中,加入了servlet映射

<? xml version="1.0" encoding="UTF-8" ?>
< web-app  id ="WebApp_ID"  version ="2.4"  xmlns ="http://java.sun.com/xml/ns/j2ee"  xmlns:xsi ="http://www.w3.org/2001/XMLSchema-instance"  xsi:schemaLocation ="http://java.sun.com/xml/ns/j2ee http://java.sun.com/xml/ns/j2ee/web-app_2_4.xsd" >
     < display-name > jndi_test </ display-name >
    
     < servlet >
         < servlet-name > BindServlet </ servlet-name >
         < servlet-class > lld.test.jndi.BindServlet </ servlet-class >
     </ servlet >
     < servlet-mapping >
         < servlet-name > BindServlet </ servlet-name >
         < url-pattern > /bind.do </ url-pattern >
     </ servlet-mapping >
    
     < servlet >
         < servlet-name > LookupServlet </ servlet-name >
         < servlet-class > lld.test.jndi.LookupServlet </ servlet-class >
     </ servlet >
    
     < servlet-mapping >
         < servlet-name > LookupServlet </ servlet-name >
         < url-pattern > /lookup.do </ url-pattern >
     </ servlet-mapping >
    
     < welcome-file-list >
         < welcome-file > index.jsp </ welcome-file >
     </ welcome-file-list >
</ web-app >


OK,所有的代码都在这里了,部署到Tomcat下运行即可。

JNDI 笔记(三) J2SE下使用JNDI

在J2SE下使用JNDI下就显得困难一些,首先,我们没有单独的JNDI服务器可以用,JBoss提供了一个免费的JNP服务,通过配置可以作为 单独的JNDI服务器启用。不过这里就不这么麻烦了,如何使用JBOSS作为JNDI服务器,以后将单独撰文讲述,这里我使用sun提供的 com.sun.jndi.fscontext.RefFSContextFactory作为JNDI服务器,其实这是使用文件系统来存储JNDI对象。 至于如何存储后文还将专门描述。

为了在J2SE下使用JNDI,我们首先得到sun的网站上下载3个包,jndi.jar、fscontext.jar和providerutil.jar,前者提供了JNDI服务的接口,后两者是我们要使用的文件系统作为JNDI服务器的支持包。

使用RefFSContextFactory,要求绑定的对象必须实现javax.naming.Referencable接口,否则在绑定时将报如下错误:

Can only bind References or Referenceable objects

各个JDBC驱动提供商提供的DataSource类都实现了Referencable接口,可以直接使用。不过本着学习的态度,我还是在这里演示一下如何实现Referencable接口。

这个如何实现将在后文结合代码详细介绍。本例包括4个类,说明如下:

  • BindedClass:自定义的实现Referenceable接口的类
  • BindedClassFactory:工厂类,能够把一个Reference对象转换为BindedClass对象
  • Bind:测试类,用于在JNDI中绑定对象
  • Loopup:测试类,用于从JNDI中获取对象

3.1 BindedClass和BindedClassFactory

3.1.1 BindedClass

package  lld.test.jndi;

import  javax.naming.NamingException;
import  javax.naming.Reference;
import  javax.naming.Referenceable;
import  javax.naming.StringRefAddr;

public   class  BindedClass  implements  Referenceable 
{
     public  String value; 
    
     public  BindedClass()
     {
    }
    
    @Override
     public  Reference getReference()  throws  NamingException
     {
        Reference r  =   new  Reference( this .getClass().getName(), BindedClassFactory. class .getName(),  null );
        r.add( new  StringRefAddr( " value " ,  this .getValue()));
         return  r;
    }

     public  String getValue()
     {
         return  value;
    }

     public   void  setValue(String value)
     {
         this .value  =  value;
    }

}

3.1.2 BindedClassFactory

package  lld.test.jndi;

import  java.util.Hashtable;

import  javax.naming. * ;
import  javax.naming.spi. * ;

public   class  BindedClassFactory  implements  ObjectFactory
{
    @Override
     public  Object getObjectInstance(Object obj, Name name, Context nameCtx,

转载于:https://www.cnblogs.com/understander/p/5558522.html

JNDI 笔记(一) 概述相关推荐

  1. JNDI 笔记(转)

    JNDI 笔记(一) 概述 NDI,Java Naming Directory Interface,J2EE的标准之一,所有的J2EE容器都必须提供一个JNDI的服务,但是,我一直都没用过,至少是没有 ...

  2. System Verilog自学笔记专栏概述博文目录

    本文用于梳理学习笔记目录下的博文笔记,概述会有笔者的System Verilog的学习反思以及相关随笔,望有同学发现问题及时提出~感谢 概述随笔 了解基本的概念,框架后,开始使用例子进行学习语言.需要 ...

  3. 计算机网络笔记Part1 概述

    本人计算机网络笔记总目录 计算机网络笔记Part1 概述 计算机网络笔记Part2 物理层(Physical Layer) 计算机网络笔记Part3 数据链路层(Data Link Layer) 计算 ...

  4. Oracle学习笔记 字符集概述

    Oracle 学习笔记 字符集概述 这节课开始讲oracle里面的字符集 偏重于原理和简单的一些判断以及实现 字符集它涉及到很多的东西 比如建库和操作系统环境 这节课把字符集的原理性的东西以及常见的操 ...

  5. JVM学习笔记上(概述-本地方法栈)

    背景 前一阵跟着宋红康的视频学了学JVM,视频没有更新完,所以也没学完,这里记录一下笔记 JVM概述 JVM位置:  运行在操作系统之上 相对于java语言,JVM的位置如下所示 对于安卓的Davli ...

  6. 计算机网络复习笔记-----计算机网络概述(附成电复试重点)

    计算机网络 一.概述 1.1 计算机网络在信息时代中的作用 1.1.1 网络简介 1.1.2 因特网(Internet)的发展 1.1.3 因特网的意义 1.1.4 计算机网络向用户提供的最重要的功能 ...

  7. esp-adf框架笔记 1 概述

    这个笔记的只是用于个人对于学习esp-adf的记录,如有错误纯属正常 esp-adf 介绍 ESP-ADF 在 ESP-IDF(乐鑫物联网开发框架,广泛运用于 ESP32 的 SDK)的基础上开发而成 ...

  8. 《JavaScript权威指南第六版》学习笔记-JavaScript概述

    第一章.JavaScript概述 JavaScript是一门高端的.动态的.弱类型的编程语言,非常适合面向对象和函数式的编程风格.JavaScript的语法源自Java,它的一等函数(first-cl ...

  9. μCos-ii学习笔记1_概述

    一.μCos-ii _概述 网上关于μCosii的文章多不胜数,本人学习的过程中也参考了很多人的理解和想法,看的是卢有亮老师的<嵌入式实时操作系统-μC/OS原理与实践>(第2版),同时也 ...

最新文章

  1. harmonyos能否移植到MCU,HarmonyOS(LiteOs_m) 官方例程移植到STM32初体验
  2. UA PHYS515A 电磁理论III 静磁学问题2 标量势方法与向量势方法简介
  3. JUC锁-ReentrantReadWrite(五)
  4. 苹果公司计划在俄勒冈州建设其第三个数据中心
  5. c语言指针的地址存放,c语言 - *指针 和 地址
  6. 家装强电弱电布线图_家装电路改造注意事项是什么?深圳广田家透彻分析全搞定...
  7. 剑指offer之使数组的奇数在偶数前面
  8. 清理apache日志
  9. workman php教程_Workerman
  10. python输入矩阵_python如何输入矩阵
  11. DDoS攻击:无限战争
  12. js 图片打包压缩下载到本地
  13. 只是一个文件节点类为了项目的数据处理
  14. 天选2无法连接WiFi解决方案(MT7921网卡问题)
  15. Spring Boot 接口数据加解密就该这样设计~
  16. 广告推荐论文 博客 项目 汇总
  17. 这个是可以将得到速查编码的存储过程 如 中国人 可以得到 ZGR
  18. ARCGIS地图导出问题
  19. 2022年登高架设免费试题及登高架设复审考试
  20. 蓝牙的ATT协议(属性协议)和GATT协议

热门文章

  1. python编程从入门到精通 叶维忠 pdf-叶维忠《Python编程从入门到精通》PDF
  2. python笔记基础-python笔记(二)基础二
  3. python游戏编程入门 免费-Python游戏编程入门4
  4. python画直方图成绩分析-使用Python绘制直方图和正态分布曲线
  5. python画树叶-使用Python turtle画分形树叶图
  6. python应该怎么自学-Python 应该怎么学?
  7. python3.7安装numpy模块-Python3.7模块numpy
  8. python好还是c语言好-初学者先学习python语言还是C语言
  9. python编程语言是什么-python是什么编程语言
  10. python语言的官方网站地址-字符串中的街道地址搜索-Python或Ruby