美文网首页
4.9 使用FactoryBean

4.9 使用FactoryBean

作者: 仙境源地 | 来源:发表于2019-10-15 17:57 被阅读0次

    解决问题
    如何创建并注入不能简单地使用new运算符创建的依赖项
    FactoryBean是一个bean,可以作为其他bean的工厂。

    当spring容器调用getBean方法时,它并不返回FactoryBean,而是调用FactoryBean.getObject()方法并返回调用的结果.
    spring内典型应用场景

    • 创建事务代理(第9章介绍)
    • 从JNDI上下文中自动获取资源
    • 构建自己的应用程序也可以使用

    说明

    FactoryBean接口
    实现
    getObject方法:FactoryBean创建的对象

    getObjectType方法:返回对象的类型

    样例

    MessageDigest消息摘要的生成,MessageDigest.getInstance生成MessageDigest实例
    源码 chapter04/factory-bean

    package com.apress.prospring5.ch4;
    
    import java.security.MessageDigest;
    
    import org.springframework.beans.factory.FactoryBean;
    import org.springframework.beans.factory.InitializingBean;
    
    public class MessageDigestFactoryBean implements 
          FactoryBean<MessageDigest>, InitializingBean {
        private String algorithmName = "MD5";
    
        private MessageDigest messageDigest = null;
    
        public MessageDigest getObject() throws Exception {
           return messageDigest;
        }
    
        public Class<MessageDigest> getObjectType() {
            return MessageDigest.class;
        }
    
        public boolean isSingleton() {
            return true;
        }
    
        public void afterPropertiesSet() throws Exception {
            messageDigest = MessageDigest.getInstance(algorithmName);
        }
    
        public void setAlgorithmName(String algorithmName) {
            this.algorithmName = algorithmName;
        }
    }
    
    package com.apress.prospring5.ch4;
    
    import java.security.MessageDigest;
    
    public class MessageDigester {
        private MessageDigest digest1;
        private MessageDigest digest2;
    
        public void setDigest1(MessageDigest digest1) {
            this.digest1 = digest1;
        }
    
        public void setDigest2(MessageDigest digest2) {
            this.digest2 = digest2;
        }
    
        public void digest(String msg) {
            System.out.println("Using digest1");
            digest(msg, digest1);
    
            System.out.println("Using digest2");
            digest(msg, digest2);
        }
    
        private void digest(String msg, MessageDigest digest) {
            System.out.println("Using alogrithm: " + digest.getAlgorithm());
            digest.reset();
            byte[] bytes = msg.getBytes();
            byte[] out = digest.digest(bytes);
            System.out.println(out);
        }
    }
    
    <?xml version="1.0" encoding="UTF-8"?>
    
    <beans xmlns="http://www.springframework.org/schema/beans"
        xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
        xmlns:p="http://www.springframework.org/schema/p"
        xsi:schemaLocation="http://www.springframework.org/schema/beans
            http://www.springframework.org/schema/beans/spring-beans.xsd">
    
        <bean id="shaDigest" class="com.apress.prospring5.ch4.MessageDigestFactoryBean"
          p:algorithmName="SHA1"/>
    
        <bean id="defaultDigest" 
            class="com.apress.prospring5.ch4.MessageDigestFactoryBean"/>
    
        <bean id="digester" 
            class="com.apress.prospring5.ch4.MessageDigester"
            p:digest1-ref="shaDigest"
            p:digest2-ref="defaultDigest"/>
    </beans>
    
    package com.apress.prospring5.ch4;
    
    import org.springframework.context.support.GenericXmlApplicationContext;
    
    public class MessageDigestDemo {
        public static void main(String... args) {
            GenericXmlApplicationContext ctx = new GenericXmlApplicationContext();
            ctx.load("classpath:spring/app-context-xml.xml");
            ctx.refresh();
    
            MessageDigester digester = (MessageDigester) ctx.getBean("digester");
            digester.digest("Hello World!");
            /*
            执行结果
            Using digest1
            Using alogrithm: SHA1
            [B@441772e
            Using digest2
            Using alogrithm: MD5
            [B@7334aada
             */
            //MessageDigestFactoryBean messageDigestFactoryBean1 = (MessageDigestFactoryBean) ctx.getBean("messageDigestFactoryBean");
            //Exception in thread "main" org.springframework.beans.factory.NoSuchBeanDefinitionException: No bean named 'messageDigestFactoryBean' available
    
            //访问产生bean的factory bean: &beanName
            MessageDigestFactoryBean messageDigestFactoryBean2 = (MessageDigestFactoryBean) ctx.getBean("&shaDigest");
            ctx.close();
        }
    }
    

    4.10 直接访问FactoryBean

    访问产生bean的factory bean: &beanName

    4.11 使用factory-bean和factory-method属性

    问题:有时需要实例化第三方应用程序提供的javaBean,可能不知道如何实例化该类,但是第三方提供了一个可获取该bean的类,典型工厂模式
    <bean>的factory-bean和factory-method属性

    样例

    源码 chapter04/factory-bean-and-factory-method-attributes

    package com.apress.prospring5.ch4;
    
    import java.security.MessageDigest;
    
    public class MessageDigestFactory {
        private String algorithmName = "MD5";
    
        public MessageDigest createInstance() throws Exception {
           return MessageDigest.getInstance(algorithmName);
        }
    
        public void setAlgorithmName(String algorithmName) {
            this.algorithmName = algorithmName;
        }
    }
    
    package com.apress.prospring5.ch4;
    
    import java.security.MessageDigest;
    
    public class MessageDigester {
        private MessageDigest digest1;
        private MessageDigest digest2;
    
        public void setDigest1(MessageDigest digest1) {
            this.digest1 = digest1;
        }
    
        public void setDigest2(MessageDigest digest2) {
            this.digest2 = digest2;
        }
    
        public void digest(String msg) {
            System.out.println("Using digest1");
            digest(msg, digest1);
    
            System.out.println("Using digest2");
            digest(msg, digest2);
        }
    
        private void digest(String msg, MessageDigest digest) {
            System.out.println("Using alogrithm: " + digest.getAlgorithm());
            digest.reset();
            byte[] bytes = msg.getBytes();
            byte[] out = digest.digest(bytes);
            System.out.println(out);
        }
    }
    
    <?xml version="1.0" encoding="UTF-8"?>
    <beans xmlns="http://www.springframework.org/schema/beans"
        xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
        xmlns:p="http://www.springframework.org/schema/p"
        xsi:schemaLocation="http://www.springframework.org/schema/beans
            http://www.springframework.org/schema/beans/spring-beans.xsd">
    
        <bean id="shaDigestFactory" 
            class="com.apress.prospring5.ch4.MessageDigestFactory"
            p:algorithmName="SHA1"/>
    
        <bean id="defaultDigestFactory"
            class="com.apress.prospring5.ch4.MessageDigestFactory"/>
    
        <bean id="shaDigest"
              factory-bean="shaDigestFactory"
              factory-method="createInstance">
        </bean>
    
        <bean id="defaultDigest"
              factory-bean="defaultDigestFactory"
              factory-method="createInstance"/>
    
        <bean id="digester" 
            class="com.apress.prospring5.ch4.MessageDigester"
            p:digest1-ref="shaDigest"
            p:digest2-ref="defaultDigest"/>
    </beans>
    
    package com.apress.prospring5.ch4;
    import org.springframework.context.support.GenericXmlApplicationContext;
    public class MessageDigestFactoryDemo {
        public static void main(String... args) {
            GenericXmlApplicationContext ctx = new GenericXmlApplicationContext();
            ctx.load("classpath:spring/app-context-xml.xml");
            ctx.refresh();
    
            MessageDigester digester = (MessageDigester) ctx.getBean("digester");
            digester.digest("Hello World!");
    
            ctx.close();
        }
    }
    

    相关文章

      网友评论

          本文标题:4.9 使用FactoryBean

          本文链接:https://www.haomeiwen.com/subject/apgsmctx.html