info-cvs
[Top][All Lists]
Advanced

[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index]

Re: FW: can I checkout up to three branches into one workspace?


From: Pierre Asselin
Subject: Re: FW: can I checkout up to three branches into one workspace?
Date: Sat, 22 Jan 2005 03:16:43 +0000 (UTC)
User-agent: tin/1.6.1-20030810 ("Mingulay") (UNIX) (NetBSD/2.0 (i386))

Mark Hanna <address@hidden> wrote:
>  Pierre,

> We don't ship src, but are currently in the situation where we have
> numerous branches all with customer specific areas which are pulled into
> the build.  The maintenance of these branches with fixes having to be
> merged between several branches has become time consuming for our small
> development team, so I've been tasked along with the chief architect to
> come up with a sensible solution which can quickly improve things before
> a new batch of customers comes on line.

I'll tell you how I would do it, but *it does not scale well*.  I'd say
it's O(N) in the number of customers and I don't think that's good.
Now if you already use a branching scheme that's O(N^2) I suppose that's
an improvement, but still...

> One alternative I'm looking at is a method of checking out the build
> combination (stable point + patches +customer files) into different
> directories and using ant to script the compilation. Do think this is
> reasonably easy to achieve or would you suggest something better ?

See, thats what I don't understand.  ant is like make for Java,
right ?  Why can't the ant script be parametrized by customer and
take appropriate actions using the appropriate parts of the source
tree ?  *That* scales well.  Anyway.

Avoid long-running branches.  Get a trunk with generic features
only.  At some point, tag the trunk and create a branch for each
customer.

    cvs tag base_1
    cvs tag -b customerA-1
    cvs tag -b customerB-1
    ...

Go on each branch and put the custom feature for the customer.

    cvs checkout -r customerA-1 the_project && cd the_project
    <make custom changes for customer A>
    cvs commit
    cd .. && cvs release -d the_project
    # repeat for the other customers

Your revision tree now looks like a linear trunk with N little
stubs at the basepoint.

    ----------------*------> generic only
                   /|\ 
                  / | \ 
                 /  |  \ 
                A   B   C 

Now the release process looks like this:
    1)  Tag the trunk.
    2)  Start a release/bugfix branch.
    3)  Stabilize the release branch.
    4)  Tag the release branch when ready to release.
So far this is standard CVS fare but it handles only
the generic code with zero customizations.

    (on a trunk sandbox)
    cvs tag product_release1_bp
    cvs tag -b product_release1
    cvs update -r product_release1
    (stabilization begins)
    cvs commit
    cvs tag product_release1_0

Now the O(N) customization process begins.  For each
customer,

    4i) Create a branch off the release point.
    5i) Merge the little stub to the new branch.e

    cvs checkout -r product_release1 the_project && cd the_project
    cvs tag -b product_release1_0_customerA
    cvs update -r product_release1_0_customerA
    cvs update -j base_1 -j customerA

Conflicts ?  Deal with them.  You have to expect conflicts
and you have to fix them by hand, therefore this process
*can not be automated*.

When the conflicts are fixed, you are not done.  You just made
nontrivial changes to a sandbox and you need to test the custom
functionality.  You also need to test the generic functionality in
case it got wrecked by the customizations.

WHEN all testing is complete, you can cut a custom release off the
branched release branch.  After a while your revision tree looks
like this:


    -----------*-----------X------------------------>trunk
              /|\           \
             / | \           \
            /  |  \           \
           A   B   C           ----*-------------*-->release
                                  /|\           /|\
                                 / | \         / | \
                                /  |  \       /  |  \
                               A   B   C     A   B   C


So you keep SHORT branchlets with customizations and ONLY
customizations.  You re-graft those branchlets up the release
branches by the techniques shown above and you test.

Eventually the original branchlets become too rusty to keep up with
the trunk and you get too many conflicts at release time.  When
that happens just stop using the originals and declare that the
branchlets of the last successful release are now the references
for customer-specific changes.

That's my process and I think it sucks.  It's ok with three customers,
but what if your company grows to 20 ? 100 ? 1000 ?  I would MUCH
rather have a unified project tree with customer-specific features
segregated to subdirectories, say.  I would create the customized
releases *at build time* with parametrized scripts.  I would also
maintain a unified test rig to keep all the variants under control
between releases.  I understand that Java tools like to impose
a directory layout that may interfere with what I say, but there
must be a way.

The ONLY good thing I have to say about my branchlet scheme is that
it is harder to leak intellectual property between customers that
way because the trunk and release branches are completely generic.
But really, my customer would have to make a big stink about their
IP for this to carry any weight with me, and then I would explain
to them that the extra IP security costs serious money.  Because
it does.

-- 
pa at panix dot com


reply via email to

[Prev in Thread] Current Thread [Next in Thread]