Delphi の詳細な探索 - CodeSite アプリケーション ガイド
Delphi は非常に強力なデバッグ機能を提供しますが、バグの発見は依然として困難な作業です。通常、コードの作成とコードのデバッグに費やす時間はほぼ同じか、それ以上の場合もあります。不必要な時間とエネルギーの無駄を減らすために、バグのロック効率を向上させるために専門的なデバッグ ツールの助けが必要な場合があります。この記事では、有名なデバッグ ツール CodeSite PRo 2.0 を紹介します (2000 年の Delphi Informant Readers' Choice Award で最優秀デバッグ ツールとして 2 位を受賞しました)。公式ウェブサイトは www.raize.com です。 CodeSite の主な機能は、開発者がコードを使用してランタイムの詳細を特別な受信機に送信し、さらに分析できるようにすることです。より正確には、CodeSite によって実装された TCodeSite クラスを通じて、ランタイム情報をパッケージ化して CodeSite ディスパッチャ (CodeSite のメッセージ ディストリビュータ) に送信できます。これにより、これらのメッセージを 1 つ以上の受信者にルーティングして表示できます。デフォルトのメッセージ受信者は CodeSite Viewer です。 CodeSite の効率性は、メッセージを表示したり、変数を確認するためのブレークポイントを設定したりする単純なダイアログ ボックスとは異なり、Delphi に付属するイベント ログ機能 (Event Log) に似ているという事実に反映されています。イベント ログよりも強力であることは間違いなく、そのメッセージは持続可能であり、保存できるため、遡及分析が容易になります。 CodeSite の具体的な使用法を紹介する前に、まずその 3 つのコンポーネントを見てみましょう。 CodeSite オブジェクト 前述したように、実行中のアプリケーションから CodeSite メッセージを送信するには、TCodeSite クラスのインスタンス (CSIntf ユニットで定義) を使用します。メッセージは CodeSite に送信されます。ディスパッチャ。たとえば、オブジェクトの SendMsg メソッドを使用して、単純な文字列メッセージを送信できます。 TCodeSite オブジェクトは、データ変換を行わずにさまざまなタイプの情報送信をサポートする多数のメソッドを実装しています。たとえば、オブジェクトの SendObject メソッドには 2 つのパラメータがあります。1 つはメッセージ文字列で、もう 1 つはオブジェクト インスタンスへの参照です。このメソッドは、公開されたすべての属性を取得し、これらの属性の情報を CodeSite メッセージにパッケージ化します。 CodeSite Dispatcher ほとんどの場合、CodeSite Dispatcher はシステム トレイ領域で静かに実行されます。その唯一の機能は、さまざまな TCodeSite オブジェクトから送信された CodeSite メッセージを宛先にルーティングすることです。デフォルトでは、CodeSite メッセージは CodeSite Viewer に送信されます。 CodeSite Dispatcher は TCodeSite などのオブジェクトによって自動的に開始されるため、CodeSite Dispatcher を開始する必要さえありません。 TCodeSite クラスは、送信された CodeSite メッセージが CodeSite Dispatcher によってログ ファイルなどのさまざまな宛先にルーティングされる方法を開発者が構成できるようにする DestinationDetails プロパティを定義します。ただし、通常はこのプロパティを変更する必要はありません。 CodeSite Viewer CodeSite はさまざまなターゲットへのメッセージの送信をサポートしていますが、ほとんどの場合、CodeSite Viewer が主な送信ターゲットになります。ログ ファイルや別のマシンなどの他の宛先に送信された場合でも、CodeSite Viewer は依然としてメッセージを表示および分析するための主要なツールです。 CodeSite Viewer は、メッセージ リスト、メッセージ ビューア、コール スタック、およびスクラッチ パネルの 4 つのパネルで構成されます。 CodeSite Viewer のメイン ワークスペースはメッセージ リストです。これは、Viewer に送信されたすべてのメッセージ、またはログ ファイルからロードされたメッセージを表示するために使用されます。 メッセージ ビューアは、メッセージに関連付けられた追加情報を表示するために使用されます。たとえば、現在のメッセージが SendObject メソッドによって送信された場合、メッセージ ビューアには、オブジェクトの公開されているすべてのプロパティの現在の値が表示されます。 呼び出しスタック パネルには、csmEnterMethod メッセージに基づいたスタック ビューが表示されます。スクラッチ パネルは、持続不可能な情報を表示するために使用されます。スクラッチ パネルは、特定の情報を追跡したいがメッセージ ログには記録したくない場合、たとえば、マウスの現在位置など、大量の繰り返しメッセージを表示したい場合に非常に便利です。この時点で、TCodeSite オブジェクトの WritePoint メソッドを使用し、Line ID パラメーターを指定して、マウス情報を収容するために使用されるスクラッチ パネルの行数を指定できます。 簡単な例を使用して、プログラムから CodeSite Viewer にメッセージを送信する方法を示します。 (1) 新しいプロジェクトを作成し、コンポーネント パネルを CodeSite ページに切り替えます (CodeSite は、TCSGlobalObject のインストール後にシステムに 2 つのコンポーネントをインストールします)および TCS オブジェクト)。 TCSGlobalObject コンポーネントを選択し、フォーム上に配置します。 TCSGlobalObject コンポーネントは、グローバル TCodeSite オブジェクトとの設計時の対話を提供します (グローバル TCodeSite は CSInft ユニットで初期化されます)。 (2) ボタンを追加し、その OnClick イベントに次のコードを記述します。 //CodeSite はグローバル TCodeSite オブジェクトです。 CodeSite.SendMsg('CodeSite's first message'); (3) この単純なプログラムをコンパイルして実行します。実行後にボタンをクリックすると、CodeSite Dispatcher と CodeSite Viewer が実行されます。同時に、CodeSite Viewer のメッセージ リストにプログラムによって送信されたメッセージが表示されます (注: プログラムを実行する前に CodeSite Dispatcher と CodeSite Viewer を起動する必要はありません。これは、プログラムの実行時に TCodeSite オブジェクトが自動的にこれらを起動するためです)メッセージを送信する必要があります)。実行結果を以下の図 4.38 に示します。
(4) 次に、プログラムを停止し、OnClick イベント処理プロセスに次のコードを追加します。 CodeSite.SendObject('Form1', Form1) (5) プログラムを再コンパイルして実行し、もう一度ボタンをクリックします。 CodeSite Viewer には 2 つのメッセージが表示されました。 Form1に対応するメッセージには、Form1のオブジェクト情報が含まれる。 (6) Form1 の関連オブジェクト情報を確認するには、CodeSite Viewer のメニュー コマンド [表示] | [インスペクター] を選択して、メッセージ リストの右側に新しいパネルを表示します。ここには、Form1 のパブリッシュされた属性が表示されます。以下の図 4.39:
(7) プログラムを再度停止し、OnClick プロセスのコードを次のように変更します。 CodeSite.EnterMethod('Button1Click') CodeSite.SendMsg('CodeSite's first message'); ; コードサイト .ExitMethod('Button1Click' ); (8) 今度はプログラムを実行してボタンをクリックすると、以下の図 4.40 に示すように、「CodeSite's first message」と「Form1」メッセージが「Button1Click」メッセージの間にインデントされていることがわかります。
EnterMethod メソッドと ExitMethod メソッドへの呼び出しを追加すると、メソッドが呼び出されたときに記録するログを生成できます。 例を見てみると、CodeSite の機能が非常に強力であることがわかります。プログラムにいくつかのステートメントを追加するだけで、非常に詳細な情報を生成し、CodeSite Viewer を通じて鮮明なグラフで表示できます。次に、CodeSite の高度なアプリケーション テクノロジーについて説明します。 ログ ファイルへのメッセージの送信 どのプログラムにも多かれ少なかれバグが存在します。現時点で発生しなくても、その時点で発生する可能性があります。また、短期間で発生する場合もあります。繰り返し表示されますが、非常に偶然に発見されることもあります。もしある人が、自分が書いたプログラムがいつでも問題なく動作すると言ったら、それは嘘になります。バグは偶発的で隠れた性質を持っているため、ユーザーから提出されたバグを繰り返すのは困難であることが多く、プログラムをデバッグして問題の原因を見つけるのに大きな障害が生じます。また、CodeSite はメッセージを送信できます。これにより、ユーザーは実行時に生成された情報ファイルを送信するだけで済むため、バグの報告が容易になります。それに応じて、CodeSite Viewer を使用してエラーの原因と場所を直感的に分析できるようになり、プログラムのデバッグ作業が容易になります。 メッセージの送信先を変更するには、TCodeSite オブジェクトの DestinationDetails プロパティを設定します。この機能を使用するには、CodeSite の無料配布可能な部分である CodeSite Dispatcher を顧客のマシンにインストールする必要があります。次の具体的なプロセスは、前述の例に基づいています。 (1) 次のコードを次の形式の OnCreate イベントに追加します。 CodeSite.DestinationDetails := 'File[Path=C:/FirstLog.csl]' (2)プログラムをコンパイルして実行します。今回はボタンをクリックすると、メッセージは CodeSite Viewer に送信されず、C ドライブの FirstLog.csl ファイルに送信されます。 (3) CodeSite Viewer を使用して FirstLog.csl ファイルを読み込みます。今回は前と同様に、保存された CodeSite メッセージを表示します。 (4) CodeSite Viewer とログ ファイルにメッセージを同時に送信したい場合は、前のコードを次のように変更します。 CodeSite.DestinationDetails := 'Viewer,File[Path=C:/FirstLog.csl]'; -カスタマイズされたデータ TCodeSite クラスは、さまざまなデータ型を処理するための多数のメソッドを提供しますが、場合によっては、特定のカスタム形式でデータ情報を送信する必要がある場合があります。この目的のために、TCodeSite クラスは SendCustomData メソッドを定義します。このメソッドは、任意のデータ型の送信をサポートし、CodeSite Viewer がデータを正しく表示できるようにカスタム フォーマッタに従ってデータをフォーマットします。 まず、TCSFormatter オブジェクトのサブクラスを作成し、次にオブジェクトの FormatData、InspectorType、および TypeName メソッドをオーバーロードする必要があります。次に、CodeSite オブジェクト マネージャー オブジェクト CSObjectManager を呼び出して、新しい TCSFormatter サブクラスを登録します。さらに、RegisterCustomFormat メソッドを呼び出して、新しいメッセージ タイプを登録する必要もあります。 以下は、TCSEmployeeRecord レコード タイプのカスタマイズされたフォーマッタがユニット CSEmployee.pas に実装されている例です。 、Uses セクションに CSIntf ユニットへの参照を追加します。 2 番目のステップでは、フォーマッタごとに新しい CodeSite メッセージ タイプの定数を定義します。定数は csmUser より大きく、32,000 より大きくない必要があることに注意してください。タイプ TCSEmployee = レコード名: 文字列; 市区町村: 文字列; 電話番号: 休暇日数: 整数; Boolean; end; 上記のレコードは、送信するカスタム データ型です。 TCSEmployee SummaryFormatter ; パブリック関数 InspectorType: TCSInspectorType; 関数 TypeName: オーバーライド;上記は 2 つのカスタム フォーマッタ クラスの定義です。最初のフォーマッタは TCSEmployee レコードをテキスト形式にフォーマットし、2 番目のフォーマッタは TCSEmployee レコードをグリッド スタイルにフォーマットします。実装では SysUtils を使用します。 {=========================================} = TCSEmployeesummaryFormatter メソッド ==} {==========================================}関数 TCSEmployee SummaryFormatter .InspectorType: TCSInspectorType; 開始結果 := itStockStringList;カスタム フォーマッタを実装する最初のステップは、フォーマットされたデータを表示するためにどのタイプの組み込みビューアを使用するかを決定することです。この場合、文字列リスト ビューアが使用されます。ビューアの種類は、FormatData メソッドによって使用されます。プロシージャ TCSEmployee SummaryFormatter.FormatData( var Data ); var EmpRec: TCSEmployee := TCSEmployee( Data ); AddLine( EmpRec.City + ', ' + EmpRec.State + ' ' + EmpRec.ZipCode ); AddLine( '電話番号: ' + EmpRec.PhoneNumber ); AddLine( '給与: ' + Format( '%) m', [ EmpRec.Salary ] ) ); AddLine( '' ); 休暇日: ' + IntToStr( EmpRec.VacationDays ) ); AddLine( 'Sick Days: ' + IntToStr( EmpRec.SickDays ) ); if EmpRec.Manager then AddLine( 'マネージャー: はい' ) else AddLine( 'マネージャー: いいえ' ); ; FormatData メソッドはコア部分です。FormatData メソッドに渡される Data パラメータは型なしの変数パラメータであることに注意してください。これは、このパラメーターが任意のデータ型である可能性があることを意味し、形式登録プロセスを通じて、強制された型が変換エラーなしでカスタム データ レコードに確実にマッピングされるようにすることができます。 データ型を変換した後、データをフォーマットできます。ここでは、TCSFormatter 基本クラスの AddLine メソッドを使用して、フォーマット用の文字列の間に区切り線を追加します。 function TCSEmployeesummaryFormatter.TypeName: string; begin Result := 'TCSEmployee'; TypeName メソッドのオーバーロードはオプションですが、通常はメッセージ リストに表示される文字列を返すために使用できます。 {=========================================} {== TCSEmployeeDetailsFormatter メソッド == {==========================================} 関数 TCSEmployeeDetailsFormatter.InspectorType: TCSInspectorType ; 開始結果 := itStockGrid 終了;従業員詳細フォーマッタの場合は、名前付きグリッド ビューアを使用してデータを表示します。 ; AddNameValuePair( 'FirstName', EmpRec.FirstName ); AddNameValuePair( '住所', EmpRec.Address ); AddNameValuePair( '州', EmpRec.State ); EmpRec.PhoneNumber ); 'HireDate', EmpRec.HireDate ); AddNameValuePair( 'Salary', Format( '%m', [ EmpRec.Salary ] ) ); AddNameValuePair( 'SickDays', EmpRec.SickDays ); AddNameValuePair( 'マネージャー', EmpRec.Manager ); ここでは、グリッド ビューアでデータをフォーマットするために、AddNameValuePair メソッドを使用します。 function TCSEmployeeDetailsFormatter.TypeName: string; begin Result := 'TCSEmployee'; ここでは、グローバル TCodeSite オブジェクト インスタンス CodeSite が呼び出されます。 =============} {== サポート メソッド ==} {======================} プロシージャ CSSendEmployeesummary ( constメッセージ: 文字列; EmpRec: TCSEmployee ); begin CodeSite.SendCustomData( csmEmployee Summary, Msg, EmpRec ); end; プロシージャ CSSendEmployeeDetails( const Msg: string; EmpRec: TCSEmployee );最後に、CSObjectManager.RegisterCustomFormatter メソッドを呼び出して、フォーマッタを CodeSite オブジェクト マネージャーに登録することを忘れないでください。初期化 CSObjectManager.RegisterCustomFormatter( csmEmployee Summary, TCSEmployee SummaryFormatter ); CSObjectManager.RegisterCustomFormatter( csmEmployeeDetails, TCSEmployeeDetailsFormatter );