forked from readthedocs/readthedocs.org
/
hg.py
109 lines (97 loc) · 3.46 KB
/
hg.py
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
import csv
from StringIO import StringIO
from projects.exceptions import ProjectImportError
from vcs_support.base import BaseVCS, VCSVersion
class Backend(BaseVCS):
supports_tags = True
supports_branches = True
fallback_branch = 'default'
def update(self):
super(Backend, self).update()
retcode = self.run('hg', 'status')[0]
if retcode == 0:
return self.pull()
else:
return self.clone()
def pull(self):
pull_output = self.run('hg', 'pull')
if pull_output[0] != 0:
raise ProjectImportError(
("Failed to get code from '%s' (hg pull): %s"
% (self.repo_url, pull_output[0]))
)
update_output = self.run('hg', 'update', '-C')[0]
if update_output[0] != 0:
raise ProjectImportError(
("Failed to get code from '%s' (hg update): %s"
% (self.repo_url, pull_output[0]))
)
return update_output
def clone(self):
output = self.run('hg', 'clone', self.repo_url, '.')
if output[0] != 0:
raise ProjectImportError(
("Failed to get code from '%s' (hg clone): %s"
% (self.repo_url, output[0]))
)
return output
@property
def branches(self):
retcode, stdout = self.run('hg', 'branches', '--active')[:2]
# error (or no tags found)
if retcode != 0:
return []
return self.parse_branches(stdout)
def parse_branches(self, data):
"""
stable 13575:8e94a1b4e9a4
default 13572:1bb2a56a9d73
"""
raw_branches = csv.reader(StringIO(data), delimiter=' ')
clean_branches = []
for branch in raw_branches:
branch = filter(lambda f: f != '', branch)
if branch == []:
continue
name, rev = branch
clean_branches.append(VCSVersion(self, name, name))
return clean_branches
@property
def tags(self):
retcode, stdout = self.run('hg', 'tags')[:2]
# error (or no tags found)
if retcode != 0:
return []
return self.parse_tags(stdout)
def parse_tags(self, data):
"""
Parses output of show-ref --tags, eg:
tip 278:c4b2d21db51a
0.2.2 152:6b0364d98837
0.2.1 117:a14b7b6ffa03
0.1 50:30c2c6b3a055
"""
# parse the lines into a list of tuples (commit-hash, tag ref name)
raw_tags = csv.reader(StringIO(data), delimiter=' ')
vcs_tags = []
for row in raw_tags:
row = filter(lambda f: f != '', row)
if row == []:
continue
name, commit = row
if name == 'tip':
continue
revision, commit_hash = commit.split(':')
vcs_tags.append(VCSVersion(self, commit_hash, name))
return vcs_tags
def checkout(self, identifier=None):
super(Backend, self).checkout()
if not identifier:
identifier = 'tip'
retcode = self.run('hg', 'status')[0]
if retcode == 0:
self.run('hg', 'pull')
return self.run('hg', 'update', '-C', identifier)
else:
self.clone()
return self.run('hg', 'update', '-C', identifier)