131、请对以下Java EE中的名词进行解释
答:
- 容器:容器为Java EE应用程序组件提供了运行时支持。容器提供了一份从底层Java EE API到应用程序组件的联合视图。Java EE应用程序组件不能直接地与其它Java EE应用程序组件交互。它们通过容器的协议和方法来达成它们之间以及它们与平台服务之间的交互。在应用程序组件和Java EE服务之间插入一个容器,这允许该容器透明地为组件注入必须的服务,例如声明式事务管理,安全检查,资源池和状态管理。
- 资源适配器:资源适配器是一个系统级的组件,它通常实现了对外部资源管理器的网络连接。资源适配器能够扩展Java EE平台的功能。这只需要实现一个Java EE标准服务API(例如JDBC驱动程序),或者定义并实现一个能连接到外部应用程序系统的资源适配器就可以达到。资源适配器也可以提供完整的本地或本地资源的服务。资源适配器接口通过Java EE服务供应商接口(Java EE SPI)来连接Java EE平台。使用Java EE SPI连接到Java EE平台的资源适配器可以和所有的Java EE产品协同工作。
- JNDI(Java Naming & Directory Interface):Java命名目录接口,主要提供的功能是:提供一个目录系统,让其它各地的应用程序在其上面留下自己的索引,从而满足快速查找和定位分布式应用程序的功能。
- JMS(Java Message Service):Java消息服务是用于消息发送的标准API,它支持可靠的“点对点”消息发送和“发布-订阅”模型。Java EE规范要求JMS供应商同时实现“点对点”消息发送和”发布/订阅”型消息发送。
- JTA(Java Transaction API):Java 事务编程接口。Java事务API由两部分组成:①一个应用程序级的边界划分接口,容器和应用程序组件用它来划分事务边界;②一个介于事务管理器和资源管理器之间的Java EE SPI级接口。
- JPA(Java Persistence API):Java持久化API是用于持久化和对象/关系映射管理的标准API。通过使用一个Java域模型来管理关系型数据库,Java EE规范为应用程序开发者提供了一种对象/关系映射功能。Java EE必须对Java持久化API提供支持。它也可以用在Java SE环境中。
- JAF(JavaBean Activation FrameWork):JAF API提供了一个框架来处理不同MIME类型的数据,它们源于不同的格式和位置。JavaMail API使用了JAF API。JAF API包含在Java SE中,因此它可以被Java EE应用程序使用。
- JAAS(Java Authentication and Authorization Service):使服务能够基于用户进行验证和实施访问控制。它实现了一个Java版的标准的的Plugable Authentication Module (PAM)框架,并支持基于用户的授权。Java Authorization Service Provider Contract for Containers (JACC) 定义了Java EE应用程序服务器和授权服务提供方之间的协议,允许将自定义的授权服务提供方插入任何Java EE产品中。
- JMX(Java Management Extension):Java平台企业版管理规范中定义了一种API,通过一种特殊的管理型EJB来管理Java EE服务器。JMX API也提供了一些管理上的支持。
132、Java EE 是什么?
答:Java EE是SUN Microsystems(2009年被Oracle收购)公司为企业级应用推出的标准平台,该平台是由一系列技术标准所组成的,包括:EJB、JAAS、JAF、JAX-WS、JDBC、JNDI、JSTL、JSF、JSP、Servlet、RMI等。
133、你是如何理解控制反转(IoC)和依赖注入(DI)的?
答:控制反转 (Inversion of Control, IoC)是把传统上由程序代码直接操控的对象的调用权交给容器,通过容器来实现对象组件的装配和管理。所谓的“控制反转”就是对组件对象控制权的转移,从程序代码本身转移到了外部容器,由容器来创建对象并管理对象之间的依赖关系。IoC体现了好莱坞原则:“Don’t call me, we will call you”。依赖注入(Dependency Injection,DI)的基本原则是:应用组件不应该负责查找资源或者其他依赖的协作对象。配置对象的工作应该由容器负责,查找资源的逻辑应该从应用组件的代码中抽取出来,交给容器来完成。DI是对IoC更准确的描述,即组件之间的依赖关系由容器在运行期决定,形象的来说,即由容器动态的将某种依赖关系注入到组件之中。
举个例子:一个类A需要用到接口B中的方法,那么就需要为类A和接口B建立关联或依赖关系,最原始的方法是在类A中创建一个接口B的实现类C的实例,但这种方法需要开发人员自行维护二者的依赖关系,也就是说当依赖关系发生变动的时候需要修改代码并重新构建整个系统。如果通过一个容器来管理这些对象以及对象的依赖关系,则只需要在类A中定义好用于关联接口B的方法(构造器或setter方法),将类A和接口B的实现类C放入容器中,通过对容器的配置来实现二者的关联。
134、请说出Spring 中依赖注入和AOP的实现机制。
答:
- 实现依赖注入的方式包括:构造器注入、设值注入和接口(回调)注入。Spring中可以通过设值注入(setter方法注入)和构造器注入实现IoC,推荐使用的方式为设值注入。
- 实现AOP的方式包括:编译时AOP(需要特殊的编译器)、运行时AOP(代理模式)、加载时AOP(需要特殊的类加载器)。Spring中使用了运行时的AOP,主要通过代理的方式对原来的代码进行增强实现。对于实现了接口的类,Spring通过Java的动态代理(请参考Proxy类和InvocationHandler接口)来进行增强;对于没有实现接口的类,Spring使用第三方字节码生成工具CGLIB,通过继承的方式对原有代码进行增强。
135、你的项目选择使用Spring框架的原因是什么?
答:
- Spring提供了企业级开发的一站式选择,有大量的功能模块可供选择,并且可以根据项目的需要自由取舍。Spring通过POJO简化了JavaEE开发,低侵入式的编程提供了代码的持续集成能力和易测试性。
- Spring框架的核心功能是依赖注入(DI)。DI使得代码的单元测试更加方便、系统更好维护、代码也更加灵活。DI代码自身很容易测试,通过构建实现了应用所需的接口的“模拟”对象就可以进行功能的黑盒测试。DI代码也更容易复用,因为其“被依赖的”功能封装在在定义良好的接口中,允许其他对象根据需要将其插入到所需的对象中,这些对象是在其他应用平台中进行配置的。DI使代码更加灵活,由于其天生的松耦合性,它允许程序员仅需考虑自己所需的接口和其他模块暴露出来的接口来就可以决定对象之间如何关联。
- Spring支持面向切面编程(AOP),允许通过分离应用业务逻辑和系统服务从而进行内聚性的开发。AOP通常用来支持日志、审计、性能和内存监控等功能。
- Spring还提供了许多实现基本功能的模板类,使得Java EE应用的开发更加容易。例如,JdbcTemplate类和JDBC、JpaTemplate类和JPA,JmsTemplate类和JMS都可以很好地结合起来使用。RestTemplate类非常简洁,使用这个模板的代码的可读性和可维护性也都很好。
- Spring提供了声明性事务处理,工作调度,身份认证,成熟的Web MVC框架以及和其他框架的集成,例如Hibernate、MyBatis、JasperReports、JSF、Struts、Tapestry、Seam和Quartz等等。
- Spring Bean对象可以通过Terracotta在不同的JVM之间共享。这就允许使用已有的Bean并在集群中共享 ,将Spring应用上下文事件变为分布式事件,还可以通过Spring JMX导出集群Bean,使得Spring应用高可用、集群化。
- Spring倾向于使用非受检异常(运行时异常)和减少不当try、catch和finally代码块,例如JpaTemplate这样的Spring模板类会负责关闭或释放数据库连接,这避免了潜在的外部资源泄露问题并提高了代码的可读性。