[svn.haxx.se] · SVN Dev · SVN Users · SVN Org · TSVN Dev · TSVN Users · Subclipse Dev · Subclipse Users · this month's index

[PROPOSAL] Managing large working copies using viewspecs

From: David James <djames_at_collab.net>
Date: 2006-07-16 10:10:46 CEST

It's often true that users want to checkout some, but not all, of a
large repository. Currently, it's easy to checkout a single subdirectory
using Subversion. However, if you want to checkout a group of
subdirectories, and manage this group as a single working copy, you're
going to run into some major challenges.

In the past year, we've seen two proposals for managing large working
copies. Last year, Ben Reser proposed creating two new subcommands,
called 'svn include' and 'svn exclude', which allow you to configure
which directories are pulled in by 'svn update' [1]. This year, Eric
Gilespie proposed to instead add a depth parameter to the 'update'
command [2].

Both Ben and Eric's proposals suffer from a similar problem: they don't
actually make it easy to checkout a group of subdirectories. With either
proposal, you're forced to execute a long series of commands (or a long
series of options) in order to check out a group of subdirectories as a
single working copy.

I'd like to propose we add full-fledged viewspecs to Subversion. Here's
how such a feature might work:

   To checkout a working copy from the server, which only includes the
   specified files:
     svn checkout --viewspec my-view.txt svn://server/trunk

   Edit the current viewspec (in your favourite editor):
     svn viewspec

   Save the current viewspec to a file:
     svn viewspec > my-view.txt

   Load a viewspec from a file:
     svn viewspec < my-view.txt

   Add the 'contrib' directory to the viewspec:
     svn viewspec --add contrib -R

   Remove contrib/client-side/svnmerge.py from the viewspec:
     svn viewspec --remove contrib/client-side/svnmerge.py


 1. +foo/... --> Checkout 'foo', and all subdirectories.
 2. +foo/* --> Checkout the immediate children of 'foo'. Don't
                  download subdirectories.
 3. -foo/... --> Don't download anything inside 'foo'
 4. -foo/* --> Don't download the immediate children of 'foo'.
 5. +bar --> Download the file 'bar'. (If 'bar' is a directory,
                  an error will be reported.)
 6. -bar --> Don't download the file 'bar'. (If 'bar' is a
                  directory, an error will be reported.)


Let's say you're just an average Subversion user. You used Subversion
to checkout 'http://svn.collab.net/repos/svn/trunk', and you type
'svn viewspec', because you're curious how the command works.

When you type svn viewspec, a template shows up in your editor, with
a few lines of helpful comments, which explain briefly how viewspecs
work, and point to documentation. Underneath, you see a single line,
which indicates that every file in the current directory is included.


Following the instructions, you decide to exclude the 'contrib',
'tools', and 'www' directories. You do so by adding the following lines.


You press enter, and voila! The contrib, tools, and www directories

Later on, you decide to switch over to work on the 1.3.x branch. You
   svn switch http://svn.collab.net/repos/svn/branches/1.3.x

When you switch branches, your viewspec is maintained, and the
'contrib', 'tools', and 'www' directories are still not pulled

Later on, you decide to checkout the same viewspec on a different
machine. To transfer your viewspec, you type:
    svn viewspec > my-view.txt
    scp my-view.txt some-other-machine:~

On the other machine, you type:
    svn checkout --viewspec my-view.txt \

After typing that command, you're presented with exactly the same
view of the repository.

EXAMPLE #1: Download only foo/images and bar/images


EXAMPLE #2: Download everything but foo/videos and bar/videos


EXAMPLE #3: Download files in the root directory, as well as files
            in the 'subversion' and 'build' directories. Don't
            download anything else.


EXAMPLE #4: Download everything except the 'contrib', 'doc', 'notes',
            'tools', and 'www' directories.



  Deeply nested view specs (with more directories specified) take
  precedence over shallowly nested view specs, and "*" takes
  precedence over "...".

  Therefore, the following viewspec checks out everything except
  the files directly in the root directory.



In some cases, users will want to reorganize their tree to have a
different structure from the one in the repository. Currently,
users can reorganize their trees using switch. I'd like to allow
users to also be able to save and restore this kind of reorganization
using a viewspec.

If you'd like to switch a directory in a viewspec, simply list
the directory you'd like to download right after the directory
in your WC. For example, if you wanted to download
'foo/images/...' and 'bar/images/...' into the directories 'foo'
and 'bar' in your WC, you could do so using the following

   +foo/... foo/images/...
   +bar/... bar/images/...

If you've already run 'svn switch' on a directory in your
working copy, this switch will show up in the viewspec.
If you checkout a brand new working copy using the same
viewspec, the same switches will be performed.


To bring up the viewspec in an editor, simply type svn viewspec. Your
current viewspec will be displayed in your favourite editor.

If you've just performed a regular checkout, your viewspec will show up
as simply "+...". If you've performed a nonrecursive checkout, your
viewspec will show up as "+*".

If you've performed switches on your WC, these operations will also
show up in your viewspec.

Viewspecs are always displayed and parsed relative to the specified
directory. If your viewspec states '+foo/images/...' for the root
directory, the viewspec for 'foo' will be 'images/...', and the
viewspec for 'foo/images' will be '...'. Everything is relative.


It's not always convenient to edit viewspecs as a text file. If you
just want to add or remove a file or directory from the viewspec,
you can simply type:

   svn viewspec --add foo.txt
   svn viewspec --remove bar.txt baz.txt

To add or remove directories, you must either specify the '-N' or
'-R' options, so as to clarify whether you want to recursively
add or remove descendents of these directories. If you do not specify
either of these options, directory targets will be skipped, and a
warning message will be printed.


It's tempting to type svn viewspec --remove * to remove all the files
from the current directory. Note, however, that this a command is
expanded by your shell, so this will only remove files which are
currently in the directory. If you wish to prevent new files from
being added, you must enclose the asterik in single quotes so that it
will not be expanded by your shell.


If you run 'svn up' on a working copy with a viewspec, 'svn up'
honours the viewspec. There are no exceptions to this rule.
'svn up' should not and will not grab files which are not in your

If you want to add or remove a file from your viewspec, use the
viewspec command.


This proposal can be implemented in libsvn_wc using the following

   a) The .svn/entries file should have entries for all directories and
      files, regardless of whether the checkout is recursive or not.

   b) We add a new "recurse-mode" field in .svn/entries.

      The following modes are supported for files:

        "+": This file is included; it should be updated.
        "-": This file is excluded; it should not be updated.

      The following modes are supported for directories:

        "+...": All children of this directory are included
                by default.

        "-...": All children of this directory are excluded
                by default.

        "+*": Immediate children of this directory are included
                by default. Subdirectories are included by default.

        "-*": Immediate children of this directory are included
                by default. Subdirectories are excluded by default.


When traversing the working copy, 'svn' will still need to recurse into
subdirectories which are marked "-...". This marker simply indicates
that child entries are excluded by default. If the directory exists
in your working copy, and a nested file or directory is marked as
included, the most deeply nested marker takes priority.


[1]: Ben Reser's proposal

[2]: Eric Gillespie's proposal

To unsubscribe, e-mail: dev-unsubscribe@subversion.tigris.org
For additional commands, e-mail: dev-help@subversion.tigris.org
Received on Sun Jul 16 10:11:18 2006

This is an archived mail posted to the Subversion Dev mailing list.

This site is subject to the Apache Privacy Policy and the Apache Public Forum Archive Policy.