You are on page 1of 26

Microsoft Virtual Labs

Event Handlers – C#
Event Handlers – C#

Table of Contents
Event Handlers – C# ..................................................................................................................... 1
Exercise 1 Asynchronous Event Handler ......................................................................................................................2
Exercise 2 Validation Event Handler........................................................................................................................... 14
Exercise 3 Feature Receiver ........................................................................................................................................ 21
Event Handlers – C#

Event Handlers – C#

Objectives After completing this lab, you will be better able to:
 Create a custom Content Type and use it in a custom list
 Write a code to process both asynchronous and synchronous Item events
 Write a code to execute when you activate a Feature

Scenario Event handlers in Windows SharePoint Services 3.0 (WSS) provide an


opportunity for you to execute custom code in response to various occurrences in
your WSS applications. WSS supports two types of events: before and after.
“Before events” occur prior to a WSS event being completed. It provides you
with the opportunity to cancel the event. “After events” occur once the event
completes. This allows you to post process data related to the event. Before
events are synchronous while after events are asynchronous. WSS defines a
number of events that you can use to control and validate data added to lists as
well as to help with installation and configuration. For more information about
events, visit http://msdn.microsoft.com/en-us/library/ms442323.aspx.

Estimated Time to 60 Minutes


Complete This Lab

Computers used in this


Lab WSS

Page 1 of 24
Event Handlers – C#

Exercise 1
Asynchronous Event Handler

Scenario
In this exercise, you will create an asynchronous event handler that executes when you add an item to a list. After
you add a new item to a list, your code will create a record in a SQL Server 2008 database that you will create. In
this scenario, you will use a custom list to track packages for shipping.

Tasks Detailed Steps


Complete the following a. Select Start | All Programs | Microsoft Visual Studio 2008 | Microsoft Visual
task on: Studio 2008.
b. Select File | New | Project.
WSS c. In the New Project dialog, select the SharePoint node under Visual C# in the
1. Asynchronous Event Project types section.
Handler d. Select Empty in the Templates section.
e. Change the Name to Shipping and the Location to
C:\SPHOLS\Labs\Lab03_EventHandler.
f. Uncheck Create directory for solution. Your New Project dialog should look
like the image below.

g. Click OK to create the project.


h. In the Solution Explorer, right-click on the Shipping project node and select
Add | New Item.
i. In the Add New Item dialog, choose the SharePoint tree node and select the
Content Type template.
j. Change the name to ShippingType and click Add.

Page 2 of 24
Event Handlers – C#
Tasks Detailed Steps

k. In the Content Type Settings dialog that appears after clicking Add, change the
Base Content Type to Item.
l. Place a check next to the Add with Event Receiver and click OK. Visual Studio
adds three new files, two code files and one XML file, under a folder called
ShippingType.

m. In the Solution Explorer, right-click on ShippingType.xml and select Open.


n. If you examine the file, you find two commented out sections of XML. The first
is for FieldRef items and the second is for Field items. You’re going to replace
both commented blocks with XML fragments that define the columns for the
content type.

Page 3 of 24
Event Handlers – C#
Tasks Detailed Steps

o. Replace the existing FieldRef commented block between the opening and closing
FieldRefs element tags with the following XML:
<FieldRef ID="{48B36503-65D4-4f0c-B73C-AB328217A34B}"
Name="ShipID" />
<FieldRef ID="{46dc1532-6304-4a1b-8d8e-eb124e35cae8}"
Name="ShipTo" />
<FieldRef ID="{12F81C62-EEDF-4b2d-B485-EAD0701E1C5E}"
Name="ShipStreet" />
<FieldRef ID="{93639B35-6338-4f18-B1D8-EC7AE0244C3A}"
Name="ShipCity" />
<FieldRef ID="{EBA1A352-E9B1-436f-8749-12816266921F}"
Name="ShipState" />
<FieldRef ID="{D01366B6-04A0-4ca4-B0E2-59E557BF685B}"
Name="ShipPostalCode" />
<FieldRef ID="{E316F9E6-1B25-4a03-898B-FF7BC9812F51}"
Name="ShipTracking" />
p. Next, replace the existing commented Field block with the following XML:
<Field ID="{48B36503-65D4-4f0c-B73C-AB328217A34B}"
Type="Text"
Name="ShipID"
DisplayName="Ship ID"
StaticName="ShipID"
Hidden="FALSE" Required="TRUE"
Sealed="FALSE" />
<Field ID="{46dc1532-6304-4a1b-8d8e-eb124e35cae8}"
Type="Text"

Page 4 of 24
Event Handlers – C#
Tasks Detailed Steps
Name="ShipTo"
DisplayName="Ship To"
StaticName="ShipTo"
Hidden="FALSE" Required="TRUE"
Sealed="FALSE" />
<Field ID="{12F81C62-EEDF-4b2d-B485-EAD0701E1C5E}"
Type="Text"
Name="ShipStreet"
DisplayName="Street"
StaticName="ShipStreet"
Hidden="FALSE" Required="TRUE"
Sealed="FALSE" />
<Field ID="{93639B35-6338-4f18-B1D8-EC7AE0244C3A}"
Type="Text"
Name="ShipCity"
DisplayName="City"
StaticName="ShipCity"
Hidden="FALSE" Required="TRUE"
Sealed="FALSE" />
<Field ID="{EBA1A352-E9B1-436f-8749-12816266921F}"
Type="Text"
Name="ShipState"
DisplayName="State"
StaticName="ShipState"
Hidden="FALSE" Required="TRUE"
Sealed="FALSE" />
<Field ID="{D01366B6-04A0-4ca4-B0E2-59E557BF685B}"
Type="Text"
Name="ShipPostalCode"
DisplayName="Postal Code"
StaticName="ShipPostalCode"
Hidden="FALSE" Required="TRUE"
Sealed="FALSE" />
<Field ID="{E316F9E6-1B25-4a03-898B-FF7BC9812F51}"
Type="Choice"
Name="ShipTracking"
DisplayName="Tracking"
StaticName="ShipTracking"
Hidden="FALSE" Required="TRUE"
Sealed="FALSE">
<CHOICES>
<CHOICE>Delivered</CHOICE>
<CHOICE>In-transit</CHOICE>
<CHOICE>Shipped</CHOICE>
<CHOICE>Waiting for Payment</CHOICE>
</CHOICES>

Page 5 of 24
Event Handlers – C#
Tasks Detailed Steps
</Field>
q. Select File | Save ShippingType\ShippingType.xml to save your work.
r. Select File | Close to close the ShippingType.xml file
s. In the Solution Explorer, right-click on the Shipping project and select Add
Reference.
t. In the Add Reference dialog, under the .NET tab, scroll down and select
System.Data and click OK.
u. In the Solution Explorer, right-click on the ItemEventReceiver.cs file under the
ShippingType folder and select Open.
v. At the top of the source file, under existing using statements, add the following
code:
using System.Data;
using System.Data.SqlClient;
w. Scroll down in the source file until you find the following block of commented
code:
//public override void ItemAdded(SPItemEventProperties
properties)
//{
//}
x. Uncomment the code and add the following code as the method body:
const string connectionString =
"Server=localhost;Database=Packages;Trusted_Connection=Tru
e";
const string baseSQL = "INSERT INTO Tracking " +
"(PackageID, PackageTitle, PackageStatus) VALUES" +
"(@PackageID, @PackageTitle, @PackageStatus);";

try
{
// Retrieve data from properties
string packageID =
properties.ListItem["ShipID"].ToString();
string packageTitle =
properties.ListItem.Title;
string packageStatus =
properties.ListItem["ShipTracking"].ToString();

using (SqlConnection con = new


SqlConnection(connectionString))
{
using (SqlCommand cmd = new SqlCommand(baseSQL, con))
{
SqlParameter prm =
new SqlParameter("@PackageID",
SqlDbType.NVarChar);
prm.Direction = ParameterDirection.Input;
prm.Value = packageID;

Page 6 of 24
Event Handlers – C#
Tasks Detailed Steps
cmd.Parameters.Add(prm);
prm = new SqlParameter("@PackageTitle",
SqlDbType.NVarChar);
prm.Direction = ParameterDirection.Input;
prm.Value = packageTitle;
cmd.Parameters.Add(prm);
prm = new SqlParameter("@PackageStatus",
SqlDbType.NVarChar);
prm.Direction = ParameterDirection.Input;
prm.Value = packageStatus;
cmd.Parameters.Add(prm);

con.Open();
int retVal = cmd.ExecuteNonQuery();
}
}
}
catch (Exception ex)
{
Console.WriteLine(ex.Message);
}

Note: The code you just added is mostly standard ADO.NET code that uses connection
and command objects to add a new record to the database. At the beginning of the
procedure, it accesses the passed in SPItemEventProperties object to read column
data related to the new item added to the list. Title is a standard, built-in field so you
can access it directly as a property of the ListItem. However, the other two properties
are custom, hence the different syntax. The code stores the data in local variables and
then passes it to the command object via SqlParameters. You’ll note that the code uses
SqlParameters to help against SQL injection attacks. You could (and should) do
additional validation against the data provided via the SPItemEventProperties.
y. Select File | Save ShippingType\ItemEventReceiver.cs to save your work.
z. Select File | Close to close the ItemEventReceiver.cs file.
aa. Select Build | Build Solution.
bb. Select Build | Deploy Solution. Watch the Visual Studio status bar for
information about the deploy process. Wait for the Deploy succeeded message as
in the image below.

Note: As part of the deploy process, the VSeWSS templates take care of installing your
assembly into the Global Assembly Cache. In addition, it deploys all of the supporting
files to the correct locations in your SharePoint installation. Because it resets your IIS

Page 7 of 24
Event Handlers – C#
Tasks Detailed Steps
application pool, it might take a bit longer to load up your SharePoint site after you
do your deployment.
cc. Select Start | Explorer to start the Windows Explorer.
dd. Navigate to C:\SPHOLS\Labs\Lab03_EventHandler.
ee. Double-click on the CreateDB.cmd file. Verify there were no errors. This script
creates a simple database called Packages with a table called Tracking that you
will use to enter shipping information.
ff. Close Windows Explorer.
gg. Select Start | All Programs | Internet Explorer.
hh. Once the SharePoint home page appears, select the Create command from the
Site Actions menu.

ii. On the Create page, click the Custom List link in the Custom Lists gallery.

jj. On the New page, enter Shipping in the Name field.


kk. Enter List to track packages being shipped in the Description field and click

Page 8 of 24
Event Handlers – C#
Tasks Detailed Steps
Create.
ll. Select the List Settings command from the Settings menu of the newly created
Shipping list.

mm. On the Customize Shipping page, select the Advanced settings link
under the General Settings gallery.

nn. On the List Advanced Settings page, set the Allow management of content
types? option to Yes.

Page 9 of 24
Event Handlers – C#
Tasks Detailed Steps

oo. Once you’ve set the option, click OK to commit your change.
pp. Back on the Customize Shipping page select the Add from existing site content
types link in the Content Types gallery.

qq. In the list of Available Site Content Types, select the ShippingType content
type and then click the Add > button.

Page 10 of 24
Event Handlers – C#
Tasks Detailed Steps

rr. Click OK to save your change.


ss. Back on the Customize Shipping page select the Change new button order and
default content type link in the Content Types gallery.
tt. Remove check for the Visible option for the Item content type and click OK.

uu. Select the Shipping list link in the site’s breadcrumb list to return to the list.

vv. Click the New command on the list’s menu bar.

Page 11 of 24
Event Handlers – C#
Tasks Detailed Steps

ww. On the New Item page, fill in the form with data from the table below and click
OK to add the new item.
Column Data
Title Super Widgets
Ship ID X12345
Ship To Jacqui Smith
Street 123 Main Street
City Redmond
State WA
Postal Code 98205
Tracking Shipped
xx. Switch to Visual Studio.
yy. Select View | Server Explorer.
zz. In the Server Explorer window, right-click on the Data Connections node and
select Add Connection.
aaa. In the Choose Data Source dialog, choose Microsoft SQL Server from the Data
source list and click Continue.
bbb. In the Server name field, enter localhost.
ccc. From the Select or enter a database name combo-box, select Packages.
ddd. Click Test Connection to verify. Dismiss any positive confirmation
dialog that appears. If the connection fails, verify your input.
eee. Click OK to complete creating the connection.
fff. Expand the spvm.Packages.dbo node until you can see the Tracking table under
the Tables folder.

Page 12 of 24
Event Handlers – C#
Tasks Detailed Steps

ggg. Right-click on the Tracking table and select Show Table Data. Verify that the
data you entered into the SharePoint list shows up as a record in the table.
hhh. Select Window | Close All Documents.
iii. Close the Server Explorer window.
jjj. Close Internet Explorer.
kkk. Leave Visual Studio running and continue to the next section.

Page 13 of 24
Event Handlers – C#

Exercise 2
Validation Event Handler

Scenario
In this exercise, you’ll enhance the code you’ve already written to validate data provided against another list. You
will first create a second list to track invoices. You will then modify the event handler code to use the data from this
second list to determine if the code should add a record to the SQL Server 2008Tracking table.

Tasks Detailed Steps


Complete the following a. In the Solution Explorer, right-click on the Shipping project node and select
task on: Add | New Item.
b. In the Add New Item dialog, select the Content Type template.
WSS c. Change the name to PaymentType and click Add.
1. Validation Event d. In the Content Type Settings dialog that appears after clicking Add, change the
Handler Base Content Type to Item.
e. Place a check next to the Add with Event Receiver and click OK. Visual Studio
adds three new files, two code files and one XML file, under a folder called
PaymentType.
f. In the Solution Explorer, right-click on PaymentType.xml and select Open.
g. Replace the existing FieldRef commented block between the opening and closing
FieldRefs element tags with the following XML:
<FieldRef ID="{1777B3D8-2237-4c8e-9982-209E437ED9EC}"
Name="InvoiceID" />
<FieldRef ID="{48B36503-65D4-4f0c-B73C-AB328217A34B}"
Name="ShipID" />
<FieldRef ID="{BDEA8538-3CE4-4a92-A305-27F5064FCA7D}"
Name="PaymentStatus" />
h. Next, replace the existing commented Field block with the following XML:
<Field ID="{1777B3D8-2237-4c8e-9982-209E437ED9EC}"
Type="Text"
Name="InvoiceID"
DisplayName="Invoice ID"
StaticName="InvoiceID"
Hidden="FALSE" Required="TRUE"
Sealed="FALSE" />
<Field ID="{48B36503-65D4-4f0c-B73C-AB328217A34B}"
Type="Text"
Name="ShipID"
DisplayName="Ship ID"
StaticName="ShipID"
Hidden="FALSE" Required="TRUE"
Sealed="FALSE" />
<Field ID="{BDEA8538-3CE4-4a92-A305-27F5064FCA7D}"
Type="Choice"
Name="PaymentStatus"

Page 14 of 24
Event Handlers – C#
Tasks Detailed Steps
DisplayName="Status"
StaticName="PaymentStatus"
Hidden="FALSE" Required="TRUE"
Sealed="FALSE">
<CHOICES>
<CHOICE>Billed</CHOICE>
<CHOICE>Paid</CHOICE>
</CHOICES>
</Field>
i. Select File | Save PaymentType\PaymentType.xml to save your work.
j. Select File | Close to close the PaymentType.xml file
k. In the Solution Explorer, right-click on the ItemEventReceiver.cs file under the
ShippingType folder and select Open.
l. Scroll down in the source file until you find the following block of commented
code:
//public override void ItemAdding(SPItemEventProperties
properties)
//{
//}
m. Uncomment the code and add the following code as the method body:
try
{
bool okToShip = false;
SPList invoices = null;
string packageID =
properties.AfterProperties["ShipID"].ToString();

using (SPSite site = new SPSite(properties.WebUrl))


{
using (SPWeb web = site.OpenWeb())
{
invoices = web.Lists["Invoices"];
}
}

if (invoices != null)
{
SPQuery q = new SPQuery();
q.ViewFields = "<FieldRef Name='PaymentStatus'/>";

q.Query =
string.Format("<Where><Eq><FieldRef Name='ShipID'/>"
+
"<Value Type='Text'>{0}</Value></Eq></Where>",
packageID);

Page 15 of 24
Event Handlers – C#
Tasks Detailed Steps
SPListItemCollection list = invoices.GetItems(q);
string paymentStatus = null;

if (list.Count == 1)
{
paymentStatus = list[0]["PaymentStatus"].ToString();
}

if (paymentStatus != null && paymentStatus == "Paid")


{
okToShip = true;
}
}

properties.Cancel = (!okToShip);
if (!okToShip)
{
properties.ErrorMessage = "Invoice has not been
paid.";
}
}

catch (Exception ex)


{
properties.Cancel = true;
properties.ErrorMessage = ex.Message;
}

Note: The code first uses the AfterProperties collection to get the ShipID value. You’ll
note since this is a Before event, the item has not been created and added to the
database, thus you can’t use ListItem object to the ShipID. Next the code opens the
web to grabs a reference to the Invoices list.
Assuming the Invoices list exists, the code creates a SPQuery object to search for a
valid invoice. First, the code restricts list of fields returned by using the ViewFields
property. Next, it creates a filter clause so that it can find the correct invoice. The
assumption is that each invoice will have a ShipID that matches the Package’s ID
(which the code already retrieved). The code assigns the filter clause to the Query
property of the SPQuery object and then executes the query by calling the GetItems
method on the Invoices list object.
The code checks to see that the list returned a single item. If this is true, the code
retrieves the PaymentStatus. If the PaymentStatus is not empty and it has a value of
Paid, then the code marks the Boolean flag okToShip as True. The code uses this flag
to determine if it should add cancel the event, which in turn would prevent the code in
the ItemAdded event from running.
n. Select File | Save ShippingType\ItemEventReceiver.vb to save your work.
o. Select File | Close to close the ItemEventReceiver.cs file.
p. Select View | Server Explorer.
q. If necessary, expand the spvm.Packages.dbo node until you can see the

Page 16 of 24
Event Handlers – C#
Tasks Detailed Steps
Tracking table under the Tables folder.
r. Right-click on the Tracking table and select Show Table Data.
s. Select the row indicator for the only row in the table.
t. Right-click and select Delete to remove the row.
u. Click Yes when asked to confirm the row deletion.
v. Select Start | All Programs | Internet Explorer.
w. Once the Team Site home page appears, click the Shipping link.

x. Select List Settings command from Shipping list’s Settings menu.


y. Under the Permissions and Management gallery, select the Delete this list
command.
z. Click OK when asked to confirm the deletion.
aa. Close Internet Explorer.
bb. Select Start | All Programs | Microsoft Visual Studio 2008 | Visual Studio
Tools | Visual Studio 2008 Command Prompt.
cc. Enter the following at the command prompt:
cd C:\SPHOLS\Labs\Lab03_EventHandler\Shipping\bin\Debug
dd. Next enter the following command:
setup /u
ee. Once you receive the message Operation completed successfully. Hit enter key
to quit., press Enter.
ff. Leave the command prompt open and return to Visual Studio.
gg. Select Build | Build Solution.
hh. Select Build | Deploy Solution. Watch the Visual Studio status bar for
information about the deploy process. Wait for the Deploy succeeded message.
Note: If you receive a deployment error stating the language-neutral solution package
was not found, close Visual Studio 2008, restart it, open your solution and try again.
ii. Select Start | All Programs | Internet Explorer.
jj. Once the Team Site home page appears, select the Create command from the
Site Actions menu.
kk. On the Create page, click the Custom Lists link in the Custom Lists gallery.
ll. On the New page, enter Invoices in the Name field.
mm. Enter List to track invoices in the Description field and click Create.
nn. Select the List Settings command from the Settings menu of the newly created
Invoices list.

Page 17 of 24
Event Handlers – C#
Tasks Detailed Steps
oo. On the Customize Invoices page, select the Advanced settings link under the
General Settings gallery.
pp. On the List Advanced Settings page, set the Allow management of content
types option to Yes.
qq. Once you’ve set the option, click OK to commit your change.
rr. Back on the Customize Invoices page select the Add from existing site content
types link in the Content Types gallery.
ss. In the list of Available Site Content Types, select the PaymentType content
type and then click the Add > button.
tt. Click OK to save your change.
uu. Back on the Customize Invoices page select the Change new button order and
default content type link in the Content Types gallery.
vv. Remove check for the Visible option for the Item content type and click OK.
ww. Now you need to recreate the Shipping list. Select the Create command from the
Site Actions menu.
xx. On the Create page, click the Custom List link in the Custom Lists gallery.
yy. On the New page, enter Shipping in the Name field.
zz. Enter List to track packages being shipped in the Description field and click
Create.
aaa. Select the List Settings command from the Settings menu of the newly created
Shipping list.
bbb. On the Customize Shipping page, select the Advanced settings link under
the General Settings gallery.
ccc. On the List Advanced Settings page, set the Allow management of content
types option to Yes.
ddd. Once you’ve set the option, click OK to commit your change.
eee. Back on the Customize Shipping page select the Add from existing site content
types link in the Content Types gallery.
fff. In the list of Available Site Content Types, select the ShippingType content
type and then click the Add > button.
ggg. Click OK to save your change.
hhh. Back on the Customize Shipping page select the Change new button order
and default content type link in the Content Types gallery.
iii. Remove check for the Visible option for the Item content type and click OK.
jjj. Click the Home tab link to return to the home page.
kkk. Select the Invoices list link in the Quick Launch list.
lll. Create an Invoice item using the data in the table below:
Column Data
Title Super Widgets
Invoice ID I98765
Ship ID X12345
Status Billed
mmm. Click the Shipping link in the Quick Launch list.
nnn. Create a Shipping item using the data in the table below.
Column Data
Title Super Widgets

Page 18 of 24
Event Handlers – C#
Tasks Detailed Steps
Ship ID X12345
Ship To Jacqui Smith
Street 123 Main Street
City Redmond
State WA
Postal Code 98205
Tracking Shipped
Note: You should receive an error as shown in the image below. The error may
include call stack information if you have this enabled on your SharePoint site.

ooo. Click the Back button on your browser to return to the data you entered.
ppp. Switch to Visual Studio.
qqq. If necessary, select View | Server Explorer.
rrr. Under the Data Connections node, expand the spvm.Packages.dbo node until
you can see the Tracking table under the Tables folder.
sss. Right-click on the Tracking table and select Show Table Data. No records
should appear.
ttt. Return to Internet Explorer. You should see your data (the active tab should be
Shipping – New Item).
uuu. Right-click on the SharePoint link in the upper left corner of the page and
select Open in New Tab.

Page 19 of 24
Event Handlers – C#
Tasks Detailed Steps

vvv. Change to the new tab.


www. Click the Invoices link.
xxx. Click the existing Super Widgets link in the Invoices list.
yyy. Select the Edit Item command.
zzz. Change the Status from Billed to Paid.
aaaa. Click OK to save your change.
bbbb. Switch back to the Shipping – New Item tab.
cccc. Click OK to submit your new item again. Your new item should be visible in
the Shipping list.
dddd. Switch to Visual Studio.
eeee. Select Query Designer | Execute SQL. One record should appear.
ffff. Select Windows | Close All Documents.
gggg. Close the Server Explorer window.
hhhh. Close the running instance of Internet Explorer.
iiii. Leave Visual Studio running and continue to the next section.

Page 20 of 24
Event Handlers – C#

Exercise 3
Feature Receiver

Scenario
In the first two exercises, you wrote code that SharePoint executed in response to Item events. In this section, you
will write code that SharePoint executes when you install a Feature. Specifically, you will create a class that inherits
from SPFeatureReceiver. You will then write code that adds an external hyperlink to the Quick Launch menu when
you activate the Feature.

Tasks Detailed Steps


Complete the following a. In the Solution Explorer window, right-click on the Shipping project node and
task on: select Add | New Folder.
b. Name the new folder Links.
WSS c. Right-click on the Links folder and select Add | New Item.
1. Feature Receiver d. In the Add New Item – Shipping, under the Categories section, select the Visual
C# node.
e. Under the Templates section, select the Class item.

f. Change the Name to LinksReceiver.cs and click Add.


g. In the new source file, add the following statements after the existing ones near
the top of the source file:
using Microsoft.SharePoint;
using Microsoft.SharePoint.Navigation;
h. You should remove the statement using System.Linq from the template class file.
i. Add the following attribute to the top of the class declaration:
[CLSCompliant(false)]
j. Add the following line of code under the class declaration.
: SPFeatureReceiver
k. Right click on the SPFeatureReceiver part of the class declaration you just added,
and select Implement Abstract Class.
Note: SharePoint implements its events using inheritance and method overrides rather
than using delegates and events. While the editor will stub out entry points for all

Page 21 of 24
Event Handlers – C#
Tasks Detailed Steps
events, you only need to put code into the members that you are interested.
l. Comment out the following line of code in the FeatureDeactivating,
FeatureInstalled, and FeatureUninstalling methods:
throw new Exception("The method or operation is not
implemented.");
m. In the FeatureActivated procedure, replace the existing code with the following
code:
try
{
const string title = "WSS Dev Center";
const string url =
"http://msdn.microsoft.com/en-
us/sharepoint/default.aspx";

SPWeb featureWeb =
(SPWeb)properties.Feature.Parent;

SPNavigationNodeCollection qlNodes =
featureWeb.Navigation.QuickLaunch;

bool exitProc = false;


foreach (SPNavigationNode link in qlNodes)
{
if (link.Title.Equals(
title, StringComparison.InvariantCultureIgnoreCase))
{
return;
}
}

SPNavigationNode newLink =
new SPNavigationNode(title, url, true);

qlNodes.AddAsFirst(newLink);

featureWeb.Update();
}
catch (Exception ex)
{
Console.WriteLine(ex.Message);
}

Note: Because you are scoping this feature to a SharePoint web, you can use the
properties instance to access the SPWeb object. Using this instance, the code gets the
list of existing links or nodes on the Quick Launch menu. The code then enumerates
the list seeing if a link with the same title already exists. If the code finds an existing
link, it exits. Otherwise, it continues and creates a new link, in the form of a

Page 22 of 24
Event Handlers – C#
Tasks Detailed Steps
SPNavigationNode instnace, and adds it to the node collection. Finally, the code calls
Update on the web object to ensure the changes are committed.
n. Select File | Save Links\LinkReceiver.cs to save your work.
o. Select File | Close.
p. Select View | Other Windows | WSP View.
q. In the WSP View window, expand the Shipping node. This window makes it
easy to add new and remove existing features as well as to reorder how VSeWSS
installs them.

r. On the WSP View toolbar, click the Create new feature button.

s. In the WSP View, click on the newly added Feature1 node and then click it again
to open edit mode and change the name to LinksFeature. Note if you’ve not
changed your keyboard bindings, you can press F2 to enter edit mode.
t. Expand the LinksFeature folder.
u. Under the LinksFeature folder, double-click feature.xml.
v. Replace the existing Feature element with the following XML:
<Feature Id="0db7b642-2f16-4d41-b16e-c4153b91d59b"
Title="LinksFeature"
Scope="Web"
Version="1.0.0.0"
Hidden="FALSE"
DefaultResourceFile="core"

xmlns="http://schemas.microsoft.com/sharepoint/"
ReceiverAssembly="Shipping,
Version=1.0.0.0,
Culture=neutral,
PublicKeyToken={Replace}"
ReceiverClass="Shipping.Links.LinksReceiver"
/>

Page 23 of 24
Event Handlers – C#
Tasks Detailed Steps
w. In the previous XML, you need to provide a valid public key token. Select Start |
Explorer.
x. Navigate to the Global Assembly Cache at C:\Windows\Assembly.
y. In the right pane, scroll until you can select the Shipping assembly.

z. Right-click on the Shipping assembly and select Properties.


aa. In the Shipping Properties dialog, highlight the public key token, right-click and
select Copy.
bb. Click OK to close the dialog.
cc. Close Windows Explorer.
dd. Paste the value from the clipboard into the correct location in feature.xml. You
are replacing the text {Replace} including the parenthesis.
ee. Select File | Save feature.xml.
ff. Select File | Close.
gg. Select Build | Build Solution.
hh. Select Build | Deploy Solution. Watch the Visual Studio status bar for
information about the deploy process. Wait for the Deploy succeeded message.
ii. Select Start | All Programs | Internet Explorer.
jj. Once the SharePoint site home page appears, if you have an Internet connection,
click the WSS Dev Center link. If not, hover over the link and verify the address
is correct by reading Internet Explorer’s status bar.

Page 24 of 24

You might also like