Accessing TeamFoundationServer source control

This chapter provides an overview about how to access a Microsoft Team Foundation Server (TFS) programmatically by using the corresponding DLLs that are supplied by Visual Studio. This documentation has been written for your convenience and to make first steps easier when trying to combine TwinCAT Automation Interface code with TFS DLLs. For a more detailed documentation about the TFS API, we highly recommend to visit the corresponding MSDN articles.

This documentation covers the following topics:

The following TFS API DLLs are being used within this documentation:

Connecting to a TFS Server

The Microsoft TFS API lets you connect your application containing TwinCAT Automation Interface code to your development repository on a remote server. The connection requires a string describing the address, the port and the collection of your remote server e.g. http://your-tfs:8080/tfs/DefaultCollection.

Before you connect, define an instance of Uri class and TfsConfigurationServer class. Assign the remote server link to the configuration server:

Code Snippet (C#):

string tfsServerUrl = "http://your-server:8080/tfs/DefaultCollection";
Uri configurationServerUri = new Uri(tfsServerUrl);
TfsTeamProjectCollection teamProjects = TfsTeamProjectCollectionFactory.GetTeamProjectCollection(configurationServerUri);
VersionControlServer verControlServer = teamProjects.GetService<VersionControlServer>();

Connecting to TeamProjects

You can get a list of team projects or a specific team project on the server by executing the following code snippets:

Code Snippet (C#):

// Get all Team projects
TeamProject[] allProjects = verControlServer.GetAllTeamProjects(true);

// Get specific Team Project
TeamProject project = verControlServer.TryGetTeamProject("TeamProjectName");

Working with workspaces

Team foundation deals with workspaces which comprises mappings to working folders. These mappings link server-side folders to local folders on your hard-drive. It additionally also stores the name of the owner and the name of your computer as a part of the workspace name. A workspace is a must before performing any version control task because it stores information about files, versions and list of pending changes.

To begin with TFS Client API offers a Workspace class which stores the information mentioned above and offers extensive suit of methods to interact with the files and folders. Suppose you wish to create a workspace for a folder named, folderName, then create a string containing the computer name and the folder:

Code Snippet (C#):

// Specify workspace name for later use
String workspaceName = String.Format("{0}-{1}", Environment.MachineName, "Test_TFSAPI");

// Create new workspace
Workspace newWorkspace = verControlServer.CreateWorkspace(workspaceName, verControlServer.AuthorizedUser);

A mapping can now exist between the server-side folder and your local folder specified by folderName under workspace. To get an existing or delete a workspace, simply execute the following methods:

Code Snippet (C#):

// Delete workspace
bool workspaceDeleted = verControlServer.DeleteWorkspace(workspaceName, verControlServer.AuthorizedUser);

// Get existing workspace
Workspace existingWorkspace = verControlServer.GetWorkspace(workspaceName, verControlServer.AuthorizedUser);

Creating working folders

To connect to a specified project folder, you need a path to the project relative to the root.

For instance, if the project is stored on: your-server\Development\TcSampleProjectX, then the relative path to that folder is $\Development\TcSampleProjectX.

To match this folder to the projects on the server, you can iterate over a set of all registered projects on the server. A registered project is the root of project collections found underneath.

Code Snippet (C#):

// Create mapping between server and local folder
string serverFolder = String.Format("$/{0}", teamProject.Name + "/Folder/SubFolder");
string localFolder = Path.Combine(@"C:\tfs", workspaceName);
WorkingFolder workingFolder = new WorkingFolder(serverFolder, localFolder);
existingWorkspace.CreateMapping(workingFolder);

Get latest version of an item

As mentioned earlier Workspace class offers a rich set of methods to execute the TFS commands from within the code. But before illustrating, here is an example of creating a link to an item in the working folder. To create a relative path:

Code Snippet (C#):

String existingItemPath = "$/Developement/TcSampleProject/Examples/Samples00/TestPlc/POUs/MAIN.TcPOU"; 

Or an absolute path:

String existingItemPath = C:/tfs/Developement/TcSampleProject/Examples/TestPlc/POUs/MAIN.TcPOU";

To get the latest version of the item in the example, add following line of code:

Code Snippet (C#):

String existingItemPath = "$/TeamProjectName/Folder/SubFolder";
GetRequest itemRequest = new GetRequest(new ItemSpec(existingItemPath, RecursionType.Full), VersionSpec.Latest);
existingWorkspace.Get(itemRequest, GetOptions.GetAll);

Here the RecursionType.Full executes the request on all the items under the item node but you can select it depending on your application’s requirement and existing item hierarchy. For more information please refer to the API documentation on MSDN.

Getting a list of pending changes

You can also get a list of pending changes made to the item or a collection of items with following line of code:

Code Snippet (C#):

PendingChange[] pendingChanges = existingWorkspace.GetPendingChanges(existingItemPath, RecursionType.Full);

For collection of items, consider the overloaded variance with Item[] as argument.

Checking-In and Checking-Out

You can check out an item or a collection of items for editing:

Code Snippet (C#):

int checkoutResult = existingWorkspace.PendEdit(existingItemPath, RecursionType.Full);

To check-in the collection of pending changes to an item by:

Code Snippet (C#):

int checkinResult = workspace.CheckIn(pendingChanges, usercomment);

Undo an operation

To Undo an operation, simply execute:

Code Snippet (C#):

int undoResult = existingWorkspace.Undo(existingItemPath, RecursionType.Full);