Showing posts with label statspack. Show all posts
Showing posts with label statspack. Show all posts

Monday, July 6, 2020

Configuring Statspack for Standby Database

Statspack provide separate set of scripts for setting it up for a standby database in a data guard configuration. If enterprise edition is used with diagnostic pack then Remote Management Framework could be configured to get AWR reports of the standby. Depending on the data guard configuration (multiple standbys, snapshot data needed only from read only instances etc) the statspack setup would result in less effort and complexity than setting up RMF for AWR.
RMF has database link from both primary to standby and vice versa. Before a role transition additional work must be done by way of creating database link between future primary and future standby. In contrast the statspack only create one database link between primary and standby. As long as the TNS entry used for creating the DB link is available in the future primary then the statspack would continue to function. This is especially useful in a configuration where only subset of instances are candidate to become primary and all others are part of a reader farm.
In a multi-tenant architecture the data guard works on CDB level. As such the standby statspack is installed on the root container. This will create two users perfstat and stdbyperf. To accomplish this the statspack and standby statspack must be installed using catcon.pl script (Refer 2020285.1). The setup of standby consists of running spcreate.sql (normal statspack) and sbcreate.sql (standby statspack) scripts.
A script defining the statspack setup parameters could be used to automate the statspack creation. Output below shows content of a such script, which defines tablespace to create the statspack related tables and the password for perfstat user among other things.
cat sp.sql
define default_tablespace='STATSPACKTBS'
define temporary_tablespace='TEMP'
define perfstat_password='asanga123'
@?/rdbms/admin/spcreate.sql;
@/home/oracle/statpack/chng.sql;
The chng.sql contains the additional work must be done after setting up statspcak. This include issues mentioned in 382993.1 and 2437142.1. Content of this files is shown below.
cat chng.sql
alter table perfstat.stats$mutex_sleep disable constraint STATS$MUTEX_SLEEP_PK;
create index perfstat.STATS$MUTEX_SLEEP_PK on STATS$MUTEX_SLEEP(SNAP_ID,DBID,INSTANCE_NUMBER,MUTEX_TYPE,LOCATION);
insert into stats$idle_event select name from v$event_name where wait_class='Idle' 
minus select event from stats$idle_event;
If perl binary out of ORACLE_HOME is not in the path then following error will occur when running catcon.pl
perl $ORACLE_HOME/rdbms/admin/catcon.pl -u sys -s -e -c 'CDB$ROOT' -n 1 -b st_spcreate sp.sql
Can't locate Term/ReadKey.pm in @INC (@INC contains: /usr/local/lib64/perl5 /usr/local/share/perl5 /usr/lib64/perl5/vendor_perl /usr/share/perl5/vendor_perl /usr/lib64/perl5 /usr/share/perl5 . /opt/cx/app/oracle/product/19.x.0/dbhome_1/rdbms/admin/) at /opt/cx/app/oracle/product/19.x.0/dbhome_1/rdbms/admin//catcon.pm line 497.
BEGIN failed--compilation aborted at /opt/cx/app/oracle/product/19.x.0/dbhome_1/rdbms/admin//catcon.pm line 497.
Compilation failed in require at /opt/cx/app/oracle/product/19.x.0/dbhome_1/rdbms/admin/catcon.pl line 165.
BEGIN failed--compilation aborted at /opt/cx/app/oracle/product/19.x.0/dbhome_1/rdbms/admin/catcon.pl line 165.
To rectify this issue put perl binary out of OH into the path and run the catcon.pl specifying sp.sql script.
export PATH=$ORACLE_HOME/perl/bin:$PATH
$ which perl
/opt/cx/app/oracle/product/19.x.0/dbhome_1/perl/bin/perl

perl $ORACLE_HOME/rdbms/admin/catcon.pl -u sys -s -e -c 'CDB$ROOT' -n 1 -b st_spcreate sp.sql


Next step is to create the standby statspack. A similar script could be created for that as well. The most important parameter in this case is the TNS alias which will be used to create the database link that will connect to the standby.
cat sb.sql
define default_tablespace='STATSPACKTBS'
define temporary_tablespace='TEMP'
define stdbyuser_password='asanga321'
define perfstat_password='asanga123'
define key='y'
define tns_alias='ppdbxdb5tns'
@?/rdbms/admin/sbcreate.sql;
@/home/oracle/statpack/sbchng.sql;
The sbchng.sql has additional work must be done on standby statspack. As stdbyperf user doesn't have access to v$event_name the idle event related workaround must be done after the setup. Also the STATS$MUTEX_SLEEP on standby statspack doesn't have DBID or instance number columns.
SQL> desc stdbyperf.stats$mutex_sleep
 Name                                      Null?    Type
 ----------------------------------------- -------- ----------------------------
 SNAP_ID                                   NOT NULL NUMBER
 DB_UNIQUE_NAME                            NOT NULL VARCHAR2(30)
 INSTANCE_NAME                             NOT NULL VARCHAR2(16)
 MUTEX_TYPE                                NOT NULL VARCHAR2(32)
 LOCATION                                  NOT NULL VARCHAR2(40)
 SLEEPS                                             NUMBER
 WAIT_TIME                                          NUMBER
Instead db_unique_name and instance_name must be used
cat sbchng.sql
alter table stdbyperf.stats$mutex_sleep disable constraint STATS$MUTEX_SLEEP_PK;
CREATE INDEX stdbyperf.STATS$MUTEX_SLEEP_PK ON stdbyperf.STATS$MUTEX_SLEEP(SNAP_ID,DB_UNIQUE_NAME,INSTANCE_NAME,MUTEX_TYPE, LOCATION);
Run the standby statspack creation with
perl $ORACLE_HOME/rdbms/admin/catcon.pl -u sys -s -e -c 'CDB$ROOT' -n 1 -b st_sbcreate sb.sql
Once standby statspack is created run as sys the following to update the idle events in stdbyperf user schema.
insert into stdbyperf.stats$idle_event select event from perfstat.stats$idle_event minus select event from stdbyperf.stats$idle_event;
Additional standby instaces could be added to the standby statspack by using sbaddins.sql. This must be run using stdbyperf and must specify the TNS entry to the standby db. A script similar to below could be used for accomplishing this. As all the standby database instnaces use same set of tables no need to do the additional work on the subsequent standby instances.
cat sbaddin.sql
connect stdbyperf/asanga321
define key='y'
define tns_alias='ppdbxdb6tns'
define perfstat_password='asanga123'
@?/rdbms/admin/sbaddins.sql;

perl $ORACLE_HOME/rdbms/admin/catcon.pl -u sys -s -e -c 'CDB$ROOT' -n 1 -b st_sbaddins sbaddin.sql
Login as stdbyperf and run the below to view the current statspack standby configuration. This only shows the standby instances added to statspack. Not the actual data guard configuation.
select * from stats$standby_config ;

DB_UNIQUE_NAME                 INST_NAME        DB_LINK                          PACKAGE_NAME
------------------------------ ---------------- -------------------------------- ----------------------------
ppdbxdb5                       ppdbxdb5         STDBY_LINK_ppdbxdb5tns           STATSPACK_ppdbxdb5_ppdbxdb5
ppdbxdb6                       ppdbxdb6         STDBY_LINK_ppdbxdb6tns           STATSPACK_ppdbxdb6_ppdbxdb6


As mentioned earlie the standby statspack uses common set of tables to store data from all the standby instances. Only unique objects created for each standby instance are the database link and PL/SQL package which has the name STATSPACK_<db_unique_name>_<instance_name>. The corresponding package for the particular standby instance must be used in order to work with the instance. This inlcuding taking snapshots, changing statspack parameters and etc. For example in orde to change the snap level on ppdbxdb5 should run the STATSPACK_PPdbxDB5_PPdbxDB5 package. Similarly to change snap level on ppdbxdb6 should use STATSPACK_PPdbxDB6_PPdbxDB6. Below output shows chaning snap level on ppdbxdb6.
exec STATSPACK_PPdbxDB6_PPdbxDB6.modify_statspack_parameter(i_snap_level => 7, i_modify_parameter=>'true');

select DB_UNIQUE_NAME,INSTANCE_NAME,snap_level from stats$statspack_parameter;

DB_UNIQUE_NAME                 INSTANCE_NAME    SNAP_LEVEL
------------------------------ ---------------- ----------
ppdbxdb5                       ppdbxdb5                  7
ppdbxdb6                       ppdbxdb6                  7
Standby statspack use a common sequence to create snap id. As such when multiple instances takes snapshots there will be gaps between two consecutive snap ids.
Manual snapshots could be taken by running STATSPACK_<db_unique_name>_<instance_name>.snap. Snapshot taking is not automated and has to be done manually. Scheduling it in a dbms_scheduler job would allow the snapshot taking to work even after swichover in a reader farm configuration mentioned at the begining of the post.
The user stdbyperf doesn't have permission to create scheduler job. Grant create job and execute on dbms_scheduler (if revoked from public) to stdbyperf. Could create one scheduler job for each standby or have a single wrapper procedure with snap call for each standby. Below shows two separate scheduler job for automating snapshot taking.
--ppdbxdb5                       

BEGIN
DBMS_SCHEDULER.CREATE_JOB (
job_name => 'STANDBY_STATSPACK_PPdbxDB5',
job_type => 'STORED_PROCEDURE',
job_action => 'STATSPACK_PPdbxDB5_PPdbxDB5.snap',
start_date => TO_TIMESTAMP('00' ,'MI'),
repeat_interval => 'FREQ=HOURLY',
enabled => TRUE);
END;
/

--ppdbxdb6
                       
BEGIN
DBMS_SCHEDULER.CREATE_JOB (
job_name => 'STANDBY_STATSPACK_PPdbxDB6',
job_type => 'STORED_PROCEDURE',
job_action => 'STATSPACK_PPdbxDB6_PPdbxDB6.snap',
start_date => TO_TIMESTAMP('01' ,'MI'),
repeat_interval => 'FREQ=HOURLY',
enabled => TRUE);
END;
/
When having multiple scheduler jobs are invoked at the same time it is possible to run into the following error.
2020-06-29T18:02:49.768983+00:00
Errors in file /opt/cx/app/oracle/diag/rdbms/ppdbxdb1/ppdbxdb1/trace/ppdbxdb1_j001_119494.trc:
ORA-12012: error on auto execute of job "STDBYPERF"."STANDBY_STATSPACK_PPdbxDB5"
ORA-02049: timeout: distributed transaction waiting for lock
ORA-06512: at "STDBYPERF.STATSPACK_PPdbxDB5_PPdbxDB5", line 3909
ORA-06512: at "STDBYPERF.STATSPACK_PPdbxDB5_PPdbxDB5", line 5486
ORA-06512: at "STDBYPERF.STATSPACK_PPdbxDB5_PPdbxDB5", line 101
ORA-06512: at line 1
2020-06-29T18:06:57.404823+00:00
To eliminate this have a time gap between two schedulers. Above schedulers are scheduled 1 minute apart.
Create standby statspack report by calling the sbreport. This will prompt to select the db_unique_name and instance_name and prompt the range of snap ids to create the statspack report.
SQL> @?/rdbms/admin/sbreport

Instances in this Statspack schema
~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~

DB Unique Name                 Instance Name
------------------------------ ----------------
ppdbxdb5                       ppdbxdb5
ppdbxdb6                       ppdbxdb6

Enter the DATABASE UNIQUE NAME of the standby database to report
Enter value for db_unique_name: ppdbxdb5
You entered: ppdbxdb5

Enter the INSTANCE NAME of the standby database instance to report
Enter value for inst_name: ppdbxdb5
You entered: ppdbxdb5


Specify the number of days of snapshots to choose from
~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
Entering the number of days (n) will result in the most recent
(n) days of snapshots being listed.  Pressing  without
specifying a number lists all completed snapshots.

Listing all Completed Snapshots
                                          Snap
Instance       Snap Id   Snap Started    Level Comment
------------ --------- ----------------- ----- --------------------
ppdbxdb5            14 30 Jun 2020 00:00     7
                    16 30 Jun 2020 01:00     7
                    18 30 Jun 2020 02:00     7
                    20 30 Jun 2020 03:00     7
                    22 30 Jun 2020 04:00     7
Standby statspack report will have a separate section on standby recovery
Recovery Progress Stats  DB/Inst: ppdbxdb5/ppdbxdb5  End Snap: 32
-> End Snapshot Time: 30-Jun-20 09:00:04
-> ordered by Recovery Start Time desc, Units, Item asc

Recovery Start Time Item                       Sofar Units   Redo Timestamp
------------------- ----------------- -------------- ------- ------------------
15-Jun-20 15:18:07  Log Files                 11,360 Files
15-Jun-20 15:18:07  Active Apply Rate            659 KB/sec
15-Jun-20 15:18:07  Average Apply Rat             12 KB/sec
15-Jun-20 15:18:07  Maximum Apply Rat         13,280 KB/sec
15-Jun-20 15:18:07  Redo Applied              14,936 Megabyt
15-Jun-20 15:18:07  Recovery ID                    0 RCVID
15-Jun-20 15:18:07  Last Applied Redo              0 SCN+Tim 30-Jun-20 09:00:15
15-Jun-20 15:18:07  Active Time               29,277 Seconds
15-Jun-20 15:18:07  Apply Time per Lo              1 Seconds
15-Jun-20 15:18:07  Checkpoint Time p              0 Seconds
15-Jun-20 15:18:07  Elapsed Time           1,273,511 Seconds
15-Jun-20 15:18:07  Standby Apply Lag              2 Seconds
          -------------------------------------------------------------
Purging of snapshots must also be done calling the purge procedure of the relavent standby instance package. Following procedure delete snapshots after 32 days of creation.
create table deleted_snaps(delete_time timestamp,
min_snapid number, 
max_snapid number, 
DB_UNIQUE_NAME VARCHAR2(30), 
INSTANCE_NAME VARCHAR2(16), primary key (DB_UNIQUE_NAME,INSTANCE_NAME,delete_time));

create or replace
Procedure Delete_Snaps As
min_snap_id stats$snapshot.snap_id%type;
max_snap_id stats$snapshot.snap_id%type;
db_unq_name stats$snapshot.DB_UNIQUE_NAME%type;
ins_name stats$snapshot.INSTANCE_NAME%type;
snapshots_purged pls_integer;
stm varchar2(500);
cursor delsnaps is select DB_UNIQUE_NAME,INSTANCE_NAME,min(snap_id) as min,
max(snap_id) as max from stats$snapshot 
where to_char(snap_time,'YYYY-MM-DD') = to_char(sysdate-32,'YYYY-MM-DD') 
group by DB_UNIQUE_NAME,INSTANCE_NAME;
begin
open delsnaps;
loop
fetch delsnaps into db_unq_name,ins_name,min_snap_id,max_snap_id;
Exit When Delsnaps%Notfound;
stm := 'begin STATSPACK_'||db_unq_name||'_'||ins_name||'.purge(i_begin_snap =>'||min_snap_id||', i_end_snap =>'|| max_snap_id||', i_snap_range  => true, i_extended_purge  => true, I_DB_UNIQUE_NAME  => '''||db_unq_name||''', I_INSTANCE_NAME => '''||ins_name||'''); end;';
dbms_output.put_line(stm);
execute immediate stm;
commit;
Insert Into Deleted_Snaps values(Systimestamp,Min_Snap_Id,Max_Snap_Id,db_unq_name,ins_name);  
end loop;
Close Delsnaps;
commit;
End;
/
Schedule the deletion of snapshots.
BEGIN
DBMS_SCHEDULER.CREATE_JOB (
job_name => 'Delete_Snaps_job',
job_type => 'STORED_PROCEDURE',
job_action => 'Delete_Snaps',
start_date => trunc(SYSDATE + 1,'DD') + 15/1444,
repeat_interval => 'FREQ=DAILY',
enabled => TRUE);
END;
/
To remove a standby instance from statspack configuration use $ORACLE_HOME/rdbms/admin/sbdelins.sql.

To drop standby statspack and statspack from the database use catcon.pl.
#remove standby statspack
perl $ORACLE_HOME/rdbms/admin/catcon.pl -u sys -s -e -c 'CDB$ROOT' -n 1 -b st_sbdrop  $ORACLE_HOME/rdbms/admin/sbdrop.sql

# remove statspack
perl $ORACLE_HOME/rdbms/admin/catcon.pl -u sys -s -e -c 'CDB$ROOT' -n 1 -b st_spdrop  $ORACLE_HOME/rdbms/admin/spdrop.sql
Useful metalink notes
STATSPACK:Idle Wait Events Missing in STATS$IDLE_EVENT [ID 2673657.1]
STATSPACK REPORTS SHOW "IDLE" DATA GUARD WAIT EVENTS IN TOP 5 IN 12.2 [ID 2305287.1]
12.2 or later STATSPACK: Idle Wait Event Such as 'Data Guard: Timer' is Erroneously Included in Top 5 Timed Events [ID 2437142.1]
New Idle Events are Erroneously Listed in STATSPACK Report [ID 1998538.1]
STATSPACK:Idle Wait Events Missing in STATS$IDLE_EVENT [ID 2673657.1]

Related Posts
Statspack setup in Brief
AWR Reports on Standby when Active Data Guard is Used

Monday, July 1, 2013

DB CPU Greater Than DB Time

According to Oracle documentation DB CPU is a child of DB Time. The document says that parent child relationship of these values is for containment only and child may not add up to the parent. But can the opposite happen? Child values exceed the parent value?
That's what has been happening on several 11gR2 Standard Edition RACs. (with PSU 11.2.0.3.4 and 11.2.0.3.5 applied). The statspack reports shows DB CPU greater than DB Time.
Example 1: 
Time Model System Stats  DB/Inst: GRAVEL/gravel1  Snaps: 1735-1746
-> Ordered by % of DB time desc, Statistic name

Statistic                                       Time (s) % DB time
----------------------------------- -------------------- ---------
DB CPU                                              72.3     116.3
sql execute elapsed time                            30.4      48.9
connection management call elapsed                   7.7      12.4
parse time elapsed                                   1.5       2.4
PL/SQL execution elapsed time                        0.8       1.3
hard parse elapsed time                              0.3        .5
hard parse (sharing criteria) elaps                  0.1        .1
sequence load elapsed time                           0.1        .1
hard parse (bind mismatch) elapsed                   0.0        .0
repeated bind elapsed time                           0.0        .0
DB time                                             62.2
background elapsed time                             81.7
background cpu time                                 21.9
          -------------------------------------------------------------

Example 2:
Time Model System Stats  DB/Inst: GRAVEL/gravel1  Snaps: 1969-1970
-> Ordered by % of DB time desc, Statistic name

Statistic                                       Time (s) % DB time
----------------------------------- -------------------- ---------
DB CPU                                             109.3     104.6
sql execute elapsed time                            58.5      56.0
connection management call elapsed                   7.3       7.0
parse time elapsed                                   3.8       3.6
PL/SQL execution elapsed time                        2.4       2.3
hard parse elapsed time                              1.3       1.2
hard parse (sharing criteria) elaps                  1.3       1.2
sequence load elapsed time                           0.2        .2
PL/SQL compilation elapsed time                      0.0        .0
repeated bind elapsed time                           0.0        .0
hard parse (bind mismatch) elapsed                   0.0        .0
DB time                                            104.5
background elapsed time                             95.3
background cpu time                                 26.2
          -------------------------------------------------------------
DB CPU exceeding DB Time has been happening intermittently for while. Following graphs show the different between DB CPU and DB Time and values below 0 indicate instances where DB CPU greater than DB Time.

After raising a SR Oracle has created "Bug 16300155 STATSPACK REPORTS SHOW DB CPU GREATER THAN DB TIME" and still investigating.



Similar observation was also made on a Enterprise Edition RAC as well.

This had been known to Oracle and already had a bug number (Bug 12713813: DB CPU LOOKS OVER-ESTIMATED) assigned to investigating this. However it was mentioned by Oracle that this bug hasn't been progressed because Oracle couldn't reproduce the issue. For the observed values it was said that DB Time is too little and to raise a SR (for awr related issue) if it's observed again at higher DB Times, although the Oracle engineer agreed that this an oddity and impossibility (that DB CPU is greater than DB Time no matter how small the observed values are).

Update 05 July 2013
AWR related SR was reopened as DB CPU higher than DB Time was observed during high activity time.


Update 18 July 2013
New bug has been created with regard to this issue. Bug 17181272 - AWR REPORTS DB CPU GREATER THAN DB TIME ON RAC DATABASE. Current status is development working.

Friday, July 23, 2010

Statspack setup in Brief

It seems statspack is the only option if the database is standard edition. Diagnostic and Tuning packs are not an option on standard edition.

Installing statspack metalink ntoe 149113.1
Blog is for 11gR1 (11.1.0.7)
SQL> @?/rdbms/admin/spcreate

Choose the PERFSTAT user's password
-----------------------------------
Not specifying a password will result in the installation FAILING

Enter value for perfstat_password: pefstat
pefstat


Choose the Default tablespace for the PERFSTAT user
---------------------------------------------------
Below is the list of online tablespaces in this database which can
store user data.  Specifying the SYSTEM tablespace for the user's
default tablespace will result in the installation FAILING, as
using SYSTEM for performance data is not supported.

Choose the PERFSTAT users's default tablespace.  This is the tablespace
in which the STATSPACK tables and indexes will be created.

TABLESPACE_NAME                CONTENTS  STATSPACK DEFAULT TABLESPACE
------------------------------ --------- ----------------------------
TOOLS                          PERMANENT
USERS                          PERMANENT
WSTBS                          PERMANENT
..
Pressing  will result in STATSPACK's recommended default
tablespace (identified by *) being used.

Enter value for default_tablespace: tools

Using tablespace TOOLS as PERFSTAT default tablespace.


Choose the Temporary tablespace for the PERFSTAT user
-----------------------------------------------------
Below is the list of online tablespaces in this database which can
store temporary data (e.g. for sort workareas).  Specifying the SYSTEM
tablespace for the user's temporary tablespace will result in the
installation FAILING, as using SYSTEM for workareas is not supported.

Choose the PERFSTAT user's Temporary tablespace.

TABLESPACE_NAME                CONTENTS  DB DEFAULT TEMP TABLESPACE
------------------------------ --------- --------------------------
TEMP                           TEMPORARY *

Pressing  will result in the database's default Temporary
tablespace (identified by *) being used.

Enter value for temporary_tablespace: temp

Using tablespace temp as PERFSTAT temporary tablespace.
... Creating PERFSTAT user
... Installing required packages
... Creating views     
..
SQL> set echo off;
Creating Package STATSPACK...
Package created.
No errors.
Creating Package Body STATSPACK...
Package body created.
No errors.
NOTE:
SPCPKG complete. Please check spcpkg.lis for any errors.
Configuring statspack refer metalink note 149121.1 which lists default values.
Change the default snap level 5 to 7 (Good for taking snapshots every hour or level 0 and every 15 minutes)
exec statspack.modify_statspack_parameter(i_snap_level => 7, i_modify_parameter=>'true');
Verify the changes in
select snap_level from stats$statspack_parameter;

SNAP_LEVEL
----------
7
On RAC systems run the parameter modify command on each instance and check snap level has been set on all nodes
SQL> select instance_number,snap_level from stats$statspack_parameter;

INSTANCE_NUMBER SNAP_LEVEL
--------------- ----------
              1          7
              2          7
To take snapshots simply run
declare
snap_no number;
begin
snap_no := statspack.snap;
dbms_output.put_line('snapshot number '||snap_no);
end;
/
To take snapshot automatically set aq_tm_processes and job_queue_processes to > 0 and
@?/rdbms/admin/spauto
will take snapshot every hour on the hour. In a RAC environment run the spauto script on all nodes to add instnace specific jobs.
JOB   INSTANCE INTERVAL
---- ---------- ------------------------------
30          1 trunc(SYSDATE+1/24,'HH')
50          2 trunc(SYSDATE+1/24,'HH')
Change the snapshot interval with
dbms_job.interval(jobid,interval);
Create statspack report with
@?/rdbms/admin/spreport
For best performance when running statspack report gather statistics on perfstat schema with
dbms_stats.gather_schema_stats('PERFSTAT');
Making baseline explained on metalink note 394937.1
There are two ways to make baselines using snapshots, which include snap_shot ranges, date range. Make a baseline with
exec Statspack.make_baseline(begin_snapid,end_snapid);
or 
statspack.make_baseline(to_date(begin_date),to_date(end_date));
Snapshots making the baselines are not affected by snapshot purge.

There are number of ways to purge snapshots by specifying range of snapshots, range of dates, purge all snapshots before a certain date or delete all snapshots taken number of days before the current date.
statspack.purge(begin_snapid,end_snapid);
could be used for this.
@?/rdbms/admin/sppurge
could also be used to purge the snapshot. It will purge snapshot of the currently connected instance.

Drop statspack with
@?/rdbms/admin/spdrop
Tuning with statspack on metalink note 228913.1
Deleting snapshots at regular intervals, this is not part of the oracle statspack setup files.
create table to store deleted snap information.
create table deleted_snaps(delete_time timestamp primary key,
min_snapid number, 
max_snapid number, 
dbid number, 
instance_number number);
Procedure for keeping only the snapshots taken two weeks ago
create or replace
Procedure Delete_Snaps As
min_snap_id stats$snapshot.snap_id%type;
max_snap_id stats$snapshot.snap_id%type;
i_dbid stats$snapshot.snap_id%type;
i_instance_num stats$snapshot.snap_id%type;
snapshots_purged pls_integer;
cursor delsnaps is select dbid,instance_number,min(snap_id) as min,
max(snap_id) as max from stats$snapshot 
where to_char(snap_time,'YYYY-MM-DD') = to_char(sysdate-15,'YYYY-MM-DD') 
group by dbid,instance_number;
begin
open delsnaps;
loop
fetch delsnaps into i_dbid,i_instance_num,min_snap_id,max_snap_id;
Exit When Delsnaps%Notfound;
snapshots_purged := statspack.purge( i_begin_snap      => min_snap_id
, i_end_snap        => max_snap_id
, i_snap_range      => true
, i_extended_purge  => true
, i_dbid            => i_dbid
, i_instance_number => i_instance_num);

Insert Into Deleted_Snaps values(Systimestamp,Min_Snap_Id,Max_Snap_Id,i_dbid,i_instance_num);  
end loop;
Close Delsnaps;
commit;
End;
/
Schedule a job to delete at 12.15 am on a Rac environment it will delete snapshots of all instances that meet the delete criteria, no need to run on all instances.
Declare
  Job_Id Number;
Begin
  Dbms_job.submit(job => job_id,
  what => 'Delete_Snaps;',
  next_date => trunc(SYSDATE + 1,'DD') + 15/1444 ,
  Interval => 'trunc(SYSDATE + 1,''DD'') +15/1444');
end;
/
Update on 07 December 2011
At times it is possible to see the following error message on the alert log
ORA-12012: error on auto execute of job 50
ORA-00001: unique constraint (PERFSTAT.STATS$MUTEX_SLEEP_PK) violated
ORA-06512: at "PERFSTAT.STATSPACK", line 5661
ORA-06512: at "PERFSTAT.STATSPACK", line 105
ORA-06512: at line 1
This is because there could be same values for columns (MUTEX_TYPE, LOCATION) in v$mutex_sleep view. As a workaround disable the unique constraint and create a non-unique index on affected columns.
SQL> alter table perfstat.stats$mutex_sleep disable constraint STATS$MUTEX_SLEEP_PK;

SQL> create index perfstat.STATS$MUTEX_SLEEP_PK on STATS$MUTEX_SLEEP(SNAP_ID,DBID,INSTANCE_NUMBER,MUTEX_TYPE,LOCATION);
This has been tracked as the BUG:5443234 - STATSPACK.SNAP CAUSING UNIQUE CONSTRAINT (STATS$MUTEX_SLEEP_PK) VIOLATED mentioned in the metalink note ORA-1 on PERFSTAT.STATS$MUTEX_SLEEP_PK when executing statspack.snap [ID 382993.1]



Update on 07 October 2020
As of 12.2 DBMS_JOB package is depreciated. Use DBMS_SCHEDULER to create a snap job and statspack delete job as below.
BEGIN
DBMS_SCHEDULER.CREATE_JOB (
job_name => 'STATSPACK_SNAP_JOB',
job_type => 'STORED_PROCEDURE',
job_action => 'statspack.snap',
start_date => TO_TIMESTAMP('0' ,'MI'),
repeat_interval => 'FREQ=HOURLY',
enabled => TRUE);
END;
/

BEGIN
DBMS_SCHEDULER.CREATE_JOB (
job_name => 'Delete_Snaps_job',
job_type => 'STORED_PROCEDURE',
job_action => 'Delete_Snaps',
start_date => trunc(SYSDATE + 1,'DD') + 30/1444,
repeat_interval => 'FREQ=DAILY',
enabled => TRUE);
END;
/