comparison MoinMoin/action/SyncPages.py @ 1136:4ba6da7e23a4

Started implementing the merging process. Not working yet.
author Alexander Schremmer <alex AT alexanderweb DOT de>
date Fri, 04 Aug 2006 22:12:30 +0200
parents bf5f8afacf59
children 0390d7857d87
comparison
equal deleted inserted replaced
1135:bf5f8afacf59 1136:4ba6da7e23a4
24 from MoinMoin import wikiutil, config, user 24 from MoinMoin import wikiutil, config, user
25 from MoinMoin.packages import unpackLine, packLine 25 from MoinMoin.packages import unpackLine, packLine
26 from MoinMoin.PageEditor import PageEditor 26 from MoinMoin.PageEditor import PageEditor
27 from MoinMoin.Page import Page 27 from MoinMoin.Page import Page
28 from MoinMoin.wikidicts import Dict, Group 28 from MoinMoin.wikidicts import Dict, Group
29 from MoinMoin.wikisync import TagStore
30 from MoinMoin.util.bdiff import decompress, patch
29 31
30 # directions 32 # directions
31 UP, DOWN, BOTH = range(3) 33 UP, DOWN, BOTH = range(3)
32 directions_map = {"up": UP, "down": DOWN, "both": BOTH} 34 directions_map = {"up": UP, "down": DOWN, "both": BOTH}
33 35
44 46
45 class ActionStatus(Exception): pass 47 class ActionStatus(Exception): pass
46 48
47 class UnsupportedWikiException(Exception): pass 49 class UnsupportedWikiException(Exception): pass
48 50
49 # Move these classes to MoinMoin.wikisync 51 # XXX Move these classes to MoinMoin.wikisync
50 class SyncPage(object): 52 class SyncPage(object):
51 """ This class represents a page in (another) wiki. """ 53 """ This class represents a page in (another) wiki. """
52 def __init__(self, name, local_rev=None, remote_rev=None, local_name=None, remote_name=None): 54 def __init__(self, name, local_rev=None, remote_rev=None, local_name=None, remote_name=None):
53 self.name = name 55 self.name = name
54 self.local_rev = local_rev 56 self.local_rev = local_rev
170 self.iwid_full = packLine([remote_iwid, interwikiname]) 172 self.iwid_full = packLine([remote_iwid, interwikiname])
171 173
172 def createConnection(self): 174 def createConnection(self):
173 return xmlrpclib.ServerProxy(self.xmlrpc_url, allow_none=True, verbose=True) 175 return xmlrpclib.ServerProxy(self.xmlrpc_url, allow_none=True, verbose=True)
174 176
177 def get_diff(self, pagename, from_rev, to_rev):
178 return str(self.connection.getDiff(pagename, from_rev, to_rev))
179
175 # Methods implementing the RemoteWiki interface 180 # Methods implementing the RemoteWiki interface
176 def get_interwiki_name(self): 181 def get_interwiki_name(self):
177 return self.connection.interwikiName()[0] 182 return self.connection.interwikiName()[0]
178 183
179 def get_pages(self): 184 def get_pages(self):
298 303
299 return self.page.send_page(self.request, msg=_("Syncronisation finished.")) 304 return self.page.send_page(self.request, msg=_("Syncronisation finished."))
300 305
301 def sync(self, params, local, remote): 306 def sync(self, params, local, remote):
302 """ This method does the syncronisation work. """ 307 """ This method does the syncronisation work. """
303 308
309 l_pages = local.get_pages()
304 r_pages = remote.get_pages() 310 r_pages = remote.get_pages()
305 l_pages = local.get_pages()
306 311
307 if params["groupList"]: 312 if params["groupList"]:
308 pages_from_groupList = set(local.getGroupItems(params["groupList"])) 313 pages_from_groupList = set(local.getGroupItems(params["groupList"]))
309 r_pages = SyncPage.filter(r_pages, pages_from_groupList.__contains__) 314 r_pages = SyncPage.filter(r_pages, pages_from_groupList.__contains__)
310 l_pages = SyncPage.filter(l_pages, pages_from_groupList.__contains__) 315 l_pages = SyncPage.filter(l_pages, pages_from_groupList.__contains__)
319 324
320 on_both_sides = list(SyncPage.iter_local_and_remote(m_pages)) 325 on_both_sides = list(SyncPage.iter_local_and_remote(m_pages))
321 remote_but_not_local = list(SyncPage.iter_remote_only(m_pages)) 326 remote_but_not_local = list(SyncPage.iter_remote_only(m_pages))
322 local_but_not_remote = list(SyncPage.iter_local_only(m_pages)) 327 local_but_not_remote = list(SyncPage.iter_local_only(m_pages))
323 328
324 # some initial test code 329 # some initial test code (XXX remove)
325 r_new_pages = u", ".join([unicode(x) for x in remote_but_not_local]) 330 #r_new_pages = u", ".join([unicode(x) for x in remote_but_not_local])
326 l_new_pages = u", ".join([unicode(x) for x in local_but_not_remote]) 331 #l_new_pages = u", ".join([unicode(x) for x in local_but_not_remote])
327 raise ActionStatus("These pages are in the remote wiki, but not local: " + wikiutil.escape(r_new_pages) + "<br>These pages are in the local wiki, but not in the remote one: " + wikiutil.escape(l_new_pages)) 332 #raise ActionStatus("These pages are in the remote wiki, but not local: " + wikiutil.escape(r_new_pages) + "<br>These pages are in the local wiki, but not in the remote one: " + wikiutil.escape(l_new_pages))
328 #if params["direction"] in (DOWN, BOTH): 333 #if params["direction"] in (DOWN, BOTH):
329 # for rp in remote_but_not_local: 334 # for rp in remote_but_not_local:
330 # XXX add locking, acquire read-lock on rp 335
331 336 # let's do the simple case first, can be refactored later to match all cases
337 for rp in on_both_sides:
338 # XXX add locking, acquire read-lock on rp
339
340 local_pagename = rp.local_pagename
341
342 tags = TagStore(Page(self.request, local_pagename))
343 matching_tags = tags.fetch(iwid_full=remote.iwid_full)
344 matching_tags.sort()
345
346 if not matching_tags:
347 remote_rev = None
348 local_rev = rp.local_rev # merge against the newest version
349 old_contents = ""
350 else:
351 newest_tag = matching_tags[-1]
352 local_rev = newest_tag.current_rev
353 remote_rev = newest_tag.remote_rev
354 old_contents = local_page.get_raw_body_str()
355
356 local_page = Page(self.request, local_pagename, rev=local_rev)
357
358 diff = remote.get_diff(rp.remote_pagename, remote_rev, None)
359 new_contents = patch(old_contents, decompress(diff)).decode("utf-8")
360 # XXX this is not finished yet
361
332 362
333 363
334 def execute(pagename, request): 364 def execute(pagename, request):
335 ActionClass(pagename, request).render() 365 ActionClass(pagename, request).render()