Mercurial > hgsubversion
annotate svnwrap/svn_swig_wrapper.py @ 89:edeec6829d80
SubversionRepo: remember svn.diff3() does not work
Calling it repeatedly is expensive, files and directories are created,
svn transport layer is reset.
author | Patrick Mezard <pmezard@gmail.com> |
---|---|
date | Fri, 14 Nov 2008 16:18:24 -0600 |
parents | b033d74be76b |
children | 7486c6f6cccc |
rev | line source |
---|---|
0
f2636cfed115
Initial import of hgsubversion into a public repository.
Augie Fackler <durin42@gmail.com>
parents:
diff
changeset
|
1 import cStringIO |
f2636cfed115
Initial import of hgsubversion into a public repository.
Augie Fackler <durin42@gmail.com>
parents:
diff
changeset
|
2 import getpass |
f2636cfed115
Initial import of hgsubversion into a public repository.
Augie Fackler <durin42@gmail.com>
parents:
diff
changeset
|
3 import os |
f2636cfed115
Initial import of hgsubversion into a public repository.
Augie Fackler <durin42@gmail.com>
parents:
diff
changeset
|
4 import shutil |
f2636cfed115
Initial import of hgsubversion into a public repository.
Augie Fackler <durin42@gmail.com>
parents:
diff
changeset
|
5 import sys |
f2636cfed115
Initial import of hgsubversion into a public repository.
Augie Fackler <durin42@gmail.com>
parents:
diff
changeset
|
6 import tempfile |
47
9738a7c4e3dd
fix svn push when there's just a file removal
Valentino Volonghi aka dialtone <valentino@adroll.com>
parents:
46
diff
changeset
|
7 import hashlib |
0
f2636cfed115
Initial import of hgsubversion into a public repository.
Augie Fackler <durin42@gmail.com>
parents:
diff
changeset
|
8 |
f2636cfed115
Initial import of hgsubversion into a public repository.
Augie Fackler <durin42@gmail.com>
parents:
diff
changeset
|
9 from svn import client |
f2636cfed115
Initial import of hgsubversion into a public repository.
Augie Fackler <durin42@gmail.com>
parents:
diff
changeset
|
10 from svn import core |
f2636cfed115
Initial import of hgsubversion into a public repository.
Augie Fackler <durin42@gmail.com>
parents:
diff
changeset
|
11 from svn import delta |
f2636cfed115
Initial import of hgsubversion into a public repository.
Augie Fackler <durin42@gmail.com>
parents:
diff
changeset
|
12 from svn import ra |
f2636cfed115
Initial import of hgsubversion into a public repository.
Augie Fackler <durin42@gmail.com>
parents:
diff
changeset
|
13 |
63
2e30b59a9c19
Added some coverage pragmas to stop it from trying to cover things we can't test.
Augie Fackler <durin42@gmail.com>
parents:
59
diff
changeset
|
14 if (core.SVN_VER_MAJOR, core.SVN_VER_MINOR, core.SVN_VER_MICRO) < (1, 5, 0): #pragma: no cover |
50
80b923ab242b
Drop any pretense of supporting svn 1.4.x.
Augie Fackler <durin42@gmail.com>
parents:
47
diff
changeset
|
15 raise ImportError, 'You must have Subversion 1.5.0 or newer and matching SWIG bindings.' |
0
f2636cfed115
Initial import of hgsubversion into a public repository.
Augie Fackler <durin42@gmail.com>
parents:
diff
changeset
|
16 |
89
edeec6829d80
SubversionRepo: remember svn.diff3() does not work
Patrick Mezard <pmezard@gmail.com>
parents:
87
diff
changeset
|
17 class SubversionRepoCanNotReplay(Exception): |
edeec6829d80
SubversionRepo: remember svn.diff3() does not work
Patrick Mezard <pmezard@gmail.com>
parents:
87
diff
changeset
|
18 """Exception raised when the svn server is too old to have replay. |
edeec6829d80
SubversionRepo: remember svn.diff3() does not work
Patrick Mezard <pmezard@gmail.com>
parents:
87
diff
changeset
|
19 """ |
edeec6829d80
SubversionRepo: remember svn.diff3() does not work
Patrick Mezard <pmezard@gmail.com>
parents:
87
diff
changeset
|
20 |
edeec6829d80
SubversionRepo: remember svn.diff3() does not work
Patrick Mezard <pmezard@gmail.com>
parents:
87
diff
changeset
|
21 class SubversionRepoCanNotDiff(Exception): |
edeec6829d80
SubversionRepo: remember svn.diff3() does not work
Patrick Mezard <pmezard@gmail.com>
parents:
87
diff
changeset
|
22 """Exception raised when the svn API diff3() command cannot be used |
edeec6829d80
SubversionRepo: remember svn.diff3() does not work
Patrick Mezard <pmezard@gmail.com>
parents:
87
diff
changeset
|
23 """ |
edeec6829d80
SubversionRepo: remember svn.diff3() does not work
Patrick Mezard <pmezard@gmail.com>
parents:
87
diff
changeset
|
24 |
75
cca31b6b1318
SubversionRepo: add optrev() to help generate client API revisions
Patrick Mezard <pmezard@gmail.com>
parents:
74
diff
changeset
|
25 def optrev(revnum): |
cca31b6b1318
SubversionRepo: add optrev() to help generate client API revisions
Patrick Mezard <pmezard@gmail.com>
parents:
74
diff
changeset
|
26 optrev = core.svn_opt_revision_t() |
cca31b6b1318
SubversionRepo: add optrev() to help generate client API revisions
Patrick Mezard <pmezard@gmail.com>
parents:
74
diff
changeset
|
27 optrev.kind = core.svn_opt_revision_number |
cca31b6b1318
SubversionRepo: add optrev() to help generate client API revisions
Patrick Mezard <pmezard@gmail.com>
parents:
74
diff
changeset
|
28 optrev.value.number = revnum |
cca31b6b1318
SubversionRepo: add optrev() to help generate client API revisions
Patrick Mezard <pmezard@gmail.com>
parents:
74
diff
changeset
|
29 return optrev |
cca31b6b1318
SubversionRepo: add optrev() to help generate client API revisions
Patrick Mezard <pmezard@gmail.com>
parents:
74
diff
changeset
|
30 |
50
80b923ab242b
Drop any pretense of supporting svn 1.4.x.
Augie Fackler <durin42@gmail.com>
parents:
47
diff
changeset
|
31 svn_config = core.svn_config_get_config(None) |
45
ce00e6ffaa90
Change the implementation of the ra_session stuff. Thanks to Ben Collins-Sussman for pointing out the problem with the other method I was using.
Augie Fackler <durin42@gmail.com>
parents:
36
diff
changeset
|
32 class RaCallbacks(ra.Callbacks): |
63
2e30b59a9c19
Added some coverage pragmas to stop it from trying to cover things we can't test.
Augie Fackler <durin42@gmail.com>
parents:
59
diff
changeset
|
33 def open_tmp_file(self, pool): #pragma: no cover |
46
f30cda3389c2
This appears to fix pushing over both the http and svn protocols.
Augie Fackler <durin42@gmail.com>
parents:
45
diff
changeset
|
34 (fd, fn) = tempfile.mkstemp() |
f30cda3389c2
This appears to fix pushing over both the http and svn protocols.
Augie Fackler <durin42@gmail.com>
parents:
45
diff
changeset
|
35 os.close(fd) |
f30cda3389c2
This appears to fix pushing over both the http and svn protocols.
Augie Fackler <durin42@gmail.com>
parents:
45
diff
changeset
|
36 return fn |
f30cda3389c2
This appears to fix pushing over both the http and svn protocols.
Augie Fackler <durin42@gmail.com>
parents:
45
diff
changeset
|
37 |
45
ce00e6ffaa90
Change the implementation of the ra_session stuff. Thanks to Ben Collins-Sussman for pointing out the problem with the other method I was using.
Augie Fackler <durin42@gmail.com>
parents:
36
diff
changeset
|
38 def get_client_string(self, pool): |
ce00e6ffaa90
Change the implementation of the ra_session stuff. Thanks to Ben Collins-Sussman for pointing out the problem with the other method I was using.
Augie Fackler <durin42@gmail.com>
parents:
36
diff
changeset
|
39 return 'hgsubversion' |
0
f2636cfed115
Initial import of hgsubversion into a public repository.
Augie Fackler <durin42@gmail.com>
parents:
diff
changeset
|
40 |
50
80b923ab242b
Drop any pretense of supporting svn 1.4.x.
Augie Fackler <durin42@gmail.com>
parents:
47
diff
changeset
|
41 |
63
2e30b59a9c19
Added some coverage pragmas to stop it from trying to cover things we can't test.
Augie Fackler <durin42@gmail.com>
parents:
59
diff
changeset
|
42 def user_pass_prompt(realm, default_username, ms, pool): #pragma: no cover |
0
f2636cfed115
Initial import of hgsubversion into a public repository.
Augie Fackler <durin42@gmail.com>
parents:
diff
changeset
|
43 creds = core.svn_auth_cred_simple_t() |
f2636cfed115
Initial import of hgsubversion into a public repository.
Augie Fackler <durin42@gmail.com>
parents:
diff
changeset
|
44 creds.may_save = ms |
f2636cfed115
Initial import of hgsubversion into a public repository.
Augie Fackler <durin42@gmail.com>
parents:
diff
changeset
|
45 if default_username: |
f2636cfed115
Initial import of hgsubversion into a public repository.
Augie Fackler <durin42@gmail.com>
parents:
diff
changeset
|
46 sys.stderr.write('Auth realm: %s\n' % (realm,)) |
f2636cfed115
Initial import of hgsubversion into a public repository.
Augie Fackler <durin42@gmail.com>
parents:
diff
changeset
|
47 creds.username = default_username |
f2636cfed115
Initial import of hgsubversion into a public repository.
Augie Fackler <durin42@gmail.com>
parents:
diff
changeset
|
48 else: |
f2636cfed115
Initial import of hgsubversion into a public repository.
Augie Fackler <durin42@gmail.com>
parents:
diff
changeset
|
49 sys.stderr.write('Auth realm: %s\n' % (realm,)) |
f2636cfed115
Initial import of hgsubversion into a public repository.
Augie Fackler <durin42@gmail.com>
parents:
diff
changeset
|
50 sys.stderr.write('Username: ') |
f2636cfed115
Initial import of hgsubversion into a public repository.
Augie Fackler <durin42@gmail.com>
parents:
diff
changeset
|
51 sys.stderr.flush() |
f2636cfed115
Initial import of hgsubversion into a public repository.
Augie Fackler <durin42@gmail.com>
parents:
diff
changeset
|
52 creds.username = sys.stdin.readline().strip() |
f2636cfed115
Initial import of hgsubversion into a public repository.
Augie Fackler <durin42@gmail.com>
parents:
diff
changeset
|
53 creds.password = getpass.getpass('Password for %s: ' % creds.username) |
f2636cfed115
Initial import of hgsubversion into a public repository.
Augie Fackler <durin42@gmail.com>
parents:
diff
changeset
|
54 return creds |
f2636cfed115
Initial import of hgsubversion into a public repository.
Augie Fackler <durin42@gmail.com>
parents:
diff
changeset
|
55 |
f2636cfed115
Initial import of hgsubversion into a public repository.
Augie Fackler <durin42@gmail.com>
parents:
diff
changeset
|
56 def _create_auth_baton(pool): |
f2636cfed115
Initial import of hgsubversion into a public repository.
Augie Fackler <durin42@gmail.com>
parents:
diff
changeset
|
57 """Create a Subversion authentication baton. """ |
f2636cfed115
Initial import of hgsubversion into a public repository.
Augie Fackler <durin42@gmail.com>
parents:
diff
changeset
|
58 # Give the client context baton a suite of authentication |
f2636cfed115
Initial import of hgsubversion into a public repository.
Augie Fackler <durin42@gmail.com>
parents:
diff
changeset
|
59 # providers.h |
f2636cfed115
Initial import of hgsubversion into a public repository.
Augie Fackler <durin42@gmail.com>
parents:
diff
changeset
|
60 providers = [ |
f2636cfed115
Initial import of hgsubversion into a public repository.
Augie Fackler <durin42@gmail.com>
parents:
diff
changeset
|
61 client.get_simple_provider(), |
f2636cfed115
Initial import of hgsubversion into a public repository.
Augie Fackler <durin42@gmail.com>
parents:
diff
changeset
|
62 client.get_username_provider(), |
f2636cfed115
Initial import of hgsubversion into a public repository.
Augie Fackler <durin42@gmail.com>
parents:
diff
changeset
|
63 client.get_ssl_client_cert_file_provider(), |
f2636cfed115
Initial import of hgsubversion into a public repository.
Augie Fackler <durin42@gmail.com>
parents:
diff
changeset
|
64 client.get_ssl_client_cert_pw_file_provider(), |
f2636cfed115
Initial import of hgsubversion into a public repository.
Augie Fackler <durin42@gmail.com>
parents:
diff
changeset
|
65 client.get_ssl_server_trust_file_provider(), |
f2636cfed115
Initial import of hgsubversion into a public repository.
Augie Fackler <durin42@gmail.com>
parents:
diff
changeset
|
66 ] |
f2636cfed115
Initial import of hgsubversion into a public repository.
Augie Fackler <durin42@gmail.com>
parents:
diff
changeset
|
67 # Platform-dependant authentication methods |
63
2e30b59a9c19
Added some coverage pragmas to stop it from trying to cover things we can't test.
Augie Fackler <durin42@gmail.com>
parents:
59
diff
changeset
|
68 if hasattr(client, 'get_windows_simple_provider'): #pragma: no cover |
36
c4523e651325
Fix tests against the improved SWIG bindings in Subversion 1.6.
Augie Fackler <durin42@gmail.com>
parents:
20
diff
changeset
|
69 try: |
c4523e651325
Fix tests against the improved SWIG bindings in Subversion 1.6.
Augie Fackler <durin42@gmail.com>
parents:
20
diff
changeset
|
70 providers.append(client.get_windows_simple_provider()) |
c4523e651325
Fix tests against the improved SWIG bindings in Subversion 1.6.
Augie Fackler <durin42@gmail.com>
parents:
20
diff
changeset
|
71 except: |
c4523e651325
Fix tests against the improved SWIG bindings in Subversion 1.6.
Augie Fackler <durin42@gmail.com>
parents:
20
diff
changeset
|
72 pass |
63
2e30b59a9c19
Added some coverage pragmas to stop it from trying to cover things we can't test.
Augie Fackler <durin42@gmail.com>
parents:
59
diff
changeset
|
73 if hasattr(client, 'get_keychain_simple_provider'): #pragma: no cover |
36
c4523e651325
Fix tests against the improved SWIG bindings in Subversion 1.6.
Augie Fackler <durin42@gmail.com>
parents:
20
diff
changeset
|
74 try: |
c4523e651325
Fix tests against the improved SWIG bindings in Subversion 1.6.
Augie Fackler <durin42@gmail.com>
parents:
20
diff
changeset
|
75 providers.append(client.get_keychain_simple_provider()) |
c4523e651325
Fix tests against the improved SWIG bindings in Subversion 1.6.
Augie Fackler <durin42@gmail.com>
parents:
20
diff
changeset
|
76 except: |
c4523e651325
Fix tests against the improved SWIG bindings in Subversion 1.6.
Augie Fackler <durin42@gmail.com>
parents:
20
diff
changeset
|
77 pass |
0
f2636cfed115
Initial import of hgsubversion into a public repository.
Augie Fackler <durin42@gmail.com>
parents:
diff
changeset
|
78 providers.extend([client.get_simple_prompt_provider(user_pass_prompt, 2), |
f2636cfed115
Initial import of hgsubversion into a public repository.
Augie Fackler <durin42@gmail.com>
parents:
diff
changeset
|
79 ]) |
f2636cfed115
Initial import of hgsubversion into a public repository.
Augie Fackler <durin42@gmail.com>
parents:
diff
changeset
|
80 return core.svn_auth_open(providers, pool) |
f2636cfed115
Initial import of hgsubversion into a public repository.
Augie Fackler <durin42@gmail.com>
parents:
diff
changeset
|
81 |
f2636cfed115
Initial import of hgsubversion into a public repository.
Augie Fackler <durin42@gmail.com>
parents:
diff
changeset
|
82 |
f2636cfed115
Initial import of hgsubversion into a public repository.
Augie Fackler <durin42@gmail.com>
parents:
diff
changeset
|
83 class Revision(object): |
f2636cfed115
Initial import of hgsubversion into a public repository.
Augie Fackler <durin42@gmail.com>
parents:
diff
changeset
|
84 """Wrapper for a Subversion revision. |
f2636cfed115
Initial import of hgsubversion into a public repository.
Augie Fackler <durin42@gmail.com>
parents:
diff
changeset
|
85 """ |
f2636cfed115
Initial import of hgsubversion into a public repository.
Augie Fackler <durin42@gmail.com>
parents:
diff
changeset
|
86 def __init__(self, revnum, author, message, date, paths, strip_path=''): |
f2636cfed115
Initial import of hgsubversion into a public repository.
Augie Fackler <durin42@gmail.com>
parents:
diff
changeset
|
87 self.revnum, self.author, self.message = revnum, author, message |
f2636cfed115
Initial import of hgsubversion into a public repository.
Augie Fackler <durin42@gmail.com>
parents:
diff
changeset
|
88 # TODO parse this into a datetime |
f2636cfed115
Initial import of hgsubversion into a public repository.
Augie Fackler <durin42@gmail.com>
parents:
diff
changeset
|
89 self.date = date |
f2636cfed115
Initial import of hgsubversion into a public repository.
Augie Fackler <durin42@gmail.com>
parents:
diff
changeset
|
90 self.paths = {} |
20
2953c867ca99
Minor fixes to the push command to make it more robust.
Augie Fackler <durin42@gmail.com>
parents:
10
diff
changeset
|
91 if paths: |
2953c867ca99
Minor fixes to the push command to make it more robust.
Augie Fackler <durin42@gmail.com>
parents:
10
diff
changeset
|
92 for p in paths: |
2953c867ca99
Minor fixes to the push command to make it more robust.
Augie Fackler <durin42@gmail.com>
parents:
10
diff
changeset
|
93 self.paths[p[len(strip_path):]] = paths[p] |
0
f2636cfed115
Initial import of hgsubversion into a public repository.
Augie Fackler <durin42@gmail.com>
parents:
diff
changeset
|
94 |
f2636cfed115
Initial import of hgsubversion into a public repository.
Augie Fackler <durin42@gmail.com>
parents:
diff
changeset
|
95 def __str__(self): |
f2636cfed115
Initial import of hgsubversion into a public repository.
Augie Fackler <durin42@gmail.com>
parents:
diff
changeset
|
96 return 'r%d by %s' % (self.revnum, self.author) |
f2636cfed115
Initial import of hgsubversion into a public repository.
Augie Fackler <durin42@gmail.com>
parents:
diff
changeset
|
97 |
87
b033d74be76b
fetch_command: in stupid non-diffy mode, take changed paths in account
Patrick Mezard <pmezard@gmail.com>
parents:
83
diff
changeset
|
98 _svntypes = { |
b033d74be76b
fetch_command: in stupid non-diffy mode, take changed paths in account
Patrick Mezard <pmezard@gmail.com>
parents:
83
diff
changeset
|
99 core.svn_node_dir: 'd', |
b033d74be76b
fetch_command: in stupid non-diffy mode, take changed paths in account
Patrick Mezard <pmezard@gmail.com>
parents:
83
diff
changeset
|
100 core.svn_node_file: 'f', |
b033d74be76b
fetch_command: in stupid non-diffy mode, take changed paths in account
Patrick Mezard <pmezard@gmail.com>
parents:
83
diff
changeset
|
101 } |
b033d74be76b
fetch_command: in stupid non-diffy mode, take changed paths in account
Patrick Mezard <pmezard@gmail.com>
parents:
83
diff
changeset
|
102 |
0
f2636cfed115
Initial import of hgsubversion into a public repository.
Augie Fackler <durin42@gmail.com>
parents:
diff
changeset
|
103 class SubversionRepo(object): |
f2636cfed115
Initial import of hgsubversion into a public repository.
Augie Fackler <durin42@gmail.com>
parents:
diff
changeset
|
104 """Wrapper for a Subversion repository. |
f2636cfed115
Initial import of hgsubversion into a public repository.
Augie Fackler <durin42@gmail.com>
parents:
diff
changeset
|
105 |
f2636cfed115
Initial import of hgsubversion into a public repository.
Augie Fackler <durin42@gmail.com>
parents:
diff
changeset
|
106 This uses the SWIG Python bindings, and will only work on svn >= 1.4. |
f2636cfed115
Initial import of hgsubversion into a public repository.
Augie Fackler <durin42@gmail.com>
parents:
diff
changeset
|
107 It takes a required param, the URL. |
f2636cfed115
Initial import of hgsubversion into a public repository.
Augie Fackler <durin42@gmail.com>
parents:
diff
changeset
|
108 """ |
6
1a5bb173170b
Fixes for win32 compatibility. Changes suggested by Shun-ichi GOTO, with some alterations by me.
Augie Fackler <durin42@gmail.com>
parents:
0
diff
changeset
|
109 def __init__(self, url='', username=''): |
0
f2636cfed115
Initial import of hgsubversion into a public repository.
Augie Fackler <durin42@gmail.com>
parents:
diff
changeset
|
110 self.svn_url = url |
6
1a5bb173170b
Fixes for win32 compatibility. Changes suggested by Shun-ichi GOTO, with some alterations by me.
Augie Fackler <durin42@gmail.com>
parents:
0
diff
changeset
|
111 self.uname = username |
0
f2636cfed115
Initial import of hgsubversion into a public repository.
Augie Fackler <durin42@gmail.com>
parents:
diff
changeset
|
112 self.auth_baton_pool = core.Pool() |
f2636cfed115
Initial import of hgsubversion into a public repository.
Augie Fackler <durin42@gmail.com>
parents:
diff
changeset
|
113 self.auth_baton = _create_auth_baton(self.auth_baton_pool) |
f2636cfed115
Initial import of hgsubversion into a public repository.
Augie Fackler <durin42@gmail.com>
parents:
diff
changeset
|
114 |
f2636cfed115
Initial import of hgsubversion into a public repository.
Augie Fackler <durin42@gmail.com>
parents:
diff
changeset
|
115 self.init_ra_and_client() |
f2636cfed115
Initial import of hgsubversion into a public repository.
Augie Fackler <durin42@gmail.com>
parents:
diff
changeset
|
116 self.uuid = ra.get_uuid(self.ra, self.pool) |
f2636cfed115
Initial import of hgsubversion into a public repository.
Augie Fackler <durin42@gmail.com>
parents:
diff
changeset
|
117 repo_root = ra.get_repos_root(self.ra, self.pool) |
f2636cfed115
Initial import of hgsubversion into a public repository.
Augie Fackler <durin42@gmail.com>
parents:
diff
changeset
|
118 # *will* have a leading '/', would not if we used get_repos_root2 |
f2636cfed115
Initial import of hgsubversion into a public repository.
Augie Fackler <durin42@gmail.com>
parents:
diff
changeset
|
119 self.subdir = url[len(repo_root):] |
f2636cfed115
Initial import of hgsubversion into a public repository.
Augie Fackler <durin42@gmail.com>
parents:
diff
changeset
|
120 if not self.subdir or self.subdir[-1] != '/': |
f2636cfed115
Initial import of hgsubversion into a public repository.
Augie Fackler <durin42@gmail.com>
parents:
diff
changeset
|
121 self.subdir += '/' |
89
edeec6829d80
SubversionRepo: remember svn.diff3() does not work
Patrick Mezard <pmezard@gmail.com>
parents:
87
diff
changeset
|
122 self.hasdiff3 = True |
0
f2636cfed115
Initial import of hgsubversion into a public repository.
Augie Fackler <durin42@gmail.com>
parents:
diff
changeset
|
123 |
f2636cfed115
Initial import of hgsubversion into a public repository.
Augie Fackler <durin42@gmail.com>
parents:
diff
changeset
|
124 def init_ra_and_client(self): |
f2636cfed115
Initial import of hgsubversion into a public repository.
Augie Fackler <durin42@gmail.com>
parents:
diff
changeset
|
125 """Initializes the RA and client layers, because sometimes getting |
f2636cfed115
Initial import of hgsubversion into a public repository.
Augie Fackler <durin42@gmail.com>
parents:
diff
changeset
|
126 unified diffs runs the remote server out of open files. |
f2636cfed115
Initial import of hgsubversion into a public repository.
Augie Fackler <durin42@gmail.com>
parents:
diff
changeset
|
127 """ |
f2636cfed115
Initial import of hgsubversion into a public repository.
Augie Fackler <durin42@gmail.com>
parents:
diff
changeset
|
128 # while we're in here we'll recreate our pool |
f2636cfed115
Initial import of hgsubversion into a public repository.
Augie Fackler <durin42@gmail.com>
parents:
diff
changeset
|
129 self.pool = core.Pool() |
f2636cfed115
Initial import of hgsubversion into a public repository.
Augie Fackler <durin42@gmail.com>
parents:
diff
changeset
|
130 self.client_context = client.create_context() |
f2636cfed115
Initial import of hgsubversion into a public repository.
Augie Fackler <durin42@gmail.com>
parents:
diff
changeset
|
131 core.svn_auth_set_parameter(self.auth_baton, |
f2636cfed115
Initial import of hgsubversion into a public repository.
Augie Fackler <durin42@gmail.com>
parents:
diff
changeset
|
132 core.SVN_AUTH_PARAM_DEFAULT_USERNAME, |
f2636cfed115
Initial import of hgsubversion into a public repository.
Augie Fackler <durin42@gmail.com>
parents:
diff
changeset
|
133 self.uname) |
f2636cfed115
Initial import of hgsubversion into a public repository.
Augie Fackler <durin42@gmail.com>
parents:
diff
changeset
|
134 |
f2636cfed115
Initial import of hgsubversion into a public repository.
Augie Fackler <durin42@gmail.com>
parents:
diff
changeset
|
135 self.client_context.auth_baton = self.auth_baton |
f2636cfed115
Initial import of hgsubversion into a public repository.
Augie Fackler <durin42@gmail.com>
parents:
diff
changeset
|
136 self.client_context.config = svn_config |
45
ce00e6ffaa90
Change the implementation of the ra_session stuff. Thanks to Ben Collins-Sussman for pointing out the problem with the other method I was using.
Augie Fackler <durin42@gmail.com>
parents:
36
diff
changeset
|
137 callbacks = RaCallbacks() |
ce00e6ffaa90
Change the implementation of the ra_session stuff. Thanks to Ben Collins-Sussman for pointing out the problem with the other method I was using.
Augie Fackler <durin42@gmail.com>
parents:
36
diff
changeset
|
138 callbacks.auth_baton = self.auth_baton |
ce00e6ffaa90
Change the implementation of the ra_session stuff. Thanks to Ben Collins-Sussman for pointing out the problem with the other method I was using.
Augie Fackler <durin42@gmail.com>
parents:
36
diff
changeset
|
139 self.callbacks = callbacks |
ce00e6ffaa90
Change the implementation of the ra_session stuff. Thanks to Ben Collins-Sussman for pointing out the problem with the other method I was using.
Augie Fackler <durin42@gmail.com>
parents:
36
diff
changeset
|
140 self.ra = ra.open2(self.svn_url.encode('utf-8'), callbacks, |
50
80b923ab242b
Drop any pretense of supporting svn 1.4.x.
Augie Fackler <durin42@gmail.com>
parents:
47
diff
changeset
|
141 svn_config, self.pool) |
0
f2636cfed115
Initial import of hgsubversion into a public repository.
Augie Fackler <durin42@gmail.com>
parents:
diff
changeset
|
142 |
f2636cfed115
Initial import of hgsubversion into a public repository.
Augie Fackler <durin42@gmail.com>
parents:
diff
changeset
|
143 @property |
f2636cfed115
Initial import of hgsubversion into a public repository.
Augie Fackler <durin42@gmail.com>
parents:
diff
changeset
|
144 def HEAD(self): |
f2636cfed115
Initial import of hgsubversion into a public repository.
Augie Fackler <durin42@gmail.com>
parents:
diff
changeset
|
145 return ra.get_latest_revnum(self.ra, self.pool) |
f2636cfed115
Initial import of hgsubversion into a public repository.
Augie Fackler <durin42@gmail.com>
parents:
diff
changeset
|
146 |
f2636cfed115
Initial import of hgsubversion into a public repository.
Augie Fackler <durin42@gmail.com>
parents:
diff
changeset
|
147 @property |
f2636cfed115
Initial import of hgsubversion into a public repository.
Augie Fackler <durin42@gmail.com>
parents:
diff
changeset
|
148 def START(self): |
f2636cfed115
Initial import of hgsubversion into a public repository.
Augie Fackler <durin42@gmail.com>
parents:
diff
changeset
|
149 return 0 |
f2636cfed115
Initial import of hgsubversion into a public repository.
Augie Fackler <durin42@gmail.com>
parents:
diff
changeset
|
150 |
f2636cfed115
Initial import of hgsubversion into a public repository.
Augie Fackler <durin42@gmail.com>
parents:
diff
changeset
|
151 @property |
f2636cfed115
Initial import of hgsubversion into a public repository.
Augie Fackler <durin42@gmail.com>
parents:
diff
changeset
|
152 def branches(self): |
f2636cfed115
Initial import of hgsubversion into a public repository.
Augie Fackler <durin42@gmail.com>
parents:
diff
changeset
|
153 """Get the branches defined in this repo assuming a standard layout. |
f2636cfed115
Initial import of hgsubversion into a public repository.
Augie Fackler <durin42@gmail.com>
parents:
diff
changeset
|
154 """ |
f2636cfed115
Initial import of hgsubversion into a public repository.
Augie Fackler <durin42@gmail.com>
parents:
diff
changeset
|
155 branches = self.list_dir('branches').keys() |
f2636cfed115
Initial import of hgsubversion into a public repository.
Augie Fackler <durin42@gmail.com>
parents:
diff
changeset
|
156 branch_info = {} |
f2636cfed115
Initial import of hgsubversion into a public repository.
Augie Fackler <durin42@gmail.com>
parents:
diff
changeset
|
157 head=self.HEAD |
f2636cfed115
Initial import of hgsubversion into a public repository.
Augie Fackler <durin42@gmail.com>
parents:
diff
changeset
|
158 for b in branches: |
f2636cfed115
Initial import of hgsubversion into a public repository.
Augie Fackler <durin42@gmail.com>
parents:
diff
changeset
|
159 b_path = 'branches/%s' %b |
f2636cfed115
Initial import of hgsubversion into a public repository.
Augie Fackler <durin42@gmail.com>
parents:
diff
changeset
|
160 hist_gen = self.fetch_history_at_paths([b_path], stop=head) |
f2636cfed115
Initial import of hgsubversion into a public repository.
Augie Fackler <durin42@gmail.com>
parents:
diff
changeset
|
161 hist = hist_gen.next() |
f2636cfed115
Initial import of hgsubversion into a public repository.
Augie Fackler <durin42@gmail.com>
parents:
diff
changeset
|
162 source, source_rev = self._get_copy_source(b_path, cached_head=head) |
f2636cfed115
Initial import of hgsubversion into a public repository.
Augie Fackler <durin42@gmail.com>
parents:
diff
changeset
|
163 # This if statement guards against projects that have non-ancestral |
f2636cfed115
Initial import of hgsubversion into a public repository.
Augie Fackler <durin42@gmail.com>
parents:
diff
changeset
|
164 # branches by not listing them has branches |
f2636cfed115
Initial import of hgsubversion into a public repository.
Augie Fackler <durin42@gmail.com>
parents:
diff
changeset
|
165 # Note that they probably are really ancestrally related, but there |
f2636cfed115
Initial import of hgsubversion into a public repository.
Augie Fackler <durin42@gmail.com>
parents:
diff
changeset
|
166 # is just no way for us to know how. |
f2636cfed115
Initial import of hgsubversion into a public repository.
Augie Fackler <durin42@gmail.com>
parents:
diff
changeset
|
167 if source is not None and source_rev is not None: |
f2636cfed115
Initial import of hgsubversion into a public repository.
Augie Fackler <durin42@gmail.com>
parents:
diff
changeset
|
168 branch_info[b] = (source, source_rev, hist.revnum) |
f2636cfed115
Initial import of hgsubversion into a public repository.
Augie Fackler <durin42@gmail.com>
parents:
diff
changeset
|
169 return branch_info |
f2636cfed115
Initial import of hgsubversion into a public repository.
Augie Fackler <durin42@gmail.com>
parents:
diff
changeset
|
170 |
f2636cfed115
Initial import of hgsubversion into a public repository.
Augie Fackler <durin42@gmail.com>
parents:
diff
changeset
|
171 @property |
f2636cfed115
Initial import of hgsubversion into a public repository.
Augie Fackler <durin42@gmail.com>
parents:
diff
changeset
|
172 def tags(self): |
f2636cfed115
Initial import of hgsubversion into a public repository.
Augie Fackler <durin42@gmail.com>
parents:
diff
changeset
|
173 """Get the current tags in this repo assuming a standard layout. |
f2636cfed115
Initial import of hgsubversion into a public repository.
Augie Fackler <durin42@gmail.com>
parents:
diff
changeset
|
174 |
f2636cfed115
Initial import of hgsubversion into a public repository.
Augie Fackler <durin42@gmail.com>
parents:
diff
changeset
|
175 This returns a dictionary of tag: (source path, source rev) |
f2636cfed115
Initial import of hgsubversion into a public repository.
Augie Fackler <durin42@gmail.com>
parents:
diff
changeset
|
176 """ |
f2636cfed115
Initial import of hgsubversion into a public repository.
Augie Fackler <durin42@gmail.com>
parents:
diff
changeset
|
177 tags = self.list_dir('tags').keys() |
f2636cfed115
Initial import of hgsubversion into a public repository.
Augie Fackler <durin42@gmail.com>
parents:
diff
changeset
|
178 tag_info = {} |
f2636cfed115
Initial import of hgsubversion into a public repository.
Augie Fackler <durin42@gmail.com>
parents:
diff
changeset
|
179 head = self.HEAD |
f2636cfed115
Initial import of hgsubversion into a public repository.
Augie Fackler <durin42@gmail.com>
parents:
diff
changeset
|
180 for t in tags: |
f2636cfed115
Initial import of hgsubversion into a public repository.
Augie Fackler <durin42@gmail.com>
parents:
diff
changeset
|
181 tag_info[t] = self._get_copy_source('tags/%s' % t, |
f2636cfed115
Initial import of hgsubversion into a public repository.
Augie Fackler <durin42@gmail.com>
parents:
diff
changeset
|
182 cached_head=head) |
f2636cfed115
Initial import of hgsubversion into a public repository.
Augie Fackler <durin42@gmail.com>
parents:
diff
changeset
|
183 return tag_info |
f2636cfed115
Initial import of hgsubversion into a public repository.
Augie Fackler <durin42@gmail.com>
parents:
diff
changeset
|
184 |
f2636cfed115
Initial import of hgsubversion into a public repository.
Augie Fackler <durin42@gmail.com>
parents:
diff
changeset
|
185 def _get_copy_source(self, path, cached_head=None): |
f2636cfed115
Initial import of hgsubversion into a public repository.
Augie Fackler <durin42@gmail.com>
parents:
diff
changeset
|
186 """Get copy revision for the given path, assuming it was meant to be |
f2636cfed115
Initial import of hgsubversion into a public repository.
Augie Fackler <durin42@gmail.com>
parents:
diff
changeset
|
187 a copy of the entire tree. |
f2636cfed115
Initial import of hgsubversion into a public repository.
Augie Fackler <durin42@gmail.com>
parents:
diff
changeset
|
188 """ |
f2636cfed115
Initial import of hgsubversion into a public repository.
Augie Fackler <durin42@gmail.com>
parents:
diff
changeset
|
189 if not cached_head: |
f2636cfed115
Initial import of hgsubversion into a public repository.
Augie Fackler <durin42@gmail.com>
parents:
diff
changeset
|
190 cached_head = self.HEAD |
f2636cfed115
Initial import of hgsubversion into a public repository.
Augie Fackler <durin42@gmail.com>
parents:
diff
changeset
|
191 hist_gen = self.fetch_history_at_paths([path], stop=cached_head) |
f2636cfed115
Initial import of hgsubversion into a public repository.
Augie Fackler <durin42@gmail.com>
parents:
diff
changeset
|
192 hist = hist_gen.next() |
f2636cfed115
Initial import of hgsubversion into a public repository.
Augie Fackler <durin42@gmail.com>
parents:
diff
changeset
|
193 if hist.paths[path].copyfrom_path is None: |
f2636cfed115
Initial import of hgsubversion into a public repository.
Augie Fackler <durin42@gmail.com>
parents:
diff
changeset
|
194 return None, None |
f2636cfed115
Initial import of hgsubversion into a public repository.
Augie Fackler <durin42@gmail.com>
parents:
diff
changeset
|
195 source = hist.paths[path].copyfrom_path |
f2636cfed115
Initial import of hgsubversion into a public repository.
Augie Fackler <durin42@gmail.com>
parents:
diff
changeset
|
196 source_rev = 0 |
f2636cfed115
Initial import of hgsubversion into a public repository.
Augie Fackler <durin42@gmail.com>
parents:
diff
changeset
|
197 for p in hist.paths: |
f2636cfed115
Initial import of hgsubversion into a public repository.
Augie Fackler <durin42@gmail.com>
parents:
diff
changeset
|
198 if hist.paths[p].copyfrom_rev: |
f2636cfed115
Initial import of hgsubversion into a public repository.
Augie Fackler <durin42@gmail.com>
parents:
diff
changeset
|
199 # We assume that the revision of the source tree as it was |
f2636cfed115
Initial import of hgsubversion into a public repository.
Augie Fackler <durin42@gmail.com>
parents:
diff
changeset
|
200 # copied was actually the revision of the highest revision |
f2636cfed115
Initial import of hgsubversion into a public repository.
Augie Fackler <durin42@gmail.com>
parents:
diff
changeset
|
201 # copied item. This could be wrong, but in practice it will |
f2636cfed115
Initial import of hgsubversion into a public repository.
Augie Fackler <durin42@gmail.com>
parents:
diff
changeset
|
202 # *probably* be correct |
f2636cfed115
Initial import of hgsubversion into a public repository.
Augie Fackler <durin42@gmail.com>
parents:
diff
changeset
|
203 if source_rev < hist.paths[p].copyfrom_rev: |
f2636cfed115
Initial import of hgsubversion into a public repository.
Augie Fackler <durin42@gmail.com>
parents:
diff
changeset
|
204 source_rev = hist.paths[p].copyfrom_rev |
f2636cfed115
Initial import of hgsubversion into a public repository.
Augie Fackler <durin42@gmail.com>
parents:
diff
changeset
|
205 source = source[len(self.subdir):] |
f2636cfed115
Initial import of hgsubversion into a public repository.
Augie Fackler <durin42@gmail.com>
parents:
diff
changeset
|
206 return source, source_rev |
f2636cfed115
Initial import of hgsubversion into a public repository.
Augie Fackler <durin42@gmail.com>
parents:
diff
changeset
|
207 |
f2636cfed115
Initial import of hgsubversion into a public repository.
Augie Fackler <durin42@gmail.com>
parents:
diff
changeset
|
208 def list_dir(self, dir, revision=None): |
f2636cfed115
Initial import of hgsubversion into a public repository.
Augie Fackler <durin42@gmail.com>
parents:
diff
changeset
|
209 """List the contents of a server-side directory. |
f2636cfed115
Initial import of hgsubversion into a public repository.
Augie Fackler <durin42@gmail.com>
parents:
diff
changeset
|
210 |
f2636cfed115
Initial import of hgsubversion into a public repository.
Augie Fackler <durin42@gmail.com>
parents:
diff
changeset
|
211 Returns a dict-like object with one dict key per directory entry. |
f2636cfed115
Initial import of hgsubversion into a public repository.
Augie Fackler <durin42@gmail.com>
parents:
diff
changeset
|
212 |
f2636cfed115
Initial import of hgsubversion into a public repository.
Augie Fackler <durin42@gmail.com>
parents:
diff
changeset
|
213 Args: |
f2636cfed115
Initial import of hgsubversion into a public repository.
Augie Fackler <durin42@gmail.com>
parents:
diff
changeset
|
214 dir: the directory to list, no leading slash |
f2636cfed115
Initial import of hgsubversion into a public repository.
Augie Fackler <durin42@gmail.com>
parents:
diff
changeset
|
215 rev: the revision at which to list the directory, defaults to HEAD |
f2636cfed115
Initial import of hgsubversion into a public repository.
Augie Fackler <durin42@gmail.com>
parents:
diff
changeset
|
216 """ |
f2636cfed115
Initial import of hgsubversion into a public repository.
Augie Fackler <durin42@gmail.com>
parents:
diff
changeset
|
217 if dir[-1] == '/': |
f2636cfed115
Initial import of hgsubversion into a public repository.
Augie Fackler <durin42@gmail.com>
parents:
diff
changeset
|
218 dir = dir[:-1] |
f2636cfed115
Initial import of hgsubversion into a public repository.
Augie Fackler <durin42@gmail.com>
parents:
diff
changeset
|
219 if revision is None: |
f2636cfed115
Initial import of hgsubversion into a public repository.
Augie Fackler <durin42@gmail.com>
parents:
diff
changeset
|
220 revision = self.HEAD |
f2636cfed115
Initial import of hgsubversion into a public repository.
Augie Fackler <durin42@gmail.com>
parents:
diff
changeset
|
221 r = ra.get_dir2(self.ra, dir, revision, core.SVN_DIRENT_KIND, self.pool) |
f2636cfed115
Initial import of hgsubversion into a public repository.
Augie Fackler <durin42@gmail.com>
parents:
diff
changeset
|
222 folders, props, junk = r |
f2636cfed115
Initial import of hgsubversion into a public repository.
Augie Fackler <durin42@gmail.com>
parents:
diff
changeset
|
223 return folders |
f2636cfed115
Initial import of hgsubversion into a public repository.
Augie Fackler <durin42@gmail.com>
parents:
diff
changeset
|
224 |
f2636cfed115
Initial import of hgsubversion into a public repository.
Augie Fackler <durin42@gmail.com>
parents:
diff
changeset
|
225 def revisions(self, start=None, chunk_size=1000): |
f2636cfed115
Initial import of hgsubversion into a public repository.
Augie Fackler <durin42@gmail.com>
parents:
diff
changeset
|
226 """Load the history of this repo. |
f2636cfed115
Initial import of hgsubversion into a public repository.
Augie Fackler <durin42@gmail.com>
parents:
diff
changeset
|
227 |
f2636cfed115
Initial import of hgsubversion into a public repository.
Augie Fackler <durin42@gmail.com>
parents:
diff
changeset
|
228 This is LAZY. It returns a generator, and fetches a small number |
f2636cfed115
Initial import of hgsubversion into a public repository.
Augie Fackler <durin42@gmail.com>
parents:
diff
changeset
|
229 of revisions at a time. |
f2636cfed115
Initial import of hgsubversion into a public repository.
Augie Fackler <durin42@gmail.com>
parents:
diff
changeset
|
230 |
f2636cfed115
Initial import of hgsubversion into a public repository.
Augie Fackler <durin42@gmail.com>
parents:
diff
changeset
|
231 The reason this is lazy is so that you can use the same repo object |
f2636cfed115
Initial import of hgsubversion into a public repository.
Augie Fackler <durin42@gmail.com>
parents:
diff
changeset
|
232 to perform RA calls to get deltas. |
f2636cfed115
Initial import of hgsubversion into a public repository.
Augie Fackler <durin42@gmail.com>
parents:
diff
changeset
|
233 """ |
f2636cfed115
Initial import of hgsubversion into a public repository.
Augie Fackler <durin42@gmail.com>
parents:
diff
changeset
|
234 # NB: you'd think this would work, but you'd be wrong. I'm pretty |
f2636cfed115
Initial import of hgsubversion into a public repository.
Augie Fackler <durin42@gmail.com>
parents:
diff
changeset
|
235 # convinced there must be some kind of svn bug here. |
f2636cfed115
Initial import of hgsubversion into a public repository.
Augie Fackler <durin42@gmail.com>
parents:
diff
changeset
|
236 #return self.fetch_history_at_paths(['tags', 'trunk', 'branches'], |
f2636cfed115
Initial import of hgsubversion into a public repository.
Augie Fackler <durin42@gmail.com>
parents:
diff
changeset
|
237 # start=start) |
f2636cfed115
Initial import of hgsubversion into a public repository.
Augie Fackler <durin42@gmail.com>
parents:
diff
changeset
|
238 # this does the same thing, but at the repo root + filtering. It's |
f2636cfed115
Initial import of hgsubversion into a public repository.
Augie Fackler <durin42@gmail.com>
parents:
diff
changeset
|
239 # kind of tough cookies, sadly. |
f2636cfed115
Initial import of hgsubversion into a public repository.
Augie Fackler <durin42@gmail.com>
parents:
diff
changeset
|
240 for r in self.fetch_history_at_paths([''], start=start, |
f2636cfed115
Initial import of hgsubversion into a public repository.
Augie Fackler <durin42@gmail.com>
parents:
diff
changeset
|
241 chunk_size=chunk_size): |
f2636cfed115
Initial import of hgsubversion into a public repository.
Augie Fackler <durin42@gmail.com>
parents:
diff
changeset
|
242 should_yield = False |
f2636cfed115
Initial import of hgsubversion into a public repository.
Augie Fackler <durin42@gmail.com>
parents:
diff
changeset
|
243 i = 0 |
f2636cfed115
Initial import of hgsubversion into a public repository.
Augie Fackler <durin42@gmail.com>
parents:
diff
changeset
|
244 paths = list(r.paths.keys()) |
f2636cfed115
Initial import of hgsubversion into a public repository.
Augie Fackler <durin42@gmail.com>
parents:
diff
changeset
|
245 while i < len(paths) and not should_yield: |
f2636cfed115
Initial import of hgsubversion into a public repository.
Augie Fackler <durin42@gmail.com>
parents:
diff
changeset
|
246 p = paths[i] |
f2636cfed115
Initial import of hgsubversion into a public repository.
Augie Fackler <durin42@gmail.com>
parents:
diff
changeset
|
247 if (p.startswith('trunk') or p.startswith('tags') |
f2636cfed115
Initial import of hgsubversion into a public repository.
Augie Fackler <durin42@gmail.com>
parents:
diff
changeset
|
248 or p.startswith('branches')): |
f2636cfed115
Initial import of hgsubversion into a public repository.
Augie Fackler <durin42@gmail.com>
parents:
diff
changeset
|
249 should_yield = True |
f2636cfed115
Initial import of hgsubversion into a public repository.
Augie Fackler <durin42@gmail.com>
parents:
diff
changeset
|
250 i += 1 |
f2636cfed115
Initial import of hgsubversion into a public repository.
Augie Fackler <durin42@gmail.com>
parents:
diff
changeset
|
251 if should_yield: |
f2636cfed115
Initial import of hgsubversion into a public repository.
Augie Fackler <durin42@gmail.com>
parents:
diff
changeset
|
252 yield r |
f2636cfed115
Initial import of hgsubversion into a public repository.
Augie Fackler <durin42@gmail.com>
parents:
diff
changeset
|
253 |
f2636cfed115
Initial import of hgsubversion into a public repository.
Augie Fackler <durin42@gmail.com>
parents:
diff
changeset
|
254 |
f2636cfed115
Initial import of hgsubversion into a public repository.
Augie Fackler <durin42@gmail.com>
parents:
diff
changeset
|
255 def fetch_history_at_paths(self, paths, start=None, stop=None, |
f2636cfed115
Initial import of hgsubversion into a public repository.
Augie Fackler <durin42@gmail.com>
parents:
diff
changeset
|
256 chunk_size=1000): |
f2636cfed115
Initial import of hgsubversion into a public repository.
Augie Fackler <durin42@gmail.com>
parents:
diff
changeset
|
257 revisions = [] |
f2636cfed115
Initial import of hgsubversion into a public repository.
Augie Fackler <durin42@gmail.com>
parents:
diff
changeset
|
258 def callback(paths, revnum, author, date, message, pool): |
f2636cfed115
Initial import of hgsubversion into a public repository.
Augie Fackler <durin42@gmail.com>
parents:
diff
changeset
|
259 r = Revision(revnum, author, message, date, paths, |
f2636cfed115
Initial import of hgsubversion into a public repository.
Augie Fackler <durin42@gmail.com>
parents:
diff
changeset
|
260 strip_path=self.subdir) |
f2636cfed115
Initial import of hgsubversion into a public repository.
Augie Fackler <durin42@gmail.com>
parents:
diff
changeset
|
261 revisions.append(r) |
f2636cfed115
Initial import of hgsubversion into a public repository.
Augie Fackler <durin42@gmail.com>
parents:
diff
changeset
|
262 if not start: |
f2636cfed115
Initial import of hgsubversion into a public repository.
Augie Fackler <durin42@gmail.com>
parents:
diff
changeset
|
263 start = self.START |
f2636cfed115
Initial import of hgsubversion into a public repository.
Augie Fackler <durin42@gmail.com>
parents:
diff
changeset
|
264 if not stop: |
f2636cfed115
Initial import of hgsubversion into a public repository.
Augie Fackler <durin42@gmail.com>
parents:
diff
changeset
|
265 stop = self.HEAD |
f2636cfed115
Initial import of hgsubversion into a public repository.
Augie Fackler <durin42@gmail.com>
parents:
diff
changeset
|
266 while stop > start: |
50
80b923ab242b
Drop any pretense of supporting svn 1.4.x.
Augie Fackler <durin42@gmail.com>
parents:
47
diff
changeset
|
267 ra.get_log(self.ra, |
45
ce00e6ffaa90
Change the implementation of the ra_session stuff. Thanks to Ben Collins-Sussman for pointing out the problem with the other method I was using.
Augie Fackler <durin42@gmail.com>
parents:
36
diff
changeset
|
268 paths, |
ce00e6ffaa90
Change the implementation of the ra_session stuff. Thanks to Ben Collins-Sussman for pointing out the problem with the other method I was using.
Augie Fackler <durin42@gmail.com>
parents:
36
diff
changeset
|
269 start+1, |
ce00e6ffaa90
Change the implementation of the ra_session stuff. Thanks to Ben Collins-Sussman for pointing out the problem with the other method I was using.
Augie Fackler <durin42@gmail.com>
parents:
36
diff
changeset
|
270 stop, |
ce00e6ffaa90
Change the implementation of the ra_session stuff. Thanks to Ben Collins-Sussman for pointing out the problem with the other method I was using.
Augie Fackler <durin42@gmail.com>
parents:
36
diff
changeset
|
271 chunk_size, #limit of how many log messages to load |
ce00e6ffaa90
Change the implementation of the ra_session stuff. Thanks to Ben Collins-Sussman for pointing out the problem with the other method I was using.
Augie Fackler <durin42@gmail.com>
parents:
36
diff
changeset
|
272 True, # don't need to know changed paths |
ce00e6ffaa90
Change the implementation of the ra_session stuff. Thanks to Ben Collins-Sussman for pointing out the problem with the other method I was using.
Augie Fackler <durin42@gmail.com>
parents:
36
diff
changeset
|
273 True, # stop on copies |
ce00e6ffaa90
Change the implementation of the ra_session stuff. Thanks to Ben Collins-Sussman for pointing out the problem with the other method I was using.
Augie Fackler <durin42@gmail.com>
parents:
36
diff
changeset
|
274 callback, |
ce00e6ffaa90
Change the implementation of the ra_session stuff. Thanks to Ben Collins-Sussman for pointing out the problem with the other method I was using.
Augie Fackler <durin42@gmail.com>
parents:
36
diff
changeset
|
275 self.pool) |
0
f2636cfed115
Initial import of hgsubversion into a public repository.
Augie Fackler <durin42@gmail.com>
parents:
diff
changeset
|
276 if len(revisions) < chunk_size: |
f2636cfed115
Initial import of hgsubversion into a public repository.
Augie Fackler <durin42@gmail.com>
parents:
diff
changeset
|
277 # this means there was no history for the path, so force the |
f2636cfed115
Initial import of hgsubversion into a public repository.
Augie Fackler <durin42@gmail.com>
parents:
diff
changeset
|
278 # loop to exit |
f2636cfed115
Initial import of hgsubversion into a public repository.
Augie Fackler <durin42@gmail.com>
parents:
diff
changeset
|
279 start = stop |
f2636cfed115
Initial import of hgsubversion into a public repository.
Augie Fackler <durin42@gmail.com>
parents:
diff
changeset
|
280 else: |
f2636cfed115
Initial import of hgsubversion into a public repository.
Augie Fackler <durin42@gmail.com>
parents:
diff
changeset
|
281 start = revisions[-1].revnum |
f2636cfed115
Initial import of hgsubversion into a public repository.
Augie Fackler <durin42@gmail.com>
parents:
diff
changeset
|
282 while len(revisions) > 0: |
f2636cfed115
Initial import of hgsubversion into a public repository.
Augie Fackler <durin42@gmail.com>
parents:
diff
changeset
|
283 yield revisions[0] |
f2636cfed115
Initial import of hgsubversion into a public repository.
Augie Fackler <durin42@gmail.com>
parents:
diff
changeset
|
284 revisions.pop(0) |
f2636cfed115
Initial import of hgsubversion into a public repository.
Augie Fackler <durin42@gmail.com>
parents:
diff
changeset
|
285 |
83
6c9b7cf1c5aa
push_cmd: delete empty svn directories, refactor directory creation
Patrick Mezard <pmezard@gmail.com>
parents:
81
diff
changeset
|
286 def commit(self, paths, message, file_data, base_revision, addeddirs, |
6c9b7cf1c5aa
push_cmd: delete empty svn directories, refactor directory creation
Patrick Mezard <pmezard@gmail.com>
parents:
81
diff
changeset
|
287 deleteddirs, properties, copies): |
0
f2636cfed115
Initial import of hgsubversion into a public repository.
Augie Fackler <durin42@gmail.com>
parents:
diff
changeset
|
288 """Commits the appropriate targets from revision in editor's store. |
f2636cfed115
Initial import of hgsubversion into a public repository.
Augie Fackler <durin42@gmail.com>
parents:
diff
changeset
|
289 """ |
f2636cfed115
Initial import of hgsubversion into a public repository.
Augie Fackler <durin42@gmail.com>
parents:
diff
changeset
|
290 self.init_ra_and_client() |
f2636cfed115
Initial import of hgsubversion into a public repository.
Augie Fackler <durin42@gmail.com>
parents:
diff
changeset
|
291 commit_info = [] |
f2636cfed115
Initial import of hgsubversion into a public repository.
Augie Fackler <durin42@gmail.com>
parents:
diff
changeset
|
292 def commit_cb(_commit_info, pool): |
f2636cfed115
Initial import of hgsubversion into a public repository.
Augie Fackler <durin42@gmail.com>
parents:
diff
changeset
|
293 commit_info.append(_commit_info) |
f2636cfed115
Initial import of hgsubversion into a public repository.
Augie Fackler <durin42@gmail.com>
parents:
diff
changeset
|
294 editor, edit_baton = ra.get_commit_editor2(self.ra, |
f2636cfed115
Initial import of hgsubversion into a public repository.
Augie Fackler <durin42@gmail.com>
parents:
diff
changeset
|
295 message, |
f2636cfed115
Initial import of hgsubversion into a public repository.
Augie Fackler <durin42@gmail.com>
parents:
diff
changeset
|
296 commit_cb, |
f2636cfed115
Initial import of hgsubversion into a public repository.
Augie Fackler <durin42@gmail.com>
parents:
diff
changeset
|
297 None, |
20
2953c867ca99
Minor fixes to the push command to make it more robust.
Augie Fackler <durin42@gmail.com>
parents:
10
diff
changeset
|
298 False, |
2953c867ca99
Minor fixes to the push command to make it more robust.
Augie Fackler <durin42@gmail.com>
parents:
10
diff
changeset
|
299 self.pool) |
0
f2636cfed115
Initial import of hgsubversion into a public repository.
Augie Fackler <durin42@gmail.com>
parents:
diff
changeset
|
300 checksum = [] |
46
f30cda3389c2
This appears to fix pushing over both the http and svn protocols.
Augie Fackler <durin42@gmail.com>
parents:
45
diff
changeset
|
301 # internal dir batons can fall out of scope and get GCed before svn is |
f30cda3389c2
This appears to fix pushing over both the http and svn protocols.
Augie Fackler <durin42@gmail.com>
parents:
45
diff
changeset
|
302 # done with them. This prevents that (credit to gvn for the idea). |
f30cda3389c2
This appears to fix pushing over both the http and svn protocols.
Augie Fackler <durin42@gmail.com>
parents:
45
diff
changeset
|
303 batons = [edit_baton, ] |
0
f2636cfed115
Initial import of hgsubversion into a public repository.
Augie Fackler <durin42@gmail.com>
parents:
diff
changeset
|
304 def driver_cb(parent, path, pool): |
46
f30cda3389c2
This appears to fix pushing over both the http and svn protocols.
Augie Fackler <durin42@gmail.com>
parents:
45
diff
changeset
|
305 if not parent: |
f30cda3389c2
This appears to fix pushing over both the http and svn protocols.
Augie Fackler <durin42@gmail.com>
parents:
45
diff
changeset
|
306 bat = editor.open_root(edit_baton, base_revision, self.pool) |
f30cda3389c2
This appears to fix pushing over both the http and svn protocols.
Augie Fackler <durin42@gmail.com>
parents:
45
diff
changeset
|
307 batons.append(bat) |
f30cda3389c2
This appears to fix pushing over both the http and svn protocols.
Augie Fackler <durin42@gmail.com>
parents:
45
diff
changeset
|
308 return bat |
83
6c9b7cf1c5aa
push_cmd: delete empty svn directories, refactor directory creation
Patrick Mezard <pmezard@gmail.com>
parents:
81
diff
changeset
|
309 if path in addeddirs: |
46
f30cda3389c2
This appears to fix pushing over both the http and svn protocols.
Augie Fackler <durin42@gmail.com>
parents:
45
diff
changeset
|
310 bat = editor.add_directory(path, parent, None, -1, pool) |
f30cda3389c2
This appears to fix pushing over both the http and svn protocols.
Augie Fackler <durin42@gmail.com>
parents:
45
diff
changeset
|
311 batons.append(bat) |
f30cda3389c2
This appears to fix pushing over both the http and svn protocols.
Augie Fackler <durin42@gmail.com>
parents:
45
diff
changeset
|
312 return bat |
83
6c9b7cf1c5aa
push_cmd: delete empty svn directories, refactor directory creation
Patrick Mezard <pmezard@gmail.com>
parents:
81
diff
changeset
|
313 if path in deleteddirs: |
6c9b7cf1c5aa
push_cmd: delete empty svn directories, refactor directory creation
Patrick Mezard <pmezard@gmail.com>
parents:
81
diff
changeset
|
314 bat = editor.delete_entry(path, base_revision, parent, pool) |
6c9b7cf1c5aa
push_cmd: delete empty svn directories, refactor directory creation
Patrick Mezard <pmezard@gmail.com>
parents:
81
diff
changeset
|
315 batons.append(bat) |
6c9b7cf1c5aa
push_cmd: delete empty svn directories, refactor directory creation
Patrick Mezard <pmezard@gmail.com>
parents:
81
diff
changeset
|
316 return bat |
0
f2636cfed115
Initial import of hgsubversion into a public repository.
Augie Fackler <durin42@gmail.com>
parents:
diff
changeset
|
317 base_text, new_text, action = file_data[path] |
f2636cfed115
Initial import of hgsubversion into a public repository.
Augie Fackler <durin42@gmail.com>
parents:
diff
changeset
|
318 compute_delta = True |
f2636cfed115
Initial import of hgsubversion into a public repository.
Augie Fackler <durin42@gmail.com>
parents:
diff
changeset
|
319 if action == 'modify': |
f2636cfed115
Initial import of hgsubversion into a public repository.
Augie Fackler <durin42@gmail.com>
parents:
diff
changeset
|
320 baton = editor.open_file(path, parent, base_revision, pool) |
f2636cfed115
Initial import of hgsubversion into a public repository.
Augie Fackler <durin42@gmail.com>
parents:
diff
changeset
|
321 elif action == 'add': |
f2636cfed115
Initial import of hgsubversion into a public repository.
Augie Fackler <durin42@gmail.com>
parents:
diff
changeset
|
322 try: |
70
49b7cbe4c8e3
push_cmd: handle copies at file level
Patrick Mezard <pmezard@gmail.com>
parents:
66
diff
changeset
|
323 frompath, fromrev = copies.get(path, (None, -1)) |
49b7cbe4c8e3
push_cmd: handle copies at file level
Patrick Mezard <pmezard@gmail.com>
parents:
66
diff
changeset
|
324 if frompath: |
49b7cbe4c8e3
push_cmd: handle copies at file level
Patrick Mezard <pmezard@gmail.com>
parents:
66
diff
changeset
|
325 frompath = self.svn_url + '/' + frompath |
49b7cbe4c8e3
push_cmd: handle copies at file level
Patrick Mezard <pmezard@gmail.com>
parents:
66
diff
changeset
|
326 baton = editor.add_file(path, parent, frompath, fromrev, pool) |
63
2e30b59a9c19
Added some coverage pragmas to stop it from trying to cover things we can't test.
Augie Fackler <durin42@gmail.com>
parents:
59
diff
changeset
|
327 except (core.SubversionException, TypeError), e: #pragma: no cover |
0
f2636cfed115
Initial import of hgsubversion into a public repository.
Augie Fackler <durin42@gmail.com>
parents:
diff
changeset
|
328 print e.message |
f2636cfed115
Initial import of hgsubversion into a public repository.
Augie Fackler <durin42@gmail.com>
parents:
diff
changeset
|
329 raise |
f2636cfed115
Initial import of hgsubversion into a public repository.
Augie Fackler <durin42@gmail.com>
parents:
diff
changeset
|
330 elif action == 'delete': |
f2636cfed115
Initial import of hgsubversion into a public repository.
Augie Fackler <durin42@gmail.com>
parents:
diff
changeset
|
331 baton = editor.delete_entry(path, base_revision, parent, pool) |
f2636cfed115
Initial import of hgsubversion into a public repository.
Augie Fackler <durin42@gmail.com>
parents:
diff
changeset
|
332 compute_delta = False |
f2636cfed115
Initial import of hgsubversion into a public repository.
Augie Fackler <durin42@gmail.com>
parents:
diff
changeset
|
333 |
10
dfdc078661db
Auto-set executable, symlink, and auto-props.
Augie Fackler <durin42@gmail.com>
parents:
9
diff
changeset
|
334 if path in properties: |
dfdc078661db
Auto-set executable, symlink, and auto-props.
Augie Fackler <durin42@gmail.com>
parents:
9
diff
changeset
|
335 if properties[path].get('svn:special', None): |
dfdc078661db
Auto-set executable, symlink, and auto-props.
Augie Fackler <durin42@gmail.com>
parents:
9
diff
changeset
|
336 new_text = 'link %s' % new_text |
dfdc078661db
Auto-set executable, symlink, and auto-props.
Augie Fackler <durin42@gmail.com>
parents:
9
diff
changeset
|
337 for p, v in properties[path].iteritems(): |
dfdc078661db
Auto-set executable, symlink, and auto-props.
Augie Fackler <durin42@gmail.com>
parents:
9
diff
changeset
|
338 editor.change_file_prop(baton, p, v) |
dfdc078661db
Auto-set executable, symlink, and auto-props.
Augie Fackler <durin42@gmail.com>
parents:
9
diff
changeset
|
339 |
0
f2636cfed115
Initial import of hgsubversion into a public repository.
Augie Fackler <durin42@gmail.com>
parents:
diff
changeset
|
340 if compute_delta: |
f2636cfed115
Initial import of hgsubversion into a public repository.
Augie Fackler <durin42@gmail.com>
parents:
diff
changeset
|
341 handler, wh_baton = editor.apply_textdelta(baton, None, |
f2636cfed115
Initial import of hgsubversion into a public repository.
Augie Fackler <durin42@gmail.com>
parents:
diff
changeset
|
342 self.pool) |
f2636cfed115
Initial import of hgsubversion into a public repository.
Augie Fackler <durin42@gmail.com>
parents:
diff
changeset
|
343 |
f2636cfed115
Initial import of hgsubversion into a public repository.
Augie Fackler <durin42@gmail.com>
parents:
diff
changeset
|
344 txdelta_stream = delta.svn_txdelta( |
f2636cfed115
Initial import of hgsubversion into a public repository.
Augie Fackler <durin42@gmail.com>
parents:
diff
changeset
|
345 cStringIO.StringIO(base_text), cStringIO.StringIO(new_text), |
f2636cfed115
Initial import of hgsubversion into a public repository.
Augie Fackler <durin42@gmail.com>
parents:
diff
changeset
|
346 self.pool) |
f2636cfed115
Initial import of hgsubversion into a public repository.
Augie Fackler <durin42@gmail.com>
parents:
diff
changeset
|
347 delta.svn_txdelta_send_txstream(txdelta_stream, handler, |
f2636cfed115
Initial import of hgsubversion into a public repository.
Augie Fackler <durin42@gmail.com>
parents:
diff
changeset
|
348 wh_baton, pool) |
47
9738a7c4e3dd
fix svn push when there's just a file removal
Valentino Volonghi aka dialtone <valentino@adroll.com>
parents:
46
diff
changeset
|
349 |
9738a7c4e3dd
fix svn push when there's just a file removal
Valentino Volonghi aka dialtone <valentino@adroll.com>
parents:
46
diff
changeset
|
350 # TODO pass md5(new_text) instead of None |
9738a7c4e3dd
fix svn push when there's just a file removal
Valentino Volonghi aka dialtone <valentino@adroll.com>
parents:
46
diff
changeset
|
351 editor.close_file(baton, None, pool) |
0
f2636cfed115
Initial import of hgsubversion into a public repository.
Augie Fackler <durin42@gmail.com>
parents:
diff
changeset
|
352 |
f2636cfed115
Initial import of hgsubversion into a public repository.
Augie Fackler <durin42@gmail.com>
parents:
diff
changeset
|
353 delta.path_driver(editor, edit_baton, base_revision, paths, driver_cb, |
f2636cfed115
Initial import of hgsubversion into a public repository.
Augie Fackler <durin42@gmail.com>
parents:
diff
changeset
|
354 self.pool) |
f2636cfed115
Initial import of hgsubversion into a public repository.
Augie Fackler <durin42@gmail.com>
parents:
diff
changeset
|
355 editor.close_edit(edit_baton, self.pool) |
f2636cfed115
Initial import of hgsubversion into a public repository.
Augie Fackler <durin42@gmail.com>
parents:
diff
changeset
|
356 |
f2636cfed115
Initial import of hgsubversion into a public repository.
Augie Fackler <durin42@gmail.com>
parents:
diff
changeset
|
357 def get_replay(self, revision, editor, oldest_rev_i_have=0): |
f2636cfed115
Initial import of hgsubversion into a public repository.
Augie Fackler <durin42@gmail.com>
parents:
diff
changeset
|
358 # this method has a tendency to chew through RAM if you don't re-init |
f2636cfed115
Initial import of hgsubversion into a public repository.
Augie Fackler <durin42@gmail.com>
parents:
diff
changeset
|
359 self.init_ra_and_client() |
f2636cfed115
Initial import of hgsubversion into a public repository.
Augie Fackler <durin42@gmail.com>
parents:
diff
changeset
|
360 e_ptr, e_baton = delta.make_editor(editor) |
f2636cfed115
Initial import of hgsubversion into a public repository.
Augie Fackler <durin42@gmail.com>
parents:
diff
changeset
|
361 try: |
f2636cfed115
Initial import of hgsubversion into a public repository.
Augie Fackler <durin42@gmail.com>
parents:
diff
changeset
|
362 ra.replay(self.ra, revision, oldest_rev_i_have, True, e_ptr, |
f2636cfed115
Initial import of hgsubversion into a public repository.
Augie Fackler <durin42@gmail.com>
parents:
diff
changeset
|
363 e_baton, self.pool) |
63
2e30b59a9c19
Added some coverage pragmas to stop it from trying to cover things we can't test.
Augie Fackler <durin42@gmail.com>
parents:
59
diff
changeset
|
364 except core.SubversionException, e: #pragma: no cover |
0
f2636cfed115
Initial import of hgsubversion into a public repository.
Augie Fackler <durin42@gmail.com>
parents:
diff
changeset
|
365 # can I depend on this number being constant? |
f2636cfed115
Initial import of hgsubversion into a public repository.
Augie Fackler <durin42@gmail.com>
parents:
diff
changeset
|
366 if (e.message == "Server doesn't support the replay command" |
59
430af23bef4a
Performance fix for branches-from-tags in real replay, which is tied up with
Augie Fackler <durin42@gmail.com>
parents:
51
diff
changeset
|
367 or e.apr_err == 170003 |
51
fd5aadd552c8
Catch other varieties of the server not having replay.
Shun-ichi GOTO <shunichi.goto@gmail.com>
parents:
50
diff
changeset
|
368 or e.message == 'The requested report is unknown.' |
fd5aadd552c8
Catch other varieties of the server not having replay.
Shun-ichi GOTO <shunichi.goto@gmail.com>
parents:
50
diff
changeset
|
369 or e.apr_err == 200007): |
0
f2636cfed115
Initial import of hgsubversion into a public repository.
Augie Fackler <durin42@gmail.com>
parents:
diff
changeset
|
370 raise SubversionRepoCanNotReplay, ('This Subversion server ' |
f2636cfed115
Initial import of hgsubversion into a public repository.
Augie Fackler <durin42@gmail.com>
parents:
diff
changeset
|
371 'is older than 1.4.0, and cannot satisfy replay requests.') |
f2636cfed115
Initial import of hgsubversion into a public repository.
Augie Fackler <durin42@gmail.com>
parents:
diff
changeset
|
372 else: |
f2636cfed115
Initial import of hgsubversion into a public repository.
Augie Fackler <durin42@gmail.com>
parents:
diff
changeset
|
373 raise |
f2636cfed115
Initial import of hgsubversion into a public repository.
Augie Fackler <durin42@gmail.com>
parents:
diff
changeset
|
374 |
f2636cfed115
Initial import of hgsubversion into a public repository.
Augie Fackler <durin42@gmail.com>
parents:
diff
changeset
|
375 def get_unified_diff(self, path, revision, other_path=None, other_rev=None, |
f2636cfed115
Initial import of hgsubversion into a public repository.
Augie Fackler <durin42@gmail.com>
parents:
diff
changeset
|
376 deleted=True, ignore_type=False): |
f2636cfed115
Initial import of hgsubversion into a public repository.
Augie Fackler <durin42@gmail.com>
parents:
diff
changeset
|
377 """Gets a unidiff of path at revision against revision-1. |
f2636cfed115
Initial import of hgsubversion into a public repository.
Augie Fackler <durin42@gmail.com>
parents:
diff
changeset
|
378 """ |
89
edeec6829d80
SubversionRepo: remember svn.diff3() does not work
Patrick Mezard <pmezard@gmail.com>
parents:
87
diff
changeset
|
379 if not self.hasdiff3: |
edeec6829d80
SubversionRepo: remember svn.diff3() does not work
Patrick Mezard <pmezard@gmail.com>
parents:
87
diff
changeset
|
380 raise SubversionRepoCanNotDiff() |
0
f2636cfed115
Initial import of hgsubversion into a public repository.
Augie Fackler <durin42@gmail.com>
parents:
diff
changeset
|
381 # works around an svn server keeping too many open files (observed |
f2636cfed115
Initial import of hgsubversion into a public repository.
Augie Fackler <durin42@gmail.com>
parents:
diff
changeset
|
382 # in an svnserve from the 1.2 era) |
f2636cfed115
Initial import of hgsubversion into a public repository.
Augie Fackler <durin42@gmail.com>
parents:
diff
changeset
|
383 self.init_ra_and_client() |
f2636cfed115
Initial import of hgsubversion into a public repository.
Augie Fackler <durin42@gmail.com>
parents:
diff
changeset
|
384 |
f2636cfed115
Initial import of hgsubversion into a public repository.
Augie Fackler <durin42@gmail.com>
parents:
diff
changeset
|
385 assert path[0] != '/' |
f2636cfed115
Initial import of hgsubversion into a public repository.
Augie Fackler <durin42@gmail.com>
parents:
diff
changeset
|
386 url = self.svn_url + '/' + path |
f2636cfed115
Initial import of hgsubversion into a public repository.
Augie Fackler <durin42@gmail.com>
parents:
diff
changeset
|
387 url2 = url |
f2636cfed115
Initial import of hgsubversion into a public repository.
Augie Fackler <durin42@gmail.com>
parents:
diff
changeset
|
388 if other_path is not None: |
f2636cfed115
Initial import of hgsubversion into a public repository.
Augie Fackler <durin42@gmail.com>
parents:
diff
changeset
|
389 url2 = self.svn_url + '/' + other_path |
f2636cfed115
Initial import of hgsubversion into a public repository.
Augie Fackler <durin42@gmail.com>
parents:
diff
changeset
|
390 if other_rev is None: |
f2636cfed115
Initial import of hgsubversion into a public repository.
Augie Fackler <durin42@gmail.com>
parents:
diff
changeset
|
391 other_rev = revision - 1 |
81
85dcea81f22b
SubversionRepo: close files before rmtree() in diff3
Patrick Mezard <pmezard@gmail.com>
parents:
77
diff
changeset
|
392 old_cwd = os.getcwd() |
0
f2636cfed115
Initial import of hgsubversion into a public repository.
Augie Fackler <durin42@gmail.com>
parents:
diff
changeset
|
393 tmpdir = tempfile.mkdtemp('svnwrap_temp') |
89
edeec6829d80
SubversionRepo: remember svn.diff3() does not work
Patrick Mezard <pmezard@gmail.com>
parents:
87
diff
changeset
|
394 out, err = None, None |
66
a31968146f3c
svnwrap: Fix leakage of temp dirs by using try/finally blocks.
Augie Fackler <durin42@gmail.com>
parents:
63
diff
changeset
|
395 try: |
a31968146f3c
svnwrap: Fix leakage of temp dirs by using try/finally blocks.
Augie Fackler <durin42@gmail.com>
parents:
63
diff
changeset
|
396 # hot tip: the swig bridge doesn't like StringIO for these bad boys |
a31968146f3c
svnwrap: Fix leakage of temp dirs by using try/finally blocks.
Augie Fackler <durin42@gmail.com>
parents:
63
diff
changeset
|
397 out_path = os.path.join(tmpdir, 'diffout') |
a31968146f3c
svnwrap: Fix leakage of temp dirs by using try/finally blocks.
Augie Fackler <durin42@gmail.com>
parents:
63
diff
changeset
|
398 error_path = os.path.join(tmpdir, 'differr') |
89
edeec6829d80
SubversionRepo: remember svn.diff3() does not work
Patrick Mezard <pmezard@gmail.com>
parents:
87
diff
changeset
|
399 out = open(out_path, 'w') |
edeec6829d80
SubversionRepo: remember svn.diff3() does not work
Patrick Mezard <pmezard@gmail.com>
parents:
87
diff
changeset
|
400 err = open(error_path, 'w') |
81
85dcea81f22b
SubversionRepo: close files before rmtree() in diff3
Patrick Mezard <pmezard@gmail.com>
parents:
77
diff
changeset
|
401 try: |
85dcea81f22b
SubversionRepo: close files before rmtree() in diff3
Patrick Mezard <pmezard@gmail.com>
parents:
77
diff
changeset
|
402 client.diff3([], url2, optrev(other_rev), url, optrev(revision), |
85dcea81f22b
SubversionRepo: close files before rmtree() in diff3
Patrick Mezard <pmezard@gmail.com>
parents:
77
diff
changeset
|
403 True, True, deleted, ignore_type, 'UTF-8', out, err, |
85dcea81f22b
SubversionRepo: close files before rmtree() in diff3
Patrick Mezard <pmezard@gmail.com>
parents:
77
diff
changeset
|
404 self.client_context, self.pool) |
89
edeec6829d80
SubversionRepo: remember svn.diff3() does not work
Patrick Mezard <pmezard@gmail.com>
parents:
87
diff
changeset
|
405 except core.SubversionException, e: |
edeec6829d80
SubversionRepo: remember svn.diff3() does not work
Patrick Mezard <pmezard@gmail.com>
parents:
87
diff
changeset
|
406 # "Can't write to stream: The handle is invalid." |
edeec6829d80
SubversionRepo: remember svn.diff3() does not work
Patrick Mezard <pmezard@gmail.com>
parents:
87
diff
changeset
|
407 # This error happens systematically under Windows, possibly |
edeec6829d80
SubversionRepo: remember svn.diff3() does not work
Patrick Mezard <pmezard@gmail.com>
parents:
87
diff
changeset
|
408 # related to file handles being non-write shareable by default. |
edeec6829d80
SubversionRepo: remember svn.diff3() does not work
Patrick Mezard <pmezard@gmail.com>
parents:
87
diff
changeset
|
409 if e.apr_err != 720006: |
edeec6829d80
SubversionRepo: remember svn.diff3() does not work
Patrick Mezard <pmezard@gmail.com>
parents:
87
diff
changeset
|
410 raise |
edeec6829d80
SubversionRepo: remember svn.diff3() does not work
Patrick Mezard <pmezard@gmail.com>
parents:
87
diff
changeset
|
411 self.hasdiff3 = False |
edeec6829d80
SubversionRepo: remember svn.diff3() does not work
Patrick Mezard <pmezard@gmail.com>
parents:
87
diff
changeset
|
412 raise SubversionRepoCanNotDiff() |
edeec6829d80
SubversionRepo: remember svn.diff3() does not work
Patrick Mezard <pmezard@gmail.com>
parents:
87
diff
changeset
|
413 out.close() |
edeec6829d80
SubversionRepo: remember svn.diff3() does not work
Patrick Mezard <pmezard@gmail.com>
parents:
87
diff
changeset
|
414 err.close() |
edeec6829d80
SubversionRepo: remember svn.diff3() does not work
Patrick Mezard <pmezard@gmail.com>
parents:
87
diff
changeset
|
415 out, err = None, None |
66
a31968146f3c
svnwrap: Fix leakage of temp dirs by using try/finally blocks.
Augie Fackler <durin42@gmail.com>
parents:
63
diff
changeset
|
416 assert len(open(error_path).read()) == 0 |
a31968146f3c
svnwrap: Fix leakage of temp dirs by using try/finally blocks.
Augie Fackler <durin42@gmail.com>
parents:
63
diff
changeset
|
417 diff = open(out_path).read() |
a31968146f3c
svnwrap: Fix leakage of temp dirs by using try/finally blocks.
Augie Fackler <durin42@gmail.com>
parents:
63
diff
changeset
|
418 return diff |
a31968146f3c
svnwrap: Fix leakage of temp dirs by using try/finally blocks.
Augie Fackler <durin42@gmail.com>
parents:
63
diff
changeset
|
419 finally: |
89
edeec6829d80
SubversionRepo: remember svn.diff3() does not work
Patrick Mezard <pmezard@gmail.com>
parents:
87
diff
changeset
|
420 if out: out.close() |
edeec6829d80
SubversionRepo: remember svn.diff3() does not work
Patrick Mezard <pmezard@gmail.com>
parents:
87
diff
changeset
|
421 if err: err.close() |
66
a31968146f3c
svnwrap: Fix leakage of temp dirs by using try/finally blocks.
Augie Fackler <durin42@gmail.com>
parents:
63
diff
changeset
|
422 shutil.rmtree(tmpdir) |
81
85dcea81f22b
SubversionRepo: close files before rmtree() in diff3
Patrick Mezard <pmezard@gmail.com>
parents:
77
diff
changeset
|
423 os.chdir(old_cwd) |
0
f2636cfed115
Initial import of hgsubversion into a public repository.
Augie Fackler <durin42@gmail.com>
parents:
diff
changeset
|
424 |
f2636cfed115
Initial import of hgsubversion into a public repository.
Augie Fackler <durin42@gmail.com>
parents:
diff
changeset
|
425 def get_file(self, path, revision): |
76
6c62bd201785
SubversionRepo: make get_file() return the file mode
Patrick Mezard <pmezard@gmail.com>
parents:
75
diff
changeset
|
426 """Return content and mode of file at given path and revision. |
6c62bd201785
SubversionRepo: make get_file() return the file mode
Patrick Mezard <pmezard@gmail.com>
parents:
75
diff
changeset
|
427 |
6c62bd201785
SubversionRepo: make get_file() return the file mode
Patrick Mezard <pmezard@gmail.com>
parents:
75
diff
changeset
|
428 Content is raw svn content, symlinks content is still prefixed |
6c62bd201785
SubversionRepo: make get_file() return the file mode
Patrick Mezard <pmezard@gmail.com>
parents:
75
diff
changeset
|
429 by 'link '. Mode is 'x' if file is executable, 'l' if a symlink, |
6c62bd201785
SubversionRepo: make get_file() return the file mode
Patrick Mezard <pmezard@gmail.com>
parents:
75
diff
changeset
|
430 the empty string otherwise. If the file does not exist at this |
6c62bd201785
SubversionRepo: make get_file() return the file mode
Patrick Mezard <pmezard@gmail.com>
parents:
75
diff
changeset
|
431 revision, raise IOError. |
6c62bd201785
SubversionRepo: make get_file() return the file mode
Patrick Mezard <pmezard@gmail.com>
parents:
75
diff
changeset
|
432 """ |
6c62bd201785
SubversionRepo: make get_file() return the file mode
Patrick Mezard <pmezard@gmail.com>
parents:
75
diff
changeset
|
433 mode = '' |
0
f2636cfed115
Initial import of hgsubversion into a public repository.
Augie Fackler <durin42@gmail.com>
parents:
diff
changeset
|
434 out = cStringIO.StringIO() |
66
a31968146f3c
svnwrap: Fix leakage of temp dirs by using try/finally blocks.
Augie Fackler <durin42@gmail.com>
parents:
63
diff
changeset
|
435 try: |
76
6c62bd201785
SubversionRepo: make get_file() return the file mode
Patrick Mezard <pmezard@gmail.com>
parents:
75
diff
changeset
|
436 info = ra.get_file(self.ra, path, revision, out) |
6c62bd201785
SubversionRepo: make get_file() return the file mode
Patrick Mezard <pmezard@gmail.com>
parents:
75
diff
changeset
|
437 if isinstance(info, list): |
6c62bd201785
SubversionRepo: make get_file() return the file mode
Patrick Mezard <pmezard@gmail.com>
parents:
75
diff
changeset
|
438 info = info[-1] |
6c62bd201785
SubversionRepo: make get_file() return the file mode
Patrick Mezard <pmezard@gmail.com>
parents:
75
diff
changeset
|
439 mode = ("svn:executable" in info) and 'x' or '' |
6c62bd201785
SubversionRepo: make get_file() return the file mode
Patrick Mezard <pmezard@gmail.com>
parents:
75
diff
changeset
|
440 mode = ("svn:special" in info) and 'l' or mode |
74
450d5d9d3b80
SubversionRepo: do not use temporary file in get_file()
Patrick Mezard <pmezard@gmail.com>
parents:
70
diff
changeset
|
441 except core.SubversionException, e: |
450d5d9d3b80
SubversionRepo: do not use temporary file in get_file()
Patrick Mezard <pmezard@gmail.com>
parents:
70
diff
changeset
|
442 notfound = (core.SVN_ERR_FS_NOT_FOUND, |
450d5d9d3b80
SubversionRepo: do not use temporary file in get_file()
Patrick Mezard <pmezard@gmail.com>
parents:
70
diff
changeset
|
443 core.SVN_ERR_RA_DAV_PATH_NOT_FOUND) |
450d5d9d3b80
SubversionRepo: do not use temporary file in get_file()
Patrick Mezard <pmezard@gmail.com>
parents:
70
diff
changeset
|
444 if e.apr_err in notfound: # File not found |
450d5d9d3b80
SubversionRepo: do not use temporary file in get_file()
Patrick Mezard <pmezard@gmail.com>
parents:
70
diff
changeset
|
445 raise IOError() |
450d5d9d3b80
SubversionRepo: do not use temporary file in get_file()
Patrick Mezard <pmezard@gmail.com>
parents:
70
diff
changeset
|
446 raise |
450d5d9d3b80
SubversionRepo: do not use temporary file in get_file()
Patrick Mezard <pmezard@gmail.com>
parents:
70
diff
changeset
|
447 data = out.getvalue() |
76
6c62bd201785
SubversionRepo: make get_file() return the file mode
Patrick Mezard <pmezard@gmail.com>
parents:
75
diff
changeset
|
448 return data, mode |
0
f2636cfed115
Initial import of hgsubversion into a public repository.
Augie Fackler <durin42@gmail.com>
parents:
diff
changeset
|
449 |
f2636cfed115
Initial import of hgsubversion into a public repository.
Augie Fackler <durin42@gmail.com>
parents:
diff
changeset
|
450 def proplist(self, path, revision, recurse=False): |
f2636cfed115
Initial import of hgsubversion into a public repository.
Augie Fackler <durin42@gmail.com>
parents:
diff
changeset
|
451 if path[-1] == '/': |
f2636cfed115
Initial import of hgsubversion into a public repository.
Augie Fackler <durin42@gmail.com>
parents:
diff
changeset
|
452 path = path[:-1] |
f2636cfed115
Initial import of hgsubversion into a public repository.
Augie Fackler <durin42@gmail.com>
parents:
diff
changeset
|
453 if path[0] == '/': |
f2636cfed115
Initial import of hgsubversion into a public repository.
Augie Fackler <durin42@gmail.com>
parents:
diff
changeset
|
454 path = path[1:] |
75
cca31b6b1318
SubversionRepo: add optrev() to help generate client API revisions
Patrick Mezard <pmezard@gmail.com>
parents:
74
diff
changeset
|
455 rev = optrev(revision) |
0
f2636cfed115
Initial import of hgsubversion into a public repository.
Augie Fackler <durin42@gmail.com>
parents:
diff
changeset
|
456 pl = dict(client.proplist2(self.svn_url+'/'+path, rev, rev, True, |
f2636cfed115
Initial import of hgsubversion into a public repository.
Augie Fackler <durin42@gmail.com>
parents:
diff
changeset
|
457 self.client_context, self.pool)) |
f2636cfed115
Initial import of hgsubversion into a public repository.
Augie Fackler <durin42@gmail.com>
parents:
diff
changeset
|
458 pl2 = {} |
f2636cfed115
Initial import of hgsubversion into a public repository.
Augie Fackler <durin42@gmail.com>
parents:
diff
changeset
|
459 for key, value in pl.iteritems(): |
f2636cfed115
Initial import of hgsubversion into a public repository.
Augie Fackler <durin42@gmail.com>
parents:
diff
changeset
|
460 pl2[key[len(self.svn_url)+1:]] = value |
f2636cfed115
Initial import of hgsubversion into a public repository.
Augie Fackler <durin42@gmail.com>
parents:
diff
changeset
|
461 return pl2 |
f2636cfed115
Initial import of hgsubversion into a public repository.
Augie Fackler <durin42@gmail.com>
parents:
diff
changeset
|
462 |
f2636cfed115
Initial import of hgsubversion into a public repository.
Augie Fackler <durin42@gmail.com>
parents:
diff
changeset
|
463 def fetch_all_files_to_dir(self, path, revision, checkout_path): |
75
cca31b6b1318
SubversionRepo: add optrev() to help generate client API revisions
Patrick Mezard <pmezard@gmail.com>
parents:
74
diff
changeset
|
464 rev = optrev(revision) |
0
f2636cfed115
Initial import of hgsubversion into a public repository.
Augie Fackler <durin42@gmail.com>
parents:
diff
changeset
|
465 client.export3(self.svn_url+'/'+path, checkout_path, rev, |
f2636cfed115
Initial import of hgsubversion into a public repository.
Augie Fackler <durin42@gmail.com>
parents:
diff
changeset
|
466 rev, True, True, True, 'LF', # should be 'CRLF' on win32 |
f2636cfed115
Initial import of hgsubversion into a public repository.
Augie Fackler <durin42@gmail.com>
parents:
diff
changeset
|
467 self.client_context, self.pool) |
f2636cfed115
Initial import of hgsubversion into a public repository.
Augie Fackler <durin42@gmail.com>
parents:
diff
changeset
|
468 |
77
ed3dd5bf45da
fetch_command: bypass export3() and checkout manually
Patrick Mezard <pmezard@gmail.com>
parents:
76
diff
changeset
|
469 def list_files(self, dirpath, revision): |
ed3dd5bf45da
fetch_command: bypass export3() and checkout manually
Patrick Mezard <pmezard@gmail.com>
parents:
76
diff
changeset
|
470 """List the content of a directory at a given revision, recursively. |
ed3dd5bf45da
fetch_command: bypass export3() and checkout manually
Patrick Mezard <pmezard@gmail.com>
parents:
76
diff
changeset
|
471 |
ed3dd5bf45da
fetch_command: bypass export3() and checkout manually
Patrick Mezard <pmezard@gmail.com>
parents:
76
diff
changeset
|
472 Yield tuples (path, kind) where 'path' is the entry path relatively to |
ed3dd5bf45da
fetch_command: bypass export3() and checkout manually
Patrick Mezard <pmezard@gmail.com>
parents:
76
diff
changeset
|
473 'dirpath' and 'kind' is 'f' if the entry is a file, 'd' if it is a |
ed3dd5bf45da
fetch_command: bypass export3() and checkout manually
Patrick Mezard <pmezard@gmail.com>
parents:
76
diff
changeset
|
474 directory. Raise IOError if the directory cannot be found at given |
ed3dd5bf45da
fetch_command: bypass export3() and checkout manually
Patrick Mezard <pmezard@gmail.com>
parents:
76
diff
changeset
|
475 revision. |
ed3dd5bf45da
fetch_command: bypass export3() and checkout manually
Patrick Mezard <pmezard@gmail.com>
parents:
76
diff
changeset
|
476 """ |
ed3dd5bf45da
fetch_command: bypass export3() and checkout manually
Patrick Mezard <pmezard@gmail.com>
parents:
76
diff
changeset
|
477 dirpath = dirpath.strip('/') |
ed3dd5bf45da
fetch_command: bypass export3() and checkout manually
Patrick Mezard <pmezard@gmail.com>
parents:
76
diff
changeset
|
478 pool = core.Pool() |
ed3dd5bf45da
fetch_command: bypass export3() and checkout manually
Patrick Mezard <pmezard@gmail.com>
parents:
76
diff
changeset
|
479 rpath = '/'.join([self.svn_url, dirpath]).strip('/') |
ed3dd5bf45da
fetch_command: bypass export3() and checkout manually
Patrick Mezard <pmezard@gmail.com>
parents:
76
diff
changeset
|
480 rev = optrev(revision) |
ed3dd5bf45da
fetch_command: bypass export3() and checkout manually
Patrick Mezard <pmezard@gmail.com>
parents:
76
diff
changeset
|
481 try: |
ed3dd5bf45da
fetch_command: bypass export3() and checkout manually
Patrick Mezard <pmezard@gmail.com>
parents:
76
diff
changeset
|
482 entries = client.ls(rpath, rev, True, self.client_context, pool) |
ed3dd5bf45da
fetch_command: bypass export3() and checkout manually
Patrick Mezard <pmezard@gmail.com>
parents:
76
diff
changeset
|
483 except core.SubversionException, e: |
ed3dd5bf45da
fetch_command: bypass export3() and checkout manually
Patrick Mezard <pmezard@gmail.com>
parents:
76
diff
changeset
|
484 if e.apr_err == core.SVN_ERR_FS_NOT_FOUND: |
ed3dd5bf45da
fetch_command: bypass export3() and checkout manually
Patrick Mezard <pmezard@gmail.com>
parents:
76
diff
changeset
|
485 raise IOError('%s cannot be found at r%d' % (dirpath, revision)) |
ed3dd5bf45da
fetch_command: bypass export3() and checkout manually
Patrick Mezard <pmezard@gmail.com>
parents:
76
diff
changeset
|
486 raise |
ed3dd5bf45da
fetch_command: bypass export3() and checkout manually
Patrick Mezard <pmezard@gmail.com>
parents:
76
diff
changeset
|
487 for path, e in entries.iteritems(): |
87
b033d74be76b
fetch_command: in stupid non-diffy mode, take changed paths in account
Patrick Mezard <pmezard@gmail.com>
parents:
83
diff
changeset
|
488 kind = _svntypes.get(e.kind) |
77
ed3dd5bf45da
fetch_command: bypass export3() and checkout manually
Patrick Mezard <pmezard@gmail.com>
parents:
76
diff
changeset
|
489 yield path, kind |
ed3dd5bf45da
fetch_command: bypass export3() and checkout manually
Patrick Mezard <pmezard@gmail.com>
parents:
76
diff
changeset
|
490 |
87
b033d74be76b
fetch_command: in stupid non-diffy mode, take changed paths in account
Patrick Mezard <pmezard@gmail.com>
parents:
83
diff
changeset
|
491 def checkpath(self, path, revision): |
b033d74be76b
fetch_command: in stupid non-diffy mode, take changed paths in account
Patrick Mezard <pmezard@gmail.com>
parents:
83
diff
changeset
|
492 """Return the entry type at the given revision, 'f', 'd' or None |
b033d74be76b
fetch_command: in stupid non-diffy mode, take changed paths in account
Patrick Mezard <pmezard@gmail.com>
parents:
83
diff
changeset
|
493 if the entry does not exist. |
b033d74be76b
fetch_command: in stupid non-diffy mode, take changed paths in account
Patrick Mezard <pmezard@gmail.com>
parents:
83
diff
changeset
|
494 """ |
b033d74be76b
fetch_command: in stupid non-diffy mode, take changed paths in account
Patrick Mezard <pmezard@gmail.com>
parents:
83
diff
changeset
|
495 kind = ra.check_path(self.ra, path.strip('/'), revision) |
b033d74be76b
fetch_command: in stupid non-diffy mode, take changed paths in account
Patrick Mezard <pmezard@gmail.com>
parents:
83
diff
changeset
|
496 return _svntypes.get(kind) |