Oracle數據庫11g新特性:數據庫重放

Oracle數據庫11g面向DBA和開發人員的重要新特性:數據庫重放

    摘要:瞭解如何使用數據庫重放(Oracle 數據庫 11g 中一個閃亮登場的全新工具)來捕獲完整的數據庫負載,以便您可以隨意進行“重放”。

    需要在數據庫中進行更改時 — 無論是進行微小的改動(如變更初始化參數和數據庫屬性)還是進行不可避免的較大改動(如應用補丁集),您最關心什麼?對於您的到 Oracle 數據庫 11g 的升級,您最關心的是什麼?

    對我而言,我最關心的是更改是否會帶來“破壞性”風險。即使微小的改動也有可能引發多米諾骨牌效應,最終導致嚴重後果。

    爲了將這種風險降至最低,許多廠商在類似於生產環境的控制環境中進行更改,應用類似於生產系統的負載並觀察隨之產生的影響。複製生產系統非常簡單(至少從技術層面上講),但再現負載卻是另一回事。說起來容易做起來難。

    多數機構會採用一些可自動運行以模擬真實用戶活動的第三方負載生成工具進行嘗試。在大多數情況下,這種方法是可以的,但其始終無法真正忠實地再現生產數據庫負載。這些第三方工具只是通過不同參數執行預編寫的查詢若干次;您必須向這些工具提供查詢並給定其可以隨機使用的參數範圍。這並不能代表您的生產系統負載,而僅僅是運行了一小部分執行了若干次的生產負載,因此,這只是對 1% 的應用程序代碼進行了測試。最糟糕的是,這些工具要求您自己提供所有來自生產負載的查詢,對於小型應用程序而言,這可能需要數週或數月,對於複雜些的而言,則可能需要多達一年的時間。

    如果可以,在數據庫本身內記錄所有數據庫操作(與 DML 相關的操作及其它),而後按這些操作出現的真實順序進行重放,難道不是一種更好的方法嗎?

    數據庫重放概述

    Oracle 數據庫 11g 將爲您帶來諸多好處。新的數據庫重放工具好似數據庫內的 DVR.使用該獨特的方法,可如實地以二進制文件格式捕獲 SQL 級別以下的所有數據庫活動,然後在同一數據庫或不同數據庫內進行重放(這正是在進行數據庫更改之前您希望做的)。您還可以自定義捕獲流程,以包括或排除某些特定類型的活動。

    數據庫重放與另一個工具 SQL 性能分析器共同構成了 Oracle 數據庫 11g 的“真正應用測試”選件。這兩個工具之間的主要不同在於涉及的範圍:數據庫重放適用於捕獲和重放數據庫內的所有(符合某些篩選條件)活動,而 SQL 性能分析器可用於捕獲特定的 SQL 語句並對其進行重放。(在數據庫重放中,您無法查看或訪問捕獲到的特定 SQL,而在 SQL 性能分析器中則可以)。後者的一個顯著優勢是 SQL 調整,因爲您可以調整由應用程序執行的 SQL 語句並評估其影響。(本系列即將推出有關 SQL 性能分析器介紹的文章。)

    理論上,數據庫重放的工作順序如下圖所示。


    1. 啓動一個記錄數據庫活動的捕獲流程。
    2. 該流程將活動寫入名爲“capture files”的特殊文件,該文件位於 /capture directory/ 目錄中。
    3. 稍後,停止捕獲流程,將這些捕獲文件移至位於 /replay directory/ 目錄中的測試系統。
    4. 啓動一個重放流程和若干重放客戶端,以重放這些捕獲文件。
    5. 這些捕獲文件將在測試數據庫上應用。

    因此,數據庫重放可以提供哪些第三方工具不能提供的優勢?一些工具僅僅重放若干您提供的複合語句。而數據庫重放不需要您提供 SQL 語句。由於它將捕獲 SQL 之下的所有活動,因此您不會遺漏任何可能導致性能問題的關鍵操作。此外,您可以有選擇地(針對特定用戶、程序等)進行捕獲,還可在捕獲負載時指定時間期限,可以重放導致問題的特定負載,而不是整個數據庫。

    例如,您注意到月末利息計算程序導致問題出現,並猜想更改參數將簡化流程。您必須做的是捕獲月末程序運行期間內的負載,在測試系統上對參數進行更改,然後在該測試系統上重放捕獲文件。如果性能有所提升,則表明此解決方案可行。如果性能沒有提升,這也僅僅是個測試系統而已。您不會妨礙到生產數據庫的運行。

    在我看來,單爲了使用該工具,也值得升級到 Oracle 數據庫 11g.下面將介紹該工具的工作原理。 


  捕獲

    1. 第一個任務是捕獲數據庫中的負載。所有任務都可通過命令行或 Oracle 企業管理器數據庫控制完成,但此處將使用後者。

    捕獲到的負載存儲在系統中的文件上,這些文件是名副其實的“攝像機”內的“磁帶”。該目錄應當爲空。因此,第一個任務是創建目錄(如果還沒有此目錄)。對於本例,創建的目錄名爲 /home/oracle/dbcapture.

  $ cd /home/oracle
  $ mkdir dbcapture 


    2. 在數據庫中爲該目錄創建一個目錄對象:

SQL> create directory dbcapture as '/home/oracle/dbcapture'; 


    目錄創建完成。

    3. 現在,可以開始捕獲了。爲了演示真實場景,將創建一個簡單的測試工具,該工具將生成許多 INSERT 語句並插入到一個名爲 TRANS 的表中。

    下面是一個可完成此任務的小的 PL/SQL 代碼片斷。該代碼片斷將生成 1,000 個插入語句並進行執行。(注意,此代碼片段將生成 1,000 個不同的插入語句,而不是在同樣的語句或程序中執行 1,000 次插入操作。)

declare
  l_stmt varchar2(2000);
begin
  for ctr in 1..1000 loop
     l_stmt := 'insert into trans values ('||
        trans_id_seq.nextval||','||
        ''''||dbms_random.string('U',20)||''','||
        'sysdate - '||
        round(dbms_random.value(1,365))||','||
        round(dbms_random.value(1,99999999),2)||','||
        round(dbms_random.value(1,99))||')';
     dbms_output.put_line(l_stmt);
     execute immediate l_stmt;
     commit;
  end loop;
end; 


    只創建包含以上內容的文件;不要運行。將該文件命名爲 add_trans.sql.

    4. 在現實情況中,您可能會在不同的數據庫上運行重放。但是,在此處,針對我們的目的,您將只是閃回同一數據庫並重放那裏的活動。您可以通過創建名爲 GOLD 的恢復點來標記該場所。

SQL> create restore point gold; 


    (第 1 步到第 4 步僅對本課而言必不可少。如果沒有目錄對象,則在生產環境中執行操作時無需這些步驟。)

    現在,準備開始捕獲。導航到 Oracle Enterprise Manager Database Control 中的 Database Replay 主頁面。在該主頁中,選擇 Software and Support(如下圖所示,標記爲“1”)


   5. 單擊 Database Replay(標記爲“2”)啓動 Database Replay 頁面(如下所示)。



  6. 在左側窗格中,您將看到一系列活動。選擇第一個活動 (Step 1:Capture Workload),方式是單擊它旁邊的 Go to Task 圖標。

    7. 下一個屏幕將顯示三個您應在啓動捕獲流程之前仔細檢查並確認的假設:

    ◆  當前數據庫可以在重放系統上恢復到負載捕獲開始時的 SCN
    ◆  有足夠的磁盤空間來保存捕獲的負載
    ◆  在負載捕獲開始之前已準備好重啓數據庫(如果您選擇這樣做) 

    8. 選中所有複選框進行確認。

    9. 單擊 Next.

    10. 下一個屏幕有兩個不同的操作項。在屏幕的上半部分,您將看到兩個單選按鈕,您可通過這兩個按鈕來選擇是否希望在捕獲流程前重啓數據庫。

    啓動捕獲流程後,可能會有一些正處於運行中的事務,其中並非所有都可進行捕獲。重啓數據庫將使這些正處於運行中的事務無效。此外,共享池可能具有數個 SQL 語句,其中一些可緩存和固定。這可能會與捕獲的負載相沖突。重啓數據庫可清除這些“干擾”。而且,重啓數據庫可以爲您提供一個乾淨備份在測試系統上進行恢復,從而確保您在與生產系統的 SCN 號相同的系統上重放活動。

    出於以上這些原因,特別是第一個,Oracle 建議在捕獲之前重啓數據庫(該選項爲默認設置)。但這不是必須的。如果不希望重啓,請選擇另一個單選按鈕。

    11. 屏幕底部顯示的內容如下所示。




    現在,您將記錄捕獲流程在捕獲活動時將考慮的過濾器。默認有兩個過濾器:排除所有來自 Oracle Management Server 的活動和來自 Oracle Management Agent 的活動。

    您也可以添加其它過濾器。例如,要添加排除所有 Perl 程序的過濾器,可單擊 Add Another Row 並在域“Filter Name”和“Value”中分別輸入“perl”和“%perl%”。同樣,糾正默認參數中的小錯誤 — Oracle Management Agent 過濾器的值應是“%emagent%”,而不是“emagent%”。

    或者,假設您希望排除所有 SYS 用戶操作。那麼,您需要從 Session Attribute 下拉框中選擇 USER,並在“Value”列中輸入 SYS.

    12. 單擊 Next.這將顯示一個類似如下所示的屏幕:



    13. 在該屏幕中,從下拉框中選擇將在其中存儲捕獲文件的目錄名。本例中已使用了目錄 DBCAPTURE.如果您沒有在以上步驟中創建該目錄,還可通過單擊 Create Directory Object 進行創建。然後單擊 Next.

    14. 在下一個屏幕中,您將看到 Job Details(作業細節),如作業執行時間等。選擇單選按鈕 Immediate 立即執行作業。

    15. 在該頁面上填寫其它細節,如 OS 用戶名、SYS 口令等,並單擊 Next.

    16. 下一個屏幕標爲“Step 5 of 5”,其中將顯示您輸入的所有信息,如作業名和排除過濾器。如果所有內容都符合您的要求,則單擊 Submit.否則,可返回以進行修改。

    17. 一旦單擊了 Submit,負載捕獲就將開始。您將看到一個確認屏幕,如下所示。



    注意 Status,其顯示爲“In Progress”。

    18. 現在,該工具正在捕獲負載,從 SQL*Plus 提示符運行您的模擬負載。當然,在實際的系統中,無需運行任何模擬;只需讓捕獲流程運行一段時間以捕獲所有負載。

SQL> connect scott/tiger
SQL> @add_trans 


    這將在表 TRANS 中執行 1,000 個插入語句。

    19. 負載完成後,單擊 Stop Capture.

    20. 您已經將捕獲的負載成功地存儲到 /home/oracle/dbcapture 目錄中的文件裏。

 預處理

    現在,負載已捕獲,可進行重放了。通常,您希望在單獨的測試系統中進行重放,因此需要將目錄 /home/oracle/dbcapture 中的文件複製到一個新的主機。請確保在將文件複製到該目錄時,該目錄爲空。出於教學目的,您將使用同一個數據庫進行重放。

    在同一數據庫中進行重放並不常見,但有可能出現。例如,您可能希望在主系統中重放事務,測試完成後閃回至起始點。您可能會中斷一個時段,以在期間測試參數更改(您將在同一數據庫中進行此更改)的效果。

    您需要在播放捕獲的負載之前對其進行預處理。預處理可使這些捕獲的文件爲重放做好準備。

    1. 轉至 Database Replay 主頁面。
    2. 選擇 Step 2:Preprocess Workload。
    3. 從下拉列表框中選擇目錄對象。這將顯示捕獲的負載。在本例中,該目錄對象是 DBCAPTURE。如果您還沒有創建目錄對象,單擊相應的按鈕即可輕鬆創建目錄。
    4. 單擊 Preprocess Workload。
    5. 在下一個頁面中,將要求您提供作業名和相關細節,如主機用戶名和口令。如果不想指定作業名,接受默認值。選擇立即運行該作業。主機用戶 ID 和口令應已填充。如果還沒有,輸入相應的值,單擊 Submit。
    6. 在下一個頁面中,您將看到確認信息和一個可用於查看作業狀態的鏈接。單擊該鏈接。
    7. 刷新該屏幕,直至您看到狀態爲“Succeeded”。

    現在,負載已經過預處理,可用於重放了。

    重放

    捕獲負載並進行預處理後,您就可在測試數據庫中進行重放了。出於教學目的,您在同一數據庫中預處理了負載,並將使用同一數據庫重放這些活動。爲此,您必須將數據庫重置回起始點。您可以通過將其閃回到在捕獲流程期間創建的恢復點 GOLD 來輕鬆實現此目的。

SQL> shutdown immediate;
... database shuts down ...
SQL> startup mount
... instance starts and mounts the database ...
SQL> flashback database to restore point gold;
... database will be flashed back ...
SQL> alter database open resetlogs;
... database is opened ... 


    現在,您處於負載啓動之前的一個點,可以重放之前捕獲的負載了。按照以下步驟對其進行重放。

    1. 從 Database 主頁轉至 Database Replay 主屏幕,如“Capturing”部分中所示。

    2. 從菜單中選擇 Step 3:Replay Workload.這將帶您進入 Replay 主屏幕。

    3. 您將看到一個用於選擇目錄的下拉框。選擇重放文件所在的目錄。這是目錄對象;不是實際的 UNIX 目錄。在之前的示例中,您使用了目錄對象 DBCAPTURE,因此將其選中。如果您還沒有創建目錄,可單擊 Create Directory 創建一個目錄對象。

    4. 單擊右上角的 Setup Replay.

    5. 下一個屏幕將顯示即將發生的事情的信息列表。以下爲每條信息項的相關說明。

    Restore Database(恢復數據庫)— 重放之前捕獲的負載時,可能需要在測試系統上執行此操作。您如何構建測試系統?您可能將生產數據庫恢復到測試系統並對其進行恢復。最大的可能是,在此活動中,生產數據庫沒有關閉,因此您的恢復可能並不完全。在這種情況下,確認恢復操作已執行至捕獲和預處理階段指定的 SCN 號。
本例中,您將數據庫閃回至該 SCN 號。因此,您遵循了規定。

    Perform System Changes(執行系統更改)— 這是爲什麼要首先執行重放的原因:測試系統更改,如參數更改或設置更改。當然,您需要在重放之前進行更改。


    Resolve References to External Systems(解決對外部系統的引用)— 假設您已經在生產數據庫中具有了一個指向 /home/appman/myfiles 的目錄對象,而測試系統上不存在該目錄。在重放時,對該目錄的引用將失敗。同樣,源系統中的所有數據庫鏈接也將在測試系統中失敗(如果它們不存在)。因此,您需要通過創建或更改目錄來解決這些問題。您可以利用下一個屏幕對其進行更改。


    Set Up Replay Clients(設置重放客戶端)— 瞭解如何在後續步驟中執行該操作。

    6. 單擊 Continue,這將顯示如下所示的屏幕:




    您可以通過單擊頁面上顯示的鏈接更改所有非引用參數。請注意,單擊任何一個鏈接都將會離開 Database Replay 頁面。因此,最好在 SQL*Plus 中對這些鏈接進行單獨更改。單擊 Continue.

    7. 輸入 Replay Name 或接受默認值。

    8. 下一個屏幕將顯示一些由於未解決的對數據庫鏈接、目錄等的引用而可能導致的問題。


    如果願意,可以在屏幕右側更改重放系統。在本例中,由於在同一數據庫上運行,因此本步驟並非必須。

    9. 單擊 Next.這將顯示如下所示的屏幕:



    該屏幕將顯示重放流程正在等待重放客戶端。重放客戶端的執行並不在 Database Control 屏幕內進行。這些客戶端程序讀取捕獲的負載並對其進行重放。程序名爲 wrc(在 UNIX 和 Windows 系統上均是該名稱)。要啓動重放客戶端,您需要轉至 UNIX 提示符並執行以下命令行:

$ wrc userid=system password=* replaydir=/home/oracle/dbcapture 


    當然,您需要提供正確的 SYSTEM 口令。如果捕獲文件存儲在另一個地方,則需更改目錄名。應返回以下消息:

Workload Replay Client: Release 11.1.0.4.0 - Beta on Wed Jun 6 01:47:53 2007

Copyright (c) 1982, 2006, Oracle.  All rights reserved.

Wait for the replay to start (01:47:53)



    此時,重放客戶端僅僅是等待重放管理程序(數據庫控制)告知其啓動。您可以決定是否啓動多個客戶端來並行處理負載。

    10. 立即轉至 Database Control 屏幕。您應當看到該屏幕已更改,其中顯示已連接重放客戶端。該屏幕將顯示客戶端連接的主機名、操作系統進程 ID 等。


    11. 單擊 Next,然後單擊 Submit 啓動重放流程。如果現在轉至 UNIX 會話,您會看到另一條消息:“Replay started (01:49:56)”。該屏幕將通過進度條來顯示目前已處理的數據量。

 12. After some time the UNIX session will show "Replay finished (01:50:35)".此時,如果查看 Database Control 屏幕,您將看到該屏幕類似如下所示:


    13. 其中顯示了重放作業的詳細狀態。左上角的關鍵域“Status”顯示爲“Completed”,指示作業已完成。

    14. 現在可以進行運行分析了。該屏幕在下半部分(標題“Comparison”下)顯示了一些量度。在本例中,重放在 41 秒內完成,是捕獲流程所花時間2 分 14 秒的 30.6%.這是個好消息嗎?您實施的更改有效嗎?

    不一定。看看下一個量度:Database Time(數據庫時間)。該值沒有變化 — 大約 2 秒鐘。因此,您實施的這些更改沒有帶來任何明顯的改善。

    15. 但請勿就此停下。要進行更爲綜合的分析,可比較捕獲期間一段時期的自動負載信息庫 (AWR) 快照和重放,看看衆多其它度量(如栓鎖爭用、鎖定、重做產生、一致獲取等)之間的差異,以使您更好、更清晰地瞭解更改所帶來的影響。
    用例

    數據庫參數更改 — 假如,您要更改參數 db_file_multiblock_read_count 的默認值,那麼是從 16 改爲 256 還是 128?亦或是將其設爲 64 或 32?選擇有限,但影響可能無限;更改此值會對優化程序帶來極大影響,對某個查詢有益的更改可能會破壞另外 100 個查詢。如何確定該參數的最佳值?

    數據庫重放可輕鬆應對這種情況。您可以從生產系統捕獲負載,而後將捕獲的負載移至不同的測試系統中,並將 db_file_multiblock_read_count 設爲 32,然後重放負載。之後,您可以將數據庫閃回至初始狀態,將該值設爲 64,並重放相同的負載。您可以針對該參數所有可能的值重複執行這一過程:閃回、設置值、重放捕獲的負載。每次重放時,您可捕獲重放前後的 AWR 快照並進行比較。然後選擇可帶來最佳整體結果的參數值。如果沒有數據庫重放,則根本不可能確定出最佳值。

    操作系統升級 — 您計劃升級操作系統或只是應用一個小補丁來修復 I/O 問題,但您如何能確保它不會帶來任何破壞或帶來一些其它問題?很簡單:只要捕獲負載並在應用補丁的測試系統中對其進行重放。該方法同樣也適用於內核參數更改。

    應用補丁 — 假設您發現一個錯誤,並且有相應的補丁可用。但您無法確保其會對現有操作產生何種影響,當然,您也可以和企業中 1000 位其他用戶共同找出答案。數據庫重放將爲您解決這一難題。

    調試 — 總是會有一些會帶來意外結果的令人討厭的程序。幸運的是,有了數據庫重放,調試變得前所未有的輕鬆。只需在程序運行期間捕獲負載,並移至一個新系統,更改程序邏輯以加入一些調試信息,而後重放負載、分析輸出並解決問題。如果第一次並未湊效,不要失去信心。重複該過程(從重放開始;無需再次捕獲)直至找到解決方案。

    對象更改 — 您希望添加索引或將索引從 b 樹轉換爲位圖。這會對 INSERT 語句產生何種影響?會在何處產生影響?不要猜測;只需捕獲負載並在測試系統中進行重放即可。

    數據庫升級 — 這是夢寐以求的更改確保。升級至 Oracle 數據庫 11g 的時代已經到來。最大的問題是:您所有的應用程序都會正常運行甚至是表現更好嗎?無需多慮,只要從 Oracle 數據庫 10g 捕獲負載並在 Oracle 數據庫 11g 中進行重放即可。您不是在新版本上測試一些複合事務,而是在測試應用程序每天都在使用的 SQL.如果有些事情並未按計劃進行,則在新系統中對其進行調整,直至您獲得完全滿意的結果。

    (注:截至本文撰寫之日,Oracle 數據庫 11g 還只有測試版,尚不支持來自 Oracle 數據庫 10g 的捕獲。但是,該功能將在 Oracle 數據庫 11g 的生產版中提供。)

    平臺更改 — 假設您希望將數據庫平臺從 Solaris 移植到 HP-UX(其中沒有提供適用於文件系統的異步 I/O)。性能是否還會一樣?爲什麼要猜測?只要捕獲 Solaris 中的負載並在 HP-UX 中進行重放即可。

    轉換到 Oracle 真正應用集羣 (RAC) — 這是一個普遍問題:您計劃將數據庫從單一實例轉換爲 RAC 實例。應用程序表現是否如初?獲取答案的唯一方法是運行實際的負載,對其進行捕獲,而後在 RAC 數據庫中進行重放。

    結論

    更改從來都是困難重重,但也不再是無法忍受。您可以通過使用新的數據庫重放工具捕獲最終用戶放入系統中的確切活動,而後在測試系統上進行重放,以精確地衡量更改影響來降低多數風險,而這些都只需幾下鼠標點擊和鍵盤敲擊即可實現。請記住,您還可以測試應用程序的功能,並不僅僅限於性能。

發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章