2/09/2008

Extending Maven SCM: proxy-scm

Problem description

Maven is a great tool, but it has one constraint that makes it inapplicable in many cases.
It can checkout the whole project (pom.xml and sources) from a single place in SCM storage using a single tag.

It's quite suitable in open-source projects, where new versions of projects don't appear too often.
But in our company we have a lot of components, each of which is stored in its own place in SCM and tagged with its own tag. To make using Maven possible, we need to create either BASH or ANT script which would check out all required projects from SCM.

This is the concern:

why do I need Maven if i still need ANT for running it?

If only Maven could do it by itself...

After thinking a while, we have created a solution.

Solution

As known, Maven SCM plugin has several SCM providers: CVS, Subversion, ClearCase etc.
Idea is to create one more provider, Proxy SCM. Its main goal is to checkout different modules from different places calling other SCM providers.
We need to extend pom.xml with 2 attributes:
  • /project/modules/module@scmProvider
  • /project/modules/module@scmHost
  • /project/modules/module@path
  • /project/modules/module@tag


Given pom.xml of form:

<project>
<scm>
<connection>scm:proxyscm:cvs:pserver:@myhost:dir:nodule</connection>
<developerConnection>scm:proxyscm:cvs:pserver:bla-bla</developerConnection>
</scm>
<modules>
<module path="robots/terminator/sdk">terminator_sdk</module>
<module path="robots/terminator/ui" tag="terminator_ui_v1-2">terminator_ui</module>
<module scmProvider="svn" scmHost="http://svn.apache.org/repos/asf/commons/proper/launcher" path="trunk">commons_launcher</module>
</modules>
</project>
,

The proxy-scm provider checks out all the 3 projects into 3 subfolders in current folder, resulting in the following content:
  • pom.xml
  • terminator_sdk
  • pom.xml
  • src
  • terminator_ui
  • pom.xml
  • src
  • commons_launcher
  • pom.xml
  • src


Implementation

The code of proxy-scm provider is quite simple: it just needs to parse file "pom.xml" and call appropriate SCM provider for every module.

I would like to commit this code into the next Maven SCM version (1.1). But it seems those guys don't respond to JRA issues neither commit patches into new version :(

2/08/2008

Null-Initialization in Java

In many languages (C++), uninitialized variables lead to errors. So, it's considered to be a good style to initialize every variable with 0 or null.

however, in Java it's quite the opposite.
Initialization with null is not recommended for those class members that should not be null.

Instead, it's recommended to declare those members final and initialize only once with an adequate value.


See example below.


Bad practice:

private CCollectorTarget m_collectTrg = null;

private CCollectorSchema m_collectSchm = null;

private CCollectorProject m_collectPrj = null;

private CCollectorFiles m_collectFiles = null;

public CCollectorData( CCollectorTarget collectTrg,
CCollectorSchema collectSchm,

CCollectorProject collectPrj,

CCollectorFiles collectFiles )

{

m_collectSchm = collectSchm;
m_collectTrg = collectTrg;
m_collectPrj = collectPrj;
m_collectFiles = collectFiles;
}

Good practice:

private final CCollectorTarget m_collectTrg;
private final CCollectorSchema m_collectSchm;
private final CCollectorProject m_collectPrj;
private final CCollectorFiles m_collectFiles;

public CCollectorData( CCollectorTarget collectTrg,
CCollectorSchema collectSchm,

CCollectorProject collectPrj,

CCollectorFiles collectFiles )

{

m_collectSchm = collectSchm;
m_collectTrg = collectTrg;
m_collectPrj = collectPrj;
m_collectFiles = collectFiles;
}

This technique has additional advantages: java compiler detects cases when you

  1. forget to initialize variable, or
  2. try to initialize it more than once.