一、NoClassDefFoundError:JobDetailBean not found
1、问题:
2019-02-19 16:15:39,688 | ERROR | ffsa.ripsg_app_ffsa_1.7.5 [296]) | SpringApplicationContextCreator | ? ? | 117 - com.travelsky.jcf.osgi-spring - 1.3.5 | JCF-Spring: failed to create spring context for service (ffsaTimer-1.7.5-BusinessService) in bundle(com.travelsky.pss.ri.ffsa.ripsg_app_ffsa_1.7.5 [296])
org.springframework.beans.factory.BeanCreationException: Error creating bean with name 'ripsg_biz_ffsa_serviceflow_ffsaTimer': Invocation of init method failed; nested exception is org.springframework.beans.factory.CannotLoadBeanClassException: Error loading class [org.springframework.scheduling.quartz.JobDetailBean] for bean with name 'myJobDetail' defined in URL [jar:file:/DATA/app/jcf_1.3.5/psgServer1/data/cache/org.eclipse.osgi/bundles/296/1/.cp/com.travelsky.pss.ri.ripsg_biz_ffsa.ffsaTimer.jar!/META-INF/spring/ffsaTimer_spring.xml]: problem with class file or dependent class; nested exception is java.lang.NoClassDefFoundError: org.springframework.scheduling.quartz.JobDetailBean not found from bundle [com.travelsky.pss.ri.ffsa.ripsg_app_ffsa_1.7.5 [296]]
at org.springframework.beans.factory.support.AbstractAutowireCapableBeanFactory.initializeBean(AbstractAutowireCapableBeanFactory.java:1512)[114:org.springframework.beans:3.2.5.RELEASE]
at org.springframework.beans.factory.support.AbstractAutowireCapableBeanFactory.doCreateBean(AbstractAutowireCapableBeanFactory.java:521)[114:org.springframework.beans:3.2.5.RELEASE]
at org.springframework.beans.factory.support.AbstractAutowireCapableBeanFactory.createBean(AbstractAutowireCapableBeanFactory.java:458)[114:org.springframework.beans:3.2.5.RELEASE]
at org.springframework.beans.factory.support.AbstractBeanFactory$1.getObject(AbstractBeanFactory.java:296)[114:org.springframework.beans:3.2.5.RELEASE]
at org.springframework.beans.factory.support.DefaultSingletonBeanRegistry.getSingleton(DefaultSingletonBeanRegistry.java:223)[114:org.springframework.beans:3.2.5.RELEASE]
at org.springframework.beans.factory.support.AbstractBeanFactory.doGetBean(AbstractBeanFactory.java:293)[114:org.springframework.beans:3.2.5.RELEASE]
at org.springframework.beans.factory.support.AbstractBeanFactory.getBean(AbstractBeanFactory.java:194)[114:org.springframework.beans:3.2.5.RELEASE]
at org.springframework.beans.factory.support.AbstractBeanFactory.doGetBean(AbstractBeanFactory.java:286)[114:org.springframework.beans:3.2.5.RELEASE]
at org.springframework.beans.factory.support.AbstractBeanFactory.getBean(AbstractBeanFactory.java:194)[114:org.springframework.beans:3.2.5.RELEASE]
at org.springframework.beans.factory.support.DefaultListableBeanFactory.preInstantiateSingletons(DefaultListableBeanFactory.java:610)[114:org.springframework.beans:3.2.5.RELEASE]
at org.springframework.context.support.AbstractApplicationContext.finishBeanFactoryInitialization(AbstractApplicationContext.java:932)[116:org.springframework.context:3.2.5.RELEASE]
at org.springframework.context.support.AbstractApplicationContext.refresh(AbstractApplicationContext.java:479)[116:org.springframework.context:3.2.5.RELEASE]
at com.travelsky.jcf.osgi.spring.SpringApplicationContextCreator$2.run(SpringApplicationContextCreator.java:360)[117:com.travelsky.jcf.osgi-spring:1.3.5]
at com.travelsky.jcf.osgi.spring.util.OSGISpringHelper$1.run(OSGISpringHelper.java:57)[117:com.travelsky.jcf.osgi-spring:1.3.5]
at java.lang.Thread.run(Thread.java:745)[:1.7.0_67]
Caused by: org.springframework.beans.factory.CannotLoadBeanClassException: Error loading class [org.springframework.scheduling.quartz.JobDetailBean] for bean with name 'myJobDetail' defined in URL [jar:file:/DATA/app/jcf_1.3.5/psgServer1/data/cache/org.eclipse.osgi/bundles/296/1/.cp/com.travelsky.pss.ri.ripsg_biz_ffsa.ffsaTimer.jar!/META-INF/spring/ffsaTimer_spring.xml]: problem with class file or dependent class; nested exception is java.lang.NoClassDefFoundError: org.springframework.scheduling.quartz.JobDetailBean not found from bundle [com.travelsky.pss.ri.ffsa.ripsg_app_ffsa_1.7.5 [296]]
at org.springframework.beans.factory.support.AbstractBeanFactory.resolveBeanClass(AbstractBeanFactory.java:1284)[114:org.springframework.beans:3.2.5.RELEASE]
at org.springframework.beans.factory.support.AbstractAutowireCapableBeanFactory.predictBeanType(AbstractAutowireCapableBeanFactory.java:575)[114:org.springframework.beans:3.2.5.RELEASE]
at org.springframework.beans.factory.support.AbstractBeanFactory.isFactoryBean(AbstractBeanFactory.java:1350)[114:org.springframework.beans:3.2.5.RELEASE]
at org.springframework.beans.factory.support.DefaultListableBeanFactory.doGetBeanNamesForType(DefaultListableBeanFactory.java:355)[114:org.springframework.beans:3.2.5.RELEASE]
at org.springframework.beans.factory.support.DefaultListableBeanFactory.getBeanNamesForType(DefaultListableBeanFactory.java:334)[114:org.springframework.beans:3.2.5.RELEASE]
at org.springframework.context.support.AbstractApplicationContext.getBeanNamesForType(AbstractApplicationContext.java:1178)[116:org.springframework.context:3.2.5.RELEASE]
at org.apache.camel.spring.CamelContextFactoryBean.getBeanForType(CamelContextFactoryBean.java:177)[119:org.apache.camel.camel-spring:2.10.3]
2、原因:
引入的spring-context-support.jar有两个版本3.2.5和4.2.5
3、解决
在pom中指定3.2.5的版本
二、并发修改异常
报错:
java.util.ConcurrentModificationException
at java.util.ArrayList$Itr.checkForComodification(ArrayList.java:859)
at java.util.ArrayList$Itr.next(ArrayList.java:831)
at com.travelsky.pss.ri.agentmonitor.das.service.FlightWarningResultDBServie.insert(FlightWarningResultDBServie.java:19)
at com.travelsky.pss.ri.agentmonitor.service.FlightWarningCollectionJob$1.run(FlightWarningCollectionJob.java:224)
at java.lang.Thread.run(Thread.java:745)
问题代码:
public void collectFlightWarningData(Boolean isExcute, final Date date,
final ArrayList<FlightWarningRuleInfo> rules,
final CountDownLatch latch,
final int end,
final int start)
throws ParseException, IllegalAccessException,
InvocationTargetException {
if (isExcute && RiCheckUtils.isNotEmpty(rules)) {
new Thread(new Runnable() {
@Override
public void run() {
Thread.currentThread().setName("航班预警子线程:" +
rules.get(0).getFlightWarningRule().getStatisticalTime() + "小时任务");
try {
LOGGER.info(Thread.currentThread().getName() + "开始");
long startTime = System.currentTimeMillis();
FlightWarningRuleInfoVo flightWarningRuleVo = new FlightWarningRuleInfoVo();
initFlightWarningRuleVo(date, flightWarningRuleVo, end, start);
for (FlightWarningRuleInfo flightWarningRuleInfo : rules) {
BeanUtils.copyProperties(flightWarningRuleVo, flightWarningRuleInfo);
List<FlightWarningResult> flightWarningResults = flightWarningCollectionMapper.selectFlightWarningResults(flightWarningRuleVo);
LOGGER.info("匹配规则“"+flightWarningRuleVo.getFlightWarningRule().getId()+":"+
flightWarningRuleVo.getFlightWarningRule().getName()+"”"+flightWarningResults.size()+"条结果");
String recipientEmail = flightWarningRuleInfo.getFlightWarningRule().getRecipientEmail();
String[] emails = recipientEmail.split("/");
if (RiCheckUtils.isNotEmpty(emails)) {
for (int i = 0; i < emails.length; i++) {
String email = emails[i];
if (resultMap.containsKey(email)) {
List<FlightWarningResult> oldList = resultMap.get(email);
oldList.addAll(flightWarningResults);
}else {
if (RiCheckUtils.isNotEmpty(flightWarningResults) && RiCheckUtils.isNotEmpty(email)) {
resultMap.put(email, flightWarningResults);
}
}
}
}
if (RiCheckUtils.isNotEmpty(flightWarningResults)) {
flightWarningResultDBServie.insert(flightWarningResults);
LOGGER.info("匹配规则“"+flightWarningRuleVo.getFlightWarningRule().getId()+":"+
flightWarningRuleVo.getFlightWarningRule().getName()+"”"+"结果入库成功");
}
}
long collectionTime = System.currentTimeMillis() - startTime;
LOGGER.info(Thread.currentThread().getName() + "结束,总共耗时(耗秒)=" + collectionTime);
} catch (Exception e) {
LOGGER.error(rules.get(0).getFlightWarningRule().getStatisticalTime()+"小时任务失败", e);
} finally {
latch.countDown();
}
}
}).start();
}
}
public void insert(List<FlightWarningResult> flightWarningResults){
for (FlightWarningResult flightWarningResult : flightWarningResults) {
flightWarningResult.setId(UUID.randomUUID().toString());
flightWarningResultMapper.insert(flightWarningResult);
}
}
解决:
public void collectFlightWarningData(Boolean isExcute, final Date date,
final ArrayList<FlightWarningRuleInfo> rules,
final CountDownLatch latch,
final int end,
final int start,
final ConcurrentHashMap<String, List<FlightWarningResult>> resultMap)
throws ParseException, IllegalAccessException,
InvocationTargetException {
if (isExcute && RiCheckUtils.isNotEmpty(rules)) {
new Thread(new Runnable() {
@Override
public void run() {
Thread.currentThread().setName("航班预警子线程:" +
rules.get(0).getFlightWarningRule().getStatisticalTime() + "小时任务");
try {
LOGGER.info(Thread.currentThread().getName() + "开始");
long startTime = System.currentTimeMillis();
FlightWarningRuleInfoVo flightWarningRuleVo = new FlightWarningRuleInfoVo();
initFlightWarningRuleVo(date, flightWarningRuleVo, end, start);
for (FlightWarningRuleInfo flightWarningRuleInfo : rules) {
BeanUtils.copyProperties(flightWarningRuleVo, flightWarningRuleInfo);
List<FlightWarningResult> flightWarningResults = flightWarningCollectionMapper.selectFlightWarningResults(flightWarningRuleVo);
LOGGER.info("匹配规则“"+flightWarningRuleVo.getFlightWarningRule().getId()+":"+
flightWarningRuleVo.getFlightWarningRule().getName()+"”"+flightWarningResults.size()+"条结果");
String recipientEmail = flightWarningRuleInfo.getFlightWarningRule().getRecipientEmail();
String[] emails = recipientEmail.split("/");
if (RiCheckUtils.isNotEmpty(emails)) {
for (int i = 0; i < emails.length; i++) {
String email = emails[i];
if (resultMap.containsKey(email)) {
List<FlightWarningResult> oldList = resultMap.get(email);//oldList=list
oldList.addAll(flightWarningResults);//list是线程安全的
}else {
if (RiCheckUtils.isNotEmpty(flightWarningResults) && RiCheckUtils.isNotEmpty(email)) {
List<FlightWarningResult> list = Collections.synchronizedList(new ArrayList<FlightWarningResult>());
list.addAll(flightWarningResults);
resultMap.put(email, list);//并发修改异常:因为map中存的是第一次查询结果的指针,所以第一次查询的结果会被修改 解决:map中存新对象的指针
}
}
}
}
if (RiCheckUtils.isNotEmpty(flightWarningResults)) {
flightWarningResultDBServie.insert(flightWarningResults);
LOGGER.info("匹配规则“"+flightWarningRuleVo.getFlightWarningRule().getId()+":"+
flightWarningRuleVo.getFlightWarningRule().getName()+"”"+"结果入库成功");
}
}
long collectionTime = System.currentTimeMillis() - startTime;
LOGGER.info(Thread.currentThread().getName() + "结束,总共耗时(耗秒)=" + collectionTime);
} catch (Exception e) {
LOGGER.error(rules.get(0).getFlightWarningRule().getStatisticalTime()+"小时任务失败", e);
} finally {
latch.countDown();
}
}
}).start();
}
}
三、spring-boot:下载jar包问题
问题1:The type org.springframework.data.repository.query.QueryLookupStrategy cannot be resolved. It is indirectly referenced from required .class files
问题2:
The type com.fasterxml.jackson.core.JsonProcessingException cannot be resolved. It is indirectly referenced from required .class files
问题3:
Multiple markers at this line
- The import com.fasterxml.jackson.databind.annotation.JsonAppend is
never used
- The import com.fasterxml.jackson cannot be resolved
解决:重新下载包
注:下载jar包是网络经常断开会导致jar包不完整,需要重新下载。
四、ERROR: failed to find conversion function from unknown to text
今天遇到写存储过程遇到的一个小问题,在查询语句中使用到了自定义的数当做列的值,然后想给这一列起一个别名 ,就直接在后面用了 as 别名。
执行存储过程,存储过程报错,ERROR: failed to find conversion function from unknown to text 。意思是没有找到一个将未知 转换成text 的函数。
举例说明:
在以下代码中 ,我们需要用到临时表update_中的三个字段来进行where条件的判断,因为_p_year,_stat_date是存储过程中输入的参数 也包括'00000' ,都是要起别名当做where的条件判断
但是类似这种,直接用的话会报上述错误。
所以需要加 ::text 转换成文本类型 ::int 转换成int类型
UPDATE employment_status e SET cgl=update_.cgl FROM (SELECT temp_.area_code as sfdm, '00000' as yxdm, _p_year as year, --问题出现的地方 _stat_date::text as stat_date, ( ( temp_.rate - _v_avg_province_cgl_score ) / _v_stddev_province_cgl_score * 10 + 50 ) / _v_cgl_rate as cgl FROM ( SELECT inf_.area_code, rate FROM ( SELECT b.yxszsdm, b.byqxdm, 1.0 * num / total AS rate FROM ( SELECT yxszsdm, COUNT (1) AS total FROM graduate_info gra, school_info sch WHERE YEAR = _p_year AND gra.yxdm = sch.code AND sch.build_type_name NOT LIKE '科研机构' GROUP BY yxszsdm ) AS A, ( SELECT yxszsdm, byqxdm, COUNT (1) AS num FROM graduate_info gra, school_info sch WHERE YEAR = _p_year AND gra.yxdm = sch.code AND sch.build_type_name NOT LIKE '科研机构' GROUP BY yxszsdm, byqxdm ) AS b WHERE A .yxszsdm = b.yxszsdm AND byqxdm ='80' ) gra_ RIGHT JOIN ( SELECT DISTINCT u.area_code FROM user_info u, school_info s WHERE u.org_code = s.code AND s.build_type_name != '科研机构' ORDER BY area_code ) inf_ ON gra_.yxszsdm = inf_.area_code ) temp_ )update_ WHERE e.sfdm=update_.sfdm AND e.yxdm=update_.yxdm AND e.stat_date=update_.stat_date AND e.year=update_.year; |
简单例子:
Select * from (select 'string' as Rowname, Data From table) Union all (select 'string2' as Rowname, Data From table) |
期望输出:
Rowname Data
string 53
string2 87
这样的话会报错,需要我们加一个转换函数 ::text 修改后
SELECT 'string'::text AS rowname, data FROM tbl1 UNION ALL SELECT 'string2', data FROM tbl2 |
来源: http://www.cnblogs.com/aima1013/p/7987713.html
五、quartz
1、quartz定时
<?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:context="http://www.springframework.org/schema/context"
xsi:schemaLocation="
http://www.springframework.org/schema/beans http://www.springframework.org/schema/beans/spring-beans.xsd
http://camel.apache.org/schema/spring http://camel.apache.org/schema/spring/camel-spring.xsd
http://www.springframework.org/schema/context http://www.springframework.org/schema/context/spring-context-3.0.xsd">
<import resource="classpath:share_psg.xml" />
<context:component-scan base-package="com.travelsky.pss.ri.autoclear" />
<!-- 定时配置 -->
<bean id="quartzMeta" class="com.travelsky.jcf.camel.extend.QuartzMetaFactoryBean">
<property name="serviceMeta" ref="serviceMeta" />
<!-- 参数all为true时, 所有执行该服务的线程(该线程数即服务入口组件的线程数)都被启动 -->
<!-- 参数all为false时,只有一个线程被启动 -->
<property name="all" value="false" />
</bean>
<bean id="myJobDetail" class="org.springframework.scheduling.quartz.JobDetailBean">
<property name="jobClass">
<value>com.travelsky.jcf.camel.extend.JCFQuartzJobBean</value>
</property>
<property name="jobDataAsMap">
<map>
<entry key="quartzMeta">
<ref bean="quartzMeta" />
</entry>
</map>
</property>
</bean>
<!-- trigger -->
<bean id="myJobTrigger" class="org.springframework.scheduling.quartz.CronTriggerBean">
<property name="jobDetail">
<ref bean="myJobDetail" />
</property>
<!-- 1.7.1 每隔30s触发一次 -->
<property name="cronExpression">
<value>0/30 * * * * ?</value>
</property>
</bean>
<!-- Quartz集群使用JCF数据源 -->
<!-- <bean id="dataSourcequartz" class="com.travelsky.jcf.datasource.DataSourceFactory">
<property name="dsName" value="dataSourcePsg" />
</bean> -->
<bean name="startQuertz" lazy-init="false" autowire="no"
class="org.springframework.scheduling.quartz.SchedulerFactoryBean">
<property name="triggers">
<list>
<ref bean="myJobTrigger" />
</list>
</property>
<!-- Quartz集群配置参数 -->
<!-- <property name="quartzProperties">
<props>
<prop key="org.quartz.jobStore.driverDelegateClass">org.quartz.impl.jdbcjobstore.PostgreSQLDelegate
</prop>
<prop key="org.quartz.jobStore.isClustered">true</prop>
<prop key="org.quartz.scheduler.instanceId">AUTO</prop>
集群中每次检查的时间间隔,单位毫秒
<prop key="org.quartz.jobStore.clusterCheckinInterval">20000</prop>
</props>
</property>
<property name="dataSource" ref="dataSourcequartz" /> -->
<property name="applicationContextSchedulerContextKey" value="applicationContextKey" />
</bean>
</beans>
2、quartz 定时+选主
<bean id="quartzMeta" class="com.travelsky.jcf.camel.extend.QuartzMetaFactoryBean">
<property name="serviceMeta" ref="serviceMeta" />
<!-- 参数all为true时, 所有执行该服务的线程(该线程数即服务入口组件的线程数)都被启动 -->
<!-- 参数all为false时,只有一个线程被启动 -->
<property name="all" value="false" />
</bean>
<bean id="myJobDetail" class="org.springframework.scheduling.quartz.JobDetailBean">
<property name="jobClass">
<value>com.travelsky.jcf.camel.extend.JCFQuartzJobBean</value>
</property>
<property name="jobDataAsMap">
<map>
<entry key="quartzMeta">
<ref bean="quartzMeta" />
</entry>
</map>
</property>
</bean>
<!-- trigger -->
<bean id="myJobTrigger" class="org.springframework.scheduling.quartz.CronTriggerBean">
<property name="jobDetail">
<ref bean="myJobDetail" />
</property>
<!-- 1.7.1 每隔30s触发一次 -->
<property name="cronExpression">
<value>0/30 * * * * ?</value>
</property>
</bean>
<!-- Quartz集群使用JCF数据源 -->
<bean id="dataSourcequartz" class="com.travelsky.jcf.datasource.DataSourceFactory">
<property name="dsName" value="dataSourcePsg" />
</bean>
<bean name="startQuertz" lazy-init="false" autowire="no"
class="org.springframework.scheduling.quartz.SchedulerFactoryBean">
<property name="triggers">
<list>
<ref bean="myJobTrigger" />
</list>
</property>
<!-- Quartz集群配置参数 -->
<property name="quartzProperties">
<props>
<prop key="org.quartz.jobStore.driverDelegateClass">org.quartz.impl.jdbcjobstore.PostgreSQLDelegate
</prop>
<prop key="org.quartz.jobStore.isClustered">true</prop>
<prop key="org.quartz.scheduler.instanceId">AUTO</prop>
<!-- 集群中每次检查的时间间隔,单位毫秒 -->
<prop key="org.quartz.jobStore.clusterCheckinInterval">20000</prop>
</props>
</property>
<property name="dataSource" ref="dataSourcequartz" />
<property name="applicationContextSchedulerContextKey" value="applicationContextKey" />
</bean>
</beans>
六、chm线程不安全场景
if(chm.containsKey(key)){
chm.put(key, value+"s");
}else{
chm.put(key, value);
}
虽然chm的containsKey和put都是原子操作。若能保证key唯一,则使用于多线程。否则,存在线程安全问题,因为:有可能A线程还没有把 key put进去时,B线程已经在进行if 的条件判断了。
chm思想:减小锁粒度。ConcurrentHashMap容器的数据分段存储,每一段数据分配一个Segment(锁),当线程占用其中一个Segment时,其他线程可正常访问
其他段数据。
七、mybatis-inset后,对象中带有id
<!--新增业务条线信息-->
<insert id="addBusinessLine" parameterType="businessLineInfo">
<selectKey resultType="java.lang.Long" keyProperty="id" >
SELECT @@IDENTITY AS id
</selectKey>
insert INTO businessLineInfo (name,leader,member,description,createTime,updateTime)
VALUES (#{name},#{leader},#{member},#{description},#{createTime},#{updateTime})
</insert>