Activiti5.19查询报错[java.sql.SQLSyntaxErrorException: ORA-00936: 缺失表达式]

在使用Activiti开发项目过程中,更新Spring、SpringMVC及MyBatis版本后出现查询错误。具体表现为activiti自带查询功能失效,并提示ORA-00936:缺失表达式错误。通过排查发现问题源于MyBatis版本升级至3.3.0,回滚至3.2.6后问题解决。

摘要生成于 C知道 ,由 DeepSeek-R1 满血版支持, 前往体验 >

一.问题

今天用activiti新做一个项目,直接复制之前的代码,然后建数据库,随手把Spring,Spring MVC和Mybatis等版本升级了一下,问题就出现了.

所有activiti自带的查询都无法使用,全部报错如下

org.springframework.web.util.NestedServletException: Request processing failed; nested exception is org.apache.ibatis.exceptions.PersistenceException: 
### Error querying database.  Cause: java.sql.SQLSyntaxErrorException: ORA-00936: 缺失表达式

### The error may exist in org/activiti/db/mapping/entity/Task.xml
### The error may involve org.activiti.engine.impl.persistence.entity.TaskEntity.selectTaskByQueryCriteria-Inline
### The error occurred while setting parameters
### SQL: select * from ( select a.*, ROWNUM rnum from (     select distinct RES.*              from ACT_RU_TASK RES                                          inner join ACT_RE_PROCDEF D on RES.PROC_DEF_ID_ = D.ID_                        WHERE  RES.ASSIGNEE_ = ?                                                                                                                                                                                   and D.KEY_ = ?                                                                                                                                                                         and RES.SUSPENSION_STATE_ = 1                order by  order by RES.ID_ desc, RES.CREATE_TIME_ desc         ) a where ROWNUM < ?) where rnum  >= ?
### Cause: java.sql.SQLSyntaxErrorException: ORA-00936: 缺失表达式

    org.springframework.web.servlet.FrameworkServlet.processRequest(FrameworkServlet.java:981)
    org.springframework.web.servlet.FrameworkServlet.doGet(FrameworkServlet.java:860)
    javax.servlet.http.HttpServlet.service(HttpServlet.java:622)
    org.springframework.web.servlet.FrameworkServlet.service(FrameworkServlet.java:845)
    javax.servlet.http.HttpServlet.service(HttpServlet.java:729)
    org.apache.tomcat.websocket.server.WsFilter.doFilter(WsFilter.java:52)
    org.springframework.web.filter.CharacterEncodingFilter.doFilterInternal(CharacterEncodingFilter.java:121)
    org.springframework.web.filter.OncePerRequestFilter.doFilter(OncePerRequestFilter.java:107)

想了半天终于想起来了,之前的项目用的mybatis是3.2.6版本的,在这个项目里升级到3.3.0版本,问题可能出在这里 
赶紧回滚到3.2.6版本,果然就解决了….真是坑爹

<think>嗯,用户提供了两段日志记录,显示同一个定时任务在短时间内被多次触发,尽管已经使用了@DisallowConcurrentExecution注解,并且cron表达式是0/5 * * * * ?。需要分析可能的原因。 首先,@DisallowConcurrentExecution的作用是防止同一个任务实例并发执行。也就是说,如果前一个任务还没结束,下一个任务不会启动。但是根据日志,任务开始和结束时间间隔大约0.4秒,而两次执行间隔只有1秒左右,明显小于5分钟的cron设置。这说明可能存在多个任务实例或者cron配置错误。 接下来检查cron表达式。用户提供的表达式是“* 0/5 * * * ? *”,这可能有误。正确的每5分钟执行一次的表达式应该是“0 0/5 * * * ?”,即秒字段为0,分钟字段为0/5。而用户的表达式在分钟字段是0/5,但秒字段是*,意味着每分钟的第0秒开始,每5分钟执行一次,但秒字段的通配符会导致每分钟都触发。例如,在08:55:00触发后,下一次会在09:00:00,但由于秒字段是*,实际可能在08:55:00、08:55:01等每秒都触发,这可能解释了任务频繁执行的原因。 另外,可能配置了多个触发器或任务被多次定义,导致即使有注解也无法阻止并发。需要检查是否有重复的定时任务配置。同时,检查应用是否集群部署,而@DisallowConcurrentExecution在集群环境下可能无法跨节点控制,需要分布式锁或其他机制。 最后,确认代码中是否正确应用了注解,是否存在继承或代理问题导致注解未生效。例如,如果方法是非public的,Spring的AOP代理可能无法正确拦截,导致注解失效。 总结可能的原因:cron表达式错误导致任务触发频率高于预期;存在多个任务实例;集群环境的问题;注解未正确应用。</think>根据提供的日志和配置信息,我们可以逐步分析定时任务并发执行的原因: --- ### 一、现象确认 日志显示 **同一个定时任务在5分钟内被多次触发**: ``` 2025-04-02 08:55:00.228 [Worker-8] 开始执行 2025-04-02 08:55:00.635 [Worker-8] 结束执行(耗时约0.4秒) 2025-04-02 08:55:01.016 [Worker-3] 再次开始执行(间隔仅0.38秒) ``` 尽管添加了 `@DisallowConcurrentExecution`,任务仍被并发执行。 --- ### 二、核心原因分析 #### 1. Cron表达式错误 提供的表达式为:`* 0/5 * * * ? *` **问题分析**: - 正确格式应为:`秒 分 时 日 月 周 年`(年可省略) - **错误点**:秒字段为 `*`(每秒触发),分钟字段为 `0/5`(每5分钟) - **实际效果**: - **每5分钟的第0秒开始,每秒触发一次任务** - 例如:在 `08:55:00`、`08:55:01`...`08:59:59` 期间每秒执行,直到下一小时的 `09:00:00` 重新按规则触发 #### 2. 注解作用范围限制 `@DisallowConcurrentExecution` 仅限制 **同一JobDetail实例的并发**,但以下情况会绕过限制: - 配置了多个相同类型的JobDetail - 集群环境下不同节点同时运行任务 - 任务因异常中断后快速重试 --- ### 三、解决方案 #### 1. 修正Cron表达式 **目标**:每5分钟执行一次 **正确表达式**:`0 0/5 * * * ?` - **秒字段**:`0`(每分钟的第0秒触发) - **分钟字段**:`0/5`(每5分钟) #### 2. 检查任务配置 - 确保系统中只定义了一个JobDetail - 在集群环境中补充分布式锁控制(如Redis锁) #### 3. 验证注解生效条件 - 确认任务类已标注 `@DisallowConcurrentExecution` - 确保任务方法为 `public`(避免Spring代理失效) --- ### 四、数学验证(执行间隔) 假设任务执行耗时 $t_{\text{exec}}$,Cron间隔为 $T_{\text{interval}}$,则需满足: $$t_{\text{exec}} < T_{\text{interval}}$$ 在修正后的Cron表达式下: $$T_{\text{interval}} = 5 \text{分钟} = 300\text{秒}$$ 当前任务耗时 $t_{\text{exec}} \approx 0.4\text{秒} \ll 300\text{秒}$,可避免并发。 --- ### 五、总结 | 问题类型 | 具体原因 | 解决方案 | |----------------|---------------------------|---------------------------| | **配置错误** | Cron表达式秒字段为`*` | 修正为`0 0/5 * * * ?` | | **环境因素** | 集群环境未同步 | 添加分布式锁 | | **注解失效** | 方法非public或重复JobDetail| 检查代码和任务配置 |
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值