Jump to content
xisto Community
evought

Basic Recipes For Cvs In Group Projects

Recommended Posts

CVS Basics

 

Some Basic Recipes for Using the Concurrent Versioning System (CVS)

in Group Projects

 

This is a basic How-To for using CVS in group projects. CVS is popular with many projects, especially open source packages hosted on sites like SourceForge. CVS is a very flexible and powerful tool, but its dozens of commands and options can be daunting for the new user. Many references tell you what the commands are for and how they work, but what is often missing is a list of common recipes for getting common tasks done. This guide will give you some simple command combinations for common tasks and some general principles. I try to focus on things the manual does not tell you.

 

This How-To is geared toward the command-line (UNIX, Linux, BSD, or Mac OS X) user. If you are using a special GUI or CVS support built into your editor, this tutorial won't make sense to you. This is also not a manual substitute; use it as a starting point for exploring the manual and learning more powerful features.

 

Getting the Code

 

There are two basic ways to get code from CVS. Which one you use depends on what you want to do with it. The first method, 'cvs checkout' will give you the code with everything you need to commit your changes back to the shared repository.

 

cvs checkout myproject

This checks out a copy of 'myproject'. Specifically, it creates a local 'myproject' directory and puts a copy of the code in that directory. It will spit out a list of the files it is copying as it works. CVS creates a 'sandbox': a safe place where you can play with your own copy of the code without messing up anyone else. Nothing you do affects other developers until you commit changes back to the repository.

 

You need to tell CVS where to get the project from, and this usually involves the '-d' option:

 

cvs -d:ext:ericvought@cvs.sourceforge.net:/cvsroot/crystal checkout

which can get fairly complex. I will not get into that here. Your project documentation or project manager should tell you what you need. After checkout, if you are in your project directory, CVS remembers the location and you do not need it anymore (it is stored in CVS/Root if you want to know). These options can be hard to type everytime you do a checkout, though, and it is easier to put it in an environment variable:

 

export CVSROOT=:ext:ericvought@cvs.sourceforge.net:/cvsroot/crystalcvs checkout myproject

Put the export command in your shell startup script (e.g. .bash_profile). If, like me, you work on more than one project, make a couple of variables:

 

export CVS_CS=:ext:ericvought@cvs.sourceforge.net:/cvsroot/crystalexport CVS_LOCAL=:ext:evought@palantir:/cvsrootexport CVSROOT=$CVS_LOCAL

Then you can select the other project two different ways:

 

cvs -d$CVS_CS checkout cs

---or---

 

export CVSROOT=$CVS_CScvs checkout cs

Another method of getting the code which is not mentioned nearly often enough is by 'cvs export'. This gives you a copy of the code *without* any of the version information and is particularly useful if 1) you just want to look at it, not work with it, 2) you are packaging it for someone else, or 3) you want to pull it in to your own repository as a starting point for your own work.

 

cvs export -D now myproject

Export is faster than checkout and all of the 'CVS' directories cvs normally creates will not be in the way when you are working with the code. '-D now' gets the latest version; check the manual for other ways of specifying the version to fetch.

 

You can use a compression option (-z) with cvs and it is particularly useful when doing checkouts or exports over slow links:

 

cvs -z3 checkout foo

gets foo using a medium-fast compression and will usually use less time and bandwidth for the checkout.

 

What Have I Done?

 

OK, now you have the code. Maybe you've played with it a little. Maybe you have built it and do not know which files came from the repository and which from the compiler. 'cvs status' tells you some useful information about a file:

 

Palantir:~/Projects/cs-tree/cs evought$ cvs status docs/history.txt===================================================================File: history.txt       Status: Up-to-date   Working revision:    1.8979   Repository revision: 1.8979  /cvsroot/crystal/CS/docs/history.txt,v   Sticky Tag:          (none)   Sticky Date:         (none)   Sticky Options:      (none)

This file is up to date. Nothing has been changed, either locally or in the repository.

 

Palantir:~/Projects/cs-tree/cs evought$ cvs status docs/history.txt===================================================================File: history.txt       Status: Locally Modified   Working revision:    1.8979   Repository revision: 1.8979  /cvsroot/crystal/CS/docs/history.txt,v   Sticky Tag:          (none)   Sticky Date:         (none)   Sticky Options:      (none)

Now, status shows that the file is locally modified (changed by me).Next we see a file which has been changed by someone else and my copy is out of date. Note the different version numbers:

 

Palantir:~/Projects/cs-tree/CS evought$ cvs status docs/history.txt===================================================================File: history.txt       Status: Needs Patch   Working revision:    1.8981   Repository revision: 1.8984  /cvsroot/crystal/CS/docs/history.txt,v   Sticky Tag:          (none)   Sticky Date:         (none)   Sticky Options:      (none)

Now, what if I decide that I do not want my changes? I said above that nothing you do affects another developer until you commit changes. You can always abandon your whole checkout and get another copy. Individual changes can be backed out using some esoteric forms of the merge command, but to just undo a single file, the easiest way to do it is hard for some people to get used to: just delete the file. When you do a 'cvs update' the file will come back as good as new. Don't panic. It works.

 

What Has Changed?

 

At some point, you may want to find out what other people have been doing with your project. 'cvs status' is fine for a single file, but if you want to know what might have been changed in a whole directory tree, 'cvs update' is the way.

'update'?!, you ask.Won't that change my sandbox even if I do not want the changes? Yes, but you can tell it not to:

 

cvs -qn update

This is a magic recipe which tells CVS to check what is available without changing anything. The 'q' option tells it to summarize. Otherwise, it will tell you every time it checks a new directory, which, in many projects fills several screens and can obscure the actual changes. The output uses letter codes in front of the file names to tell you their status:

 

A foo.txtM bar.txtU baz.txt? foo.bak

'foo.txt' is locally added; 'bar.txt' has been locally modified; baz.txt has an update in the repository, and 'foo.bak' us unknown. It is locally created and cvs does not know anything about it. If you clean your sandbox first, you will see less of the '?' unknown files (In many projects, this is 'make clean' or 'jam clean'). To find out more about the changes, use 'cvs log' and 'cvs diff'.

 

cvs log -r -N

'cvs log' gives you the history of the file which will let you read the comments. The '-r' option lets you select which changes to view the comments from. With no argument as seen here, it gives the latest check-in, which is usually what you want. '-N' skips tag information which can be lengthy in some projects.

 

cvs diff -c baz.txt

 

'cvs diff' gives you an output of exactly which lines were changed. The '-c' option outputs a context diff which gives you some of the unchanged lines on either side and is likely to be more readable than the 'standard' format.

 

 

Commit Early and Often

 

It is good manners and good practice to commit your changes often. Frequent commits makes it easier to sort out which changes may have broken something, makes for more specific log messages,and protects you work in case of local accident (accidental deletion, drive crash, whatever). Only commit something which works, though, so plan your changes to be in bite-sized, easily understandable chunks. Commit related changes to several files at once to make the log messages more understandable and so that other developers only get the complete set of changes.

 

Update-Before-Commit

 

Before you commit your changes, update your sandbox. This prevents conflicting changes from getting into the repository. The update may break your local code, but you are then in a position to fix it and you still have in mind what you have changed. If the repository version gets broken, someone will need to sort it out down the road and will not have a clue where to start.

 

Do a 'cvs update' to get the latest version, compile, run whatever tests you have, then commit.

 

Do Not Version Control Project Files (MSVC, etc.)

 

As a general rule, never put IDE project files into the repository (for MSVC or CodeWarrior for instance). The project files do not version control well. When two developers each add a file, a conflict occurs and some of the project formats are ugly to change by hand. Even if everyone uses the same IDE, the project files often save your individual preferences and people start fighting over the back-and-forth updates. If different IDEs are used, multiple project files have to be maintained and a nightmare ensues when files are added or removed. It is generally much better to use stand-alone build tools like 'make', 'jam' or 'ant' and let people use whatever editor they wish. You can keep your own IDE project file in a different directory (outside the code) or just use an editor which does not need them.

 

Use Your ~/.cvsrc

 

CVS allows you to create a file in your home directory to specify the common options you use. The file is called '.cvsrc' and contains one command per line. 'cvs' specifies global options and a command name specifies options for that command. For example:

 

cvs -z3 -qupdate -ddiff -c

This saves a good bit of later typing. ('update -d' adds any directories to your sandbox which are new in the repository; normally you have to use 'checkout' to get new subdirectories.)If you want to use a different option for a particular command, say, no compression, specify something different:

 

cvs -z0 checkout foo

Will use no compression. Also, you can use the -f option to ignore what you specified in your .cvsrc file for that command:

 

cvs -f checkout foo

Scripting Makes It Easier

 

CVS is very powerful and flexible; it also is designed to be combined with scripting, and some lightweight scripts can your job faster and easier. Consider:

 

cvs -f -qn update -d |grep -v '^?'

This forces CVS to ignore options in the .cvsrc ('-f', always wise with scripts), quietly ('-q') and without changing anything ('-n') check for updates, including new subdirectories ('-d'), then pipes the output through grep (search utility) and removes ('-v') any line which starts with a question mark ('^?'). This gives you a quick look at what has changed without seeing local build files, editor backups and so forth and without having to clean your local tree and then possibly rebuild. It is a bit much to type each time, but putting it in a shell script or function named 'cvscheck', or instance, can make your job much more pleasant.

 

Conclusion

 

Well, hopefully, you have a few pointers in the right direction. In an active project, you will spend a lot of time using CVS, so it is worth putting in the effort to learn and explore.

 

Changes

 

2 Dec 2009 - Fixed many typos. Fixed cvs export example (missing project directory argument). Made it more clear what the '-f' option does.

Edited by evought (see edit history)

Share this post


Link to post
Share on other sites

LOL!!! If someday I need a CVS tutorial to survive in console, I will use your one.For my job I use RapidSVN, is more "click"-friendly and safe time tool. Good Hard Work!!! Thank You!

Share this post


Link to post
Share on other sites

Create an account or sign in to comment

You need to be a member in order to leave a comment

Create an account

Sign up for a new account in our community. It's easy!

Register a new account

Sign in

Already have an account? Sign in here.

Sign In Now

×
×
  • Create New...

Important Information

Terms of Use | Privacy Policy | Guidelines | We have placed cookies on your device to help make this website better. You can adjust your cookie settings, otherwise we'll assume you're okay to continue.