Jun 22, 2008

Creating a custom Master Page Template

Creating a custom master page template involves several steps. First, you must create the master page template itself. Second, you must create a custom feature that provisions an instance of this master page template inside the Master Page gallery for a specific site. Finally, you need to add some code to redirect site pages to use your custom master page instead of using default.master. The Visual Studio project named CustomBranding provides a working sample that demonstrates how all of the pieces fit together.

Remember that the CustomBranding feature is scoped to the level of the site collection. While you can create a custom feature scoped at the site level to integrate a custom master page template, it’s better to design such a feature at the site collection level because users typically want branding to occur at this level. It is less convenient if you force users to activate the feature separately for every site within a site collection.

You can create a custom template by using two different approaches. First, you can make a copy of default.master and then modify it according to taste. A second approach involves starting from scratch so that you can design the exact HTML layout you’re looking for. If you start from scratch, be sure to think through which named placeholders you need to include. There are over 30 named placeholders defined inside default.master, and many of the standard site pages, such as default.aspx and AllItems.aspx, assume that whatever master page they link to will have these same named placeholders.

If you forget to include the same set of named placeholders found in default.master, you will likely experience problems. ASP.NET generates errors whenever it finds that a site page references a named placeholder that is not defined in the master page to which it is linked.

The custom master page template used in the CustomBranding project is named Litware.master. The Litware.master template is a variation on the default.master template with changes to allow for fly-out menus on both the top link bar and Quick Launch menu. The CustomBranding feature includes a Module element that has been designed to provision an instance of the Litware.master page template into the Master Page gallery of the top-level site.

            
            
            

            

Note that this Module element has several differences compared with the Module element for provisioning site pages shown earlier in this chapter. While the previous Module was used to provision pages into a site, it did not target a document library. However, this Module targets the Master Page gallery, which is a special type of document library. Therefore, the Module is defined with a List attribute of 116, which is the list type identifier for the Master Page gallery. The Url attribute for this Module is defined with a value of _catalogs/masterpage, which is the standard site-relative path to the Master Page gallery.

If you examine the File element that provisions an instance of Litware.master, you notice that the Type attribute has a value of GhostableInLibrary as opposed to a value of Ghostable that was shown earlier when provisioning site pages inside a site but outside the scope of a document library. A value of GhostableInLibrary should be used whenever you are provisioning an instance of a file, such as a master page template, inside a target document library.

We have reviewed the steps involved in creating a master page template and provisioning an instance of it in the Master Page gallery of the top-level site. The next step involves redirecting all site pages within a site to link to this provisioned instance of our custom master page template. To understand the technique for accomplishing this, take a closer look at the MasterPageFile attribute defined within a Page directive. Examine the following page template, which is defined to link to a target master page by using a special syntax in the form of~masterurl/default.master.

            <%@ Page MasterPageFile="~masterurl/default.master" %>

            
            Custom content goes here
            

            

The value of~masterurl/default.master represents a tokenized reference to a master page that can be changed programmatically on a site-wide basis. The support for tokenized master page references is provided by the SPVirtualPathProvider class. The way things work is that the SPVirtualPathProvider class reads the value of an SPWeb property named MasterUrl at run time and then parses this value into the MasterPageFile attribute of an .aspx file before sending it to the ASP.NET page parser. You can redirect any site page that uses this token by acquiring an SPWeb reference to the current site and then updating the MasterUrl property.

            SPWeb site = SPContext.Current.Web;
            string MasterUrlPath = site.ServerRelativeUrl;
            if (!MasterUrlPath.EndsWith(@"/"))
            MasterUrlPath += @"/";
            MasterUrlPath += @"_catalogs/masterpage/Litware.master";
            site.MasterUrl = MasterUrlPath;
            site.Update();

            

Delegate Controls

WSS introduces a powerful new extensibility mechanism known as delegate controls. In some ways, a delegate control is similar to a named placeholder because it defines a region inside a master page that can be substituted with unique content to meet the needs of a particular business solution. Like a placeholder, a delegate control can optionally supply default content that is used until a substitution is performed.

One major difference when compared to placeholders is that the substitution mechanism for replacing the contents of a delegate control is driven through feature activation. Therefore, you can replace what’s defined inside a delegate control in default.master without requiring any changes to default.master or the site pages that link to it. All you need to do is define a Control element within a feature and then activate that feature.

A significant aspect of using delegate controls involves the scope of the feature that is being used to drive substitution. When you design a feature to substitute the contents of a delegate control, your feature can be scoped at any of the four supported levels. These levels include site scope, site collection scope, Web application scope, and farm scope. This dimension of delegate controls provides a powerful mechanism for enabling and disabling functionality on a wide-scale basis.

Let’s begin by looking at an example of a delegate control that is defined in default.master to create the region that defines the standard search area in site pages just above the Site Settings menu. The delegate control definition in default.master looks like the following:

            
            

This is an example of a delegate control that defines no default content. Instead, the default content for this delegate control is supplied by a standard WSS feature named ContentLightup. The ContentLightup feature defines a Control element that substitutes content into the SmallSearchInputBox delegate control by referencing a built-in user control with the standard WSS search area content.

            

            

If you want to replace a delegate control, such as the WSS search area, with your own customized version, you start by adding a Control element to a feature. The Control element should have an ID value of SmallSearchInputBox. The Control element should also have a Sequence number smaller than any other active Control element pointing to the same ID. The following code demonstrates how the Control element is defined inside the elements.xml file of the CustomBranding feature.

            
            

In addition to substituting delegate controls by using .ascx files, WSS also supports delegate control substitution by using control classes that are compiled into assemblies installed in the Global Assembly Cache. As an example, let’s examine a technique for replacing the SiteMapDataSource that is used to populate the Quick Launch menu. Examine the following fragment from the standard default.master page template that defines a delegate control named QuickLaunchDataSource.

            
            
            
            
            

            

Unlike the last example of a delegate control, this delegate control with a ControlId of QuickLaunchDataSource defines default content that is used until a substitution is performed. The default content includes a SiteMapDataSource control with an ID of QuickLaunchSiteMap. If you want to substitute this control with a different SiteMapDataSource control, you can add the following Control element to a custom feature.

            
            QuickLaunchSiteMap
            SPSiteMapProvider
            False
            
            

As shown in the previous example, this Control element provides an ID that matches the ControlId of the target delegate on which the substitution should be performed. However, this example differs because it uses the ControlAssembly and ControlClass attributes to reference a specific control type within a target assembly.

You should also observe that the Control element contains several nested Property elements that define the initialization parameters for the control instance being used in the substitution. It is important in this example that the control instance being created is assigned an ID of QuickLaunchSiteMap because the hosting page expects to find a control of that name. The control instance is also initialized to use the SPSiteMapProvider class, which provides different behavior than the default that uses the SPNavigationProvider class instead.

            

WSS Navigation Component

Several standard controls are included with default.master that provide the basic infrastructure for navigation. For example, the ASP.NET SiteMapPath control that has been positioned at the very top of the page populates a breadcrumb navigation menu that allows users to navigate from the current site upward to the parent site and all the way to the top-level site of the current site collection.

Navigation in WSS is based on the navigation-provider infrastructure introduced in ASP.NET 2.0. In this model, a navigation provider is designed and created to provide a set of navigation nodes. In many cases, the nodes supplied by a navigation provider can be bound to a menu control or a treeview to give users a user interface component with which to navigate around the site.

WSS provides several standard navigation providers such as the SPNavigationProvider, SPSiteMapProvider, SPContentMapProvider, and SPXmlContentMapProvider classes. You can see where all the active navigation providers are defined by examining the siteMap section inside the system.web section of the standard WSS web.config file.

The top link bar and the Quick Launch menu represent the two main navigation components defined in default.master. The top link bar is defined by using a WSS-specific control of type AspMenu along with a SiteMapDataSource control that is configured to point to the standard SPNavigationProvider component. The Quick Launch menu is defined in the same way. The major difference between the two is that the SiteMapDataSource for the top link bar is configured with a StartingNodeUrl attribute with a value of sid:1002, whereas the Quick Launch menu is configured with a StartingNodeUrl attribute with a value of sid:1025.

The next question you should be asking is what the significance is between 1002 and 1025. It has to do with the data stored in the content database for tracking navigation nodes. The top node for the top link bar has an ID of 1002, and the top node to the Quick Launch menu has an ID of 1025. WSS provides users with the flexibility to add navigation nodes to either the top link bar or the Quick Launch menu. You can access the application pages that allow users to perform these actions from the Site Settings page. What’s nice about this scheme for developers is that you can customize the standard WSS navigation menus without making any changes to default.master. You simply need to find a way to add new navigation nodes to the content database. While it’s possible for users to add navigation nodes through site administration pages in the browser-based user interface, it’s also possible and far more flexible to accomplish the same goal by using the WSS object model. The CustomSitePages feature provides code in the FeatureActivated event handler to add navigation nodes to construct a custom drop-down menu in a fashion that is not possible to replicate through the user interface. Examine the following code and observe how it creates SPNavigationNode objects and adds them to the collection of nodes that define the structure for the top link bar.

            public override void FeatureActivated(SPFeatureReceiverProperties properties) {

            // get a hold of current site in context of feature activation
            SPWeb site = (SPWeb)properties.Feature.Parent;
            SPNavigationNodeCollection topNav = site.Navigation.TopNavigationBar;

            // create dropdown menu for custom site pages
            SPNavigationNode DropDownMenu1;
            DropDownMenu1 = new SPNavigationNode("Site Pages", "", false);
            topNav[0].Children.AddAsLast(DropDownMenu1);

            // add navigation nodes to create menu items
            DropDownMenu1.Children.AddAsLast(
            new SPNavigationNode( "Site Page 1",
            "SitePages/Page01.aspx"));
            DropDownMenu1.Children.AddAsLast(
            new SPNavigationNode("Site Page 2",
            "SitePages/Page02.aspx"));
            }

            

Web Part Pages

Before diving into the details of how Web Part pages work, two important aspects of their architecture must be noted. First, support for customizing and personalizing Web Parts is available in site pages but not in application pages, thus giving site pages a clear design advantage over application pages.

Second, adding and customizing Web Parts does not require customizing the Web Part pages that host them. A Web Part page defines Web Part zones but does not define what goes inside these zones. Instead, all of the data for tracking Web Part instances and their customization and personalization data are kept in separate tables inside the content database. This means that a Web Part page can remain in a ghosted state even though users are continually adding, customizing, and personalizing the Web Parts within its zone.

Web Part pages in a WSS 3.0 site are built on top of the new Web Part infrastructure introduced with ASP.NET 2.0. To create a Web Part page in an ASP.NET 2.0 application, you must create an .aspx page that contains exactly one instance of a control named WebPartManager and one or more WebPartZone controls. The WebPartManager is responsible for managing the lifetime of Web Part instances as well as serializing Web Part–related data so that they can be stored and retrieved from the tables in the ASP.NET services database.

The Web Part infrastructure of WSS 3.0 does not use the standard WebPartManager control from ASP.NET. Instead, WSS relies on a specialized control named SPWebPartManager that derives from the ASP.NET 2.0 WebPartManager control. The SPWebPartManager control overrides the standard behavior of the WebPartManager control to persist Web Part data inside the WSS content database instead of inside the ASP.NET services database.

In most cases, you don’t have to worry about dealing with the SPWebPartManager control directly because the one and only required instance of the SPWebPartManager is already defined in the standard default.master page. When you create a site page that links to default.master, the SPWebPartManager control is automatically added to the page. Therefore, you simply need to add one or more WebPartZone controls.

Two things must be done when creating a page template for a Web Part page. The first is to inherit from the WebPartPage class that is defined inside the Microsoft.SharePoint.dll assembly. The second is to add one or more WebPartZone controls. Note that you must use the WebPartZone control defined by the WSS team and not the one of the same name defined by the ASP.NET team.

To add WebPartZone controls to a page template, you must add a Register directive that imports all of the controls from the Microsoft.SharePoint.dll assembly defined in the Microsoft.SharePoint.WebPartPages namespace as shown in the following page template definition.

            <%@ Page MasterPageFile="~masterurl/default.master"
            Inherits="Microsoft.SharePoint.WebPartPages.WebPartPage,
            Microsoft.SharePoint, [full 4-part assembly name]"
            meta:progid="SharePoint.WebPartPage.Document" %>

            <%@ Register Tagprefix="WebPartPages"
            Namespace="Microsoft.SharePoint.WebPartPages"
            Assembly="Microsoft.SharePoint, ..." %>

            

            

Custom Web Part page

It is easier to create pages that host Web Parts in the WSS framework than in the ASP.NET Framework. For example, when you design an ASP.NET application that involves Web Parts, you are required to add logic to each page that interacts with the WebPartManager control to manage the display mode. It is also necessary to explicitly add controls, such as Editor Zones and Catalog Zones, to the page so that users can customize existing Web Parts as well as add new Web Parts.

Fortunately, you don’t need to worry about managing the display mode or adding Editor Zones and Catalog Zones when creating Web Part pages for WSS. When you create a Web Part page that inherits from the WebPartPage class, all of this work is done for you behind the scenes. The Site Actions menu automatically provides the Edit Page command that allows the user to enter a mode for adding and customizing Web Parts.

In the CustomSitePages project, three different site pages are provisioned from the page template named WebPartPage.aspx. If you navigate to the first site page named WebPartPage01.aspx and select the Edit Page command from the Site Actions menu, you will see that there are two empty zones, as shown in Figure 3-7. At this point, you can use basic WSS support to add a new Web Part instance as you would to any other Web Part page, such as default.aspx.

When you provision a Web Part page from a page template, it initially contains no Web Parts in any of its Web Part zones. While you could rely on users manually adding Web Parts to your pages, it is more convenient and reliable for you to use a technique in which you prepopulate Web Part zones with whatever Web Parts your business solution requires.

There are two common techniques for adding a Web Part instance to a Web Part zone. The first technique involves a declarative approach used inside a feature in which you define an AllUsersWebPart element inside a File element. The following example demonstrates the File element that is used in the CustomSitePages project to provision the Web Part page named WebPartPage02.aspx.

            
            
            
            
            
            
            Microsoft.SharePoint, ...
            Microsoft.SharePoint.WebPartPages.ImageWebPart
            None
            Watch My Gears Run
            /_layouts/images/GEARS_AN.GIF
            
            ]]>
            
            
            
            

            

As you can see, a File element can contain an inner AllUsersWebPart element that references a target Web Part zone and includes serialized data for the Web Part instance to be created. We will revisit the inner WebPart element in more detail in Chapter 4 when we discuss Web Part description files.

The second technique for adding a Web Part instance to a Web Part page involves writing code against the WSS object model. An example of this type of code is supplied in the FeatureActivated event handler for the CustomSitePages project. The code obtains a reference to the SPFile object associated with WebPartPage03.aspx and uses an SPLimitedWebPartManager object to add a new Web Part instance to a particular target zone.

            public override void FeatureActivated(
            SPFeatureReceiverProperties properties) {
            // acquire objects for site, page and limited Web Part Manager
            SPWeb site = (SPWeb)properties.Feature.Parent;
            SPFile page = site.GetFile("SitePages/WebPartPage03.aspx");
            SPLimitedWebPartManager mgr;
            mgr = page.GetLimitedWebPartManager(PersonalizationScope.Shared);
            // add Web Part to Right Zone
            ImageWebPart wp1 = new ImageWebPart();
            wp1.ChromeType = PartChromeType.None;
            wp1.ImageLink = @"/_layouts/images/IPVW.GIF";
            mgr.AddWebPart(wp1, "RightZone", 0);
            }
            

The advantage to using the first technique is that Web Parts can be added to pages with declarative logic in the same place where the actual page is being provisioned. The advantage of using the second approach involving code is that it is more flexible. While you can execute code that adds a Web Part instance during feature activation, you can also execute the same code long after the feature is activated. For example, imagine a scenario in which you would like to write the code required to enumerate through every site within a farm to add a special Web Part to a target zone on every home page. The WSS object model makes it possible to automate this type of administrative task with Web Part pages.

User control in wss3

It is important to understand that WSS does not support user customization of user controls. User controls are always loaded from the file system of the front-end Web server and compiled into assembly DLLs. Furthermore, user controls can be copied to the front-end Web server only by someone with farm-level administrative privileges. For these reasons, you can assume that you can always write in-line code in an .ascx file.

Just like the virtual _layouts directory for the purpose of deploying application pages, WSS provides a similar virtual directory for deploying user controls. Inside the TEMPLATE directory resides a nested directory named CONTROLTEMPLATES. This directory contains many different user controls that are deployed as part of the standard WSS installation.

The CONTROLTEMPLATES directory is also a place where you should deploy custom user control files. However, it’s a good practice to create your own nested directory inside the CONTROLTEMPLATES directory to avoid potential file name conflicts. The CustomSitePages project creates a company-specific inner directory named Litware and copies its user controls into that directory. Each custom user control is copied to a physical path that looks like the following: TEMPLATES/CONTROLTEMPLATES/Litware/UserControl1.ascx

Each Web application is configured with a virtual directory named _controltemplates that points to the physical CONTROLTEMPLATES directory. This makes it possible to reference any user control file by using a standard path relative to the hosting Web application. For example, one of the user controls from the CustomSitePages project can be referenced by using a virtual path that looks like the following: ~/_controltemplates/Litware/UserControl1.ascx

When deploying user controls, it’s important to remember that they follow the same rules with respect to safe mode processing. If you want to place a user control on a site page that might be customized, the .ascx file must be registered as a safe control in the web.config file of the hosting Web application. Fortunately, you don’t have to worry about this if you deploy your custom user controls inside the virtual _controltemplates directory because the standard web.config file for a Web application already contains the following SafeControl entry:

            
            

Now that you have seen how to create and properly deploy a user control, the final step is constructing a page template that references the .ascx file and creates an instance. Similar to constructing pages with custom controls, this is accomplished by placing a Register directive on the page template. However, the process is different with user controls because the Register directive requires an src attribute that points to the virtual path of the target .ascx file.

            <%@ Page MasterPageFile="~masterurl/default.master"
            meta:progid="SharePoint.WebPartPage.Document" %>

            <%@ Register TagPrefix="luc" TagName="UserControl1"
            src="~/_controltemplates/Litware/UserControl1.ascx" %>

            

            

            

            

Safe Mode Processing

Ghosted site page and application page can containe inline code, it is basically traditional aspx page. But all customized(unghosted) site pages are parsed and processed in a special mode known as safe mode. The primary motivation for safe mode involves the fact that standard users can modify the contents of site pages. In other words, a user(such as a site owner) processing no administrator privileges within the farm can make any modifications to a page within a site. Consider a scenario in a large farm in which a site administrator attempts to mount an attack on the Web server by writing C# code within a customized site page inside an in-line script block. Safe mode prevents this type of attack by disallowing in-line script in any customized source. So if your site pages is an instance of page template which has inline code, the site page will break if you modify the site page in the site unless you do something to prevent this happening. For this reason, you should advoid adding in-line script to page templates. If you want o allow in-line scripts to run in unghosted site pages, you can accomplishe this by adding the following PageParserPath element within the SharePoint section of the web.config file.

            
            
            
            
            
            
            

            

If you examine the PageParserPath element, you see that the VirtualPath attribute has a Web application relative path followed by an asterisk, which includes every site page in that particular folder. Also note that the CompilationMode attribute has a value of Always and the AllowServerSideScript attribute has a value of true. This instructs the safe mode parser to compile all site pages into assembly DLLs and allow in-line script.

Note that a page must be compiled into an assembly DLL to support in-line script, which means that it is not valid to assign a value of Never to the CompilationMode attribute while assigning a value of true to the AllowServerSideScript attribute. Also note that you can assign a value of Auto instead of a value of Always to the CompilationMode attribute. This has the effect of compiling only pages that contain in-line script. When the CompilationMode attribute has a value of Auto, pages without in-line script are still run in no-compile mode.

It is possible to enable in-line script for all site pages within a Web application by configuring the VirtualPath attribute with a value of /* and then setting the CompilationMode attribute to a value of Always or Auto. However, two significant factors should motivate you not to do this.

The first factor is security. By enabling in-line script for all site pages within a Web application, you open the door to attacks on the Web server because any user who has the ability to customize a page can freely write managed code that executes on the Web server.

The second factor pertains to scalability. Earlier in this chapter, I discussed how no-compile pages are more scalable than compiled pages in a large Web application. WSS experiences scaling problems if your Web application attempts to compile and load thousands of assembly DLLs for all of your customized pages. At the very least, you should prefer a CompilationMode setting of Auto instead of Always so that only pages that actually contain script are compiled into assembly DLLs, whereas those pages that do not contain script continue to be parsed and processed in no-compile mode.

Safe Cotnrols

Safe mode processing goes a step beyond protecting against in-line script by also considering what controls a user might place on a customized page. For example, imagine a scenario in which a site administrator tries to mount an attack by adding a server-side control to a site page and parameterizing it in a certain way. Safe mode allows the farm administrator to determine which controls can be used in pages that are processed in safe mode.

Customized pages can only contain server-side controls that are explicitly registered as safe controls. Registering a control as a safe control is accomplished by adding a SafeControl entry into the web.config file for the hosting Web application.

            
            
            


            

Note that a PageParserPath element, in addition to allowing in-line script, can also override the default safe mode behavior and allow for server-side controls that are explicitly registered as safe. For example, you can allow the users of a particular site to add any server-side controls to customized pages by using the following entry within the web.config file.

            
            
            
            
            
            
            

            

Note that using this option affects only which server-side controls can be added to a page when customizing a page with a tool, such as the SharePoint Designer. This configuration option does not extend to control instances when users are adding Web Parts to Web Part zones on a page through the browser. Assembly DLLs containing Web Parts must always be explicitly registered by using SafeControl elements for users to be able to place them inside Web Part zones.

Although you have just learned several ways to disable safe mode or lessen its effects, you should remember to proceed here with extreme caution. It’s usually best to leave safe mode with its default behavior. WSS was engineered with safe mode processing to protect the farm from attacks and allow WSS to scale out the way it was designed in large farm environments.

Non compile mode in sharepoint

In wss3, cutomized pages are not processed by using the standard ASP.NET mode in which a page is compiled into an assembly, instead, customized pages are parsed by the ASP.NET page parser and then processed using the no-compiled mode feature that was instoduced with asp.net 2.0.

Why customized pages are processed in non-compile mode? Although compiled pages run faster than non-compile pages. However, no-compile pages can be more efficient and more scalable in certain scenarios. This is ture in a large WSS enviroment where the number of customized pages can reach into the thousands or tens of thousands. No-compile pages can be loaded into memory and then unloaded in a memner that is not possible for comiled pages because the .net framework doesn't really support the concept of unloading an assembly dll from memory. The closes equivalent would be recycle the current windows process or .net appdomain. Howevery, this type of recycling involves unloading all assembly dlls from the memory, not just those assebly dlls that haven't been used recently. Futhurmore, the .net Framework places an upper limit on the number of assembly dlls that can be loaded into a .net appdomain.

No-compile pages provide higher levles of scalability because they do not require loading new assembly dlls or managed classes into memory. Instead, the processing of no-complie pages involves loading control trees into memory. WSS can manage the memory usage for the control trees associated with customized pages more efficently because they are not compiled into assembly dlls. For example, once wss has finished processing a customized page, it can unload the page's control tree to free up memory for other purpose. Furthermore, noncompile pages eliminate the need to go throuhg the compilation process, which actually provides faster response time for pages unpon first access.

Jun 20, 2008

minimun sharepoint master page

<%-- Identifies this page as a .master page written in Microsoft Visual C# and registers tag prefixes, namespaces, assemblies, and controls. --%>
<%@ Master language="C#" %>

<%@ Import Namespace="Microsoft.SharePoint" %>
<%@ Register Tagprefix="SPSWC" Namespace="Microsoft.SharePoint.Portal.WebControls" Assembly="Microsoft.SharePoint.Portal, Version=12.0.0.0, Culture=neutral, PublicKeyToken=71e9bce111e9429c" %>
<%@ Register Tagprefix="SharePoint" Namespace="Microsoft.SharePoint.WebControls" Assembly="Microsoft.SharePoint, Version=12.0.0.0, Culture=neutral, PublicKeyToken=71e9bce111e9429c" %>
<%@ Register Tagprefix="WebPartPages" Namespace="Microsoft.SharePoint.WebPartPages" Assembly="Microsoft.SharePoint, Version=12.0.0.0, Culture=neutral, PublicKeyToken=71e9bce111e9429c" %>
<%@ Register Tagprefix="PublishingWebControls" Namespace="Microsoft.SharePoint.Publishing.WebControls" Assembly="Microsoft.SharePoint.Publishing, Version=12.0.0.0, Culture=neutral, PublicKeyToken=71e9bce111e9429c" %>
<%@ Register Tagprefix="PublishingNavigation" Namespace="Microsoft.SharePoint.Publishing.Navigation" Assembly="Microsoft.SharePoint.Publishing, Version=12.0.0.0, Culture=neutral, PublicKeyToken=71e9bce111e9429c" %>
<%@ Register TagPrefix="wssuc" TagName="Welcome" src="~/_controltemplates/Welcome.ascx" %>
<%@ Register TagPrefix="wssuc" TagName="DesignModeConsole" src="~/_controltemplates/DesignModeConsole.ascx" %>
<%@ Register TagPrefix="PublishingVariations" TagName="VariationsLabelMenu" src="~/_controltemplates/VariationsLabelMenu.ascx" %>
<%@ Register Tagprefix="PublishingConsole" TagName="Console" src="~/_controltemplates/PublishingConsole.ascx" %>
<%@ Register TagPrefix="PublishingSiteAction" TagName="SiteActionMenu" src="~/_controltemplates/PublishingActionMenu.ascx" %>
<%-- Uses the Microsoft Office namespace and schema. --%>




<%-- The head section includes a content placeholder for the page title and links to CSS and ECMAScript (JScript, JavaScript) files that run on the server. --%>



<asp:ContentPlaceHolder id="PlaceHolderPageTitle" runat="server" />






<%-- When loading the body of the .master page, SharePoint Server 2007 also loads the SpBodyOnLoadWrapper class. This class handles .js calls for the master page. --%>

<%-- The SPWebPartManager manages all of the Web part controls, functionality, and events that occur on a Web page. --%>
<%-- The PlaceHolderMain content placeholder defines where to place the page content for all the content from the page layout. The page layout can overwrite any content placeholder from the master page. Example: The PlaceHolderLeftNavBar can overwrite the left navigation bar. --%> <%-- These ContentPlaceHolders ensure all default SharePoint Server pages render with this master page. If the system master page is set to any default master page, the only content placeholders required are those that are overridden by your page layouts. --%>

Master Page customization

Default.master contains ~30 placeholders, ~22 of them in the page body. All of them must be defined in a replacement master page.

Two techniques for customizing layout:

  • Start with a copy of default.master

    Remove markup around placeholder Rebuild in place

  • Start with a blank master

    Build from ground up, Copy placeholders from default.master

Below is the minimal master page from msdn,

            <%-- Identifies this page as a .master page written in Microsoft Visual C# and registers tag prefixes, namespaces, assemblies, and controls. --%>
            <%@ Master language="C#" %>
            
            <%@ Import Namespace="Microsoft.SharePoint" %>
            <%@ Register Tagprefix="SPSWC" Namespace="Microsoft.SharePoint.Portal.WebControls" Assembly="Microsoft.SharePoint.Portal, Version=12.0.0.0, Culture=neutral, PublicKeyToken=71e9bce111e9429c" %>
            <%@ Register Tagprefix="SharePoint" Namespace="Microsoft.SharePoint.WebControls" Assembly="Microsoft.SharePoint, Version=12.0.0.0, Culture=neutral, PublicKeyToken=71e9bce111e9429c" %>
            <%@ Register Tagprefix="WebPartPages" Namespace="Microsoft.SharePoint.WebPartPages" Assembly="Microsoft.SharePoint, Version=12.0.0.0, Culture=neutral, PublicKeyToken=71e9bce111e9429c" %>
            <%@ Register Tagprefix="PublishingWebControls" Namespace="Microsoft.SharePoint.Publishing.WebControls" Assembly="Microsoft.SharePoint.Publishing, Version=12.0.0.0, Culture=neutral, PublicKeyToken=71e9bce111e9429c" %>
            <%@ Register Tagprefix="PublishingNavigation" Namespace="Microsoft.SharePoint.Publishing.Navigation" Assembly="Microsoft.SharePoint.Publishing, Version=12.0.0.0, Culture=neutral, PublicKeyToken=71e9bce111e9429c" %>
            <%@ Register TagPrefix="wssuc" TagName="Welcome" src="~/_controltemplates/Welcome.ascx" %>
            <%@ Register TagPrefix="wssuc" TagName="DesignModeConsole" src="~/_controltemplates/DesignModeConsole.ascx" %>
            <%@ Register TagPrefix="PublishingVariations" TagName="VariationsLabelMenu" src="~/_controltemplates/VariationsLabelMenu.ascx" %>
            <%@ Register Tagprefix="PublishingConsole" TagName="Console" src="~/_controltemplates/PublishingConsole.ascx" %>
            <%@ Register TagPrefix="PublishingSiteAction" TagName="SiteActionMenu" src="~/_controltemplates/PublishingActionMenu.ascx" %>
            <%-- Uses the Microsoft Office namespace and schema. --%>
            
            
            

            <%-- The head section includes a content placeholder for the page title and links to CSS and ECMAScript (JScript, JavaScript) files that run on the server. --%>
            
            
            
            <asp:ContentPlaceHolder id="PlaceHolderPageTitle" runat="server" />
            
            
            
            
            

            <%-- When loading the body of the .master page, SharePoint Server 2007 also loads the SpBodyOnLoadWrapper class. This class handles .js calls for the master page. --%>
            
            <%-- The SPWebPartManager manages all of the Web part controls, functionality, and events that occur on a Web page. --%>
            
<%-- The PlaceHolderMain content placeholder defines where to place the page content for all the content from the page layout. The page layout can overwrite any content placeholder from the master page. Example: The PlaceHolderLeftNavBar can overwrite the left navigation bar. --%> <%-- These ContentPlaceHolders ensure all default SharePoint Server pages render with this master page. If the system master page is set to any default master page, the only content placeholders required are those that are overridden by your page layouts. --%>

Master Page

Content Page's Master Page

Dynamic Master Page

Dynamic Master Page is to control what master marge to be used by variable or property, so if you change the property, then the dynamic page is changed.

  1. System Master Page

    Page language="C#" MasterPageFile="~masterurl/default.master"

    Property of "spweb.MasterUrl" is used to represent this token. It is most frequenet used Master page. We use the system master page for all forms and view pages in this site.

  2. Site Master Page

    Page language="C#" MasterPageFile="~masterurl/custom.master"

    Property of "spweb.CustomMasterUrl" is used to represent this token.The site master page will be used by all publishing pages

Although WSS 3.0 sites do not utilize the SPWeb.CustomMasterUrl property, MOSS 2007 publishing sites make heavy use of it. All page layouts are automatically configured to use the master page defined in the SPWeb.CustomMasterUrl property when rendering the site. The master page defined in SPWeb.MasterUrl property is till used for standard SharePoing Pages such as list or form pages.

Static Master Page

~sitecollection/default.master or ~site/default.master they are not variable so you can not change it, they static point to a physical relative url.The first part is considered a replaceable token. At runtime, sharepoint evaluate the first part of the token and replace it with url specified, but it will not change the anem of the master page. For example if a content page is within the site http://site/subsite, Sharepoint will would switch the "~site" token out at runtime to "/subsite".

Application Page's Master Page

Application's Page are served by the files in file systems. It can not use all the token used above. Default master page for application page is

MasterPageFile="~/_layouts/application.master"

Style in sharepoint

When we use the default master, the style sequence is as follow.

            

            
            

            
            
            
            
            
            

So we can use still use the css selector in the core.css, but we can override the style in core.css, because the alternate style and theme style come after.

If we want use customize customized master page, then we need to take control of all the style.

Jun 19, 2008

Site Definition and site configuration

A site definition defines a unique type of SharePoint site. There are five site definitions natively installed in Windows SharePoint Services. A site definition can include more than one site definition configuration. SharePoint Web sites are based on particular site defnition configurations.

STS includes the site definition configurations for Team Site, Blank Site, and Document Workspace.

MPS includes the site definition configurations for Basic Meeting Workspace, Blank Meeting Workspace, Decision Meeting Workspace, Social Meeting Workspace, and Multipage Meeting Workspace.

CENTRALADMIN provides a site definition configuration sfor central administration Web sites.

WIKI provides a site definition configuration for Web sites that support community content using wiki technology.

BLOG provides a site definition configuration for blogs.

Jun 15, 2008

feature difference between MOSS standard and MOSS enterprise

The following features are available with the Standard license type:

  • Collaboration
  • Enterprise content management
  • Workflow
  • My Sites
  • Profiles and personalization
  • Enterprise search

The following additional features are available with the Enterprise license type:

  • Business Data Catalog
  • Excel Services
  • Report Center
  • InfoPath Forms Services
  • KPI and Filter Web Parts

security in central admin site

The previous section described how the user web site works. But how do you modify the inner guts of WSS? You may remember that I said that the account used during the installation will initially also be the only account that can access the Central Administration web site. But this is not completely true!

Assume that Anna is the only user who can access the Administration web site. In other words, she is the SharePoint Goddess. By mistake, you happen to delete her user account. Quickly you try to repair the damage before anyone notices, so you create a new user account, with the exact same name and password. Will Anna still be able to use the Administration web site? No! Because when you created a new account, it got a new Security ID (SID), although with the same name. But SharePoint has granted administrative access to the old SID for Anna, so she cannot get in.

How do you solve this? Well, you can't unless you do a restore of the user account, that is, restore the complete Active Directory database, and this is not an easy task. Is there an easier way? Yes! Your escape route out of this misery is the fact that every user who is a member of the local Administrators group of the WSS server automatically has full and unlimited access to the Central Administration tool! The solution is to add Anna's new account to this group.

The important thing for you to understand that everyone - every user and every member of any domain group - who is a member of the local Administrators group is a SharePoint God or Goddess. And by default, the domain group Domain Admins is always a member of the local Administrator group in every computer in the domain. This results in the fact that every member of Domain Admins has full access to the Central Administration tool. But not to any of the user sites in WSS! This is different from WSS 2.0, where members of the local Administrator group had full access to every site, both administrative and user sites! So, the security is better in WSS 3.0. However, any user who can access the Central Administrator tool can also add themselves as Owners to any user site, so note that only trusted people should be members of the local Administrator group!

Jun 11, 2008

sharepoint hidden url

sharepoint template gallery: http://b-wss1:81/_catalogs/wt/Forms/Common.aspx

http://wss1:8088/_vti_bin/SharePointEmailWS.asmx

            

Jun 9, 2008

Workflow persistence

What triggers persistence?

  • Runtime decides when to persist
  • Persistence service decides how and where
  • Conditions:
    • Anytime the WF goes idle (e.g. Delay Activity)
    • Host App can control by calling Unload or TryUnload methods
    • Transactions complete (TransactionScopeActivity or CompensatableTransactionScopeActivity)
    • Custom Activity with PersistOnCloseAttribute completes
    • CompensatableSequenceActivity completes
    • When the WF terminates or completes

            
            
            
            

Jun 1, 2008

EventHandling in WF

In WF, CallExternalMethod is used to transfer data from workflow instance to host, and HandleExternalEvent is used to transfer data from host to workflow instance. The pattern of HandleExternalEvent is similar to the one of CallExternalMethod. Basically, you specify the interface the HandleExternalEvent can support, then you need to specify the event that HandleExternalEvent can handle. The event is from the interface supported. To use HandleExternalEvent in our workflow, we have more supporting activities need to be introduced into the workflow. Firstly, you need a listener activity to support event listening. In the listening activity, you define one or more EventDrivenActivity. In side of EventDrivenActivity, the first child activity should be HandleExternalEvent, which is define what event it is listening. To achieve the purpose of transferring information from external host to workflow instance, we can embed the information in the event argument. At the workflow client side, we need to add the external service to workflow host. The external service inplement the interface that the HandleExternalEvent want to handle. Then client call external service's fire event method, magically, the workflow instance will intercept the event.

ExternalDataExchangeService exSvc = new ExternalDataExchangeService(); workflowRuntime.AddService(exSvc); CustomerService custSvc = new CustomerService(); exSvc.AddService(custSvc); public void SendCustomerInfo(Guid id) { if (this.GotCustomerInfo != null) { CustomerEventArgs args = new CustomerEventArgs(id); args.CustomerName = "fred"; GotCustomerInfo(null, args); } }