Recipe 13.6. Uncovering Problems Within Dual-Use Components


Problem

Because you intend to use a business component in web and non-web applications, you want to enable tracing within the component without having to reference its current HTTP context.

Solution

Modify web.config, as shown in Example 13-12, to add the WebPageTraceListener listener to the Listeners collection and make it available to your application.

In your non-web-specific components, add plain-vanilla TRace.Write statements to output any desired information to the trace log, as shown in our sample component in Examples 13-13 (VB) and 13-14 (C#).

A web form and the associated VB and C# code-behind we've written to test the tracing in our non-web-specific component are shown in Examples 13-15, 13-16 through 13-17.

Discussion

The .NET Framework uses the concept of trace listeners in its handling of trace messages. By default, the TraceListeners collection contains a single listener (DefaultTraceListener) when you enable tracing. Additional listeners can be added via the web.config file or programmatically. When a TRace.Write is executed, all listeners in the TRaceListeners collection receive and process the message. This mechanism allows you to add trace statements to your components without the need to add a reference to the System.Web assembly.

ASP.NET 1.x does not provide any functionality to write trace information within your application's business and data tiers and display it in the page trace data. If you need this functionality for your 1.x application, you will have to write a custom trace listener. ASP.NET 2.0 provides the WebPageTraceListener class to support writing trace information from anywhere in your application and displaying it in the page trace information.

The custom WebPageTraceListener is available by adding the entry to web.config, shown in Example 13-12.

When adding a WebPageTraceListener to your web.config file, you must specify the type correctly. The type attribute must be specified as shown here:

 type="namespace, assembly" 

The namespace must be the fully qualified namespace of the WebPageTraceListener. The assembly must be the name of the assembly containing the WebPageTraceListener (System.Web).


Our example business service class is nearly identical to the one we used in Recipe 13.4. Here are the differences:

  • The imports (or using) statement at the beginning of the class is changed from System.Web to System.Diagnostics. (The System.Diagnostics namespace provides the abstract base class for the trace listeners.)

  • The HttpContext.Current.Trace.Write statements are changed to trace.Write.

Our test web form, like our example business service class, is nearly identical to our test web form used in Recipe 13.4. The only difference is that it uses our example business service class.

There are two advantages to the approach this recipe takes over the previous recipe:

  • You can use plain-vanilla TRace.Writes in your component; they don't have to reference the current HTTP context, thus maintaining the component's compatibility for non-web uses.

  • You can turn tracing on and off via a configuration file.

All classes containing Trace statements must be compiled with tracing enabled. If tracing is not enabled, the Trace statements will not be compiled into the output and, thus, will not be executed in the application.

Trace statements can be enabled by explicitly adding the TRACE compiler directive to the top of the classes in which you want tracing enabled:

 

#CONST TRACE = true

#define TRACE

Alternately, tracing can be enabled for the entire application in web.config:

 

<configuration> … <system.codedom> <compilers> <compiler language="VB" extension=".vb" compilerOptions="/d:Trace=true" type="Microsoft.VisualBasic.VBCodeProvider, System, Version=2.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089" /> </compilers> </system.codedom> </configuration>

<configuration> … <system.codedom> <compilers> <compiler language="c#;cs;csharp" extension=".cs" compilerOptions="/d:TRACE" type="Microsoft.CSharp.CSharpCodeProvider, System, Version=2.0.3500.0, Culture=neutral, PublicKeyToken=b77a5c561934e089" />

</compilers> </system.codedom> … </configuration>


See Also

Recipe 13.4

Example 13-12. Web.config settings to add the trace listener

 <trace autoflush="true" indentsize="0"> <listeners> <add name="WebPageTraceListener" type="System.Web.WebPageTraceListener,  System.Web,  Version=2.0.3600.0,  Culture=neutral,  PublicKeyToken=b03f5f7f11d50a3a" /> </listeners> </trace> 

Example 13-13. Business service class with plain-vanilla Trace.Writes (.vb)

 Option Explicit On Option Strict On Imports System Imports System.Diagnostics Namespace ASPNetCookbook.VBExamples ''' <summary> ''' This class provides a "non-web" component for demonstrating outputting ''' trace information from within a class ''' </summary> Public Class CH13TestNonWebComponentVB Private mStr As String '''*********************************************************************** ''' <summary> ''' This property provides the ability to get/set the string in the object ''' </summary> Public Property theString( ) As String Get Return (mStr) End Get Set(ByVal Value As String) mStr = Value End Set End Property 'theString '''*********************************************************************** ''' <summary> ''' This routine provides the ability to add the passed string to the ''' private string in this object one or more times. ''' </summary> ''' ''' <param name="stringToAdd">Set to the string that is part of this object ''' </param> ''' <param name="numberOfCopies">Set to the number of copies to add ''' </param> Public Sub addToString(ByVal stringToAdd As String, _ ByVal numberOfCopies As Integer) Dim counter As Integer Dim startTime As DateTime Dim elapsedTime As TimeSpan Dim averageTime As Double 'output trace message indicating the start of the concatenations Trace.Write("In Non-web Component", _ "Before performing concatenations") 'concatenation the passed string as requested startTime = DateTime.Now( ) For counter = 1 To numberOfCopies mStr &= stringToAdd Next 'output trace message indicating the end of the concatenations Trace.Write("In Non-web Component", _ "After performing concatenations") 'calculate the elapsed time for the string concatenations elapsedTime = DateTime.Now.Subtract(startTime) 'Write average time per concatenation in milliseconds to trace sequence averageTime = elapsedTime.TotalMilliseconds / numberOfCopies Trace.Write("In Non-web Component", _ "Aver/concat = " &averageTime.ToString("0.0000")) End Sub 'addToString '''*********************************************************************** ''' <summary> ''' This constructor creates the object and initializes the variables ''' in the object ''' </summary> Public Sub New( ) 'initialize string in object mStr = "" End Sub 'New End Class 'CH13TestNonWebComponentVB End Namespace 

Example 13-14. Business service class with plain-vanilla Trace.Writes (.cs)

 using System; using System.Diagnostics; namespace ASPNetCookbook.CSExamples { /// <summary> /// This class provides a "non-web" component for demonstrating outputting /// trace information from within a class /// </summary> public class CH13TestNonWebComponentCS { private String mStr; ///*********************************************************************** /// <summary> /// This property provides the ability to get/set the string in the object /// </summary> public String theString { get { return(mStr); } set { mStr = value; } } // theString ///*********************************************************************** /// <summary> /// This routine provides the ability to add the passed string to the /// private string in this object one or more times. /// </summary> /// /// <param name="stringToAdd">Set to the string that is part of this object /// </param> /// <param name="numberOfCopies">Set to the number of copies to add /// </param> public void addToString(String stringToAdd, int numberOfCopies) { int counter; DateTime startTime; TimeSpan elapsedTime; Double averageTime; // output trace message indicating the start of the concatenations Trace.Write("In Non-web Component", "Before performing concatenations"); // concatenation the passed string as requested startTime = DateTime.Now; for (counter = 1; counter <numberOfCopies; counter++) { mStr += stringToAdd; } // output trace message indicating the end of the concatenations Trace.Write("In Non-web Component", "After performing concatenations"); // calculate the elapsed time for the string concatenations elapsedTime = DateTime.Now.Subtract(startTime); // Write average time per concatenation in milliseconds to trace sequence averageTime = elapsedTime.TotalMilliseconds / numberOfCopies; Trace.Write("In Non-web Component", "Aver/concat = " + averageTime.ToString("0.0000")); } // addToString ///*********************************************************************** /// <summary> /// This constructor creates the object and initializes the variables /// in the object /// </summary> public CH13TestNonWebComponentCS( ) { // initialize string in object mStr = ""; } // CH13TestNonWebComponentCS } // CH13TestNonWebComponentCS } 

Example 13-15. Code to test tracing in the non-web component (.aspx)

 <%@ Page Trace="true" Language="VB" MasterPageFile="~/ASPNetCookbookVB.master" AutoEventWireup="false" CodeFile="CH13TestTraceWithinNonWebComponentVB.aspx.vb" Inherits="ASPNetCookbook.VBExamples.CH13TestTraceWithinNonWebComponentVB" Title="Test Trace Within NonWeb Component" %> <asp:Content  runat="server" ContentPlaceHolder> <div align="center" > Tracing Within Non-Web Components (VB) </div> </asp:Content> 

Example 13-16. Code to test tracing in the non-web component code-behind (.vb)

 Option Explicit On Option Strict On Imports System Namespace ASPNetCookbook.VBExamples ''' <summary> ''' This class provides the code-behind for ''' CH13TestTraceWithinNonWebComponentVB.aspx ''' </summary> Partial Class CH13TestTraceWithinNonWebComponentVB Inherits System.Web.UI.Page '''*********************************************************************** ''' <summary> ''' This routine provides the event handler for the page load event. It ''' is responsible for initializing the controls on the page. ''' </summary> ''' ''' <param name="sender">Set to the sender of the event</param> ''' <param name="e">Set to the event arguments</param> Private Sub Page_Load(ByVal sender As Object, _   ByVal e As System.EventArgs) Handles Me.Load Dim nonWebComponent As CH13TestNonWebComponentVB 'create the "non-web aware" component nonWebComponent = New CH13TestNonWebComponentVB 'add a string to the string in the component 1000 times nonWebComponent.addToString("1234567890", _ 1000) End Sub 'Page_Load End Class 'CH13TestTraceWithinNonWebComponentVB End Namespace 

Example 13-17. Code to test tracing in the non-web component code-behind (.cs)

 using System; using System.Configuration; namespace ASPNetCookbook.CSExamples { /// <summary> /// This class provides the code-behind for /// CH13TestTraceWithinNonWebComponentCS.aspx /// </summary> public partial class CH13TestTraceWithinNonWebComponentCS : System.Web.UI.Page { ///*********************************************************************** /// <summary> /// This routine provides the event handler for the page load event. /// It is responsible for initializing the controls on the page. /// </summary> /// /// <param name="sender">Set to the sender of the event</param> /// <param name="e">Set to the event arguments</param> protected void Page_Load(object sender, EventArgs e) { CH13TestNonWebComponentCS nonwebComponent = null; // create the "non-web aware" component nonwebComponent = new CH13TestNonWebComponentCS(); // add a string to the string in the component 1000 times nonWebComponent.addToString("1234567890", 1000); } // Page_Load } // CH13TestTraceWithinNonWebComponentCS } 



ASP. NET Cookbook
ASP.Net 2.0 Cookbook (Cookbooks (OReilly))
ISBN: 0596100647
EAN: 2147483647
Year: 2003
Pages: 202

flylib.com © 2008-2017.
If you may any questions please contact us: flylib@qtcs.net