2009-03-17 4 views
7

Ho un'applicazione Java JDBC in esecuzione su un database Oracle 10g. Predispongo un PreparedStatement per eseguire una query e quindi chiamare ps.executeQuery() per eseguirlo. Occasionalmente la query richiede molto tempo e ho bisogno di ucciderlo. Ho un altro accesso thread che oggetto PreparedStatement e chiama cancel() su di esso.Quando chiamo PreparedStatement.cancel() in un'applicazione JDBC, lo uccide effettivamente in un database Oracle?

La mia domanda è, questo in realtà uccide la query nel database? O lo interrompe semplicemente dal client e la query è ancora in esecuzione da qualche parte nelle viscere di Oracle?

Grazie!

risposta

8

La risposta è che si tratta di un problema di qualità dell'implementazione. Se si guarda allo javadoc per Statement.cancel(), si dice che succederà "se sia il DBMS che il supporto del driver interrompono un'istruzione SQL".

Nella mia esperienza con varie versioni di driver JDBC Oracle, Statement.cancel() sembra fare ciò che si desidera. La query sembra interrompersi immediatamente quando viene annullata.

+0

Non nel mio caso. https://stackoverflow.com/questions/44383579/how-do-i-forcibly-close-connections-from-a-connection-pool – supertonsky

1

Dipende dal driver che si sta utilizzando, sia il driver che il database devono supportare l'annullamento di una dichiarazione affinché funzioni come desiderato. Oracle supporta questa funzione, ma è necessario conoscere di più sul driver specifico che si sta utilizzando per sapere con certezza.

In alternativa, è possibile eseguire un semplice test osservando il database dopo l'avvio e l'annullamento di una query di lunga durata.

10

Si prega di notare che ciò che dico di seguito si basa su osservazioni e inferenze di Oracle in uso, e non si basa su una profonda comprensione degli interni di Oracle. Nessuno di questi deve essere considerato autorevole.

Ciò che detto nel proprio primo paragrafo è corretto. Tuttavia, fai attenzione al test suggerito. Non tutte le query Oracle a lunga esecuzione sono uguali. Sembra che le query siano valutate su due fasi, prima una fase che combina dati sufficienti per sapere come restituire le righe nel giusto ordine e secondo una fase che restituisce le righe che riempiono gli spazi vuoti che non ha calcolato nel prima fase. La divisione del lavoro tra le due fasi è influenzata anche dalle impostazioni dell'ottimizzatore basato sui costi. per esempio. Prime righe vs Tutte le righe.

Ora, se la query è in fase 1, la richiesta di annullamento sembra al meglio essere accodata per essere applicata alla fine della fase 1, il che significa che la query continua a funzionare.

Nella fase 2, le righe vengono restituite in mazzi, e dopo ogni gruppo, il comando di annullamento può avere effetto, quindi supponendo che il driver supporti il ​​comando, la richiesta di annullamento comporterà l'interruzione della query.

Le specifiche per il comando di annullamento JDBC non sembrano dire cosa dovrebbe accadere se la query non si interrompe e quindi il comando può attendere la conferma dell'uccisione, oppure può scadere e tornare con la query ancora in esecuzione.

Problemi correlati