Merge changes from mainline
[jelmer/subvertpy.git] / __init__.py
1 # Copyright (C) 2005-2007 Jelmer Vernooij <jelmer@samba.org>
2
3 # This program is free software; you can redistribute it and/or modify
4 # it under the terms of the GNU General Public License as published by
5 # the Free Software Foundation; either version 2 of the License, or
6 # (at your option) any later version.
7
8 # This program is distributed in the hope that it will be useful,
9 # but WITHOUT ANY WARRANTY; without even the implied warranty of
10 # MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
11 # GNU General Public License for more details.
12
13 # You should have received a copy of the GNU General Public License
14 # along with this program; if not, write to the Free Software
15 # Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA
16
17 """
18 Support for foreign branches (Subversion)
19 """
20 import os
21 import sys
22 import unittest
23 import bzrlib
24
25 from bzrlib.trace import warning
26
27 __version__ = '0.4.0'
28 COMPATIBLE_BZR_VERSIONS = [(0, 15), (0, 16)]
29
30 def check_bzrlib_version(desired):
31     """Check that bzrlib is compatible.
32
33     If version is < all compatible version, assume incompatible.
34     If version is compatible version + 1, assume compatible, with deprecations
35     Otherwise, assume incompatible.
36     """
37     bzrlib_version = bzrlib.version_info[:2]
38     if bzrlib_version in desired:
39         return
40     if bzrlib_version < desired[0]:
41         warning('Installed bzr version %s is too old to be used with bzr-svn'
42                 ' %s.' % (bzrlib.__version__, __version__))
43         # Not using BzrNewError, because it may not exist.
44         raise Exception, ('Version mismatch', desired)
45     else:
46         warning('bzr-svn is not up to date with installed bzr version %s.'
47                 ' \nThere should be a newer version of bzr-svn available.' 
48                 % (bzrlib.__version__))
49         if not (bzrlib_version[0], bzrlib_version[1]-1) in desired:
50             raise Exception, 'Version mismatch'
51
52 def check_subversion_version():
53     """Check that Subversion is compatible.
54
55     """
56     import svn.delta
57     if not hasattr(svn.delta, 'svn_delta_invoke_txdelta_window_handler'):
58         warning('Installed Subversion version does not have updated Python '
59                 'bindings. See the bzr-svn README for details.')
60         raise bzrlib.errors.BzrError("incompatible python subversion bindings")
61
62 def check_pysqlite_version():
63     """Check that sqlite library is compatible.
64
65     """
66     try:
67         try:
68             import sqlite3
69         except ImportError:
70             from pysqlite2 import dbapi2 as sqlite3
71     except:
72         warning('Needs at least Python2.5 or Python2.4 with the pysqlite2 '
73                 'module')
74         raise bzrlib.errors.BzrError("missing sqlite library")
75
76     if (sqlite3.sqlite_version_info[0] < 3 or 
77             (sqlite3.sqlite_version_info[0] == 3 and 
78              sqlite3.sqlite_version_info[1] < 3)):
79         warning('Needs at least sqlite 3.3.x')
80         raise bzrlib.errors.BzrError("incompatible sqlite library")
81
82 check_bzrlib_version(COMPATIBLE_BZR_VERSIONS)
83 check_subversion_version()
84 check_pysqlite_version()
85
86 import branch
87 import convert
88 import format
89 import transport
90 import checkout
91
92 from bzrlib.transport import register_transport
93 register_transport('svn://', transport.SvnRaTransport)
94 register_transport('svn+', transport.SvnRaTransport)
95
96 from bzrlib.bzrdir import BzrDirFormat
97
98 from bzrlib.repository import InterRepository
99
100 from fetch import InterSvnRepository
101
102 BzrDirFormat.register_control_format(format.SvnFormat)
103
104 import svn.core
105 _subr_version = svn.core.svn_subr_version()
106
107 BzrDirFormat.register_control_format(checkout.SvnWorkingTreeDirFormat)
108
109 InterRepository.register_optimiser(InterSvnRepository)
110
111 from bzrlib.branch import Branch
112 from bzrlib.commands import Command, register_command, display_command, Option
113 from bzrlib.errors import BzrCommandError
114 from bzrlib.repository import Repository
115 import bzrlib.urlutils as urlutils
116
117
118 def get_scheme(schemename):
119     """Parse scheme identifier and return a branching scheme."""
120     from scheme import BranchingScheme
121     
122     ret = BranchingScheme.find_scheme(schemename)
123     if ret is None:
124         raise BzrCommandError('No such branching scheme %r' % schemename)
125     return ret
126
127
128 class cmd_svn_import(Command):
129     """Convert a Subversion repository to a Bazaar repository.
130     
131     """
132     takes_args = ['from_location', 'to_location?']
133     takes_options = [Option('trees', help='Create working trees'),
134                      Option('shared', help='Create shared repository'),
135                      Option('all', 
136                          help='Convert all revisions, even those not in '
137                               'current branch history (implies --shared)'),
138                      Option('scheme', type=get_scheme,
139                          help='Branching scheme (none, trunk, or trunk-INT)')]
140
141     @display_command
142     def run(self, from_location, to_location=None, trees=False, 
143             shared=False, scheme=None, all=False):
144         from convert import convert_repository
145         from scheme import TrunkBranchingScheme
146
147         if scheme is None:
148             scheme = TrunkBranchingScheme()
149
150         if to_location is None:
151             to_location = os.path.basename(from_location.rstrip("/\\"))
152
153         if all:
154             shared = True
155         convert_repository(from_location, to_location, scheme, shared, trees,
156                            all)
157
158
159 register_command(cmd_svn_import)
160
161 class cmd_svn_upgrade(Command):
162     """Upgrade the revisions mapped from Subversion in a Bazaar branch.
163     
164     This will change the revision ids of revisions whose parents 
165     were mapped from svn revisions.
166     """
167     takes_args = ['svn_repository?']
168     takes_options = [Option('allow-changes', help='Allow content changes')]
169
170     @display_command
171     def run(self, svn_repository=None, allow_changes=False):
172         from upgrade import upgrade_branch
173         
174         branch_to = Branch.open(".")
175
176         stored_loc = branch_to.get_parent()
177         if svn_repository is None:
178             if stored_loc is None:
179                 raise BzrCommandError("No pull location known or"
180                                              " specified.")
181             else:
182                 display_url = urlutils.unescape_for_display(stored_loc,
183                         self.outf.encoding)
184                 self.outf.write("Using saved location: %s\n" % display_url)
185                 svn_repository = stored_loc
186
187         upgrade_branch(branch_to, Repository.open(svn_repository), 
188                        allow_changes)
189
190 register_command(cmd_svn_upgrade)
191
192
193 def test_suite():
194     from unittest import TestSuite
195     import tests
196     suite = TestSuite()
197     suite.addTest(tests.test_suite())
198     return suite
199
200 if __name__ == '__main__':
201     print ("This is a Bazaar plugin. Copy this directory to ~/.bazaar/plugins "
202           "to use it.\n")
203     runner = unittest.TextTestRunner()
204     runner.run(test_suite())
205 else:
206     sys.path.append(os.path.dirname(os.path.abspath(__file__)))