Establishing ASP.NET 2.0 WebPart Communication

I use a number of Web sites every day. Each Web site has a header, footer, some kind of navigation, and an area where I actually do my work. I am almost certain that each of these sites has “widgetized” or componentized its functional UI into smaller breakable pieces. For instance, the navigation is probably something a site reuses all over, so it is probably driven out of the same binaries, or code logic, on every part of the Web site. Clicking on the navigation widget would change what you see in the main content area.

So, if a site has two widgets, one for the menu/navigation and another for the content area, they obviously need to be able to communicate with each other. Also, clicking on one widget frequently updates more than one content area on a Web page. So, as a Web application developer, you need some kind of mechanism that allows these various widgets to communicate with each other.

The good news is the ASP.NET 2.0 WebPart framework comes with built-in support for such scenarios. You can have WebParts consume or provide data to other WebParts, and at design or run time, you can establish connections enabling various WebParts to communicate with them as necessary. These WebParts fall within two major categories:

  1. Providers, which make information available to other WebParts
  2. Consumers, which need and make use of that information

A number of consumers can consume information provided by a single provider. The information exchanged is defined by a communication contract, which is described in code as an interface. With these pieces in place, you can begin WebPart communication on your Web page. This article describes how.

To follow along, you need to have set up a WebPart framework and dropped a connections zone on the page already. Also, you need a link button, or some other mechanism on your Web page, that sets the WebPartManager in the “Connect” display mode. (If this sounds like Greek, I strongly recommend that you read my article on ASP.NET 2.0 WebPart framework basics first.)

ASP.NET 2.0 WebPart Connections Basics

The following four elements establish communication among WebParts:

  1. The communication contract: The first thing you need to do is decide what information the WebParts need to exchange, and then represent that in an interface you write. Because an interface you write serves as the communication contract, you have complete freedom to choose the structure of the information interchanged between WebParts. If two WebParts that need to communicate do not use the same interface to share information, they can still communicate using transformer objects, which are classes that inherit from the WebPartTransformer class.
  2. The Provider: A provider WebPart provides the information to be communicated by providing the consumer with an instance of a class that implements this interface. It provides this information in a method that is decorated with the ConnectionProvider attribute. Now, the class that implements the communication contract could be the provider itself, in which case it simply returns an instance of itself.
  3. The Consumer: The consumer WebPart simply needs to have a method that lets it get a hold of the provider, or a class that the provider intends the consumer to get. It creates a method that is decorated with the ConnectionConsumer attribute and accepts a parameter of the type held by the interface that describes the communication contract. Once the consumer has an instance that is of the type described by the communication contract, it can access various properties and methods to gain access to the information being communicated.
  4. Establish the communication: Once you have the communication contract written and the provider and consumer WebParts added to your Web page, you need to establish communication between the two or more WebParts. You can do this statically through the <StaticConnections> section within the WebPartManager, or at runtime through the browser using a ConnectionsZone.

With a grasp of the theory, you’re ready to write two simple WebParts that communicate a string of text between them.

ASP.NET 2.0 WebPart Communication: A Code Example

To solidify your understanding of WebPart communication, take an exemplary problem. You will write two WebParts. One will show a textbox and an update button that provides information to the second WebPart, which simply consumes this information and displays it as text. By going through the four steps described above, you can write such an infrastructure.

The communication contract

The information you intend to communicate is a simple string. This means your communication contract can look like this:

public interface ITextContract
{
   string TheContent {get;set;}
}

Note that the ASP.NET 2.0 WebPart framework ships with some standard interfaces, such as IWebPartFIeld, IWebPartRow, IWebPartParameters, IWebPartTable, and so forth. Also, SharePoint 2007 libraries define a few such standard interfaces to help you establish a commonality and to get you off the ground easily by using one of the interfaces declared in the framework.

Writing the provider WebPart

The provider WebPart creates a method decorated by the ConnectionProvider attribute, which returns an instance of a class that implements the interface ITextContract you declared above.

Now, this class, which implements the interface, can be either the provider WebPart itself or some other class. Simply create a WebPart that implements the ITextContract interface to serve as the provider:

public class TheProvider: WebPart, ITextContract
{
    // Implementation goes here.
}

In this WebPart, you need a textbox to allow the user to input new string values and a button to cause a postback. You can do this very easily by using the following code:

private TextBox contentTextLabel;
private Button btnUpdate;

protected override void CreateChildControls()
{
   contentTextLabel      = new TextBox();
   contentTextLabel.Text = "Sample Text";
   btnUpdate             = new Button();
   btnUpdate.Text        = "Update Text";

   this.Controls.Add(contentTextLabel);
   this.Controls.Add(btnUpdate);
}

Also, implement the “TheContent” property that ITextContract requires as follows:

public string TheContent
{
   get { return contentTextLabel.Text; }
   set { contentTextLabel.Text = value; }
}

As you can see, you simply set and return the value contained in contentTextLabel, which is the value the user just entered.

Finally, add the requisite method decorated with the ConnectionProvider attribute, which returns an instance of ITextContract. This method will simply return an instance of the provider WebPart you are writing:

[ConnectionProvider("The Content")]
public ITextContract GetTextCommunicationPoint()
{
   return this as ITextContract;
}

Putting all these pieces together, the following is the full code for your provider WebPart:

public class TheProvider: WebPart, ITextContract
{
   private TextBox contentTextLabel;
   private Button btnUpdate;

   protected override void CreateChildControls()
   {
      contentTextLabel      = new TextBox();
      contentTextLabel.Text = "Sample Text";
      btnUpdate             = new Button();
      btnUpdate.Text        = "Update Text";

      this.Controls.Add(contentTextLabel);
      this.Controls.Add(btnUpdate);
   }

   public string TheContent
   {
      get { return contentTextLabel.Text; }
      set { contentTextLabel.Text = value; }
   }

   [ConnectionProvider("The Content")]
   public ITextContract GetTextCommunicationPoint()
   {
      return this as ITextContract;
   }
}

Writing the consumer WebPart

The Consumer WebPart is a rather simple WebPart that simply renders the text provided by the provider. To render information, it first needs an instance of ITextContact—in this case, an instance of the provider itself. You do this by creating a method decorated by the ConnectionConsumer attribute that accepts a single parameter of type ITextContract:

private ITextContract theProvider ;

[ConnectionConsumer("The Content")]
public void InitializeProvider(ITextContract provider)
{
   theProvider = provider ;
}

To render some text, you can simply add an instance of a Label control to the controls collection of the WebPart:

private Label lblText;

protected override void CreateChildControls()
{
   lblText = new Label();
   this.Controls.Add(lblText);
}

Now, any value set to lblText.Text will render at runtime. What is left is hooking up the ITextContract instance in the theProvider variable and lblText.Text property. You easily can achieve this in the OnPreRender method:

protected override void OnPreRender(EventArgs e)
{
   base.OnPreRender(e);

   if (theProvider != null)
   {
      lblText.Text = theProvider.TheContent ;
   }
}

Putting all these pieces together, the following is the complete code for your consumer WebPart:

public class TheConsumer : WebPart
{
   private ITextContract theProvider ;
   private Label lblText;

   protected override void CreateChildControls()
   {
      lblText = new Label();
      this.Controls.Add(lblText);
   }

   [ConnectionConsumer("The Content")]
   public void InitializeProvider(ITextContract provider)
   {
      theProvider = provider ;
   }

   protected override void OnPreRender(EventArgs e)
   {
      base.OnPreRender(e);

      if (theProvider != null)
      {
         lblText.Text = theProvider.TheContent ;
      }
   }
}

With the provider and consumer written up, you are ready to begin establishing communication between these WebParts.

More by Author

Get the Free Newsletter!

Subscribe to Developer Insider for top news, trends & analysis

Must Read