provides a svn:externals like workflow in an scm agnostic manner
Fetching latest commit…
Cannot retrieve the latest commit at this time.
Failed to load latest commit information.


Externals is a project that allows you to use the workflow normally made
possible by svn:externals in an SCM independent manner.

Please report bugs to

I was inspired to create this project because I had several projects that had
a mix of plugins managed by git and by svn.  Git's submodule feature is
not exactly like svn:externals.  Basically, I don't like how you have to manually
checkout a branch, and I don't like git status not propagating through the
submodules.  Also, the branch tip doesn't automatically move with git-submodule.
Subversion always checks out the branch tip for subprojects when performing a
checkout or update.

Externals is designed such that adding support for a new SCM, or new project
types is easy.

The externals executable is called ext.  Commands come in a long form and a
short form.  The longer form applies the action to the main project.  The short
forms apply the action to all sub projects.

There's a tutorial available at

The commands and usage are as follows (from 'ext help'):

ext [OPTIONS] <command> [repository] [-b <branch>] [path]
      --svn, --subversion  same as '--scm svn' Uses subversion to
                           checkout/export the main project
  -g, --git                same as '--scm git' Uses git to checkout/export the
                           main project
  -t, --type TYPE          The type of project the main project is. For example,
  -s, --scm SCM            The SCM used to manage the main project. For example,
                           '--scm svn'.
  -b, --branch BRANCH      The branch you want the subproject to checkout when
                           doing 'ext install'
  -r, --revision REVISION  The revision you want the subproject to checkout when
                           doing 'ext install'
  -f, --force_removal      When doing an uninstall of a subproject, remove it's
                           files and subfolders, too.
  -w, --workdir DIR        The working directory to execute commands from. Use
                           this if for some reason you cannot execute ext from
                           the main project's directory (or if it's just
                           inconvenient, such as in a script or in a Capistrano
      --help               does the same as 'ext help' If you use this with a
                           command it will ignore the command and run help
      --version            Displays the version number of externals and then
                           exits. Same as 'ext version'

Commands that apply to the main project or the .externals file:
freeze, help, init, install, switch, touch_emptydirs, unfreeze, uninstall, update_ignore, version

freeze          Usage: ext freeze <subproject> [REVISION]
                Locks a subproject into a specific revision/branch.  If no
                revision is supplied, the current revision/branch of the
                project will be used.  You can specify the subproject by name
                or path.

help            It helps.  Hopefully.

init            Creates a .externals file containing only [main]
                It will try to determine the SCM used by the main project,
                as well as the project type.  You don't have to specify
                a project type if you don't want to or if your project type
                isn't supported.  It just means that when using 'install'
                that you'll want to specify the path.

install         Usage: ext install <repository> [-b <branch>] [path]
                Registers <repository> in .externals under the appropriate
                SCM.  Checks out the project, and also adds it to the ignore
                feature offered by the SCM of the main project.  If the SCM
                type is not obvious from the repository URL, use the --scm,
                --git, or --svn flags.

switch          Usage: ext switch <branch_name>
                Changes to the named branch <branch_name> and updates any
                subprojects and applies any changes that have been made to the
                .externals file.

touch_emptydirs Recurses through all directories from the
                top and adds a .emptydir file to any empty directories it
                comes across.  Useful for dealing with SCMs that refuse to
                track empty directories (such as git, for example)

unfreeze        Usage: ext unfreeze <subproject>
                Unfreezes a previously frozen subproject.  You can specify
                the subproject by name or path.

uninstall       Usage: ext uninstall [-f|--force_removal] <project>
                Removes a subproject from being tracked by ext.  If you
                want the files associated with this subproject deleted as well
                (if, for example, you wish to reinstall it from a different
                repository) then you can use the -f option to remove the files.

update_ignore   Adds all paths to subprojects that are
                registered in .externals to the ignore feature of the
                main project.  This is automatically performed by install,
                and so you probably only will run this if you are manually
                maintaining .externals

version         Displays the version number of externals and exits.

Commands that apply to the main project and all subprojects:
checkout, export, status, update

checkout        Usage: ext checkout <repository>
                Checks out <repository>, and checks out any subprojects
                registered in <repository>'s .externals file.

export          Usage: ext export <repository>
                Like checkout except this command fetches as little
                history as possible.

status          Usage: ext status
                Prints out the status of the main project, followed by
                the status of each subproject.

update          Usage: ext update
                Brings the main project, and all subprojects, up to the
                latest version.

Commands that only apply to the subprojects:
co, ex, st, up

co              Like checkout, but skips the main project and
                only checks out subprojects.

ex              Like export, but skips the main project.

st              Like status, but skips the main project.

up              Like update, but skips the main project.

Sometimes it's convenient to have options passed to the underlying scm
executable, like --trust-certid to svn, etc.  This can be done by editing the
.externals file.  You can put scm_opts = <options> under the project you want,
and it will be passed whenever externals calls the executable. You can specify
an option to only be ran when doing co/ex/st/up by adding _co/_ex/_st/_up to
the scm_opts option.


scm = git
scm_opts = --verbose

scm = svn
scm_opts = --trust-certid
scm_opts_co = --non-interactive

This type of a .externals file tells externals to pass
" --non-interactive --trust-certid" to svn when doing a checkout of some_plugin.
"--trust-certid" will be sent to all other calls to svn dealing with
some_plugin.  "--verbose" will be passed to git on all calls dealing with the
main project.

You can pass options globally by setting <scm_name>_opts in the main project.


scm = svn
svn_opts = --trust-certid
svn_opts_co = --non-interactive

scm = svn

This will pass "--non-interactive --trust-certid" to all co calls dealing with
subversion projects, regardless of which project it is.

Subversion does not have a branch feature. Instead, subversion users use the copy
feature to copy directories within the repository (branch), a switch command to switch the
URL that the working directory points at (checkout), and a merge feature to merge
directories (merge).

ext handles branches in Subversion by splitting the URL given by 'svn info' into
a repository part and a branch part.

If you find yourself doing this:

ext checkout svn+ssh://someserver/somepath/repository/branches/new_feature

Then you almost certainly mean to do this:

ext checkout svn+ssh://someserver/somepath/repository -b branches/new_feature

For ext to use branch-related features with Subversion repositories, the repository
must be known.  For subprojects this is never a problem, but for the main project,
it's important that there is a repository field under [.] in the .externals file.
This can be accomplished by using -b with commands like 'ext checkout' and 'ext init'
or by manually editing the .externals file.


Tests are ran with:

rake test

You will need git and svn installed.
If you are using Ruby 1.9 to run the tests, you will need to have the simplecov gem installed.

Copyright Information
The externals project is copyright 2008 by Miles Georgi
and is released under the MIT license.

The license is available in the same directory as this README
file and is named MIT_LICENSE.txt