Chapter 49. Documenting the Source Code with XML Comments

One of the most common programming rules states that documenting the source code is fundamental. This is the truth, but you have to think about the way source code is commented. Classical comments are useful to explain what code does so that you can easily remember how your code works if you need to reuse it after a long time, or they can help other developers to understand your code. But this is not the only way of documenting code in .NET development. A sophisticated environment such as Visual Studio offers the IntelliSense technology that speeds up the way you write code and shows instructions on how you use objects and members. This is possible because of special kinds of comments that you can add to your code, known as XML comments. Such comments enable you to write the source code documentation, explain objects’ and members’ behavior, and provide descriptions and examples that can be displayed by IntelliSense. But that is not all. Documenting code with XML comments is particularly important if you develop reusable compiled libraries and enables you to automate the process of building compiled documentation files (such as .chm files) in a similar way to the MSDN documentation. In this chapter, you learn to use XML comments to provide simple and complex source code documentation, also learning how to build compiled documentation.

Understanding XML Comments

XML comments are not new in Visual Basic 2012; they were first natively introduced with Visual Basic 2005. (In versions prior to 2005, XML comments were possible only via third-party add-ins.) To understand why XML comments are an essential topic, let’s take a look at a method invocation within the code editor. Figure 49.1 shows how IntelliSense appears on an uncommented method.

Image

Figure 49.1. Uncommented members make IntelliSense incapable of displaying useful information.

As you can see from Figure 49.1, IntelliSense will correctly display, but it will just show the method name in a tooltip, without providing information on the method usage. This is because the method was not commented with XML comments. Now take a look at Figure 49.2. It shows how IntelliSense can provide information if the method was commented with XML comments.

Image

Figure 49.2. Commented members are well described when IntelliSense displays in the code editor.

The difference is evident. Objects and members decorated with XML comments can provide full explanation on their usage. This works in the code editor when IntelliSense displays with both source files and with compiled executables. As mentioned at the beginning of this chapter, providing XML comments is useful not only for IntelliSense, but also when you investigate objects in the Object Browser or for automating the process of building compiled documentation for your libraries. Because of this, adding XML comments to your code is necessary in most cases, especially if you develop reusable assemblies. In the next sections, you learn practical techniques for commenting the source code and getting the most out of XML comments with Visual Basic.

Enabling XML Comments

When Visual Studio builds the project output, it also creates an XML document storing all XML comments. The XML document constitutes the actual code documentation. In Visual Studio 2012, XML comments are enabled by default. Before reading this chapter, ensure that XML comments are enabled in your project. To accomplish this, open My Project; select the Compile tab and, if it’s not checked, check the Generate XML Documentation file box. See Figure 49.3 for details.

Image

Figure 49.3. Enabling XML comments.

Behind the scenes, this requires the Visual Basic compiler to be launched by Visual Studio with the /doc option, which makes the compiler also generate the XML documentation. At this point, you are ready to implement XML comments in your Visual Basic code.

Implementing XML Comments

XML comments have a double purpose. The first one is enabling additional help within IntelliSense when you write code. The second one is generating an XML file storing information that can be built into a compiled documentation file, such as the .chm format that also enables navigation between documented items. In this section, you learn to implement XML comments and learn the various tags and why they are important, although in some cases they might not seem to be. Before implementing comments, create a new Console application and implement a Person class as follows:

Public Class Person

    Public Overridable Property FirstName As String
    Public Overridable Property LastName As String
    Public Overridable Property Age As Integer

    Public Overridable Function GetFullName() As String
        Dim fn As New Text.StringBuilder
        fn.Append(Me.FirstName)
        fn.Append(" ")
        fn.Append(Me.LastName)
        Return fn.ToString
    End Function
End Class

The Person class will be the base for our experiments. You implement an XML comment by typing three apostrophes. The Visual Studio code editor adds a comment skeleton to your code that first looks like the following example:

''' <summary>
'''
''' </summary>
''' <returns></returns>
''' <remarks></remarks>
Public Overridable Function GetFullName() As String
    Dim fn As New Text.StringBuilder
    fn.Append(Me.FirstName)
    fn.Append(" ")
    fn.Append(Me.LastName)
    Return fn.ToString
End Function

As you can see, these comments have typical XML structure according to the <tag> </tag> syntax. The summary XML tag enables describing what an object (or member) does. The description will be also available within IntelliSense. The remarks tag enables you to provide additional information on what you already specified in the summary, and the information will also be displayed within the Object Browser (but not within IntelliSense). The returns tag specifies the type returned by the member (being a method or a property); if the member is a method that does not return a value, Visual Studio will not add the returns tag. For a better understanding, populate comments as follows:

''' <summary>
''' Gets the complete person's name
''' </summary>
''' <returns>String</returns>
''' <remarks>This method returns the complete person's name</remarks>
Public Overridable Function GetFullName() As String
    Dim fn As New Text.StringBuilder
    fn.Append(Me.FirstName)
    fn.Append(" ")
    fn.Append(Me.LastName)
    Return fn.ToString
End Function

Now go to the Main method in your Console application, and write the following code that instantiates and populates the Person class:

Dim p As New Person With {.FirstName = "Alessandro", .LastName = "Del Sole",
                          .Age = 35}

Dim fullName As String = p.GetFullName

When typing code, IntelliSense provides information on the GetFullName method according to the XML comment’s content. This is represented in Figure 49.4.

Image

Figure 49.4. IntelliSense shows the information provided by the XML comments.

As you can see, IntelliSense shows the content of the summary tag, but it does not show the content of the returns and remarks tags. This makes sense in that IntelliSense’s tooltips are the fastest way for getting help. If you instead open the Object Browser on the Person class, you get a result that looks similar to Figure 49.5 (additional information appearing in the window is covered shortly). You obtain the same detailed information if you build a compiled documentation file, as described later in this chapter. The one shown before is the most basic implementation of XML comments. This great Visual Basic feature enables you to define complex documentation over your code, which can be particularly useful due to the integration with the Visual Studio environment.

Image

Figure 49.5. The Object Browser shows information provided by XML comments.


Scope

XML comments can be applied to both public and private objects and members.


Defining Complex Code Documentation

The MSDN documentation says that the Visual Basic compiler can parse any valid XML tag. The MSDN also recommends a series of tags that are specific to the code documentation. Table 49.1 summarizes the recommended tags.

Table 49.1. Recommended Tags for XML Comments

Image

Case-Sensitiveness

Tags within XML comments are case-sensitive and lowercase. Take note of this to ensure that the Visual Basic compiler correctly recognizes tags.



Note on Complex Documentation

You can appreciate complex documentation generated with XML comments only when building compiled help files. This is because within IntelliSense or in the Object Browser, only a few tags’ contents will be shown. For example, XML comments enable you to build bulleted lists or specify links to other documentation regarding different code. All this cannot be shown in IntelliSense, but it makes a lot of sense in a help file or a help system built on HTML pages. If you are interested in only building documentation for Visual Studio internal usage, you can theoretically limit XML comments to the basic implementations.


Let’s go back to the Person class and provide an XML comment for the FirstName property. The XML comment must look like this:

''' <summary>
''' Contains the person's first name
''' </summary>
''' <value>Person's first name</value>
''' <returns>String</returns>
''' <remarks></remarks>
Public Overridable Property FirstName As String

Here there is a new tag, value. The summary tag describes a property, and value describes the property’s value. Do the same thing on the LastName property, specifying the appropriate description, similarly to FirstName. Other tags can be added in a straightforward way, thanks to the always present IntelliSense. Figure 49.6 shows how IntelliSense provides available XML tags, according to the particular context where they have to be added.

Image

Figure 49.6. IntelliSense helps you select XML tags according to the particular context.

Referring to Code Elements

XML comments enable references to other code elements with specific tags. The first one is c that identifies the element within angle bracket as code. To show an example, rewrite XML comments for the GetFullName method as follows:

''' <summary>
''' Gets the complete person's name
''' </summary>
''' <returns>String</returns>
''' <remarks>This method concatenates <c>LastName</c> and
''' <c>FirstName</c> properties</remarks>
Public Overridable Function GetFullName() As String
    Dim fn As New Text.StringBuilder
    fn.Append(Me.FirstName)
    fn.Append(" ")
    fn.Append(Me.LastName)
    Return fn.ToString
End Function

Notice how the c tag embraces both the LastName and FirstName properties, communicating to the compiler that both tags represent a code element. It is enclosed and nested within a remarks tag (IntelliSense can be helpful in choosing the allowed tags). This is not the only way of referring to code; you can provide an entire code example that will be included in your documentation. To accomplish this, you first declare a sample tag, which contains the sample description and then a code tag that contains a code snippet demonstrating the member purpose. Edit the preceding XML comment as follows:

''' <summary>
''' Gets the complete person's name
''' </summary>
''' <returns>String</returns>
''' <remarks>This method concatenates <c>LastName</c> and
''' <c>FirstName</c> properties
''' <example>This example shows how you can invoke
''' the <c>GetFullName</c> method
''' <code>
''' Dim result As String = Person1.GetFullName()
''' </code>
''' </example>
''' </remarks>
Public Overridable Function GetFullName() As String

This is useful because your documentation also shows examples of your libraries.


Why Don’t I See Them?

Code, c, and example tags provide documentation that is not available within IntelliSense. It is, however, available within the generated XML file; thus you can appreciate them when building an HTML-based or compiled documentation or within the Object Browser.


XML comments enable you to easily refer to and document members’ arguments. For a better understanding, write the following overload of the GetFullName method that accepts a Title argument:

Public Overridable Function GetFullName(ByVal Title As String) As String

    If String.IsNullOrEmpty(Title) = True Then Throw New _
                                               ArgumentNullException

    Dim fn As New Text.StringBuilder
    fn.Append(Title)
    fn.Append(" ")
    fn.Append(Me.FirstName)
    fn.Append(" ")
    fn.Append(Me.LastName)
    Return fn.ToString
End Function

Now add an XML comment. It looks likes this:

''' <summary>
''' Gets the complete person's name
''' </summary>
''' <param name="Title"></param>
''' <returns>String</returns>
''' <remarks></remarks>
Public Overridable Function GetFullName(ByVal Title As String) As String

The param tag enables you to referr to a member’s argument, specified by the name attribute. If you try to type the name on your own, IntelliSense helps you choose the argument. XML comments also enable you to specify an exception that your member could encounter, according to the actions it takes. For example, the GetFullName method could throw a NullReferenceException if the Title argument is an empty or null string. For this, you use an exception tag to specify the exception. The tag is used with cref. This one is straightforward in that it enables you to point a reference to a .NET object using IntelliSense. The following tag (which must be added before the method definition) specifies which exception can be thrown:

''' <exception cref="ArgumentNullException">
''' The exception that is thrown when <paramref name="Title"/> is Nothing
''' </exception>
''' <returns>String</returns>
''' <remarks></remarks>
Public Overridable Function GetFullName(ByVal Title As String) As String

When typing cref, the IntelliSense window shows all the available objects. You pick the exception you are interested in. This speeds up the way you write your comment, also ensuring that you type a valid object name. You can also specify the description for the exception. The good news about cref is that it creates a cross-reference to the documentation related to the pointed object. For instance, when you create a compiled documentation file based on the XML comments, cref enables you to redirect to another page showing information on the pointed object. You can also refer to the argument by specifying the paramref tag within a descriptive text, which requires a name attribute pointing to the argument. paramref also takes advantages of IntelliSense.

Referring to an External Documentation File

The Visual Basic compiler can link documentation to your code from an external XML document. To do this, you use the include tag. The tag requires a file attribute that points to the external document and a path attribute that points to the position in the document providing documentation for the given member. The following code sets external documentation for the Age property:

''' <include file="ExternalDoc.xml" path="Help/Property[@name='Age']"/>
Public Overridable Property Age As Integer

To understand how the path tag works, here is the XML representation of the external document:

<?xml version="1.0" encoding="utf-8" ?>
<Help>
  <Property name="Age">
    <summary>Returns how old a person is</summary>
    <returns>Integer</returns>
  </Property>
  <!–– Other properties...––>
  <Property>

  </Property>
</Help>

Creating Lists

Documentation often requires bulleted and numbered lists or tables, as in any other kind of document. Luckily, XML comments enable you to easily build lists. You do this with the list tag that requires a type attribute specifying whether the list is a bulleted or numbered list or a two-column table. The following example shows how to build a numbered list on the Person class documentation:

''' <summary>
''' Represents a human being
''' </summary>
''' <remarks>
''' <list type="number">
''' <item><description>Instantiate the class</description></item>
''' <item><description>Populate its properties</description></item>
''' <item><description>Eventually retrieve the full
''' name</description></item>
''' </list>
''' </remarks>
Public Class Person
....
End Class

The type attribute can have one of the following values: bullet (bulleted list), number (numbered list), or table (two-column table). Notice how each item in the list is represented by an item tag that requires a nested description tag providing the actual description. If you want to provide a table, each item must contain a term tag and a description tag as in the following example:

''' <item><term>Action one</term></item>
''' <item><description>Instantiate the class</description></item>

The item’s content will be also shown in IntelliSense and the Object Browser, but it will be formatted as a list only in the compiled documentation.

Documenting Permissions Requirements

Sometimes your objects expose members that require special permissions to access system resources. You can provide documentation about required permissions by adding a permission tag with cref, pointing to the desired .NET permission. The following example shows how to comment the GetFullName method with the UIPermission requirement:

''' <permission cref="System.Security.Permissions.UIPermission"/>
Public Overridable Function GetFullName() As String

Of course, you can specify multiple permissions by adding multiple permission tags.

Specifying Links to Other Resources

When documenting the code, it is not unusual to provide links to other members. XML comments enable you to do this by specifying see and seealso tags. The see tag enables you to specify a link to another member’s documentation from within the description text. The seealso tag does the same, but it differs in that the link to the other member appears in the See Also section of the compiled page. The following example demonstrates this on the FirstName property providing a link to LastName:

''' <remarks>Use the <see cref="LastName"/>
''' property for the person's last name</remarks>
Public Overridable Property FirstName As String

If you want the link to be shown in the See Also section, replace see with seealso.

XML Comments and Generics

When you define your custom generics, you can use XML comments to describe the type parameter. This is accomplished via the typeparam tag, as shown in the following code snippet:

''' <summary>
''' A test class
''' </summary>
''' <typeparam name="T">
''' A type parameter that must implement IEnumerable
''' </typeparam>
''' <remarks></remarks>
Public Class TestGenerics(Of T As IEnumerable)

End Class

The Visual Basic compiler automatically recognizes the generic implementation and thus adds for you the typeparam tag when adding the XML comment.

Generating Compiled Help Files

When you document your source code with XML comments, you might want to generate compiled help files that you can distribute together with your libraries. Compiled help files are .chm files that can be easily opened with the Windows integrated Help Viewer. The .chm file format is the most appropriate in such situations because it is a standalone and does not require additional applications. Several tools can generate .chm files starting from XML comments. A very popular one is SandCastle, an open source tool from Microsoft that is also used to build documentation. At the moment in which this chapter is being written, SandCastle supports Visual Studio 2010 so our suggestion is to check out the SandCastle website (http://www.codeplex.com/sandcastle) periodically to see if an update is available. Also, a number of third party (paid) tools exist on the market. Popular tools are the following:

• Help + Manual from EC Software (http://www.ec-software.com)

• HelpNDoc (http://www.helpndoc.com)

These tools are very good in that they enable you to generate multiple output formats, not only .chm files.

Summary

This chapter covered how to use XML comments instead of classic comments. With XML comments, you specify tags that identify an element in the code as a special formatted element in the generated documentation file. Such a file is an XML document that enables IntelliSense documentation for your own code and constitutes the source for automating building compiled help files that accompany your libraries as the documentation. To automate this process, you were informed about the existence of Microsoft SandCastle, a free tool from Microsoft that is available on CodePlex as an open-source application, and of tools produced by other vendors.

..................Content has been hidden....................

You can't read the all page of ebook, please click here login for view all page.
Reset
3.148.102.166