Show More
@@ -126,9 +126,79 b' class gittreemanifest(object):' | |||
|
126 | 126 | def hasdir(self, dir): |
|
127 | 127 | return dir in self._dirs |
|
128 | 128 | |
|
129 |
def diff(self, other, match= |
|
|
130 | # TODO | |
|
131 | assert False | |
|
129 | def diff(self, other, match=lambda x: True, clean=False): | |
|
130 | '''Finds changes between the current manifest and m2. | |
|
131 | ||
|
132 | The result is returned as a dict with filename as key and | |
|
133 | values of the form ((n1,fl1),(n2,fl2)), where n1/n2 is the | |
|
134 | nodeid in the current/other manifest and fl1/fl2 is the flag | |
|
135 | in the current/other manifest. Where the file does not exist, | |
|
136 | the nodeid will be None and the flags will be the empty | |
|
137 | string. | |
|
138 | ''' | |
|
139 | result = {} | |
|
140 | ||
|
141 | def _iterativediff(t1, t2, subdir): | |
|
142 | """compares two trees and appends new tree nodes to examine to | |
|
143 | the stack""" | |
|
144 | if t1 is None: | |
|
145 | t1 = {} | |
|
146 | if t2 is None: | |
|
147 | t2 = {} | |
|
148 | ||
|
149 | for e1 in t1: | |
|
150 | realname = subdir + pycompat.fsencode(e1.name) | |
|
151 | ||
|
152 | if e1.type == pygit2.GIT_OBJ_TREE: | |
|
153 | try: | |
|
154 | e2 = t2[e1.name] | |
|
155 | if e2.type != pygit2.GIT_OBJ_TREE: | |
|
156 | e2 = None | |
|
157 | except KeyError: | |
|
158 | e2 = None | |
|
159 | ||
|
160 | stack.append((realname + b'/', e1, e2)) | |
|
161 | else: | |
|
162 | n1, fl1 = self.find(realname) | |
|
163 | ||
|
164 | try: | |
|
165 | e2 = t2[e1.name] | |
|
166 | n2, fl2 = other.find(realname) | |
|
167 | except KeyError: | |
|
168 | e2 = None | |
|
169 | n2, fl2 = (None, b'') | |
|
170 | ||
|
171 | if e2 is not None and e2.type == pygit2.GIT_OBJ_TREE: | |
|
172 | stack.append((realname + b'/', None, e2)) | |
|
173 | ||
|
174 | if not match(realname): | |
|
175 | continue | |
|
176 | ||
|
177 | if n1 != n2 or fl1 != fl2: | |
|
178 | result[realname] = ((n1, fl1), (n2, fl2)) | |
|
179 | elif clean: | |
|
180 | result[realname] = None | |
|
181 | ||
|
182 | for e2 in t2: | |
|
183 | if e2.name in t1: | |
|
184 | continue | |
|
185 | ||
|
186 | realname = subdir + pycompat.fsencode(e2.name) | |
|
187 | ||
|
188 | if e2.type == pygit2.GIT_OBJ_TREE: | |
|
189 | stack.append((realname + b'/', None, e2)) | |
|
190 | elif match(realname): | |
|
191 | n2, fl2 = other.find(realname) | |
|
192 | result[realname] = ((None, b''), (n2, fl2)) | |
|
193 | ||
|
194 | stack = [] | |
|
195 | _iterativediff(self._tree, other._tree, b'') | |
|
196 | while stack: | |
|
197 | subdir, t1, t2 = stack.pop() | |
|
198 | # stack is populated in the function call | |
|
199 | _iterativediff(t1, t2, subdir) | |
|
200 | ||
|
201 | return result | |
|
132 | 202 | |
|
133 | 203 | def setflag(self, path, flag): |
|
134 | 204 | node, unused_flag = self._resolve_entry(path) |
General Comments 0
You need to be logged in to leave comments.
Login now