Exemple #1
0
	def docRead(self, readWrite, handle):
		stat = Connector().stat(self.rev())
		uti = stat.type()
		if readWrite:
			linkMap = None
		else:
			linkMap = stat.linkMap()
		if uti in DictModel.UTIs:
			model = DictModel(linkMap, self)
		elif uti in SetModel.UTIs:
			model = SetModel(linkMap, self)
		else:
			raise TypeError('Unhandled type code: %s' % (uti))

		self.__setModel(model)
		if self.__settings:
			self.__applySettings(self.__settings)

		model.rowsInserted.connect(self._emitSaveNeeded)
		model.rowsRemoved.connect(self._emitSaveNeeded)
		model.dataChanged.connect(self.__dataChanged)
		model.modelReset.connect(self.__dataChanged)
		model.modelReset.connect(lambda: self.selectionChanged.emit())
		self.listView.selectionModel().selectionChanged.connect(
			lambda: self.selectionChanged.emit())

		autoClean = self.metaDataGetField(CollectionModel.AUTOCLEAN, False)
		model.doLoad(handle, readWrite, autoClean)
		if model.hasChanged():
			self._emitSaveNeeded()
Exemple #2
0
    def docRead(self, readWrite, handle):
        stat = Connector().stat(self.rev())
        uti = stat.type()
        if readWrite:
            linkMap = None
        else:
            linkMap = stat.linkMap()
        if uti in DictModel.UTIs:
            model = DictModel(linkMap, self)
        elif uti in SetModel.UTIs:
            model = SetModel(linkMap, self)
        else:
            raise TypeError('Unhandled type code: %s' % (uti))

        self.__setModel(model)
        if self.__settings:
            self.__applySettings(self.__settings)

        model.rowsInserted.connect(self._emitSaveNeeded)
        model.rowsRemoved.connect(self._emitSaveNeeded)
        model.dataChanged.connect(self.__dataChanged)
        model.modelReset.connect(self.__dataChanged)
        model.modelReset.connect(lambda: self.selectionChanged.emit())
        self.listView.selectionModel().selectionChanged.connect(
            lambda: self.selectionChanged.emit())

        autoClean = self.metaDataGetField(CollectionModel.AUTOCLEAN, False)
        model.doLoad(handle, readWrite, autoClean)
        if model.hasChanged():
            self._emitSaveNeeded()
Exemple #3
0
	def test_sync_merge(self):
		(doc, rev1, rev2) = self.createMerge("org.hotchpotch.dict",
			{'HPSD' : struct.dumps({"a":1}) },
			{'HPSD' : struct.dumps({"a":1, "b":2}) },
			{'HPSD' : struct.dumps({"a":1, "c":3}) })
		l = self.performSync(doc, 'merge')

		rev = l.revs()[0]
		s = Connector().stat(rev)
		self.assertEqual(len(s.parents()), 2)
		self.assertTrue(rev1 in s.parents())
		self.assertTrue(rev2 in s.parents())

		# all revs on all stores?
		l = Connector().lookup_rev(rev1)
		self.assertTrue(self.store1 in l)
		self.assertTrue(self.store2 in l)
		l = Connector().lookup_rev(rev2)
		self.assertTrue(self.store1 in l)
		self.assertTrue(self.store2 in l)

		# see if merge was ok
		with Connector().peek(rev) as r:
			hpsd = struct.loads(r.readAll('HPSD'))
			self.assertEqual(hpsd, {"a":1, "b":2, "c":3})
Exemple #4
0
    def test_merge(self):
        c = Connector()
        stores = [self.store1, self.store2]
        w = self.create("public.data", "test.ignore", stores)
        w.commit()
        doc = w.getDoc()
        rev = w.getRev()

        with c.update(doc, rev, stores=[self.store1]) as w:
            w.write('FILE', 'first')
            w.commit()
            rev1 = w.getRev()

        with c.update(doc, rev, stores=[self.store2]) as w:
            w.write('FILE', 'second')
            w.commit()
            rev2 = w.getRev()

        with c.update(doc, rev1, stores=stores) as w:
            w.setParents([rev1, rev2])
            w.commit()
            rev3 = w.getRev()

        self.assertTrue(c.sync(doc) == rev3)

        l = c.lookup_doc(doc)
        self.assertEqual(l.revs(), [rev3])

        self.assertEqual(set(c.lookup_rev(rev)), set(stores))
        self.assertEqual(set(c.lookup_rev(rev1)), set(stores))
        self.assertEqual(set(c.lookup_rev(rev2)), set(stores))
        self.assertEqual(set(c.lookup_rev(rev3)), set(stores))
Exemple #5
0
	def test_bad(self):
		c = Connector()
		stores = [self.store1, self.store2]
		w = self.create("public.data", "test.ignore", stores)
		w.commit()
		doc = w.getDoc()
		rev = w.getRev()

		with c.update(doc, rev, stores=[self.store1]) as w:
			w.write('FILE', 'first')
			w.commit()
			rev1 = w.getRev()

		with c.update(doc, rev, stores=[self.store2]) as w:
			w.write('FILE', 'second')
			w.commit()
			rev2 = w.getRev()

		self.failIfEqual(rev, rev1)
		self.failIfEqual(rev, rev2)
		self.failIfEqual(rev1, rev2)

		self.assertRaises(IOError, c.sync, doc)

		l = c.lookup_doc(doc)
		self.assertEqual(len(l.revs()), 2)
		self.assertEqual(l.rev(self.store1), rev1)
		self.assertEqual(l.rev(self.store2), rev2)
Exemple #6
0
 def tearDown(self):
     CommonParts.tearDown(self)
     # make sure stores are unmounted to kill sync
     if Connector().enum().isMounted(STORE1):
         Connector().unmount(STORE1)
     if Connector().enum().isMounted(STORE2):
         Connector().unmount(STORE2)
Exemple #7
0
	def test_sticky(self):
		s = struct.Set()
		# create sticky contianer on two stores
		with s.create("foo", [self.store1, self.store2]) as dummy:
			# create document on first store
			with Connector().create("test.format.foo", "test.ignore", [self.store1]) as w:
				w.commit()
				doc = w.getDoc()
				rev = w.getRev()

				watch1 = self.watchDoc(doc, connector.Watch.EVENT_REPLICATED)
				watch2 = self.watchRev(rev, connector.Watch.EVENT_REPLICATED)

				# add to sticky container
				s['dummy'] = struct.DocLink(doc)
				s.save()

			# wait for sticky replicatin to happen
			self.assertTrue(watch1.waitForWatch())
			self.assertTrue(watch2.waitForWatch())

			# check doc (with rev) to exist on all stores
			l = Connector().lookup_doc(doc)
			self.assertEqual(l.revs(), [rev])
			self.assertEqual(len(l.stores(rev)), 2)
			self.assertTrue(self.store1 in l.stores(rev))
			self.assertTrue(self.store2 in l.stores(rev))

			l = Connector().lookup_rev(rev)
			self.assertEqual(len(l), 2)
			self.assertTrue(self.store1 in l)
			self.assertTrue(self.store2 in l)
Exemple #8
0
    def test_bad(self):
        c = Connector()
        stores = [self.store1, self.store2]
        w = self.create("public.data", "test.ignore", stores)
        w.commit()
        doc = w.getDoc()
        rev = w.getRev()

        with c.update(doc, rev, stores=[self.store1]) as w:
            w.write('FILE', 'first')
            w.commit()
            rev1 = w.getRev()

        with c.update(doc, rev, stores=[self.store2]) as w:
            w.write('FILE', 'second')
            w.commit()
            rev2 = w.getRev()

        self.failIfEqual(rev, rev1)
        self.failIfEqual(rev, rev2)
        self.failIfEqual(rev1, rev2)

        self.assertRaises(IOError, c.sync, doc)

        l = c.lookup_doc(doc)
        self.assertEqual(len(l.revs()), 2)
        self.assertEqual(l.rev(self.store1), rev1)
        self.assertEqual(l.rev(self.store2), rev2)
Exemple #9
0
 def setUp(self):
     # make sure stores are unmounted to kill sync
     if Connector().enum().isMounted(STORE1):
         Connector().unmount(STORE1)
     if Connector().enum().isMounted(STORE2):
         Connector().unmount(STORE2)
     CommonParts.setUp(self)
Exemple #10
0
	def test_create(self):
		w = self.create("public.data", "test.foo", [self.store1])
		w.commit()
		doc = w.getDoc()
		rev = w.getRev()

		s = Connector().stat(rev)
		self.assertEqual(s.creator(), "test.foo")
Exemple #11
0
    def test_create(self):
        w = self.create("public.data", "test.foo", [self.store1])
        w.commit()
        doc = w.getDoc()
        rev = w.getRev()

        s = Connector().stat(rev)
        self.assertEqual(s.creator(), "test.foo")
Exemple #12
0
	def test_suspend(self):
		c = Connector()
		(doc, rev1, rev2) = self.createSuspendDoc()

		l = c.lookup_doc(doc)
		self.assertEqual(l.revs(), [rev1])
		self.assertEqual(l.preRevs(), [rev2])
		self.assertRevContent(rev1, {'FILE' : 'ok'})
		self.assertRevContent(rev2, {'FILE' : 'update'})
Exemple #13
0
    def test_suspend(self):
        c = Connector()
        (doc, rev1, rev2) = self.createSuspendDoc()

        l = c.lookup_doc(doc)
        self.assertEqual(l.revs(), [rev1])
        self.assertEqual(l.preRevs(), [rev2])
        self.assertRevContent(rev1, {'FILE': 'ok'})
        self.assertRevContent(rev2, {'FILE': 'update'})
Exemple #14
0
    def assertRevContent(self, rev, content):
        with Connector().peek(rev) as r:
            for (part, data) in content.items():
                revData = r.readAll(part)
                self.assertEqual(revData, data)

        s = Connector().stat(rev)
        for part in s.parts():
            self.assertTrue(part in content)
Exemple #15
0
	def assertRevContent(self, rev, content):
		with Connector().peek(rev) as r:
			for (part, data) in content.items():
				revData = r.readAll(part)
				self.assertEqual(revData, data)

		s = Connector().stat(rev)
		for part in s.parts():
			self.assertTrue(part in content)
Exemple #16
0
    def test_resume_wrong(self):
        c = Connector()
        (doc, rev1, rev2) = self.createSuspendDoc()
        self.assertRaises(IOError, c.resume, doc, rev1)

        l = c.lookup_doc(doc)
        self.assertEqual(l.revs(), [rev1])
        self.assertEqual(l.preRevs(), [rev2])
        self.assertRevContent(rev1, {'FILE': 'ok'})
        self.assertRevContent(rev2, {'FILE': 'update'})
Exemple #17
0
	def test_already_same(self):
		c = Connector()
		stores = [self.store1, self.store2]
		w = self.create("public.data", "test.ignore", stores)
		w.commit()
		doc = w.getDoc()
		rev = w.getRev()

		self.assertTrue(c.sync(doc) == rev)
		self.assertTrue(c.sync(doc, stores=stores) == rev)
Exemple #18
0
	def test_resume_wrong(self):
		c = Connector()
		(doc, rev1, rev2) = self.createSuspendDoc()
		self.assertRaises(IOError, c.resume, doc, rev1)

		l = c.lookup_doc(doc)
		self.assertEqual(l.revs(), [rev1])
		self.assertEqual(l.preRevs(), [rev2])
		self.assertRevContent(rev1, {'FILE' : 'ok'})
		self.assertRevContent(rev2, {'FILE' : 'update'})
Exemple #19
0
    def test_already_same(self):
        c = Connector()
        stores = [self.store1, self.store2]
        w = self.create("public.data", "test.ignore", stores)
        w.commit()
        doc = w.getDoc()
        rev = w.getRev()

        self.assertTrue(c.sync(doc) == rev)
        self.assertTrue(c.sync(doc, stores=stores) == rev)
Exemple #20
0
    def test_create(self):
        c = Connector()
        w = self.create("test.format", "test.ignore", [self.store1])
        self.assertEqual(w.getType(), "test.format")
        w.commit()
        doc = w.getDoc()
        rev = w.getRev()

        s = c.stat(rev)
        self.assertEqual(s.type(), "test.format")
Exemple #21
0
	def test_create(self):
		c = Connector()
		w = self.create("test.format", "test.ignore", [self.store1])
		self.assertEqual(w.getType(), "test.format")
		w.commit()
		doc = w.getDoc()
		rev = w.getRev()

		s = c.stat(rev)
		self.assertEqual(s.type(), "test.format")
Exemple #22
0
	def test_merge(self):
		c = Connector()
		stores = [self.store1, self.store2]
		w = self.create("public.data", "test.ignore", stores)
		w.commit()
		doc = w.getDoc()
		rev = w.getRev()

		with c.update(doc, rev, stores=[self.store1]) as w:
			w.write('FILE', 'first')
			w.commit()
			rev1 = w.getRev()

		with c.update(doc, rev, stores=[self.store2]) as w:
			w.write('FILE', 'second')
			w.commit()
			rev2 = w.getRev()

		with c.update(doc, rev1, stores=stores) as w:
			w.setParents([rev1, rev2])
			w.commit()
			rev3 = w.getRev()

		self.assertTrue(c.sync(doc) == rev3)

		l = c.lookup_doc(doc)
		self.assertEqual(l.revs(), [rev3])

		self.assertEqual(set(c.lookup_rev(rev)), set(stores))
		self.assertEqual(set(c.lookup_rev(rev1)), set(stores))
		self.assertEqual(set(c.lookup_rev(rev2)), set(stores))
		self.assertEqual(set(c.lookup_rev(rev3)), set(stores))
Exemple #23
0
	def test_sync_merge_fallback(self):
		(doc, rev1, rev2) = self.createMerge("public.data", {}, {'FILE' : "left"},
			{'FILE' : "right"})
		l = self.performSync(doc, 'merge')

		rev = l.revs()[0]
		s = Connector().stat(rev)
		self.assertEqual(len(s.parents()), 2)
		self.assertTrue(rev1 in s.parents())
		self.assertTrue(rev2 in s.parents())
		self.assertRevContent(rev, {'FILE' : 'left'})
Exemple #24
0
    def test_sync_merge_fallback(self):
        (doc, rev1, rev2) = self.createMerge("public.data", {},
                                             {'FILE': "left"},
                                             {'FILE': "right"})
        l = self.performSync(doc, 'merge')

        rev = l.revs()[0]
        s = Connector().stat(rev)
        self.assertEqual(len(s.parents()), 2)
        self.assertTrue(rev1 in s.parents())
        self.assertTrue(rev2 in s.parents())
        self.assertRevContent(rev, {'FILE': 'left'})
Exemple #25
0
	def __doCreate(self, sourceRev):
		info = Connector().stat(sourceRev)
		destStores = Connector().lookup_rev(self.rev())
		with Connector().create(info.type(), info.creator(), destStores) as w:
			with Connector().peek(sourceRev) as r:
				for part in info.parts():
					w.write(part, r.readAll(part))
			w.commit()
			destDoc = w.getDoc()
			# add link
			self.model().insertLink(struct.DocLink(destDoc))
			# save immediately
			self.save()
Exemple #26
0
 def __addCreateActions(self, menu):
     newMenu = menu.addMenu(QtGui.QIcon("icons/filenew.png"),
                            "New document")
     sysStore = struct.Container(
         struct.DocLink(Connector().enum().sysStore()))
     templatesDict = struct.Container(sysStore.get("templates:"))
     items = templatesDict.items()
     items.sort(key=lambda item: item[0])
     for (name, link) in items:
         rev = link.rev()
         icon = QtGui.QIcon(Registry().getIcon(
             Connector().stat(rev).type()))
         action = newMenu.addAction(icon, name)
         action.triggered.connect(lambda x, r=rev: self.__doCreate(r))
Exemple #27
0
    def test_sticky(self):
        s = struct.Set()
        # create sticky contianer on two stores
        with s.create("foo", [self.store1, self.store2]) as dummy:
            # create document on first store
            with Connector().create("test.format.foo", "test.ignore",
                                    [self.store1]) as w:
                w.commit()
                doc = w.getDoc()
                rev = w.getRev()

                watch1 = self.watchDoc(doc, connector.Watch.EVENT_REPLICATED)
                watch2 = self.watchRev(rev, connector.Watch.EVENT_REPLICATED)

                # add to sticky container
                s['dummy'] = struct.DocLink(doc)
                s.save()

            # wait for sticky replicatin to happen
            self.assertTrue(watch1.waitForWatch())
            self.assertTrue(watch2.waitForWatch())

            # check doc (with rev) to exist on all stores
            l = Connector().lookup_doc(doc)
            self.assertEqual(l.revs(), [rev])
            self.assertEqual(len(l.stores(rev)), 2)
            self.assertTrue(self.store1 in l.stores(rev))
            self.assertTrue(self.store2 in l.stores(rev))

            l = Connector().lookup_rev(rev)
            self.assertEqual(len(l), 2)
            self.assertTrue(self.store1 in l)
            self.assertTrue(self.store2 in l)
Exemple #28
0
	def createSuspendDoc(self):
		c = Connector()
		w = self.create("test.format", "test.ignore", [self.store1])
		w.writeAll('FILE', 'ok')
		w.commit()
		doc = w.getDoc()
		rev1 = w.getRev()

		with c.update(doc, rev1) as w:
			w.writeAll('FILE', 'update')
			w.suspend()
			rev2 = w.getRev()

		return (doc, rev1, rev2)
Exemple #29
0
    def createSuspendDoc(self):
        c = Connector()
        w = self.create("test.format", "test.ignore", [self.store1])
        w.writeAll('FILE', 'ok')
        w.commit()
        doc = w.getDoc()
        rev1 = w.getRev()

        with c.update(doc, rev1) as w:
            w.writeAll('FILE', 'update')
            w.suspend()
            rev2 = w.getRev()

        return (doc, rev1, rev2)
Exemple #30
0
 def __addReplicateActions(self, menu, link):
     c = Connector()
     try:
         allVolumes = set(c.lookup_rev(self.rev()))
         if isinstance(link, struct.DocLink):
             lookup = c.lookup_doc(link.doc())
             curVolumes = set(lookup.stores())
             try:
                 for rev in lookup.revs():
                     curVolumes = curVolumes & set(
                         c.lookup_rev(rev, curVolumes))
             except IOError:
                 curVolumes = set()
         else:
             curVolumes = set(c.lookup_rev(link.rev()))
     except IOError:
         return
     repVolumes = allVolumes - curVolumes
     for store in repVolumes:
         try:
             rev = c.lookup_doc(store).rev(store)
             with c.peek(rev) as r:
                 metaData = struct.loads(r.readAll('META'))
                 try:
                     name = metaData["org.hotchpotch.annotation"]["title"]
                 except:
                     name = "Unknown store"
                 action = menu.addAction("Replicate item to '%s'" % name)
                 action.triggered.connect(
                     lambda x, l=link, s=store: self.__doReplicate(l, s))
         except:
             pass
Exemple #31
0
    def __init__(self, uuid, isDoc, parent=None):
        super(PropertiesDialog, self).__init__(parent)

        mainLayout = QtGui.QVBoxLayout()
        mainLayout.setSizeConstraint(QtGui.QLayout.SetFixedSize)

        if isDoc:
            self.doc = uuid
            info = Connector().lookup_doc(uuid)
            mainLayout.addWidget(DocumentTab(info.stores(), "document"))
            self.revs = info.revs()
        else:
            self.doc = None
            mainLayout.addWidget(
                DocumentTab(Connector().lookup_rev(uuid), "revision"))
            self.revs = [uuid]

        if len(self.revs) == 0:
            QtGui.QMessageBox.warning(
                self, 'Missing document',
                'The requested document was not found on any store.')
            sys.exit(1)

        tabWidget = QtGui.QTabWidget()
        self.annoTab = AnnotationTab(self.revs, isDoc
                                     and (len(self.revs) == 1))
        QtCore.QObject.connect(self.annoTab, QtCore.SIGNAL("changed()"),
                               self.__changed)
        tabWidget.addTab(self.annoTab, "Annotation")
        tabWidget.addTab(HistoryTab(self.revs), "History")
        if isDoc:
            tabWidget.addTab(RevisionTab(self.revs), "Revisions")
        else:
            tabWidget.addTab(RevisionTab(self.revs), "Revision")
        mainLayout.addWidget(tabWidget)

        if isDoc and (len(self.revs) == 1):
            self.buttonBox = QtGui.QDialogButtonBox(
                QtGui.QDialogButtonBox.Save | QtGui.QDialogButtonBox.Close)
            self.buttonBox.button(
                QtGui.QDialogButtonBox.Save).setEnabled(False)
            self.buttonBox.accepted.connect(self.__save)
            self.buttonBox.rejected.connect(self.reject)
        else:
            self.buttonBox = QtGui.QDialogButtonBox(QtGui.QDialogButtonBox.Ok)
            self.buttonBox.accepted.connect(self.accept)
        mainLayout.addWidget(self.buttonBox)
        self.setLayout(mainLayout)
        self.setWindowTitle("Properties of %s" % (self.annoTab.getTitle()))
Exemple #32
0
    def test_update_change(self):
        c = Connector()
        w = self.create("public.data", "test.foo", [self.store1])
        w.commit()
        doc = w.getDoc()
        rev1 = w.getRev()

        with c.update(doc, rev1, "test.baz") as w:
            w.commit()
            rev2 = w.getRev()

        s = c.stat(rev1)
        self.assertEqual(s.creator(), "test.foo")
        s = c.stat(rev2)
        self.assertEqual(s.creator(), "test.baz")
Exemple #33
0
	def test_update_change(self):
		c = Connector()
		w = self.create("public.data", "test.foo", [self.store1])
		w.commit()
		doc = w.getDoc()
		rev1 = w.getRev()

		with c.update(doc, rev1, "test.baz") as w:
			w.commit()
			rev2 = w.getRev()

		s = c.stat(rev1)
		self.assertEqual(s.creator(), "test.foo")
		s = c.stat(rev2)
		self.assertEqual(s.creator(), "test.baz")
Exemple #34
0
	def test_fork(self):
		c = Connector()
		w = self.create("public.data", "test.foo", [self.store1])
		w.commit()
		doc1 = w.getDoc()
		rev1 = w.getRev()

		w = self.fork(rev1, "test.bar")
		w.commit()
		doc2 = w.getDoc()
		rev2 = w.getRev()

		s = c.stat(rev1)
		self.assertEqual(s.creator(), "test.foo")
		s = c.stat(rev2)
		self.assertEqual(s.creator(), "test.bar")
	def __update(self):
		if self.__seen:
			self.__unwatch()
			self.__available = len(Connector().lookup_rev(self.__rev)) > 0
		else:
			self.__available = False
			try:
				stat = Connector().stat(self.__rev)
				self.__mtime = stat.mtime()
				self.__seen = True
				self.__available = True
				self.__view._addParents(stat.parents())
				self.__unwatch()
			except IOError:
				self.__watch()
				return
Exemple #36
0
    def performSync(self, doc, strategy):
        watch = self.watchDoc(doc, connector.Watch.EVENT_MODIFIED)

        self.startSync(strategy, self.store1, self.store2)

        while True:
            watch.reset()
            self.assertTrue(watch.waitForWatch())
            l = Connector().lookup_doc(doc)
            if len(l.revs()) == 1:
                break

        self.assertEqual(len(l.stores()), 2)
        self.assertTrue(self.store1 in l.stores())
        self.assertTrue(self.store2 in l.stores())
        return l
Exemple #37
0
    def test_collect(self):
        c = Connector()

        # deliberately close handle after creating!
        with c.create("public.data", "test.foo", [self.store1]) as w:
            w.commit()
            doc = w.getDoc()
            rev = w.getRev()

        # perform a GC cycle
        self.gc(self.store1)

        l = c.lookup_doc(doc)
        self.assertEqual(l.revs(), [])
        self.assertEqual(l.preRevs(), [])
        self.assertRaises(IOError, c.stat, rev)
Exemple #38
0
    def test_fork(self):
        c = Connector()
        w = self.create("public.data", "test.foo", [self.store1])
        w.commit()
        doc1 = w.getDoc()
        rev1 = w.getRev()

        w = self.fork(rev1, "test.bar")
        w.commit()
        doc2 = w.getDoc()
        rev2 = w.getRev()

        s = c.stat(rev1)
        self.assertEqual(s.creator(), "test.foo")
        s = c.stat(rev2)
        self.assertEqual(s.creator(), "test.bar")
 def __update(self):
     if self.__seen:
         self.__unwatch()
         self.__available = len(Connector().lookup_rev(self.__rev)) > 0
     else:
         self.__available = False
         try:
             stat = Connector().stat(self.__rev)
             self.__mtime = stat.mtime()
             self.__seen = True
             self.__available = True
             self.__view._addParents(stat.parents())
             self.__unwatch()
         except IOError:
             self.__watch()
             return
Exemple #40
0
	def test_sync_ff_err(self):
		(doc, rev1, rev2) = self.createMerge("public.data", {}, {'FILE' : "left"},
			{'FILE' : "right"})

		watch = self.watchDoc(doc, connector.Watch.EVENT_MODIFIED)

		self.startSync('ff', self.store1, self.store2)
		self.startSync('ff', self.store2, self.store1)

		self.assertFalse(watch.waitForWatch(1))

		# check that doc is not synced
		l = Connector().lookup_doc(doc)
		self.assertEqual(len(l.revs()), 2)
		self.assertEqual(l.rev(self.store1), rev1)
		self.assertEqual(l.rev(self.store2), rev2)
Exemple #41
0
	def performSync(self, doc, strategy):
		watch = self.watchDoc(doc, connector.Watch.EVENT_MODIFIED)

		self.startSync(strategy, self.store1, self.store2)

		while True:
			watch.reset()
			self.assertTrue(watch.waitForWatch())
			l = Connector().lookup_doc(doc)
			if len(l.revs()) == 1:
				break

		self.assertEqual(len(l.stores()), 2)
		self.assertTrue(self.store1 in l.stores())
		self.assertTrue(self.store2 in l.stores())
		return l
Exemple #42
0
	def test_create_keep_handle(self):
		c = Connector()

		with c.create("public.data", "test.foo", [self.store1]) as w:
			w.commit()
			doc = w.getDoc()
			rev = w.getRev()

			# perform a GC cycle
			self.gc(self.store1)

			l = c.lookup_doc(doc)
			self.assertEqual(l.revs(), [rev])
			self.assertEqual(l.preRevs(), [])

			c.stat(rev)
Exemple #43
0
	def test_collect(self):
		c = Connector()

		# deliberately close handle after creating!
		with c.create("public.data", "test.foo", [self.store1]) as w:
			w.commit()
			doc = w.getDoc()
			rev = w.getRev()

		# perform a GC cycle
		self.gc(self.store1)

		l = c.lookup_doc(doc)
		self.assertEqual(l.revs(), [])
		self.assertEqual(l.preRevs(), [])
		self.assertRaises(IOError, c.stat, rev)
Exemple #44
0
    def update(self):
        # reset everything
        self.__valid = False
        self.__icon = None
        for i in xrange(len(self.__columnDefs)):
            column = self.__columnDefs[i]
            if column.derived():
                self.__columnValues[i] = column.default()

        # determine revision
        needMerge = False
        if isinstance(self.__link, struct.DocLink):
            self.__link.update()
            revisions = self.__link.revs()
            if len(revisions) == 0:
                return
            elif len(revisions) > 1:
                needMerge = True
            # TODO: maybe sort by date
            rev = revisions[0]
        else:
            rev = self.__link.rev()
        self.__rev = rev

        # stat
        try:
            s = Connector().stat(rev)
        except IOError:
            return
        self.__uti = s.type()
        if needMerge:
            image = QtGui.QImage(Registry().getIcon(s.type()))
            painter = QtGui.QPainter()
            painter.begin(image)
            painter.drawImage(0, 0,
                              QtGui.QImage("icons/uti/merge_overlay.png"))
            painter.end()
            self.__icon = QtGui.QIcon(QtGui.QPixmap.fromImage(image))
        else:
            self.__icon = QtGui.QIcon(Registry().getIcon(s.type()))

        # overwritable by external files?
        self.__replacable = (not needMerge) and (not Registry().conformes(
            self.__uti, "org.hotchpotch.container"))

        self.__valid = True
        self.__updateColumns()
Exemple #45
0
	def test_resume_suspend_orig(self):
		c = Connector()
		(doc, rev1, rev2) = self.createSuspendDoc()

		with c.resume(doc, rev2) as w:
			w.suspend()
			rev3 = w.getRev()

		l = c.lookup_doc(doc)
		self.assertEqual(l.revs(), [rev1])
		self.assertEqual(l.preRevs(), [rev3])

		s = c.stat(rev3)
		self.assertEqual(s.parents(), [rev1])

		self.assertRevContent(rev1, {'FILE' : 'ok'})
		self.assertRevContent(rev3, {'FILE' : 'update'})
Exemple #46
0
	def test_resume_commit(self):
		c = Connector()
		(doc, rev1, rev2) = self.createSuspendDoc()

		with c.resume(doc, rev2) as w:
			w.writeAll('FILE', 'What are you waiting for, christmas?')
			w.commit()
			rev3 = w.getRev()

		l = c.lookup_doc(doc)
		self.assertEqual(l.revs(), [rev3])
		self.assertEqual(len(l.preRevs()), 0)

		s = c.stat(rev3)
		self.assertEqual(s.parents(), [rev1])
		self.assertRevContent(rev1, {'FILE' : 'ok'})
		self.assertRevContent(rev3, {'FILE' : 'What are you waiting for, christmas?'})
Exemple #47
0
    def test_resume_suspend_orig(self):
        c = Connector()
        (doc, rev1, rev2) = self.createSuspendDoc()

        with c.resume(doc, rev2) as w:
            w.suspend()
            rev3 = w.getRev()

        l = c.lookup_doc(doc)
        self.assertEqual(l.revs(), [rev1])
        self.assertEqual(l.preRevs(), [rev3])

        s = c.stat(rev3)
        self.assertEqual(s.parents(), [rev1])

        self.assertRevContent(rev1, {'FILE': 'ok'})
        self.assertRevContent(rev3, {'FILE': 'update'})
Exemple #48
0
	def update(self):
		# reset everything
		self.__valid = False
		self.__icon = None
		for i in xrange(len(self.__columnDefs)):
			column = self.__columnDefs[i]
			if column.derived():
				self.__columnValues[i] = column.default()

		# determine revision
		needMerge = False
		if isinstance(self.__link, struct.DocLink):
			self.__link.update()
			revisions = self.__link.revs()
			if len(revisions) == 0:
				return
			elif len(revisions) > 1:
				needMerge = True
			# TODO: maybe sort by date
			rev = revisions[0]
		else:
			rev = self.__link.rev()
		self.__rev = rev

		# stat
		try:
			s = Connector().stat(rev)
		except IOError:
			return
		self.__uti = s.type()
		if needMerge:
			image = QtGui.QImage(Registry().getIcon(s.type()))
			painter = QtGui.QPainter()
			painter.begin(image)
			painter.drawImage(0, 0, QtGui.QImage("icons/uti/merge_overlay.png"))
			painter.end()
			self.__icon = QtGui.QIcon(QtGui.QPixmap.fromImage(image))
		else:
			self.__icon = QtGui.QIcon(Registry().getIcon(s.type()))

		# overwritable by external files?
		self.__replacable = (not needMerge) and (
			not Registry().conformes(self.__uti, "org.hotchpotch.container"))

		self.__valid = True
		self.__updateColumns()
Exemple #49
0
    def test_sync_ff_err(self):
        (doc, rev1, rev2) = self.createMerge("public.data", {},
                                             {'FILE': "left"},
                                             {'FILE': "right"})

        watch = self.watchDoc(doc, connector.Watch.EVENT_MODIFIED)

        self.startSync('ff', self.store1, self.store2)
        self.startSync('ff', self.store2, self.store1)

        self.assertFalse(watch.waitForWatch(1))

        # check that doc is not synced
        l = Connector().lookup_doc(doc)
        self.assertEqual(len(l.revs()), 2)
        self.assertEqual(l.rev(self.store1), rev1)
        self.assertEqual(l.rev(self.store2), rev2)
Exemple #50
0
	def __addReplicateActions(self, menu, link):
		c = Connector()
		try:
			allVolumes = set(c.lookup_rev(self.rev()))
			if isinstance(link, struct.DocLink):
				lookup = c.lookup_doc(link.doc())
				curVolumes = set(lookup.stores())
				try:
					for rev in lookup.revs():
						curVolumes = curVolumes & set(c.lookup_rev(rev, curVolumes))
				except IOError:
					curVolumes = set()
			else:
				curVolumes = set(c.lookup_rev(link.rev()))
		except IOError:
			return
		repVolumes = allVolumes - curVolumes
		for store in repVolumes:
			try:
				rev = c.lookup_doc(store).rev(store)
				with c.peek(rev) as r:
					metaData = struct.loads(r.readAll('META'))
					try:
						name = metaData["org.hotchpotch.annotation"]["title"]
					except:
						name = "Unknown store"
					action = menu.addAction("Replicate item to '%s'" % name)
					action.triggered.connect(
						lambda x,l=link,s=store: self.__doReplicate(l, s))
			except:
				pass
Exemple #51
0
    def test_suspend_multi(self):
        c = Connector()
        (doc, rev1, rev_s1) = self.createSuspendDoc()

        with c.update(doc, rev1) as w:
            w.writeAll('FILE', 'forward')
            w.commit()
            rev2 = w.getRev()

        with c.update(doc, rev2) as w:
            w.writeAll('FILE', 'Hail to the king, baby!')
            w.suspend()
            rev_s2 = w.getRev()

        l = c.lookup_doc(doc)
        self.assertEqual(l.revs(), [rev2])
        self.assertEqual(len(l.preRevs()), 2)
        self.assertTrue(rev_s1 in l.preRevs())
        self.assertTrue(rev_s2 in l.preRevs())

        s = c.stat(rev_s1)
        self.assertEqual(s.parents(), [rev1])
        s = c.stat(rev_s2)
        self.assertEqual(s.parents(), [rev2])

        self.assertRevContent(rev1, {'FILE': 'ok'})
        self.assertRevContent(rev_s1, {'FILE': 'update'})
        self.assertRevContent(rev2, {'FILE': 'forward'})
        self.assertRevContent(rev_s2, {'FILE': 'Hail to the king, baby!'})
Exemple #52
0
    def test_sync_merge(self):
        (doc, rev1,
         rev2) = self.createMerge("org.hotchpotch.dict",
                                  {'HPSD': struct.dumps({"a": 1})},
                                  {'HPSD': struct.dumps({
                                      "a": 1,
                                      "b": 2
                                  })},
                                  {'HPSD': struct.dumps({
                                      "a": 1,
                                      "c": 3
                                  })})
        l = self.performSync(doc, 'merge')

        rev = l.revs()[0]
        s = Connector().stat(rev)
        self.assertEqual(len(s.parents()), 2)
        self.assertTrue(rev1 in s.parents())
        self.assertTrue(rev2 in s.parents())

        # all revs on all stores?
        l = Connector().lookup_rev(rev1)
        self.assertTrue(self.store1 in l)
        self.assertTrue(self.store2 in l)
        l = Connector().lookup_rev(rev2)
        self.assertTrue(self.store1 in l)
        self.assertTrue(self.store2 in l)

        # see if merge was ok
        with Connector().peek(rev) as r:
            hpsd = struct.loads(r.readAll('HPSD'))
            self.assertEqual(hpsd, {"a": 1, "b": 2, "c": 3})
Exemple #53
0
    def test_resume_abort(self):
        c = Connector()
        (doc, rev1, rev2) = self.createSuspendDoc()

        with c.resume(doc, rev2) as w:
            w.writeAll('FILE', 'Hail to the king, baby!')

            l = c.lookup_doc(doc)
            self.assertEqual(l.revs(), [rev1])
            self.assertEqual(l.preRevs(), [rev2])

            w.close()

        l = c.lookup_doc(doc)
        self.assertEqual(l.revs(), [rev1])
        self.assertEqual(l.preRevs(), [rev2])
        self.assertRevContent(rev1, {'FILE': 'ok'})
        self.assertRevContent(rev2, {'FILE': 'update'})
Exemple #54
0
    def test_resume_commit(self):
        c = Connector()
        (doc, rev1, rev2) = self.createSuspendDoc()

        with c.resume(doc, rev2) as w:
            w.writeAll('FILE', 'What are you waiting for, christmas?')
            w.commit()
            rev3 = w.getRev()

        l = c.lookup_doc(doc)
        self.assertEqual(l.revs(), [rev3])
        self.assertEqual(len(l.preRevs()), 0)

        s = c.stat(rev3)
        self.assertEqual(s.parents(), [rev1])
        self.assertRevContent(rev1, {'FILE': 'ok'})
        self.assertRevContent(rev3,
                              {'FILE': 'What are you waiting for, christmas?'})
Exemple #55
0
	def test_resume_abort(self):
		c = Connector()
		(doc, rev1, rev2) = self.createSuspendDoc()

		with c.resume(doc, rev2) as w:
			w.writeAll('FILE', 'Hail to the king, baby!')

			l = c.lookup_doc(doc)
			self.assertEqual(l.revs(), [rev1])
			self.assertEqual(l.preRevs(), [rev2])

			w.close()

		l = c.lookup_doc(doc)
		self.assertEqual(l.revs(), [rev1])
		self.assertEqual(l.preRevs(), [rev2])
		self.assertRevContent(rev1, {'FILE' : 'ok'})
		self.assertRevContent(rev2, {'FILE' : 'update'})
Exemple #56
0
    def test_update_keep(self):
        c = Connector()
        w = self.create("test.format.foo", "test.ignore", [self.store1])
        self.assertEqual(w.getType(), "test.format.foo")
        w.commit()
        doc = w.getDoc()
        rev1 = w.getRev()

        with c.update(doc, rev1, "test.ignore") as w:
            self.assertEqual(w.getType(), "test.format.foo")
            w.write('FILE', 'update')
            w.commit()
            rev2 = w.getRev()

        s = c.stat(rev1)
        self.assertEqual(s.type(), "test.format.foo")
        s = c.stat(rev2)
        self.assertEqual(s.type(), "test.format.foo")
Exemple #57
0
	def test_update_keep(self):
		c = Connector()
		w = self.create("test.format.foo", "test.ignore", [self.store1])
		self.assertEqual(w.getType(), "test.format.foo")
		w.commit()
		doc = w.getDoc()
		rev1 = w.getRev()

		with c.update(doc, rev1, "test.ignore") as w:
			self.assertEqual(w.getType(), "test.format.foo")
			w.write('FILE', 'update')
			w.commit()
			rev2 = w.getRev()

		s = c.stat(rev1)
		self.assertEqual(s.type(), "test.format.foo")
		s = c.stat(rev2)
		self.assertEqual(s.type(), "test.format.foo")
Exemple #58
0
	def test_good(self):
		c = Connector()
		stores = [self.store1, self.store2]
		w = self.create("public.data", "test.ignore", stores)
		w.commit()
		doc = w.getDoc()
		rev = w.getRev()

		with c.update(doc, rev, stores=[self.store1]) as w:
			w.write('FILE', 'update')
			w.commit()
			rev = w.getRev()

		self.assertTrue(c.sync(doc) == rev)

		l = c.lookup_doc(doc)
		self.assertEqual(len(l.revs()), 1)
		self.assertEqual(l.rev(self.store1), rev)
		self.assertEqual(l.rev(self.store2), rev)
Exemple #59
0
    def __init__(self, uuid, isDoc, parent=None):
        super(PropertiesDialog, self).__init__(parent)

        mainLayout = QtGui.QVBoxLayout()
        mainLayout.setSizeConstraint(QtGui.QLayout.SetFixedSize)

        if isDoc:
            self.doc = uuid
            info = Connector().lookup_doc(uuid)
            mainLayout.addWidget(DocumentTab(info.stores(), "document"))
            self.revs = info.revs()
        else:
            self.doc = None
            mainLayout.addWidget(DocumentTab(Connector().lookup_rev(uuid), "revision"))
            self.revs = [uuid]

        if len(self.revs) == 0:
            QtGui.QMessageBox.warning(self, "Missing document", "The requested document was not found on any store.")
            sys.exit(1)

        tabWidget = QtGui.QTabWidget()
        self.annoTab = AnnotationTab(self.revs, isDoc and (len(self.revs) == 1))
        QtCore.QObject.connect(self.annoTab, QtCore.SIGNAL("changed()"), self.__changed)
        tabWidget.addTab(self.annoTab, "Annotation")
        tabWidget.addTab(HistoryTab(self.revs), "History")
        if isDoc:
            tabWidget.addTab(RevisionTab(self.revs), "Revisions")
        else:
            tabWidget.addTab(RevisionTab(self.revs), "Revision")
        mainLayout.addWidget(tabWidget)

        if isDoc and (len(self.revs) == 1):
            self.buttonBox = QtGui.QDialogButtonBox(QtGui.QDialogButtonBox.Save | QtGui.QDialogButtonBox.Close)
            self.buttonBox.button(QtGui.QDialogButtonBox.Save).setEnabled(False)
            self.buttonBox.accepted.connect(self.__save)
            self.buttonBox.rejected.connect(self.reject)
        else:
            self.buttonBox = QtGui.QDialogButtonBox(QtGui.QDialogButtonBox.Ok)
            self.buttonBox.accepted.connect(self.accept)
        mainLayout.addWidget(self.buttonBox)
        self.setLayout(mainLayout)
        self.setWindowTitle("Properties of %s" % (self.annoTab.getTitle()))
Exemple #60
0
	def test_fork_change(self):
		c = Connector()
		w = self.create("test.format.foo", "test.ignore", [self.store1])
		self.assertEqual(w.getType(), "test.format.foo")
		w.commit()
		doc1 = w.getDoc()
		rev1 = w.getRev()

		w = self.fork(rev1, "test.ignore")
		w.write('FILE', 'update')
		self.assertEqual(w.getType(), "test.format.foo")
		w.setType("test.format.bar")
		self.assertEqual(w.getType(), "test.format.bar")
		w.commit()
		doc2 = w.getDoc()
		rev2 = w.getRev()

		s = c.stat(rev1)
		self.assertEqual(s.type(), "test.format.foo")
		s = c.stat(rev2)
		self.assertEqual(s.type(), "test.format.bar")