From ffc93497ad16ea54faffd7ba76e5ce2c9186d714 Mon Sep 17 00:00:00 2001 From: Jelmer Vernooij Date: Tue, 28 Feb 2012 17:00:49 +0100 Subject: Remove the various exporters. --- NEWS | 8 + __init__.py | 7 - cmds.py | 225 ----------- exporters/Makefile | 15 - exporters/__init__.py | 326 --------------- exporters/darcs/.gitignore | 3 - exporters/darcs/Makefile | 55 --- exporters/darcs/NEWS | 26 -- exporters/darcs/README | 187 --------- exporters/darcs/TODO | 8 - exporters/darcs/asciidoc.conf | 21 - exporters/darcs/d2x | 112 ------ exporters/darcs/d2x.txt | 27 -- exporters/darcs/darcs-fast-export | 380 ------------------ exporters/darcs/darcs-fast-export.txt | 68 ---- exporters/darcs/darcs-fast-import | 375 ----------------- exporters/darcs/darcs-fast-import.txt | 57 --- exporters/darcs/git-darcs | 279 ------------- exporters/darcs/git-darcs.txt | 92 ----- exporters/darcs/t/Makefile | 9 - exporters/darcs/t/bench-results/Makefile | 5 - exporters/darcs/t/bench-results/bench-results.gnu | 6 - exporters/darcs/t/bench-results/bench-results.py | 23 -- exporters/darcs/t/bench-tailor.sh | 59 --- exporters/darcs/t/bench.sh | 38 -- exporters/darcs/t/data/hungarian.gif | Bin 90 -> 0 bytes exporters/darcs/t/lib-httpd.sh | 67 ---- exporters/darcs/t/lib.sh | 337 ---------------- exporters/darcs/t/test-bzr.sh | 16 - exporters/darcs/t/test-git-d2x.sh | 19 - exporters/darcs/t/test-git-incremental.sh | 24 -- exporters/darcs/t/test-git-progress.sh | 18 - exporters/darcs/t/test-git.sh | 18 - exporters/darcs/t/test-hg-d2x.sh | 12 - exporters/darcs/t/test-hg.sh | 16 - exporters/darcs/t/test2-bzr-d2x.sh | 19 - exporters/darcs/t/test2-bzr-incremental.sh | 21 - exporters/darcs/t/test2-git-funny-tagname.sh | 25 -- exporters/darcs/t/test2-git-http.sh | 22 - .../darcs/t/test2-git-incremental-specworkdir.sh | 22 - exporters/darcs/t/test2-git-incremental.sh | 21 - exporters/darcs/t/test2-git.sh | 18 - exporters/darcs/t/testimport-bzr-x2d.sh | 15 - exporters/darcs/t/testimport-bzr.sh | 15 - exporters/darcs/t/testimport-copy.sh | 26 -- exporters/darcs/t/testimport-darcs.sh | 17 - exporters/darcs/t/testimport-deleteall.sh | 31 -- exporters/darcs/t/testimport-git-incremental.sh | 16 - exporters/darcs/t/testimport-git-twoway-gd.sh | 34 -- exporters/darcs/t/testimport-git-twoway.sh | 30 -- exporters/darcs/t/testimport-git-x2d.sh | 15 - exporters/darcs/t/testimport-git.sh | 15 - exporters/darcs/t/testimport-gitsymlink.sh | 45 --- exporters/darcs/t/testimport-hg-x2d.sh | 15 - exporters/darcs/t/testimport-hg.sh | 15 - exporters/darcs/t/testimport-rename.sh | 25 -- exporters/darcs/x2d | 125 ------ exporters/darcs/x2d.txt | 28 -- exporters/hg-fast-export.README | 54 --- exporters/hg-fast-export.py | 442 --------------------- exporters/hg-fast-export.sh | 100 ----- exporters/hg2git.py | 112 ------ exporters/svn-archive.c | 240 ----------- exporters/svn-fast-export.README | 12 - exporters/svn-fast-export.c | 187 --------- exporters/svn-fast-export.py | 225 ----------- setup.py | 1 - 67 files changed, 8 insertions(+), 4918 deletions(-) delete mode 100644 exporters/Makefile delete mode 100644 exporters/__init__.py delete mode 100644 exporters/darcs/.gitignore delete mode 100644 exporters/darcs/Makefile delete mode 100644 exporters/darcs/NEWS delete mode 100644 exporters/darcs/README delete mode 100644 exporters/darcs/TODO delete mode 100644 exporters/darcs/asciidoc.conf delete mode 100755 exporters/darcs/d2x delete mode 100644 exporters/darcs/d2x.txt delete mode 100755 exporters/darcs/darcs-fast-export delete mode 100644 exporters/darcs/darcs-fast-export.txt delete mode 100755 exporters/darcs/darcs-fast-import delete mode 100644 exporters/darcs/darcs-fast-import.txt delete mode 100755 exporters/darcs/git-darcs delete mode 100644 exporters/darcs/git-darcs.txt delete mode 100644 exporters/darcs/t/Makefile delete mode 100644 exporters/darcs/t/bench-results/Makefile delete mode 100644 exporters/darcs/t/bench-results/bench-results.gnu delete mode 100644 exporters/darcs/t/bench-results/bench-results.py delete mode 100644 exporters/darcs/t/bench-tailor.sh delete mode 100644 exporters/darcs/t/bench.sh delete mode 100644 exporters/darcs/t/data/hungarian.gif delete mode 100644 exporters/darcs/t/lib-httpd.sh delete mode 100644 exporters/darcs/t/lib.sh delete mode 100644 exporters/darcs/t/test-bzr.sh delete mode 100644 exporters/darcs/t/test-git-d2x.sh delete mode 100644 exporters/darcs/t/test-git-incremental.sh delete mode 100644 exporters/darcs/t/test-git-progress.sh delete mode 100644 exporters/darcs/t/test-git.sh delete mode 100644 exporters/darcs/t/test-hg-d2x.sh delete mode 100644 exporters/darcs/t/test-hg.sh delete mode 100644 exporters/darcs/t/test2-bzr-d2x.sh delete mode 100644 exporters/darcs/t/test2-bzr-incremental.sh delete mode 100644 exporters/darcs/t/test2-git-funny-tagname.sh delete mode 100644 exporters/darcs/t/test2-git-http.sh delete mode 100644 exporters/darcs/t/test2-git-incremental-specworkdir.sh delete mode 100644 exporters/darcs/t/test2-git-incremental.sh delete mode 100644 exporters/darcs/t/test2-git.sh delete mode 100644 exporters/darcs/t/testimport-bzr-x2d.sh delete mode 100644 exporters/darcs/t/testimport-bzr.sh delete mode 100644 exporters/darcs/t/testimport-copy.sh delete mode 100644 exporters/darcs/t/testimport-darcs.sh delete mode 100644 exporters/darcs/t/testimport-deleteall.sh delete mode 100644 exporters/darcs/t/testimport-git-incremental.sh delete mode 100644 exporters/darcs/t/testimport-git-twoway-gd.sh delete mode 100644 exporters/darcs/t/testimport-git-twoway.sh delete mode 100644 exporters/darcs/t/testimport-git-x2d.sh delete mode 100644 exporters/darcs/t/testimport-git.sh delete mode 100644 exporters/darcs/t/testimport-gitsymlink.sh delete mode 100644 exporters/darcs/t/testimport-hg-x2d.sh delete mode 100644 exporters/darcs/t/testimport-hg.sh delete mode 100644 exporters/darcs/t/testimport-rename.sh delete mode 100755 exporters/darcs/x2d delete mode 100644 exporters/darcs/x2d.txt delete mode 100644 exporters/hg-fast-export.README delete mode 100755 exporters/hg-fast-export.py delete mode 100755 exporters/hg-fast-export.sh delete mode 100755 exporters/hg2git.py delete mode 100644 exporters/svn-archive.c delete mode 100644 exporters/svn-fast-export.README delete mode 100644 exporters/svn-fast-export.c delete mode 100755 exporters/svn-fast-export.py diff --git a/NEWS b/NEWS index 582762b..08a5fbc 100644 --- a/NEWS +++ b/NEWS @@ -6,6 +6,14 @@ bzr-fastimport Release Notes 0.13 UNRELEASED +Changes +------- + +* bzr-fastimport no longer ships exporters for various other version + control systems. The versions of these exporters shipped with bzr-fastimport + have been outdated for some time. Better and more recent exporters + are widely available. + Compatibility ------------- diff --git a/__init__.py b/__init__.py index c79f5be..6821602 100644 --- a/__init__.py +++ b/__init__.py @@ -108,12 +108,5 @@ for name in [ "fast_import_info", "fast_import_query", "fast_export", - "fast_export_from_cvs", - "fast_export_from_darcs", - "fast_export_from_hg", - "fast_export_from_git", - "fast_export_from_mtn", - "fast_export_from_p4", - "fast_export_from_svn" ]: plugin_cmds.register_lazy("cmd_%s" % name, [], "bzrlib.plugins.fastimport.cmds") diff --git a/cmds.py b/cmds.py index d90393a..424a7ff 100644 --- a/cmds.py +++ b/cmds.py @@ -682,228 +682,3 @@ class cmd_fast_export(Command): revision=revision, verbose=verbose, plain_format=plain, rewrite_tags=rewrite_tag_names, baseline=baseline) return exporter.run() - - -class cmd_fast_export_from_cvs(Command): - """Generate a fast-import file from a CVS repository. - - Destination is a dump file, typically named xxx.fi where xxx is - the name of the project. If '-' is given, standard output is used. - - cvs2svn 2.3 or later must be installed as its cvs2bzr script is used - under the covers to do the export. - - The source must be the path on your filesystem to the part of the - repository you wish to convert. i.e. either that path or a parent - directory must contain a CVSROOT subdirectory. The path may point to - either the top of a repository or to a path within it. In the latter - case, only that project within the repository will be converted. - - .. note:: - Remote access to the repository is not sufficient - the path - must point into a copy of the repository itself. See - http://cvs2svn.tigris.org/faq.html#repoaccess for instructions - on how to clone a remote CVS repository locally. - - By default, the trunk, branches and tags are all exported. If you - only want the trunk, use the `--trunk-only` option. - - By default, filenames, log messages and author names are expected - to be encoded in ascii. Use the `--encoding` option to specify an - alternative. If multiple encodings are used, specify the option - multiple times. For a list of valid encoding names, see - http://docs.python.org/lib/standard-encodings.html. - - Windows users need to install GNU sort and use the `--sort` - option to specify its location. GNU sort can be downloaded from - http://unxutils.sourceforge.net/. - """ - hidden = False - _see_also = ['fast-import', 'fast-import-filter'] - takes_args = ['source', 'destination'] - takes_options = ['verbose', - Option('trunk-only', - help="Export just the trunk, ignoring tags and branches." - ), - ListOption('encoding', type=str, argname='CODEC', - help="Encoding used for filenames, commit messages " - "and author names if not ascii." - ), - Option('sort', type=str, argname='PATH', - help="GNU sort program location if not on the path." - ), - ] - encoding_type = 'exact' - def run(self, source, destination, verbose=False, trunk_only=False, - encoding=None, sort=None): - load_fastimport() - from bzrlib.plugins.fastimport.exporters import fast_export_from - custom = [] - if trunk_only: - custom.append("--trunk-only") - if encoding: - for enc in encoding: - custom.extend(['--encoding', enc]) - if sort: - custom.extend(['--sort', sort]) - fast_export_from(source, destination, 'cvs', verbose, custom) - - -class cmd_fast_export_from_darcs(Command): - """Generate a fast-import file from a Darcs repository. - - Destination is a dump file, typically named xxx.fi where xxx is - the name of the project. If '-' is given, standard output is used. - - Darcs 2.2 or later must be installed as various subcommands are - used to access the source repository. The source may be a network - URL but using a local URL is recommended for performance reasons. - """ - hidden = False - _see_also = ['fast-import', 'fast-import-filter'] - takes_args = ['source', 'destination'] - takes_options = ['verbose', - Option('encoding', type=str, argname='CODEC', - help="Encoding used for commit messages if not utf-8." - ), - ] - encoding_type = 'exact' - def run(self, source, destination, verbose=False, encoding=None): - from bzrlib.plugins.fastimport.exporters import fast_export_from - custom = None - if encoding is not None: - custom = ['--encoding', encoding] - fast_export_from(source, destination, 'darcs', verbose, custom) - - -class cmd_fast_export_from_hg(Command): - """Generate a fast-import file from a Mercurial repository. - - Destination is a dump file, typically named xxx.fi where xxx is - the name of the project. If '-' is given, standard output is used. - - Mercurial 1.2 or later must be installed as its libraries are used - to access the source repository. Given the APIs currently used, - the source repository must be a local file, not a network URL. - """ - hidden = False - _see_also = ['fast-import', 'fast-import-filter'] - takes_args = ['source', 'destination'] - takes_options = ['verbose'] - encoding_type = 'exact' - def run(self, source, destination, verbose=False): - load_fastimport() - from bzrlib.plugins.fastimport.exporters import fast_export_from - fast_export_from(source, destination, 'hg', verbose) - - -class cmd_fast_export_from_git(Command): - """Generate a fast-import file from a Git repository. - - Destination is a dump file, typically named xxx.fi where xxx is - the name of the project. If '-' is given, standard output is used. - - Git 1.6 or later must be installed as the git fast-export - subcommand is used under the covers to generate the stream. - The source must be a local directory. - - .. note:: - - Earlier versions of Git may also work fine but are - likely to receive less active support if problems arise. - """ - hidden = False - _see_also = ['fast-import', 'fast-import-filter'] - takes_args = ['source', 'destination'] - takes_options = ['verbose'] - encoding_type = 'exact' - def run(self, source, destination, verbose=False): - load_fastimport() - from bzrlib.plugins.fastimport.exporters import fast_export_from - fast_export_from(source, destination, 'git', verbose) - - -class cmd_fast_export_from_mtn(Command): - """Generate a fast-import file from a Monotone repository. - - Destination is a dump file, typically named xxx.fi where xxx is - the name of the project. If '-' is given, standard output is used. - - Monotone 0.43 or later must be installed as the mtn git_export - subcommand is used under the covers to generate the stream. - The source must be a local directory. - """ - hidden = False - _see_also = ['fast-import', 'fast-import-filter'] - takes_args = ['source', 'destination'] - takes_options = ['verbose'] - encoding_type = 'exact' - def run(self, source, destination, verbose=False): - load_fastimport() - from bzrlib.plugins.fastimport.exporters import fast_export_from - fast_export_from(source, destination, 'mtn', verbose) - - -class cmd_fast_export_from_p4(Command): - """Generate a fast-import file from a Perforce repository. - - Source is a Perforce depot path, e.g., //depot/project - - Destination is a dump file, typically named xxx.fi where xxx is - the name of the project. If '-' is given, standard output is used. - - bzrp4 must be installed as its p4_fast_export.py module is used under - the covers to do the export. bzrp4 can be downloaded from - https://launchpad.net/bzrp4/. - - The P4PORT environment variable must be set, and you must be logged - into the Perforce server. - - By default, only the HEAD changelist is exported. To export all - changelists, append '@all' to the source. To export a revision range, - append a comma-delimited pair of changelist numbers to the source, - e.g., '100,200'. - """ - hidden = False - _see_also = ['fast-import', 'fast-import-filter'] - takes_args = ['source', 'destination'] - takes_options = [] - encoding_type = 'exact' - def run(self, source, destination, verbose=False): - load_fastimport() - from bzrlib.plugins.fastimport.exporters import fast_export_from - custom = [] - fast_export_from(source, destination, 'p4', verbose, custom) - - -class cmd_fast_export_from_svn(Command): - """Generate a fast-import file from a Subversion repository. - - Destination is a dump file, typically named xxx.fi where xxx is - the name of the project. If '-' is given, standard output is used. - - Python-Subversion (Python bindings to the Subversion APIs) - 1.4 or later must be installed as this library is used to - access the source repository. The source may be a network URL - but using a local URL is recommended for performance reasons. - """ - hidden = False - _see_also = ['fast-import', 'fast-import-filter'] - takes_args = ['source', 'destination'] - takes_options = ['verbose', - Option('trunk-path', type=str, argname="STR", - help="Path in repo to /trunk.\n" - "May be `regex:/cvs/(trunk)/proj1/(.*)` in " - "which case the first group is used as the " - "branch name and the second group is used " - "to match files.", - ), - ] - encoding_type = 'exact' - def run(self, source, destination, verbose=False, trunk_path=None): - load_fastimport() - from bzrlib.plugins.fastimport.exporters import fast_export_from - custom = [] - if trunk_path is not None: - custom.extend(['--trunk-path', trunk_path]) - fast_export_from(source, destination, 'svn', verbose, custom) diff --git a/exporters/Makefile b/exporters/Makefile deleted file mode 100644 index 2b71211..0000000 --- a/exporters/Makefile +++ /dev/null @@ -1,15 +0,0 @@ -SVN ?= /usr -CFLAGS += -I${SVN}/include/subversion-1 -pipe -O2 -std=c99 -CFLAGS += `pkg-config --cflags apr-1` -LDFLAGS += -L${SVN}/lib -lsvn_fs-1 -lsvn_repos-1 -LDFLAGS += `pkg-config --libs apr-1` - -all: svn-fast-export svn-archive - -svn-fast-export: svn-fast-export.c -svn-archive: svn-archive.c - -.PHONY: clean - -clean: - rm -rf svn-fast-export svn-archive diff --git a/exporters/__init__.py b/exporters/__init__.py deleted file mode 100644 index 3175109..0000000 --- a/exporters/__init__.py +++ /dev/null @@ -1,326 +0,0 @@ -# Copyright (C) 2009 Canonical Ltd -# -# This program is free software; you can redistribute it and/or modify -# it under the terms of the GNU General Public License as published by -# the Free Software Foundation; either version 2 of the License, or -# (at your option) any later version. -# -# This program is distributed in the hope that it will be useful, -# but WITHOUT ANY WARRANTY; without even the implied warranty of -# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the -# GNU General Public License for more details. -# -# You should have received a copy of the GNU General Public License -# along with this program. If not, see . - -"""Simplified and unified access to the various xxx-fast-export tools.""" - - -import gzip, os, subprocess, sys - -from bzrlib import errors -from bzrlib.trace import note, warning - - -class MissingDependency(Exception): - - def __init__(self, tool, minimum_version, missing): - self.tool = tool - self.minimum_version = minimum_version - self.missing = missing - - def get_message(self): - return "%s missing. Please install %s %s or later and try again." % \ - (self.missing, self.tool, self.minimum_version) - - -class _Exporter(object): - - def check_install(self, tool_name, minimum_version, required_commands=None, - required_libraries=None): - """Check dependencies are correctly installed. - - :param tool_name: name of the tool - :param minimum_version: minimum version required - :param required_commands: list of commands that must be on the path - :param required_libraries: list of Python libraries that must be - available - :raises MissingDependency: if a required dependency is not found - """ - self.tool_name = tool_name - self.minimum_version = minimum_version - if required_commands: - for cmd in required_commands: - self._check_cmd_available(cmd) - if required_libraries: - for lib in required_libraries: - self._check_lib_available(lib) - - def _check_cmd_available(self, cmd): - try: - if isinstance(cmd, str): - args = [cmd] - else: - args = cmd - retcode = subprocess.call(args, stdout=subprocess.PIPE, - stderr=subprocess.PIPE) - except OSError: - raise MissingDependency(self.tool_name, self.minimum_version, cmd) - - def _check_lib_available(self, lib): - try: - __import__(lib) - except ImportError: - raise MissingDependency(self.tool_name, self.minimum_version, lib) - - def generate(self, source, destination, verbose=False, custom=None): - """Generate a fast import stream. - - :param source: the source filename or URL - :param destination: filename or '-' for standard output - :param verbose: if True, output additional diagnostics - :param custom: a list of custom options to be added to the - command line of the underlying scripts used. If an option - and its argument are to be separated by a space, pass them - as consecutive items. - """ - raise NotImplementedError(self.generate) - - def get_output_info(self, dest): - """Get the output streams/filenames given a destination filename. - - :return: outf, basename, marks where - outf is a file-like object for storing the output, - basename is the name without the .fi and .gz prefixes - marks is the name of the marks file to use, if any - """ - if dest == '-': - return sys.stdout, None, None - else: - #if dest.endswith('.gz'): - # outf = gzip.open(dest, 'wb') - # base = dest[:-3] - #else: - outf = open(dest, 'w') - base = dest - if base.endswith(".fi"): - base = dest[:-3] - marks = "%s.marks" % (base,) - return outf, base, marks - - def execute(self, args, outf, cwd=None): - """Execute a command, capture the output and close files. - - :param args: list of arguments making up the command - :param outf: a file-like object for storing the output, - :param cwd: current working directory to use - :return: the return code - """ - if cwd is not None: - note("Executing %s in directory %s ..." % (" ".join(args), cwd)) - else: - note("Executing %s ..." % (" ".join(args),)) - try: - p = subprocess.Popen(args, stdout=outf, cwd=cwd) - p.wait() - finally: - if outf != sys.stdout: - outf.close() - return p.returncode - - def report_results(self, retcode, destination): - """Report whether the export succeeded or otherwise.""" - if retcode == 0: - note("Export to %s completed successfully." % (destination,)) - else: - warning("Export to %s exited with error code %d." - % (destination, retcode)) - - def execute_exporter_script(self, args, outf): - """Execute an exporter script, capturing the output. - - The script must be a Python script under the exporters directory. - - :param args: list of arguments making up the script, the first of - which is the script name relative to the exporters directory. - :param outf: a file-like object for storing the output, - :return: the return code - """ - # Note: currently assume Python is on the path. We could work around - # this later (for Windows users say) by packaging the scripts as Python - # modules and calling their internals directly. - exporters_dir = os.path.dirname(__file__) - script_abspath = os.path.join(exporters_dir, args[0]) - actual_args = ['python', script_abspath] + args[1:] - return self.execute(actual_args, outf) - - -class CvsExporter(_Exporter): - - def __init__(self): - self.check_install('cvs2svn', '2.30', ['cvs2bzr']) - self.check_install('CVS', '1.11', ['cvs']) - - def generate(self, source, destination, verbose=False, custom=None): - """Generate a fast import stream. See _Exporter.generate() for details.""" - # TODO: pass a custom cvs2bzr-default.options file as soon as - # cvs2bzr handles --options along with others. - args = ["cvs2bzr", "--dumpfile", destination] - outf, base, marks = self.get_output_info(destination) - # Marks aren't supported by cvs2bzr so no need to set that option - if custom: - args.extend(custom) - args.append(source) - retcode = self.execute(args, outf) - self.report_results(retcode, destination) - - -class DarcsExporter(_Exporter): - - def __init__(self): - self.check_install('Darcs', '2.2', [('darcs', '--version')]) - - def generate(self, source, destination, verbose=False, custom=None): - """Generate a fast import stream. See _Exporter.generate() for details.""" - args = ["darcs/darcs-fast-export"] - outf, base, marks = self.get_output_info(destination) - if marks: - args.append('--export-marks=%s' % marks) - if custom: - args.extend(custom) - args.append(source) - retcode = self.execute_exporter_script(args, outf) - self.report_results(retcode, destination) - - -class MercurialExporter(_Exporter): - - def __init__(self): - self.check_install('Mercurial', '1.2', None, ['mercurial']) - - def generate(self, source, destination, verbose=False, custom=None): - """Generate a fast import stream. See _Exporter.generate() for details.""" - # XXX: Should we add --force here? - args = ["hg-fast-export.py", "-r", source, "-s"] - outf, base, marks = self.get_output_info(destination) - if base: - args.append('--marks=%s.marks' % (base,)) - args.append('--mapping=%s.mapping' % (base,)) - args.append('--heads=%s.heads' % (base,)) - args.append('--status=%s.status' % (base,)) - if custom: - args.extend(custom) - retcode = self.execute_exporter_script(args, outf) - self.report_results(retcode, destination) - - -class GitExporter(_Exporter): - - def __init__(self): - self.cmd_name = "git" - if sys.platform == 'win32': - self.cmd_name = "git.cmd" - self.check_install('Git', '1.6', [self.cmd_name]) - - def generate(self, source, destination, verbose=False, custom=None): - """Generate a fast import stream. See _Exporter.generate() for details.""" - args = [self.cmd_name, "fast-export", "--all", "--signed-tags=warn"] - outf, base, marks = self.get_output_info(destination) - if marks: - marks = os.path.abspath(marks) - # Note: we don't pass import-marks because that creates - # a stream of incremental changes, not the full thing. - # We may support incremental output later ... - #if os.path.exists(marks): - # args.append('--import-marks=%s' % marks) - args.append('--export-marks=%s' % marks) - if custom: - args.extend(custom) - retcode = self.execute(args, outf, cwd=source) - self.report_results(retcode, destination) - - -class MonotoneExporter(_Exporter): - - def __init__(self): - self.check_install('Monotone', '0.43', ['mtn']) - - def generate(self, source, destination, verbose=False, custom=None): - """Generate a fast import stream. See _Exporter.generate() for details.""" - args = ["mtn", "git_export"] - outf, base, marks = self.get_output_info(destination) - if marks: - marks = os.path.abspath(marks) - if os.path.exists(marks): - args.append('--import-marks=%s' % marks) - args.append('--export-marks=%s' % marks) - if custom: - args.extend(custom) - retcode = self.execute(args, outf, cwd=source) - self.report_results(retcode, destination) - - -class PerforceExporter(_Exporter): - - def __init__(self): - self.check_install('p4', '2009.1', ['p4']) - self.check_install('Perforce Python API', '2009.1', None, ['P4']) - self.check_install('bzrp4', '', None, ['bzrlib.plugins.bzrp4']) - - def generate(self, source, destination, verbose=False, custom=None): - """Generate a fast import stream. See _Exporter.generate() for details.""" - from bzrlib.plugins.bzrp4 import p4_fast_export - outf, base, marks = self.get_output_info(destination) - # Marks aren't supported by p4_fast_export so no need to set that - # option - original_stdout = sys.stdout - sys.stdout = outf - try: - retcode = p4_fast_export.main([source]) - finally: - sys.stdout = original_stdout - self.report_results(retcode, destination) - - -class SubversionExporter(_Exporter): - - def __init__(self): - self.check_install('Python Subversion', '1.4', None, - ['svn.fs', 'svn.core', 'svn.repos']) - - def generate(self, source, destination, verbose=False, custom=None): - """Generate a fast import stream. See _Exporter.generate() for details.""" - args = ["svn-fast-export.py"] - outf, base, marks = self.get_output_info(destination) - # Marks aren't supported by svn-fast-export so no need to set that option - if custom: - args.extend(custom) - args.append(source) - retcode = self.execute_exporter_script(args, outf) - self.report_results(retcode, destination) - - -def fast_export_from(source, destination, tool, verbose=False, custom=None): - # Get the exporter - if tool == 'cvs': - factory = CvsExporter - elif tool == 'darcs': - factory = DarcsExporter - elif tool == 'hg': - factory = MercurialExporter - elif tool == 'git': - factory = GitExporter - elif tool == 'mtn': - factory = MonotoneExporter - elif tool == 'p4': - factory = PerforceExporter - elif tool == 'svn': - factory = SubversionExporter - try: - exporter = factory() - except MissingDependency, ex: - raise errors.BzrError(ex.get_message()) - - # Do the export - exporter.generate(source, destination, verbose=verbose, - custom=custom) diff --git a/exporters/darcs/.gitignore b/exporters/darcs/.gitignore deleted file mode 100644 index d26377c..0000000 --- a/exporters/darcs/.gitignore +++ /dev/null @@ -1,3 +0,0 @@ -Changelog -HEADER.html -.htaccess diff --git a/exporters/darcs/Makefile b/exporters/darcs/Makefile deleted file mode 100644 index 0c81c68..0000000 --- a/exporters/darcs/Makefile +++ /dev/null @@ -1,55 +0,0 @@ -VERSION = 0.9 -DATE := $(shell date +%Y-%m-%d) - -INSTALL = /usr/bin/install -c -DESTDIR = -prefix = /usr -bindir = $(prefix)/bin -mandir = $(prefix)/share/man/man1 - -MAN_TXT = $(wildcard *.txt) -MAN_HTML=$(patsubst %.txt,%.html,$(MAN_TXT)) -MAN=$(patsubst %.txt,%.1,$(MAN_TXT)) - -PROGRAMS = darcs-fast-export darcs-fast-import d2x x2d git-darcs - -all: man - -install: all - $(INSTALL) -d $(DESTDIR)$(bindir) - $(INSTALL) -d $(DESTDIR)$(mandir) - $(INSTALL) -m755 $(PROGRAMS) $(DESTDIR)$(bindir) - $(INSTALL) -m644 *.1 $(DESTDIR)$(mandir) - -doc: HEADER.html Changelog html - -HEADER.html: README Makefile - asciidoc -a toc -a numbered -a sectids -o HEADER.html README - -Changelog: .git/refs/heads/master - git log >Changelog - -%.html: %.txt - asciidoc $^ - -%.1: %.txt asciidoc.conf - a2x --asciidoc-opts="-f asciidoc.conf" \ - -a dfe_version=$(VERSION) -a dfe_date=$(DATE) -f manpage $< - -man: $(MAN) - -html: $(MAN_HTML) - -dist: - git archive --format=tar --prefix=darcs-fast-export-$(VERSION)/ $(VERSION) > darcs-fast-export-$(VERSION).tar - mkdir -p darcs-fast-export-$(VERSION) - git log > darcs-fast-export-$(VERSION)/Changelog - tar rf darcs-fast-export-$(VERSION).tar darcs-fast-export-$(VERSION)/Changelog - rm -rf darcs-fast-export-$(VERSION) - gzip -f -9 darcs-fast-export-$(VERSION).tar - -release: - git tag -l |grep -q $(VERSION) || dg tag $(VERSION) - $(MAKE) dist - gpg --comment "See http://vmiklos.hu/gpg/ for info" \ - -ba darcs-fast-export-$(VERSION).tar.gz diff --git a/exporters/darcs/NEWS b/exporters/darcs/NEWS deleted file mode 100644 index 1a0daa5..0000000 --- a/exporters/darcs/NEWS +++ /dev/null @@ -1,26 +0,0 @@ -VERSION DESCRIPTION ------------------------------------------------------------------------------ -0.9 - fix handling of accents in tag names - - warning fixes for Python-2.6 - - git-darcs: the add subcommand can now remember d-f-e - options - - git-darcs: new list, find-darcs and find-git subcommands -0.8 - revert the "not exporting unchanged files multiple - times" optimization, it causes corrupted results in some - cases. -0.7 - new darcs-fast-export option: --progress - - massive speedup in darcs-fast-export due to not - exporting unchanged files multiple times and reading - patches directly -0.6 - add a new darcs-fast-import script, allowing two-way sync - - new darcs-fast-export option: --git-branch - - add a new git-darcs script, making two-way sync easy -0.5 - new --help, --encoding, --authors-file, --working and - --logfile options - - add "hashed" support (see darcs init -h) - - add incremental conversion support for darcs1 as well - - add d2x wrapper script -0.4 - add incremental conversion support -0.3 - add darcs2 support -0.2 - add bzr and hg support -0.1 - initial short and fast version, supporting darcs1->git diff --git a/exporters/darcs/README b/exporters/darcs/README deleted file mode 100644 index 3fc9449..0000000 --- a/exporters/darcs/README +++ /dev/null @@ -1,187 +0,0 @@ -= darcs backend for fast data importers -Miklos Vajna - -== Purpose and Features - -darcs-fast-export is a tool to dump a http://darcs.net/[darcs] -repository in a format understood by "fast-importers" such as -http://git.or.cz/[git] -http://www.kernel.org/pub/software/scm/git/docs/git-fast-import.html[fast-import]. -It exhibits the following _features:_ - -Fast:: - darcs-fast-export provides a fast darcs backend for fast-import. - See link:t/bench-results/[here] for exact details. - -Correct:: - darcs-fast-export produces correct results in any extreme cases. - It has been tested with a collection of large darcs repos (called - http://code.haskell.org/darcs/big-zoo/[big-zoo]). And several testcases - under the `t/` directory. - -Independent:: - Ideally it should work with any fast importer, but actually it has been - tested with git fast-import, bzr fast-import and hg fastimport. (These - are the three fast-import implementations available ATM.) - -Formats:: - It supports the 'darcs-2', 'hashed', and 'old-fashioned-inventory' darcs - repository formats. - -Incremental conversions:: - It supports the usual `--export-marks` / `--import-marks` switches to - allow incremental conversion. - -Wrapper scripts:: - A wrapper script called `d2x` is available if you find typing - `--export-marks` / `--import-marks` all the time boring. A similar one - is also provided for the other direction, called `x2d`. Finally, if you - want to work on darcs repos with git, you can use the `git-darcs` - wrapper. - -Author mappings:: - Supports `--authors-file` option like Git's SVN adaptor, for DARCS - repositories that originated in CVS or SVN. - -Import script:: - The pair of `darcs-fast-export`, `darcs-fast-import` is also - included in this repo. It has been tested with the fast-expoters of Git, - Hg, Bzr and - of course - Darcs itself. - -Two-way sync:: - Using `darcs-fast-export` / `darcs-fast-import`, it is possible to - convert a darcs repo to an other VCS, work there, then convert your work - back to Darcs (or vica versa). This has been tested with "darcs -> git; - hack hack; git -> darcs". - -== Usage - -See the manpages: - -* link:darcs-fast-export.html[darcs-fast-export] -* link:darcs-fast-import.html[darcs-fast-import] -* link:d2x.html[d2x] -* link:x2d.html[x2d] -* link:git-darcs.html[git-darcs] - -=== Example - -Assuming that `test/` is a darcs repo, you could do this: ----- -$ mkdir test.git -$ cd test.git -$ git --bare init -$ cd .. -$ darcs-fast-export test |(cd test.git; git fast-import) ----- - -For more examples (especially for bzr and hg), see the `t/` directory. - -== Download - -Using git: ----- -$ git clone git://vmiklos.hu/darcs-fast-export ----- - -== Status - -In general, darcs-fast-export should work fine. darcs-fast-import has -known problems with tags - other than that it should be okay. git-darcs -should work properly as long as you are not paying too much attention to -the imported tags (newly created tags won't be pushed back). - -darcs-fast-export has been tested with the following versions: - -Darcs version (see http://bugs.darcs.net/issue844[this bug] on why do -you need such a new version): ----- -$ darcs --version -2.2.0 (release) ----- - -Git version: ----- -$ git --version -git version 1.6.0.2 ----- - -Bzr versions: ----- -$ bzr version -Bazaar (bzr) 1.12 -$ (cd ~/bzr/fastimport; bzr log --limit 1|grep revno) -revno: 181 ----- - -Yes, you need the fastiport plugin from BZR, the last hg release series -supported by fastimport-0.6 is hg-1.0.x. - -Mercurial (Hg) version: ----- -$ hg version -Mercurial Distributed SCM (version 1.3) ----- - -Strictly speaking this document is a wrong place to talk about -configuring hg fastimport. However... you will need something like: - ----- -$ hg clone http://vc.gerg.ca/hg/pyfastimport -$ hg clone http://vc.gerg.ca/hg/hg-fastimport -$ sudo ln -s /path/to/pyfastimport/fastimport /usr/lib/python2.6/site-packages/fastimport -$ sudo ln -s /path/to/hg-fastimport/hgfastimport /usr/lib/python2.6/site-packages/hgfastimport -echo -e "[extensions]\nfastimport = /usr/lib/python2.6/site-packages/hgfastimport" > ~/.hgrc ----- - -and once you installed the plugin correctly, you should have something like: - ----- -$ ls /usr/lib/python*/site-packages/hgext/fastimport/__init__.py -/usr/lib/python2.5/site-packages/hgext/fastimport/__init__.py ----- - -== Additional resources - -You can reach the Changelog link:Changelog[here], and a gitweb interface -http://vmiklos.hu/gitweb/?p=darcs-fast-export.git[here]. - -The fast-import stream format documentation is -http://git.kernel.org/?p=git/git.git;a=blob;f=fast-import.c;hb=HEAD[here] -if you're interested. - -== Alternatives - -- http://repo.or.cz/w/darcs2git.git[darcs2git] tries to find conflict - resolutions (to map them to merge commits), but it's rather slow - because of this. It does not support the darcs2 format and/or - incremental conversions, either. darcs-fast-export may support mapping - to merge commits later, but not before - http://bugs.darcs.net/issue1261[this issue] is addressed. - -- http://progetti.arstecnica.it/tailor[tailor] is an any2any VCS - converter, but it produces corrupted results when converting the - big-zoo - see http://progetti.arstecnica.it/tailor/ticket/171[this - ticket]. - -- http://git.sanityinc.com/?p=darcs-to-git.git[darcs-to-git] is similar - to darcs2git, but it fails for the testcases found in the testsuite of - darcs-fast-export. - -- http://github.com/freshtonic/undarcs/tree/master[undarcs] claims to be - fast, but its own README says it produces incorrect results. When I - tried, it did not handle the darcs2 format, binary files and incremental - support. - -== Thanks - -- Jason Dagit for helping me with darcs2 issues -- Shawn O. Pearce and Johannes Schindelin for writing `git-fast-import` - / `git-fast-export` -- Ian Clatworthy for writing bzr fast-import -- Paul Crowley for writing hg fast-import -- Matthias Andree for assorted improvements, among them the --help, - --encoding and --authors-file features (using Python's optparse), support - for hashed repositories, `_darcs/format` interpretation, and mangling - whitespace in tags to cope with repos imported into DARCS from CVS. -- Pieter de Bie for writing git-bzr, which was the base of git-darcs diff --git a/exporters/darcs/TODO b/exporters/darcs/TODO deleted file mode 100644 index c6892c8..0000000 --- a/exporters/darcs/TODO +++ /dev/null @@ -1,8 +0,0 @@ -more intelligent tests, such as detect if the hg fastimport extension is -not enabled, etc. - -parse the patches manually so we can avoid re-adding existing files manually. - -avoid darcs apply. - -import: handle evil merges (git-subtree), maybe using git log --first-parent diff --git a/exporters/darcs/asciidoc.conf b/exporters/darcs/asciidoc.conf deleted file mode 100644 index cb31717..0000000 --- a/exporters/darcs/asciidoc.conf +++ /dev/null @@ -1,21 +0,0 @@ -ifdef::doctype-manpage[] -ifdef::backend-docbook[] -[header] -template::[header-declarations] - - - {dfe_date} - - - {mantitle} - {manvolnum} - darcs-fast-export - {dfe_version} - darcs-fast-export manual - - - {manname} - {manpurpose} - -endif::backend-docbook[] -endif::doctype-manpage[] diff --git a/exporters/darcs/d2x b/exporters/darcs/d2x deleted file mode 100755 index 85e15e2..0000000 --- a/exporters/darcs/d2x +++ /dev/null @@ -1,112 +0,0 @@ -#!/bin/sh -# -# d2x - convert darcs repos to git, bzr or hg using fast-import -# -# Copyright (c) 2008 by Miklos Vajna -# -# This program is free software; you can redistribute it and/or modify -# it under the terms of the GNU General Public License as published by -# the Free Software Foundation; either version 2 of the License, or -# (at your option) any later version. -# -# This program is distributed in the hope that it will be useful, -# but WITHOUT ANY WARRANTY; without even the implied warranty of -# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the -# GNU General Public License for more details. -# -# You should have received a copy of the GNU General Public License -# along with this program. If not, see . -# - -usage() -{ - echo "Usage: d2x -f format darcsrepo" -} - -die() -{ - echo "$@" - usage - exit 1 -} - -check_up_to_date() -{ - upstreamnum=$(cd $origin; darcs show repo|grep 'Num Patches'|sed 's/.*: //') - if [ "$upstreamnum" = "$(eval $*)" ]; then - echo "No remote changes to pull!" - exit 0 - fi -} - -case $1 in - -h|--help) - usage - exit 0 - ;; - -f) - format="$2" - shift 2 - ;; -esac - -[ -n "$format" ] || die "Target format is not given!" - -case $format in - git|bzr|hg) - ;; - *) - die "The requested target format is not yet supported!" - ;; -esac - -origin="$1" -shift 1 - -[ -d "$origin" ] || die "Source repo does not exist!" - -# convert to abspath -cd $origin -origin=$(pwd) - -dmark="$origin.$format/darcs/dfe-marks" -fmark="$origin.$format/darcs/ffi-marks" - -mkdir -p $origin.$format/darcs -cd $origin.$format - -common_opts="--working $origin.$format/darcs/repo --logfile $origin.$format/darcs/log $origin" -if [ ! -f $dmark ]; then - case $format in - git) - git --bare init - darcs-fast-export $* --export-marks=$dmark $common_opts | \ - git fast-import --export-marks=$fmark - ;; - bzr) - bzr init-repo . - darcs-fast-export $* --export-marks=$dmark $common_opts | \ - bzr fast-import --export-marks=$fmark - - ;; - hg) - hg init - darcs-fast-export $* $origin | \ - hg fastimport - - esac -else - case $format in - git) - check_up_to_date "git rev-list HEAD |wc -l" - darcs-fast-export $* --export-marks=$dmark --import-marks=$dmark $common_opts | \ - git fast-import --export-marks=$fmark --import-marks=$fmark - ;; - bzr) - check_up_to_date "cd master; bzr revno" - darcs-fast-export $* --export-marks=$dmark --import-marks=$dmark $common_opts | \ - bzr fast-import --export-marks=$fmark --import-marks=$fmark - - ;; - hg) - die "Incremental conversion to hg is not yet supported by hg fastimport." - ;; - esac -fi diff --git a/exporters/darcs/d2x.txt b/exporters/darcs/d2x.txt deleted file mode 100644 index 41732fd..0000000 --- a/exporters/darcs/d2x.txt +++ /dev/null @@ -1,27 +0,0 @@ -= d2x(1) - -== NAME - -d2x - convert darcs repos to git, bzr or hg using fast-import - -== SYNOPSIS - -d2x -f [] - -== DESCRIPTION - -d2x is a wrapper script that just automates doing an initial or -continuing an incremental conversion. All it does is initializing the -target repo, starting darcs-fast-export and the relevant importer with -the proper switches and pipe the exporter's output to the importer's -standard input. - -== OPTIONS - ---help:: - Display usage. - --f :: - Specify the format of the target repo. Currently supported targets are - git, bzr and hg. Incremental conversion is supported in case of git and - bzr. diff --git a/exporters/darcs/darcs-fast-export b/exporters/darcs/darcs-fast-export deleted file mode 100755 index fa850de..0000000 --- a/exporters/darcs/darcs-fast-export +++ /dev/null @@ -1,380 +0,0 @@ -#!/usr/bin/env python - -""" - - darcs-fast-export - darcs backend for fast data importers - - Copyright (c) 2008, 2009 Miklos Vajna - Copyright (c) 2008 Matthias Andree - - This program is free software; you can redistribute it and/or modify - it under the terms of the GNU General Public License as published by - the Free Software Foundation; either version 2, or (at your option) - any later version. - - This program is distributed in the hope that it will be useful, - but WITHOUT ANY WARRANTY; without even the implied warranty of - MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - GNU General Public License for more details. - - You should have received a copy of the GNU General Public License - along with this program; if not, write to the Free Software - Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. - -""" - -import xml.dom.minidom -import xml.parsers.expat -import os -import sys -import gzip -import time -import calendar -import shutil -import subprocess -import optparse -import re -import urllib -import urllib2 -import StringIO - -sys = reload(sys) -sys.setdefaultencoding("utf-8") - -class Handler: - def __init__(self): - self.hashes = [] - self.authormap = {} - self.export_marks = [] - self.import_marks = [] - - def get_patchname(self, patch): - ret = [] - s = "" - if patch.attributes['inverted'].value == 'True': - s = "UNDO: " - cs = patch.getElementsByTagName("name")[0].childNodes - if cs.length > 0: - ret.append(s + cs[0].data) - lines = patch.getElementsByTagName("comment") - if lines: - for i in lines[0].childNodes[0].data.split('\n'): - if not i.startswith("Ignore-this: "): - ret.append(i) - return "\n".join(ret).encode('utf-8') - - def get_author(self, patch): - """darcs allows any freeform string, but fast-import has a more - strict format, so fix up broken author names here.""" - - author = patch.attributes['author'].value - if author in self.authormap: - author = self.authormap[author] - if not len(author): - author = "darcs-fast-export " - # add missing name - elif not ">" in author: - author = "%s <%s>" % (author.split('@')[0], author) - # avoid double quoting - elif author[0] == '"' and author[-1] == '"': - author = author[1:-1] - # name after email - elif author[-1] != '>': - author = author[author.index('>')+2:] + ' ' + author[:author.index('>')+1] - return author.encode('utf-8') - - def get_date(self, patch): - try: - date = time.strptime(patch, "%Y%m%d%H%M%S") - except ValueError: - date = time.strptime(patch[:19] + patch[-5:], '%a %b %d %H:%M:%S %Y') - return calendar.timegm(date) - - def progress(self, s): - print "progress [%s] %s" % (time.strftime("%Y-%m-%d %H:%M:%S", time.localtime()), s) - sys.stdout.flush() - - def log(self, s): - self.logsock.write("[%s] %s" % (time.strftime("%Y-%m-%d %H:%M:%S", time.localtime()), s)) - self.logsock.flush() - - def parse_inventory(self, sock=None): - prev = None - nextprev = False - buf = [] - if not sock: - sock = self.open(os.path.join(self.origin, "_darcs", "hashed_inventory")) - for i in sock.readlines(): - if i.startswith("hash"): - buf.insert(0, i[6:-1]) - if i.startswith("Starting with inventory:"): - nextprev = True - elif nextprev: - prev = i[:-1] - nextprev = False - sock.close() - for i in buf: - self.hashes.insert(0, i) - if prev: - sock = self.gzip_open(os.path.join(self.origin, "_darcs", "inventories", prev)) - self.parse_inventory(sock) - - # this is like gzip.open but supports urls as well - def gzip_open(self, path): - if os.path.exists(path): - return gzip.open(path) - buf = urllib.urlopen(path).read() - sock = StringIO.StringIO(buf) - return gzip.GzipFile(fileobj=sock) - - # this is like os.path.exists but supports urls as well - def path_exists(self, path): - if os.path.exists(path): - return True - else: - try: - urllib2.urlopen(urllib2.Request(path)) - return True - except urllib2.HTTPError, e: - return False - - # this is like open, but supports urls as well - def open(self, path): - if os.path.exists(path): - return open(path) - else: - return urllib.urlopen(path) - - def handle_opts(self): - # Option Parser - usage="%prog [options] darcsrepo" - opp = optparse.OptionParser(usage=usage) - opp.add_option("--import-marks", metavar="IFILE", - help="read state for incremental imports from IFILE") - opp.add_option("--export-marks", metavar="OFILE", - help="write state for incremental imports from OFILE") - opp.add_option("--encoding", - help="encoding of log [default: %default], if unspecified and input isn't utf-8, guess") - opp.add_option("--authors-file", metavar="F", - help="read author transformations in old=new format from F") - opp.add_option("--working", metavar="W", - help="working directory which is removed at the end of non-incremental conversions") - opp.add_option("--logfile", metavar="L", - help="log file which contains the output of external programs invoked during the conversion") - opp.add_option("--git-branch", metavar="B", - help="git branch [default: refs/heads/master]") - opp.add_option("--progress", metavar="P", - help="insert progress statements after every n commit [default: 100]") - (self.options, self.args) = opp.parse_args() - if len(self.args) < 1: - opp.error("darcsrepo required") - - # read author mapping file in gitauthors format, - # i. e. in=out (one per # line) - if self.options.authors_file: - sock = open(self.options.authors_file) - self.authormap = dict([i.strip().split('=',1) for i in sock]) - sock.close() - - if "://" not in self.args[0]: - self.origin = os.path.abspath(self.args[0]) - else: - self.origin = self.args[0].strip('/') - if self.options.working: - self.working = os.path.abspath(self.options.working) - else: - if "://" not in self.origin: - self.working = "%s.darcs" % self.origin - else: - self.working = "%s.darcs" % os.path.split(self.origin)[-1] - if self.options.logfile: - logfile = os.path.abspath(self.options.logfile) - else: - if "://" not in self.origin: - logfile = "%s.log" % self.origin - else: - logfile = "%s.log" % os.path.split(self.origin)[-1] - self.logsock = open(logfile, "a") - if self.options.git_branch: - self.git_branch = self.options.git_branch - else: - self.git_branch = "refs/heads/master" - - if self.options.progress: - self.prognum = int(self.options.progress) - else: - self.prognum = 100 - - def handle_import_marks(self): - if self.options.import_marks: - sock = open(self.options.import_marks) - for i in sock.readlines(): - line = i.strip() - if not len(line): - continue - self.import_marks.append(line.split(' ')[1]) - self.export_marks.append(line) - sock.close() - - def get_patches(self): - self.progress("getting list of patches") - if not len(self.import_marks): - sock = os.popen("darcs changes --xml --reverse --repo %s" % self.origin) - else: - sock = os.popen("darcs changes --xml --reverse --repo %s --from-match 'hash %s'" % (self.origin, self.import_marks[-1])) - buf = sock.read() - sock.close() - # this is hackish. we need to escape some bad chars, otherwise the xml - # will not be valid - buf = buf.replace('\x1b', '^[') - if self.options.encoding: - xmldoc = xml.dom.minidom.parseString(unicode(buf, self.options.encoding).encode('utf-8')) - else: - try: - xmldoc = xml.dom.minidom.parseString(buf) - except xml.parsers.expat.ExpatError: - try: - import chardet - except ImportError: - sys.exit("Error, encoding is not utf-8. Please " + - "either specify it with the --encoding " + - "option or install chardet.") - self.progress("encoding is not utf8, guessing charset") - encoding = chardet.detect(buf)['encoding'] - self.progress("detected encoding is %s" % encoding) - xmldoc = xml.dom.minidom.parseString(unicode(buf, encoding).encode('utf-8')) - sys.stdout.flush() - return xmldoc.getElementsByTagName('patch') - - def setup_workdir(self): - darcs2 = False - self.oldfashionedpatch = True - self.cwd = os.getcwd() - if self.path_exists(os.path.join(self.origin, "_darcs", "format")): - sock = self.open(os.path.join(self.origin, "_darcs", "format")) - format = [x.strip() for x in sock] - sock.close() - darcs2 = 'darcs-2' in format - self.oldfashionedpatch = not 'hashed' in format - if not self.oldfashionedpatch: - self.progress("parsing the inventory") - if "://" not in self.origin: - os.chdir(self.origin) - self.parse_inventory() - if not self.options.import_marks or not os.path.exists(self.working): - # init the tmp darcs repo - os.mkdir(self.working) - os.chdir(self.working) - if darcs2: - os.system("darcs init --darcs-2") - else: - os.system("darcs init --old-fashioned-inventory") - else: - os.chdir(self.working) - if self.options.import_marks: - sock = os.popen("darcs pull -a --match 'hash %s' %s" % (self.import_marks[-1], self.origin)) - self.log("Building/updating working directory:\n%s" % sock.read()) - sock.close() - - def export_patches(self): - patches = self.get_patches() - # this is the number of the NEXT patch - count = 1 - if len(self.import_marks): - patches = patches[1:] - count = len(self.import_marks) + 1 - if len(self.export_marks): - # this is the mark number of the NEXT patch - markcount = int(self.export_marks[-1].split(' ')[0][1:]) + 1 - else: - markcount = count - # this may be huge and we need it many times - patchnum = len(patches) - - if not len(self.import_marks): - self.progress("starting export, repo has %d patches" % patchnum) - else: - self.progress("continuing export, %d patches to convert" % patchnum) - paths = [] - for i in patches: - # apply the patch - hash = i.attributes['hash'].value - buf = ["\nNew patches:\n"] - if self.oldfashionedpatch: - sock = self.gzip_open(os.path.join(self.origin, "_darcs", "patches", hash)) - else: - sock = self.gzip_open(os.path.join(self.origin, "_darcs", "patches", self.hashes[count-1])) - buf.append(sock.read()) - sock.close() - sock = os.popen("darcs changes --context") - buf.append(sock.read()) - sock.close() - sock = subprocess.Popen(["darcs", "apply", "--allow-conflicts"], stdin=subprocess.PIPE, stdout=subprocess.PIPE) - sock.stdin.write("".join(buf)) - sock.stdin.close() - self.log("Applying %s:\n%s" % (hash, sock.stdout.read())) - sock.stdout.close() - message = self.get_patchname(i) - # export the commit - print "commit %s" % self.git_branch - print "mark :%s" % markcount - if self.options.export_marks: - self.export_marks.append(":%s %s" % (markcount, hash)) - date = self.get_date(i.attributes['date'].value) - print "committer %s %s +0000" % (self.get_author(i), date) - print "data %d\n%s" % (len(message), message) - if markcount > 1: - print "from :%s" % (markcount-1) - # export the files - for j in paths: - print "D %s" % j - paths = [] - for (root, dirs, files) in os.walk ("."): - for f in files: - j = os.path.normpath(os.path.join(root, f)) - if j.startswith("_darcs") or "-darcs-backup" in j: - continue - paths.append(j) - sock = open(j) - buf = sock.read() - sock.close() - # darcs does not track the executable bit :/ - print "M 644 inline %s" % j - print "data %s\n%s" % (len(buf), buf) - if message[:4] == "TAG ": - tag = re.sub('[^\xe9-\xf8\w.\-]+', '_', message[4:].strip().split('\n')[0]).strip('_') - print "tag %s" % tag - print "from :%s" % markcount - print "tagger %s %s +0000" % (self.get_author(i), date) - print "data %d\n%s" % (len(message), message) - if count % self.prognum == 0: - self.progress("%d/%d patches" % (count, patchnum)) - count += 1 - markcount += 1 - - os.chdir(self.cwd) - - if not self.options.export_marks: - shutil.rmtree(self.working) - self.logsock.close() - - def handle_export_marks(self): - if self.options.export_marks: - self.progress("writing export marks") - sock = open(self.options.export_marks, 'w') - sock.write("\n".join(self.export_marks)) - sock.write("\n") - sock.close() - - self.progress("finished") - - def handle(self): - self.handle_opts() - self.handle_import_marks() - self.setup_workdir() - self.export_patches() - self.handle_export_marks() - -if __name__ == "__main__": - h = Handler() - h.handle() diff --git a/exporters/darcs/darcs-fast-export.txt b/exporters/darcs/darcs-fast-export.txt deleted file mode 100644 index d404ecf..0000000 --- a/exporters/darcs/darcs-fast-export.txt +++ /dev/null @@ -1,68 +0,0 @@ -= darcs-fast-export(1) - -== NAME - -darcs-fast-export - darcs frontend to git fast-import - -== SYNOPSIS - -darcs-fast-export [] - -== DESCRIPTION - -darcs-fast-export expects one argument, the path to the source darcs -repository. It will print the git fast-import format on standard output -(stdout). - -The script can produce the fast-import stream format from the darcs -repository. It supports incremental conversion as well, via the ---import-marks / --export-marks switches. - -Optionally the darcsrepo string may be a HTTP repository, in that case -only the patches are downloaded, not the pristine, speeding up a -one-time import. - -== OPTIONS - --h, --help:: - Display usage. - ---import-marks=:: - Import marks from . This is read at the beginning of the - conversion at once. Use it if you want to continue an incremental - conversion. - ---export-marks=:: - Export marks to at the end of the conversion. It can be the - same as the one for --import-marks as it is written only once at the - end. Use it if you want to be able to incrementally update the target - repository later. - ---encoding=:: - The encoding of the author names and commit messages in the repository. - The default is utf-8. If it is not the default, it will be guessed. - Given that it takes some time, you can explicitly specify it as an - option to make the conversion faster. Content in the output will encoded - as utf-8 and will be written that way to the target repository, unless - the importer re-encodes it again to some other character set. - ---working=:: - The conversion is done by applying the patches one by one and recording - the state of the working directory. You can specify the path of this - directory using this option. - ---logfile=:: - The output of external commands are redirected to a log file. You can - specify the path of that file with this parameter. - ---git-branch=:: - There is only one branch in one darcs repository, but the fast-import - stream format allows multiple branches, thus the exporter has to name - darcs's branch. The default value is 'refs/heads/master'. - ---progress=:: - Insert progress statements after every patches, to be shown by the - fast importer during import. The default value is '100'. - ---authors-file=:: - Read author transformations in old=new format from . diff --git a/exporters/darcs/darcs-fast-import b/exporters/darcs/darcs-fast-import deleted file mode 100755 index 69ec7bb..0000000 --- a/exporters/darcs/darcs-fast-import +++ /dev/null @@ -1,375 +0,0 @@ -#!/usr/bin/env python - -""" - - darcs-fast-export - darcs backend for fast data exporters - - Copyright (c) 2008, 2009, 2010 Miklos Vajna - Copyright (c) 2008 Matthias Andree - - This program is free software; you can redistribute it and/or modify - it under the terms of the GNU General Public License as published by - the Free Software Foundation; either version 2, or (at your option) - any later version. - - This program is distributed in the hope that it will be useful, - but WITHOUT ANY WARRANTY; without even the implied warranty of - MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - GNU General Public License for more details. - - You should have received a copy of the GNU General Public License - along with this program; if not, write to the Free Software - Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. - -""" - -import sys -import os -import re -import time -import shutil -import optparse -import subprocess - -class Handler: - def __init__(self): - self.marks = {} - self.files = [] - self.prevfiles = None - self.ch = None - self.line = None - self.unread_line = False - self.eof = False - self.debug = False - self.export_marks = [] - self.import_marks = [] - - def read_next_line(self): - if self.unread_line: - self.unread_line = False - return - self.line = "" - if self.eof: - return - if self.ch: - self.line += self.ch - self.ch = None - buf = sys.stdin.readline() - if not len(buf): - self.eof = True - else: - self.line += buf - if self.debug: - print "read_next_line: '%s'" % self.line - - def read(self, length): - buf = "" - if self.ch: - buf += self.ch - self.ch = None - buf += sys.stdin.read(length) - if self.debug: - print "read: '%s'" % buf - return buf - - def skip_optional_lf(self): - self.ch = self.read(1) - if self.ch == "\n": - self.ch = None - - def bug(self, s): - raise Exception(s) - - def get_date(self, ts, tz): - # first fix the case when tz is higher than +1200, as - # darcs won't accept it - if int(tz[:3]) > 12: - ts = str(int(ts) + 60*60*24) - tz = str(int(tz[:3])-24) + tz[3:] - # int(ts) is seconds since epoch. Since we're trying to - # capture both the absolute time of the commit and the - # localtime in the timezone of the committer, we need to turn - # the (seconds-since-epoch, committer-timezone-offset) pair - # that we get from the git-fast-export stream format into a - # localized-time-plus-timezone-marker string that darcs will - # accept. Therefore, we parse the timezone-offset (which - # looks like +0500 or +0000 or -0730 or something) and add it - # to seconds-since-epoch before calling gmtime(). - mo = re.search(r'^([\+\-])(\d\d)(\d\d)$', tz) - offset = 60*60*int(mo.group(2)) + 60*int(mo.group(3)) - if mo.group(1) == "-": - offset = -offset - offset_time = int(ts) + offset - s = time.strftime("%a %b %d %H:%M:%S %Y", time.gmtime(offset_time)) - items = s.split(' ') - return " ".join(items[:-1]) + " " + tz + " " + items[-1] - - def invoke_darcs(self, cmdline): - if os.system("darcs %s" % cmdline) != 0: - self.bug("darcs failed") - - def invoke_add(self, path): - self.invoke_darcs("add --boring --case-ok %s" % path) - - def handle_mark(self): - if self.line.startswith("mark :"): - self.mark_num = int(self.line[6:-1]) - self.read_next_line() - - def handle_data(self): - if not self.line.startswith("data "): - self.bug("Expected 'data n' command, found: '%s'" % self.line[:-1]) - length = int(self.line[5:-1]) - self.buf = self.read(length) - self.skip_optional_lf() - - def handle_blob(self): - self.read_next_line() - self.handle_mark() - self.handle_data() - self.marks[self.mark_num] = self.buf - - def handle_ident(self, s): - items = s.split(' ') - self.ident = " ".join(items[:-2]) - self.date = self.get_date(items[-2], items[-1]) - - def handle_msg(self): - items = self.buf.split('\n') - self.short = items[0] - self.long = "\n".join(items[1:]) - - def handle_tag(self): - version = self.line[:-1].split(' ')[1] - self.read_next_line() - if self.line.startswith("from "): - self.read_next_line() - if self.line.startswith("tagger "): - self.handle_ident(self.line[7:-1]) - self.read_next_line() - self.handle_data() - self.skip_optional_lf() - sock = subprocess.Popen(["darcs", "tag", "--pipe"], stdin=subprocess.PIPE, stdout=subprocess.PIPE) - buf = [self.date, self.ident, version] - sock.stdin.write("\n".join(buf)) - sock.stdin.close() - self.log("Tagging %s:\n%s" % (version, sock.stdout.read())) - sock.stdout.close() - if sock.wait() != 0: - self.bug("darcs tag failed: '%s'" % sock.returncode) - - def handle_commit(self): - if not self.prevfiles and self.options.import_marks: - # first commit in an incremental continued - # import - for (root, dirs, files) in os.walk("."): - for i in files: - path = os.path.normpath(os.path.join(root, i)) - if path.startswith("_darcs") or "-darcs-backup" in path: - continue - self.files.append(path) - self.prevfiles = self.files[:] - adds = [] - symlinks = [] - - self.read_next_line() - self.handle_mark() - if self.line.startswith("author "): - self.handle_ident(self.line[7:-1]) - self.read_next_line() - if self.line.startswith("committer "): - self.handle_ident(self.line[10:-1]) - self.read_next_line() - self.handle_data() - self.skip_optional_lf() - self.handle_msg() - self.read_next_line() - if self.line.startswith("from "): - self.read_next_line() - while self.line.startswith("merge "): - self.read_next_line() - change = False - while len(self.line) > 0: - if self.line.startswith("deleteall"): - path = self.line[2:-1] - for path in self.files: - os.unlink(path) - self.files = [] - change = True - elif self.line.startswith("D "): - path = self.line[2:-1] - if os.path.exists(path): - os.unlink(path) - if path in self.files: - self.files.remove(path) - change = True - elif self.line.startswith("R "): - self.invoke_darcs("mv %s" % self.line[2:]) - change = True - elif self.line.startswith("C "): - src, dest = self.line[:-1].split(' ')[1:] - shutil.copy(src.strip('"'), dest.strip('"')) - self.invoke_add(dest) - change = True - elif self.line.startswith("M "): - items = self.line.split(' ') - path = items[3][:-1] - dir = os.path.split(path)[0] - if len(dir) and not os.path.exists(dir): - os.makedirs(dir) - if items[1] == "120000": - if not self.options.symhack: - print "Adding symbolic links (symlinks) is not supported by Darcs." - sys.exit(2) - idx = int(items[2][1:]) # TODO: handle inline symlinks - symlinks.append((self.marks[idx], path)) - self.read_next_line() - continue - sock = open(path, "w") - if items[2] != "inline": - idx = int(items[2][1:]) - sock.write(self.marks[idx]) - else: - self.read_next_line() - self.handle_data() - sock.write(self.buf) - sock.close() - if path not in self.prevfiles: - adds.append(path) - if path not in self.files: - self.files.append(path) - change = True - else: - self.unread_line = True - break - self.read_next_line() - if not len(self.line): - break - - if not change: - # darcs does not support empty commits - return - for i in adds: - self.invoke_add(i) - args = ["darcs", "record", "--ignore-times", "-a", "--pipe"] - buf = [self.date, self.ident] - if not len(self.short): - args.extend(['-m', '']) - else: - buf.extend([self.short, self.long]) - sock = subprocess.Popen(args, stdin=subprocess.PIPE, stdout=subprocess.PIPE) - sock.stdin.write("\n".join(buf)+"\n") - sock.stdin.close() - self.log("Recording :%s:\n%s" % (self.mark_num, sock.stdout.read())) - sock.stdout.close() - if sock.wait() != 0: - self.bug("darcs record failed: '%s'" % sock.returncode) - - for src, path in symlinks: - # symlink does not do what we want if path is - # already there - if os.path.exists(path): - # rmtree() does not work on symlinks - if os.path.islink(path): - os.remove(path) - else: - shutil.rmtree(path) - os.symlink(src, path) - if self.options.export_marks: - # yeah, an xml parser would be better, but - # should we mess with encodings just because of - # this? i hope not - sock = os.popen("darcs changes --last=1 --xml", "r") - buf = sock.read() - sock.close() - hash = buf.split('\n')[1].split("'")[-2] - self.export_marks.append(":%s %s" % (self.mark_num, hash)) - - def handle_progress(self, s): - print "import progress [%s] %s" % (time.strftime("%Y-%m-%d %H:%M:%S", time.localtime()), s.strip()) - sys.stdout.flush() - - def handle_opts(self): - # Option Parser - usage="%prog [options]" - opp = optparse.OptionParser(usage=usage) - opp.set_defaults(symhack=False) - opp.add_option("--import-marks", metavar="IFILE", - help="read state for incremental imports from IFILE") - opp.add_option("--export-marks", metavar="OFILE", - help="write state for incremental imports to OFILE") - opp.add_option("--logfile", metavar="L", - help="log file which contains the output of external programs invoked during the conversion") - opp.add_option("--symhack", action="store_true", dest="symhack", - help="Do not error out when a symlink would be created, just create it in the workdir") - opp.add_option("--progress", metavar="P", - help="insert progress statements after every n commit [default: 100]") - (self.options, args) = opp.parse_args() - - if self.options.logfile: - logfile = self.options.logfile - else: - logfile = "_darcs/import.log" - self.logsock = open(os.path.abspath(logfile), "a") - - if self.options.progress: - self.prognum = int(self.options.progress) - else: - self.prognum = 0 - - def log(self, s): - self.logsock.write("[%s] %s" % (time.strftime("%Y-%m-%d %H:%M:%S", time.localtime()), s)) - self.logsock.flush() - - def handle_export_marks(self): - if self.options.export_marks: - sock = open(self.options.export_marks, 'w') - sock.write("\n".join(self.export_marks)) - sock.write("\n") - sock.close() - - def handle_import_marks(self): - if self.options.import_marks: - sock = open(self.options.import_marks) - for i in sock.readlines(): - line = i.strip() - if not len(line): - continue - self.import_marks.append(line.split(' ')[1]) - self.export_marks.append(line) - sock.close() - - def handle(self): - self.handle_opts() - self.handle_import_marks() - - commitcount = 0 - while not self.eof: - self.read_next_line() - if not len(self.line[:-1]): - pass - elif self.line.startswith("blob"): - self.handle_blob() - elif self.line.startswith("commit"): - self.handle_commit() - commitcount += 1 - if self.prognum != 0 and commitcount % self.prognum == 0: - self.handle_progress("%d patches" % commitcount) - elif self.line.startswith("tag"): - self.handle_tag() - elif self.line.startswith("reset"): - self.read_next_line() - if not self.line.startswith("from "): - self.unread_line = True - elif self.line.startswith("checkpoint"): - pass - elif self.line.startswith("progress"): - self.handle_progress(self.line[9:]) - else: - self.bug("'%s': invalid command" % self.line[:-1]) - - self.handle_export_marks() - -if __name__ == "__main__": - h = Handler() - h.handle() diff --git a/exporters/darcs/darcs-fast-import.txt b/exporters/darcs/darcs-fast-import.txt deleted file mode 100644 index a7f2a12..0000000 --- a/exporters/darcs/darcs-fast-import.txt +++ /dev/null @@ -1,57 +0,0 @@ -= darcs-fast-import(1) - -== NAME - -darcs-fast-import - darcs backend to the 'fast-import stream' format - -== SYNOPSIS - -darcs-fast-import [] - -== DESCRIPTION - -darcs-fast-import can produce a darcs repository from a fast-import -stream, read from the standard input. It supports incremental conversion -as well, via the --import-marks / --export-marks switches. - -== OPTIONS - --h, --help:: - Display usage. - ---import-marks:: - Import marks from a given file. This is read at the beginning of the - conversion at once. Use it if you want to continue an incremental - conversion. - ---export-marks:: - Export marks to a given file at the end of the conversion. It can be the - same as the one for --import-marks as it is written only once at the - end. Use it if you want to be able to incrementally update the target - repository later. - ---logfile:: - The output of external commands are redirected to a log file. You can - specify the path of that file with this parameter. - ---symhack:: - Enable hack for symbolic links. darcs add does not handle them - but in case they are just added, we can create them in the working - directory. This can be handy in case for example the symbolic link is in - a subdirectory of the project and you don't even care about that - subdirectory. So the hack can be useful, but be extremely careful when - you use it. - ---progress=:: - Insert progress statements after every created patches. The - default is not to print anything as progress info is usually provided by - the exporter. Use this option in case the exporter does not have such a - switch but you still want to get some feedback. - -== EXIT CODES - -The exit code is: - -* 0 on success -* 1 on unhandled exception -* 2 in case the stream would try to let the importer create a symlink diff --git a/exporters/darcs/git-darcs b/exporters/darcs/git-darcs deleted file mode 100755 index c4343ef..0000000 --- a/exporters/darcs/git-darcs +++ /dev/null @@ -1,279 +0,0 @@ -#!/bin/bash -# -# git-darcs - bidirectional operation between a darcs repo and git -# -# Copyright (c) 2008, 2010 by Miklos Vajna -# -# Based on git-bzr, which is -# -# Copyright (c) 2008 Pieter de Bie -# -# This program is free software; you can redistribute it and/or modify -# it under the terms of the GNU General Public License as published by -# the Free Software Foundation; either version 2 of the License, or -# (at your option) any later version. -# -# This program is distributed in the hope that it will be useful, -# but WITHOUT ANY WARRANTY; without even the implied warranty of -# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the -# GNU General Public License for more details. -# -# You should have received a copy of the GNU General Public License -# along with this program. If not, see . -# - -add() -{ - name="$1" - shift - location="$1" - shift - if ! [ -n "$name" -a -n "$location" ]; then - echo "Usage: git darcs add name location [darcs-fast-export options]" - return 1 - fi - if git remote show |grep -q $name; then - echo "There is already a remote with that name" - return 1 - fi - if [ -n "$(git config git-darcs.$name.location)" ]; then - echo "There is already a darcs repo with that name" - return 1 - fi - repo=$location/_darcs - if [ ! -d $repo ] && ! wget --quiet --spider $repo; then - echo "Remote is not a darcs repository" - return 1 - fi - git config git-darcs.$name.location $location - echo "Darcs repo $name added. You can fetch it with 'git darcs fetch $name'" - if ! [ -z "$*" ]; then - git config git-darcs.$name.darcs-fast-export-options "$*" - echo "darcs-fast-export will get options: $*" - fi -} - -get_location() -{ - l=$(git config git-darcs.$remote.location) - if [ -z "$l" ]; then - echo "Cannot find darcs remote with name '$remote'." >&2 - return 1 - fi - echo $l -} - -fetch() -{ - remote="$1" - shift - if ! [ -n "$remote" -a -z "$*" ]; then - echo "Usage: git darcs fetch reponame" - return 1 - fi - location=$(get_location $remote) || return $? - git_map=$git_dir/darcs-git/$remote-git-map - darcs_map=$git_dir/darcs-git/$remote-darcs-map - common_opts="--working $git_dir/darcs-git/repo --logfile $git_dir/darcs-git/fetch.log --git-branch=refs/remotes/darcs/$remote" - dfe_opts=$(git config git-darcs.$remote.darcs-fast-export-options) - pre_fetch="$(git config git-darcs.$remote.pre-fetch)" - if [ -n "$pre_fetch" ]; then - $pre_fetch - fi - if [ ! -f $git_map -a ! -f $darcs_map ]; then - echo "There doesn't seem to be an existing refmap." - echo "Doing an initial import" - mkdir -p $git_dir/darcs-git - darcs-fast-export --export-marks=$darcs_map $common_opts $dfe_opts $location | \ - git fast-import --export-marks=$git_map - elif [ -f $git_map -a -f $darcs_map ]; then - echo "Updating remote $remote" - old_rev=$(git rev-parse refs/remotes/darcs/$remote) - darcs-fast-export --import-marks=$darcs_map --export-marks=$darcs_map $common_opts $dfe_opts $location | \ - git fast-import --quiet --import-marks=$git_map --export-marks=$git_map - new_rev=$(git rev-parse refs/remotes/darcs/$remote) - if [ "$old_rev" != "$new_rev" ]; then - echo "Fetched the following updates:" - git shortlog $old_rev..$new_rev - else - echo "Nothing fetched." - return 0 - fi - else - echo "One of the mapfiles is missing! Something went wrong!" - return 1 - fi - post_fetch="$(git config git-darcs.$remote.post-fetch)" - if [ -n "$post_fetch" ]; then - $post_fetch - fi -} - -pull() -{ - remote="$1" - shift - if ! [ -n "$remote" -a -z "$*" ]; then - echo "Usage: git darcs pull reponame" - return 1 - fi - fetch $remote || return $? - # see if we need to merge or rebase - branch=$(git symbolic-ref HEAD|sed 's|.*/||') - if [ "$(git config branch.$branch.rebase)" = "true" ]; then - git rebase refs/remotes/darcs/$remote - else - git merge refs/remotes/darcs/$remote - fi -} - -push() -{ - remote="$1" - shift - if ! [ -n "$remote" -a -z "$*" ]; then - echo "Usage: git darcs push reponame" - return 1 - fi - location=$(get_location $remote) || return $? - if [ -n "$(git rev-list --left-right HEAD...refs/remotes/darcs/$remote | sed -n '/^>/ p')" ]; then - echo "HEAD is not a strict child of $remote, cannot push. Merge first" - return 1 - fi - if [ -z "$(git rev-list --left-right HEAD...refs/remotes/darcs/$remote | sed -n '/^" - return 1 - fi - for remote in $(git for-each-ref --format='%(refname)' refs/remotes/darcs) - do - remote=`basename $remote` - git_map=$git_dir/darcs-git/$remote-git-map - darcs_map=$git_dir/darcs-git/$remote-darcs-map - if [ ! -f $git_map -o ! -f $darcs_map ] - then - echo "Missing mappings for remote $remote" - return 1 - fi - for row in `sed -n -e "/:.* $sha1.*/ s/[^ ]*/&/p" $git_map` - do - sed -n -e "/$row / {s/[^ ]*//; s/.*/$remote\t&/p}" $darcs_map - done - done -} - -# Find the git commit(s) supporting a darcs patch prefix -find_git() -{ - patch="$1" - shift - if [ -z "$patch" -o -n "$*" ] - then - echo "Usage: git darcs find-git " - return 1 - fi - for remote in $(git for-each-ref --format='%(refname)' refs/remotes/darcs) - do - remote=`basename $remote` - git_map=$git_dir/darcs-git/$remote-git-map - darcs_map=$git_dir/darcs-git/$remote-darcs-map - if [ ! -f $git_map -o ! -f $darcs_map ] - then - echo "Missing mappings for remote $remote" - return 1 - fi - for row in `sed -n -e "/:.* $patch.*/ s/[^ ]*/&/p" $darcs_map` - do - sed -n -e "/$row / {s/[^ ]* \(.*\)/$remote\t\1/p}" $git_map - done - done -} - -git rev-parse 2> /dev/null -if [ $? != 0 ]; then - echo "Must be inside a git repository to work" - exit 1 -fi - -git_dir=$(git rev-parse --git-dir) -# make it absolute -cd $git_dir -git_dir=$(pwd) -cd - >/dev/null -command="$1" -shift - -case $command in - add|push|fetch|pull|list) - ;; - find-darcs) - command=find_darcs - ;; - find-git) - command=find_git - ;; - *) - echo "Usage: git darcs [COMMAND] [OPTIONS]" - echo "Commands: add, push, fetch, pull, list, find-darcs, find-git" - exit 1 - ;; -esac - - -up=$(git rev-parse --show-cdup) -[ -z "$up" ] && up="." -cd $up -$command "$@" diff --git a/exporters/darcs/git-darcs.txt b/exporters/darcs/git-darcs.txt deleted file mode 100644 index 8bf5b33..0000000 --- a/exporters/darcs/git-darcs.txt +++ /dev/null @@ -1,92 +0,0 @@ -= git-darcs(1) - -== NAME - -git-darcs - a bidirectional git - darcs gateway - -== SYNOPSIS - -git-darcs - -== DESCRIPTION - -git darcs can convert a darcs repo to a git one, can update such an -existing git repo later, and finally can push back your changes from the -git repo to the darcs one. - -A typical workflow is: - ----- -$ mkdir git-repo -$ cd git-repo -$ git init -$ git darcs add upstream /path/to/darcs-repo -$ git darcs pull upstream - -... hack, hack, hack ... - -$ git darcs push upstream ----- - -== GLOBAL OPTIONS - --h, --help:: - Display usage. - -== COMMANDS - -The supported commands are the followings: - -add:: - This can register a new darcs repo in the git one, so that you - can fetch from it. The syntax is `add nick path [dfe-options]`. - Add any options you want to be passed to darcs-fast-export, - like --encoding=utf-8, or --authors-file AUTHORMAP. Remember - that if AUTHORMAP is not absolute, it will be interpreted - relative to the git repository's root directory. - -push:: - Transfers your changes created in the current branch back the - darcs one. The syntax is `push nick`. - -fetch:: - Downloads changes from the darcs repo and updates the - `darcs/` branch. None of your local branches are updated. - -pull:: - Calls `fetch` then `git merge` or `git rebase` based on the - `branch..rebase` configuration setting, where `` - is the current branch. The default is - just like with `git pull` - is - to `git merge`. - -list:: - List the name [and location] of each registered darcs repo. - The syntax is `list [-v|--verbose]`. - -find-darcs:: - Searches for darcs patches matching a SHA1 prefix. - The syntax is `find-darcs `. - -find-git:: - Searches for git commits matching a darcs patch prefix. - The syntax is `find-git `. - -== HOOKS - -It's possible to automatically run before and after the fetch and the -push subcommand. For example if you want to automatically run `darcs -pull -a` before a `git darcs fetch upstream`: - ----- -git config git-darcs.upstream.pre-fetch "darcs pull -a --repodir=/path/to/darcs-repo" ----- - -Or in case you want to automatically `darcs send` all patches after a -`git darcs push upstream`: - ----- -git config git-darcs.upstream.post-push "darcs send -a --repodir=/path/to/darcs-repo" ----- - -== SEE-ALSO -*git*(1), *darcs*(1) diff --git a/exporters/darcs/t/Makefile b/exporters/darcs/t/Makefile deleted file mode 100644 index de8a7ab..0000000 --- a/exporters/darcs/t/Makefile +++ /dev/null @@ -1,9 +0,0 @@ -T = $(wildcard test*.sh) - -all: $(T) - @echo "passed $$(echo $(T)|wc -w) tests." - -$(T): - @echo "*** $@ ***"; sh $@ - -.PHONY: $(T) diff --git a/exporters/darcs/t/bench-results/Makefile b/exporters/darcs/t/bench-results/Makefile deleted file mode 100644 index 0157f69..0000000 --- a/exporters/darcs/t/bench-results/Makefile +++ /dev/null @@ -1,5 +0,0 @@ -bench-results.png: bench-results.gnu bench-results.dat - gnuplot bench-results.gnu - -bench-results.dat: bench-results.py $(wildcard ../darcs-benchmark/big-zoo/*.log) - python bench-results.py > bench-results.dat diff --git a/exporters/darcs/t/bench-results/bench-results.gnu b/exporters/darcs/t/bench-results/bench-results.gnu deleted file mode 100644 index f4e8917..0000000 --- a/exporters/darcs/t/bench-results/bench-results.gnu +++ /dev/null @@ -1,6 +0,0 @@ -set terminal png -set output 'bench-results.png' -unset key -set xlabel "number of patches" -set ylabel "elapsed time in hours" -plot 'bench-results.dat' with linespoints diff --git a/exporters/darcs/t/bench-results/bench-results.py b/exporters/darcs/t/bench-results/bench-results.py deleted file mode 100644 index fbb834b..0000000 --- a/exporters/darcs/t/bench-results/bench-results.py +++ /dev/null @@ -1,23 +0,0 @@ -from glob import glob -import re - -def cmp_data(a, b): - return cmp(a[0], b[0]) - -logs = glob("../darcs-benchmark/big-zoo/*.log") - -data = [] - -for i in logs: - sock = open(i) - for j in sock.readlines(): - if "Num Patches:" in j: - patches = int(j.split(": ")[1].strip()) - elif j.startswith("real"): - l = re.sub("real\t([0-9]+)m([0-9.]+)s\n", r"\1 \2", j).split(" ") - secs = int(l[0])*60 + float(l[1]) - hours = secs / 3600 - data.append([patches, hours]) -data.sort(cmp=cmp_data) -for i in data: - print "%s %s" % (i[0], i[1]) diff --git a/exporters/darcs/t/bench-tailor.sh b/exporters/darcs/t/bench-tailor.sh deleted file mode 100644 index 7567f7b..0000000 --- a/exporters/darcs/t/bench-tailor.sh +++ /dev/null @@ -1,59 +0,0 @@ -#!/bin/sh - -create_config() -{ - cd $1 - mypath=$(pwd) - cd - >/dev/null - myname=$(basename $mypath) - - cat > config << EOF -[DEFAULT] -encoding-errors-policy = replace - -[$myname] -source = darcs:$myname -target = git:$myname - -[darcs:$myname] -subdir = darcs -repository = $mypath - -[git:$myname] -subdir = git -repository = $mypath.git -EOF -} - -PATH=$HOME/darcs/tailor:$PATH -if [ ! -d darcs-benchmark ]; then - darcs get http://code.haskell.org/darcs/darcs-benchmark - cd darcs-benchmark -else - cd darcs-benchmark - darcs pull -a -fi -sh initialise.sh -cd big-zoo -if [ -n "$1" ]; then - targets=$1 -else - targets=*_play.tar.gz -fi -for i in $targets -do - echo "benchmarking $i" - rm -rf _playground - tar xf $i - cd _playground - log="../$i.tailor-$(tailor --version).log" - create_config sandbox - sh -c 'time tailor --configfile config' 2>&1 |tee $log - if diff --exclude _darcs --exclude .git -Nur sandbox git >/dev/null; then - echo "ok, the result is correct" >> $log - else - echo "ouch, the result is corrupted" >> $log - exit 1 - fi - cd .. -done diff --git a/exporters/darcs/t/bench.sh b/exporters/darcs/t/bench.sh deleted file mode 100644 index a4b3d0d..0000000 --- a/exporters/darcs/t/bench.sh +++ /dev/null @@ -1,38 +0,0 @@ -#!/bin/sh - -# this is a test as well, but it would take a lot of time, so don't -# prefix it with 'test'. - -. lib.sh - -if [ ! -d darcs-benchmark ]; then - darcs get http://code.haskell.org/darcs/darcs-benchmark - cd darcs-benchmark -else - cd darcs-benchmark - darcs pull -a -fi -sh initialise.sh -cd big-zoo -if [ -n "$1" ]; then - targets=$1 -else - targets=*_play.tar.gz -fi -for i in $targets -do - echo "benchmarking $i" - rm -rf _playground - tar xf $i - cd _playground - log="../$i.d-f-e-$(git describe).log" - sh -c 'time d2x -f git sandbox' 2>&1 |tee $log - darcs show repo --repodir sandbox |egrep -v 'Root|Cache|Default' >> $log - if diff_git sandbox >/dev/null; then - echo "ok, the result is correct" >> $log - else - echo "ouch, the result is corrupted" >> $log - exit 1 - fi - cd .. -done diff --git a/exporters/darcs/t/data/hungarian.gif b/exporters/darcs/t/data/hungarian.gif deleted file mode 100644 index 41a36fe..0000000 Binary files a/exporters/darcs/t/data/hungarian.gif and /dev/null differ diff --git a/exporters/darcs/t/lib-httpd.sh b/exporters/darcs/t/lib-httpd.sh deleted file mode 100644 index fad953e..0000000 --- a/exporters/darcs/t/lib-httpd.sh +++ /dev/null @@ -1,67 +0,0 @@ -#!/bin/sh -# -# This is based on git's t/lib-httpd.sh, which is -# Copyright (c) 2008 Clemens Buchacher -# - -if test -n "$DFE_TEST_SKIP_HTTPD" -then - echo "skipping test (undef DFE_TEST_SKIP_HTTPD to enable)" - exit -fi - -LIB_HTTPD_PATH=${LIB_HTTPD_PATH-'/usr/sbin/httpd'} -LIB_HTTPD_PORT=${LIB_HTTPD_PORT-'8111'} - -HTTPD_ROOT_PATH="$PWD"/httpd -HTTPD_DOCUMENT_ROOT_PATH=$HTTPD_ROOT_PATH/www - -if ! test -x "$LIB_HTTPD_PATH" -then - echo "skipping test, no web server found at '$LIB_HTTPD_PATH'" - exit -fi - -HTTPD_VERSION=`$LIB_HTTPD_PATH -v | \ - sed -n 's/^Server version: Apache\/\([0-9]*\)\..*$/\1/p; q'` - -if test -n "$HTTPD_VERSION" -then - if test -z "$LIB_HTTPD_MODULE_PATH" - then - if ! test $HTTPD_VERSION -ge 2 - then - echo "skipping test, at least Apache version 2 is required" - exit - fi - - LIB_HTTPD_MODULE_PATH='/usr/lib/apache' - fi -else - error "Could not identify web server at '$LIB_HTTPD_PATH'" -fi - -HTTPD_PARA="-d $HTTPD_ROOT_PATH -f $HTTPD_ROOT_PATH/apache.conf" - -prepare_httpd() { - mkdir -p $HTTPD_DOCUMENT_ROOT_PATH - - ln -s $LIB_HTTPD_MODULE_PATH $HTTPD_ROOT_PATH/modules - - echo "PidFile httpd.pid" > $HTTPD_ROOT_PATH/apache.conf - echo "DocumentRoot www" >> $HTTPD_ROOT_PATH/apache.conf - echo "ErrorLog error.log" >> $HTTPD_ROOT_PATH/apache.conf - - HTTPD_URL=http://127.0.0.1:$LIB_HTTPD_PORT -} - -start_httpd() { - prepare_httpd - - "$LIB_HTTPD_PATH" $HTTPD_PARA \ - -c "Listen 127.0.0.1:$LIB_HTTPD_PORT" -k start -} - -stop_httpd() { - "$LIB_HTTPD_PATH" $HTTPD_PARA -k stop -} diff --git a/exporters/darcs/t/lib.sh b/exporters/darcs/t/lib.sh deleted file mode 100644 index 7d2218a..0000000 --- a/exporters/darcs/t/lib.sh +++ /dev/null @@ -1,337 +0,0 @@ -export DARCS_EMAIL="user@example.com" -export GIT_PAGER=cat -export PATH="$(pwd)/..:$PATH" -pypath="/$(python -c 'from distutils import sysconfig; print sysconfig.get_python_lib()[1:]')/" - -_drrec() -{ - darcs rec --ignore-times "$@" -} - -_drrec_multiline() -{ - echo -e "`LANG= LC_ALL= date +"%a %b %d %H:%M:%S %Z %Y"` -$DARCS_EMAIL -$@" | darcs rec --ignore-times -a --pipe . -} - -_drrecamend() -{ - echo y |darcs amend-rec --ignore-times -a -} - -create_darcs() -{ - rm -rf $1 - mkdir -p $1 - cd $1 - darcs init $2 - echo A > file - darcs add file - _drrec -a -m A - cd .. - rm -rf $1.tmp - darcs get $1 $1.tmp - cd $1 - echo B > file - _drrec -a -m B - cd ../$1.tmp - echo C > file - _drrec -a -m C - cd ../$1 - darcs pull -a ../$1.tmp - echo D > file - _drrec_multiline "first line -second line -third line" - darcs tag 1.0 - echo e > file - _drrec -a -m e - echo f > file - _drrec --author="éáõû <$DARCS_EMAIL>" -a -m f - echo g > file - _drrec --author="" -a -m g - cp ../data/hungarian.gif . - darcs add hungarian.gif - _drrec -a -m "add a binary file" - rm file - echo test > file2 - darcs add file2 - _drrec -a -m "replace file with file2" - touch file3 - darcs add file3 - _drrec -a -m "add empty file" - rm file3 - _drrec -a -m "remove file" - mkdir dir dir2 - darcs add dir - darcs add dir2 - _drrec -a -m "add empty dirs" - darcs mv dir dir-p - darcs mv dir2 dir2-p - _drrec -a -m "rename empty dirs" - echo a > a - echo b > b - darcs add a b - _drrec -a -m "add a b" - rm b - _drrec -a -m "remove and rename" - darcs mv a b - _drrecamend - echo c > c - darcs add c - # empty commit message - _drrec -a -m "" - cd .. -} - -create_bzr() -{ - rm -rf $1 - mkdir -p $1 - cd $1 - bzr init $2 - echo A > file - bzr add file - bzr commit -m A - cd .. - rm -rf $1.tmp - bzr branch $1 $1.tmp - cd $1 - echo B > file - bzr commit -m B - cd ../$1.tmp - echo C > file - bzr commit -m C - cd ../$1 - bzr merge ../$1.tmp - echo D > file - bzr resolve file - echo "first line -second line -third line" | bzr commit -F /dev/stdin - bzr tag 1.0 - echo e > file - bzr commit -m e - #echo f > file - #bzr commit --author="éáõû <$DARCS_EMAIL>" -m f - #echo g > file - #_drrec --author="" -a -m g - cp ../data/hungarian.gif . - bzr add hungarian.gif - bzr commit -m "add a binary file" - rm file - echo test > file2 - bzr add file2 - bzr commit -m "replace file with file2" - touch file3 - bzr add file3 - bzr commit -m "add empty file" - rm file3 - bzr commit -m "remove file" - cd .. -} - -create_hg() -{ - rm -rf $1 - mkdir -p $1 - cd $1 - hg init $2 - echo A > file - hg add file - hg commit -m A - cd .. - rm -rf $1.tmp - hg clone $1 $1.tmp - cd $1 - echo B > file - hg commit -m B - cd ../$1.tmp - echo C > file - hg commit -m C - cd ../$1 - hg pull ../$1.tmp - hg merge - echo D > file - hg resolve -m file - echo "first line -second line -third line" | hg commit -l /dev/stdin - hg tag 1.0 - echo e > file - hg commit -m e - #echo f > file - #bzr commit --author="éáõû <$DARCS_EMAIL>" -m f - #echo g > file - #_drrec --author="" -a -m g - cp ../data/hungarian.gif . - hg add hungarian.gif - hg commit -m "add a binary file" - hg rm file - echo test > file2 - hg add file2 - hg commit -m "replace file with file2" - touch file3 - hg add file3 - hg commit -m "add empty file" - hg rm file3 - hg commit -m "remove file" - mkdir subdir - echo test > subdir/file - hg add subdir/file - hg commit -m "add subdir file" - echo test2 > subdir/file - hg commit -m "commit with weird date" -d "Fri Apr 03 12:38:26 2009 +1300" - cd .. -} -create_git() -{ - rm -rf $1 - mkdir -p $1 - cd $1 - git init $2 - git commit --allow-empty -m 'root commit' - echo A > file - git add file - git commit -a -m A - echo B > file - git commit -a -m B - git checkout -b tmp HEAD~1 - echo C > file - git commit -a -m C - git checkout master - git merge tmp - echo D > file - echo "first line -second line -third line" | git commit -a -F - - git branch -d tmp - git tag 1.0 - echo e > file - git commit -a -m e - echo f > file - git config i18n.commitencoding ISO-8859-2 - git commit --author="éáõû <$DARCS_EMAIL>" -a -m f - cp ../data/hungarian.gif . - git add hungarian.gif - git commit -a -m "add a binary file" - rm file - echo test > file2 - git add file2 - git commit -a -m "replace file with file2" - touch file3 - git add file3 - git commit -a -m "add empty file" - rm file3 - git commit -a -m "remove file" - # now add back 'file' with its old conents, so the mark gets - # reused - echo f > file - git add file - git commit -a -m "file: other -> f" - # this is a boring file for Darcs - touch foo.pyc - git add foo.pyc - git commit -a -m "boring file" - # replace an uppercase file to a lowercase one - echo SPAM > SPAM - git add SPAM - git commit -a -m SPAM - rm SPAM - echo spam > spam - git add spam - git commit -a -m "SPAM -> spam" - cd .. -} - -diff_git() -{ - rm -rf $1.git.nonbare - git clone -q $1.git $1.git.nonbare - diff --exclude _darcs --exclude .git --exclude '*-darcs-backup*' -Nur $1.git.nonbare $1 - return $? -} - -diff_importgit() -{ - test -z "`(cd $1.darcs; darcs diff)`" && - diff --exclude _darcs --exclude .git --exclude '*-darcs-backup*' -Nur $1 $1.darcs - return $? -} - -diff_importhg() -{ - cd $1.darcs && test -z "`darcs diff 2>&1`" && cd .. && - diff --exclude _darcs --exclude .hg --exclude '*-darcs-backup*' --exclude 'hg-export.*' \ - --exclude '.hgtags' --exclude '*.orig' -Nur $1 $1.darcs - return $? -} - -diff_importdarcs() -{ - cd $1.importdarcs && test -z "`darcs diff 2>&1`" && cd .. && - diff --exclude _darcs --exclude '*-darcs-backup*' -Nur $1 $2 - return $? -} - -diff_importbzr() -{ - cd $1.darcs && test -z "`darcs diff 2>&1`" && cd .. && - diff --exclude _darcs --exclude .bzr --exclude '*-darcs-backup*' -Nur $1 $1.darcs - return $? -} - -diff_bzr() -{ - cd $1.bzr/trunk - bzr update - cd - >/dev/null - diff --exclude _darcs --exclude .bzr --exclude '*-darcs-backup*' -Nur $1.bzr/trunk $1 - return $? -} - -diff_hg() -{ - hg -R $1.hg update - diff --exclude _darcs --exclude .hg --exclude '*-darcs-backup*' -Nur $1.hg $1 - return $? -} - -die() -{ - echo "fatal: $@" - exit 1 -} - -upd_file_darcs() -{ - cd $1 - echo $3 > $2 - _drrec -a -m "updated '$2' to '$3'" - cd .. -} - -upd_file_git() -{ - cd $1 - echo $3 > $2 - git commit -a -m "updated '$2' to '$3'" - cd .. -} - -upd_file_bzr() -{ - cd $1 - echo $3 > $2 - bzr commit -m "updated '$2' to '$3'" - cd .. -} - -upd_file_hg() -{ - cd $1 - echo $3 > $2 - hg commit -m "updated '$2' to '$3'" - cd .. -} diff --git a/exporters/darcs/t/test-bzr.sh b/exporters/darcs/t/test-bzr.sh deleted file mode 100644 index 479f259..0000000 --- a/exporters/darcs/t/test-bzr.sh +++ /dev/null @@ -1,16 +0,0 @@ -. ./lib.sh - -create_darcs test --old-fashioned-inventory - -rm -rf test.darcs test.bzr -mkdir test.bzr -cd test.bzr -bzr init-repo . -cd .. -if [ "$1" != "--stdout" ]; then - darcs-fast-export test |(cd test.bzr; bzr fast-import -) - diff_bzr test - exit $? -else - darcs-fast-export test -fi diff --git a/exporters/darcs/t/test-git-d2x.sh b/exporters/darcs/t/test-git-d2x.sh deleted file mode 100644 index 364edec..0000000 --- a/exporters/darcs/t/test-git-d2x.sh +++ /dev/null @@ -1,19 +0,0 @@ -. ./lib.sh - -create_darcs test --old-fashioned-inventory - -rm -rf test.git -if [ "$1" != "--stdout" ]; then - d2x -f git test - diff_git test || die "initial conversion differs" - upd_file_darcs test file2 upd_contents - d2x -f git test - diff_git test || die "update differs" - upd_file_darcs test hungarian.gif "binary to text" - d2x -f git test - diff_git test || die "update2 differs" - d2x -f git test - diff_git test || die "update3 (noop) differs" -else - darcs-fast-export test -fi diff --git a/exporters/darcs/t/test-git-incremental.sh b/exporters/darcs/t/test-git-incremental.sh deleted file mode 100644 index 1c62b9a..0000000 --- a/exporters/darcs/t/test-git-incremental.sh +++ /dev/null @@ -1,24 +0,0 @@ -. ./lib.sh - -create_darcs test --old-fashioned-inventory - -rm -rf test.darcs test.git -mkdir test.git -cd test.git -git --bare init -cd .. -if [ "$1" != "--stdout" ]; then - dmark="$(pwd)/test.dfe-marks" - gmark="$(pwd)/test.gfi-marks" - rm -f $mark $gmark - darcs-fast-export --export-marks=$dmark test |(cd test.git; git fast-import --export-marks=$gmark) - diff_git test || die "initial conversion differs" - upd_file_darcs test file2 upd_contents - darcs-fast-export --export-marks=$dmark --import-marks=$dmark test |(cd test.git; git fast-import --export-marks=$gmark --import-marks=$gmark) - diff_git test || die "update differs" - upd_file_darcs test hungarian.gif "binary to text" - darcs-fast-export --export-marks=$dmark --import-marks=$dmark test |(cd test.git; git fast-import --export-marks=$gmark --import-marks=$gmark) - diff_git test || die "update2 differs" -else - darcs-fast-export test -fi diff --git a/exporters/darcs/t/test-git-progress.sh b/exporters/darcs/t/test-git-progress.sh deleted file mode 100644 index 6586e80..0000000 --- a/exporters/darcs/t/test-git-progress.sh +++ /dev/null @@ -1,18 +0,0 @@ -. ./lib.sh - -create_darcs test --old-fashioned-inventory - -rm -rf test.darcs test.git -mkdir test.git -cd test.git -git --bare init -cd .. -if [ "$1" != "--stdout" ]; then - darcs-fast-export --progres 2 test |(cd test.git; git fast-import) - if [ $? = 0 ]; then - diff_git test - exit $? - fi -else - darcs-fast-export test -fi diff --git a/exporters/darcs/t/test-git.sh b/exporters/darcs/t/test-git.sh deleted file mode 100644 index de504ee..0000000 --- a/exporters/darcs/t/test-git.sh +++ /dev/null @@ -1,18 +0,0 @@ -. ./lib.sh - -create_darcs test --old-fashioned-inventory - -rm -rf test.darcs test.git -mkdir test.git -cd test.git -git --bare init -cd .. -if [ "$1" != "--stdout" ]; then - darcs-fast-export test |(cd test.git; git fast-import) - if [ $? = 0 ]; then - diff_git test - exit $? - fi -else - darcs-fast-export test -fi diff --git a/exporters/darcs/t/test-hg-d2x.sh b/exporters/darcs/t/test-hg-d2x.sh deleted file mode 100644 index bc83385..0000000 --- a/exporters/darcs/t/test-hg-d2x.sh +++ /dev/null @@ -1,12 +0,0 @@ -. ./lib.sh - -create_darcs test --old-fashioned-inventory - -rm -rf test.hg -if [ "$1" != "--stdout" ]; then - d2x -f hg test - diff_hg test - exit $? -else - darcs-fast-export test -fi diff --git a/exporters/darcs/t/test-hg.sh b/exporters/darcs/t/test-hg.sh deleted file mode 100644 index 95bfc4b..0000000 --- a/exporters/darcs/t/test-hg.sh +++ /dev/null @@ -1,16 +0,0 @@ -. ./lib.sh - -create_darcs test --old-fashioned-inventory - -rm -rf test.darcs test.hg -mkdir test.hg -cd test.hg -hg init -cd .. -if [ "$1" != "--stdout" ]; then - darcs-fast-export test |(cd test.hg; hg fastimport -) - diff_hg test - exit $? -else - darcs-fast-export test -fi diff --git a/exporters/darcs/t/test2-bzr-d2x.sh b/exporters/darcs/t/test2-bzr-d2x.sh deleted file mode 100644 index 13812eb..0000000 --- a/exporters/darcs/t/test2-bzr-d2x.sh +++ /dev/null @@ -1,19 +0,0 @@ -. ./lib.sh - -create_darcs test2 --darcs-2 - -rm -rf test2.bzr -if [ "$1" != "--stdout" ]; then - d2x -f bzr test2 - diff_bzr test2 || die "initial conversion differs" - upd_file_darcs test2 file2 upd_contents - d2x -f bzr test2 - diff_bzr test2 || die "update differs" - upd_file_darcs test2 hungarian.gif "binary to text" - d2x -f bzr test2 - diff_bzr test2 || die "update2 differs" - d2x -f bzr test2 - diff_bzr test2 || die "update3 (noop) differs" -else - darcs-fast-export test2 -fi diff --git a/exporters/darcs/t/test2-bzr-incremental.sh b/exporters/darcs/t/test2-bzr-incremental.sh deleted file mode 100644 index d464559..0000000 --- a/exporters/darcs/t/test2-bzr-incremental.sh +++ /dev/null @@ -1,21 +0,0 @@ -. ./lib.sh - -create_darcs test2 --darcs-2 - -rm -rf test2.darcs test2.bzr -mkdir test2.bzr -cd test2.bzr -bzr init-repo . -cd .. -if [ "$1" != "--stdout" ]; then - dmark="$(pwd)/test2.dfe-marks" - bmark="$(pwd)/test2.bfi-marks" - rm -f $mark $gmark - darcs-fast-export --export-marks=$dmark test2 |(cd test2.bzr; bzr fast-import --export-marks=$bmark -) - diff_bzr test2 || die "initial conversion differs" - upd_file_darcs test2 file2 upd_contents - darcs-fast-export --export-marks=$dmark --import-marks=$dmark test2 |(cd test2.bzr; bzr fast-import --export-marks=$bmark --import-marks=$bmark -) - diff_bzr test2 || die "update differs" -else - darcs-fast-export test2 -fi diff --git a/exporters/darcs/t/test2-git-funny-tagname.sh b/exporters/darcs/t/test2-git-funny-tagname.sh deleted file mode 100644 index 03eca66..0000000 --- a/exporters/darcs/t/test2-git-funny-tagname.sh +++ /dev/null @@ -1,25 +0,0 @@ -. ./lib.sh - -create_darcs test2 --darcs-2 -cd test2 -darcs tag "this :just (won't work; die)" -darcs tag "accent-tag-éáőű" -cd .. - -rm -rf test2.darcs test2.git -mkdir test2.git -cd test2.git -git --bare init -cd .. -if [ "$1" != "--stdout" ]; then - darcs-fast-export test2 |(cd test2.git; git fast-import) - ret=$? - if [ $ret = 0 ]; then - diff_git test2 - exit $? - else - exit $ret - fi -else - darcs-fast-export test2 -fi diff --git a/exporters/darcs/t/test2-git-http.sh b/exporters/darcs/t/test2-git-http.sh deleted file mode 100644 index 02549e4..0000000 --- a/exporters/darcs/t/test2-git-http.sh +++ /dev/null @@ -1,22 +0,0 @@ -. ./lib.sh -. ./lib-httpd.sh - -rm -rf test2.darcs test2.git httpd -create_darcs test2 --darcs-2 -mkdir -p $HTTPD_DOCUMENT_ROOT_PATH -mv -v test2 $HTTPD_DOCUMENT_ROOT_PATH -ln -s $HTTPD_DOCUMENT_ROOT_PATH/test2 . - -mkdir test2.git -cd test2.git -git --bare init -cd .. -start_httpd -darcs-fast-export $HTTPD_URL/test2 |(cd test2.git; git fast-import) -ret=$? -stop_httpd -if [ $ret != 0 ]; then - exit $ret -fi -diff_git test2 -exit $? diff --git a/exporters/darcs/t/test2-git-incremental-specworkdir.sh b/exporters/darcs/t/test2-git-incremental-specworkdir.sh deleted file mode 100644 index 83731f2..0000000 --- a/exporters/darcs/t/test2-git-incremental-specworkdir.sh +++ /dev/null @@ -1,22 +0,0 @@ -. ./lib.sh - -create_darcs test2 --darcs-2 - -rm -rf test2.darcs test2.git -mkdir test2.git -cd test2.git -git --bare init -mkdir darcs -cd .. -if [ "$1" != "--stdout" ]; then - dmark="$(pwd)/test2.git/darcs/test2.dfe-marks" - gmark="$(pwd)/test2.git/darcs/test2.gfi-marks" - rm -f $mark $gmark - darcs-fast-export --export-marks=$dmark test2 --working test2.git/darcs/repo |(cd test2.git; git fast-import --export-marks=$gmark) - diff_git test2 || die "initial conversion differs" - upd_file_darcs test2 file2 upd_contents - darcs-fast-export --export-marks=$dmark --import-marks=$dmark test2 --working test2.git/darcs/repo |(cd test2.git; git fast-import --export-marks=$gmark --import-marks=$gmark) - diff_git test2 || die "update differs" -else - darcs-fast-export test2 -fi diff --git a/exporters/darcs/t/test2-git-incremental.sh b/exporters/darcs/t/test2-git-incremental.sh deleted file mode 100644 index 41a3937..0000000 --- a/exporters/darcs/t/test2-git-incremental.sh +++ /dev/null @@ -1,21 +0,0 @@ -. ./lib.sh - -create_darcs test2 --darcs-2 - -rm -rf test2.darcs test2.git -mkdir test2.git -cd test2.git -git --bare init -cd .. -if [ "$1" != "--stdout" ]; then - dmark="$(pwd)/test2.dfe-marks" - gmark="$(pwd)/test2.gfi-marks" - rm -f $mark $gmark - darcs-fast-export --export-marks=$dmark test2 |(cd test2.git; git fast-import --export-marks=$gmark) - diff_git test2 || die "initial conversion differs" - upd_file_darcs test2 file2 upd_contents - darcs-fast-export --export-marks=$dmark --import-marks=$dmark test2 |(cd test2.git; git fast-import --export-marks=$gmark --import-marks=$gmark) - diff_git test2 || die "update differs" -else - darcs-fast-export test2 -fi diff --git a/exporters/darcs/t/test2-git.sh b/exporters/darcs/t/test2-git.sh deleted file mode 100644 index a8fc005..0000000 --- a/exporters/darcs/t/test2-git.sh +++ /dev/null @@ -1,18 +0,0 @@ -. ./lib.sh - -create_darcs test2 --darcs-2 - -rm -rf test2.darcs test2.git -mkdir test2.git -cd test2.git -git --bare init -cd .. -if [ "$1" != "--stdout" ]; then - darcs-fast-export test2 |(cd test2.git; git fast-import) - if [ $? = 0 ]; then - diff_git test2 - exit $? - fi -else - darcs-fast-export test2 -fi diff --git a/exporters/darcs/t/testimport-bzr-x2d.sh b/exporters/darcs/t/testimport-bzr-x2d.sh deleted file mode 100644 index ebe014b..0000000 --- a/exporters/darcs/t/testimport-bzr-x2d.sh +++ /dev/null @@ -1,15 +0,0 @@ -. ./lib.sh - -create_bzr test - -rm -rf test.darcs -x2d -f bzr test -diff_importbzr test || die "initial conversion differs" -upd_file_bzr test file2 upd_contents -x2d -f bzr test -diff_importbzr test || die "update differs" -upd_file_bzr test hungarian.gif "binary to text" -x2d -f bzr test -diff_importbzr test || die "update2 differs" -x2d -f bzr test -diff_importbzr test || die "update3 (noop) differs" diff --git a/exporters/darcs/t/testimport-bzr.sh b/exporters/darcs/t/testimport-bzr.sh deleted file mode 100644 index 358c5e5..0000000 --- a/exporters/darcs/t/testimport-bzr.sh +++ /dev/null @@ -1,15 +0,0 @@ -. ./lib.sh - -create_bzr test - -rm -rf test.darcs -mkdir test.darcs -cd test.darcs -darcs init -cd .. -(cd test; bzr fast-export .) | (cd test.darcs; darcs-fast-import) -if [ $? != 0 ]; then - exit 1 -fi -diff_importbzr test -exit $? diff --git a/exporters/darcs/t/testimport-copy.sh b/exporters/darcs/t/testimport-copy.sh deleted file mode 100644 index 109d87e..0000000 --- a/exporters/darcs/t/testimport-copy.sh +++ /dev/null @@ -1,26 +0,0 @@ -. ./lib.sh - -rm -rf test -mkdir test -cd test -git init -echo a > file -git add file -git commit -m a1 -cp file file2 -git add file2 -git commit -m b -cd .. - -rm -rf test.darcs -mkdir test.darcs -cd test.darcs -darcs init -cd .. -(cd test; git fast-export -C -C HEAD) > out -cat out | (cd test.darcs; darcs-fast-import) -if [ $? != 0 ]; then - exit 1 -fi -diff_importgit test -exit $? diff --git a/exporters/darcs/t/testimport-darcs.sh b/exporters/darcs/t/testimport-darcs.sh deleted file mode 100644 index 8b6d603..0000000 --- a/exporters/darcs/t/testimport-darcs.sh +++ /dev/null @@ -1,17 +0,0 @@ -. ./lib.sh - -create_darcs test2 --darcs-2 - -rm -rf test2.importdarcs test2.darcs -mkdir test2.importdarcs -cd test2.importdarcs -darcs init -cd .. - -darcs-fast-export test2 | (cd test2.importdarcs; darcs-fast-import) - -if [ $? != 0 ]; then - exit 1 -fi -diff_importdarcs test2 test2.importdarcs -exit $? diff --git a/exporters/darcs/t/testimport-deleteall.sh b/exporters/darcs/t/testimport-deleteall.sh deleted file mode 100644 index 11c5a83..0000000 --- a/exporters/darcs/t/testimport-deleteall.sh +++ /dev/null @@ -1,31 +0,0 @@ -. ./lib.sh - -rm -rf test -mkdir test -cd test -git init -echo a > file -git add file -echo A > file2 -git add file2 -git commit -m a12 -git rm file* -echo b>file3 -git add file3 -git commit -m b -cd .. - -rm -rf test.darcs -mkdir test.darcs -cd test.darcs -darcs init -cd .. -(cd test; git fast-export --progress=2 HEAD) > out -sed -i '/^D file$/d' out -sed -i 's/^D file2$/deleteall/' out -cat out | (cd test.darcs; darcs-fast-import) -if [ $? != 0 ]; then - exit 1 -fi -diff_importgit test -exit $? diff --git a/exporters/darcs/t/testimport-git-incremental.sh b/exporters/darcs/t/testimport-git-incremental.sh deleted file mode 100644 index 6c92880..0000000 --- a/exporters/darcs/t/testimport-git-incremental.sh +++ /dev/null @@ -1,16 +0,0 @@ -. ./lib.sh - -create_git test - -rm -rf test.darcs -mkdir test.darcs -cd test.darcs -darcs init -cd .. -gmark="$(pwd)/test.gfe-marks" -dmark="$(pwd)/test.dfi-marks" -(cd test; git fast-export --export-marks=$gmark HEAD) | (cd test.darcs; darcs-fast-import --export-marks=$dmark) -diff_importgit test || die "initial conversion differs" -upd_file_git test file2 upd_contents -(cd test; git fast-export --export-marks=$gmark --import-marks=$gmark HEAD) | (cd test.darcs; darcs-fast-import --export-marks=$dmark --import-marks=$dmark) -diff_importgit test || die "update differs" diff --git a/exporters/darcs/t/testimport-git-twoway-gd.sh b/exporters/darcs/t/testimport-git-twoway-gd.sh deleted file mode 100644 index 0e0c981..0000000 --- a/exporters/darcs/t/testimport-git-twoway-gd.sh +++ /dev/null @@ -1,34 +0,0 @@ -. ./lib.sh - -create_darcs test - -rm -rf test.git -mkdir test.git -cd test.git -git init -git darcs add upstream ../test -git darcs pull upstream -cd .. -diff_git test || die "initial fetch differs" -upd_file_darcs test file2 upd_contents -cd test.git -git darcs pull upstream -cd .. -diff_git test || die "fetch #1 differs" -upd_file_git test.git file2 upd_contents2 -cd test.git -git darcs push upstream -cd .. -diff_git test || die "push #1 difers" -upd_file_darcs test file2 upd_contents3 -upd_file_darcs test file2 upd_contents32 -cd test.git -git darcs pull upstream -cd .. -diff_git test || die "fetch #2 (multiple commits) differs" -upd_file_git test.git file2 upd_contents4 -upd_file_git test.git file2 upd_contents42 -cd test.git -git darcs push upstream -cd .. -diff_git test || die "push #2 (multiple commits) differs" diff --git a/exporters/darcs/t/testimport-git-twoway.sh b/exporters/darcs/t/testimport-git-twoway.sh deleted file mode 100644 index f9b515a..0000000 --- a/exporters/darcs/t/testimport-git-twoway.sh +++ /dev/null @@ -1,30 +0,0 @@ -. ./lib.sh - -create_git test - -rm -rf test.darcs -mkdir test.darcs -cd test.darcs -darcs init -cd .. -gmark="$(pwd)/test.gmarks" -dmark="$(pwd)/test.dmarks" - -(cd test; git fast-export --export-marks=$gmark HEAD) | (cd test.darcs; darcs-fast-import --export-marks=$dmark) -diff_importgit test || die "initial conversion differs" -upd_file_git test file2 upd_contents -(cd test; git fast-export --export-marks=$gmark --import-marks=$gmark HEAD) | (cd test.darcs; darcs-fast-import --export-marks=$dmark --import-marks=$dmark) -diff_importgit test || die "git -> darcs update #1 differs" -upd_file_darcs test.darcs file2 upd_contents2 -darcs-fast-export --export-marks=$dmark --import-marks=$dmark --working test/.git/darcs test.darcs | (cd test; git fast-import --export-marks=$gmark --import-marks=$gmark) -(cd test; git checkout -f) -diff_importgit test || die "darcs -> git update #2 differs" -upd_file_git test file2 upd_contents3 -upd_file_git test file2 upd_contents32 -(cd test; git fast-export --export-marks=$gmark --import-marks=$gmark HEAD) | (cd test.darcs; darcs-fast-import --export-marks=$dmark --import-marks=$dmark) -diff_importgit test || die "git -> darcs update #3 differs" -upd_file_darcs test.darcs file2 upd_contents4 -upd_file_darcs test.darcs file2 upd_contents42 -darcs-fast-export --export-marks=$dmark --import-marks=$dmark --working test/.git/darcs test.darcs | (cd test; git fast-import --export-marks=$gmark --import-marks=$gmark) -(cd test; git checkout -f) -diff_importgit test || die "darcs -> git update #4 differs" diff --git a/exporters/darcs/t/testimport-git-x2d.sh b/exporters/darcs/t/testimport-git-x2d.sh deleted file mode 100644 index f3f02a7..0000000 --- a/exporters/darcs/t/testimport-git-x2d.sh +++ /dev/null @@ -1,15 +0,0 @@ -. ./lib.sh - -create_git test - -rm -rf test.darcs -x2d -f git test -diff_importgit test || die "initial conversion differs" -upd_file_git test file2 upd_contents -x2d -f git test -diff_importgit test || die "update differs" -upd_file_git test hungarian.gif "binary to text" -x2d -f git test -diff_importgit test || die "update2 differs" -x2d -f git test -diff_importgit test || die "update3 (noop) differs" diff --git a/exporters/darcs/t/testimport-git.sh b/exporters/darcs/t/testimport-git.sh deleted file mode 100644 index 2e64e62..0000000 --- a/exporters/darcs/t/testimport-git.sh +++ /dev/null @@ -1,15 +0,0 @@ -. ./lib.sh - -create_git test - -rm -rf test.darcs -mkdir test.darcs -cd test.darcs -darcs init -cd .. -(cd test; git fast-export --progress=2 HEAD) | (cd test.darcs; darcs-fast-import) -if [ $? != 0 ]; then - exit 1 -fi -diff_importgit test -exit $? diff --git a/exporters/darcs/t/testimport-gitsymlink.sh b/exporters/darcs/t/testimport-gitsymlink.sh deleted file mode 100644 index 100c583..0000000 --- a/exporters/darcs/t/testimport-gitsymlink.sh +++ /dev/null @@ -1,45 +0,0 @@ -. ./lib.sh - -create_git test -cd test -# add two dirs with the some contents, then remove the second -# and make it a symlink to the first -mkdir dira -echo blabla > dira/file -echo blablabla > dira/file2 -mkdir dirb -touch dirb/file -touch dirb/file2 -git add dira dirb -git commit -a -m "add dira/dirb" -rm -rf dirb -ln -s dira dirb -git add dirb -git commit -a -m "change a dir to a symlink" -cd .. - -rm -rf test.darcs -mkdir test.darcs -cd test.darcs -darcs init -cd .. -(cd test; git fast-export --progress=2 HEAD) | (cd test.darcs; darcs-fast-import) -# we *do* want this to fail, but with error code 2. that means that we -# detected that symlinks are not supported and the user does not get a -# meaningless exception -if [ $? != 2 ]; then - exit 1 -fi - -# now try with the symhack option -rm -rf test.darcs -mkdir test.darcs -cd test.darcs -darcs init -cd .. -(cd test; git fast-export --progress=2 HEAD) | (cd test.darcs; darcs-fast-import --symhack) -if [ $? != 0 ]; then - exit 1 -fi -diff_importgit test -exit $? diff --git a/exporters/darcs/t/testimport-hg-x2d.sh b/exporters/darcs/t/testimport-hg-x2d.sh deleted file mode 100644 index a1d7d62..0000000 --- a/exporters/darcs/t/testimport-hg-x2d.sh +++ /dev/null @@ -1,15 +0,0 @@ -. ./lib.sh - -create_hg test - -rm -rf test.darcs -x2d -f hg test -diff_importhg test || die "initial conversion differs" -upd_file_hg test file2 upd_contents -x2d -f hg test -diff_importhg test || die "update differs" -upd_file_hg test hungarian.gif "binary to text" -x2d -f hg test -diff_importhg test || die "update2 differs" -x2d -f hg test -diff_importhg test || die "update3 (noop) differs" diff --git a/exporters/darcs/t/testimport-hg.sh b/exporters/darcs/t/testimport-hg.sh deleted file mode 100644 index 7f6d215..0000000 --- a/exporters/darcs/t/testimport-hg.sh +++ /dev/null @@ -1,15 +0,0 @@ -. ./lib.sh - -create_hg test - -rm -rf test.darcs -mkdir test.darcs -cd test.darcs -darcs init -cd .. -(cd test; $pypath/bzrlib/plugins/fastimport/exporters/hg-fast-export.py -r .) | (cd test.darcs; darcs-fast-import) -if [ $? != 0 ]; then - exit 1 -fi -diff_importhg test -exit $? diff --git a/exporters/darcs/t/testimport-rename.sh b/exporters/darcs/t/testimport-rename.sh deleted file mode 100644 index c6fa29f..0000000 --- a/exporters/darcs/t/testimport-rename.sh +++ /dev/null @@ -1,25 +0,0 @@ -. ./lib.sh - -rm -rf test -mkdir test -cd test -git init -echo a > file -git add file -git commit -m a1 -git mv file file2 -git commit -m b -cd .. - -rm -rf test.darcs -mkdir test.darcs -cd test.darcs -darcs init -cd .. -(cd test; git fast-export -M HEAD) > out -cat out | (cd test.darcs; darcs-fast-import) -if [ $? != 0 ]; then - exit 1 -fi -diff_importgit test -exit $? diff --git a/exporters/darcs/x2d b/exporters/darcs/x2d deleted file mode 100755 index ea4bdbd..0000000 --- a/exporters/darcs/x2d +++ /dev/null @@ -1,125 +0,0 @@ -#!/bin/sh -# -# x2d - convert git, bzr or hg repos to darcs using fast-export -# -# Copyright (c) 2008 by Miklos Vajna -# -# This program is free software; you can redistribute it and/or modify -# it under the terms of the GNU General Public License as published by -# the Free Software Foundation; either version 2 of the License, or -# (at your option) any later version. -# -# This program is distributed in the hope that it will be useful, -# but WITHOUT ANY WARRANTY; without even the implied warranty of -# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the -# GNU General Public License for more details. -# -# You should have received a copy of the GNU General Public License -# along with this program. If not, see . -# - -usage() -{ - echo "Usage: x2d -f format repo" -} - -die() -{ - echo "$@" - usage - exit 1 -} - -check_up_to_date() -{ - upstreamnum=$(darcs show repo|grep 'Num Patches'|sed 's/.*: //') - if [ "$upstreamnum" = "$(cd $origin; eval $*)" ]; then - echo "No remote changes to pull!" - exit 0 - fi -} - -case $1 in - -h|--help) - usage - exit 0 - ;; - -f) - format="$2" - shift 2 - ;; -esac - -[ -n "$format" ] || die "Source format is not given!" - -case $format in - git|bzr|hg) - ;; - *) - die "The requested source format is not yet supported!" - ;; -esac - -common_opts="" -while [ -n "$2" ] -do - common_opts="$common_opts $1" - shift 1 -done -origin="$1" -shift 1 - -[ -d "$origin" ] || die "Source repo does not exist!" - -# convert to abspath -cd $origin -origin=$(pwd) - -dmark="$origin.darcs/_darcs/fast-import/dfe-marks" -fmark="$origin.darcs/_darcs/fast-import/ffi-marks" - -mkdir -p $origin.darcs -cd $origin.darcs - -common_opts="$common_opts --logfile $origin.darcs/_darcs/fast-import/log" -pypath="/$(python -c 'from distutils import sysconfig; print sysconfig.get_python_lib()[1:]')/" - -if [ ! -f $dmark ]; then - darcs init - mkdir -p _darcs/fast-import - case $format in - git) - (cd $origin; git fast-export --export-marks=$fmark HEAD) | \ - darcs-fast-import --export-marks=$dmark $common_opts - ;; - bzr) - (cd $origin; bzr fast-export \ - --export-marks=$fmark . ) | darcs-fast-import --export-marks=$dmark $common_opts - ;; - hg) - (cd $origin; $pypath/bzrlib/plugins/fastimport/exporters/hg-fast-export.py -r . ) | \ - darcs-fast-import --export-marks=$dmark $common_opts - esac -else - case $format in - git) - check_up_to_date "git rev-list HEAD |wc -l" - (cd $origin; git fast-export --export-marks=$fmark --import-marks=$fmark HEAD) | \ - darcs-fast-import --export-marks=$dmark --import-marks=$dmark $common_opts - ;; - bzr) - # bzr revno is not good here, because at merges - # it produces less revision than the number we - # have in darcs - check_up_to_date "bzr log --include-merges |grep -c revno:" - (cd $origin; bzr fast-export \ - --export-marks=$fmark --import-marks=$fmark . ) | \ - darcs-fast-import --export-marks=$dmark --import-marks=$dmark $common_opts - ;; - hg) - check_up_to_date 'echo $(($(hg tip --template "{rev}")+1))' - (cd $origin; $pypath/bzrlib/plugins/fastimport/exporters/hg-fast-export.py -r . ) | \ - darcs-fast-import --export-marks=$dmark --import-marks=$dmark $common_opts - ;; - esac -fi diff --git a/exporters/darcs/x2d.txt b/exporters/darcs/x2d.txt deleted file mode 100644 index 25ed6bb..0000000 --- a/exporters/darcs/x2d.txt +++ /dev/null @@ -1,28 +0,0 @@ -= x2d(1) - -== NAME - -x2d - convert git, bzr or hg repos to a darcs one using fast-export - -== SYNOPSIS - -x2d -f [] - -== DESCRIPTION - -x2d is a wrapper script that just automates doing an initial or -continuing an incremental conversion. All it does is initializing the -target darcs repo, starting darcs-fast-import and the relevant exporter -with the proper switches and pipe the importer's output to the -importer's standard input. - -== OPTIONS - ---help:: - Display usage. - --f :: - Specify the format of the source repo. Currently supported sources are - git, bzr and hg. Incremental conversion is supported for all of them. - -The rest of the options is directly passed to darcs-fast-import. diff --git a/exporters/hg-fast-export.README b/exporters/hg-fast-export.README deleted file mode 100644 index a5999de..0000000 --- a/exporters/hg-fast-export.README +++ /dev/null @@ -1,54 +0,0 @@ -hg-fast-import.py - mercurial to bzr converter using bzr fast-import - -Legal -===== - -Most hg-* scripts are licensed under the MIT license[0] and were written -by Rocco Rutte with hints and help from the git list and -#mercurial on freenode. hg-fast-export[1] was integrated into -bzr-fastimport by Ian Clatworthy with permission from Rocco. - -The current maintainer is Frej Drejhammar . - -Usage -===== - -Using hg-fast-export is quite simple for a mercurial repository : - - bzr init-repo foo.bzr - cd foo.bzr - hg-fast-import.py -r | bzr fast-import - - -Notes/Limitations -================= - -hg-fast-import supports multiple branches but only named branches with exactly -one head each. Otherwise commits to the tip of these heads within branch -will get flattened into merge commits. - -The way the hg API and remote access protocol is designed it is not -possible to use hg-fast-export on remote repositories -(http/ssh). First clone the repository, then convert it. - -Design -====== - -hg-fast-import.py was designed in a way that doesn't require a 2-pass mechanism -or any prior repository analysis: if just outputs what it finds. -This also implies that it heavily relies on strictly -linear ordering of changesets from hg, i.e. its append-only storage -model so that changesets hg-fast-import already saw never get modified. - -Todo -==== - -Test incremental imports, particularly handling of branches and tags. - -For one-time conversions, everything should be fine. - -Footnotes -========= - -[0] http://www.opensource.org/licenses/mit-license.php - -[1] http://repo.or.cz/w/fast-export.git diff --git a/exporters/hg-fast-export.py b/exporters/hg-fast-export.py deleted file mode 100755 index 45c9ab4..0000000 --- a/exporters/hg-fast-export.py +++ /dev/null @@ -1,442 +0,0 @@ -#!/usr/bin/env python - -# Copyright (c) 2007, 2008 Rocco Rutte and others. -# License: MIT - -from mercurial import repo,hg,cmdutil,util,ui,revlog,node -from hg2git import setup_repo,fixup_user,get_branch,get_changeset -from hg2git import load_cache,save_cache,get_git_sha1,set_default_branch,set_origin_name -from tempfile import mkstemp -from optparse import OptionParser -import re -import sys -import os - -# silly regex to catch Signed-off-by lines in log message -sob_re=re.compile('^Signed-[Oo]ff-[Bb]y: (.+)$') -# insert 'checkpoint' command after this many commits or none at all if 0 -cfg_checkpoint_count=0 -# write some progress message every this many file contents written -cfg_export_boundary=1000 - -def gitmode(flags): - return 'l' in flags and '120000' or 'x' in flags and '100755' or '100644' - -def wr(msg=''): - if msg == None: - msg = '' - print msg - #map(lambda x: sys.stderr.write('\t[%s]\n' % x),msg.split('\n')) - -def checkpoint(count): - count=count+1 - if cfg_checkpoint_count>0 and count%cfg_checkpoint_count==0: - sys.stderr.write("Checkpoint after %d commits\n" % count) - wr('checkpoint') - wr() - return count - -def get_parent_mark(parent,marks): - """Get the mark for some parent. - If we saw it in the current session, return :%d syntax and - otherwise the SHA1 from the cache.""" - return marks.get(str(parent),':%d' % (parent+1)) - -def file_mismatch(f1,f2): - """See if two revisions of a file are not equal.""" - return node.hex(f1)!=node.hex(f2) - -def split_dict(dleft,dright,l=[],c=[],r=[],match=file_mismatch): - """Loop over our repository and find all changed and missing files.""" - for left in dleft.keys(): - right=dright.get(left,None) - if right==None: - # we have the file but our parent hasn't: add to left set - l.append(left) - elif match(dleft[left],right): - # we have it but checksums mismatch: add to center set - c.append(left) - for right in dright.keys(): - left=dleft.get(right,None) - if left==None: - # if parent has file but we don't: add to right set - r.append(right) - # change is already handled when comparing child against parent - return l,c,r - -def get_filechanges(repo,revision,parents,mleft): - """Given some repository and revision, find all changed/deleted files.""" - l,c,r=[],[],[] - for p in parents: - if p<0: continue - mright=repo.changectx(p).manifest() - l,c,r=split_dict(mleft,mright,l,c,r) - l.sort() - c.sort() - r.sort() - return l,c,r - -def get_author(logmessage,committer,authors): - """As git distincts between author and committer of a patch, try to - extract author by detecting Signed-off-by lines. - - This walks from the end of the log message towards the top skipping - empty lines. Upon the first non-empty line, it walks all Signed-off-by - lines upwards to find the first one. For that (if found), it extracts - authorship information the usual way (authors table, cleaning, etc.) - - If no Signed-off-by line is found, this defaults to the committer. - - This may sound stupid (and it somehow is), but in log messages we - accidentially may have lines in the middle starting with - "Signed-off-by: foo" and thus matching our detection regex. Prevent - that.""" - - loglines=logmessage.split('\n') - i=len(loglines) - # from tail walk to top skipping empty lines - while i>=0: - i-=1 - if len(loglines[i].strip())==0: continue - break - if i>=0: - # walk further upwards to find first sob line, store in 'first' - first=None - while i>=0: - m=sob_re.match(loglines[i]) - if m==None: break - first=m - i-=1 - # if the last non-empty line matches our Signed-Off-by regex: extract username - if first!=None: - r=fixup_user(first.group(1),authors) - return r - return committer - -def export_file_contents(ctx,manifest,files): - count=0 - max=len(files) - for file in files: - # Skip .hgtags files. They only get us in trouble. - if file == ".hgtags": - sys.stderr.write('Skip %s\n' % (file)) - continue - d=ctx.filectx(file).data() - wr('M %s inline %s' % (gitmode(manifest.flags(file)),file)) - wr('data %d' % len(d)) # had some trouble with size() - wr(d) - count+=1 - if count%cfg_export_boundary==0: - sys.stderr.write('Exported %d/%d files\n' % (count,max)) - if max>cfg_export_boundary: - sys.stderr.write('Exported %d/%d files\n' % (count,max)) - -def is_merge(parents): - c=0 - for parent in parents: - if parent>=0: - c+=1 - return c>1 - -def sanitize_name(name,what="branch"): - """Sanitize input roughly according to git-check-ref-format(1)""" - - def dot(name): - if name[0] == '.': return '_'+name[1:] - return name - - n=name - p=re.compile('([[ ~^:?*]|\.\.)') - n=p.sub('_', n) - if n[-1] == '/': n=n[:-1]+'_' - n='/'.join(map(dot,n.split('/'))) - p=re.compile('_+') - n=p.sub('_', n) - - if n!=name: - sys.stderr.write('Warning: sanitized %s [%s] to [%s]\n' % (what,name,n)) - return n - -def export_commit(ui,repo,revision,marks,mapping,heads,last,max,count,authors,sob,brmap): - def get_branchname(name): - if brmap.has_key(name): - return brmap[name] - n=sanitize_name(name) - brmap[name]=n - return n - - (revnode,_,user,(time,timezone),files,desc,branch,_)=get_changeset(ui,repo,revision,authors) - parents=repo.changelog.parentrevs(revision) - - branch=get_branchname(branch) - - wr('commit refs/heads/%s' % branch) - wr('mark :%d' % (revision+1)) - if sob: - wr('author %s %d %s' % (get_author(desc,user,authors),time,timezone)) - wr('committer %s %d %s' % (user,time,timezone)) - wr('data %d' % (len(desc)+1)) # wtf? - wr(desc) - wr() - - pidx1, pidx2 = 0, 1 - if parents[1] > 0: - if parents[0] <= 0 or \ - repo.changelog.node(parents[0]) < repo.changelog.node(parents[1]): - pidx1, pidx2 = 1, 0 - - full_rev=False - if revision==0: full_rev=True - - src=heads.get(branch,'') - link='' - if src!='': - # if we have a cached head, this is an incremental import: initialize it - # and kill reference so we won't init it again - wr('from %s' % src) - heads[branch]='' - sys.stderr.write('%s: Initializing to parent [%s]\n' % - (branch,src)) - link=src # avoid making a merge commit for incremental import - elif link=='' and not heads.has_key(branch) and revision>0: - if parents[0]>=0: - # newly created branch with parent: connect to parent - tmp=get_parent_mark(parents[0],marks) - wr('from %s' % tmp) - sys.stderr.write('%s: Link new branch to parent [%s]\n' % - (branch,tmp)) - link=tmp # avoid making a merge commit for branch fork - else: - # newly created branch without parent: feed full revision - full_rev=True - elif last.get(branch,revision) != parents[pidx1] and parents[pidx1] > 0 and revision > 0: - pm=get_parent_mark(parents[pidx1],marks) - sys.stderr.write('%s: Placing commit [r%d] in branch [%s] on top of [r%d]\n' % - (branch,revision,branch,parents[pidx1])); - wr('from %s' % pm) - - if parents[pidx2] > 0: - pm=get_parent_mark(parents[pidx2],marks) - sys.stderr.write('%s: Merging with parent [%s] from [r%d]\n' % - (branch,pm,parents[pidx2])) - wr('merge %s' % pm) - - last[branch]=revision - heads[branch]='' - # we need this later to write out tags - marks[str(revision)]=':%d'%(revision+1) - - ctx=repo.changectx(str(revision)) - man=ctx.manifest() - added,changed,removed,type=[],[],[],'' - - if full_rev: - # first revision: feed in full manifest - added=man.keys() - added.sort() - type='full' - elif is_merge(parents): - # later merge revision: feed in changed manifest - # for many files comparing checksums is expensive so only do it for - # merges where we really need it due to hg's revlog logic - added,changed,removed=get_filechanges(repo,revision,parents,man) - type='thorough delta' - else: - # later non-merge revision: feed in changed manifest - # if we have exactly one parent, just take the changes from the - # manifest without expensively comparing checksums - f=repo.status(repo.lookup(parents[0]),revnode)[:3] - added,changed,removed=f[1],f[0],f[2] - type='simple delta' - - sys.stderr.write('%s: Exporting %s revision %d/%d with %d/%d/%d added/changed/removed files\n' % - (branch,type,revision+1,max,len(added),len(changed),len(removed))) - - map(lambda r: wr('D %s' % r),removed) - export_file_contents(ctx,man,added) - export_file_contents(ctx,man,changed) - wr() - - return checkpoint(count) - -def export_tags(ui,repo,marks_cache,mapping_cache,count,authors): - l=repo.tagslist() - for tag,node in l: - tag=sanitize_name(tag,"tag") - # ignore latest revision - if tag=='tip': continue - # ignore tags to nodes that are missing (ie, 'in the future') - if node.encode('hex_codec') not in mapping_cache: - sys.stderr.write('Tag %s refers to unseen node %s\n' % (tag, node.encode('hex_codec'))) - continue - - rev=int(mapping_cache[node.encode('hex_codec')]) - - ref=marks_cache.get(str(rev),':%d' % (rev)) - if ref==None: - sys.stderr.write('Failed to find reference for creating tag' - ' %s at r%d\n' % (tag,rev)) - continue - sys.stderr.write('Exporting tag [%s] at [hg r%d] [git %s]\n' % (tag,rev,ref)) - wr('reset refs/tags/%s' % tag) - wr('from %s' % ref) - wr() - count=checkpoint(count) - return count - -def load_authors(filename): - cache={} - if not os.path.exists(filename): - return cache - f=open(filename,'r') - l=0 - lre=re.compile('^([^=]+)[ ]*=[ ]*(.+)$') - for line in f.readlines(): - l+=1 - m=lre.match(line) - if m==None: - sys.stderr.write('Invalid file format in [%s], line %d\n' % (filename,l)) - continue - # put key:value in cache, key without ^: - cache[m.group(1).strip()]=m.group(2).strip() - f.close() - sys.stderr.write('Loaded %d authors\n' % l) - return cache - -def verify_heads(ui,repo,cache,force): - branches=repo.branchtags() - l=[(-repo.changelog.rev(n), n, t) for t, n in branches.items()] - l.sort() - - # get list of hg's branches to verify, don't take all git has - for _,_,b in l: - b=get_branch(b) - sha1=get_git_sha1(b) - c=cache.get(b) - if sha1!=None and c!=None: - sys.stderr.write('Verifying branch [%s]\n' % b) - if sha1!=c: - sys.stderr.write('Error: Branch [%s] modified outside hg-fast-export:' - '\n%s (repo) != %s (cache)\n' % (b,sha1,c)) - if not force: return False - - # verify that branch has exactly one head - t={} - for h in repo.heads(): - (_,_,_,_,_,_,branch,_)=get_changeset(ui,repo,h) - if t.get(branch,False): - sys.stderr.write('Error: repository has at least one unnamed head: hg r%s\n' % - repo.changelog.rev(h)) - if not force: return False - t[branch]=True - - return True - -def mangle_mark(mark): - return str(int(mark)-1) - -def hg2git(repourl,m,marksfile,mappingfile,headsfile,tipfile,authors={},sob=False,force=False): - _max=int(m) - - try: - import msvcrt - msvcrt.setmode(sys.stdout.fileno(), os.O_BINARY) - except ImportError: - pass - - marks_cache=load_cache(marksfile,mangle_mark) - mapping_cache=load_cache(mappingfile) - heads_cache=load_cache(headsfile) - state_cache=load_cache(tipfile) - - ui,repo=setup_repo(repourl) - - if not verify_heads(ui,repo,heads_cache,force): - return 1 - - try: - tip=repo.changelog.count() - except AttributeError: - tip=len(repo) - - min=int(state_cache.get('tip',0)) - max=_max - if _max<0 or max>tip: - max=tip - - for rev in range(0,max): - (revnode,_,_,_,_,_,_,_)=get_changeset(ui,repo,rev,authors) - mapping_cache[revnode.encode('hex_codec')] = str(rev) - - - c=0 - last={} - brmap={} - for rev in range(min,max): - c=export_commit(ui,repo,rev,marks_cache,mapping_cache,heads_cache,last,max,c,authors,sob,brmap) - - state_cache['tip']=max - state_cache['repo']=repourl - save_cache(tipfile,state_cache) - save_cache(mappingfile,mapping_cache) - - c=export_tags(ui,repo,marks_cache,mapping_cache,c,authors) - - sys.stderr.write('Issued %d commands\n' % c) - - return 0 - -if __name__=='__main__': - def bail(parser,opt): - sys.stderr.write('Error: No %s option given\n' % opt) - parser.print_help() - sys.exit(2) - - parser=OptionParser() - - parser.add_option("-m","--max",type="int",dest="max", - help="Maximum hg revision to import") - parser.add_option("--mapping",dest="mappingfile", - help="File to read last run's hg-to-git SHA1 mapping") - parser.add_option("--marks",dest="marksfile", - help="File to read git-fast-import's marks from") - parser.add_option("--heads",dest="headsfile", - help="File to read last run's git heads from") - parser.add_option("--status",dest="statusfile", - help="File to read status from") - parser.add_option("-r","--repo",dest="repourl", - help="URL of repo to import") - parser.add_option("-s",action="store_true",dest="sob", - default=False,help="Enable parsing Signed-off-by lines") - parser.add_option("-A","--authors",dest="authorfile", - help="Read authormap from AUTHORFILE") - parser.add_option("-f","--force",action="store_true",dest="force", - default=False,help="Ignore validation errors by force") - parser.add_option("-M","--default-branch",dest="default_branch", - help="Set the default branch") - parser.add_option("-o","--origin",dest="origin_name", - help="use as namespace to track upstream") - - (options,args)=parser.parse_args() - - m=-1 - if options.max!=None: m=options.max - - if options.marksfile==None: options.marksfile = 'hg-export.marks' - if options.mappingfile==None: options.mappingfile = 'hg-export.mapping' - if options.headsfile==None: options.headsfile = 'hg-export.heads' - if options.statusfile==None: options.statusfile = 'hg-export.status' - if options.repourl==None: bail(parser,'--repo') - - a={} - if options.authorfile!=None: - a=load_authors(options.authorfile) - - if options.default_branch!=None: - set_default_branch(options.default_branch) - - if options.origin_name!=None: - set_origin_name(options.origin_name) - - sys.exit(hg2git(options.repourl,m,options.marksfile,options.mappingfile,options.headsfile, - options.statusfile,authors=a,sob=options.sob,force=options.force)) diff --git a/exporters/hg-fast-export.sh b/exporters/hg-fast-export.sh deleted file mode 100755 index a2ef9ea..0000000 --- a/exporters/hg-fast-export.sh +++ /dev/null @@ -1,100 +0,0 @@ -#!/bin/sh - -# Copyright (c) 2007, 2008 Rocco Rutte and others. -# License: MIT - -ROOT="`dirname $0`" -REPO="" -PFX="hg2git" -SFX_MAPPING="mapping" -SFX_MARKS="marks" -SFX_HEADS="heads" -SFX_STATE="state" -QUIET="" -PYTHON=${PYTHON:-python} - -USAGE="[--quiet] [-r ] [-m ] [-s] [-A ] [-M ] [-o ]" -LONG_USAGE="Import hg repository up to either tip or -If is omitted, use last hg repository as obtained from state file, -GIT_DIR/$PFX-$SFX_STATE by default. - -Note: The argument order matters. - -Options: - -m Maximum revision to import - --quiet Passed to git-fast-import(1) - -s Enable parsing Signed-off-by lines - -A Read author map from file - (Same as in git-svnimport(1) and git-cvsimport(1)) - -r Mercurial repository to import - -M Set the default branch name (default to 'master') - -o Use as branch namespace to track upstream (eg 'origin') -" - -. "$(git --exec-path)/git-sh-setup" -cd_to_toplevel - -while case "$#" in 0) break ;; esac -do - case "$1" in - -r|--r|--re|--rep|--repo) - shift - REPO="$1" - ;; - --q|--qu|--qui|--quie|--quiet) - QUIET="--quiet" - ;; - -*) - # pass any other options down to hg2git.py - break - ;; - *) - break - ;; - esac - shift -done - -# for convenience: get default repo from state file -if [ x"$REPO" = x -a -f "$GIT_DIR/$PFX-$SFX_STATE" ] ; then - REPO="`egrep '^:repo ' "$GIT_DIR/$PFX-$SFX_STATE" | cut -d ' ' -f 2`" - echo "Using last hg repository \"$REPO\"" -fi - -# make sure we have a marks cache -if [ ! -f "$GIT_DIR/$PFX-$SFX_MARKS" ] ; then - touch "$GIT_DIR/$PFX-$SFX_MARKS" -fi - -GIT_DIR="$GIT_DIR" $PYTHON "$ROOT/hg-fast-export.py" \ - --repo "$REPO" \ - --marks "$GIT_DIR/$PFX-$SFX_MARKS" \ - --mapping "$GIT_DIR/$PFX-$SFX_MAPPING" \ - --heads "$GIT_DIR/$PFX-$SFX_HEADS" \ - --status "$GIT_DIR/$PFX-$SFX_STATE" \ - "$@" \ -| git fast-import $QUIET --export-marks="$GIT_DIR/$PFX-$SFX_MARKS.tmp" - -# move recent marks cache out of the way... -if [ -f "$GIT_DIR/$PFX-$SFX_MARKS" ] ; then - mv "$GIT_DIR/$PFX-$SFX_MARKS" "$GIT_DIR/$PFX-$SFX_MARKS.old" -else - touch "$GIT_DIR/$PFX-$SFX_MARKS.old" -fi - -# ...to create a new merged one -cat "$GIT_DIR/$PFX-$SFX_MARKS.old" "$GIT_DIR/$PFX-$SFX_MARKS.tmp" \ -| uniq > "$GIT_DIR/$PFX-$SFX_MARKS" - -# cleanup -rm -rf "$GIT_DIR/$PFX-$SFX_MARKS.old" "$GIT_DIR/$PFX-$SFX_MARKS.tmp" - -# save SHA1s of current heads for incremental imports -# and connectivity (plus sanity checking) -for head in `git branch | sed 's#^..##'` ; do - id="`git rev-parse $head`" - echo ":$head $id" -done > "$GIT_DIR/$PFX-$SFX_HEADS" - -# check diff with color: -# ( for i in `find . -type f | grep -v '\.git'` ; do diff -u $i $REPO/$i ; done | cdiff ) | less -r diff --git a/exporters/hg2git.py b/exporters/hg2git.py deleted file mode 100755 index e342834..0000000 --- a/exporters/hg2git.py +++ /dev/null @@ -1,112 +0,0 @@ - -# Copyright (c) 2007, 2008 Rocco Rutte and others. -# License: MIT - -from mercurial import repo,hg,cmdutil,util,ui,revlog,node -import re -import os -import sys - -# default git branch name -cfg_master='master' -# default origin name -origin_name='' -# silly regex to see if user field has email address -user_re=re.compile('([^<]+) (<[^>]+>)$') -# silly regex to clean out user names -user_clean_re=re.compile('^["]([^"]+)["]$') - -def set_default_branch(name): - global cfg_master - cfg_master = name - -def set_origin_name(name): - global origin_name - origin_name = name - -def setup_repo(url): - try: - myui=ui.ui(interactive=False) - except TypeError: - myui=ui.ui() - myui.setconfig('ui', 'interactive', 'off') - return myui,hg.repository(myui,url) - -def fixup_user(user,authors): - if authors!=None: - # if we have an authors table, try to get mapping - # by defaulting to the current value of 'user' - user=authors.get(user,user) - name,mail,m='','',user_re.match(user) - if m==None: - # if we don't have 'Name ' syntax, use 'user - # ' if use contains no at and - # 'user ' otherwise - name=user - if '@' not in user: - mail='' - else: - mail='<%s>' % user - else: - # if we have 'Name ' syntax, everything is fine :) - name,mail=m.group(1),m.group(2) - - # remove any silly quoting from username - m2=user_clean_re.match(name) - if m2!=None: - name=m2.group(1) - return '%s %s' % (name,mail) - -def get_branch(name): - # 'HEAD' is the result of a bug in mutt's cvs->hg conversion, - # other CVS imports may need it, too - if name=='HEAD' or name=='default' or name=='': - name=cfg_master - if origin_name: - return origin_name + '/' + name - return name - -def get_changeset(ui,repo,revision,authors={}): - node=repo.lookup(revision) - (manifest,user,(time,timezone),files,desc,extra)=repo.changelog.read(node) - tz="%+03d%02d" % (-timezone / 3600, ((-timezone % 3600) / 60)) - branch=get_branch(extra.get('branch','master')) - return (node,manifest,fixup_user(user,authors),(time,tz),files,desc,branch,extra) - -def mangle_key(key): - return key - -def load_cache(filename,get_key=mangle_key): - cache={} - if not os.path.exists(filename): - return cache - f=open(filename,'r') - l=0 - for line in f.readlines(): - l+=1 - fields=line.split(' ') - if fields==None or not len(fields)==2 or fields[0][0]!=':': - sys.stderr.write('Invalid file format in [%s], line %d\n' % (filename,l)) - continue - # put key:value in cache, key without ^: - cache[get_key(fields[0][1:])]=fields[1].split('\n')[0] - f.close() - return cache - -def save_cache(filename,cache): - f=open(filename,'w+') - map(lambda x: f.write(':%s %s\n' % (str(x),str(cache.get(x)))),cache.keys()) - f.close() - -def get_git_sha1(name,type='heads'): - try: - # use git-rev-parse to support packed refs - cmd="GIT_DIR='%s' git rev-parse --verify refs/%s/%s 2>/dev/null" % (os.getenv('GIT_DIR','/dev/null'),type,name) - p=os.popen(cmd) - l=p.readline() - p.close() - if l == None or len(l) == 0: - return None - return l[0:40] - except IOError: - return None diff --git a/exporters/svn-archive.c b/exporters/svn-archive.c deleted file mode 100644 index 6632d19..0000000 --- a/exporters/svn-archive.c +++ /dev/null @@ -1,240 +0,0 @@ -/* - * svn-archive.c - * ---------- - * Walk through a given revision of a local Subversion repository and export - * all of the contents as a tarfile. - * - * Author: Chris Lee - * License: MIT - */ - -#define _XOPEN_SOURCE -#include -#include -#include -#include - -#ifndef PATH_MAX -#define PATH_MAX 4096 -#endif - -#include -#include -#include -#include - -#include -#include -#include -#include - -#undef SVN_ERR -#define SVN_ERR(expr) SVN_INT_ERR(expr) -#define apr_sane_push(arr, contents) *(char **)apr_array_push(arr) = contents - -#define TRUNK "/trunk" - -static time_t archive_time; - -time_t get_epoch(char *svn_date) -{ - struct tm tm = {0}; - char *date = malloc(strlen(svn_date) * sizeof(char *)); - strncpy(date, svn_date, strlen(svn_date) - 8); - strptime(date, "%Y-%m-%dT%H:%M:%S", &tm); - free(date); - return mktime(&tm); -} - -int tar_header(apr_pool_t *pool, char *path, char *node, size_t f_size) -{ - char buf[512]; - unsigned int i, checksum; - svn_boolean_t is_dir; - - memset(buf, 0, sizeof(buf)); - - if ((strlen(path) == 0) && (strlen(node) == 0)) { - return 0; - } - - if (strlen(node) == 0) { - is_dir = 1; - } else { - is_dir = 0; - } - - if (strlen(path) == 0) { - strncpy(buf, apr_psprintf(pool, "%s", node), 99); - } else if (strlen(path) + strlen(node) < 100) { - strncpy(buf, apr_psprintf(pool, "%s/%s", path+1, node), 99); - } else { - fprintf(stderr, "really long file path...\n"); - strncpy(&buf[0], node, 99); - strncpy(&buf[345], path+1, 154); - } - - strncpy(&buf[100], apr_psprintf(pool, "%07o", (is_dir ? 0755 : 0644)), 7); - strncpy(&buf[108], apr_psprintf(pool, "%07o", 1000), 7); - strncpy(&buf[116], apr_psprintf(pool, "%07o", 1000), 7); - strncpy(&buf[124], apr_psprintf(pool, "%011lo", f_size), 11); - strncpy(&buf[136], apr_psprintf(pool, "%011lo", archive_time), 11); - strncpy(&buf[156], (is_dir ? "5" : "0"), 1); - strncpy(&buf[257], "ustar ", 8); - strncpy(&buf[265], "clee", 31); - strncpy(&buf[297], "clee", 31); - // strncpy(&buf[329], apr_psprintf(pool, "%07o", 0), 7); - // strncpy(&buf[337], apr_psprintf(pool, "%07o", 0), 7); - - strncpy(&buf[148], " ", 8); - checksum = 0; - for (i = 0; i < sizeof(buf); i++) { - checksum += buf[i]; - } - strncpy(&buf[148], apr_psprintf(pool, "%07o", checksum & 0x1fffff), 7); - - fwrite(buf, sizeof(char), sizeof(buf), stdout); - - return 0; -} - -int tar_footer() -{ - char block[1024]; - memset(block, 0, sizeof(block)); - fwrite(block, sizeof(char), sizeof(block), stdout); -} - -int dump_blob(svn_fs_root_t *root, char *prefix, char *path, char *node, apr_pool_t *pool) -{ - char *full_path, buf[512]; - apr_size_t len; - svn_stream_t *stream; - svn_filesize_t stream_length; - - full_path = apr_psprintf(pool, "%s%s/%s", prefix, path, node); - - SVN_ERR(svn_fs_file_length(&stream_length, root, full_path, pool)); - SVN_ERR(svn_fs_file_contents(&stream, root, full_path, pool)); - - tar_header(pool, path, node, stream_length); - - do { - len = sizeof(buf); - memset(buf, '\0', sizeof(buf)); - SVN_ERR(svn_stream_read(stream, buf, &len)); - fwrite(buf, sizeof(char), sizeof(buf), stdout); - } while (len == sizeof(buf)); - - return 0; -} - -int dump_tree(svn_fs_root_t *root, char *prefix, char *path, apr_pool_t *pool) -{ - const void *key; - void *val; - char *node, *subpath, *full_path; - - apr_pool_t *subpool; - apr_hash_t *dir_entries; - apr_hash_index_t *i; - - svn_boolean_t is_dir; - - tar_header(pool, path, "", 0); - - SVN_ERR(svn_fs_dir_entries(&dir_entries, root, apr_psprintf(pool, "%s/%s", prefix, path), pool)); - - subpool = svn_pool_create(pool); - - for (i = apr_hash_first(pool, dir_entries); i; i = apr_hash_next(i)) { - svn_pool_clear(subpool); - apr_hash_this(i, &key, NULL, &val); - node = (char *)key; - - subpath = apr_psprintf(subpool, "%s/%s", path, node); - full_path = apr_psprintf(subpool, "%s%s", prefix, subpath); - - svn_fs_is_dir(&is_dir, root, full_path, subpool); - - if (is_dir) { - dump_tree(root, prefix, subpath, subpool); - } else { - dump_blob(root, prefix, path, node, subpool); - } - } - - svn_pool_destroy(subpool); - - return 0; -} - -int crawl_filesystem(char *repos_path, char *root_path, apr_pool_t *pool) -{ - char *path; - - apr_hash_t *props; - apr_hash_index_t *i; - - svn_repos_t *repos; - svn_fs_t *fs; - svn_string_t *svndate; - svn_revnum_t youngest_rev, export_rev; - svn_fs_root_t *fs_root; - - SVN_ERR(svn_fs_initialize(pool)); - SVN_ERR(svn_repos_open(&repos, repos_path, pool)); - if ((fs = svn_repos_fs(repos)) == NULL) - return -1; - SVN_ERR(svn_fs_youngest_rev(&youngest_rev, fs, pool)); - - export_rev = youngest_rev; - - SVN_ERR(svn_fs_revision_root(&fs_root, fs, export_rev, pool)); - SVN_ERR(svn_fs_revision_proplist(&props, fs, export_rev, pool)); - - svndate = apr_hash_get(props, "svn:date", APR_HASH_KEY_STRING); - archive_time = get_epoch((char *)svndate->data); - - fprintf(stderr, "Exporting archive of r%ld... \n", export_rev); - - dump_tree(fs_root, root_path, "", pool); - - tar_footer(); - - fprintf(stderr, "done!\n"); - - return 0; -} - -int main(int argc, char *argv[]) -{ - apr_pool_t *pool; - apr_getopt_t *options; - - apr_getopt_option_t long_options[] = { - { "help", 'h', 0 }, - { "prefix", 'p', 0 }, - { "basename", 'b', 0 }, - { "revision", 'r', 0 }, - { NULL, 0, 0 } - }; - - if (argc < 2) { - fprintf(stderr, "usage: %s REPOS_PATH [prefix]\n", argv[0]); - return -1; - } - - if (apr_initialize() != APR_SUCCESS) { - fprintf(stderr, "You lose at apr_initialize().\n"); - return -1; - } - - pool = svn_pool_create(NULL); - - crawl_filesystem(argv[1], (argc == 3 ? argv[2] : TRUNK), pool); - - apr_terminate(); - - return 0; -} diff --git a/exporters/svn-fast-export.README b/exporters/svn-fast-export.README deleted file mode 100644 index e08277e..0000000 --- a/exporters/svn-fast-export.README +++ /dev/null @@ -1,12 +0,0 @@ -To compile svn-fast-export.c, use make. You'll need to install -some packages first using the package manager on your OS: - -* libsvn-dev - the Subversion libraries -* libapr1-dev - the Apache Portable Runtime libraries - -Note: If someone with good knowledge of the Subversion -Python bindings could rewrite svn-fast-export.py so that -https://bugs.launchpad.net/bzr-fastimport/+bug/273361 -went away, then there would be much rejoicing throughout -the land and the need for svn-fast-export.c would largely -disappear. diff --git a/exporters/svn-fast-export.c b/exporters/svn-fast-export.c deleted file mode 100644 index 34e7fc6..0000000 --- a/exporters/svn-fast-export.c +++ /dev/null @@ -1,187 +0,0 @@ -/* - * svn-fast-export.c - * ---------- - * Walk through each revision of a local Subversion repository and export it - * in a stream that git-fast-import can consume. - * - * Author: Chris Lee - * License: MIT - */ - -#define _XOPEN_SOURCE -#include -#include -#include -#include - -#ifndef PATH_MAX -#define PATH_MAX 4096 -#endif - -#include -#include -#include - -#include -#include -#include -#include - -#undef SVN_ERR -#define SVN_ERR(expr) SVN_INT_ERR(expr) -#define apr_sane_push(arr, contents) *(char **)apr_array_push(arr) = contents - -#define TRUNK "/trunk/" - -time_t get_epoch(char *svn_date) -{ - struct tm tm = {0}; - char *date = malloc(strlen(svn_date) * sizeof(char *)); - strncpy(date, svn_date, strlen(svn_date) - 8); - strptime(date, "%Y-%m-%dT%H:%M:%S", &tm); - free(date); - return mktime(&tm); -} - -int dump_blob(svn_fs_root_t *root, char *full_path, apr_pool_t *pool) -{ - apr_size_t len; - svn_stream_t *stream, *outstream; - svn_filesize_t stream_length; - - SVN_ERR(svn_fs_file_length(&stream_length, root, full_path, pool)); - SVN_ERR(svn_fs_file_contents(&stream, root, full_path, pool)); - - fprintf(stdout, "data %lu\n", stream_length); - fflush(stdout); - - SVN_ERR(svn_stream_for_stdout(&outstream, pool)); - SVN_ERR(svn_stream_copy(stream, outstream, pool)); - - fprintf(stdout, "\n"); - fflush(stdout); - - return 0; -} - -int export_revision(svn_revnum_t rev, svn_fs_t *fs, apr_pool_t *pool) -{ - unsigned int mark; - const void *key; - void *val; - char *path, *file_change; - apr_pool_t *revpool; - apr_hash_t *changes, *props; - apr_hash_index_t *i; - apr_array_header_t *file_changes; - svn_string_t *author, *committer, *svndate, *svnlog; - svn_boolean_t is_dir; - svn_fs_root_t *fs_root; - svn_fs_path_change_t *change; - - fprintf(stderr, "Exporting revision %ld... ", rev); - - SVN_ERR(svn_fs_revision_root(&fs_root, fs, rev, pool)); - SVN_ERR(svn_fs_paths_changed(&changes, fs_root, pool)); - SVN_ERR(svn_fs_revision_proplist(&props, fs, rev, pool)); - - revpool = svn_pool_create(pool); - - file_changes = apr_array_make(pool, apr_hash_count(changes), sizeof(char *)); - mark = 1; - for (i = apr_hash_first(pool, changes); i; i = apr_hash_next(i)) { - svn_pool_clear(revpool); - apr_hash_this(i, &key, NULL, &val); - path = (char *)key; - change = (svn_fs_path_change_t *)val; - - SVN_ERR(svn_fs_is_dir(&is_dir, fs_root, path, revpool)); - - if (is_dir || strncmp(TRUNK, path, strlen(TRUNK))) { - continue; - } - - if (change->change_kind == svn_fs_path_change_delete) { - apr_sane_push(file_changes, (char *)svn_string_createf(pool, "D %s", path + strlen(TRUNK))->data); - } else { - apr_sane_push(file_changes, (char *)svn_string_createf(pool, "M 644 :%u %s", mark, path + strlen(TRUNK))->data); - fprintf(stdout, "blob\nmark :%u\n", mark++); - dump_blob(fs_root, (char *)path, revpool); - } - } - - if (file_changes->nelts == 0) { - fprintf(stderr, "skipping.\n"); - svn_pool_destroy(revpool); - return 0; - } - - author = apr_hash_get(props, "svn:author", APR_HASH_KEY_STRING); - if (svn_string_isempty(author)) - author = svn_string_create("nobody", pool); - svndate = apr_hash_get(props, "svn:date", APR_HASH_KEY_STRING); - svnlog = apr_hash_get(props, "svn:log", APR_HASH_KEY_STRING); - - fprintf(stdout, "commit refs/heads/master\n"); - fprintf(stdout, "committer %s <%s@localhost> %ld -0000\n", author->data, author->data, get_epoch((char *)svndate->data)); - fprintf(stdout, "data %d\n", svnlog->len); - fputs(svnlog->data, stdout); - fprintf(stdout, "\n"); - fputs(apr_array_pstrcat(pool, file_changes, '\n'), stdout); - fprintf(stdout, "\n\n"); - fflush(stdout); - - svn_pool_destroy(revpool); - - fprintf(stderr, "done!\n"); - - return 0; -} - -int crawl_revisions(char *repos_path) -{ - apr_pool_t *pool, *subpool; - svn_fs_t *fs; - svn_repos_t *repos; - svn_revnum_t youngest_rev, min_rev, max_rev, rev; - - pool = svn_pool_create(NULL); - - SVN_ERR(svn_fs_initialize(pool)); - SVN_ERR(svn_repos_open(&repos, repos_path, pool)); - if ((fs = svn_repos_fs(repos)) == NULL) - return -1; - SVN_ERR(svn_fs_youngest_rev(&youngest_rev, fs, pool)); - - min_rev = 1; - max_rev = youngest_rev; - - subpool = svn_pool_create(pool); - for (rev = min_rev; rev <= max_rev; rev++) { - svn_pool_clear(subpool); - export_revision(rev, fs, subpool); - } - - svn_pool_destroy(pool); - - return 0; -} - -int main(int argc, char *argv[]) -{ - if (argc != 2) { - fprintf(stderr, "usage: %s REPOS_PATH\n", argv[0]); - return -1; - } - - if (apr_initialize() != APR_SUCCESS) { - fprintf(stderr, "You lose at apr_initialize().\n"); - return -1; - } - - crawl_revisions(argv[1]); - - apr_terminate(); - - return 0; -} diff --git a/exporters/svn-fast-export.py b/exporters/svn-fast-export.py deleted file mode 100755 index 520ee16..0000000 --- a/exporters/svn-fast-export.py +++ /dev/null @@ -1,225 +0,0 @@ -#!/usr/bin/python -# -# svn-fast-export.py -# ---------- -# Walk through each revision of a local Subversion repository and export it -# in a stream that git-fast-import can consume. -# -# Author: Chris Lee -# License: MIT - -trunk_path = '/trunk/' -branches_path = '/branches/' -tags_path = '/tags/' -address = 'localhost' - -first_rev = 1 -final_rev = 0 - -import gc, sys, os.path -from optparse import OptionParser -from time import sleep, mktime, localtime, strftime, strptime -from svn.fs import svn_fs_dir_entries, svn_fs_file_length, svn_fs_file_contents, svn_fs_is_dir, svn_fs_revision_root, svn_fs_youngest_rev, svn_fs_revision_proplist, svn_fs_revision_prop, svn_fs_paths_changed -from svn.core import svn_pool_create, svn_pool_clear, svn_pool_destroy, svn_stream_read, svn_stream_for_stdout, svn_stream_copy, svn_stream_close, run_app -from svn.repos import svn_repos_open, svn_repos_fs - -ct_short = ['M', 'A', 'D', 'R', 'X'] - -def dump_file_blob(root, full_path, pool): - stream_length = svn_fs_file_length(root, full_path, pool) - stream = svn_fs_file_contents(root, full_path, pool) - sys.stdout.write("data %s\n" % stream_length) - sys.stdout.flush() - ostream = svn_stream_for_stdout(pool) - svn_stream_copy(stream, ostream, pool) - svn_stream_close(ostream) - sys.stdout.write("\n") - - -class Matcher(object): - - branch = None - - def __init__(self, trunk_path): - self.trunk_path = trunk_path - - def branchname(self): - return self.branch - - def __str__(self): - return super(Matcher, self).__str__() + ":" + self.trunk_path - - @staticmethod - def getMatcher(trunk_path): - if trunk_path.startswith("regex:"): - return RegexStringMatcher(trunk_path) - else: - return StaticStringMatcher(trunk_path) - -class StaticStringMatcher(Matcher): - - branch = "master" - - def matches(self, path): - return path.startswith(trunk_path) - - def replace(self, path): - return path.replace(self.trunk_path, '') - -class RegexStringMatcher(Matcher): - - def __init__(self, trunk_path): - super(RegexStringMatcher, self).__init__(trunk_path) - import re - self.matcher = re.compile(self.trunk_path[len("regex:"):]) - - def matches(self, path): - match = self.matcher.match(path) - if match: - self.branch = match.group(1) - return True - else: - return False - - def replace(self, path): - return self.matcher.sub("\g<2>", path) - -MATCHER = None - -def export_revision(rev, repo, fs, pool): - sys.stderr.write("Exporting revision %s... " % rev) - - revpool = svn_pool_create(pool) - svn_pool_clear(revpool) - - # Open a root object representing the youngest (HEAD) revision. - root = svn_fs_revision_root(fs, rev, revpool) - - # And the list of what changed in this revision. - changes = svn_fs_paths_changed(root, revpool) - - i = 1 - marks = {} - file_changes = [] - - for path, change_type in changes.iteritems(): - c_t = ct_short[change_type.change_kind] - if svn_fs_is_dir(root, path, revpool): - continue - if not MATCHER.matches(path): - # We don't handle branches. Or tags. Yet. - pass - else: - if c_t == 'D': - file_changes.append("D %s" % MATCHER.replace(path).lstrip("/")) - else: - marks[i] = MATCHER.replace(path) - file_changes.append("M 644 :%s %s" % (i, marks[i].lstrip("/"))) - sys.stdout.write("blob\nmark :%s\n" % i) - dump_file_blob(root, path, revpool) - i += 1 - - # Get the commit author and message - props = svn_fs_revision_proplist(fs, rev, revpool) - - # Do the recursive crawl. - if props.has_key('svn:author'): - author = "%s <%s@%s>" % (props['svn:author'], props['svn:author'], address) - else: - author = 'nobody ' - - if len(file_changes) == 0: - svn_pool_destroy(revpool) - sys.stderr.write("skipping.\n") - return - - svndate = props['svn:date'][0:-8] - commit_time = mktime(strptime(svndate, '%Y-%m-%dT%H:%M:%S')) - sys.stdout.write("commit refs/heads/%s\n" % MATCHER.branchname()) - sys.stdout.write("committer %s %s -0000\n" % (author, int(commit_time))) - sys.stdout.write("data %s\n" % len(props['svn:log'])) - sys.stdout.write(props['svn:log']) - sys.stdout.write("\n") - sys.stdout.write('\n'.join(file_changes)) - sys.stdout.write("\n\n") - - svn_pool_destroy(revpool) - - sys.stderr.write("done!\n") - - #if rev % 1000 == 0: - # sys.stderr.write("gc: %s objects\n" % len(gc.get_objects())) - # sleep(5) - - -def crawl_revisions(pool, repos_path): - """Open the repository at REPOS_PATH, and recursively crawl all its - revisions.""" - global final_rev - - # Open the repository at REPOS_PATH, and get a reference to its - # versioning filesystem. - repos_obj = svn_repos_open(repos_path, pool) - fs_obj = svn_repos_fs(repos_obj) - - # Query the current youngest revision. - youngest_rev = svn_fs_youngest_rev(fs_obj, pool) - - - if final_rev == 0: - final_rev = youngest_rev - for rev in xrange(first_rev, final_rev + 1): - export_revision(rev, repos_obj, fs_obj, pool) - - -if __name__ == '__main__': - usage = '%prog [options] REPOS_PATH' - parser = OptionParser() - parser.set_usage(usage) - parser.add_option('-f', '--final-rev', help='Final revision to import', - dest='final_rev', metavar='FINAL_REV', type='int') - parser.add_option('-r', '--first-rev', help='First revision to import', - dest='first_rev', metavar='FIRST_REV', type='int') - parser.add_option('-t', '--trunk-path', help="Path in repo to /trunk, may be `regex:/cvs/(trunk)/proj1/(.*)`\nFirst group is used as branchname, second to match files", - dest='trunk_path', metavar='TRUNK_PATH') - parser.add_option('-b', '--branches-path', help='Path in repo to /branches', - dest='branches_path', metavar='BRANCHES_PATH') - parser.add_option('-T', '--tags-path', help='Path in repo to /tags', - dest='tags_path', metavar='TAGS_PATH') - parser.add_option('-a', '--address', help='Domain to put on users for their mail address', - dest='address', metavar='hostname', type='string') - (options, args) = parser.parse_args() - - if options.trunk_path != None: - trunk_path = options.trunk_path - if options.branches_path != None: - branches_path = options.branches_path - if options.tags_path != None: - tags_path = options.tags_path - if options.final_rev != None: - final_rev = options.final_rev - if options.first_rev != None: - first_rev = options.first_rev - if options.address != None: - address = options.address - - MATCHER = Matcher.getMatcher(trunk_path) - sys.stderr.write("%s\n" % MATCHER) - if len(args) != 1: - parser.print_help() - sys.exit(2) - - # Canonicalize (enough for Subversion, at least) the repository path. - repos_path = os.path.normpath(args[0]) - if repos_path == '.': - repos_path = '' - - try: - import msvcrt - msvcrt.setmode(sys.stdout.fileno(), os.O_BINARY) - except ImportError: - pass - - # Call the app-wrapper, which takes care of APR initialization/shutdown - # and the creation and cleanup of our top-level memory pool. - run_app(crawl_revisions, repos_path) diff --git a/setup.py b/setup.py index a94e6f0..0192d16 100755 --- a/setup.py +++ b/setup.py @@ -14,7 +14,6 @@ if __name__ == '__main__': url="https://launchpad.net/bzr-fastimport", scripts=[], packages=['bzrlib.plugins.fastimport', - 'bzrlib.plugins.fastimport.exporters', 'bzrlib.plugins.fastimport.processors', 'bzrlib.plugins.fastimport.tests', ], -- cgit v1.2.1