# Path: src/petmail/test/common.py
# class BasedirMixin:
#     def make_basedir(self):
#         # TestCase.mktemp() creates _trial_temp/MODULE/CLASS/TEST/RANDOM and
#         # returns join(that,"temp"). We just want the part that ends with
#         # TEST. So we rmdir the RANDOM and return .../TEST
#         basedir = self.mktemp()
#         random = os.path.dirname(basedir)
#         os.rmdir(random)
#         test = os.path.dirname(random)
#         return test
# 
# class NodeRunnerMixin:
#     def setUp(self):
#         self.sparent = service.MultiService()
#         self.sparent.startService()
#         d = allocate_port()
#         def _allocated(port):
#             p = "tcp:%d:interface=127.0.0.1" % port
#             r = RelayServer(p, None, wormhole.__version__)
#             r.setServiceParent(self.sparent)
#             self.relay_url = "http://127.0.0.1:%d/wormhole-relay/" % port
#         d.addCallback(_allocated)
#         return d
# 
#     def tearDown(self):
#         return self.sparent.stopService()
# 
#     def createNode(self, basedir, type="agent", local_mailbox=True):
#         so = runner.CreateNodeOptions()
#         args = []
#         if local_mailbox:
#             args.append("--local-mailbox")
#         args.extend(["--relay-url", self.relay_url])
#         args.append(basedir)
#         so.parseOptions(args)
#         out,err = StringIO(), StringIO()
#         rc = create_node(so, out, err, [type])
#         self.failUnlessEqual(rc, 0, (rc, out, err))
#         return rc, out ,err
# 
#     def buildNode(self, basedir):
#         so = runner.StartNodeOptions()
#         so.parseOptions([basedir])
#         p = startstop.MyPlugin(basedir, os.path.join(basedir, "petmail.db"))
#         n = p.makeService(so)
#         return n
# 
#     def startNode(self, basedir):
#         n = self.buildNode(basedir)
#         n.setServiceParent(self.sparent)
#         return n
# 
# class CLIinThreadMixin:
#     def cli(self, *args, **kwargs):
#         stdout, stderr = StringIO(), StringIO()
#         d = threads.deferToThread(runner.run, list(args), stdout, stderr,
#                                   kwargs.get("petmail"))
#         def _done(rc):
#             return stdout.getvalue(), stderr.getvalue(), rc
#         d.addCallback(_done)
#         return d
#     def mustSucceed(self, (out, err, rc)):
#         if rc != 0:
#             self.fail("rc=%s out='%s' err='%s'" % (rc, out, err))
#         self.stderr = err
#         return out
# 
#     def cliMustSucceed(self, *args, **kwargs):
#         d = self.cli(*args, **kwargs)
#         d.addCallback(self.mustSucceed)
#         return d
# 
# Path: src/petmail/test/pollmixin.py
# class PollMixin:
#     _poll_should_ignore_these_errors = []
# 
#     def poll(self, check_f, pollinterval=0.01, timeout=60):
#         # Return a Deferred, then call check_f periodically until it returns
#         # True, at which point the Deferred will fire.. If check_f raises an
#         # exception, the Deferred will errback. If the check_f does not
#         # indicate success within timeout= seconds, the Deferred will
#         # errback. If timeout=None, no timeout will be enforced, and the loop
#         # will poll forever (or really until Trial times out).
#         cutoff = None
#         if timeout is not None:
#             cutoff = time.time() + timeout
#         lc = task.LoopingCall(self._poll, check_f, cutoff)
#         d = lc.start(pollinterval)
#         def _convert_done(f):
#             f.trap(PollComplete)
#             return None
#         d.addErrback(_convert_done)
#         return d
# 
#     def _poll(self, check_f, cutoff):
#         if cutoff is not None and time.time() > cutoff:
#             raise TimeoutError("PollMixin never saw %s return True" % check_f)
#         if check_f():
#             raise PollComplete()
#         # since PollMixin is mostly used for unit tests, quit if we see any
#         # logged errors. This should give us a nice fast failure, instead of
#         # waiting for a timeout. Tests which use flushLoggedErrors() will
#         # need to warn us by putting the error types they'll be ignoring in
#         # self._poll_should_ignore_these_errors
#         if hasattr(self, "_observer") and hasattr(self._observer, "getErrors"):
#             errs = []
#             for e in self._observer.getErrors():
#                 if not e.check(*self._poll_should_ignore_these_errors):
#                     errs.append(e)
#             if errs:
#                 print errs
#                 self.fail("Errors snooped, terminating early")


import os, re, json
from twisted.trial import unittest
from .common import BasedirMixin, NodeRunnerMixin, CLIinThreadMixin
from .pollmixin import PollMixin
                return False
            self.cid_bob = a1[0]["cid"]
            a2 = n2.agent.command_list_addressbook()
            if not a2 or not a2[0]["acked"]:
                return False
            return True
        d.addCallback(lambda _: self.poll(until_invited))

        d.addCallback(lambda _: self.cli_1("send-basic", str(self.cid_bob),
                                           "hello bob"))

        def until_received():
            m2 = n2.agent.command_fetch_all_messages()
            if not m2:
                return False
            self.bob_messages = m2
            return True
        d.addCallback(lambda _: self.poll(until_received))

        def _check_message(_):
            m = self.bob_messages[0]
            self.failUnlessEqual(m["petname"], u"alice")
            self.failUnlessEqual(m["seqnum"], 1)
            self.failUnlessEqual(m["payload"], {"basic": "hello bob"})
        d.addCallback(_check_message)

        return d

    def test_mailbox(self):
        # two nodes, using a localdir relay, and --local-mailbox

# Path: src/petmail/test/common.py
# class BasedirMixin:
#     def make_basedir(self):
#         # TestCase.mktemp() creates _trial_temp/MODULE/CLASS/TEST/RANDOM and
#         # returns join(that,"temp"). We just want the part that ends with
#         # TEST. So we rmdir the RANDOM and return .../TEST
#         basedir = self.mktemp()
#         random = os.path.dirname(basedir)
#         os.rmdir(random)
#         test = os.path.dirname(random)
#         return test
# 
# class NodeRunnerMixin:
#     def setUp(self):
#         self.sparent = service.MultiService()
#         self.sparent.startService()
#         d = allocate_port()
#         def _allocated(port):
#             p = "tcp:%d:interface=127.0.0.1" % port
#             r = RelayServer(p, None, wormhole.__version__)
#             r.setServiceParent(self.sparent)
#             self.relay_url = "http://127.0.0.1:%d/wormhole-relay/" % port
#         d.addCallback(_allocated)
#         return d
# 
#     def tearDown(self):
#         return self.sparent.stopService()
# 
#     def createNode(self, basedir, type="agent", local_mailbox=True):
#         so = runner.CreateNodeOptions()
#         args = []
#         if local_mailbox:
#             args.append("--local-mailbox")
#         args.extend(["--relay-url", self.relay_url])
#         args.append(basedir)
#         so.parseOptions(args)
#         out,err = StringIO(), StringIO()
#         rc = create_node(so, out, err, [type])
#         self.failUnlessEqual(rc, 0, (rc, out, err))
#         return rc, out ,err
# 
#     def buildNode(self, basedir):
#         so = runner.StartNodeOptions()
#         so.parseOptions([basedir])
#         p = startstop.MyPlugin(basedir, os.path.join(basedir, "petmail.db"))
#         n = p.makeService(so)
#         return n
# 
#     def startNode(self, basedir):
#         n = self.buildNode(basedir)
#         n.setServiceParent(self.sparent)
#         return n
# 
# class CLIinThreadMixin:
#     def cli(self, *args, **kwargs):
#         stdout, stderr = StringIO(), StringIO()
#         d = threads.deferToThread(runner.run, list(args), stdout, stderr,
#                                   kwargs.get("petmail"))
#         def _done(rc):
#             return stdout.getvalue(), stderr.getvalue(), rc
#         d.addCallback(_done)
#         return d
#     def mustSucceed(self, (out, err, rc)):
#         if rc != 0:
#             self.fail("rc=%s out='%s' err='%s'" % (rc, out, err))
#         self.stderr = err
#         return out
# 
#     def cliMustSucceed(self, *args, **kwargs):
#         d = self.cli(*args, **kwargs)
#         d.addCallback(self.mustSucceed)
#         return d
# 
# Path: src/petmail/test/pollmixin.py
# class PollMixin:
#     _poll_should_ignore_these_errors = []
# 
#     def poll(self, check_f, pollinterval=0.01, timeout=60):
#         # Return a Deferred, then call check_f periodically until it returns
#         # True, at which point the Deferred will fire.. If check_f raises an
#         # exception, the Deferred will errback. If the check_f does not
#         # indicate success within timeout= seconds, the Deferred will
#         # errback. If timeout=None, no timeout will be enforced, and the loop
#         # will poll forever (or really until Trial times out).
#         cutoff = None
#         if timeout is not None:
#             cutoff = time.time() + timeout
#         lc = task.LoopingCall(self._poll, check_f, cutoff)
#         d = lc.start(pollinterval)
#         def _convert_done(f):
#             f.trap(PollComplete)
#             return None
#         d.addErrback(_convert_done)
#         return d
# 
#     def _poll(self, check_f, cutoff):
#         if cutoff is not None and time.time() > cutoff:
#             raise TimeoutError("PollMixin never saw %s return True" % check_f)
#         if check_f():
#             raise PollComplete()
#         # since PollMixin is mostly used for unit tests, quit if we see any
#         # logged errors. This should give us a nice fast failure, instead of
#         # waiting for a timeout. Tests which use flushLoggedErrors() will
#         # need to warn us by putting the error types they'll be ignoring in
#         # self._poll_should_ignore_these_errors
#         if hasattr(self, "_observer") and hasattr(self._observer, "getErrors"):
#             errs = []
#             for e in self._observer.getErrors():
#                 if not e.check(*self._poll_should_ignore_these_errors):
#                     errs.append(e)
#             if errs:
#                 print errs
#                 self.fail("Errors snooped, terminating early")


# Path: src/petmail/test/test_system.py
import os, re, json
from twisted.trial import unittest
from .common import BasedirMixin, NodeRunnerMixin, CLIinThreadMixin
from .pollmixin import PollMixin

                return False
            self.cid_bob = a1[0]["cid"]
            a2 = n2.agent.command_list_addressbook()
            if not a2 or not a2[0]["acked"]:
                return False
            return True
        d.addCallback(lambda _: self.poll(until_invited))

        d.addCallback(lambda _: self.cli_1("send-basic", str(self.cid_bob),
                                           "hello bob"))

        def until_received():
            m2 = n2.agent.command_fetch_all_messages()
            if not m2:
                return False
            self.bob_messages = m2
            return True
        d.addCallback(lambda _: self.poll(until_received))

        def _check_message(_):
            m = self.bob_messages[0]
            self.failUnlessEqual(m["petname"], u"alice")
            self.failUnlessEqual(m["seqnum"], 1)
            self.failUnlessEqual(m["payload"], {"basic": "hello bob"})
        d.addCallback(_check_message)

        return d

    def test_mailbox(self):
        # two nodes, using a localdir relay, and --local-mailbox

        self.basedir1 = os.path.join(self.make_basedir(), "node1")