[Zope3-checkins] CVS: Zope3/src/zope/fssync - fssync.py:1.6 main.py:1.3

Guido van Rossum guido@python.org
Tue, 13 May 2003 11:28:04 -0400


Update of /cvs-repository/Zope3/src/zope/fssync
In directory cvs.zope.org:/tmp/cvs-serv12952

Modified Files:
	fssync.py main.py 
Log Message:
More refactoring.  More to come.

=== Zope3/src/zope/fssync/fssync.py 1.5 => 1.6 ===
--- Zope3/src/zope/fssync/fssync.py:1.5	Mon May 12 18:23:42 2003
+++ Zope3/src/zope/fssync/fssync.py	Tue May 13 11:28:03 2003
@@ -79,17 +79,38 @@
     def __repr__(self):
         return "%s%r" % (self.__class__.__name__, (self.msg,)+self.args)
 
-class FSSync(object):
+class Network(object):
+
+    def loadrooturl(self, target):
+        rooturl = self.findrooturl(target)
+        if not rooturl:
+            raise Error("can't find root url for target", target)
+        self.setrooturl(rooturl)
 
-    def __init__(self, topdir, verbose=False):
-        self.topdir = topdir
-        self.verbose = verbose
-        self.setrooturl(self.findrooturl())
-        self.metadata = Metadata()
+    def saverooturl(self, target):
+        if self.rooturl:
+            self.writefile(self.rooturl + "\n",
+                           join(target, "@@Zope", "Root"))
+
+    def findrooturl(self, target):
+        dir = realpath(target)
+        while dir:
+            zopedir = join(dir, "@@Zope")
+            rootfile = join(zopedir, "Root")
+            try:
+                data = self.readfile(rootfile)
+            except IOError:
+                pass
+            else:
+                data = data.strip()
+                if data:
+                    return data
+            dir = dirname(dir)
+        return None
 
     def setrooturl(self, rooturl):
         self.rooturl = rooturl
-        if self.rooturl is None:
+        if not self.rooturl:
             self.roottype = self.rootpath = None
             self.user_passwd = self.host_port = None
             return
@@ -101,6 +122,20 @@
         netloc, self.rootpath = urllib.splithost(rest)
         self.user_passwd, self.host_port = urllib.splituser(netloc)
 
+    def readfile(self, file, mode="r"):
+        f = open(file, mode)
+        try:
+            return f.read()
+        finally:
+            f.close()
+
+    def writefile(self, data, file, mode="w"):
+        f = open(file, mode)
+        try:
+            f.write(data)
+        finally:
+            f.close()
+
     def httpreq(self, path, view, datafp=None, content_type="application/zip"):
         if not path.endswith("/"):
             path += "/"
@@ -140,39 +175,75 @@
                         errcode, errmsg,
                         self.slurptext(fp, headers))
         if headers["Content-type"] != "application/zip":
-            raise Error("The request didn't return a zipfile:\n%s",
-                        self.slurptext(fp, headers).strip())
+            raise Error(self.slurptext(fp, headers).strip())
         return fp, headers
 
-    def checkout(self):
-        fspath = self.topdir
-        if not self.rooturl:
-            raise Error("root url not found nor explicitly set")
-        if os.path.exists(fspath):
-            raise Error("can't checkout into existing directory", fspath)
-        fp, headers = self.httpreq(self.rootpath,
-                                   "@@toFS.zip?writeOriginals=False")
+    def slurptext(self, fp, headers):
+        data = fp.read()
+        ctype = headers["Content-type"]
+        if ctype == "text/html":
+            s = StringIO()
+            f = formatter.AbstractFormatter(formatter.DumbWriter(s))
+            p = htmllib.HTMLParser(f)
+            p.feed(data)
+            p.close()
+            return s.getvalue()
+        if ctype.startswith("text/"):
+            return data
+        return "Content-Type %r" % ctype
+
+class FSSync(object):
+
+    def __init__(self, metadata=None, network=None, rooturl=None):
+        if metadata is None:
+            metadata = Metadata()
+        if network is None:
+            network = Network()
+        self.metadata = metadata
+        self.network = network
+        self.network.setrooturl(rooturl)
+
+    def checkout(self, target):
+        rootpath = self.network.rootpath
+        if not rootpath:
+            raise Error("root url not set")
+        if self.metadata.getentry(target):
+            raise Error("target already registered", target)
+        if exists(target) and not isdir(target):
+            raise Error("target should be a directory", target)
+        self.ensuredir(target)
+        fp, headers = self.network.httpreq(rootpath,
+                                           "@@toFS.zip?writeOriginals=False")
         try:
-            self.merge_zipfile(fp)
+            self.merge_zipfile(fp, target)
         finally:
             fp.close()
-        self.saverooturl()
+        self.network.saverooturl(target)
 
-    def commit(self):
-        names = self.metadata.getnames(self.topdir)
-        if len(names) != 1:
-            raise Error("can only commit from toplevel directory")
-        entry = self.metadata.getentry(join(self.topdir, names[0]))
+    def commit(self, target):
+        entry = self.metadata.getentry(target)
+        if not entry:
+            names = self.metadata.getnames(target)
+            if len(names) != 1:
+                raise Error("can only commit a single directory")
+            target = join(target, names[0])
+            entry = self.metadata.getentry(target)
+        self.network.loadrooturl(target)
         path = entry["path"]
         zipfile = tempfile.mktemp(".zip")
+        head, tail = split(realpath(target))
         try:
-            sts = os.system("cd %s; zip -q -r %s ." %
-                            (commands.mkarg(self.topdir), zipfile))
+            sts = os.system("cd %s; zip -q -r %s %s @@Zope" %
+                            (commands.mkarg(head),
+                             zipfile,
+                             commands.mkarg(tail)))
             if sts:
                 raise Error("zip command failed")
             infp = open(zipfile, "rb")
             try:
-                outfp, headers = self.httpreq(path, "@@fromFS.zip", infp)
+                outfp, headers = self.network.httpreq(path,
+                                                      "@@fromFS.zip",
+                                                      infp)
             finally:
                 infp.close()
         finally:
@@ -180,22 +251,29 @@
             if isfile(zipfile):
                 os.remove(zipfile)
         try:
-            self.merge_zipfile(outfp)
+            self.merge_zipfile(outfp, head)
         finally:
             outfp.close()
 
-    def update(self):
-        fp, headers = self.httpreq(self.rootpath,
-                                   "@@toFS.zip?writeOriginals=False")
+    def update(self, target):
+        entry = self.metadata.getentry(target)
+        if not entry:
+            names = self.metadata.getnames(target)
+            if len(names) != 1:
+                raise Error("can only commit a single directory")
+            target = join(target, names[0])
+            entry = self.metadata.getentry(target)
+        self.network.loadrooturl(target)
+        head, tail = split(realpath(target))
+        path = entry["path"]
+        fp, headers = self.network.httpreq(path,
+                                           "@@toFS.zip?writeOriginals=False")
         try:
-            if headers["Content-Type"] != "application/zip":
-                raise Error("The request didn't return a zipfile:\n%s",
-                            self.slurptext(fp, headers).strip())
-            self.merge_zipfile(fp)
+            self.merge_zipfile(fp, head)
         finally:
             fp.close()
 
-    def merge_zipfile(self, fp):
+    def merge_zipfile(self, fp, localdir):
         zipfile = tempfile.mktemp(".zip")
         try:
             tfp = open(zipfile, "wb")
@@ -208,7 +286,7 @@
                 os.mkdir(tmpdir)
                 cmd = "cd %s; unzip -q %s" % (tmpdir, zipfile)
                 sts, output = commands.getstatusoutput(cmd)
-                self.merge_dirs(self.topdir, tmpdir)
+                self.merge_dirs(localdir, tmpdir)
                 print "All done."
             finally:
                 if isdir(tmpdir):
@@ -282,7 +360,7 @@
             if lentry or rentry:
                 if x not in ldirs:
                     os.mkdir(local)
-            self.merge_dirs(local, remote)
+                self.merge_dirs(local, remote)
 
         for x in sorted(nondirs):
             if x in dirs:
@@ -363,64 +441,3 @@
     def ensuredir(self, dir):
         if not isdir(dir):
             os.makedirs(dir)
-
-    def slurptext(self, fp, headers):
-        data = fp.read()
-        ctype = headers["Content-type"]
-        if ctype == "text/html":
-            s = StringIO()
-            f = formatter.AbstractFormatter(formatter.DumbWriter(s))
-            p = htmllib.HTMLParser(f)
-            p.feed(data)
-            p.close()
-            return s.getvalue()
-        if ctype.startswith("text/"):
-            return data
-        return "Content-Type %r" % ctype
-
-    def findrooturl(self):
-        dir = self.topdir
-        while dir:
-            zopedir = join(dir, "@@Zope")
-            rootfile = join(zopedir, "Root")
-            try:
-                data = self.readfile(rootfile)
-                return data.strip()
-            except IOError:
-                pass
-            dir = self.parent(dir)
-        return None
-
-    def saverooturl(self):
-        if self.rooturl:
-            self.writefile(self.rooturl + "\n",
-                           join(self.topdir, "@@Zope", "Root"))
-        else:
-            print "No root url saved"
-
-    def readfile(self, file, mode="r"):
-        f = open(file, mode)
-        try:
-            return f.read()
-        finally:
-            f.close()
-
-    def writefile(self, data, file, mode="w"):
-        f = open(file, mode)
-        try:
-            f.write(data)
-        finally:
-            f.close()
-
-    def parent(self, path):
-        anomalies = ("", os.curdir, os.pardir)
-        head, tail = split(path)
-        if tail not in anomalies:
-            return head
-        head, tail = split(normpath(path))
-        if tail not in anomalies:
-            return head
-        head, tail = split(realpath(path))
-        if tail not in anomalies:
-            return head
-        return None


=== Zope3/src/zope/fssync/main.py 1.2 => 1.3 ===
--- Zope3/src/zope/fssync/main.py:1.2	Sat May 10 20:16:06 2003
+++ Zope3/src/zope/fssync/main.py	Tue May 13 11:28:03 2003
@@ -96,18 +96,17 @@
     else:
         return None
 
-def checkout(url, fspath, writeOriginals=True):
-    fs = FSSync(fspath)
-    fs.setrooturl(url)
-    fs.checkout()
+def checkout(rooturl, target):
+    fs = FSSync(rooturl=rooturl)
+    fs.checkout(target)
 
-def commit(fspath):
-    fs = FSSync(fspath)
-    fs.commit()
+def commit(target):
+    fs = FSSync()
+    fs.commit(target)
 
-def update(fspath):
-    fs = FSSync(fspath)
-    fs.update()
+def update(target):
+    fs = FSSync()
+    fs.update(target)
 
 def add(args):
     fs = FSSync(os.curdir)