ActiveMQ-自定義用戶驗證

ActiveMQ採用plugin方式擴展方法,下面是如何使用plugin方式進行自定義的登陸方式。java

準備建立mysql數據庫保存用戶,密碼,權限等信息。mysql

多臺MQ服務器加入自定義的plugin插件,經過這個plugin訪問mysql服務器進行登陸與受權操做。web

1、plugin基本結構與配置spring

具體代碼以下:sql

public class AuthPlugin implements BrokerPlugin {
    @Override
    public Broker installPlugin(Broker broker) throws Exception {
        return new AuthBroker(broker);
    }
}

public class AuthBroker extends AbstractAuthenticationBroker {

    private static Log log = LogFactory.getLog(AuthBroker.class);

    public AuthBroker(Broker next) {
        super(next);
    }

    @Override
    public void addConnection(ConnectionContext context, ConnectionInfo info) throws Exception {
        log.debug("addConnection");
        SecurityContext securityContext = context.getSecurityContext();
        if (securityContext == null) {
            securityContext = authenticate(info.getUserName(), info.getPassword(), null);
            context.setSecurityContext(securityContext);
            securityContexts.add(securityContext);
        }
        
        try {
            super.addConnection(context, info);
        } catch (Exception e) {
            securityContexts.remove(securityContext);
            context.setSecurityContext(null);
            throw e;
        }
    }
    

    @Override
    public SecurityContext authenticate(String username, String password, X509Certificate[] peerCertificates) throws SecurityException {
        SecurityContext securityContext = null;
        if("admin".equals(username)&&"1234".equals(password)){
             securityContext = new SecurityContext(username) {
                    @Override
                    public Set<Principal> getPrincipals() {
                        Set<Principal> groups = new HashSet<Principal>();
                        groups.add(new GroupPrincipal("users"));
                        return groups;
                    }
                };
        }else{
            throw new SecurityException("驗證失敗");
        }
        return securityContext;
    }
}

 

安裝插件的步驟以下:數據庫

1.將代碼導出jarapache

2.將jar包拷貝到activemq目錄下的lib目錄下服務器

3.修改activemq\conf\activemq.xmlapp

  在broker中加入eclipse

<broker xmlns="http://activemq.apache.org/schema/core" brokerName="localhost" dataDirectory="${activemq.data}">
//...
    <plugins>
            <bean xmlns="http://www.springframework.org/schema/beans" id="jhPlugin" class="com.test.activemq.plugin.AuthPlugin"/>
        </plugins>
</broker>

 

4.修改activemq/conf/log4j.properties。日誌文件目錄在activemq/data/activemq.log

log4j.rootLogger=INFO, console, logfile
log4j.logger.org.apache.activemq.spring=WARN
log4j.logger.org.apache.activemq.web.handler=WARN
log4j.logger.org.springframework=WARN
log4j.logger.org.apache.xbean=WARN
log4j.logger.org.apache.camel=INFO
log4j.logger.org.eclipse.jetty=WARN

log4j.logger.com.test.activemq=DEBUG

5.重啓activemq服務。

2、集成mysql

1.將mysql-connector-java-5.1.20.jar複製到activemq\lib目錄下

2.數據庫操做採用spring-jdbc的方式,須要將spring-jdbc-4.1.9.RELEASE.jar複製到activemq\lib\optional目錄下(spring-jdbc的版本應與lib\optional其餘的spring相同)

3.修改activemq\conf\activemq.xml文件

<beans>
    //...
    <!-- mysql數據庫數據源-->  
    <bean id="mySqlDataSource" class="org.apache.commons.dbcp2.BasicDataSource" destroy-method="close">  
            <property name="driverClassName" value="${jdbc.driverClassName}" />  
            <property name="url" value="${jdbc.url}" />  
            <property name="username" value="${jdbc.username}" />  
            <property name="password" value="${jdbc.password}" />  
    </bean>  
    <!-- 增長jdbcTemplate-->
    <bean id="jdbcTemplate" class="org.springframework.jdbc.core.JdbcTemplate" abstract="false"
        lazy-init="false" autowire="default" >
        <property name="dataSource">
            <ref bean="mySqlDataSource" />
        </property>
    </bean>
</beans>

4.修改activemq\conf\activemq.xml文件的PropertyPlaceholderConfigurer

<beans>
    //...
    <bean class="org.springframework.beans.factory.config.PropertyPlaceholderConfigurer">
        <property name="locations">
            <list>
                <value>file:${activemq.conf}/credentials.properties</value>
                <value>file:${activemq.conf}/db.properties</value>
            </list>
        </property>
    </bean>
</beans>

5.增長activemq\conf\activemq.xml文件的<broker>

<beans>
        <broker>
            <plugins>
            <bean xmlns="http://www.springframework.org/schema/beans" id="testPlugin" class="com.test.activemq.plugin.AuthPlugin">
                <constructor-arg>
                    <ref bean="jdbcTemplate"/>
                </constructor-arg>
            </bean>
        </plugins>
        </broker>
</beans>

6.AuthPlugin的代碼以下:

public class AuthPlugin implements BrokerPlugin {
    JdbcTemplate jdbcTemplate;//注入了spring-jdbc
    public AuthPlugin(JdbcTemplate jdbcTemplate) {
        this.jdbcTemplate=jdbcTemplate;
    }
    @Override
    public Broker installPlugin(Broker broker) throws Exception {
        return new AuthBroker(broker,jdbcTemplate);
    }
}

7.AuthBroker的代碼以下:

public class AuthBroker extends AbstractAuthenticationBroker {

    private static Log log = LogFactory.getLog(AuthBroker.class);
    
    private JdbcTemplate jdbcTemplate;

    public AuthBroker(Broker next,JdbcTemplate jdbcTemplate) {
        super(next);
        this.jdbcTemplate=jdbcTemplate;
    }

    /**
     * <p>
     * 建立鏈接的時候攔截
     * </p>
     */
    @Override
    public void addConnection(ConnectionContext context, ConnectionInfo info) throws Exception {
        log.debug("addConnection");
        SecurityContext securityContext = context.getSecurityContext();
        if (securityContext == null) {
            securityContext = authenticate(info.getUserName(), info.getPassword(), null);
            context.setSecurityContext(securityContext);
            securityContexts.add(securityContext);
        }
        
        try {
            super.addConnection(context, info);
        } catch (Exception e) {
            securityContexts.remove(securityContext);
            context.setSecurityContext(null);
            throw e;
        }
    }
    /**
     * 獲得用戶信息
     * <p>Title: getUser</p>
     * @param username
     * @return
     */
    private User getUser(String username){
        String sql="select * from jh_user where username=? limit 1";
        User user=jdbcTemplate.queryForObject(sql,new Object[]{username},new BeanPropertyRowMapper<User>(User.class));
        return user;
    }
    /**
     * 認證
     * <p>Title: authenticate</p>
     */
    @Override
    public SecurityContext authenticate(String username, String password, X509Certificate[] peerCertificates) throws SecurityException {
        SecurityContext securityContext = null;
        User user=getUser(username);
        //驗證用戶信息
        if(user!=null&&user.getPwd().equals(password)){
             securityContext = new SecurityContext(username) {
                    @Override
                    public Set<Principal> getPrincipals() {
                        Set<Principal> groups = new HashSet<Principal>();
                        groups.add(new GroupPrincipal("users"));//默認加入了users的組
                        return groups;
                    }
                };
        }else{
            throw new SecurityException("驗證失敗");
        }
        return securityContext;
    }
}

8.在activemq\conf\目錄下加入db.properties

jdbc.driverClassName=com.mysql.jdbc.Driver
jdbc.url=jdbc:mysql://127.0.0.1:3306/test?autoReconnect=true&useUnicode=true&characterEncoding=utf8
jdbc.username=root
jdbc.password=admin

9.重啓服務器

相關文章
相關標籤/搜索