|
2 | 2 | import mock
|
3 | 3 | from zope.interface import implementer
|
4 | 4 | from twisted.trial import unittest
|
5 |
| -from twisted.internet import defer, reactor |
| 5 | +from twisted.internet import endpoints, defer, reactor |
6 | 6 | from twisted.internet.endpoints import clientFromString
|
7 | 7 | from twisted.internet.defer import inlineCallbacks
|
8 | 8 | from twisted.internet.interfaces import IStreamClientEndpoint
|
|
11 | 11 | from foolscap.api import Tub
|
12 | 12 | from foolscap.info import ConnectionInfo
|
13 | 13 | from foolscap.connection import get_endpoint
|
14 |
| -from foolscap.connections import tcp, tor |
| 14 | +from foolscap.connections import tcp, tor, i2p |
15 | 15 | from foolscap.tokens import NoLocationHintsError
|
16 | 16 | from foolscap.ipb import InvalidHintError
|
17 | 17 | from foolscap.test.common import (certData_low, certData_high, Target,
|
@@ -538,3 +538,108 @@ def make_takes_status(arg, update_status):
|
538 | 538 | self.assertIsInstance(ep, txtorcon.endpoints.TorClientEndpoint)
|
539 | 539 | self.assertEqual(host, "foo.onion")
|
540 | 540 | self.assertEqual(h._socks_desc, "tcp:127.0.0.1:1234")
|
| 541 | + |
| 542 | + |
| 543 | + |
| 544 | +class I2P(unittest.TestCase): |
| 545 | + @inlineCallbacks |
| 546 | + def test_default(self): |
| 547 | + with mock.patch("foolscap.connections.i2p.SAMI2PStreamClientEndpoint") as sep: |
| 548 | + sep.new = n = mock.Mock() |
| 549 | + n.return_value = expected_ep = object() |
| 550 | + h = i2p.default(reactor, misc_kwarg="foo") |
| 551 | + res = yield h.hint_to_endpoint("i2p:fppym.b32.i2p", reactor, |
| 552 | + discard_status) |
| 553 | + self.assertEqual(len(n.mock_calls), 1) |
| 554 | + args = n.mock_calls[0][1] |
| 555 | + got_sep, got_host, got_portnum = args |
| 556 | + self.assertIsInstance(got_sep, endpoints.TCP4ClientEndpoint) |
| 557 | + self.failUnlessEqual(got_sep._host, "127.0.0.1") # fragile |
| 558 | + self.failUnlessEqual(got_sep._port, 7656) |
| 559 | + self.failUnlessEqual(got_host, "fppym.b32.i2p") |
| 560 | + self.failUnlessEqual(got_portnum, None) |
| 561 | + kwargs = n.mock_calls[0][2] |
| 562 | + self.failUnlessEqual(kwargs, {"misc_kwarg": "foo"}) |
| 563 | + |
| 564 | + ep, host = res |
| 565 | + self.assertIdentical(ep, expected_ep) |
| 566 | + self.assertEqual(host, "fppym.b32.i2p") |
| 567 | + self.assertEqual(h.describe(), "i2p") |
| 568 | + |
| 569 | + @inlineCallbacks |
| 570 | + def test_default_with_portnum(self): |
| 571 | + # I2P addresses generally don't use port numbers, but the parser is |
| 572 | + # supposed to handle them |
| 573 | + with mock.patch("foolscap.connections.i2p.SAMI2PStreamClientEndpoint") as sep: |
| 574 | + sep.new = n = mock.Mock() |
| 575 | + n.return_value = expected_ep = object() |
| 576 | + h = i2p.default(reactor) |
| 577 | + res = yield h.hint_to_endpoint("i2p:fppym.b32.i2p:1234", reactor, |
| 578 | + discard_status) |
| 579 | + self.assertEqual(len(n.mock_calls), 1) |
| 580 | + args = n.mock_calls[0][1] |
| 581 | + got_sep, got_host, got_portnum = args |
| 582 | + self.assertIsInstance(got_sep, endpoints.TCP4ClientEndpoint) |
| 583 | + self.failUnlessEqual(got_sep._host, "127.0.0.1") # fragile |
| 584 | + self.failUnlessEqual(got_sep._port, 7656) |
| 585 | + self.failUnlessEqual(got_host, "fppym.b32.i2p") |
| 586 | + self.failUnlessEqual(got_portnum, 1234) |
| 587 | + ep, host = res |
| 588 | + self.assertIdentical(ep, expected_ep) |
| 589 | + self.assertEqual(host, "fppym.b32.i2p") |
| 590 | + |
| 591 | + @inlineCallbacks |
| 592 | + def test_default_with_portnum_kwarg(self): |
| 593 | + # setting extra kwargs on the handler should provide a default for |
| 594 | + # the portnum. sequential calls with/without portnums in the hints |
| 595 | + # should get the right values. |
| 596 | + h = i2p.default(reactor, port=1234) |
| 597 | + |
| 598 | + with mock.patch("foolscap.connections.i2p.SAMI2PStreamClientEndpoint") as sep: |
| 599 | + sep.new = n = mock.Mock() |
| 600 | + yield h.hint_to_endpoint("i2p:fppym.b32.i2p", reactor, |
| 601 | + discard_status) |
| 602 | + got_portnum = n.mock_calls[0][1][2] |
| 603 | + self.failUnlessEqual(got_portnum, 1234) |
| 604 | + |
| 605 | + with mock.patch("foolscap.connections.i2p.SAMI2PStreamClientEndpoint") as sep: |
| 606 | + sep.new = n = mock.Mock() |
| 607 | + yield h.hint_to_endpoint("i2p:fppym.b32.i2p:3456", reactor, |
| 608 | + discard_status) |
| 609 | + got_portnum = n.mock_calls[0][1][2] |
| 610 | + self.failUnlessEqual(got_portnum, 3456) |
| 611 | + |
| 612 | + with mock.patch("foolscap.connections.i2p.SAMI2PStreamClientEndpoint") as sep: |
| 613 | + sep.new = n = mock.Mock() |
| 614 | + yield h.hint_to_endpoint("i2p:fppym.b32.i2p", reactor, |
| 615 | + discard_status) |
| 616 | + got_portnum = n.mock_calls[0][1][2] |
| 617 | + self.failUnlessEqual(got_portnum, 1234) |
| 618 | + |
| 619 | + def test_default_badhint(self): |
| 620 | + h = i2p.default(reactor) |
| 621 | + d = defer.maybeDeferred(h.hint_to_endpoint, "i2p:not@a@hint", reactor, |
| 622 | + discard_status) |
| 623 | + f = self.failureResultOf(d, InvalidHintError) |
| 624 | + self.assertEqual(str(f.value), "unrecognized I2P hint") |
| 625 | + |
| 626 | + @inlineCallbacks |
| 627 | + def test_sam_endpoint(self): |
| 628 | + with mock.patch("foolscap.connections.i2p.SAMI2PStreamClientEndpoint") as sep: |
| 629 | + sep.new = n = mock.Mock() |
| 630 | + n.return_value = expected_ep = object() |
| 631 | + my_ep = FakeHostnameEndpoint(reactor, "localhost", 1234) |
| 632 | + h = i2p.sam_endpoint(my_ep, misc_kwarg="foo") |
| 633 | + res = yield h.hint_to_endpoint("i2p:fppym.b32.i2p", reactor, |
| 634 | + discard_status) |
| 635 | + self.assertEqual(len(n.mock_calls), 1) |
| 636 | + args = n.mock_calls[0][1] |
| 637 | + got_sep, got_host, got_portnum = args |
| 638 | + self.assertIdentical(got_sep, my_ep) |
| 639 | + self.failUnlessEqual(got_host, "fppym.b32.i2p") |
| 640 | + self.failUnlessEqual(got_portnum, None) |
| 641 | + kwargs = n.mock_calls[0][2] |
| 642 | + self.failUnlessEqual(kwargs, {"misc_kwarg": "foo"}) |
| 643 | + ep, host = res |
| 644 | + self.assertIdentical(ep, expected_ep) |
| 645 | + self.assertEqual(host, "fppym.b32.i2p") |
0 commit comments