Oracle
 sql >> Database >  >> RDS >> Oracle

Campionamento dinamico che mi uccide in 12c

Undici giorni fa, ho scritto sul blog come Adaptive Dynamic Stats stava consumando risorse nei miei database RAC di produzione.

Dopo aver spento quell'incendio, stavo esaminando alcune query con prestazioni scadenti segnalate dai nostri addetti al controllo qualità in Test e altri database non di produzione. Ho fatto come farebbe qualsiasi buon Oracle DBA. Ho raccolto una chiamata alla procedura memorizzata che ha duplicato il problema. Nella mia sessione, ho avviato una traccia SQL ed eseguito la procedura memorizzata. Ci sono voluti 50 secondi per il completamento, quando ci volevano 5 secondi o meno prima di eseguire l'aggiornamento da 11.2.0.4 a 12.1.0.2. Questa procedura memorizzata contiene una serie di istruzioni SQL e una traccia SQL sembrava un punto di partenza logico. Avevo bisogno di sapere quale istruzione SQL nella procedura stava causando i problemi.

Ho eseguito il file di traccia SQL tramite TKPROF e sono rimasto sorpreso dai risultati. Le istruzioni SQL nella procedura memorizzata sembravano essere eseguite abbastanza rapidamente. Ma sono stato accolto da molte affermazioni simili alle seguenti:

SELECT /* DS_SVC */ /*+ dynamic_sampling(0) no_sql_tune no_monitoring
 optimizer_features_enable(default) no_parallel */ SUM(C1)
FROM
 (SELECT /*+ qb_name("innerQuery") INDEX_FFS( "XXX"
 "INDEX_NAME") */ 1 AS C1 FROM
 "OWNER"."TABLE_NAME" SAMPLE BLOCK(71.048, 8) SEED(1)
 "XXX") innerQuery

Questo è il campionamento dinamico al lavoro. Osservando tutte le istruzioni di campionamento dinamico eseguite nel mio file di traccia, sono stato in grado di determinare che queste rappresentavano 45 secondi del tempo di esecuzione complessivo! Accidenti!

Il campionamento dinamico dovrebbe aiutarmi. Il tempo impiegato per ottenere alcune statistiche di esempio dovrebbe essere molto inferiore al tempo risparmiato eseguendo l'istruzione SQL con statistiche migliori. In caso contrario, le prestazioni dell'istruzione SQL potrebbero risentirne, come nel mio caso.

Ho notato una cosa che ho ritenuto interessante era che queste query di campionamento dinamico sono state eseguite una volta per ogni tabella e una volta per ciascuno dei suoi indici. Una delle tabelle coinvolte nella mia query contiene 7 indici, quindi per quella tabella avevo 8 query di campionamento dinamico!

Nel mio post sul blog 11 giorni fa, avevo impostato il parametro optimization_dynamic_sampling su 0, che impedisce l'esecuzione di queste query. Non avevo ancora inserito quella modifica nel nostro ambiente di test, quindi dovevo farlo. Non appena l'ho fatto, le prestazioni della query sono tornate alla normalità. Il valore predefinito di questo parametro per il mio database è 2. Il valore predefinito può variare a seconda del valore dell'impostazione Optimizer_features_enable. Secondo questo post del blog, un valore di 2 significa che il campionamento dinamico si avvierà quando almeno una delle tabelle non ha statistiche. Ma ad essere onesti, il campionamento dinamico non mi sta dando alcun vantaggio e mi fa solo del male. Quindi per ora lo lascerò completamente.