springBoot 八 整合之整合阿里druid数据库连接池

首先给大家推荐一下我老师大神的人工智能教学网站。教学不仅零基础,通俗易懂,而且非常风趣幽默,还时不时有内涵黄段子!点这里可以跳转到网站

         当时是基于C3P0处理数据库,然后偶发性出现连接超时,然后加上需要查看连接次数以及访问次数,我就想到采用druid数据库连接池,话不多说,先上代码

官网传送门:https://github.com/alibaba/druid/wiki/%E5%B8%B8%E8%A7%81%E9%97%AE%E9%A2%98

其实下面的部分出于演示,用硬编码,其实完全可以通过配置属性,来进行动态改变,至于SpringCloud中的动态配置,其实也是通过重启SpringBoot来达到充值属性的效果,至于这部分,我之后会再说,这部分我也是看过某篇推文获悉

目录

配置数据库源:

1、pom.xml

2、application.properties

配置监控器

1、过滤不需要监控的后缀

2、监控视图配置

3、读取连接属性

4、测试:

StatFilter拓展(用于统计监控信息)

    SQL合并配置

  记录慢SQL

多个Druid数据源监控合并

配置防御SQL注入攻击


配置数据库源:

1、pom.xml

		<dependency>			<groupId>mysql</groupId>			<artifactId>mysql-connector-java</artifactId>		</dependency>		<!-- druid数据库 -->		<!-- https://mvnrepository.com/artifact/com.alibaba/druid -->		<dependency>		    <groupId>com.alibaba</groupId>		    <artifactId>druid</artifactId>		    <version>1.1.11</version>		</dependency>

2、application.properties

spring.datasource.type=com.alibaba.druid.pool.DruidDataSourcespring.datasource.url=jdbc:mysql://*********************?allowMultiQueries=true&autoReconnect=true spring.datasource.username=adminspring.datasource.password=adminspring.datasource.driverClassName=com.mysql.jdbc.Driver#dataSource Pool configurationspring.datasource.initialSize=5spring.datasource.minIdle=5spring.datasource.maxActive=20spring.datasource.maxWait=60000spring.datasource.timeBetweenEvictionRunsMillis=60000   spring.datasource.minEvictableIdleTimeMillis=300000spring.datasource.validationQuery=SELECT 1 FROM DUALspring.datasource.testWhileIdle=truespring.datasource.testOnBorrow=falsespring.datasource.exceptionSorter=truespring.datasource.testOnReturn=falsespring.datasource.poolPreparedStatements=truespring.datasource.filters=stat,wall,log4jspring.datasource.maxPoolPreparedStatementPerConnectionSize=20spring.datasource.connectionProperties=druid.stat.mergeSql=true;druid.stat.slowSqlMillis=500spring.datasource.useGlobalDataSourceStat=true

对配置的属性不懂得的,可以https://github.com/alibaba/druid/wiki/%E9%85%8D%E7%BD%AE_DruidDataSource%E5%8F%82%E8%80%83%E9%85%8D%E7%BD%AE       或则 参考  DruidDataSource.class

配置监控器

1、过滤不需要监控的后缀

/**   * 配置监控拦截器 * druid监控拦截器   * @ClassName: DruidStatFilter    * @author CoffeeAndIce * @date 2017年7月24日 上午10:53:40   */  @WebFilter(filterName="druidWebStatFilter",  urlPatterns="/*",  initParams={      @WebInitParam(name="exclusions",value="*.js,*.gif,*.jpg,*.bmp,*.png,*.css,*.ico,/druid/*"),// 忽略资源  }) public class DruidStatFilter extends WebStatFilter { }

有人想在这里直接继承StatFilter进行操作,但是这样会导致重复导入,导致无法运行,因为Druid之前已经有将其置入。

2、监控视图配置

/**   * druid监控视图配置   * @ClassName: DruidStatViewServlet    * @author CoffeeAndIce * @date 2017年7月24日 上午10:54:27   */  @WebServlet(urlPatterns = "/druid/*", initParams={      @WebInitParam(name="allow",value=""),// IP白名单 (没有配置或者为空,则允许所有访问)      @WebInitParam(name="deny",value="192.168.16.111"),// IP黑名单 (存在共同时,deny优先于allow)      @WebInitParam(name="loginUsername",value="admin"),// 用户名      @WebInitParam(name="loginPassword",value="admin"),// 密码      @WebInitParam(name="resetEnable",value="true")// 禁用HTML页面上的“Reset All”功能  }) public class DruidStatViewServlet extends StatViewServlet {	private static final long serialVersionUID = 2359758657306626394L; }



如果仅仅这样配置,我这边不知道为什么和网上的不一样,我这边是用MyBatis来做数据处理的,这边就sql监控和sql防火墙监控都没有用,当前使用的spring boot版本为1.4.x版本

然后搜索了一番,数据源决定自己处理

3、读取连接属性

 (这是之前的写法)方式一

@Configuration  public class DruidConfiguration {      @Value("${spring.datasource.url}")      private String dbUrl;      @Value("${spring.datasource.username}")      private String username;      @Value("${spring.datasource.password}")      private String password;      @Value("${spring.datasource.driverClassName}")      private String driverClassName;      @Value("${spring.datasource.initialSize}")      private int initialSize;      @Value("${spring.datasource.minIdle}")      private int minIdle;      @Value("${spring.datasource.maxActive}")      private int maxActive;      @Value("${spring.datasource.maxWait}")      private int maxWait;      @Value("${spring.datasource.timeBetweenEvictionRunsMillis}")      private int timeBetweenEvictionRunsMillis;      @Value("${spring.datasource.minEvictableIdleTimeMillis}")      private int minEvictableIdleTimeMillis;      @Value("${spring.datasource.validationQuery}")      private String validationQuery;      @Value("${spring.datasource.testWhileIdle}")      private boolean testWhileIdle;      @Value("${spring.datasource.testOnBorrow}")      private boolean testOnBorrow;      @Value("${spring.datasource.testOnReturn}")      private boolean testOnReturn;      @Value("${spring.datasource.poolPreparedStatements}")      private boolean poolPreparedStatements;      @Value("${spring.datasource.maxPoolPreparedStatementPerConnectionSize}")      private int maxPoolPreparedStatementPerConnectionSize;      @Value("${spring.datasource.filters}")      private String filters;      @Value("${spring.datasource.connectionProperties}")      private String connectionProperties;      @Value("${spring.datasource.useGlobalDataSourceStat}")      private boolean useGlobalDataSourceStat;        @Bean     //声明其为Bean实例      @Primary  //在同样的DataSource中,首先使用被标注的DataSource      public DataSource dataSource(){          DruidDataSource datasource = new DruidDataSource();          datasource.setUrl(this.dbUrl);          datasource.setUsername(username);          datasource.setPassword(password);          datasource.setDriverClassName(driverClassName);            //configuration          datasource.setInitialSize(initialSize);          datasource.setMinIdle(minIdle);          datasource.setMaxActive(maxActive);          datasource.setMaxWait(maxWait);          datasource.setTimeBetweenEvictionRunsMillis(timeBetweenEvictionRunsMillis);          datasource.setMinEvictableIdleTimeMillis(minEvictableIdleTimeMillis);          datasource.setValidationQuery(validationQuery);          datasource.setTestWhileIdle(testWhileIdle);          datasource.setTestOnBorrow(testOnBorrow);          datasource.setTestOnReturn(testOnReturn);          datasource.setPoolPreparedStatements(poolPreparedStatements);          datasource.setMaxPoolPreparedStatementPerConnectionSize(maxPoolPreparedStatementPerConnectionSize);          datasource.setUseGlobalDataSourceStat(useGlobalDataSourceStat);          try {              datasource.setFilters(filters);          } catch (SQLException e) {              System.err.println("druid configuration initialization filter: "+ e);          }          datasource.setConnectionProperties(connectionProperties);          return datasource;      }  }  

感谢读者给出的建议,同时让我学会了很多注解的应用玉机制,方式二

@SpringBootApplication@ServletComponentScan//这行是为了避免扫描不到Druid的Servletpublic class WebBootApplication {     public static void main(String[] args) throws Exception {        SpringApplication.run(WebBootApplication.class, args);    }      /**    *    * 其实大家主要关心下面的就好    */     @Bean("duridDatasource")    @ConfigurationProperties(prefix="spring.datasource")    public DataSource druidDataSource() { return new DruidDataSource(); } }

4、测试:

连入 :http://localhost:8080/druid/login.html   

输入(3.2、监控视图配置)设置的密码,终于看到梦寐以求的数据,这个问题可能是只有这个版本才有或者有其他处理方法

注意:上面的这个类需要放到和application同级的目录下,这样才能在程序启动的时候初始化DataSource
 

StatFilter拓展(用于统计监控信息)

    SQL合并配置

         Tips: 在druid-0.2.17版本之后,sql合并支持tddl,能够对分表进行合并。

当你程序中存在没有参数化的sql执行时,sql统计的效果会不好。比如:select * from t where id = 1select * from t where id = 2select * from t where id = 3  在统计中,显示为3条sql,这不是我们希望要的效果。StatFilter提供合并的功能,能够将这3个SQL合并为如下的SQLselect * from t where id = ? 

spring.datasource.connectionProperties=druid.stat.mergeSql=true  属性配置是这样

  记录慢SQL

   之前的版本 可能是true,现在为false

/** * @author wenshao [szujobs@hotmail.com] */public class StatFilter extends FilterEventAdapter implements StatFilterMBean {     private final static Log          LOG                        = LogFactory.getLog(StatFilter.class);     private static final String       SYS_PROP_LOG_SLOW_SQL      = "druid.stat.logSlowSql";    private static final String       SYS_PROP_SLOW_SQL_MILLIS   = "druid.stat.slowSqlMillis";    private static final String       SYS_PROP_MERGE_SQL         = "druid.stat.mergeSql";     public final static String        ATTR_NAME_CONNECTION_STAT  = "stat.conn";    public final static String        ATTR_TRANSACTION           = "stat.tx";     private final Lock                lock                       = new ReentrantLock();     // protected JdbcDataSourceStat dataSourceStat;     @Deprecated    protected final JdbcStatementStat statementStat              = JdbcStatManager.getInstance().getStatementStat();     @Deprecated    protected final JdbcResultSetStat resultSetStat              = JdbcStatManager.getInstance().getResultSetStat();     private boolean                   connectionStackTraceEnable = false;     // 3 seconds is slow sql    protected long                    slowSqlMillis              = 3 * 1000;     protected boolean                 logSlowSql                 = false;     private String                    dbType;     private boolean                   mergeSql                   = false;

所以我们需要开启的话:

spring.datasource.connectionProperties=druid.stat.logSlowSql=true;

默认时间是3秒,如需要设置自定义值: druid.stat.slowSqlMillis 加上你需要的毫秒数

多个Druid数据源监控合并

    spring.datasource.useGlobalDataSourceStat=true

试中有其他问题或者解决方案,麻烦告知一下,共同进步,谢谢

配置防御SQL注入攻击

https://github.com/alibaba/druid/wiki/%E9%85%8D%E7%BD%AE-wallfilter

   开启过滤器的在开头已经给你开启了:spring.datasource.filters=wall

只要你下载了源码,搜索相应参数名:

  eg:  selelctAllow,你就会发现缺省值

public class WallConfig implements WallConfigMBean {     private boolean             noneBaseStatementAllow      = false;     private boolean             callAllow                   = true;    private boolean             selelctAllow                = true;    private boolean             selectIntoAllow             = true;    private boolean             selectIntoOutfileAllow      = false;    private boolean             selectWhereAlwayTrueCheck   = true;    private boolean             selectHavingAlwayTrueCheck  = true;    private boolean             selectUnionCheck            = true;    private boolean             selectMinusCheck            = true;    private boolean             selectExceptCheck           = true;    private boolean             selectIntersectCheck        = true;    private boolean             createTableAllow            = true;    private boolean             dropTableAllow              = true;    private boolean             alterTableAllow             = true;

搜索:configFromProperties,你就会发现,如果这样还不会怎么配置,对不起,无能为力

     Boolean propertyValue = getBoolean(properties, "druid.wall.selelctAllow");            if (propertyValue != null) {                this.setSelelctAllow(propertyValue);            }

点这里可以跳转到人工智能网站

发表评论