Commit direct to other repositories [then pull]

James Sleeman mercurial at gogo.co.nz
Sun Feb 21 17:57:45 CST 2010


Situation:
    I'm a web developer, I have a core (trunk) of a framework
    I have clients (branches of trunk), who have sites (branches of client),
    I do development mainly in the site branches and "propagate" the 
changes up and down client & site

I'm presently using Subversion with a structure like this...

  /trunk
  /branches/client/client-1
  /branches/site/site-A

client-1 is branch of trunk
site-A is branch of client-1

I do development in site-A
I commit development (to site-A) in separate commits as defined by
  "what should go to trunk",
  "what should go to client",
  "what should go no further than site"
commit messages prefixed with "Site:" "Client:" or "Trunk:"

I use a modified svnmerge script which essentially
  pulls client & trunk changesets to from site to client
  pulls trunk changesets from client to trunk
  pulls changesets from trunk to client
  pulls changesets from client to site
 
This has been happening for 2 years, it works, but it's cumbersome and 
involves a lot of "noise" in the revision history (a LOT of noise).

I like the way mercurial does lots of things, I would like to move to 
mercurial.

The first inclination as to handle the above is to have clients be a 
clone of trunk, sites be a clone of client. 

But how to stop "site only" changes getting into client and "client 
only" changes getting into trunk while still allowing most/all 
development directly in site and then getting the certain changes 
cleanly "up the line"?  This is important.

Could use "transport", but that's just messy I think, what would happen 
for example if in trunk I transport a change from a site branch and then 
in the site I pull, do we now have 3 commits about the same thing, the 
original in client, the transport  when it went to trunk, and now 
possibly a merge in client again.

So I thought about it, and thought some more, and what I think I want to 
do, is to make a (selective) commit directly into another repository, 
then pull into the current one, and update, that way, assuming client 
only pulls from trunk, and site from client, everything is good and the 
log is really clean (much cleaner than with svn+svnmerge).

In short, I imagine something like....
 
mkdir trunk && cd trunk && hg init
  touch trunk-test
  hg ci -A -m "Trunk: Test"
  cd ../

hg clone trunk client-1 && cd client-1
  touch client-test
  hg ci -A m "Client: Test"
  cd ../

hg clone client-1 site-A && cd site-A
  touch site-test
  hg ci -A m "Site: Test"
 
  echo "More" >trunk-test
  echo "More" >client-test

  ###  UP TO HERE IS JUST LIKE NORMAL ###
  ###  NOW I WANT TO COMMIT A "TRUNK" CHANGE FROM WITHIN SITE ###
 
  hg ci --REPO=../trunk -m "Trunk: Test-2" trunk-test
  hg pull ../trunk && hg merge

  ### AND COMMIT A "CLIENT"  CHANGE ALSO FROM WITHIN SITE ###

  hg ci --REPO=../client -m "Client: Test-2" client-test
  hg pull ../client && hg merge

  ### BACK TO NORMAL! ###

My thinking here, is that my two steps...

  hg ci --REPO=../client -m "Client: Test-2" client-test
  hg pull ../client && hg merge

is something like generating a patch of parts of the working directory 
changes, switching to the working directory of the "parent" repository, 
applying the patch, committing, switching back to the "child" 
repository, pulling and merging from the parent.  With the proviso, that 
the "patch" needs to include also binary files which have been added or 
modified.

Can anybody see a flaw in my thought process.  And is there a plugin 
which does this already?  And if not, does anybody think it would be 
something that could be written as a plugin, or something totally crazy 
and impossible to automate?

---
James Sleeman



More information about the Mercurial mailing list