# HG changeset patch
# User Antoine Beaupré <anarcat@koumbit.org>
# Date 1190232151 14400
# Node ID 4ca1dc1ddeccbbc2b47a739c427a482394945a0c
# Parent  c8a7086b20c3d523a4331693713515c1dd85d928
backport out-of-space error handling in PageEditor and fix 'current' corruption

diff -r c8a7086b20c3 -r 4ca1dc1ddecc MoinMoin/PageEditor.py
--- a/MoinMoin/PageEditor.py	Tue Sep 11 18:49:25 2007 +0200
+++ b/MoinMoin/PageEditor.py	Wed Sep 19 16:02:31 2007 -0400
@@ -795,6 +795,7 @@ Try a different name.""") % (wikiutil.es
         revdir = os.path.join(pagedir, 'revisions')
         cfn = os.path.join(pagedir,'current')
         clfn = os.path.join(pagedir,'current-locked')
+        cltfn = os.path.join(pagedir, 'current-locked.tmp')
         
         # !!! these log objects MUST be created outside the locked area !!!
 
@@ -837,14 +838,33 @@ Try a different name.""") % (wikiutil.es
                 f = open(clfn)
                 revstr = f.read()
                 f.close()
-                rev = int(revstr)
+                try:
+                    rev = int(revstr)
+                except ValueError, err:
+                    raise self.SaveError, _("Unabled to determine current page revision from the current page marker. The page %s is damaged and cannot be edited right now.") % self.page_name
+
                 if not was_deprecated:
                     if self.do_revision_backup or rev == 0:
                         rev += 1
                 revstr = '%08d' % rev
-                f = open(clfn, 'w')
-                f.write(revstr+'\n')
-                f.close()
+                # write the actual current marker to a tmpfile
+                try:
+                    f = file(cltfn, 'w')
+                    f.write(revstr+'\n')
+                    f.close()
+                except IOError, err:
+                    try:
+                        os.remove(cltfn)
+                    except:
+                        pass # we don't care for errors in the os.remove
+                    # throw a nicer exception
+                    if err.errno == errno.ENOSPC:
+                        raise self.SaveError, _("Cannot save page %s, no storage space left") % self.page_name
+                    else:
+                        raise self.SaveError, _("An unknown I/O error occured while saving page %s (errno=%d)") % (self.page_name, err.errno)
+                # atomically put it in place (except on windows)
+                else:
+                    filesys.rename(cltfn, clfn)
                 
                 # save to page file
                 pagefile = os.path.join(revdir, revstr)
