【问题标题】:Kotlin EJB with Java Interface throw UndeclaredThrowableException带有 Java 接口的 Kotlin EJB 抛出 UndeclaredThrowableException
【发布时间】:2017-08-16 06:26:29
【问题描述】:

Java 接口:

public interface IUserSettingManager {

        UserSettingApi updateSetting(Long userId, UserSetting userSettingNew) throws FailUpdateUserSettingException;
    }

Kotlin ejb:

@Stateless

@Local(IUserSettingManager::class)

open class UserSettingManager : DataManager(), IUserSettingManager {

    private companion object {
        private val LOG = LoggerFactory.getLogger(UserSettingManager::class.java)
    }

        @Throws(FailUpdateUserSettingException::class)
        private fun validate(userSetting: UserSetting) {
            if (userSetting.avatar?.length ?: 0 > DBConstant.UUID_VARCHAR_SIZE) {
                throw FailUpdateUserSettingException("avatar length")
            }
        }

        @Throws(FailUpdateUserSettingException::class)
        override fun updateSetting(userId: Long, userSettingNew: UserSetting): UserSettingApi {
            val logger = LOG.silentEnter("updateSetting")

            try {
                validate(userSettingNew)

                .....

            } catch (ex: Exception) {
                val msg = "userId:$userId, user setting:$userSettingNew"

                when (ex) {
                    is FailUpdateUserSettingException -> {
                        logger.debug("$msg, ex:$ex")
                        throw ex
                    }
                    else -> {
                        logger.error(msg, ex)
                        throw FailUpdateUserSettingException(ex.toString())
                    }
                }
            }
        }
    }

带有异常的 Java 类:

公共类 FailUpdateUserSettingException 扩展异常 {

        public FailUpdateUserSettingException() {
this(error);

    }

}

当尝试使用不正确的数据调用 ejb 时,得到异常 UndeclaredThrowableException,结果事务滚动

Caused by: java.lang.reflect.UndeclaredThrowableException
    at org.jboss.invocation.InitialInterceptor.processInvocation(InitialInterceptor.java:34)
    at org.jboss.invocation.InterceptorContext.proceed(InterceptorContext.java:340)
    at org.jboss.invocation.ChainedInterceptor.processInvocation(ChainedInterceptor.java:61)
    at org.jboss.as.ee.component.interceptors.ComponentDispatcherInterceptor.processInvocation(ComponentDispatcherInterceptor.java:52)
    at org.jboss.invocation.InterceptorContext.proceed(InterceptorContext.java:340)
    at org.jboss.as.ejb3.component.interceptors.NonPooledEJBComponentInstanceAssociatingInterceptor.processInvocation(NonPooledEJBComponentInstanceAssociatingInterceptor.java:59) [wildfly-ejb3-10.0.0.Final.jar:10.0.0.Final]
    at org.jboss.invocation.InterceptorContext.proceed(InterceptorContext.java:340)
    at org.jboss.as.ejb3.tx.CMTTxInterceptor.invokeInCallerTx(CMTTxInterceptor.java:254) [wildfly-ejb3-10.0.0.Final.jar:10.0.0.Final]
    ... 137 more
Caused by: com.pay.utils.shared.exception.user.FailUpdateUserSettingException: Fail update user setting. avatar length
    at com.pay.manager.UserSettingManager.validate(UserSettingManager.kt:xx)
    at com.pay.manager.UserSettingManager.updateSetting(UserSettingManager.kt:xx)
    at com.pay.manager.UserSettingManager.updateSetting(UserSettingManager.kt:xx)


.....

结果

javax.ejb.EJBTransactionRolledbackException

【问题讨论】:

  • 如何避免这个问题?如果函数是自己编写的,那么解决方案就简单多了。是的,声明该函数将抛出一个检查异常。例如:@Throws(ParseException::class) fun convertToDate(){/**/} 不适合我
  • 为什么不适合你?
  • fun validate throw UndeclaredThrowableException,虽然我写了@Throws注解
  • 你应该注意到UndeclaredThrowableException是由jboss而不是你的代码抛出的,这意味着你的代码是好的。

标签: ejb kotlin


【解决方案1】:

我没有看到任何远程方法调用或任何序列化,这是此类问题的常见原因,但它可能是类加载器问题吗? Kotlin 代码实例化的类是从不同的类加载器加载的,而不是 JBoss 检查的类,因此它被视为无法识别的 throwable?

我不确定如何检查。 EJB 容器中的类加载器策略可能 - parent-first vs parent-last?

如果您将 Kotlin 代码替换为始终只是从私有 validate() 方法中抛出该异常的 Java 版本,会发生什么行为,只是为了看看这是否会有所不同?

你用的是什么JDK版本、什么Kotlin版本、什么JBoss版本?

【讨论】:

  • WildFly Full 10.0.0.Final(WildFly Core 2.0.10.Final),java版本“1.8.0_91,kotlin 1.0.6
  • 您的 Java 版本和 Kotlin 版本都已过期。我建议至少更新到 Kotlin 1.1.4 您是否按照我的建议尝试用 Java 类替换代码?那有类似的问题吗?
  • 如果将 ejb 接口从 java 更改为 kotlin
  • 如果您怀疑 Kotlin 以及它如何实现 Java 接口存在问题,请先升级到 Kotlin 1.1.4 看是否解决了问题,如果没有,请创建演示问题的代码中的最小示例,作为具有最少示例的自包含项目,因此 IntelliJ 的 Kotlin 团队可以更轻松地对其进行调查。
  • Kotlin 1.1.4 没有帮助
猜你喜欢
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 2013-05-21
  • 2013-03-14
  • 2017-03-14
  • 1970-01-01
  • 2023-03-31
  • 1970-01-01
相关资源
最近更新 更多