2010-05-30 2 views
7

'아직도 실행중인'상태로 매달려있는 HardDeadlineExceededError를 치는 많은 수의 작업/서블릿이 있습니다.HardDeadlineExceededError를 처리하기위한 작업 전략

수행중인 작업이 쉽게 29 초 임계 값을 초과 할 수 있습니다.

나는

는 큐에있는 또는 어떤 작업을 확인하는 방법이 있나요 ... 출구 상태지만 적발되고 이러한 예외 핸들러의도를 저장하기 위해 DeadlineExceededException 및 기본 예외를 잡으려고 현재 실행 중입니까?

이 상황을 처리하기위한 다른 전략이 있습니까?

내가 처리하는 상황은 "The Request Timer" 제목 아래에 문서화되어 있습니다. 내가이 상황에 들어갈 때 여기

// task handler for retrieving information from external web services 
protected void doPost(HttpServletRequest req, HttpServletResponse resp) 
throws ServletException, IOException { 

    String taskRetryCountParam = req.getParameter("X-AppEngine-TaskRetryCount"); 
    int taskRetryCount = (taskRetryCountParam==null) ? 0 : Integer.parseInt(taskRetryCountParam); 
      // look up the persistent 'task' and mark it as 'running' 

    logger.info(this.getClass().getName() + ".doPost("+ taskId + ") retryCount=" + taskRestryCount); 


    // Do lots of heavy lifting here 
    // like calling external web services using URL fetch service 
      // and saving the contents into our database. 

      // look up the persistent 'task' and mark it as 'completed' 

    } catch (DeadlineExceededException deadline) { 
     // got this deadline exception 
        // look up the persistent 'task' and mark it as 'errored - try again' 
     logger.warning("DeadlineExceeded Exception while loading content " + deadline.getMessage()); 
     resp.setStatus(HttpServletResponse.SC_REQUEST_TIMEOUT); 

     } 
    } catch (Exception unknown) { 
     // got some unknown exception 
        // look up the persistent 'task' and mark it as 'errored - cancelled' 
     logger.severe("General Exception while loading content exception:" + unknown.getMessage()); 
     resp.setStatus(HttpServletResponse.SC_OK); 

    } 
} 

내 데이터베이스 트랜잭션이 너무 오래가 시간이 올 때 복용하는 것으로 보인다 ... 로그 파일 항목입니다. 당신의 자신의 코드에서 발생하는 경우

W 05-30 12:42PM 09.535 
    Error for /loadstatus 
    com.google.apphosting.runtime.HardDeadlineExceededError: This request (083793d1091c2ca3) started at 2010/05/30 19:41:39.814 UTC and was still executing at 2010/05/30 19:42:09.529 UTC. 
    at java.lang.Object.wait(Native Method) 
    at java.lang.Object.wait(Object.java:443) 
    at java.util.concurrent.TimeUnit.timedWait(Unknown Source) 
    at com.google.apphosting.runtime.AsyncFuture.get(AsyncFuture.java:60) 
    at com.google.apphosting.runtime.ApiProxyImpl$AsyncApiFuture.get(ApiProxyImpl.java:326) 
    at com.google.apphosting.runtime.ApiProxyImpl$AsyncApiFuture.get(ApiProxyImpl.java:217) 
    at com.google.apphosting.runtime.ApiProxyImpl.doSyncCall(ApiProxyImpl.java:131) 
    at com.google.apphosting.runtime.ApiProxyImpl.access$000(ApiProxyImpl.java:43) 
    at com.google.apphosting.runtime.ApiProxyImpl$1.run(ApiProxyImpl.java:104) 
    at com.google.apphosting.runtime.ApiProxyImpl$1.run(ApiProxyImpl.java:102) 
    at java.security.AccessController.doPrivileged(Native Method) 
    at com.google.apphosting.runtime.ApiProxyImpl.makeSyncCall(ApiProxyImpl.java:102) 
    at com.google.apphosting.runtime.ApiProxyImpl.makeSyncCall(ApiProxyImpl.java:43) 
    at com.google.apphosting.api.ApiProxy.makeSyncCall(ApiProxy.java:98) 
    at com.google.appengine.api.datastore.DatastoreApiHelper.makeSyncCall(DatastoreApiHelper.java:58) 
    at com.google.appengine.api.datastore.TransactionImpl.makeSyncCall(TransactionImpl.java:42) 
    at com.google.appengine.api.datastore.TransactionImpl.makeSyncCall(TransactionImpl.java:56) 
    at com.google.appengine.api.datastore.TransactionImpl.commit(TransactionImpl.java:66) 
    at org.datanucleus.store.appengine.DatastoreTransaction.commit(DatastoreTransaction.java:61) 
    at org.datanucleus.store.appengine.DatastoreXAResource.commit(DatastoreXAResource.java:88) 
    at org.datanucleus.transaction.Transaction.commit(Transaction.java:149) 
    at org.datanucleus.transaction.TransactionManager.commit(TransactionManager.java:95) 
    at org.datanucleus.TransactionImpl.internalCommit(TransactionImpl.java:390) 
    at org.datanucleus.TransactionImpl.commit(TransactionImpl.java:258) 
    at org.datanucleus.jdo.JDOTransaction.commit(JDOTransaction.java:83) 
    at org.datanucleus.store.appengine.jdo.DatastoreJDOTransaction.commit(DatastoreJDOTransaction.java:56) 
    <snip> 
    C 05-30 12:42PM 09.629 
    Uncaught exception from servlet 
    com.google.apphosting.runtime.HardDeadlineExceededError: This request (083793d1091c2ca3) started at 2010/05/30 19:41:39.814 UTC and was still executing at 2010/05/30 19:42:09.529 UTC. 
    at java.lang.Object.wait(Native Method) 
    at java.lang.Object.wait(Object.java:443) 
    at java.util.concurrent.TimeUnit.timedWait(Unknown Source) 
    at com.google.apphosting.runtime.AsyncFuture.get(AsyncFuture.java:60) 
    at com.google.apphosting.runtime.ApiProxyImpl$AsyncApiFuture.get(ApiProxyImpl.java:326) 
    at com.google.apphosting.runtime.ApiProxyImpl$AsyncApiFuture.get(ApiProxyImpl.java:217) 
    at com.google.apphosting.runtime.ApiProxyImpl.doSyncCall(ApiProxyImpl.java:131) 
    at com.google.apphosting.runtime.ApiProxyImpl.access$000(ApiProxyImpl.java:43) 
    at com.google.apphosting.runtime.ApiProxyImpl$1.run(ApiProxyImpl.java:104) 
    at com.google.apphosting.runtime.ApiProxyImpl$1.run(ApiProxyImpl.java:102) 
    at java.security.AccessController.doPrivileged(Native Method) 
    at com.google.apphosting.runtime.ApiProxyImpl.makeSyncCall(ApiProxyImpl.java:102) 
    at com.google.apphosting.runtime.ApiProxyImpl.makeSyncCall(ApiProxyImpl.java:43) 
    at com.google.apphosting.api.ApiProxy.makeSyncCall(ApiProxy.java:98) 
    at com.google.appengine.api.datastore.DatastoreApiHelper.makeSyncCall(DatastoreApiHelper.java:58) 
    at com.google.appengine.api.datastore.TransactionImpl.makeSyncCall(TransactionImpl.java:42) 
    at com.google.appengine.api.datastore.TransactionImpl.makeSyncCall(TransactionImpl.java:56) 
    at com.google.appengine.api.datastore.TransactionImpl.commit(TransactionImpl.java:66) 
    at org.datanucleus.store.appengine.DatastoreTransaction.commit(DatastoreTransaction.java:61) 
    at org.datanucleus.store.appengine.DatastoreXAResource.commit(DatastoreXAResource.java:88) 
    at org.datanucleus.transaction.Transaction.commit(Transaction.java:149) 
    at org.datanucleus.transaction.TransactionManager.commit(TransactionManager.java:95) 
    at org.datanucleus.TransactionImpl.internalCommit(TransactionImpl.java:390) 
    at org.datanucleus.TransactionImpl.commit(TransactionImpl.java:258) 
    at org.datanucleus.jdo.JDOTransaction.commit(JDOTransaction.java:83) 
    at org.datanucleus.store.appengine.jdo.DatastoreJDOTransaction.commit(DatastoreJDOTransaction.java:56) 
    <snip> 
    W 05-30 12:42PM 09.644 
    A serious problem was encountered with the process that handled this request, causing it to exit. This is likely to cause a new process to be used for the next request to your application. If you see this message frequently, you may be throwing exceptions during the initialization of your application. (Error code 104) 
+2

[DeadlineExceededException] (http://code.google.com/appengine/docs/java/runtime.html#The_Request_Timer)를 포착 할 수 있어야합니다. 코드를 게시 할 수 있습니까? –

+0

@Matthew : 저는 GAE를하지 않지만,'HardDeadlineExceededError'는'Exception'처럼 들리지는 않습니다. – BalusC

+0

@Balus, 나는 그것이라고 말하지 않았다. 'DeadlineExceededException'과'HardDeadlineExceededError'는 두 가지 다른 것들입니다. 전자는 잡힐 수 있습니다. 후자는 처리 할 수 ​​없으며, 처리하는 데 약 1 초 이상 걸리는 경우 throw됩니다. –

답변

3

http://groups.google.com/group/google-appengine-java/msg/e3fd2b621bb96013

HDEEs는 DEE없이 던져 질 수 있습니다.
일반적으로 시간이 많이 걸리는 것은
으로 돌아 오는 API 호출을 기다리고 있으므로 여기서 시간 제한을 설정하면
DEE로 끝나는 API 호출이 발생합니다. 따라서 API를 자주 호출하지 않으면 HDEE를 직접 공격 할 수 있습니다.

또한 데이터 처리
을 반복 실행하고 결과를 저장하는 장기 실행 작업이 있습니다. 결과를 반환하지 않는 반복자를 사용합니다.
20 초 후 마지막으로 처리 된 개체를 저장 한 다음 처리를 계속하려면
을 새 작업에서 끕니다.

내 원래 솔루션이 DEE를 잡아서 정리했지만이
이 안정적으로 작동을 멈췄습니다.

+0

입력 해 주셔서 감사합니다. Error를 잡아서 HDEE를 추측하고 있습니까? – Stevko

+1

HDEE 오류를 catch 할 수 없습니다. 이러한 catch를 추가 할 수 없으므로 (가능한 경우) 코드가 중지됩니다. 이를 위해 HDEE 이전에 0.5 초 정도 던져야하는 DEE가 있었지만, 자신의 코드 안에 있다면 DEE가 작동하지 않습니다. – Marc

관련 문제