MyBatis集成Oracle报:java.sql.SQLException: Invalid column type: 1111
insert报错日志:
org.springframework.jdbc.UncategorizedSQLException: Error setting null for parameter #12 with JdbcType OTHER . Try setting a different JdbcType for this parameter or a different jdbcTypeForNull configuration property. Cause: java.sql.SQLException: Invalid column type: 1111
; uncategorized SQLException for SQL []; SQL state [99999]; error code [17004]; Invalid column type: 1111; nested exception is java.sql.SQLException: Invalid column type: 1111
at org.springframework.jdbc.support.AbstractFallbackSQLExceptionTranslator.translate(AbstractFallbackSQLExceptionTranslator.java:83)
at org.springframework.jdbc.support.AbstractFallbackSQLExceptionTranslator.translate(AbstractFallbackSQLExceptionTranslator.java:80)
at org.springframework.jdbc.support.AbstractFallbackSQLExceptionTranslator.translate(AbstractFallbackSQLExceptionTranslator.java:80)
at org.mybatis.spring.MyBatisExceptionTranslator.translateExceptionIfPossible(MyBatisExceptionTranslator.java:71)
at org.mybatis.spring.SqlSessionTemplate$SqlSessionInterceptor.invoke(SqlSessionTemplate.java:364)
at com.sun.proxy.$Proxy38.insert(Unknown Source)
at org.mybatis.spring.SqlSessionTemplate.insert(SqlSessionTemplate.java:236)
at org.apache.ibatis.binding.MapperMethod.execute(MapperMethod.java:46)
at org.apache.ibatis.binding.MapperProxy.invoke(MapperProxy.java:43)
at com.sun.proxy.$Proxy215.addYppcmx(Unknown Source)
at com.appcenter.bcls.ypgl.service.impl.YppcServiceImpl.saveDj(YppcServiceImpl.java:171)
at com.appcenter.bcls.ypgl.service.impl.YppcServiceImpl.saveDj(YppcServiceImpl.java:38)
at com.appcenter.bcls.clgl.action.YppcAction.handleYppc(YppcAction.java:181)
at sun.reflect.GeneratedMethodAccessor7606.invoke(Unknown Source)
at sun.reflect.DelegatingMethodAccessorImpl.invoke(DelegatingMethodAccessorImpl.java:25)
at java.lang.reflect.Method.invoke(Method.java:597)
at com.opensymphony.xwork2.DefaultActionInvocation.invokeAction(DefaultActionInvocation.java:450)
at com.opensymphony.xwork2.DefaultActionInvocation.invokeActionOnly(DefaultActionInvocation.java:289)
at com.opensymphony.xwork2.DefaultActionInvocation.invoke(DefaultActionInvocation.java:252)
at com.opensymphony.xwork2.interceptor.PrepareInterceptor.doIntercept(PrepareInterceptor.java:171)
at com.opensymphony.xwork2.interceptor.MethodFilterInterceptor.intercept(MethodFilterInterceptor.java:98)
at com.opensymphony.xwork2.DefaultActionInvocation.invoke(DefaultActionInvocation.java:246)
at com.appcenter.cp.component.web.struts2.interceptor.PrescriptionAnalysisInterceptor.intercept(PrescriptionAnalysisInterceptor.java:49)
at com.opensymphony.xwork2.DefaultActionInvocation.invoke(DefaultActionInvocation.java:246)
at com.appcenter.cp.component.web.struts2.interceptor.SessionVOInterceptor.intercept(SessionVOInterceptor.java:25)
at com.opensymphony.xwork2.DefaultActionInvocation.invoke(DefaultActionInvocation.java:246)
at com.opensymphony.xwork2.interceptor.ParametersInterceptor.doIntercept(ParametersInterceptor.java:239)
at com.opensymphony.xwork2.interceptor.MethodFilterInterceptor.intercept(MethodFilterInterceptor.java:98)
at com.opensymphony.xwork2.DefaultActionInvocation.invoke(DefaultActionInvocation.java:246)
at org.apache.struts2.interceptor.FileUploadInterceptor.intercept(FileUploadInterceptor.java:252)
at com.opensymphony.xwork2.DefaultActionInvocation.invoke(DefaultActionInvocation.java:246)
at com.appcenter.cp.component.web.struts2.interceptor.SysLogInterceptor.intercept(SysLogInterceptor.java:80)
at com.opensymphony.xwork2.DefaultActionInvocation.invoke(DefaultActionInvocation.java:246)
at com.appcenter.cp.component.web.struts2.interceptor.RequestCacheInterceptor.intercept(RequestCacheInterceptor.java:22)
at com.opensymphony.xwork2.DefaultActionInvocation.invoke(DefaultActionInvocation.java:246)
at com.appcenter.cp.component.web.struts2.interceptor.BusinessExceptionMappingInterceptor.intercept(BusinessExceptionMappingInterceptor.java:42)
at com.opensymphony.xwork2.DefaultActionInvocation.invoke(DefaultActionInvocation.java:246)
at com.appcenter.cp.module.token.interceptor.TokenInterceptor.intercept(TokenInterceptor.java:49)
at com.opensymphony.xwork2.DefaultActionInvocation.invoke(DefaultActionInvocation.java:246)
at com.opensymphony.xwork2.interceptor.TimerInterceptor.intercept(TimerInterceptor.java:120)
at com.opensymphony.xwork2.DefaultActionInvocation.invoke(DefaultActionInvocation.java:246)
at net.bull.javamelody.StrutsInterceptor.intercept(StrutsInterceptor.java:68)
at com.opensymphony.xwork2.DefaultActionInvocation.invoke(DefaultActionInvocation.java:246)
at org.apache.struts2.impl.StrutsActionProxy.execute(StrutsActionProxy.java:54)
at org.apache.struts2.dispatcher.Dispatcher.serviceAction(Dispatcher.java:563)
at org.apache.struts2.dispatcher.ng.ExecuteOperations.executeAction(ExecuteOperations.java:77)
at org.apache.struts2.dispatcher.ng.filter.StrutsPrepareAndExecuteFilter.doFilter(StrutsPrepareAndExecuteFilter.java:99)
at org.apache.catalina.core.ApplicationFilterChain.internalDoFilter(ApplicationFilterChain.java:280)
at org.apache.catalina.core.ApplicationFilterChain.doFilter(ApplicationFilterChain.java:248)
at com.appcenter.cp.component.web.filter.SessionVOFilter.doFilter(SessionVOFilter.java:36)
at org.apache.catalina.core.ApplicationFilterChain.internalDoFilter(ApplicationFilterChain.java:280)
at org.apache.catalina.core.ApplicationFilterChain.doFilter(ApplicationFilterChain.java:248)
at com.appcenter.cp.component.web.filter.HttpAppserverInjectFilter.doFilter(HttpAppserverInjectFilter.java:35)
at org.apache.catalina.core.ApplicationFilterChain.internalDoFilter(ApplicationFilterChain.java:280)
at org.apache.catalina.core.ApplicationFilterChain.doFilter(ApplicationFilterChain.java:248)
at com.appcenter.cp.component.monitor.RequestFilterInterceptor.doFilter(RequestFilterInterceptor.java:55)
at org.apache.catalina.core.ApplicationFilterChain.internalDoFilter(ApplicationFilterChain.java:280)
at org.apache.catalina.core.ApplicationFilterChain.doFilter(ApplicationFilterChain.java:248)
at org.springframework.security.web.FilterChainProxy$VirtualFilterChain.doFilter(FilterChainProxy.java:311)
at org.springframework.security.web.access.intercept.FilterSecurityInterceptor.invoke(FilterSecurityInterceptor.java:116)
at org.springframework.security.web.access.intercept.FilterSecurityInterceptor.doFilter(FilterSecurityInterceptor.java:83)
at org.springframework.security.web.FilterChainProxy$VirtualFilterChain.doFilter(FilterChainProxy.java:323)
at org.springframework.security.web.access.ExceptionTranslationFilter.doFilter(ExceptionTranslationFilter.java:113)
at org.springframework.security.web.FilterChainProxy$VirtualFilterChain.doFilter(FilterChainProxy.java:323)
at org.springframework.security.web.session.SessionManagementFilter.doFilter(SessionManagementFilter.java:101)
at org.springframework.security.web.FilterChainProxy$VirtualFilterChain.doFilter(FilterChainProxy.java:323)
at org.springframework.security.web.authentication.AnonymousAuthenticationFilter.doFilter(AnonymousAuthenticationFilter.java:113)
at org.springframework.security.web.FilterChainProxy$VirtualFilterChain.doFilter(FilterChainProxy.java:323)
at org.springframework.security.web.servletapi.SecurityContextHolderAwareRequestFilter.doFilter(SecurityContextHolderAwareRequestFilter.java:54)
at org.springframework.security.web.FilterChainProxy$VirtualFilterChain.doFilter(FilterChainProxy.java:323)
at org.springframework.security.web.savedrequest.RequestCacheAwareFilter.doFilter(RequestCacheAwareFilter.java:45)
at org.springframework.security.web.FilterChainProxy$VirtualFilterChain.doFilter(FilterChainProxy.java:323)
at org.springframework.security.web.authentication.AbstractAuthenticationProcessingFilter.doFilter(AbstractAuthenticationProcessingFilter.java:182)
at org.springframework.security.web.FilterChainProxy$VirtualFilterChain.doFilter(FilterChainProxy.java:323)
at org.jasig.cas.client.session.SingleSignOutFilter.doFilter(SingleSignOutFilter.java:76)
at org.springframework.security.web.FilterChainProxy$VirtualFilterChain.doFilter(FilterChainProxy.java:323)
at org.springframework.security.web.authentication.logout.LogoutFilter.doFilter(LogoutFilter.java:105)
at org.springframework.security.web.FilterChainProxy$VirtualFilterChain.doFilter(FilterChainProxy.java:323)
at org.springframework.security.web.authentication.logout.LogoutFilter.doFilter(LogoutFilter.java:105)
at org.springframework.security.web.FilterChainProxy$VirtualFilterChain.doFilter(FilterChainProxy.java:323)
at org.springframework.security.web.context.SecurityContextPersistenceFilter.doFilter(SecurityContextPersistenceFilter.java:87)
at org.springframework.security.web.FilterChainProxy$VirtualFilterChain.doFilter(FilterChainProxy.java:323)
at com.appcenter.cp.component.web.filter.SecuritySessionCheckFilter.doFilter(SecuritySessionCheckFilter.java:55)
at org.springframework.security.web.FilterChainProxy$VirtualFilterChain.doFilter(FilterChainProxy.java:323)
at org.springframework.security.web.FilterChainProxy.doFilter(FilterChainProxy.java:173)
at org.springframework.web.filter.DelegatingFilterProxy.invokeDelegate(DelegatingFilterProxy.java:346)
at org.springframework.web.filter.DelegatingFilterProxy.doFilter(DelegatingFilterProxy.java:259)
at com.appcenter.cp.component.web.filter.SpringSecuritySupportedFilter.doFilter(SpringSecuritySupportedFilter.java:41)
at org.apache.catalina.core.ApplicationFilterChain.internalDoFilter(ApplicationFilterChain.java:280)
at org.apache.catalina.core.ApplicationFilterChain.doFilter(ApplicationFilterChain.java:248)
at org.springframework.web.filter.CharacterEncodingFilter.doFilterInternal(CharacterEncodingFilter.java:88)
at org.springframework.web.filter.OncePerRequestFilter.doFilter(OncePerRequestFilter.java:76)
at org.apache.catalina.core.ApplicationFilterChain.internalDoFilter(ApplicationFilterChain.java:280)
at org.apache.catalina.core.ApplicationFilterChain.doFilter(ApplicationFilterChain.java:248)
at org.apache.catalina.core.StandardWrapperValve.invoke(StandardWrapperValve.java:275)
at org.apache.catalina.core.StandardContextValve.invoke(StandardContextValve.java:161)
at org.jboss.as.web.security.SecurityContextAssociationValve.invoke(SecurityContextAssociationValve.java:153)
at org.apache.catalina.core.StandardHostValve.invoke(StandardHostValve.java:155)
at org.apache.catalina.valves.ErrorReportValve.invoke(ErrorReportValve.java:102)
at org.apache.catalina.core.StandardEngineValve.invoke(StandardEngineValve.java:109)
at org.apache.catalina.connector.CoyoteAdapter.service(CoyoteAdapter.java:368)
at org.apache.coyote.http11.Http11Processor.process(Http11Processor.java:877)
at org.apache.coyote.http11.Http11Protocol$Http11ConnectionHandler.process(Http11Protocol.java:671)
at org.apache.tomcat.util.net.JIoEndpoint$SocketProcessor.run(JIoEndpoint.java:518)
at org.jboss.threads.SimpleDirectExecutor.execute(SimpleDirectExecutor.java:33)
at org.jboss.threads.QueueExecutor.runTask(QueueExecutor.java:801)
at org.jboss.threads.QueueExecutor.access$100(QueueExecutor.java:45)
at org.jboss.threads.QueueExecutor$Worker.run(QueueExecutor.java:842)
at java.lang.Thread.run(Thread.java:662)
at org.jboss.threads.JBossThread.run(JBossThread.java:122)
Caused by: java.sql.SQLException: Invalid column type: 1111
at oracle.jdbc.driver.OracleStatement.getInternalType(OracleStatement.java:3900)
at oracle.jdbc.driver.OraclePreparedStatement.setNullCritical(OraclePreparedStatement.java:4406)
at oracle.jdbc.driver.OraclePreparedStatement.setNull(OraclePreparedStatement.java:4388)
at oracle.jdbc.driver.OraclePreparedStatementWrapper.setNull(OraclePreparedStatementWrapper.java:1281)
at org.apache.commons.dbcp.DelegatingPreparedStatement.setNull(DelegatingPreparedStatement.java:108)
at org.apache.commons.dbcp.DelegatingPreparedStatement.setNull(DelegatingPreparedStatement.java:108)
at sun.reflect.GeneratedMethodAccessor665.invoke(Unknown Source)
at sun.reflect.DelegatingMethodAccessorImpl.invoke(DelegatingMethodAccessorImpl.java:25)
at java.lang.reflect.Method.invoke(Method.java:597)
at net.bull.javamelody.JdbcWrapper$StatementInvocationHandler.invoke(JdbcWrapper.java:146)
at net.bull.javamelody.JdbcWrapper$DelegatingInvocationHandler.invoke(JdbcWrapper.java:271)
at com.sun.proxy.$Proxy309.setNull(Unknown Source)
at org.apache.ibatis.type.BaseTypeHandler.setParameter(BaseTypeHandler.java:39)
at org.apache.ibatis.scripting.defaults.DefaultParameterHandler.setParameters(DefaultParameterHandler.java:77)
at org.apache.ibatis.executor.statement.PreparedStatementHandler.parameterize(PreparedStatementHandler.java:77)
at org.apache.ibatis.executor.statement.RoutingStatementHandler.parameterize(RoutingStatementHandler.java:58)
at org.apache.ibatis.executor.SimpleExecutor.prepareStatement(SimpleExecutor.java:71)
at org.apache.ibatis.executor.SimpleExecutor.doUpdate(SimpleExecutor.java:44)
at org.apache.ibatis.executor.BaseExecutor.update(BaseExecutor.java:100)
at org.apache.ibatis.executor.CachingExecutor.update(CachingExecutor.java:75)
at sun.reflect.GeneratedMethodAccessor692.invoke(Unknown Source)
at sun.reflect.DelegatingMethodAccessorImpl.invoke(DelegatingMethodAccessorImpl.java:25)
at java.lang.reflect.Method.invoke(Method.java:597)
at org.apache.ibatis.plugin.Plugin.invoke(Plugin.java:59)
at com.sun.proxy.$Proxy308.update(Unknown Source)
at sun.reflect.GeneratedMethodAccessor692.invoke(Unknown Source)
at sun.reflect.DelegatingMethodAccessorImpl.invoke(DelegatingMethodAccessorImpl.java:25)
at java.lang.reflect.Method.invoke(Method.java:597)
at org.apache.ibatis.plugin.Invocation.proceed(Invocation.java:46)
at com.appcenter.cp.config.service.impl.FillSqlInterceptor.intercept(FillSqlInterceptor.java:59)
at org.apache.ibatis.plugin.Plugin.invoke(Plugin.java:57)
at com.sun.proxy.$Proxy308.update(Unknown Source)
at org.apache.ibatis.session.defaults.DefaultSqlSession.update(DefaultSqlSession.java:148)
at org.apache.ibatis.session.defaults.DefaultSqlSession.insert(DefaultSqlSession.java:137)
at sun.reflect.GeneratedMethodAccessor1159.invoke(Unknown Source)
at sun.reflect.DelegatingMethodAccessorImpl.invoke(DelegatingMethodAccessorImpl.java:25)
at java.lang.reflect.Method.invoke(Method.java:597)
at org.mybatis.spring.SqlSessionTemplate$SqlSessionInterceptor.invoke(SqlSessionTemplate.java:354)
... 105 more
- 首先,MyBatis生成插入语句时,需要获取每个字段的vlaue和jdbcType。
- value通过参数传入,jdbcType则来自在Mapper中的显式声明。
- 假如某字段的value为null,Mapper中也未为其声明jdbcType,MyBatis将从org.apache.ibatis.session.Configuration对象中的jdbcTypeForNull拿来作为当前字段的jdbcType,而jdbcTypeForNull的默认值为,JdbcType.OTHER。
- 将这个JdbcType.OTHER传入后续的映射逻辑,由于Oracle驱动中,没有与之对应的映射关系,所以,就会报错。
- 若预判某字段可能为null,则需要在Mapper的SQL中显式声明其jdbcType。
可以以此方法为入口(带3个问号的行注释,代表主要方法,会在下文一并贴出)
org.apache.ibatis.scripting.defaults.DefaultParameterHandler#setParameters
public void setParameters(PreparedStatement ps) throws SQLException {
ErrorContext.instance().activity("setting parameters").object(this.mappedStatement.getParameterMap().getId());
List<ParameterMapping> parameterMappings = this.boundSql.getParameterMappings();
if (parameterMappings != null) {
MetaObject metaObject = this.parameterObject == null ? null : this.configuration.newMetaObject(this.parameterObject);
for(int i = 0; i < parameterMappings.size(); ++i) {
ParameterMapping parameterMapping = (ParameterMapping)parameterMappings.get(i);
if (parameterMapping.getMode() != ParameterMode.OUT) {
String propertyName = parameterMapping.getProperty();
Object value;
if (this.boundSql.hasAdditionalParameter(propertyName)) {
value = this.boundSql.getAdditionalParameter(propertyName);
} else if (this.parameterObject == null) {
value = null;
} else if (this.typeHandlerRegistry.hasTypeHandler(this.parameterObject.getClass())) {
value = this.parameterObject;
} else {
value = metaObject == null ? null : metaObject.getValue(propertyName);
}
TypeHandler typeHandler = parameterMapping.getTypeHandler();
// 1.从Mapper中获取当前字段的jdbcType
JdbcType jdbcType = parameterMapping.getJdbcType();
// 2.value为null,且Mapper中的jdbcType也为null(一般是未声明),则获取configeration中的jdbcTypeForNull
if (value == null && jdbcType == null) {
jdbcType = this.configuration.getJdbcTypeForNull(); // ???
}
typeHandler.setParameter(ps, i + 1, value, jdbcType); // ???
}
}
}
}
org.apache.ibatis.session.Configuration#jdbcTypeForNull
public Configuration() {
...
this.localCacheScope = LocalCacheScope.SESSION;
// 无参构造器中,给jdbcTypeForNull设置默认值,其他类型
this.jdbcTypeForNull = JdbcType.OTHER; // ???
this.lazyLoadTriggerMethods = new HashSet(Arrays.asList("equals", "clone", "hashCode", "toString"));
...
}
org.apache.ibatis.type.JdbcType#OTHER
public enum JdbcType {
...
NULL(0),
// 其他类型的枚举项
OTHER(1111),
BLOB(2004),
CLOB(2005)
...
}
org.apache.ibatis.type.BaseTypeHandler#setParameter
public void setParameter(PreparedStatement ps, int i, T parameter, JdbcType jdbcType) throws SQLException {
if (parameter == null) {
if (jdbcType == null) { // 此时jdbcType是OTHER,故不会走这个分支
throw new TypeException("JDBC requires that the JdbcType must be specified for all nullable parameters.");
}
try {
ps.setNull(i, jdbcType.TYPE_CODE); // ???
} catch (SQLException var6) {
throw new TypeException("Error setting null for parameter #" + i + " with JdbcType " + jdbcType + " . " + "Try setting a different JdbcType for this parameter or a different jdbcTypeForNull configuration property. " + "Cause: " + var6, var6);
}
} else {
this.setNonNullParameter(ps, i, parameter, jdbcType);
}
}
以Oracle的jdbc实现为例,
jdbcType和数据库厂商的字段类型,都是以数字编码来表示的,于是jdbc标准和厂商之间就需要实现映射;以下逻辑就是为了完成MyBatis中定义的jdbcType向Oracle数据类型的映射。
oracle.jdbc.driver.OraclePreparedStatement#setNull(int, int)
public void setNull(int var1, int var2) throws SQLException {
synchronized(this.connection) {
this.setNullCritical(var1, var2); // ???
}
}
oracle.jdbc.driver.OraclePreparedStatement#setNullCritical
void setNullCritical(int var1, int var2) throws SQLException {
int var3 = var1 - 1;
SQLException var4;
if (var3 >= 0 && var1 <= this.numberOfBindPositions) {
var4 = null;
int var5 = this.getInternalType(var2); // ???
SQLException var6;
Binder var7;
switch(var5) {
case 1:
case 8:
case 96:
case 995:
var7 = this.theVarcharNullBinder;
this.currentRowCharLens[var3] = 1;
break;
case 6:
var7 = this.theVarnumNullBinder;
break;
case 12:
var7 = this.theDateNullBinder;
break;
case 23:
case 24:
var7 = this.theRawNullBinder;
break;
case 100:
var7 = this.theBinaryFloatNullBinder;
break;
case 101:
var7 = this.theBinaryDoubleNullBinder;
break;
case 102:
case 998:
default:
var6 = DatabaseError.createSqlException(this.getConnectionDuringExceptionHandling(), 23, "sqlType=" + var2);
var6.fillInStackTrace();
throw var6;
case 104:
var7 = this.getRowidNullBinder(var3);
break;
case 109:
case 111:
var6 = DatabaseError.createSqlException(this.getConnectionDuringExceptionHandling(), 4, "sqlType=" + var2);
var6.fillInStackTrace();
throw var6;
case 112:
var7 = this.theClobNullBinder;
break;
case 113:
var7 = this.theBlobNullBinder;
break;
case 114:
var7 = this.theBfileNullBinder;
break;
case 180:
var7 = this.theTimestampNullBinder;
break;
case 181:
var7 = this.theTSTZNullBinder;
break;
case 182:
var7 = this.theIntervalYMNullBinder;
break;
case 183:
var7 = this.theIntervalDSNullBinder;
break;
case 231:
var7 = this.theTSLTZNullBinder;
break;
case 999:
var7 = this.theFixedCHARNullBinder;
}
this.currentRowBinders[var3] = var7;
} else {
var4 = DatabaseError.createSqlException(this.getConnectionDuringExceptionHandling(), 3);
var4.fillInStackTrace();
throw var4;
}
}
oracle.jdbc.driver.OracleStatement#getInternalType
int getInternalType(int var1) throws SQLException {
boolean var2 = false;
short var4;
switch(var1) {
case -104:
var4 = 183;
break;
case -103:
var4 = 182;
break;
case -102:
var4 = 231;
break;
case -101:
var4 = 181;
break;
case -100:
case 93:
var4 = 180;
break;
case -16:
case -1:
var4 = 8;
break;
case -15:
case -9:
case 12:
var4 = 1;
break;
case -14:
var4 = 998;
break;
case -13:
var4 = 114;
break;
case -10:
var4 = 102;
break;
case -8:
var4 = 104;
break;
case -7:
case -6:
case -5:
case 2:
case 3:
case 4:
case 5:
case 6:
case 7:
case 8:
var4 = 6;
break;
case -4:
var4 = 24;
break;
case -3:
case -2:
var4 = 23;
break;
case 0:
var4 = 995;
break;
case 1:
var4 = 96;
break;
case 70:
var4 = 1;
break;
case 91:
case 92:
var4 = 12;
break;
case 100:
var4 = 100;
break;
case 101:
var4 = 101;
break;
case 999:
var4 = 999;
break;
case 2002:
case 2003:
case 2007:
case 2008:
var4 = 109;
break;
case 2004:
var4 = 113;
break;
case 2005:
case 2011:
var4 = 112;
break;
case 2006:
var4 = 111;
break;
default:
SQLException var3 = DatabaseError.createSqlException(this.getConnectionDuringExceptionHandling(), 4, Integer.toString(var1));
var3.fillInStackTrace();
throw var3;
}
return var4;
}
学习使我充实,分享给我快乐!

浙公网安备 33010602011771号