def setupCollector(tor_process_protocol): def setup_complete(port): print("Exposed collector Tor hidden service on httpo://%s" % port.onion_uri) tempfile.tempdir = os.path.join(_repo_dir, 'tmp') if not os.path.isdir(tempfile.gettempdir()): os.makedirs(tempfile.gettempdir()) _temp_dir = tempfile.mkdtemp() if config.main.tor_datadir is None: log.warn("Option 'tor_datadir' in oonib.conf is unspecified!") log.msg("Creating tmp directory in current directory for datadir.") log.debug("Using %s" % _temp_dir) datadir = _temp_dir else: datadir = config.main.tor_datadir torconfig = TorConfig(tor_process_protocol.tor_protocol) public_port = 80 # XXX there is currently a bug in txtorcon that prevents data_dir from # being passed properly. Details on the bug can be found here: # https://github.com/meejah/txtorcon/pull/22 hs_endpoint = TCPHiddenServiceEndpoint(reactor, torconfig, public_port, data_dir=datadir) hidden_service = hs_endpoint.listen(reportingBackend) hidden_service.addCallback(setup_complete) hidden_service.addErrback(txSetupFailed)
def test_failure(self): self.reactor.failures = 1 ep = TCPHiddenServiceEndpoint(self.reactor, self.config, 123) d = ep.listen(NoOpProtocolFactory()) self.config.bootstrap() d.addErrback(self.check_error) return d
def test_multiple_listen(self): ep = TCPHiddenServiceEndpoint(self.reactor, self.config, 123) d0 = ep.listen(NoOpProtocolFactory()) @defer.inlineCallbacks def more_listen(arg): yield arg.stopListening() d1 = ep.listen(NoOpProtocolFactory()) def foo(arg): return arg d1.addBoth(foo) defer.returnValue(arg) return d0.addBoth(more_listen) self.config.bootstrap() def check(arg): self.assertEqual('127.0.0.1', ep.tcp_endpoint._interface) self.assertEqual(len(self.config.HiddenServices), 1) d0.addCallback(check).addErrback(self.fail) return d0
def test_bad_listener(self): def test_gen(*args, **kw): kw['interface'] = '0.0.0.0' return TCP4ServerEndpoint(*args, **kw) ep = TCPHiddenServiceEndpoint(self.reactor, self.config, 123, endpoint_generator=test_gen) d = ep.listen(FakeProtocolFactory()) class ErrorCallback(object): got_error = None def __call__(self, err, *args, **kw): self.got_error = err.value error_cb = ErrorCallback() d.addErrback(error_cb) ## enough answers so the config bootstraps properly self.protocol.answers.append('config/names=\nHiddenServiceOptions Virtual') self.protocol.answers.append('HiddenServiceOptions') self.config.bootstrap() ## now we should have attempted to listen on the endpoint our ## test_gen() is generating - which should be the "wrong" ## answer of anything (0.0.0.0) self.assertEqual('0.0.0.0', ep.tcp_endpoint._interface) ## ...and the point of this test; ensure we got an error ## trying to listen on not-127.* self.assertTrue(error_cb.got_error is not None) self.assertTrue(isinstance(error_cb.got_error, RuntimeError)) return d
def test_stealth_auth(self): ''' make sure we produce a HiddenService instance with stealth-auth lines if we had authentication specified in the first place. ''' config = TorConfig(self.protocol) ep = TCPHiddenServiceEndpoint(self.reactor, config, 123, '/dev/null', stealth_auth=['alice', 'bob']) # make sure listen() correctly configures our hidden-serivce # with the explicit directory we passed in above d = ep.listen(NoOpProtocolFactory()) def foo(fail): print "ERROR", fail d.addErrback(foo) port = yield d self.assertEqual(1, len(config.HiddenServices)) self.assertEqual(config.HiddenServices[0].dir, '/dev/null') self.assertEqual(config.HiddenServices[0].authorize_client[0], 'stealth alice,bob') self.assertEqual(None, ep.onion_uri) config.HiddenServices[0].hostname = 'oh my' self.assertEqual('oh my', ep.onion_uri)
def test_multiple_listen(self): ep = TCPHiddenServiceEndpoint(self.reactor, self.config, 123) d0 = ep.listen(NoOpProtocolFactory()) @defer.inlineCallbacks def more_listen(arg): yield arg.stopListening() d1 = ep.listen(NoOpProtocolFactory()) def foo(arg): return arg d1.addBoth(foo) defer.returnValue(arg) return d0.addBoth(more_listen) self.config.bootstrap() def check(arg): self.assertEqual("127.0.0.1", ep.tcp_endpoint._interface) self.assertEqual(len(self.config.HiddenServices), 1) d0.addCallback(check).addErrback(self.fail) return d0
def test_basic(self): ep = TCPHiddenServiceEndpoint(self.reactor, self.config, 123) d = ep.listen(FakeProtocolFactory()) self.protocol.answers.append('config/names=\nHiddenServiceOptions Virtual\nOK') self.protocol.answers.append('HiddenServiceOptions') self.config.bootstrap() return d
def test_stealth_auth(self, ftb): ''' make sure we produce a HiddenService instance with stealth-auth lines if we had authentication specified in the first place. ''' config = TorConfig(self.protocol) ep = TCPHiddenServiceEndpoint(self.reactor, config, 123, '/dev/null', stealth_auth=['alice', 'bob']) # make sure listen() correctly configures our hidden-serivce # with the explicit directory we passed in above d = ep.listen(NoOpProtocolFactory()) def foo(fail): print("ERROR", fail) d.addErrback(foo) yield d # returns 'port' self.assertEqual(1, len(config.HiddenServices)) self.assertEqual(config.HiddenServices[0].dir, '/dev/null') self.assertEqual( config.HiddenServices[0].authorize_client[0], 'stealth alice,bob' ) self.assertEqual(None, ep.onion_uri) # XXX cheating; private API config.HiddenServices[0].hostname = 'oh my' self.assertEqual('oh my', ep.onion_uri)
def setupHSEndpoint(self, tor_process_protocol, torconfig, endpoint): endpointName = endpoint.settings['name'] def setup_complete(port): if LooseVersion(txtorcon_version) >= LooseVersion('0.10.0'): onion_uri = port.address.onion_uri else: onion_uri = port.onion_uri print("Exposed %s Tor hidden service " "on httpo://%s" % (endpointName, onion_uri)) public_port = 80 data_dir = os.path.join(torconfig.DataDirectory, endpointName) if LooseVersion(txtorcon_version) >= LooseVersion('0.10.0'): hs_endpoint = TCPHiddenServiceEndpoint(reactor, torconfig, public_port, hidden_service_dir=data_dir) else: hs_endpoint = TCPHiddenServiceEndpoint(reactor, torconfig, public_port, data_dir=data_dir) d = hs_endpoint.listen(endpoint) d.addCallback(setup_complete) d.addErrback(self.txSetupFailed) return d
def test_basic(self): ep = TCPHiddenServiceEndpoint(self.reactor, self.config, 123) d = ep.listen(FakeProtocolFactory()) self.protocol.answers.append( 'config/names=\nHiddenServiceOptions Virtual\nOK') self.protocol.answers.append('HiddenServiceOptions') self.config.bootstrap() return d
def test_explicit_data_dir(self): ep = TCPHiddenServiceEndpoint(self.reactor, self.config, 123, '/mumble/mumble') d = ep.listen(FakeProtocolFactory()) self.protocol.answers.append('config/names=\nHiddenServiceOptions Virtual') self.protocol.answers.append('HiddenServiceOptions') self.config.bootstrap() return d
def test_too_many_failures(self): self.reactor.failures = 12 ep = TCPHiddenServiceEndpoint(self.reactor, self.config, 123) d = ep.listen(FakeProtocolFactory()) self.protocol.answers.append('config/names=\nHiddenServiceOptions Virtual') self.protocol.answers.append('HiddenServiceOptions') self.config.bootstrap() d.addErrback(self.check_error) return d
def test_already_bootstrapped(self): self.protocol.answers.append('''config/names= HiddenServiceOptions Virtual''') self.protocol.answers.append('HiddenServiceOptions') self.config.bootstrap() ep = TCPHiddenServiceEndpoint(self.reactor, self.config, 123) d = ep.listen(FakeProtocolFactory()) return d
def test_basic(self): ep = TCPHiddenServiceEndpoint(self.reactor, self.config, 123) d = ep.listen(FakeProtocolFactory()) self.protocol.answers.append('config/names=\nHiddenServiceOptions Virtual') self.protocol.answers.append('HiddenServiceOptions') self.config.bootstrap() self.assertEqual('127.0.0.1', ep.tcp_endpoint._interface) ## make sure _ListWrapper's __repr__ doesn't explode repr(self.config.HiddenServices) return d
def getHSEndpoint(data_dir): if LooseVersion(txtorcon_version) >= LooseVersion('0.10.0'): return TCPHiddenServiceEndpoint(reactor, torconfig, 80, hidden_service_dir=data_dir) else: return TCPHiddenServiceEndpoint(reactor, torconfig, 80, data_dir=data_dir)
def test_too_many_failures(self): self.reactor.failures = 12 ep = TCPHiddenServiceEndpoint(self.reactor, self.config, 123) d = ep.listen(FakeProtocolFactory()) self.protocol.answers.append( 'config/names=\nHiddenServiceOptions Virtual\nOK') self.protocol.answers.append('HiddenServiceOptions') self.config.bootstrap() d.addErrback(self.check_error) return d
def test_already_bootstrapped(self): self.protocol.answers.append('''config/names= HiddenServiceOptions Virtual OK''') self.protocol.answers.append('HiddenServiceOptions') self.config.bootstrap() ep = TCPHiddenServiceEndpoint(self.reactor, self.config, 123) d = ep.listen(FakeProtocolFactory()) return d
def test_progress_updates(self): config = TorConfig() ep = TCPHiddenServiceEndpoint(self.reactor, config, 123) self.assertTrue(IProgressProvider.providedBy(ep)) prog = IProgressProvider(ep) ding = Mock() prog.add_progress_listener(ding) args = (50, "blarg", "Doing that thing we talked about.") # kind-of cheating, test-wise? ep._tor_progress_update(*args) self.assertTrue(ding.called_with(*args))
def setupHSEndpoint(self, tor_process_protocol, torconfig, endpoint): endpointName = endpoint.settings['name'] def setup_complete(port): print("Exposed %s Tor hidden service on httpo://%s" % (endpointName, port.onion_uri)) public_port = 80 hs_endpoint = TCPHiddenServiceEndpoint(reactor, torconfig, public_port, data_dir=os.path.join(torconfig.DataDirectory, endpointName)) d = hs_endpoint.listen(endpoint) d.addCallback(setup_complete) d.addErrback(self.txSetupFailed) return d
def test_explicit_data_dir(self): config = TorConfig(self.protocol) ep = TCPHiddenServiceEndpoint(self.reactor, config, 123, '/dev/null') # make sure listen() correctly configures our hidden-serivce # with the explicit directory we passed in above d = ep.listen(NoOpProtocolFactory()) def foo(fail): print "ERROR", fail d.addErrback(foo) port = yield d self.assertEqual(1, len(config.HiddenServices)) self.assertEqual(config.HiddenServices[0].dir, '/dev/null')
def setupBouncer(tor_process_protocol, datadir): def setup_complete(port): #XXX: drop some other noise about what API are available on this machine print("Exposed bouncer Tor hidden service on httpo://%s" % port.onion_uri) torconfig = TorConfig(tor_process_protocol.tor_protocol) public_port = 80 hs_endpoint = TCPHiddenServiceEndpoint(reactor, torconfig, public_port, data_dir=os.path.join(datadir, 'bouncer')) d = hs_endpoint.listen(ooniBouncer) d.addCallback(setup_complete) d.addErrback(txSetupFailed)
def test_explicit_data_dir(self): config = TorConfig(self.protocol) ep = TCPHiddenServiceEndpoint(self.reactor, config, 123, "/dev/null") # make sure listen() correctly configures our hidden-serivce # with the explicit directory we passed in above d = ep.listen(NoOpProtocolFactory()) def foo(fail): print "ERROR", fail d.addErrback(foo) port = yield d self.assertEqual(1, len(config.HiddenServices)) self.assertEqual(config.HiddenServices[0].dir, "/dev/null")
def test_endpoint_properties(self): ep = yield TCPHiddenServiceEndpoint.private_tor(Mock(), 80) self.assertEqual(None, ep.onion_private_key) self.assertEqual(None, ep.onion_uri) ep.hiddenservice = Mock() ep.hiddenservice.private_key = 'mumble' self.assertEqual('mumble', ep.onion_private_key)
def test_progress_updates_system_tor(self, ftb): control_ep = Mock() control_ep.connect = Mock(return_value=defer.succeed(None)) directlyProvides(control_ep, IStreamClientEndpoint) ep = TCPHiddenServiceEndpoint.system_tor(self.reactor, control_ep, 1234) ep._tor_progress_update(40, "FOO", "foo to bar") return ep
def test_system_tor(self): from test_torconfig import FakeControlProtocol def boom(*args): # why does the new_callable thing need a callable that # returns a callable? Feels like I must be doing something # wrong somewhere... def bam(*args, **kw): return self.protocol return bam with patch('txtorcon.endpoints.launch_tor') as launch_mock: with patch('txtorcon.endpoints.build_tor_connection', new_callable=boom) as btc: client = clientFromString(self.reactor, "tcp:host=localhost:port=9050") ep = yield TCPHiddenServiceEndpoint.system_tor( self.reactor, client, 80) port = yield ep.listen(NoOpProtocolFactory()) toa = port.getHost() self.assertTrue(hasattr(toa, 'onion_uri')) self.assertTrue(hasattr(toa, 'onion_port')) port.startListening() str(port) port.tor_config # system_tor should be connecting to a running one, # *not* launching a new one. self.assertFalse(launch_mock.called)
def test_explicit_data_dir(self, ftb): with util.TempDir() as tmp: d = str(tmp) with open(os.path.join(d, 'hostname'), 'w') as f: f.write('public') config = TorConfig(self.protocol) ep = TCPHiddenServiceEndpoint(self.reactor, config, 123, d) # make sure listen() correctly configures our hidden-serivce # with the explicit directory we passed in above yield ep.listen(NoOpProtocolFactory()) self.assertEqual(1, len(config.HiddenServices)) self.assertEqual(config.HiddenServices[0].dir, d) self.assertEqual(config.HiddenServices[0].hostname, 'public')
def test_private_tor_no_control_port(self): m = Mock() from txtorcon import endpoints endpoints.launch_tor = m ep = yield TCPHiddenServiceEndpoint.private_tor(Mock(), 80) m.assert_called()
def test_private_tor(self): m = Mock() from txtorcon import endpoints endpoints.launch_tor = m ep = yield TCPHiddenServiceEndpoint.private_tor(Mock(), 80, control_port=1234) self.assertTrue(m.called)
def test_system_tor(self): from test_torconfig import FakeControlProtocol def boom(*args): # why does the new_callable thing need a callable that # returns a callable? Feels like I must be doing something # wrong somewhere... def bam(*args, **kw): return self.protocol return bam with patch('txtorcon.endpoints.launch_tor') as launch_mock: with patch('txtorcon.endpoints.build_tor_connection', new_callable=boom) as btc: client = clientFromString( self.reactor, "tcp:host=localhost:port=9050" ) ep = yield TCPHiddenServiceEndpoint.system_tor(self.reactor, client, 80) port = yield ep.listen(NoOpProtocolFactory()) toa = port.getHost() self.assertTrue(hasattr(toa, 'onion_uri')) self.assertTrue(hasattr(toa, 'onion_port')) port.startListening() str(port) port.tor_config # system_tor should be connecting to a running one, # *not* launching a new one. self.assertFalse(launch_mock.called)
def getHSEndpoint(endpoint_config): from txtorcon import TCPHiddenServiceEndpoint hsdir = endpoint_config['hsdir'] hsdir = os.path.expanduser(hsdir) hsdir = os.path.realpath(hsdir) return TCPHiddenServiceEndpoint(reactor, config=get_global_tor(reactor), public_port=80, hidden_service_dir=hsdir)
def test_basic(self): listen = RuntimeError("listen") connect = RuntimeError("connect") reactor = proto_helpers.RaisingMemoryReactor(listen, connect) reactor.addSystemEventTrigger = Mock() ep = TCPHiddenServiceEndpoint(reactor, self.config, 123) self.config.bootstrap() yield self.config.post_bootstrap self.assertTrue(IProgressProvider.providedBy(ep)) try: port = yield ep.listen(NoOpProtocolFactory()) self.fail("Should have been an exception") except RuntimeError as e: # make sure we called listenTCP not connectTCP self.assertEqual(e, listen) repr(self.config.HiddenServices)
def test_explicit_data_dir(self): d = tempfile.mkdtemp() try: with open(os.path.join(d, 'hostname'), 'w') as f: f.write('public') config = TorConfig(self.protocol) ep = TCPHiddenServiceEndpoint(self.reactor, config, 123, d) # make sure listen() correctly configures our hidden-serivce # with the explicit directory we passed in above port = yield ep.listen(NoOpProtocolFactory()) self.assertEqual(1, len(config.HiddenServices)) self.assertEqual(config.HiddenServices[0].dir, d) self.assertEqual(config.HiddenServices[0].hostname, 'public') finally: shutil.rmtree(d, ignore_errors=True)
def test_explicit_data_dir(self): config = TorConfig() td = tempfile.mkdtemp() ep = TCPHiddenServiceEndpoint(self.reactor, config, 123, td) # fake out some things so we don't actually have to launch + bootstrap class FakeTorProcessProtocol(object): tor_protocol = self.reactor.protocol process = FakeTorProcessProtocol() ep._launch_tor = Mock(return_value=process) config._update_proto(Mock()) config.bootstrap() yield config.post_bootstrap # make sure listen() correctly configures our hidden-serivce # with the explicit directory we passed in above port = yield ep.listen(NoOpProtocolFactory()) self.assertEqual(1, len(config.HiddenServices)) self.assertEqual(config.HiddenServices[0].dir, td) shutil.rmtree(td)
def test_hiddenservice_key_unfound(self): ep = TCPHiddenServiceEndpoint.private_tor(self.reactor, 1234, hidden_service_dir="/dev/null") # FIXME Mock() should work somehow for this, but I couldn't # make it "go" class Blam(object): @property def private_key(self): raise IOError("blam") ep.hiddenservice = Blam() self.assertEqual(ep.onion_private_key, None) return ep
def setupCollector(tor_process_protocol, datadir): def setup_complete(port): #XXX: drop some other noise about what API are available on this machine print("Exposed collector Tor hidden service on httpo://%s" % port.onion_uri) torconfig = TorConfig(tor_process_protocol.tor_protocol) public_port = 80 # XXX there is currently a bug in txtorcon that prevents data_dir from # being passed properly. Details on the bug can be found here: # https://github.com/meejah/txtorcon/pull/22 #XXX: set up the various API endpoints, if configured and enabled #XXX: also set up a separate keyed hidden service for collectors to push their status to, if the bouncer is enabled hs_endpoint = TCPHiddenServiceEndpoint(reactor, torconfig, public_port, data_dir=os.path.join(datadir, 'collector')) d = hs_endpoint.listen(ooniBackend) d.addCallback(setup_complete) d.addErrback(txSetupFailed) return tor_process_protocol
def test_hiddenservice_key_unfound(self): ep = TCPHiddenServiceEndpoint.private_tor( self.reactor, 1234, hidden_service_dir='/dev/null') # FIXME Mock() should work somehow for this, but I couldn't make it "go" class Blam(object): @property def private_key(self): raise IOError("blam") ep.hiddenservice = Blam() self.assertEqual(ep.onion_private_key, None) return ep
def test_multiple_listen(self): ep = TCPHiddenServiceEndpoint(self.reactor, self.config, 123) d0 = ep.listen(FakeProtocolFactory()) @defer.inlineCallbacks def more_listen(arg): yield arg.stopListening() d1 = ep.listen(FakeProtocolFactory()) def foo(arg): return arg d1.addBoth(foo) defer.returnValue(arg) return d0.addBoth(more_listen) self.protocol.answers.append('config/names=\nHiddenServiceOptions Virtual') self.protocol.answers.append('HiddenServiceOptions') self.config.bootstrap() def check(arg): self.assertEqual('127.0.0.1', ep.tcp_endpoint._interface) d0.addCallback(check).addErrback(self.fail) return d0
def test_stealth_auth(self): """ make sure we produce a HiddenService instance with stealth-auth lines if we had authentication specified in the first place. """ config = TorConfig(self.protocol) ep = TCPHiddenServiceEndpoint(self.reactor, config, 123, "/dev/null", stealth_auth=["alice", "bob"]) # make sure listen() correctly configures our hidden-serivce # with the explicit directory we passed in above d = ep.listen(NoOpProtocolFactory()) def foo(fail): print "ERROR", fail d.addErrback(foo) port = yield d self.assertEqual(1, len(config.HiddenServices)) self.assertEqual(config.HiddenServices[0].dir, "/dev/null") self.assertEqual(config.HiddenServices[0].authorize_client[0], "stealth alice,bob") self.assertEqual(None, ep.onion_uri) config.HiddenServices[0].hostname = "oh my" self.assertEqual("oh my", ep.onion_uri)
def test_explicit_data_dir_valid_hostname(self): datadir = tempfile.mkdtemp() with open(os.path.join(datadir, 'hostname'), 'w') as f: f.write('timaq4ygg2iegci7.onion') with open(os.path.join(datadir, 'private_key'), 'w') as f: f.write('foo\nbar') try: ep = TCPHiddenServiceEndpoint(self.reactor, self.config, 123, datadir) self.assertEqual(ep.onion_uri, 'timaq4ygg2iegci7.onion') self.assertEqual(ep.onion_private_key, 'foo\nbar') finally: shutil.rmtree(datadir, ignore_errors=True)
def test_progress_updates_global_tor(self, ftb): with patch('txtorcon.endpoints.get_global_tor') as tor: ep = TCPHiddenServiceEndpoint.global_tor(self.reactor, 1234) tor.call_args[1]['progress_updates'](40, 'FOO', 'foo to the bar') return ep
def test_already_bootstrapped(self): self.config.bootstrap() ep = TCPHiddenServiceEndpoint(self.reactor, self.config, 123) d = ep.listen(NoOpProtocolFactory()) return d
def test_progress_updates_private_tor(self, ftb): with patch('txtorcon.endpoints.launch_tor') as tor: ep = TCPHiddenServiceEndpoint.private_tor(self.reactor, 1234) self.assertEqual(len(tor.mock_calls), 1) tor.call_args[1]['progress_updates'](40, 'FOO', 'foo to the bar') return ep
def run(reactor, cfg, tor, dry_run, once, file, count, keys): to_share = file.read() file.close() # stealth auth. keys authenticators = [] if keys: for x in xrange(keys): authenticators.append('carml_%d' % x) if len(authenticators): print(len(to_share), "bytes to share with", len(authenticators), "authenticated clients.") else: print(len(to_share), "bytes to share.") sys.stdout.flush() if dry_run: print('Not launching a Tor, listening on 8899.') ep = serverFromString(reactor, 'tcp:8899:interface=127.0.0.1') elif True: # connection is None: print("Launching Tor.") ep = TCPHiddenServiceEndpoint.global_tor(reactor, 80) txtorcon.IProgressProvider(ep).add_progress_listener(_progress) if keys: ep.stealth_auth = [ 'user_{}'.format(n) for n in range(keys) ] else: config = yield txtorcon.TorConfig.from_connection(connection) ep = txtorcon.TCPEphemeralHiddenServiceEndpoint(reactor, config, 80) root = Resource() data = Data(to_share, 'text/plain') root.putChild('', data) if once: count = 1 port = yield ep.listen(PasteBinSite(root, max_requests=count)) if keys == 0: clients = None else: # FIXME clients = port.tor_config.hiddenservices[0].clients host = port.getHost() if dry_run: print("Try it locally via http://127.0.0.1:8899") elif clients: print("You requested stealth authentication.") print("Tor has created %d keys; each key should be given to one person." % len(clients)) print('They can set one using the "HidServAuth" torrc option, like so:') print("") for client in clients: print(" HidServAuth %s %s" % (client[0], client[1])) print("") print("Alternatively, any Twisted endpoint-aware client can be given") print("the following string as an endpoint:") print("") for client in clients: print(" tor:%s:authCookie=%s" % (client[0], client[1])) print("") print("For example, using carml:") print("") for client in clients: print(" carml copybin --service tor:%s:authCookie=%s" % (client[0], client[1])) else: print("People using Tor Browser Bundle can find your paste at (once the descriptor uploads):") print("\n http://{0}\n".format(host.onion_uri)) print("for example:") print(" torsocks curl -o data.asc http://{0}\n".format(host.onion_uri)) if not count: print("Type Control-C to stop serving and shut down the Tor we launched.") print("If you wish to keep the hidden-service keys, they're in (until we shut down):") print(ep.hidden_service_dir) reactor.addSystemEventTrigger('before', 'shutdown', lambda: print(util.colors.red('Shutting down.'))) # we never callback() on this, so we serve forever d = defer.Deferred() yield d
def test_progress_updates_global_tor(self, tor): ep = TCPHiddenServiceEndpoint.global_tor(self.reactor, 1234) tor.call_args[1]['progress_updates'](40, 'FOO', 'foo to the bar') return ep
def __test_progress_updates_system_tor(self): ep = TCPHiddenServiceEndpoint.system_tor(self.reactor, 1234) ep._tor_progress_update(40, "FOO", "foo to bar") return ep