Thursday, February 12, 2009

How to programmatically check in and out from StarTeam using .NET


I recently had a need at my job to programmatically check out some files from a StarTeam repository, modify them and check them back in. Note that I don’t mean the regular use of a source code repository where you check things in and out from your IDE as you work on them. I’m talking about writing a program that checks the file out, modifies it and checks it back in.

I knew that StarTeam had an SDK that would allow programmatic access to files under source control and after looking around I found that it could be used with .Net. What I couldn’t find was anything telling exactly how to check files in and out via the .Net SDK. So after playing around with it a while I finally figured it out and decided to post this so that others wouldn’t have to go through the trouble I did.

What You'll Need

To access a StarTeam repository from .Net you need to download and install the StarTeam SDK for .Net. Currently you can find it on the Borland StarTeam Download page. (I also have the StarTeam Cross Platform Client installed on my machine. I don’t know if this is required as well, but I have a feeling that it probably is.)

In your .Net project you need to add references to Borland.StarTeam.dll and Borland.StarTeam.Core.dll. You should be able to find these files in your C:\Program Files\borland\StarTeam SDK Runtime for .NET 10.4\bin folder.

In your code, the first thing you need to do is create a Borland StarTeam Server object. This will be your interface to the StarTeam repository. When creating the object you pass it the name (or IP address) of your StarTeam server and the port number that it’s listening on:

Imports Borland

Dim ServerName As String = "STSRV"
Dim ServerPort As Integer = 49201

Dim STServer As StarTeam.Server
STServer = New StarTeam.Server(ServerName, ServerPort)

Note that you could change the “Imports Borland” at the top of your code to “Imports Borland.Starteam” to eliminate typing all the “StarTeam” prefixes. I’ve haven’t done that here because I think it makes it easier to see what is a StarTeam object and what is a regular .Net object.

Next you need to connect to the server:


Now that you’re connected, you can log in with your StarTeam user id and password:

STServer.LogOn(userid, starpassword)

Now that you’ve logged onto the server, you have to pick which StarTeam project you want to work with. You can get a reference to a StarTeam Project object by passing the project’s name to the Server object’s projects method:

     Dim ProjectName As String = "Payroll"
Dim STProject As StarTeam.Project
STProject = STServer.Projects(ProjectName)

Next you need to get a reference to your root folder. If you’re like me, you can just use the Project’s default view’s root folder:

Dim STRootFolder As StarTeam.Folder
STRootFolder = STProject.DefaultView.RootFolder

Then you’re going to set your file folder. This is a StarTeam folder object that represents the folder (in StarTeam) that contains the file you are trying to check out. For instance, if the folder structure in your repository looked like this:

and you wanted to get a the file called Processed located under the Payable folder, you would want to set your file folder to “Reports\Payable.” (This is assuming your root folder gets set to Accounting.)

So you first create a StarTeam folder object. Then you use the StarTeamFinder to find your folder in StarTeam and set your object to point to it:

Dim MyFolderName As String = "Reports\Payable"
Dim STFileFolder As StarTeam.Folder
STFileFolder = StarTeam.StarTeamFinder.FindFolder(STRootFolder, MyFolderName)

Now we need to create a StarTeam file object to represent the file that we’re trying to check out. Then we’ll point it to the file by using the StarTeamFinder again. (The last parameter indicates whether or not the search should be case sensitive.)

Dim MyFileName As String = "Processed"
Dim STFile As StarTeam.File
STFile = StarTeam.StarTeamFinder.FindFile(STFileFolder, MyFileName, False)

Theoretically, we could now check out the file by coding STFile.Checkout(). This should check the file out to the StarTeam project’s working folder.

However, my task called for checking out the file to somewhere besides the StarTeam working folder. To do this, I had to use a CheckOutManager. You create these by using a method on the project’s default view

 Dim STCheckOutManager As StarTeam.CheckoutManager
STCheckOutManager = STProject.DefaultView.CreateCheckoutManager

I needed my file to be checked out with an exclusive lock (so no one else could check it out while I had it). So I set this option on the Checkoutmanager:

STCheckOutManager.Options.LockType = StarTeam.Item.LockType.EXCLUSIVE

Now, we need a (.Net) file object to represent where we want the file to be checked out to:

Dim MyFileIO As New System.IO.FileInfo("G:\temp\work\Processed")

Then –finally-- we actually give the command to check out the file:

STCheckOutManager.CheckoutTo(STFile, MyFileIO)

Check It In

Okay, now that we’ve got our file checked out and made our changes, it’s time to check it in. How do we do that? We’ll, you’ve probably guessed that we’re going to use a CheckInManager.

Dim STCheckInManager As StarTeam.CheckinManager
STCheckInManager = STProject.DefaultView.CreateCheckinManager
STCheckInManager.CheckinFrom(STFile, MyFileIO)

Assigning to a Change Request

My project required me to give the reason and a change request number for the check-in, so I had some more code to write. It involved finding the change request in StarTeam and setting some options on the CheckInManager. I created a function that takes the change request number you are looking for and returns a StarTeam Change Request object.

Private Function GetChangeRequest(ByVal STProject As StarTeam.Project, ByVal CRNumber As Integer) As StarTeam.ChangeRequest

First we have to have to declare a Borland StarTeam Type variable and set it to the type of object that we’re looking for – Change Requests.

Dim CRType As StarTeam.Type
CRType = STProject.DefaultView.Server.TypeForName(STProject.TypeNames.CHANGEREQUEST)

Next we need a Folder List Manager object. This object holds a collection of StarTeam folders. We set it to use our default view and to include everything by telling it to start at the root and include all subfolders. The -1 means include all subfolders

Dim Flm As StarTeam.FolderListManager
Flm = New StarTeam.FolderListManager(STProject.DefaultView
' The -1 means include all subfolders
Flm.IncludeFolders(STProject.DefaultView.RootFolder, -1)

Now we will create an Item List Manager that will hold all the change request items that are found in the folders in the Folder List Manager. We pass it the type of items we are looking for and the Folder List Manager:

Dim Ilm As New StarTeam.ItemListManager(CRType, Flm)

Now that we have a collection of all the change requests, we can search through them and find the one that matches our number. (The value passed in through the CRNumber parameter.)

       For Each cr As StarTeam.ChangeRequest In Ilm.Items
If cr.Number = CRNumber Then
Return cr
End If

Return Nothing
End Function

We loop through and if we found the one we’re looking for we return it, otherwise we return null.

Using this function I could now tell the CheckInManager which change request to associate it with (change request number 212 in this case):

STCheckInManager.Options.ProcessItem = GetChangeRequest(STProject, 212)
STCheckInManager.Options.CheckinReason = "Reason goes here"
STCheckInManager.CheckinFrom(STFile, MyFileIO)

A Easier Way

Wow, that was a lot of work just to check a file in and out wasn’t it? For my project, I ended up wrapping all that up into an object to make it (a lot) easier. If you’re interested, I’ve made the object available at the bottom of the post. BE WARNED, it’s not really suitable for a production environment. Error handling is non-existent. Use at your own risk.

To use the object, first set a reference to the StarTeamLib.dll.

In your code, create an object of type StarTeamAccess:

Dim sta As New StarTeamLib.StarTeamAccess
Then set your properties:
// Server name & port
sta.STServerName = STSRV"
sta.STServerPort = 49201

// User id and password
sta.STUserID = "youruserid"
sta.STPassword = "yourpassword"

// Project name and folder
sta.STProjectName = "Payroll"
sta.STFolder = "Reports\Payable"
Now you can checkout your files:
//Finally checkout the file
sta.CheckOutFile("Processed", "c:\temp\checkouts")
Then, when you're done, you can check it in with:
//Checkin the file
sta.CheckOutFile("Processed", "c:\temp\checkouts")
Much easier, right?

Here's the dll: StarTeamLib.dll

No comments: