From 914655c52bbf1ca52792a57a831c35d337011cc6 Mon Sep 17 00:00:00 2001
From: Brian Warner <warner@lothar.com>
Date: Mon, 27 Oct 2008 13:34:49 -0700
Subject: [PATCH] interfaces.py: promote
 immutable.encode.NotEnoughSharesError.. it isn't just for immutable files any
 more

---
 src/allmydata/immutable/download.py          |  3 +--
 src/allmydata/immutable/encode.py            |  6 +-----
 src/allmydata/immutable/upload.py            |  6 +++---
 src/allmydata/interfaces.py                  |  3 +++
 src/allmydata/mutable/node.py                |  3 +--
 src/allmydata/mutable/retrieve.py            |  3 +--
 src/allmydata/test/common.py                 |  3 +--
 src/allmydata/test/test_encode.py            | 16 ++++++++--------
 src/allmydata/test/test_immutable_checker.py |  6 +++---
 src/allmydata/test/test_mutable.py           |  3 +--
 src/allmydata/test/test_system.py            |  4 ++--
 src/allmydata/test/test_upload.py            |  6 +++---
 12 files changed, 28 insertions(+), 34 deletions(-)

diff --git a/src/allmydata/immutable/download.py b/src/allmydata/immutable/download.py
index a2216bee..80cd2460 100644
--- a/src/allmydata/immutable/download.py
+++ b/src/allmydata/immutable/download.py
@@ -11,9 +11,8 @@ from allmydata.util import base32, mathutil, hashutil, log, observer
 from allmydata.util.assertutil import _assert
 from allmydata import codec, hashtree, storage, uri
 from allmydata.interfaces import IDownloadTarget, IDownloader, IFileURI, \
-     IDownloadStatus, IDownloadResults
+     IDownloadStatus, IDownloadResults, NotEnoughSharesError
 from allmydata.immutable import layout
-from allmydata.immutable.encode import NotEnoughSharesError
 from pycryptopp.cipher.aes import AES
 
 class HaveAllPeersError(Exception):
diff --git a/src/allmydata/immutable/encode.py b/src/allmydata/immutable/encode.py
index 1982567c..a2a13438 100644
--- a/src/allmydata/immutable/encode.py
+++ b/src/allmydata/immutable/encode.py
@@ -10,7 +10,7 @@ from allmydata.util import mathutil, hashutil, base32, log
 from allmydata.util.assertutil import _assert, precondition
 from allmydata.codec import CRSEncoder
 from allmydata.interfaces import IEncoder, IStorageBucketWriter, \
-     IEncryptedUploadable, IUploadStatus
+     IEncryptedUploadable, IUploadStatus, NotEnoughSharesError
 
 """
 The goal of the encoder is to turn the original file into a series of
@@ -60,10 +60,6 @@ hash tree is put into the URI.
 
 """
 
-class NotEnoughSharesError(Exception):
-    servermap = None
-    pass
-
 class UploadAborted(Exception):
     pass
 
diff --git a/src/allmydata/immutable/upload.py b/src/allmydata/immutable/upload.py
index 40fed09b..8c219935 100644
--- a/src/allmydata/immutable/upload.py
+++ b/src/allmydata/immutable/upload.py
@@ -17,7 +17,7 @@ from allmydata.immutable import encode
 from allmydata.util import base32, idlib, mathutil
 from allmydata.util.assertutil import precondition
 from allmydata.interfaces import IUploadable, IUploader, IUploadResults, \
-     IEncryptedUploadable, RIEncryptedUploadable, IUploadStatus
+     IEncryptedUploadable, RIEncryptedUploadable, IUploadStatus, NotEnoughSharesError
 from allmydata.immutable import layout
 from pycryptopp.cipher.aes import AES
 
@@ -161,7 +161,7 @@ class Tahoe2PeerSelector:
 
         peers = client.get_permuted_peers("storage", storage_index)
         if not peers:
-            raise encode.NotEnoughSharesError("client gave us zero peers")
+            raise NotEnoughSharesError("client gave us zero peers")
 
         # figure out how much space to ask for
 
@@ -273,7 +273,7 @@ class Tahoe2PeerSelector:
                 if self.last_failure_msg:
                     msg += " (%s)" % (self.last_failure_msg,)
                 log.msg(msg, level=log.UNUSUAL, parent=self._log_parent)
-                raise encode.NotEnoughSharesError(msg)
+                raise NotEnoughSharesError(msg)
             else:
                 # we placed enough to be happy, so we're done
                 if self._status:
diff --git a/src/allmydata/interfaces.py b/src/allmydata/interfaces.py
index 31d19c12..7acc163d 100644
--- a/src/allmydata/interfaces.py
+++ b/src/allmydata/interfaces.py
@@ -649,6 +649,9 @@ class IMutableFileNode(IFileNode, IMutableFilesystemNode):
         writer-visible data using this writekey.
         """
 
+class NotEnoughSharesError(Exception):
+    servermap = None
+
 class ExistingChildError(Exception):
     """A directory node was asked to add or replace a child that already
     exists, and overwrite= was set to False."""
diff --git a/src/allmydata/mutable/node.py b/src/allmydata/mutable/node.py
index b7d8800f..8ab2eacf 100644
--- a/src/allmydata/mutable/node.py
+++ b/src/allmydata/mutable/node.py
@@ -6,12 +6,11 @@ from zope.interface import implements
 from twisted.internet import defer, reactor
 from foolscap.eventual import eventually
 from allmydata.interfaces import IMutableFileNode, IMutableFileURI, \
-     ICheckable, ICheckerResults
+     ICheckable, ICheckerResults, NotEnoughSharesError
 from allmydata.util import hashutil, log
 from allmydata.util.assertutil import precondition
 from allmydata.uri import WriteableSSKFileURI
 from allmydata.monitor import Monitor
-from allmydata.immutable.encode import NotEnoughSharesError
 from pycryptopp.publickey import rsa
 from pycryptopp.cipher.aes import AES
 
diff --git a/src/allmydata/mutable/retrieve.py b/src/allmydata/mutable/retrieve.py
index 300475e0..9ce25c0d 100644
--- a/src/allmydata/mutable/retrieve.py
+++ b/src/allmydata/mutable/retrieve.py
@@ -6,10 +6,9 @@ from twisted.internet import defer
 from twisted.python import failure
 from foolscap import DeadReferenceError
 from foolscap.eventual import eventually, fireEventually
-from allmydata.interfaces import IRetrieveStatus
+from allmydata.interfaces import IRetrieveStatus, NotEnoughSharesError
 from allmydata.util import hashutil, idlib, log
 from allmydata import hashtree, codec, storage
-from allmydata.immutable.encode import NotEnoughSharesError
 from pycryptopp.cipher.aes import AES
 from pycryptopp.publickey import rsa
 
diff --git a/src/allmydata/test/common.py b/src/allmydata/test/common.py
index b40c1fc5..4e08af29 100644
--- a/src/allmydata/test/common.py
+++ b/src/allmydata/test/common.py
@@ -10,8 +10,7 @@ from foolscap.eventual import flushEventualQueue, fireEventually
 from allmydata import uri, dirnode, client
 from allmydata.introducer.server import IntroducerNode
 from allmydata.interfaces import IURI, IMutableFileNode, IFileNode, \
-     FileTooLargeError, ICheckable
-from allmydata.immutable.encode import NotEnoughSharesError
+     FileTooLargeError, NotEnoughSharesError, ICheckable
 from allmydata.checker_results import CheckerResults, CheckAndRepairResults, \
      DeepCheckResults, DeepCheckAndRepairResults
 from allmydata.mutable.common import CorruptShareError
diff --git a/src/allmydata/test/test_encode.py b/src/allmydata/test/test_encode.py
index 9266fdb8..0a477bbb 100644
--- a/src/allmydata/test/test_encode.py
+++ b/src/allmydata/test/test_encode.py
@@ -9,7 +9,7 @@ from allmydata import hashtree, uri
 from allmydata.immutable import encode, upload, download
 from allmydata.util import hashutil, testutil
 from allmydata.util.assertutil import _assert
-from allmydata.interfaces import IStorageBucketWriter, IStorageBucketReader
+from allmydata.interfaces import IStorageBucketWriter, IStorageBucketReader, NotEnoughSharesError
 
 class LostPeerError(Exception):
     pass
@@ -455,7 +455,7 @@ class Roundtrip(unittest.TestCase, testutil.ShouldFailMixin):
         d = self.send_and_recover((4,8,10), AVAILABLE_SHARES=2)
         def _done(res):
             self.failUnless(isinstance(res, Failure))
-            self.failUnless(res.check(download.NotEnoughSharesError))
+            self.failUnless(res.check(NotEnoughSharesError))
         d.addBoth(_done)
         return d
 
@@ -527,7 +527,7 @@ class Roundtrip(unittest.TestCase, testutil.ShouldFailMixin):
         d = self.send_and_recover((4,8,10), bucket_modes=modemap)
         def _done(res):
             self.failUnless(isinstance(res, Failure))
-            self.failUnless(res.check(download.NotEnoughSharesError))
+            self.failUnless(res.check(NotEnoughSharesError))
         d.addBoth(_done)
         return d
 
@@ -550,7 +550,7 @@ class Roundtrip(unittest.TestCase, testutil.ShouldFailMixin):
         d = self.send_and_recover((4,8,10), bucket_modes=modemap)
         def _done(res):
             self.failUnless(isinstance(res, Failure))
-            self.failUnless(res.check(download.NotEnoughSharesError))
+            self.failUnless(res.check(NotEnoughSharesError))
         d.addBoth(_done)
         return d
 
@@ -680,7 +680,7 @@ class Roundtrip(unittest.TestCase, testutil.ShouldFailMixin):
         d = self.send_and_recover((4,8,10), bucket_modes=modemap)
         def _done(res):
             self.failUnless(isinstance(res, Failure))
-            self.failUnless(res.check(download.NotEnoughSharesError))
+            self.failUnless(res.check(NotEnoughSharesError))
         d.addBoth(_done)
         return d
 
@@ -703,7 +703,7 @@ class Roundtrip(unittest.TestCase, testutil.ShouldFailMixin):
         d = self.send_and_recover((4,8,10), bucket_modes=modemap)
         def _done(res):
             self.failUnless(isinstance(res, Failure))
-            self.failUnless(res.check(download.NotEnoughSharesError))
+            self.failUnless(res.check(NotEnoughSharesError))
         d.addBoth(_done)
         return d
 
@@ -732,7 +732,7 @@ class Roundtrip(unittest.TestCase, testutil.ShouldFailMixin):
         d = self.send_and_recover((4,8,10), bucket_modes=modemap)
         def _done(res):
             self.failUnless(isinstance(res, Failure))
-            self.failUnless(res.check(encode.NotEnoughSharesError), res)
+            self.failUnless(res.check(NotEnoughSharesError), res)
         d.addBoth(_done)
         return d
 
@@ -743,7 +743,7 @@ class Roundtrip(unittest.TestCase, testutil.ShouldFailMixin):
         d = self.send_and_recover((4,8,10), bucket_modes=modemap)
         def _done(res):
             self.failUnless(isinstance(res, Failure))
-            self.failUnless(res.check(encode.NotEnoughSharesError))
+            self.failUnless(res.check(NotEnoughSharesError))
         d.addBoth(_done)
         return d
 
diff --git a/src/allmydata/test/test_immutable_checker.py b/src/allmydata/test/test_immutable_checker.py
index 7d1d99d8..8bf28f15 100644
--- a/src/allmydata/test/test_immutable_checker.py
+++ b/src/allmydata/test/test_immutable_checker.py
@@ -1,8 +1,8 @@
-from allmydata.immutable import encode, upload
+from allmydata.immutable import upload
 from allmydata.test.common import SystemTestMixin, ShareManglingMixin
 from allmydata.util import testutil
 from allmydata.monitor import Monitor
-from allmydata.interfaces import IURI
+from allmydata.interfaces import IURI, NotEnoughSharesError
 from twisted.internet import defer
 from twisted.trial import unittest
 import random, struct
@@ -273,7 +273,7 @@ class Test(ShareManglingMixin, unittest.TestCase):
                 self.fail() # should have gotten an errback instead
                 return result
             def _after_download_errb(failure):
-                failure.trap(encode.NotEnoughSharesError)
+                failure.trap(NotEnoughSharesError)
                 return None # success!
             d.addCallbacks(_after_download_callb, _after_download_errb)
         d.addCallback(_then_download)
diff --git a/src/allmydata/test/test_mutable.py b/src/allmydata/test/test_mutable.py
index bcf0d088..d778b93a 100644
--- a/src/allmydata/test/test_mutable.py
+++ b/src/allmydata/test/test_mutable.py
@@ -6,13 +6,12 @@ from twisted.internet import defer, reactor
 from twisted.python import failure
 from allmydata import uri, storage
 from allmydata.immutable import download
-from allmydata.immutable.encode import NotEnoughSharesError
 from allmydata.util import base32, testutil, idlib
 from allmydata.util.idlib import shortnodeid_b2a
 from allmydata.util.hashutil import tagged_hash
 from allmydata.util.fileutil import make_dirs
 from allmydata.interfaces import IURI, IMutableFileURI, IUploadable, \
-     FileTooLargeError, IRepairResults
+     FileTooLargeError, NotEnoughSharesError, IRepairResults
 from allmydata.monitor import Monitor
 from allmydata.test.common import ShouldFailMixin
 from foolscap.eventual import eventually, fireEventually
diff --git a/src/allmydata/test/test_system.py b/src/allmydata/test/test_system.py
index 42837841..e3d0ddfb 100644
--- a/src/allmydata/test/test_system.py
+++ b/src/allmydata/test/test_system.py
@@ -15,7 +15,7 @@ from allmydata.util import log, base32
 from allmydata.scripts import runner
 from allmydata.interfaces import IDirectoryNode, IFileNode, IFileURI, \
      ICheckerResults, ICheckAndRepairResults, IDeepCheckResults, \
-     IDeepCheckAndRepairResults, NoSuchChildError
+     IDeepCheckAndRepairResults, NoSuchChildError, NotEnoughSharesError
 from allmydata.monitor import Monitor, OperationCancelledError
 from allmydata.mutable.common import NotMutableError
 from allmydata.mutable import layout as mutable_layout
@@ -194,7 +194,7 @@ class SystemTest(SystemTestMixin, unittest.TestCase):
                 log.msg("finished downloading non-existend URI",
                         level=log.UNUSUAL, facility="tahoe.tests")
                 self.failUnless(isinstance(res, Failure))
-                self.failUnless(res.check(download.NotEnoughSharesError),
+                self.failUnless(res.check(NotEnoughSharesError),
                                 "expected NotEnoughSharesError, got %s" % res)
                 # TODO: files that have zero peers should get a special kind
                 # of NotEnoughSharesError, which can be used to suggest that
diff --git a/src/allmydata/test/test_upload.py b/src/allmydata/test/test_upload.py
index 221c985b..6bfe12eb 100644
--- a/src/allmydata/test/test_upload.py
+++ b/src/allmydata/test/test_upload.py
@@ -7,8 +7,8 @@ from twisted.internet import defer
 from cStringIO import StringIO
 
 from allmydata import uri
-from allmydata.immutable import upload, encode
-from allmydata.interfaces import IFileURI, FileTooLargeError
+from allmydata.immutable import upload
+from allmydata.interfaces import IFileURI, FileTooLargeError, NotEnoughSharesError
 from allmydata.util.assertutil import precondition
 from allmydata.util.deferredutil import DeferredListShouldSucceed
 from allmydata.util.testutil import ShouldFailMixin
@@ -347,7 +347,7 @@ class FullServer(unittest.TestCase):
         self.u.parent = self.node
 
     def _should_fail(self, f):
-        self.failUnless(isinstance(f, Failure) and f.check(encode.NotEnoughSharesError), f)
+        self.failUnless(isinstance(f, Failure) and f.check(NotEnoughSharesError), f)
 
     def test_data_large(self):
         data = DATA
-- 
2.45.2