Click here to Skip to main content
13,552,161 members
Click here to Skip to main content
Add your own
alternative version

Tagged as


2 bookmarked
Posted 4 Sep 2014
Licenced CPOL

Small Tweaks, Big Benefits: How to Customize Your PMIS for Greater Business Value

, 4 Sep 2014
Rate this:
Please Sign up or sign in to vote.
How to customize your PMIS for greater business value


Project Management Information Systems (PMIS) are many things—powerful, capable, adaptable, and versatile software creations.

But one thing they’re not—is perfect (at least right out-of-the-box).

Every company has its own internal standards for project management functions, and the baseline platform features you’ll find in an out-of-the-box PMIS can never match those preferences, automatically.

But with a bit of customization, you can attune your PMIS experience to the unique requirements of your organization—unlocking hidden business value and mobilizing a cadre of powerful but underutilized platform features.

The Trouble With Defaults

In this paper, we’ll be examining the customization of Microsoft Project Server.

Especially when combined with Microsoft SharePoint, Project Server is one of the most effective—and widely implemented—choices for enterprise PMIS. But like any PMIS, it’s far from perfect right out-of-the-box.

Generally speaking, PMIS like Project Server have a host of responsibilities, including:

  • Project initiation (including project validation and analysis of scope, capacity, resource, and budget requirements)
  • Network scheduling
  • Project resources management
  • Operational information maintenance and project status monitoring
  • Project document flow and documentation archiving;
  • Management of project risks, problems, and requests for changes
  • Operational and statistical reporting

When it comes to some of these tasks—like network scheduling and project resource management—MS Project Server performs fairly well “out-of-the-box.” But project workflow functionality is quite a different story.

To illustrate the workflow problem, let’s look at a real-world project.

In the Initiation and Planning stages of this project, we’ll be asking MS Project Server to facilitate two main tasks:

  1. Creating a project that adheres to all of our internal standards—for example, ensuring that project codes meet internal budget and portfolio classifications.
  2. Creating a collaborative workspace that holds all of our project data regarding:
    • Categorization (goals, solutions, results, benefits, feasibility analyses)
    • Organizational structure (management and operational guidance, working groups, skill sets)
    • Scope (functional, organizational, and technical elements, procedures for making scope changes)
    • Implementation approach (strategies for deployment, assumptions and restrictions, impact analyses)
    • Budget (budgeting phases, scope of work within budgeting phases and cost items, overall project budgeting)
    • Documentation (structured storage of all project reporting)
    • Charter (automated generation of the final project document)

Furthermore, we’ll need this collaborative workspace to have an intuitive user interface. (This is particularly important in the early phases of the project, since many of your team members may still be building familiarity with MS Project Server.)

First, let’s look at what happens when we attempt these tasks “out-of-the-box.”

Task one—creating the project—works fairly well. We can select our extended project attributes through the custom fields mechanism, which means they’ll be automatically included in our reporting databases, and we can build analytics on top of them.

The only significant limitation we encounter “out-of-the-box” is that we cannot automatically generate project codes based on project types and other classifying attributes.

Task two—creating a workspace—proves much more problematic, as we can only create a standard project workspace containing documents, risks, and questions.

Image 1: Standard project workspace

So our preliminary conclusion is that while “out-of-the-box” settings are well aligned with project management functions involving network scheduling, resource management, and risks, they are poorly adapted to the automatic generation of a project charter, project financial planning, contract work, and project documentation flow in general.

Given those limitations, let’s explore how to improve functionality with just a few modifications to the system’s default settings.

Customization in Action

Returning to our project example, you’ll recall that during task one, we lacked the automatic generation of project codes according to project characteristics.

When creating a project, it’s necessary to generate codes using the following format: PRJ [type of project specifier] [activities] [numbers within selected type and direction].

MS Project Server’s event handler mechanism is a good fit for this task. Hence, we’ll need to implement a handler, which will generate and save our required project codes.

To work directly with the field, a proxy assembly is required for Project Server Web API, called PSI, ProjectServerServices.dll. (Please note that working with PSI is very specific because all actions are made using specialized DataSet, and this object lacks coherent documentation).

First, you’ll need to obtain the required field ID, which is explained here.


//read project information
var projectDS = ProjectSvc.ReadProject(ProjectUID, SvcProject.DataStoreEnum.WorkingStore);

foreach (ProjectDataSet.ProjectCustomFieldsRow cfRow in projectDS.ProjectCustomFields)
                //if field exists, just update it
                if (cfRow.MD_PROP_UID.ToString() == id.ToString())
                    //update the value
                    cfRow.TEXT_VALUE = code;
                    customFieldFound = true;

After that, the project needs to be returned:

//create a new job id
jobId = Guid.NewGuid();

//checkin the updated project
bool force = false;
string sessionDescription = "updated custom fields";
ProjectSvc.QueueCheckInProject(jobId, ProjectUID,
    force, sessionId, sessionDescription);

And published:

    //create a new job id
jobId = Guid.NewGuid();

bool fullPublish = false;
ProjectSvc.QueuePublish(jobId, ProjectUID,
    fullPublish, EndpointAddressProjectSvc.Uri.ToString())

Once the project has been created (task one) we’ll need to create a workspace (task two) that provides the functionality to compile project data—for instance, our project charter.

But as you’ll recall, a standard MS SharePoint workspace is just a simple web template containing a document library and lists of issues and risks.

We’ll need a web template with much richer functionality.

Generally speaking, there are two ways to create a site definition that can be used as a workspace template for MS SharePoint—creating a Sandboxed Solution based on a standard PWS workspace, or creating a Farm Solution site definition.

A Sandboxed Solution site definition is an adjustment to an existing workspace. The advantage here is that our created workspace appears immediately in the administrating interface. However, Sandboxed Solutions have stiff restrictions. For example, one cannot access databases, which is precisely the functionality we’re missing in order to show various MS Project and workspace data sets.

A Farm Solution has an obvious advantage—we’ll have full access to OM SharePoint, and we can retrieve data from various sources. But with a Farm Solution, how will we make our site definition acceptable for use as a template workspace on the Project? Google couldn’t help us at the time—so off we go armed with IL-Spy or Reflector.

It’s best to start with the “Enterprise Project Type Details” page (\PWA\ADMIN\EnterpriseProjectTypeDetails.aspx).

From there, after a series of calls, we will get into Microsoft.Office.Project.Server.dll and ReadWssInstalledLanguagesAndWebTempalates(…) method of Microsoft.Office.Project.Server.BusinessLayer.Admin class.

Here is what we will see:

foreach (SPWebTemplate sPWebTemplate in sPWebTemplateCollection)
        if (sPWebTemplate.ID >= 6000 && sPWebTemplate.ID <= 6220)
            dataRow = webTemplatesTable.NewRow();
            dataRow["LanguageId"] = sPLanguage.LCID;
            dataRow["TemplateName"] = sPWebTemplate.Name;
            dataRow["TemplateTitle"] = sPWebTemplate.Title;
            dataRow["TemplateId"] = sPWebTemplate.ID;

This ID is the same ID that’s defined in webtemp_***.xml (it has to be between 6000 and 6220). However, if we create a SiteDefinition with the right ID, it will definitely appear on the “Enterprise Project Type Details” page—but the creation of the site will fail.

An explanation for why this happens can be found in AddOrChangeProjectWorkspaceAddress(…) method of Microsoft.Office.Project.Server.BusinessLayer.Project class.

If you scrutinize the code, you can see that it relies on PWSIssues, PWSRisk and PWSDocLibs lists. We could add relevant Features in our SiteDefinition, or we could simply add Feature PWS into onet.xml, and this would add whatever is necessary.

<!--Activate PWS Feature -->
<Feature ID="90014905-433F-4a06-8A61-FD153A27A2B5">
  <Properties xmlns="">
    <Property Key="InheritGlobalNavigation" Value="false"/>
    <Property Key="OnQuickLaunch" Value="false"/>
    <Property Key="InheritCurrentNavigation" Value="false"/>
    <Property Key="IncludeSubSites" Value="false"/>
    <Property Key="IncludePages" Value="False"/>

This is not surprising because the standard site definition PWS is just a site with this feature activated. (Please note that the creation of our workspace is happening in “Microsoft Project Server Queue Service 2010.” Therefore, we’ll need to restart it once changes are made to the SiteDefinition.)

Taking this approach, our workspace will become a set of lists with specific data, and a set of pages that reflect the different list slices—as well as ProjectServer_Reporting databases. But two questions remain:

  1. How do we implement the data connection with minimal code?
  2. How do we choose data (particularly the Tasks that are relevant to a current project and not to other projects)?

Regarding question one, DataFormWebPart and its AggregateDataSource are good fit for the connection. The key here is that we’ll choose data from all the sources and then implement the connection on .xsl level. For example:

<cc1:AggregateDataSource runat="server" 

RowsName="" SeparateRoot="true" RootName="" IsSynchronous="">
        <cc1:SPSqlDataSource runat="server" AllowIntegratedSecurity="False" ConnectionString="
          <%$ connectionStrings:.._ConnectionString %>" 

          SelectCommand="SELECT TOP 1000 [Results] as WorkResults, 
          [TaskIndex], [TaskOutlineNumber],  [TaskUID],cast(cast(TaskWork as decimal(9,2)) AS FLOAT) 
          as TaskWork,[TaskName] FROM [ProjectServer_Reporting].[dbo].[MSP_EpmTask_UserView] 
          TV INNER JOIN [ProjectServer_Reporting].[dbo].[MSP_EpmProject] PR ON  
          TV.ProjectUID = PR.ProjectUID  WHERE PR.ProjectUID = @ProjUid " ID="SqlDataSource1">
            <asp:controlparameter name="ProjUid" controlid="PlaceHolderMain$wspp" propertyname="ProjUid"/>
        <cc1:SPDataSource runat="server" DataSourceMode="List" SelectCommand="..."/>
        <cc1:SPDataSource runat="server" DataSourceMode="List" SelectCommand="..."/>
        <cc1:SPDataSource runat="server" DataSourceMode="List" SelectCommand="..."/>
        <concat name="data source">
          <datasource name="TasksInfo" id="0"  />
          <datasource name="ProjectPhases" id="1" />
          <datasource name="ProjectWorkSteps" id="2" />
          <datasource name="Contracts" id="3"  />

Looking at the above code, we can see the set of SPSqlDataSource for database query, and SPDataSource for lists query. All that remains is to write an .xls that will display these in the right order.

Regarding question two—how to choose data—we have a pair of options. On the one hand, we could focus on the URL of the workspace, and later get the ProjUid configured using the MSP_EpmProject table in the request. On the other hand, ProjUid for MS SharePoint workspaces is written in the SPWeb properties in the MSPWAPROJUID field—so we can write a simple control that will return it:

public class WSProjectProperties : WebControl
    public String ProjUid
            if (SPContext.Current == null)
                return null;
            if (SPContext.Current.Web == null)
                return null;

            return SPContext.Current.Web.AllProperties["MSPWAPROJUID"] as string;

Its value should then be passed to DataSource, which is precisely what the previous example covers.

The Fruits of Customization

With only these few, slight modifications, we’ve given the standard workspace full-featured functionality for collaboration—according to our own, internal requirements.

Let’s take a look:

Image 2: Projects classification and auto coding based on our requirements

Image 3: User-friendly workspace with required functionality fully customized

Images 4-5: Compiling the project main target values

Images 6-8: Project organizational structure, including management of several project teams

Images 9-10: Determining project scope and implementation approaches

Image 11: Project budget planning with detailed project stages, and contract relations planning based on calendar schedule configured in Microsoft Project 2010

Image 12: Included task list is built based on calendar schedule

Image 13: Contract relations planning and matching jobs with account costs and time frames

Image 14: Automatic generation of document hard copies based on planned project data (project charter)

Image 15: Project operational control panels based on the key parameters (project summary)

Note: The parameters formed automatically based on fact data from Microsoft Project 2010 calendar schedule or financial systems are marked in red.

Image 16: Operations control by stages is based on planned and actual timeframes and achieving project milestones including color-coded dashboard indicators

Note: The information about project stages, scope of work and deadlines is gathered in real time based on Microsoft Project 2010 calendar schedule data; information about project milestone achievement is gathered from the documents stored in the project library.

Simple But Powerful

In this project example, we were able to meet all necessary requirements with strikingly low labor costs. Through customization, we achieved:

  • Comprehensive project information, categorization and structure
  • Budget management with multi-phase budgeting scenarios support
  • Risk/Scope/Change/Quality/Time/Cost/Procurement management
  • Documents repository
  • Support for all project phases
  • Project status dashboard, reports and automatic calculation of project metrics
  • Support for multi-step processes defined in our internal project management methodology
  • Integration between Project Server and SharePoint

Furthermore, this project example was based on an actual Microsoft Project Server 2010 adoption and customization effort—and could be easily replicated by any project management team, in any industry.

In fact, basic customization can benefit much more than just collaboration on project planning. All project tasks that involve working with operational data could be facilitated in this manner, including:

  • Procurement management
  • Contracting work management
  • Working with project questions and risks
  • Working with project related documentation, including structured document storage and customized workflows

The message is clear: Regardless of a company’s internal standards, a bit of customization can foster a world of new potential for PMIS functionality—and a world of new value for your enterprise.


This article, along with any associated source code and files, is licensed under The Code Project Open License (CPOL)


About the Author

United States United States
This member doesn't quite have enough reputation to be able to display their biography and homepage.
Group type: Organisation (No members)

You may also be interested in...


Comments and Discussions

-- There are no messages in this forum --
Permalink | Advertise | Privacy | Terms of Use | Mobile
Web03-2016 | 2.8.180515.1 | Last Updated 4 Sep 2014
Article Copyright 2014 by EastBancTech
Everything else Copyright © CodeProject, 1999-2018
Layout: fixed | fluid