springBoot2集成shardingsphere4做读写分离并记录sql
本⽂记录springboot2集成shardingsphere4实现业务层读写分离,其余相关涉及组件 :mybatis-plus,hikari, postgresql , logback ,p6spy 1. pom⽂件引⼊shardingsphere4依赖     
<dependency>
spring怎么读视频<groupId>org.apache.shardingsphere</groupId>
<artifactId>sharding-jdbc-spring-boot-starter</artifactId>
<version>4.0.1</version>
</dependency>
2.shardingsphere4相关配置项
1 spring:
2  shardingsphere:
3    datasource:
4      names: master,slave0,slave1
5      master:
6        type: com.zaxxer.hikari.HikariDataSource
7        driver-class-name: ine.spy.P6SpyDriver
8 #        连接池配置项
9        jdbc-url: jdbc:p6spy:postgresql://a:5432/bb
10        username: postgres
11        password: postgres
12        autoCommit: false
13        maximum-pool-size: 10
14        validation-timeout: 5_000
15        connection-timeout: 30_000
16        idle-timeout: 600_000
17        max-lifetime: 1_800_000
18      slave0:
19        type: com.zaxxer.hikari.HikariDataSource
20        driver-class-name: ine.spy.P6SpyDriver
21        jdbc-url: jdbc:p6spy:postgresql://b:5432/bb
22        username: postgres
23        password: postgres
24        autoCommit: false
25        maximum-pool-size: 10
26        validation-timeout: 5_000
27        connection-timeout: 30_000
28        idle-timeout: 600_000
29        max-lifetime: 1_800_000
30      slave1:
31        type: com.zaxxer.hikari.HikariDataSource
32        driver-class-name: ine.spy.P6SpyDriver
33        jdbc-url: jdbc:p6spy:postgresql://c:5432/bb
34        username: postgres
35        password: postgres
36        autoCommit: false
37        maximum-pool-size: 10
38        validation-timeout: 5_000
39        connection-timeout: 30_000
40        idle-timeout: 600_000
41        max-lifetime: 1_800_000
42 #        读写分离配置项
43    masterslave:
44      load-balance-algorithm-type: round_robin  # random
45      master-data-source-name: master
46      slave-data-source-names: slave0,slave1
47      name: ms
48    props:
49      sql:
50        show: true
3.p6spy相关配置项 (resources下创建spy.properties⽂件,内容如下)
1 #开启模块sql记录和长时sql记录
2 module.log=ine.logging.P6LogFactory,ine.outage.P6OutageFactory
3 logMessageFormat=ine.spy.appender.CustomLineFormat
4 #⾃定义sql输出格式
5 customLogMessageFormat=%(currentTime) | TIME\uFF1A %(executionTime) ms | SQL\uFF1A %(sql)
6 #⽇志输出⽅式
7 appender=ine.spy.appender.Slf4JLogger
8 excludecategories=info,debug,result,resultset
9 deregisterdrivers=true
10 dateformat=yyyy-MM-dd HH:mm:ss
11 driverlist=org.postgresql.Driver
12 #开启长时sql记录
13 outagedetection=true
14 #触发长时记录时限
15 outagedetectioninterval=2
4.logback相关配置(resource⽂件夹下创建l内容如下)
1 <?xml version="1.0" encoding="UTF-8"?>
2 <configuration>
3
4    <!--⽇志格式应⽤spring boot默认的格式,也可以⾃⼰更改-->
5    <include resource="org/springframework/boot/logging/l"/>
6
7    <!--定义⽇志存放的位置,默认存放在项⽬启动的相对路径的⽬录-->
8    <springProperty scope="context" name="LOG_PATH" source="log.path" defaultValue="log"/>
9    <springProperty scope="context" name="ZONE" source="" defaultValue="default"/>
10    <springProperty scope="context" name="APP_NAME" source="spring.application.name" defaultValue="app"/>
11    <springProperty scope="context" name="LOGSTASH_URL" source="logstash.url" defaultValue="localhost:4560"/>
12
13    <!-- ****************************************************************************************** -->
14    <!-- ****************************** 开发环境⽇志 ************************************ -->
15    <!-- ****************************************************************************************** -->
16    <springProfile name="local">
17        <appender name="STDOUT"class="ch.ConsoleAppender">
18            <encoder>
19                <pattern>${CONSOLE_LOG_PATTERN}</pattern>
20                <charset>utf-8</charset>
21            </encoder>
22        </appender>
23
24        <!-- ⽇志记录器,⽇期滚动记录 -->
25        <appender name="FILE"class="ch.olling.RollingFileAppender">
26
27            <!-- 正在记录的⽇志⽂件的路径及⽂件名 -->
28            <file>${LOG_PATH}/${ZONE}-${APP_NAME}-local.log</file>
29
30            <!-- ⽇志记录器的滚动策略,按⽇期,按⼤⼩记录 -->
31            <rollingPolicy class="ch.olling.TimeBasedRollingPolicy">
32
33                <!-- 归档的⽇志⽂件的路径,%d{yyyy-MM-dd}指定⽇期格式,%i指定索引 -->
34                <fileNamePattern>${LOG_PATH}/all/${ZONE}-${APP_NAME}-%d{yyyy-MM-dd}.%i-local.log</fileNamePattern> 35
36                <timeBasedFileNamingAndTriggeringPolicy class="ch.olling.SizeAndTimeBasedFNATP">
37                    <maxFileSize>10MB</maxFileSize>
38                </timeBasedFileNamingAndTriggeringPolicy>
39            </rollingPolicy>
40
41            <!-- 追加⽅式记录⽇志 -->
42            <append>true</append>
43
44            <!-- ⽇志⽂件的格式 -->
45            <encoder class="ch.qos.der.PatternLayoutEncoder">
46                <pattern>${FILE_LOG_PATTERN}</pattern>
47                <charset>utf-8</charset>
48            </encoder>
49        </appender>
50
51        <!--默认所有的包以warn-->
52        <root level="warn">
53            <appender-ref ref="STDOUT"/>
54            <appender-ref ref="FILE"/>
55        </root>
56
57        <!--ShardingSphere打印sql⽤-->
58        <logger name="ShardingSphere-SQL" level="info"/>
59        <!--p6spy打印sql-->
60        <logger name="p6spy" level="info"/>
61        <!--屏蔽getRowIdLifetime未实作警告-->
62        <logger name="com.zaxxer.hikari.pool.ProxyConnection" level="error"/>
63
64        <!--各个服务的包在本地执⾏的时候,打开debug模式-->
65        <logger name="project" level="debug" additivity="false">
66            <appender-ref ref="STDOUT"/>
67            <appender-ref ref="FILE"/>
68        </logger>
69    </springProfile>
70
71    <!-- ********************************************************************************************** -->
72    <!-- **** 放到服务器上不管在什么环境都只在⽂件记录⽇志,控制台(catalina.out)打印logback捕获不到的⽇志 **** -->
73    <!-- ********************************************************************************************** -->
74    <springProfile name="!local">
75
76        <appender name="STDOUT"class="ch.ConsoleAppender">
77            <encoder>
78                <pattern>${CONSOLE_LOG_PATTERN}</pattern>
79                <charset>utf-8</charset>
80            </encoder>
81        </appender>
82
83        <!-- ⽇志记录器,⽇期滚动记录 -->
84        <appender name="FILE_ERROR"class="ch.olling.RollingFileAppender">
85
86            <!-- 正在记录的⽇志⽂件的路径及⽂件名 -->
87            <file>${LOG_PATH}/quick/${ZONE}-${APP_NAME}-log-error.log</file>
88
89            <!-- ⽇志记录器的滚动策略,按⽇期,按⼤⼩记录 -->
90            <rollingPolicy class="ch.olling.TimeBasedRollingPolicy">
91
92                <!-- 归档的⽇志⽂件的路径,%d{yyyy-MM-dd}指定⽇期格式,%i指定索引 -->
93                <fileNamePattern>${LOG_PATH}/quick/${ZONE}-${APP_NAME}-error-%d{yyyy-MM-dd}.%i.log</fileNamePattern> 94
95                <!-- 除按⽇志记录之外,还配置了⽇志⽂件不能超过10M,若超过10M,⽇志⽂件会以索引0开始,
96命名⽇志⽂件,例如log-error-2013-12-21.0.log -->
97                <timeBasedFileNamingAndTriggeringPolicy class="ch.olling.SizeAndTimeBasedFNATP">
98                    <maxFileSize>10MB</maxFileSize>
99                </timeBasedFileNamingAndTriggeringPolicy>
100            </rollingPolicy>
101
102            <!-- 追加⽅式记录⽇志 -->
103            <append>true</append>
104
105            <!-- ⽇志⽂件的格式 -->
106            <encoder class="ch.qos.der.PatternLayoutEncoder">
107                <pattern>${FILE_LOG_PATTERN}</pattern>
108                <charset>utf-8</charset>
109            </encoder>
110
111            <!-- 此⽇志⽂件只记录error级别的 -->
112            <filter class="ch.qos.logback.classic.filter.LevelFilter">
113                <level>error</level>
114                <onMatch>ACCEPT</onMatch>
115                <onMismatch>DENY</onMismatch>
116            </filter>
117        </appender>
118
119        <!-- ⽇志记录器,⽇期滚动记录 -->
120        <appender name="FILE_ALL"class="ch.olling.RollingFileAppender">
121
122            <!-- 正在记录的⽇志⽂件的路径及⽂件名 -->
123            <file>${LOG_PATH}/quick/${ZONE}-${APP_NAME}-log-all.log</file>
124
125            <!-- ⽇志记录器的滚动策略,按⽇期,按⼤⼩记录 -->
126            <rollingPolicy class="ch.olling.TimeBasedRollingPolicy">
127
128                <!-- 归档的⽇志⽂件的路径,%d{yyyy-MM-dd}指定⽇期格式,%i指定索引 -->
129                <fileNamePattern>${LOG_PATH}/quick/${ZONE}-${APP_NAME}-all-%d{yyyy-MM-dd}.%i.log</fileNamePattern> 130
131                <!-- 除按⽇志记录之外,还配置了⽇志⽂件不能超过10M,若超过10M,⽇志⽂件会以索引0开始,
132命名⽇志⽂件,例如log-error-2013-12-21.0.log -->
133                <timeBasedFileNamingAndTriggeringPolicy class="ch.olling.SizeAndT
imeBasedFNATP"> 134                    <maxFileSize>10MB</maxFileSize>
135                </timeBasedFileNamingAndTriggeringPolicy>
136            </rollingPolicy>
137
138            <!-- 追加⽅式记录⽇志 -->
139            <append>true</append>
140
141            <!-- ⽇志⽂件的格式 -->
142            <encoder class="ch.qos.der.PatternLayoutEncoder">
143                <pattern>${FILE_LOG_PATTERN}</pattern>
144                <charset>utf-8</charset>
145            </encoder>
146        </appender>
147
148        <!-- ⽇志记录器,⽇期滚动记录纪录TAM⽇志-->
149        <appender name="FILE_TAM"class="ch.olling.RollingFileAppender">
150
151            <!-- 正在记录的⽇志⽂件的路径及⽂件名 -->
152            <file>${LOG_PATH}/quick/${ZONE}-${APP_NAME}-log-tam.log</file>
153
154            <!-- ⽇志记录器的滚动策略,按⽇期,按⼤⼩记录 -->
155            <rollingPolicy class="ch.olling.TimeBasedRollingPolicy">
156
157                <!-- 归档的⽇志⽂件的路径,%d{yyyy-MM-dd}指定⽇期格式,%i指定索引 -->
158                <fileNamePattern>${LOG_PATH}/quick/${ZONE}-${APP_NAME}-tam-%d{yyyy-MM-dd}.%i.log</fileNamePattern> 159
160                <!-- 除按⽇志记录之外,还配置了⽇志⽂件不能超过10M,若超过10M,⽇志⽂件会以索引0开始,
161命名⽇志⽂件,例如log-error-2013-12-21.0.log -->
162                <timeBasedFileNamingAndTriggeringPolicy class="ch.olling.SizeAndTimeBasedFNATP">
163                    <maxFileSize>10MB</maxFileSize>
164                </timeBasedFileNamingAndTriggeringPolicy>
165            </rollingPolicy>
166
167            <!-- 追加⽅式记录⽇志 -->
168            <append>true</append>
169
170            <!-- ⽇志⽂件的格式 -->
171            <encoder class="ch.qos.der.PatternLayoutEncoder">
172                <pattern>${FILE_LOG_PATTERN}</pattern>
173                <charset>utf-8</charset>
174            </encoder>
175            <!-- 此⽇志⽂件只记录error级别的 -->
176            <filter class="ch.qos.logback.classic.filter.LevelFilter">
177                <level>error</level>
178                <onMatch>ACCEPT</onMatch>
179                <onMismatch>DENY</onMismatch>
180            </filter>
181        </appender>
182
183        <!-- ⽇志记录器,⽇期滚动记录纪录AUDITLOG⽇志-->
184        <appender name="FILE_AUDIT"class="ch.olling.RollingFileAppender">
185
186            <!-- 正在记录的⽇志⽂件的路径及⽂件名 -->
187            <file>${LOG_PATH}/auditlog/${ZONE}-${APP_NAME}-log-auditLog.log</file>
188
189            <!-- ⽇志记录器的滚动策略,按⽇期,按⼤⼩记录 -->
190            <rollingPolicy class="ch.olling.TimeBasedRollingPolicy">
191
192                <!-- 归档的⽇志⽂件的路径,%d{yyyy-MM-dd}指定⽇期格式,%i指定索引 -->
193                <fileNamePattern>${LOG_PATH}/auditlog/${ZONE}-${APP_NAME}-auditlog-%d{yyyy-MM-dd}.%i.log</fileNamePattern> 194
195                <!-- 除按⽇志记录之外,还配置了⽇志⽂件不能超过10M,若超过10M,⽇志⽂件会以索引0开始,
196命名⽇志⽂件,例如log-error-2013-12-21.0.log -->
197                <timeBasedFileNamingAndTriggeringPolicy class="ch.olling.SizeAndTimeBasedFNATP">
198                    <maxFileSize>10MB</maxFileSize>
199                </timeBasedFileNamingAndTriggeringPolicy>
200            </rollingPolicy>
201
202            <!-- 追加⽅式记录⽇志 -->
203            <append>true</append>
204
205            <!-- ⽇志⽂件的格式 -->
206            <encoder class="ch.qos.der.PatternLayoutEncoder">
207                <pattern>${FILE_LOG_PATTERN}</pattern>
208                <charset>utf-8</charset>
209            </encoder>
210            <!-- 此⽇志⽂件只记录info级别的 -->
211            <filter class="ch.qos.logback.classic.filter.LevelFilter">
212                <level>info</level>
213                <onMatch>ACCEPT</onMatch>
214                <onMismatch>DENY</onMismatch>
215            </filter>
216        </appender>
217
218        <appender name="LOGSTASH"class="net.logstash.logback.appender.LogstashTcpSocketAppender">
219            <destination>${LOGSTASH_URL}</destination>
220            <encoder charset="UTF-8"class="net.der.LogstashEncoder" />
221        </appender>
222
223
224        <!--记录到⽂件时,记录两类⼀类是error⽇志,⼀个是所有⽇志-->
225        <root level="warn">
226            <appender-ref ref="STDOUT"/>
227            <appender-ref ref="FILE_ERROR"/>
228            <appender-ref ref="FILE_ALL"/>
229        </root>
230
231        <logger name="project" level="info"/>
232        <!--ShardingSphere打印sql⽤-->
233        <logger name="ShardingSphere-SQL" level="info"/>
234        <!--p6spy打印sql-->
235        <logger name="p6spy" level="info"/>
236        <!--屏蔽getRowIdLifetime未实作警告-->
237        <logger name="com.zaxxer.hikari.pool.ProxyConnection" level="error"/>
238    </springProfile>
239
240 </configuration>
5.集成结果
通过以上⽇志观察发现已经实现了业务层⾯读写分离和读库的轮询负载策略
通过以上⽇志发现已经实现了线上环境的完整sql记录,⾄此已达到预期效果,集成完毕
6.问题总结
  1.从数据层⽅⾯shardingsphere4并没有实现主从库的数据同步,在其他⽅案的数据同步过程中主从数据不⼀致导致的数据差异是否满⾜应⽤场景还需具体评估.
  2.本实例数据库采⽤postgres,⽬前最新版本的postgres数据库驱动也没有实现getRowIdLifetime()⽅法,shardingsphere4缓存数据源元数据的时候会去调⽤该⽅法,
驱动程序会抛出⼀个⽅法未实作的异常从下⾯代码可见框架捕获后不做处理并缓存该项为UNSUPPORTED,但是因为实例集成hikari连接池,hikar的ProxyConnection类会抛出⼀个⼀个警告如下图⼆,看起来像是项⽬启动报错,但实际并不影响,程序运⾏,因此在输出⽇志中将项屏蔽,具体配置在上⾯logback中
警告:

版权声明:本站内容均来自互联网,仅供演示用,请勿用于商业和其他非法用途。如果侵犯了您的权益请与我们联系QQ:729038198,我们将在24小时内删除。