In my last article, I mentioned a method to associate work items and change sets. So, now is time to show it to you.
I tried many approaches to do it on server side and only got one way to make it work. But there is a catch, I'll first show the method then I explain the catch.
/**
* Method that associate an work item with a change set
*
* @param workItem Work item that will be associated
* @param changeSet The change set to associate the work item with
* @param stream The stream that within the association will occur
* @throws TeamRepositoryException
*/
private void associateWorkItem(IWorkItem workItem, IChangeSetHandle changeSet, IWorkspaceHandle stream) throws TeamRepositoryException {
// Repository Item Service
IRepositoryItemService itemService = (IRepositoryItemService) getService(IRepositoryItemService.class);
// Fetch fresh states of work item and change set
IWorkItem wi = (IWorkItem) itemService.fetchItem(workItem, IRepositoryItemService.COMPLETE);
IChangeSet cs = (IChangeSet) itemService.fetchItem(changeSet, IRepositoryItemService.COMPLETE);
// Link Service (an association is basically a link between the objects)
ILinkServiceLibrary linkLibrary = (ILinkServiceLibrary) getService(ILinkService.class).getServiceLibrary(ILinkServiceLibrary.class);
// Target = Work Item and Source = Change set
IItemReference target = IReferenceFactory.INSTANCE.createReferenceToItem(wi);
IReference source = IReferenceFactory.INSTANCE.createReferenceToItem(cs);
// Create and save the link
ILink link = ILinkFactory.INSTANCE.createLink(ILinkConstants.CHANGESET_WORKITEM_LINKTYPE_ID, source, target);
linkLibrary.saveLink(link);
}
As I said, it's pretty straight forward. An association is nothing more than a link between the work item and the change set. So all you have to do is to create this link.
But what is the catch? Well, for reasons unknown to me, Jazz Team has restricted the creation of these type of link to the component that has the id "com.ibm.team.filesystem.workitems"
So you have to override the method getComponentId() to match the allowed component id, as showed bellow:
@Override
public String getComponentId() {
return "com.ibm.team.filesystem.workitems";
}
That is it, pretty simple, but with a workaround that might be a deal breaker for some.
Modified by EduardoBello 270003RXWC
|
The RTC has many types of links that we can use, but depending on the software development process of your business, you may feel the need to create a new type of relationship between WorkItems. In my opinion, this creation of new link types, although not very complicated, could be more simplified. Anyone who has read the previous posts or have developed some plugin for RTC will have no difficulty in creating a new type of link, because it is nothing more than a plugin. The main difference is that you have to install the plugin on the server and if you use the Ide Client you have to install the eclipse plugin directly into the client as well. As I said earlier a link type is a plugin, so the first step is to create a Plug-in Project Name your plugin, in our case we call it rtc_rework_link, as it will indicate that a workitem is a Rework opened by another ( Rework Opener). Remember, do not select any additional options to create the plugin.
Go to Dependencies tab and add the plugin com.ibm.tean.repository.common Now, go to the Extensions tab, add the Extension Point com.ibm.team.repository.common.linkTypes. Then right click on newly created item, choose New -> LinkTypes. Fill out the following properties: id: com.ibm.team.apt.linktype.rework constrained: true internal: false In plugin.xml tab, which is actually the source code of the plugin, add the elements <source> and <target> to the <linkType> element that was created in the previous step. Note that you can skip the previous step and configure directly the plugin.xml with all options. I chose to show the previous step so that you can relate the tab with the xml element. The above code defines a type of link that connects two WorkItems ( itemReferenceType). One source WorkItem will be called Rework and has cardinality 0..n, and the target WorkItem will be called WorkItem Rework Opener and have cardinality 0..1. There, the plugin is finished. Only thing left is the well-known steps of creating a feature for the plugin, create the update site for the feature and deploy the site on the server. If you have questions regarding these steps take a look at this post to remember. As I mentioned at the beginning of the post, if you use the RTC Client (Eclipse) will need to install the plugin directly on the client. This is done in the same way you install any plugin via the Eclipse Update Sites. Access: Help -> Install New Software... . Click Add to add the new site, choose the location where the Update Site was compiled, select your plugin and install it normally. Any questions just email me, tweet or comment here. See you!
|
Hello today I'll show an example code to duplicate an workitem using the Jazz API. In order to facilitate the customization to any template, in this example we will be able to choose which fields to copy using a vector.
Finally, we will create a link between the two workitems, one was a duplicate of another.
First, let's create the main functions:
Now, fill the vector fields and call the function, as in the example below:
That's it, see you next post.
Modified by EduardoBello 270003RXWC
|
Hello everybody, finally we begin to actually show how to develop plugins to extend Rational Team Concert (RTC). To follow the steps in this post, you must already have a server and a client properly configured for plugin development. If you have not, take a look at three part tutorial I published in this blog ( part 1, part 2 and part 3). For our first example, I chose something simple and easy, but it will clarify the process in a very objective way. Most steps in this example will be repeated for almost all plugins you will need, in fact the main change is usually at the source code. In this example, we will develop a plugin that check summary description of a WorkItem and if this description contains the character "#", the plugin will not let this WorkItem to be saved. As I said, a simple example, but changing just one line of code, you can audit what you want in the summary of the WorkItem (eg: Avoid numbers, forcing some specific content) Let's get started. First let's create a new Plug-in Project Let's call it "rtc-summary-check-advisor." We don't need to mark any option (activator, UI contributions, API analysis): With the project created, select Dependencies tab and add most frequently used plugins as required ( com.ibm.team.process.service, com.ibm.team.workitem.common, com.ibm.team. workitem.service, com.ibm.team.process.common, com.ibm.team.repository.common, com.ibm.team.repository.service) and import the package org.eclipse.core.runtime. After that, it is important that you save the project to refresh the workspace. A pause now for important explanations. Before we continue we need a brief definition about extensions points and their relationship with the RTC. Well, Extension points are, as the name suggests, entry points where the plugins runs on system. In the RTC, these entry points are pre-defined by its API. In my work, the vast majority (95%) of the customizations that I develop uses as entry point the save workitem event. For this event there are basically two types of plugins: Advisors and Participants. Advisors are the preconditions and the Participants are known as follow-up actions. It is important to consider that IBM suggest as good practice (and I follow as a rule) that if a plugin will change the state of a workitem, it must be a participant. Advisors should not change the data, they only validate it. With this in mind, let's select Extensions tab and add our Extension Point for this plugin. And since this is a pre-condition and will not change the state of the workitem, let's use an Operation Advisor. Click Add. Look for: com.ibm.team.proccess.service.operationAdvisors. This option only appears if you have correctly added the required plugins as mentioned earlier. Fill the following fields: id: Identifier of the advisor class: Java class that will be called by the advisor name: Name by which the advisor will be identified in the process settings. operationId: Id of the operation where the advisor will be injected. Now we add an extension service. For this simple example we would not need an extension service, but as in most complex plugins will need to load services from RTC API, I thought I would show you the complete way. Right click, New -> extensionService Type an id and use the same class used in the extension point. Click implementationClass to create the class, it extends AbstractService and implements IOperationAdvisor. Now we implement the class with the following code: We will explore more details about programming in future posts, but with the comments and because it is a simple example, you will have no difficulty understanding the logic. Now we need to create a feature and a site for our plugin. This is very simple. Create a new Feature Project Let's call it rtc-check-summary-advisor-feature Now in Plug-ins tab, let`s add our plugin, as shown in sequence below. Now let's create a Site Project To speed up the development we can create the site in the server folder. The recommended folder is server\conf\ccm\sites\YOUR_SITE_FOLDER, in our case \server\conf\ccm\sites\rtc-check-summary-advisor-site. Similar as we did with the plugin, we will add our feature to created site: Now we build our site, right click site.xml file, and select PDE Tools -> Build Site Before starting the server, we must create a provision file for our site to load. This file should be created in the \server\conf\ccm\provision_profiles. Create a text file with the following content and name it rtc-summary-check-advisor-site.ini url=file:ccm/sites/rtc-check-summary-advisor-sitefeatureid=rtc_check_summary_advisor_feature After starting the server there is only one thing to do: Enable the advisor. Open the project area. Select Process Configuration, go to Team Configuration -> Operation Behavior, look for Work Items -> Save Work Item (server) and click Add to add our Advisor. All done! Now if you try to save a Work Item typing the "#" character in the summary will receive this message. That is it, I hope this material help you guys. In coming posts I will bring more examples and will focus more on programming. The level will increase, I will assume that you've got the basics and I will focus in the API. Source code is available for download Leave your comments, critics, suggestions. Your feedback is very
important to make me improve the material. Despite the fact that I'm
relatively "old" in development world, I am entirely new in this area of
articles, blogs and video lessons. Some spelling errors may occur. If you find any misspelled words, let me know.
|
Hi, this week I received an email from a consultant asking about the process to update a plug-in (bundle) for Rational Team Concert. This can be a doubt of other readers, so I decided to write this little post to explain how this can be done. As readers of this blog already know, the customizations are plug-ins, which are included in a Feature, which is related to an Update Site. Then a provision file is created to inform RTC where is the site and which feature has to be loaded.
The update sites can be placed on any path (relative or absolute) that the server can access. In RTC 3.0, sites are usually placed in the "/server/conf/ccm/sites" or "/server/conf/jazz/sites". note: (ccm e jazz are the two most common path options for the application Change and Configuration Management). So if you made any changes in a plugin and want the server to update this plugin, you first need to rebuild the Update Site After that, you need to configure the server to reload bundles on next restart. For that, access to this URL: https://{your-server-address}:9443/ccm/admin/cmd/requestReset. You will see a message like this:
Now replace old site directory with the one newly built. Okay, next time you restart the JazzTeamServer, the new plugins will be loaded. In a few cases, this may not be enough, then you must perform an extra step between stopping and restarting the server, which is delete the directory tomcat/work/Catalina/localhost/ccm, thus forcing application deploy. That's it. See you on next post.
|
It makes a while since I update my blog, but that will change a lot. I was hired by Pitang/Qualiti to work in its office in Sao Paulo/Brazil. Pitang/Qualiti is an IBM Business Partner, and was finalist for Rational Award for Innovation in IT Development at IBM Innovate 2012. I'll be working directly with IBM's products, especially Rational Tools, which surely will render great (and frequent) posts to this blog. So be sure to closely follow the updates.
|
Hello, It has been a while since I posted here, I've been really busy, but I got a few minutes of free time to write this example of Operation Advisor which aims to prevent a certain type of workitem to be linked to another workitem of a different type. For this example, let's make Tasks workitems unable to link Defect workitems as children. You can easily change the types of workitems and links in this example to suit your needs. The purpose of this and future posts is to get familiar with the API Jazz. Before proceeding it is essential that you already know the first steps to creating a RTC plug-in, if you do not know stop here and read this previous post that explains the basic steps with a simple example. First create your Plug-in Project and select Dependencies tab and add most frequently used plugins as required ( com.ibm.team.process.service,
com.ibm.team.workitem.common, com.ibm.team. workitem.service,
com.ibm.team.process.common, com.ibm.team.repository.common,
com.ibm.team.repository.service) and import the package org.eclipse.core.runtime. After that, it is important that you save the project to refresh the workspace. Let's select Extensions tab and add our Extension Point for this
plugin. And since this is a pre-condition and will not change the state
of the workitem, let's use an Operation Advisor. Click Add. Look for: com.ibm.team.proccess.service.operationAdvisors. This option only appears if you have correctly added the required plugins as mentioned earlier. Fill the following fields: id: Identifier of the advisor class: Java class that will be called by the advisor name: Name by which the advisor will be identified in the process settings. operationId: Id of the operation where the advisor will be injected. Add an extension service, Right click, New -> extensionService and fill an id and use the same class used in the extension point. Now let's the code:
All done! Now just create the feature and the site and upload the plugin to server. I will try to shorten the time between posts, but by May it can be a bit difficult. See you next time!
|
To begin the development of customizations to the RTC is necessary to prepare and configure the environment. Here I will split this preparation into three parts, the first one will cover the jazz server and client installation, the second one will explain the initial settings of the server and licenses, and the third part in which we talk about the changes needed to make environment ready for development, such as debug configuration and using the SDK. We will be using version 3.0 of Rational Team Concert, if you want to develop for previous versions like 2.0.0.2, you won't find major problems, because although the product itself has improved considerably, the development methods have not changed that much. Preparing the Environment for Extending RTC (1/3) - Installing the RTC 3.0 (windows)
Important: This tutorial was produced using the windows version of the RTC, some screenshots may not match for other operating systems. A few aspects will be different, for example, the extension of some files "*. bat", "*. sh", "*. exe". Ok, lets get started. First you need to download the necessary files from the Jazz website (you must be registered and registration is free). After you log in, access the following download page https://jazz.net/downloads/rational-team-concert/releases/3.0?P=allDownloads There you will find several files for download, including web installers. Here we'll use the offline installers, and for that we need to download the following files: The first one is the license file (10 free developers licenses), then we have the installer, and the repositories of the server and client respectively. After downloading the files, unzip them to their respective folders, as shown below: Now install the Installation Manager (agent.installer\install.exe). Setup is very simple and requires no further explanation. Once installed, we will now configure the repositories in Installation Manager. Access the "File" -> "Preferences", select the tab "Repositories" and click the "Add Repository" Look for the file "repository.config" in folder " RTC-Eclipse-Client-repo-3.0\im\repo\rtc-client-offering\offering-repo", then repeat the process to file with same name, but in the folder " JTS-CCM-With-Trial-Licenses-repo-3.0\im\repo\jts-ccm-trial\offering-repo". Now that the Installation Manager know where are the installation files, we can install the server and client. To do this click "Install". The order of installation between server and client doesn't matter right now. Of course, you can only use the client if the server is up, but as in this first part we will not run the client, we can install it first because its installation is simpler. Select the package Rational Team Concert - Client for Eclipse IDE and proceed with the installation, accepting the License Terms and choosing the desired directory. Then it's time to install the server Okay, we have the server and the client installed. In the next post, we will configure the server initial settings to make it work properly. Leave your comments, critics, suggestions. Your feedback is very important to make me improve the material. Despite the fact that I'm relatively "old" in development world, I am entirely new in this area of articles, blogs and video lessons. Some spelling errors may occur. If you find any misspelled words, let me know.
|
This is the second part of the article "Preparing the Environment for Extending RTC", you can access the first part here. In this post we will deal with the initial configuration of the RTC local server to make it running and ready to be prepared for development.
Preparing the Environment for Extending RTC (2/3) - Initial Settings
Important: This tutorial was produced using the windows version of the RTC, some screenshots may not match for other operating systems. A few aspects will be different, for example, the extension of some files "*. bat", "*. sh", "*. exe".
Once installed, we need to make the initial settings on the server local RTC to make it run properly. First, let's start the server. Go to the folder where the Jazz server was installed and run " server.startup.bat" (or " server.startup.sh", see note above)
The first time may take up to several minutes to start the server. When the message " INFO: Server startup in seconds *****" appears, it means the server is up.
Now let's access server for the first time to configure it. Access: https://localhost:9443/jts/setup and login with username ADMIN and password ADMIN.
The first screen will be shown as follow. Click "Next"
Here we set the public URI for our server. This part requires some additional steps, as shown below, the Jazz do not kindly accept us to leave "localhost" as our Public URI.
There are MANY ways to solve this, I chose a really simple one: Create an entry in the hosts file resolving any given name (I chose "rtclocaljazz.com") to our local ip. In windows the file to be edited is "windows\system32\drivers\etc\hosts", in Linux is "/etc/hosts". Below is the windows screenshot
Then the jazz server will let us set up our public URI without restrictions. So fill the field with the value: https://rtclocaljazz.com:9443/jts
For the next steps, we can leave the default settings.
Database configuration, if you have some SQL Server, Oracle or DB2 that prefer to use, you can configure it here.
E-mail notifications. For now we'll leave it disabled.
Setup user registry. Here we can also leave the default option for the Jazz use tomcat's database.
For security reasons, Jazz recommends to you disable the ADMIN user, since it is a standard user. So you must create your user and check "Disable default ADMIN access" option.
For now do not choose any license. Later we'll add the free developers licenses.
Now let's set and register the Jazz application named "Change and Configuration Management." Click " Register Applications"
If all goes well, you see the following message.
The application public URI will be the same as the jazz server, only changing "jts" (Jazz team server) to "ccm" (change and configuration management). In this case: https://rtclocaljazz.com:9443/ccm
In database configuration, we can leave the default options
Finalize application setup.
After that, choose "Administer the Server"
Ok, it's almost done. Now we need to install the licenses on the server, remember that in our case we'll use the 10 free licenses that IBM provides to RTC Express Edition. Access server administration: https://rtclocaljazz.com:9443/jts/admin .
Choose the "Manage server" option via "Jazz Team Server - Server Administration", then navigate to option License Key Management
In the Client Access License Types box click "Add". In file dialog that appears click on "Choose File" (or "Browser" depending on your OS and browser)
Find and select the file "RTC_Developer-10-C.jar" (which was unzipped from licenses archive as mentioned in the first part of this article)
The jazz will recognize the file, then just click "Next."
Do not forget to edit the user you created and assign to him one of these 10 licenses free.
Finally! Our server is fully functional. I advise you to create users, project areas, workitems, browse through the server options ... In other words, become familiar with Jazz Team Concert.
After I finished this tutorial, I found an official Jazz Team video ( http://jazz.net/library/video/552) about the same subject. Check it also:
Next post will be about the necessary changes to configure the development environment. Probably the third part will be a video lesson, if I can solve minor problems with sound on my workstation. This third party should only be published in early January, so Happy New Year everyone!
Leave your comments, critics, suggestions. Your feedback is very important to make me improve the material. Despite the fact that I'm relatively "old" in development world, I am entirely new in this area of articles, blogs and video lessons.
Some spelling errors may occur. If you find any misspelled words, let me know.
Modified by EduardoBello 270003RXWC
|
This is the third part of the article "Preparing the Environment for Extending RTC", you can access the first part here and second part here.
In this post we will deal with the initial configuration of the SDK and Debug environment. Both are critical to extend RTC. Preparing the Environment for Extending RTC (3/3) - Configuring SDK and Debug.
Important: This tutorial was produced using the windows version of the
RTC, some screenshots may not match for other operating systems. A few
aspects will be different, for example, the extension of some files "*.
bat", "*. sh", "*. exe". To follow this tutorial you must have a local server configured and running normally. If you haven't already, please go to the first two parts of the tutorial using the links in the first paragraph. Some files we will need only exist if the server runs at least once (deploy war files). I will refer to the directory where you installed the applications as jazz {jazzdir}, so replace that expression with the directory where you installed the platform jazz on your machine and not its literal value. Let's get started! Our first step will be to configure three files. The first will enable debugging on the server side, the other two, nearly identical, will enable the use of the server console to obtain some information during the development process. Open the file {jazzdir}\IBM\JazzTeamServer\server\server.startup.bat Find the lines with JAVA_OPTS option, and add the following line: set JAVA_OPTS=%JAVA_OPTS% -Xrunjdwp:transport=dt_socket,server=y,suspend=n,address=2244. Important: The port can be any one that are not in use, in our case I chose port 2244. What is required is that the port configured in this file is used to configure client debug as we shall see. There is also an optional step, configure this launcher to automatically delete the work directory of ccm (or jazz). Whenever you update a customization (plugin), to make sure that the server will read the newest version is useful to delete the work directory of tomcat. But you don't have to do it in this file, so it is more like a personal choice. At the end, your file will look like this: Now let's make a change in two similar files. Open the files: {jazzdir}\IBM\JazzTeamServer\server\tomcat\webapps\ ccm\WEB-INF\web.xml and {jazzdir}\IBM\JazzTeamServer\server\tomcat\webapps\ jts\WEB-INF\web.xml. Then uncomment the block that deals with the commandline -console argument Now you need to download the SDK 3.0 (you must be logged in jazz.net) and then unpack it. In our case we chose the directory {jazzdir}\IBM\TeamConcert\sdk. As the structure of folders and directories is very long, some unzip tools are unable to extract the files correctly, so JazzTeam recommends using 7-zip (free). The setup outside the client eclipse is over, now let's configure the client. Start the server to make sure it's running smoothly. Open the Jazz Client (or eclipse with jazz plugin installed) and go to menu Window -> Preferences and select Plug-in Development -> Target Platform. Select Running Platform and click the "Edit" Let's add a new location for this platform: Select source " Installation" Type the path where you extracted the SDK, in our case: ${eclipse_home}\sdk The eclipse will recognize the plugins, then finish the dialog. Open the view "Plugins" and select all Right-click, select "Add to Java Search". This step may take a while to complete. Ok, now both our server and our client should be read to extending RTC and debugging . Let's try to debug by placing a breakpoint on a server call . To do this, find and open the class ServerStatusRestService. Navigate to the method declaration getActiveServiceInfo() and insert a breakpoint in the first line. Now create a new debug configuration. Go to menu Run -> Debug Configurations and add a new item Remove Java Application Configure the port as we configured in server.startup file (in our case: 2244) and click on debug. Now we call the event which will trigger our breakpoint. Access the administrative area of the Jazz Team Server Click on Active Services. This should trigger our breakpoint. If all goes as planned, you'll see the debug screen on the client Okay, now the environment is completely configured for development and extending Rational Team Concert. In future posts we will finally see how to extend RTC. Leave your comments, critics, suggestions. Your feedback is very
important to make me improve the material. Despite the fact that I'm
relatively "old" in development world, I am entirely new in this area of
articles, blogs and video lessons. Some spelling errors may occur. If you find any misspelled words, let me know.
|
First, yes I'm back, after a couple years out, I decided to reactivate this blog and now I have tons of things to talk about.
For my "Welcome back" article I'll do a very nice peace of code. The demand has started with a customer asking for a solution to read a "pom.xml" file from an Stream, increment the version number attribute and deliver it back to the stream. So I began my research and found an article from Kelvin that did help me a lot: Reading and writing files directly on a stream. And of course I found this article by the Ralph's blog tsjazz | Jazz in Flight . (which is the best blog about RTC API that I know of).
That article showed me the way, but I still had a problem, the article was all about using client API and as I said, the customer needed to do this at server side, more specifically using an IOperationParticipant. So, after some hours of digging the RTC SDK, I was able to get it done. So, here is it.
First, the method to update the file
/**
* Update the content of a file
*
* @param workItem
* @param filePath
* @param stream
* @param component
* @param myService
* @return
*/
public boolean updatePomVersion(IWorkItem workItem, String filePath, IWorkspace stream, IComponent component, AbstractService myService) {
// File pat, e.g. src/pom.xml
IPath pomPath = new Path(filePath);
// Getting services
IScmItemService scmItemService = (IScmItemService) myService.getService(IScmItemService.class);
IScmService scmService = (IScmService) myService.getService(IScmService.class);
ServiceConfigurationProvider config = ServiceConfigurationProvider.FACTORY.create(stream, component);
IServerSideVersionedContentService contentService = myService.getService(IServerSideVersionedContentService.class);
IServerSideFileContentService fileContentService = myService.getService(IServerSideFileContentService.class);
// Trying to locate the file within the component
IVersionableHandle versionableHandle;
try {
versionableHandle = scmService.configurationResolvePath(
config, component.getRootFolder(),
pomPath.segments(), null, null);
// File not found
if (versionableHandle == null) {
System.out.println("Versionable not found.");
return false;
} else {
// Fetching Versionable from its handle
IVersionable versionable = scmItemService.fetchState(versionableHandle, IScmItemService.COMPLETE);
// If not file (that is just to be safe)
if( !(versionable instanceof IFileItem ) ) {
System.out.println("Versionable is not a file"); //$NON-NLS-1$
return false;
} else {
// Reading file content
IFileItem file = (IFileItem) versionable;
IFileContent content = file.getContent();
ByteArrayOutputStream outStream = new ByteArrayOutputStream();
contentService.fetchContentTrusted(versionableHandle, content.getHash(), outStream);
// Now that you have the content of the file in "outStream" object
// I'll skip the code to update the file content
// as this is not the goal of this article.
// Let's just assume that you have the new
// content in a new object called "newOutputStream"
// with something like:
// ByteArrayOutputStream newOutputStream = updateStreamContent(outStream);
// Updating File content
IFileItem fileWorkingCopy = (IFileItem) file.getWorkingCopy();
IFileContent newFileContent = createFileContent(newOutputStream.toByteArray(), fileContentService);
ICommitParameter param = ICommitParameter.FACTORY.create();
fileWorkingCopy.setContent((IFileContent) newFileContent);
param.addItemToSave(fileWorkingCopy);
// Applying lock and delivering
applyLock(stream, component, fileWorkingCopy, scmService);
try {
// Create change set
IChangeSetHandle cs = scmService.createChangeSetForStream(stream, component, "Changeset Comment - File content updated", param, IScmService.DELTA_PER_INVOCATION, null);
IChangeSetHandle[] csHandles = new IChangeSetHandle[1];
csHandles[0] = cs;
// Deliver
scmService.deliverCombined(null, null, stream, new IBaselineHandle[0], csHandles, null, null, null, null);
// I'll cover how to associate a changeset with an work item (server side) in another post
// So this is only to get you curious :)
// associateWorkItem(workItem, cs, stream);
return true;
} finally {
// Remove the lock
removeLock(stream, component, fileWorkingCopy, scmService);
}
}
}
} catch (Exception e) {
return false;
}
}
Now let's look at the others methods created.
Starting with the two methods to lock and unlock the file. This is necessary to create a changeset.
@SuppressWarnings("unchecked")
/**
* Lock the file
*
* @param streamHandle
* @param componentHandle
* @param fileItem
* @param scmService
* @throws TeamRepositoryException
*/
private void applyLock(IWorkspace streamHandle, IComponentHandle componentHandle, IFileItem fileItem, IScmService scmService) throws TeamRepositoryException {
// Commit parameter
ICommitParameter instruction = ICommitParameter.FACTORY.create();
instruction.addItemToSave(fileItem);
// Setting up workspace/stream, component and contributor
LockParameter operationParameter = ScmDtoFactory.eINSTANCE.createLockParameter();
WorkspaceLocks wl = ScmDtoFactory.eINSTANCE.createWorkspaceLocks();
operationParameter.getToAcquire().add(wl);
wl.setWorkspace(streamHandle);
ComponentLocks cl = ScmDtoFactory.eINSTANCE.createComponentLocks();
cl.setComponent(componentHandle);
wl.getComponentLocks().add(cl);
ContributorLocks contL = ScmDtoFactory.eINSTANCE.createContributorLocks();
contL.setContributor(getAuthenticatedContributor());
contL.getVersionables().add(fileItem);
cl.getContributorLocks().add(contL);
// Locking file
scmService.updateLocks(operationParameter , null);
}
@SuppressWarnings("unchecked")
/**
*
* @param streamHandle
* @param componentHandle
* @param fileItem
* @param scmService
* @throws TeamRepositoryException
*/
private void removeLock(IWorkspace streamHandle, IComponentHandle componentHandle, IFileItem fileItem, IScmService scmService) throws TeamRepositoryException {
// Commit parameter
ICommitParameter instruction = ICommitParameter.FACTORY.create();
instruction.addItemToSave(fileItem);
// Setting up workspace/stream, component and contributor
LockParameter operationParameter = ScmDtoFactory.eINSTANCE.createLockParameter();
WorkspaceLocks wl = ScmDtoFactory.eINSTANCE.createWorkspaceLocks();
operationParameter.getToRelease().add(wl);
wl.setWorkspace(streamHandle);
ComponentLocks cl = ScmDtoFactory.eINSTANCE.createComponentLocks();
cl.setComponent(componentHandle);
wl.getComponentLocks().add(cl);
ContributorLocks contL = ScmDtoFactory.eINSTANCE.createContributorLocks();
contL.setContributor(getAuthenticatedContributor());
contL.getVersionables().add(fileItem);
cl.getContributorLocks().add(contL);
// Removing the lock
scmService.updateLocks(operationParameter , null);
}
And lastly the method to create the file content
@SuppressWarnings("restriction")
/**
* Create an IFileContent with the bytes informed
* @param bytes Usually coming from an Input or Output Stream
* @param fileContentService Service used to store de content
* @return
* @throws TeamRepositoryException
*/
private IFileContent createFileContent(byte[] bytes, IServerSideFileContentService fileContentService) throws TeamRepositoryException {
// Generate has code
ContentHash contentHashCode;
try {
contentHashCode = ContentHash.valueOf(new UnsynchronizedByteArrayInputStream(bytes));
} catch (IOException e) {
throw new TeamRepositoryException(e);
}
// Create an Input Stream with the informed bytes
ByteArrayInputStream inStream = new ByteArrayInputStream(bytes);
// Store the content
fileContentService.storeContent(contentHashCode, bytes.length, null, IFileContent.ENCODING_UTF_8, FileLineDelimiter.LINE_DELIMITER_NONE, 0, inStream);
// Setting the file content object
FileContent c = FilesystemFactory.eINSTANCE.createFileContent();
c.setHash(contentHashCode);
c.setPredecessorHint((ContentHash)null);
c.setSize(bytes.length);
c.setCharacterEncoding(IFileContent.ENCODING_UTF_8);
c.setLineDelimiter(FileLineDelimiter.LINE_DELIMITER_NONE);
c.setLineDelimiterCount(0);
return c;
}
All the code above runs directly with in a IOperationParticipant. You'll need the follow interfaces to make it works:
<requiredservice interface="com.ibm.team.repository.service.IRepositoryItemService">
<requiredservice interface="com.ibm.team.repository.service.IServerQueryService">
<requiredservice interface="com.ibm.team.repository.service.IContentService">
<requiredservice interface="com.ibm.team.scm.common.IScmService">
<requiredservice interface="com.ibm.team.scm.service.IScmItemService">
<requiredservice interface="com.ibm.team.scm.service.IServerSideVersionedContentService">
<requiredservice interface="com.ibm.team.repository.common.service.IPermissionService">
<requiredservice interface="com.ibm.team.repository.common.service.IContributorService">
<requiredservice interface="com.ibm.team.filesystem.service.internal.IServerSideFileContentService">
<requiredservice interface="com.ibm.team.process.service.IProcessServerService">
<requiredservice interface="com.ibm.team.repository.service.ITransactionService">
That is it! Let me know if you need anything else.
Modified by EduardoBello 270003RXWC
|
Recently, I worked on an implementation of Rational Team Concert (RTC) in a company in São Paulo. This company hired us to implement the Rational tool and to create its process of software development. This company also hired a Kanban professional. After a few meetings we decided to implement all together: the tool, the process of development and Kanban. This union turned out to be a success and opening my eyes to a new concept of the relationship between tools and process.
The method Kanban of software development has an emphasis on preventing waste and workload, as well as offer a visualization of the development process. It brings several concepts like "pulled" work rather than "pushed", a team or a user only starts a new task when it is able to achieve it without compromising the process. Another concept of Kanban is the continuous improvement process where changes are welcome and implemented in an evolutionary way without generating major impacts all at once. And finally, another important concept of Kanban is the limitation of work. A team has a limit of work (items) in progress, this increases team collaboration ("swarming") to solve problems that affect the progress of the work. Another benefit of the work limitation, is that a team will never overwhelm and exceed its production capacity.
RTC has been over their latest releases, increasingly adapting themselves to the use of Kanban. The best feature in this direction is the limitation of WIP (Work In Progress). This feature along with the Taskboard Plan View, allows us to have a fully functional Kanban board within the web interface of the RTC.
 Image from Jazz Blog: https://jazz.net/blog/
The tool allows us to visually change the board, changing WorkItems status by dragging and dropping virtual post-its, exactly as we would in a physical Kanban board. We can also set post-it colors by a variety of WorkItem properties (type, status and others)
The columns are defined from RTC states groups configured in the workflow process.
The union of a tool as powerful and customizable as the RTC, with a methodology like Kanban is proving its value in the market, and provides several benefits for companies such as:
- Flexibility: Both Kanban and RTC, are known for their ability to adapt to the changes.
- Process Visualization: Through the plans views, we can generate virtual kanban board, which give us visual information about development bottlenecks and the progress of the work;
- Continuous Improvement: With dashboards and reports features, you can extract indicators, generate graphs, and obtain productivity data that will help identify areas for improvement;
- Environment: The replacement of the physical board with a virtual one, helps maintain a better work environment and aligns with global sustainability, eliminating the excessive use of post-its.
Lastly, the combination of the RTC with Kanban is extremely beneficial and effective, and soon will become one of the most adopted market combinations. Soon I will publish other posts with more practicals examples of Kanban in RTC
|