Hg Init: Part 3. Getting used to working in a team

Original author: Joel Spolsky
  • Transfer
This is the third part of a series Hg Init: Tutorial Mercurial by Joel Spolsky ( by Joel Spolsky ). Previous Parts:


One of the advantages of using Mercurial is the ability to work as a team on one code. Mercurial allows everyone to work independently and helps to integrate the changes made.

Part 3. We get used to working in a team




When working with Mercurial, it is customary to set up a central repository in addition to personal repositories located on the computers of team members. The central repository can be seen as a kind of flea market, that is, as a place where they meet and exchange what they have done.





The easiest way is to create a central repository using the built-in web server in Mercurial. You only need to create a repository using hg initand open access to it using hg serve. By default, the repository will be available on port 8000.



hg serve
launches a web server and makes the current repository available on the Internet.


Since the server is running on joel.example.com , I can simply open joel.example.com:8000 in a browser and see that the server is working, although the repository is completely empty.



With the central web server running, I can clone the central repository from the server to my computer for personal use. The repository is currently empty, which means I will get another empty repository as a result of cloning.



hg clone
makes a full copy of the entire repository.


Now I will create a guac file in which I write down my famous guacamole recipe .



I will add and commit this file to the repository. This will be the first official version:



I will write a comment on the commit:



I will quickly edit the file, making one small change, so that we have at least a little history of changes in the repository.



And commit the changes:



Please note that when I committed this time, I used an argument -mthat I did not do before. This is just to specify a comment on the commit on the command line and not use the editor.

Good, what do we have? Currently, I have a central repository and my personal clone of this repository. I made two changes and committed them, but these changes are stored in my clone. They are not in the central repository yet. So everything looks like this:



And now I will use the command hg pushthat will push my changes from the local to the central repository:

hg push
pushes fresh changes from the current repository to the central one.




Well, great. It’s clear that this will not work. I do not want to think about the security and consequences of starting some kind of web server with permission for everyone to push their stupid changes into it. Bear with me a little bit, I'm going to configure the server so that it allows everyone to do anything. You need to edit the .hg \ hgrc file on the server:



Needless to say, this is not safe. But if you are in a secure LAN at work, and you have a good firewall, and you trust everyone in your network, then this can be done. Otherwise, you should read about security settings.

Well, it's time to restart the server:



Now I should be able to push through the changes:



Aha! Now everything looks like this:



I know what you are thinking. You think, “Lord, Joel, this is all strange. Why do repositories contain changes and not files ? Where is that guac file ? ”

Well, yes, it’s strange. But that is how distributed version control works. Repositories simply store large stacks of changes. Imagine that one change is like a sheet of partially transparent material. If you have a pack of such sheets, and you stack them on top of each other so that the latest change is on top, and then look at this pack from top to bottom, then - yes, yes! - you will see the current version of the file. If you remove the sheets one at a time from the top of the stack, then you will see more and more earlier versions of the file.

We’ll use the browser and look again at the central repository:



There is exactly what was expected.

Now I will call Rose to help me with the recipe. Rosa from the team of testers. Anyone will confirm that it resembles one of those grannies that can be seen in Vegas, sitting for hours with a sagging jaw in front of the "one-armed bandit" and throwing coin after coin into the coveted slot. All the difference is that the Rose program is testing. You can give her a new version of the program, and she will test it on 23 Linux distributions. Check in turn on each. Without showing any emotions, without making unnecessary movements. Stopping only to inform you that the point over i is missing in the Turkish version of Ubuntu Linux. Rose tests great, but I swear she sometimes behaves like a zombie.



Rosa used the team hg cloneto create her own complete copy of the repository.hg clonetakes two arguments: the repository URL and the name of the directory to which you want to clone. Rosa has her own recipes catalog .



Note that when executed, hg logshe sees the whole story. That is, Rosa downloaded the entire repository with a full history of everything that has already happened.

Now Rose will make a change and make it to the repository:



Here, commit. Please note that it can work even if the server is down: the commit is fully executed on her machine.



While Rose was making her changes, I did something too.



After I commit my changes, it will become clear that in my log number two is indicated not the same as that of Rosa.



The stories in our repositories began to differ.



Don’t worry, we will soon see how to bring all these changes together to get a delicious treat with chips and habanero pepper .

Rosa can continue to work without connecting to the server, making as many changes as necessary. She can commit or roll back changes to her repository. However, there will come a time when she decides to share her changes with the rest. She can run the command hg outgoingand see a list of changes awaiting submission to the central repository. These are the changes that will be sent upon execution hg push.



hg outgoing
Displays a list of changes awaiting submission in the current repository.


hg outgoingthis is just a list of all such changes in the current repository that are not in the central repository.

Well, here Rosa pushes her changes to the central repository.



And now it looks like this:



After I went to drink the fourth cup of latte for today, I am also ready to push my change about potato chips.



AAAAA !!! Error! Oh, by the way, see the message? The one that says use the -f switch to force push (use push -f to force)? This is terrible advice. Never use the -f switch for anything . You will regret using it. Just believe me at the moment.

The reason Rosa managed to push through the changes, and I don’t, is because the potato chips and guacamole do not mix well. Just kidding! I just wanted to make sure you hadn't fallen asleep there yet.

The team ended in error because each of us made changes, which means that they need to be merged together, and Mercurial knows about it.

First of all, I will take all the changes from the central repository that I don’t have yet to merge.



There’s some gibberish about +1 head (+1 heads). This is because my repository, in which three changes were neatly laid out, has become a two-headed monster. At the top of the repository, two different changes are dangerously located. Here's what it looks like:



I now have both versions in my repository. Here is mine:



And here is the version of Rosa:



And I have to merge these versions together. Fortunately, it's simple:



Look! The team hg mergetook and combined both of my “heads” (changes at the top of the repository) into one. Since in this case, Rosa and I changed different parts of the file, there were no conflicts during the merger and everything went without a hitch.

hg merge
produces a merger (association) of two "goals".


I still need to commit. It is important. If the merger failed, then I could always roll back and try again. But, since the merger was successful, I will commit. After that, I can push my changes to the central repository.



Now the central repository is the same as mine:



Okay, I have Rosa changes and my own changes, but Rosa does not have my changes yet.

There is one more point connected with Rosa about which I forgot to tell. She is a doctor. Yeah, the doctor who is the doctor. Well, isn't it wonderful? She was the chief pediatrician at Mt. Sinaiand probably received "five times more than this filthy stupid pays its testers." No one knows for sure why she left the medicine. The rest of the testers think that something tragic happened. She also had a family: on her table is a picture of a cute preteen. But now she lives alone, and we do not want to get into her soul.

Rose needs to pull fresh incoming changes from the repository to get my changes.



Done. Now, - it may seem strange to you, - despite the fact that Rose pulled new changes into her repository, these changes are not in her working directory .



See, She still works with corn chips . With corn chips!

She hasmy latest changes are somewhere in the repository ...



It's just that my changes are not in its working directory. This is because she is still modifying the second set of changes. This can be seen by running the command hg parent:



hg parent
displays a set of changes located in the working directory.


Mercurial is kind to us. Pulling changes is always safe. All that happens is getting fresh changes made by other people. We can start working with these changes later at our convenience.

Remember that a command hg upwith no arguments will bring the working directory to the “tip”, that is, it will apply all changes to the very top set of changes. In this case, this is the fourth set of changes:



Now Rose sees the latest version with changes from both of us.

When you work in a team, the workflow will look much like this:
  1. Pick up the latest version that everyone works with if you haven’t done this for a long time by doing:
    • hg pull
    • hg up

  2. Make changes
  3. Commit Changes (Locally)
  4. Repeat steps 2-3 until you have a good code that you want to dump on everyone else
  5. When you are ready to share, do:
    • hg pull to get other people's changes (if any)
    • hg merge to merge these changes with your
    • testing! in order to make sure that nothing is spoiled during the merger
    • hg commit (to commit the merge result)
    • hg push



check yourself


Here is all that you should be able to do at the moment:
  1. Set up a central repository and give team members the opportunity to make clones of it
  2. Push changes to the central repository
  3. Pull changes from the central repository
  4. Merge changes from different authors


Continued here:
Hg Init: Part 4. Bug Fixes

Also popular now: