Mercurial: Difference between revisions

From Wiki
Jump to navigation Jump to search
No edit summary
Line 6: Line 6:
hg log          # to see logs of all versions
hg log          # to see logs of all versions
hg update -r 33  # to revert to version 33
hg update -r 33  # to revert to version 33
hg update -r 38  # to revert back to version 38
</pre>
</pre>



Revision as of 23:18, 23 February 2015

Cheat Sheet

You are currently on version 38 but want to revert to version 33:

hg log           # to see logs of all versions
hg update -r 33  # to revert to version 33
hg update -r 38  # to revert back to version 38

Client

http://hginit.com/

The command for Mercurial is hg.

Create a repository

Suppose you want to set up version control for the my_code directory.

cd my_code
hg init    # creates .hg directory
hg add     # adds everything from the current directory
hg commit  # has you enter a text description, then creates a first snapshot of the directory

Ignoring files

Manually create a file called .hgignore at the top level of your repository and add patterns that mercurial should ignore:

# use glob syntax.
syntax: glob
log/*  # ignore these directories in rails
tmp/*
*~     # ignore emacs backup files
*.bak  # ignore other backup files

Commit, Revert, Backout, Tag, Log

hg commit                  # has you enter a text description in a text editor, then creates a snapshot of the directory
hg commit -m "my comment"  # commit with this comment
hg revert --all            # reverts everything back to the last commit
hg rollback                # rolls back to the commit before last
hg backout -r 2            # undo just changeset number 2 
hg tag Version-1.0         # add a tag to the current changeset
hg log                     # shows a list of all commits
hg log -v -r 2             # show all notes (and changed files) of changeset number 2

Status, Diff, Remove, Add

> cp a.txt b.txt
> emacs a.txt
> rm favicon.ico
> hg status
M a.txt                   # Modified
? b.txt                   # "?" means mercurial doesn't know anything about this file yet
! favicon.ico             # "!" means missing
>
> hg diff a.txt           # show differences between last snapshot and current version
> hg add                  # add all new files to repository
> hg remove favicon.ico   # really remove this file
> hg status
M a.txt
A b.txt                   # Added
R favicon.ico             # Removed

You need to clear up all the ?s and !s in order to commit.

Cat, Diff, Update

hg cat a.txt            # print current version of a.txt
hg cat -r 0 a.txt       # print version 0 of a.txt
hg diff -r 0:1 a.txt    # show differences between versions 0 and 1 of a.txt
hg update -r 0          # revert to version 0 of the repository
hg update               # revert to the latest version of the repository

Working with a server

hg clone http://my_server:8000/ my_copy_of_the_code  # name the directory as you like
... commit some changes ...
hg push                               # upload latest committed version to the server
... commit more changes ...
hg outgoing            # show differences between my current version and the server's

Push will fail if conflicting changes have been uploaded to the server in the meantime. If this happens, you need to merge the updates into your version:

hg incoming           # show differences between my current version and the server's
hg pull               # pull down more recent changes from the server
hg merge              # merge my version with the latest changes from the server
hg commit -m "merge"  # commit the merge
hg push               # upload

Pull does not automatically update the files in your directory to the latest version, it just downloads the latest changes. Use parent to see what version number you're currently working with:

hg parent             # show the changeset that’s in the working directory
hg heads              # show any changesets that are at the head of the repository

Workflow:

  1. If you haven’t done so in a while, get the latest version that everyone else is working off of:
    • hg pull
    • hg up
  2. Make some changes
  3. Commit them (locally)
  4. Repeat steps 2-3 until you’ve got some nice code that you’re willing to inflict on everyone else
  5. When you’re ready to share:
    • hg pull to get everyone else’s changes (if there are any)
    • hg merge to merge them into yours
    • test! to make sure the merge didn’t screw anything up
    • hg commit (the merge)
    • hg push

Experimenting

hg clone my_code my_code_experiment    # make a hard-linked duplicate directory
hg push                                # push experimental changes back into original directory

Stable and dev repositories

Clone my_code-stable to my_code-dev. Fix bugs in the stable repository, and add features in the dev repository. Regularly pull down bug fixes from stable to dev and merge them to stay current. When the new features are ready, push them back to stable.

Troubleshooting: first commit

When you first create your repository, add everything to it, and then try to commit, you get this error:

> hg commit -m "first commit"
error:  abort: no username supplied (see "hg help config") 

You must create a .hgrc file in your home directory and add something like this to it:

[ui]
username = Your Name <your@mail>

Troubleshooting: push and pull

$ hg pull
abort: repository default not found!
$ hg push
pushing to default-push
abort: repository default-push not found!

You have to specify the server/repository manually:

hg pull ssh://hg@my_server/my_code
hg push ssh://hg@my_server/my_code

To avoid this in the future, edit .hg/hgrc like this:

[paths]
default = ssh://hg@my_server/my_code

Server

Quick and dirty web server

mkdir my_code
cd my_code
hg init
hg serve   # now accessible from http://my_server:8000/

SSH-based Server

http://dev.lshift.net/paul/mercurial-server/docbook.html

Creating accounts

Assume that dev@mybox is the developer's account on his local machine, and luser@myserver is an account on the server where mercurial is running.

dev@mybox:~$ ssh-keygen -t ecdsa -b 521   # add a passphrase
  • send a copy of the public key to luser@myserver
  • as root@myserver, copy the public key to a file named /etc/mercurial-server/keys/root/dev/mybox and run this command:
root@myserver:# sudo -u hg /usr/share/mercurial-server/refresh-auth

NOTE: this creates a root user with the authority to create and delete repositories. To set up a regular user who can only check code in and out, change root to users in the public key path above.

Uploading a repository to the server

To upload the myproj folder as a repository

cd myproj
hg init; hg add; hg commit
hg clone . ssh://hg@myserver/my/project
hg pull ssh://hg@myserver/my/project