170
161
to_weave = self.to_weaves.get_weave_or_empty(file_id,
171
162
self.to_repository.get_transaction())
172
from_weave = self.from_weaves.get_weave(file_id,
173
self.from_repository.get_transaction())
175
if to_weave.numversions() > 0:
164
if to_weave.num_versions() > 0:
176
165
# destination has contents, must merge
178
to_weave.join(from_weave)
179
except errors.WeaveParentMismatch:
180
to_weave.reweave(from_weave)
166
from_weave = self.from_weaves.get_weave(file_id,
167
self.from_repository.get_transaction())
168
# we fetch all the texts, because texts do
169
# not reference anything, and its cheap enough
170
to_weave.join(from_weave)
182
172
# destination is empty, just replace it
183
to_weave = from_weave.copy()
185
self.to_weaves.put_weave(file_id, to_weave,
186
self.to_repository.get_transaction())
173
self.to_weaves.copy_multi(self.from_weaves, [file_id], self.pb,
174
self.from_repository.get_transaction(),
175
self.to_repository.get_transaction())
189
178
def _fetch_inventory_weave(self, revs):
190
179
self.pb.update("inventory fetch", 0, 2)
191
from_weave = self.from_repository.get_inventory_weave()
192
self.to_inventory_weave = self.to_repository.get_inventory_weave()
193
self.pb.update("inventory fetch", 1, 2)
194
self.to_inventory_weave = self.to_control.get_weave('inventory',
180
to_weave = self.to_control.get_weave('inventory',
195
181
self.to_repository.get_transaction())
196
self.pb.update("inventory fetch", 2, 2)
198
if self.to_inventory_weave.numversions() > 0:
183
if to_weave.num_versions() > 0:
199
184
# destination has contents, must merge
201
self.to_inventory_weave.join(from_weave, pb=self.pb, msg='merge inventory')
202
except errors.WeaveParentMismatch:
203
self.to_inventory_weave.reweave(from_weave, pb=self.pb, msg='reweave inventory')
185
self.pb.update("inventory fetch", 1, 2)
186
from_weave = self.from_repository.get_inventory_weave()
187
self.pb.update("inventory fetch", 2, 2)
188
# we fetch only the referenced inventories because we do not
189
# know for unselected inventories whether all their required
190
# texts are present in the other repository - it could be
192
to_weave.join(from_weave, pb=self.pb, msg='merge inventory',
205
195
# destination is empty, just replace it
206
self.to_inventory_weave = from_weave.copy()
208
# must be written before pulling any revisions
209
self.to_control.put_weave('inventory', self.to_inventory_weave,
210
self.to_repository.get_transaction())
196
self.to_control.copy_multi(self.from_control,
199
self.from_repository.get_transaction(),
200
self.to_repository.get_transaction())
205
class GenericRepoFetcher(RepoFetcher):
206
"""This is a generic repo to repo fetcher.
208
This makes minimal assumptions about repo layout and contents.
209
It triggers a reconciliation after fetching to ensure integrity.
212
def _fetch_revision_texts(self, revs):
213
self.to_transaction = self.to_repository.get_transaction()
217
self.pb.update('copying revisions', count, total)
219
sig_text = self.from_repository.get_signature_text(rev)
220
self.to_repository._revision_store.add_revision_signature_text(
221
rev, sig_text, self.to_transaction)
222
except errors.NoSuchRevision:
225
self.to_repository._revision_store.add_revision(
226
self.from_repository.get_revision(rev),
229
self.pb.update('copying revisions', count, total)
230
# fixup inventory if needed:
231
# this is expensive because we have no inverse index to current ghosts.
232
# but on local disk its a few seconds and sftp push is already insane.
234
# FIXME: repository should inform if this is needed.
235
reconciler = RepoReconciler(self.to_repository)
236
reconciler.reconcile()
239
class KnitRepoFetcher(RepoFetcher):
240
"""This is a knit format repository specific fetcher.
242
This differs from the GenericRepoFetcher by not doing a
243
reconciliation after copying, and using knit joining to
247
def _fetch_revision_texts(self, revs):
248
# may need to be a InterRevisionStore call here.
249
from_transaction = self.from_repository.get_transaction()
250
to_transaction = self.to_repository.get_transaction()
251
to_sf = self.to_repository._revision_store.get_signature_file(
253
from_sf = self.from_repository._revision_store.get_signature_file(
255
to_sf.join(from_sf, version_ids=revs, pb=self.pb, ignore_missing=True)
256
to_rf = self.to_repository._revision_store.get_revision_file(
258
from_rf = self.from_repository._revision_store.get_revision_file(
260
to_rf.join(from_rf, version_ids=revs, pb=self.pb)
261
reconciler = RepoReconciler(self.to_repository)
262
reconciler.reconcile()
215
265
class Fetcher(object):
216
266
"""Backwards compatability glue for branch.fetch()."""