Anupam Gupta
Anupam Gupta

Reputation: 1687

a sleeping Thread is getting interrupted causing loss of connection to db

I am new to Multi-threading in JAVA and am facing a problem. I am getting an exception which says that

java.lang.InterruptedException: sleep interrupted

this follows a loss to connection to db. I am clueless regarding what is going wrong there. It looks like after thread is interrupted, they are being re-initialized but are not getting started..

following is my run method

public void run() {
        LOG.info("Started");
        running = true;
        while (running) {
            Lock readLock = readWriteLock.readLock();
            readLock.lock();
            long loopDelay;
            try {
                loopDelay = executor.execute();
                if (loopDelay > 0) {
                    Thread.sleep(loopDelay);
                }
            } catch (Exception e) {
                LOG.info("Executor Interrupted", e);
                break;
            } finally {
                readLock.unlock();
            }
        }
        LOG.info("Stopped");
    }

possible solution: after going through the link suggested by david I feel the problem here is the same mentioned by David i.e "A thread cannot process an interrupt while it's sleeping." so to fix this I should handle the Interrrupted Exception in a better way i.e as suggesteb by david.

Following is my stack trace.. Can Some one please help me in understanding the issue

    2012-02-03 10:38:09,260   150696427 [taskDiscoveryCallExecutorThread] INFO  (TaskExecutorThread.java:89) - Executor Interrupted
    java.lang.InterruptedException: sleep interrupted
        at java.lang.Thread.sleep(Native Method)
        at com.xyz.abc.backgroundtask.impl.TaskExecutorThread.run(TaskExecutorThread.java:86)
    2012-02-03 10:38:09,261   150696428 [taskDiscoveryCallExecutorThread] INFO  (TaskExecutorThread.java:95) - Stopped
    2012-02-03 10:38:09,261   150696428 [main] INFO  (TaskExecutorThread.java:69) - shutdown
    2012-02-03 10:38:09,262   150696429 [taskRuleExecutorThread] ERROR (JDBCExceptionReporter.java:101) - Cannot get a connection, general error
    2012-02-03 10:38:09,262   150696429 [taskRuleExecutorThread] ERROR (JDBCExceptionReporter.java:101) - Cannot get a connection, general error
    2012-02-03 10:38:09,294   150696461 [taskRuleExecutorThread] DEBUG (EventScope.java:107) - Destroy scope for customer c02c5ac7-8dee-42aa-b344-ff7f7f6894f5
    2012-02-03 10:38:09,294   150696461 [taskRuleExecutorThread] ERROR (TaskExecutor.java:205) - Catch exception
    org.springframework.jdbc.UncategorizedSQLException: Hibernate operation: Cannot open connection; uncategorized SQLException for SQL [???]; SQL state [null]; error code [0]; Cannot get a connection, general error; nested exception is org.apache.commons.dbcp.SQLNestedException: Cannot get a connection, general error
        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.springframework.orm.hibernate3.HibernateAccessor.convertJdbcAccessException(HibernateAccessor.java:424)
        at org.springframework.orm.hibernate3.HibernateAccessor.convertHibernateAccessException(HibernateAccessor.java:410)
        at org.springframework.orm.hibernate3.HibernateTemplate.doExecute(HibernateTemplate.java:411)
        at org.springframework.orm.hibernate3.HibernateTemplate.executeWithNativeSession(HibernateTemplate.java:374)
        at org.springframework.orm.hibernate3.HibernateTemplate.findByCriteria(HibernateTemplate.java:1046)
        at org.springframework.orm.hibernate3.HibernateTemplate.findByCriteria(HibernateTemplate.java:1039)
        at com.xyz.abc.web.dao.RuleDao.loadActive(RuleDao.java:53)
        at com.xyz.abc.web.service.RuleServiceImpl.createRulesByTemplate(RuleServiceImpl.java:39)
        at sun.reflect.NativeMethodAccessorImpl.invoke0(Native Method)
        at sun.reflect.NativeMethodAccessorImpl.invoke(NativeMethodAccessorImpl.java:39)
        at sun.reflect.DelegatingMethodAccessorImpl.invoke(DelegatingMethodAccessorImpl.java:25)
        at java.lang.reflect.Method.invoke(Method.java:597)
        at org.springframework.aop.support.AopUtils.invokeJoinpointUsingReflection(AopUtils.java:309)
        at org.springframework.aop.framework.ReflectiveMethodInvocation.invokeJoinpoint(ReflectiveMethodInvocation.java:183)
        at org.springframework.aop.framework.ReflectiveMethodInvocation.proceed(ReflectiveMethodInvocation.java:150)
        at org.springframework.transaction.interceptor.TransactionInterceptor.invoke(TransactionInterceptor.java:110)
        at org.springframework.aop.framework.ReflectiveMethodInvocation.proceed(ReflectiveMethodInvocation.java:172)
        at org.springframework.aop.framework.JdkDynamicAopProxy.invoke(JdkDynamicAopProxy.java:202)
        at $Proxy60.createRulesByTemplate(Unknown Source)
        at com.xyz.abc.rules.RulesInvoker.checkIsInitialized(RulesInvoker.java:97)
        at com.xyz.abc.rules.RulesInvoker.invokeForEvent(RulesInvoker.java:73)
        at com.xyz.abc.mdp.RabbitMqMessageProcessor.processMessage(RabbitMqMessageProcessor.java:53)
        at sun.reflect.GeneratedMethodAccessor101.invoke(Unknown Source)
        at sun.reflect.DelegatingMethodAccessorImpl.invoke(DelegatingMethodAccessorImpl.java:25)
        at java.lang.reflect.Method.invoke(Method.java:597)
        at org.springframework.util.ReflectionUtils.invokeMethod(ReflectionUtils.java:186)
        at com.xyz.abc.backgroundtask.impl.TaskExecutor.invokeMethod(TaskExecutor.java:156)
        at com.xyz.abc.backgroundtask.impl.TaskExecutor.invokeBean(TaskExecutor.java:139)
        at com.xyz.abc.backgroundtask.impl.TaskExecutor.doExecute(TaskExecutor.java:116)
        at com.xyz.abc.backgroundtask.impl.TaskExecutor.executeTask(TaskExecutor.java:104)
        at com.xyz.abc.backgroundtask.impl.TaskExecutor.access$200(TaskExecutor.java:39)
        at com.xyz.abc.backgroundtask.impl.TaskExecutor$1.doInTransaction(TaskExecutor.java:85)
        at com.xyz.abc.backgroundtask.impl.TaskExecutor$1.doInTransaction(TaskExecutor.java:79)
        at org.springframework.transaction.support.TransactionTemplate.execute(TransactionTemplate.java:130)
        at com.xyz.abc.backgroundtask.impl.TaskExecutor.execute(TaskExecutor.java:79)
        at com.xyz.abc.backgroundtask.impl.TaskExecutorThread.run(TaskExecutorThread.java:84)
    Caused by: org.apache.commons.dbcp.SQLNestedException: Cannot get a connection, general error
        at org.apache.commons.dbcp.PoolingDataSource.getConnection(PoolingDataSource.java:118)
        at org.apache.commons.dbcp.BasicDataSource.getConnection(BasicDataSource.java:1044)
        at org.springframework.orm.hibernate3.LocalDataSourceConnectionProvider.getConnection(LocalDataSourceConnectionProvider.java:81)
        at org.hibernate.jdbc.ConnectionManager.openConnection(ConnectionManager.java:446)
        at org.hibernate.jdbc.ConnectionManager.getConnection(ConnectionManager.java:167)
        at org.hibernate.jdbc.AbstractBatcher.prepareQueryStatement(AbstractBatcher.java:161)
        at org.hibernate.loader.Loader.prepareQueryStatement(Loader.java:1596)
        at org.hibernate.loader.Loader.doQuery(Loader.java:717)
        at org.hibernate.loader.Loader.doQueryAndInitializeNonLazyCollections(Loader.java:270)
        at org.hibernate.loader.Loader.doList(Loader.java:2294)
        at org.hibernate.loader.Loader.listIgnoreQueryCache(Loader.java:2172)
        at org.hibernate.loader.Loader.list(Loader.java:2167)
        at org.hibernate.loader.criteria.CriteriaLoader.list(CriteriaLoader.java:119)
        at org.hibernate.impl.SessionImpl.list(SessionImpl.java:1706)
        at org.hibernate.impl.CriteriaImpl.list(CriteriaImpl.java:347)
        at org.springframework.orm.hibernate3.HibernateTemplate$36.doInHibernate(HibernateTemplate.java:1056)
        at org.springframework.orm.hibernate3.HibernateTemplate$36.doInHibernate(HibernateTemplate.java:1)
        at org.springframework.orm.hibernate3.HibernateTemplate.doExecute(HibernateTemplate.java:406)
        ... 33 more
    Caused by: java.lang.InterruptedException
        at java.lang.Object.wait(Native Method)
        at java.lang.Object.wait(Object.java:485)
        at org.apache.commons.pool.impl.GenericObjectPool.borrowObject(GenericObjectPool.java:1104)
        at org.apache.commons.dbcp.PoolingDataSource.getConnection(PoolingDataSource.java:106)
        ... 50 more
    2012-02-03 10:38:09,399   150696566 [taskRuleExecutorThread] INFO  (TaskExecutor.java:93) - org.springframework.transaction.UnexpectedRollbackException: Transaction rolled back because it has been marked as rollback-only
2012-02-03 10:38:09,399   150696566 [taskRuleExecutorThread] INFO  (TaskExecutorThread.java:89) - Executor Interrupted
java.lang.InterruptedException: sleep interrupted
    at java.lang.Thread.sleep(Native Method)
    at com.xyz.abc.backgroundtask.impl.TaskExecutorThread.run(TaskExecutorThread.java:86)
2012-02-03 10:38:09,399   150696566 [taskRuleExecutorThread] INFO  (TaskExecutorThread.java:95) - Stopped
2012-02-03 10:38:09,400   150696567 [main] INFO  (TaskExecutorThread.java:69) - shutdown
2012-02-03 10:38:09,400   150696567 [taskParatureExecutorThread] INFO  (TaskExecutorThread.java:89) - Executor Interrupted
java.lang.InterruptedException: sleep interrupted
    at java.lang.Thread.sleep(Native Method)
    at com.xyz.abc.backgroundtask.impl.TaskExecutorThread.run(TaskExecutorThread.java:86)
2012-02-03 10:38:09,400   150696567 [taskParatureExecutorThread] INFO  

(TaskExecutorThread.java:95) - Stopped
2012-02-03 10:38:09,400   150696567 [main] INFO  (TaskExecutorThread.java:69) - shutdown

Upvotes: 5

Views: 48687

Answers (4)

Hritik Shinde
Hritik Shinde

Reputation: 1

You may check whether the h2 db lock file survived the server shutdown. The file’s name is ‘<keycloak_dir>/data/h2/keycloakdb.lock.db’.

Remove the file and start the server.

Upvotes: 0

Milan Sheth
Milan Sheth

Reputation: 972

Let's understand with your code:

while (true) {
  // Your logic code
}

What does it do? Nothing, it just spins the CPU endlessly. Can we terminate it? Not in Java. It will only stop when the entire JVM stops, when you hit Ctrl-C. There is no way in Java to terminate a thread unless the thread exits by itself. That’s the principle we have to have in mind, and everything else will just be obvious.

So, how do we stop a thread when we need it to stop?

Here is how it is designed in Java. There is a flag in every thread that we can set from the outside. And the thread may check it occasionally and stop its execution. Voluntarily! Here is how:

Thread loop = new Thread(
  new Runnable() {
    @Override
    public void run() {
      while (true) {
        if (Thread.interrupted()) {
          break;
        }
        // Your logic code
      }
    }
  }
);
loop.start();

Upvotes: 0

Eugene
Eugene

Reputation: 120978

Are you throwing an interrupted Exception somewhere in your code may be to signal that a Thread should stop? Can you provide the code for this method:

com.xyz.abc.backgroundtask.impl.TaskExecutorThread.run

Upvotes: 1

David Schwartz
David Schwartz

Reputation: 182827

A thread cannot process an interrupt while it's sleeping. So you need to catch the exception when the thread comes out of sleep and then process the interrupt. The method is explained well in this answer. Usually it looks like this:

  try
  {
      Thread.sleep(whatever);
  }
  catch (InterruptedException e)
  {
       Thread.currentThread().interrupt(); // restore interrupted status
  }

Upvotes: 19

Related Questions