Archives For quick&dirty

if you ever wondered where oracle stores the statistic preferences one can set by using the dbms_stats.set_*_prefs procedures here you go:

global statistic preferences

table which holds the values: sys.optstat_hist_control$

example script to query the settings:

COLUMN SNAME FOR a30;
COLUMN SVAL1 FOR 9999;
COLUMN SVAL2 FOR a20;
COLUMN SPARE1 FOR 999999;
COLUMN SPARE2 FOR 999;
COLUMN SPARE3 FOR 999999;
COLUMN SPARE4 FOR a30;
COLUMN SPARE5 FOR a10;
COLUMN SPARE6 FOR a10;
SELECT sname
, sval1
, to_char(sval2,'DD.MM.YYYY HH24:MI:SS') sval2
, spare1
, spare2
, spare3
, spare4
, spare5
, spare6
FROM sys.optstat_hist_control$
ORDER BY 1
;

procedure which affects the table: dbms_stats.set_global_prefs, e.g.:

exec dbms_stats.set_global_prefs ( 'ESTIMATE_PERCENT', '11');

non-global ( user ) statistic preferences

table which holds the values: sys.optstat_user_prefs$

example script to query the settings:

COLUMN owner FOR a20;
COLUMN object_name FOR a20;
COLUMN object_type FOR a20;
COLUMN pname FOR a30;
COLUMN valnum FOR 99999;
COLUMN valchar FOR a30;
COLUMN chgtime FOR a20;
COLUMN spare1 FOR 999;
SELECT do.owner
, do.object_name
, do.object_type
, o.pname
, o.valnum
, o.valchar
, to_char(o.chgtime,'DD.MM.YYYY HH24:MI:SS') chgtime
, o.spare1
FROM sys.optstat_user_prefs$ o
, dba_objects do
WHERE o.obj# = do.object_id
;

procedures which affects the table: dbms_stats.set_global_prefs, dbms_stats.set_schema_prefs, dbms_stats.set_database_prefs,e.g.:

exec dbms_stats.set_table_prefs ( USER,'T1','GRANULARITY','ALL');
exec dbms_stats.set_schema_prefs ( USER,'ESTIMATE_PERCENT','11' );
exec dbms_stats.set_database_prefs ( 'ESTIMATE_PERCENT', '12', FALSE );

did you ever had the situation where you’d want to quickly monitor how a filesystem grows or what gets written to it without typing the commands again and again ?

some examples:

watch "ls -latr"
Every 2.0s: ls -latr Tue Apr 3 08:29:48 2012
total 60
-rw-r--r-- 1 oracle oinstall 515 Mar 23 08:41 .emacs
-rw-r--r-- 1 oracle oinstall 124 Mar 23 08:41 .bashrc
-rw-r--r-- 1 oracle oinstall 33 Mar 23 08:41 .bash_logout
drwxr-xr-x 4 root root 4096 Mar 23 08:41 ..
drwxr-xr-x 3 oracle oinstall 4096 Mar 26 14:34 oradiag_oracle
-rw-r--r-- 1 oracle oinstall 685 Mar 26 14:36 .bash_profile
-rw------- 1 oracle oinstall 1802 Mar 28 13:06 .viminfo
drwx------ 3 oracle oinstall 4096 Mar 28 13:06 .
-rw------- 1 oracle oinstall 6626 Mar 28 16:36 .bash_history

Without providing any additional arguments watch displays the command one provides and refreshes the output every two seconds.

Another example:
watch -d -n 5 -t "ls -latr"
total 60
-rw-r--r-- 1 oracle oinstall 515 Mar 23 08:41 .emacs
-rw-r--r-- 1 oracle oinstall 124 Mar 23 08:41 .bashrc
-rw-r--r-- 1 oracle oinstall 33 Mar 23 08:41 .bash_logout
drwxr-xr-x 4 root root 4096 Mar 23 08:41 ..
drwxr-xr-x 3 oracle oinstall 4096 Mar 26 14:34 oradiag_oracle
-rw-r--r-- 1 oracle oinstall 685 Mar 26 14:36 .bash_profile
-rw------- 1 oracle oinstall 1802 Mar 28 13:06 .viminfo
-rw------- 1 oracle oinstall 6626 Mar 28 16:36 .bash_history
-rw-r--r-- 1 oracle oinstall 0 Apr 3 08:34 a
drwx------ 3 oracle oinstall 4096 Apr 3 08:34 .

“-d” highlightes the differences since the last refresh
“-n” specifies the refresh interval
“-t” supresses the heading

grepping?
watch -t "grep aaa" bbb

happy watching…

…a customer needed a quick way for enabling index monitoring for a whole schema:

don’t know what index monitoring is? check the documentation

example calls:

@index_monitoring_bulk USER ON Y
@index_monitoring_bulk USER OFF Y

Script:

/**
enable index monitoring for a given user
   parameters: user, on/off, debug
       e.g. @index_monitoring_bulk USER ON Y
**/
SET SERVEROUT ON
SET LINES 164
SET VERIFY OFF
SET FEEDBACK OFF
CLEAR COLUMNS
VARIABLE for_user CHAR(30)
VARIABLE on_off CHAR(3)
VARIABLE debug_on CHAR(1)
BEGIN
  :for_user := '&1';
  :on_off := '&2';
  :debug_on := '&3';
END;
/
DECLARE
  lcb_debug CONSTANT BOOLEAN := :debug_on = 'Y';
  lcv_user CONSTANT all_users.username%TYPE := UPPER ( REPLACE ( :for_user, ' ','' ) );
  lcv_on_off CONSTANT VARCHAR2(3) := NVL ( REPLACE ( :on_off, ' ', '' ), 'OFF' );
  TYPE tab_index_names IS TABLE OF all_indexes.index_name%TYPE INDEX BY PLS_INTEGER;
  ltab_index_names tab_index_names;
  lv_statement VARCHAR2(2000);
  lv_monitoring_clause VARCHAR2(12);
  le_iot EXCEPTION;
  le_resouce_busy EXCEPTION;
  PRAGMA EXCEPTION_INIT(le_iot, -25176);
  PRAGMA EXCEPTION_INIT(le_resouce_busy, -00054);
  PROCEDURE debug ( pv_text IN VARCHAR2 )
  IS
  BEGIN
    IF ( lcb_debug )
    THEN
      dbms_output.put_line ( pv_text );
    END IF;
  END debug;
  FUNCTION user_exists ( pv_user IN all_users.username%TYPE )
                       RETURN BOOLEAN
  IS
    CURSOR cur_check_user
    IS SELECT 'does_exist'
         FROM all_users
        WHERE username = pv_user
    ;
    lv_cursor_result VARCHAR2(10);
  BEGIN
    debug ( ' Checking database for user: '|| lcv_user );
    OPEN cur_check_user;
      FETCH cur_check_user INTO lv_cursor_result;
    CLOSE cur_check_user;
    RETURN lv_cursor_result IS NOT NULL;
  END user_exists;
  PROCEDURE get_indexes_for_user ( pv_user IN all_users.username%TYPE )
  IS
    CURSOR cur_get_indexes_for_user
    IS SELECT index_name
         FROM all_indexes
        WHERE owner = pv_user
    ;
  BEGIN
    OPEN cur_get_indexes_for_user;
      FETCH cur_get_indexes_for_user BULK COLLECT INTO ltab_index_names;
    CLOSE cur_get_indexes_for_user;
  END get_indexes_for_user;
BEGIN
  IF user_exists ( pv_user => lcv_user )
  THEN
    IF lcv_on_off IN ('ON','OFF')
    THEN
      debug ( ' User: '||lcv_user||' does exist ');
      debug ( ' ON/OFF flag is: '||lcv_on_off );
      debug ( ' Loading indexes ' );
      get_indexes_for_user ( pv_user => lcv_user );
      IF ( lcv_on_off = 'ON' )
      THEN
        lv_monitoring_clause := 'MONITORING';
      ELSE
        lv_monitoring_clause := 'NOMONITORING';
      END IF;
      IF ltab_index_names IS NOT NULL
         AND
         ltab_index_names.COUNT > 0
      THEN
         FOR i IN ltab_index_names.FIRST..ltab_index_names.LAST
         LOOP
           debug ( ' Processing index: '||lcv_user||'.'||ltab_index_names(i) );
           lv_statement := 'ALTER INDEX "'||lcv_user||'"."'||ltab_index_names(i)||'" '||lv_monitoring_clause||' USAGE';
           debug ( ' Statement is: '||lv_statement );
           BEGIN
             EXECUTE IMMEDIATE lv_statement;
           EXCEPTION WHEN le_iot THEN debug ( ' --- Index monitoring not possible on IOTs, skipping' );
                     WHEN le_resouce_busy THEN debug ( ' --- Resource busy, propably SYS_ indexes ' );
           END;
         END LOOP;
      END IF;
    ELSE
      dbms_output.put_line ( ' ON/OFF flag must be ON or OFF ' );
    END IF;
  ELSE
    dbms_output.put_line ( ' User '||lcv_user|| ' does not exist ! ');
  END IF;
END;
/

After your usual workload check the results in v$object_usage:

SQL> desc v$object_usage;
 Name					   Null?    Type
 ----------------------------------------- -------- ----------------------------
 INDEX_NAME				   NOT NULL VARCHAR2(30)
 TABLE_NAME				   NOT NULL VARCHAR2(30)
 MONITORING					    VARCHAR2(3)
 USED						    VARCHAR2(3)
 START_MONITORING				    VARCHAR2(19)
 END_MONITORING 				    VARCHAR2(19)
SQL>