oracle一卡通消費數據分區表創建及自動創建分區存儲過程

因爲一卡通消費數據過多,不利於按時間統計計算,故採起創建分區表的方式來優化查詢效率,創建過程以下less

  1. 建立一卡通消費數據分區表,按時間進行分區,創建時可暫時只建立一個最先時間分區,後續分區經過存儲過程自動建立。這裏把一卡通消費表直接複製過來,因爲操做時間在自動創建分區時很差處理,故修改成varchar類型。

    create table M_REC_CONSUME
    (
    ECODE VARCHAR2(20) default 00000000 not null,
    ID NUMBER not null,
    NOTECASE NUMBER,
    CUSTOMERID NUMBER not null,
    OUTID VARCHAR2(18) not null,
    CARDSN NUMBER not null,
    OPCOUNT NUMBER,
    OPDT VARCHAR2(100) not null,
    ODDFARE NUMBER not null,
    OPFARE NUMBER not null,
    MNGFARE NUMBER not null,
    ACCCODE NUMBER not null,
    DSCRP VARCHAR2(20) not null,
    TERMID NUMBER not null,
    RECNO NUMBER not null,
    UPLOADDATE DATE not null,
    SAMCARDNO NUMBER not null,
    SAMTRADENO NUMBER not null,
    TRADECARDTYPE NUMBER not null,
    TAC NUMBER,
    ASN VARCHAR2(20),
    UPDATEFLAG VARCHAR2(20) not null,
    UPDATEDT DATE default sysdate not null,
    DOWNDT DATE,
    SOURCETABLE NUMBER not null
    )
    partition by range (opdt)優化

    (spa

    partition p201201 values less than ('2012-02-01 00:00:00')日誌

    --建立分區以歷史有效記錄的第一個月開始,這裏要注意分區條件爲less than
    )orm

  2. 建立存儲過程自動創建到當前月份的分區,並寫入日誌。
    存儲過程建立:

    CREATE OR REPLACE PROCEDURE GENE_AUTO_ADD_PARTITION
    IS
    /***********************************************************************
    /* Procedure : GENE_AUTO_ADD_PARTITION
    /* Description : General類程序,用於自動增長分區表的分區 == 計算到part_month爲止,該增長多少個分區
    /* Logic : 一、找出須要增長分區的分區表,以及這些分區表的最近分區
    /* 二、計算這些分區表要增長几個分區
    /* 三、循環爲這些分區表增長分區,直至增長到part_month分區爲止
    /* 四、記錄日誌
    /* Warning : 確保有足夠權限,需顯示受權:Grant select on dba_segments to user;
    /* eg : call gene_auto_add_partition;
    /* Author YYYY-MM-DD DSC
    /* lihan 2015-04-24 初始版本
    /*
    /*********************************************************************/
    part_month varchar2(100);
    vcurrPartitionName varchar2(100);
    vhistPartitionName varchar2(100);
    vCount number;
    vDDLSql varchar2(1024);
    vLessthan varchar2(100);
    i1 number;
    i2 number;ip

    BEGIN
    --初始化參數值
    part_month :=to_char(sysdate + 90,'yyyymm');--可提早新建三個月後的分區,預留問題發現及修復時間
    i1 :=0;
    --format current partition name
    vcurrPartitionName := 'p'||part_month;get

    For x in (
    SELECT segment_name , max(partition_name) partition_name, max(tablespace_name) tablespace_name
    FROM dba_segments a
    WHERE owner = 'YBG_CP'
    AND segment_type = 'TABLE PARTITION'
    AND segment_name not like '%BIN%'
    AND not exists (
    SELECT 1 FROM dba_segments b
    WHERE a.segment_name = b.segment_name
    AND b.partition_name = vcurrPartitionName)
    GROUP BY a.segment_name
    ) LOOPit

    --計算須要增長几個分區
    SELECT (extract(year from to_date(part_month,'yyyymm')) - extract(year from to_date(substr(x.partition_name,2,6),'yyyymm')))*12 +
    (extract(month from to_date(part_month,'yyyymm')) - extract(month from to_date(substr(x.partition_name,2,6),'yyyymm')))
    INTO vCount
    FROM dual;io

    For j in 1..vCount LOOPtable


    --get history Partition name
    vhistPartitionName := 'p'||to_char(add_months(to_date(substr(x.partition_name,2,6),'yyyymm'),j),'yyyymm');
    vLessthan := to_char(add_months(to_date(substr(x.partition_name,2,6)||'01','yyyy-mm-dd hh24:mi:ss'),j+1),'yyyy-mm-dd hh24:mi:ss');

     


    vDDLSql := 'ALTER TABLE M_REC_CONSUME ADD PARTITION '||vhistPartitionName||' VALUES LESS THAN ('''||vLessthan||''' ) TABLESPACE '||x.tablespace_name;

    DBMS_UTILITY.exec_ddl_statement(vDDLSql);

    i1:= i1 + 1;

    END LOOP;

    i1 := i1;
    i2 := i2 + 1;

    END LOOP;

    insert into m_rec_consume_log(updtime,prc_name,dscp)values(sysdate,'GENE_AUTO_ADD_PARTITION','爲M_REC_CONSUME建立三個月後子分區成功,共建立了'||i1||'個分區');
    commit;
    EXCEPTION
    WHEN others THEN
    raise;
    rollback;
    insert into m_rec_consume_log(updtime,prc_name,dscp)values(sysdate,'GENE_AUTO_ADD_PARTITION','更新分區失敗!');

    END;

    還需建立一個日誌表:

    create table m_rec_consume_log
    (
    updtime date,
    prc_name varchar2(1000),
    dscp varchar2(1000)
    )

  3. 設定job定時執行存儲過程完成分區自動建立。

相關文章
相關標籤/搜索