Ejemplo n.º 1
0
 def test_hostname_labels_valid_idn(self, label):
     # type: (Text) -> None
     """
     hostname_labels() generates IDN host name labels.
     """
     try:
         check_label(label)
         idna_encode(label)
     except UnicodeError:  # pragma: no cover
         raise AssertionError("Invalid IDN label: {!r}".format(label))
Ejemplo n.º 2
0
 def test_hostname_labels_valid_ascii(self, label):
     # type: (Text) -> None
     """
     hostname_labels() generates a ASCII host name labels.
     """
     try:
         check_label(label)
         label.encode("ascii")
     except UnicodeError:  # pragma: no cover
         raise AssertionError("Invalid ASCII label: {!r}".format(label))
Ejemplo n.º 3
0
 def test_hostnames_ascii(self, hostname):
     # type: (Text) -> None
     """
     hostnames() generates a ASCII host names.
     """
     try:
         for label in hostname.split(u"."):
             check_label(label)
         hostname.encode("ascii")
     except UnicodeError:  # pragma: no cover
         raise AssertionError(
             "Invalid ASCII host name: {!r}".format(hostname))
Ejemplo n.º 4
0
 def test_hostnames_idn(self, hostname):
     # type: (Text) -> None
     """
     hostnames() generates a IDN host names.
     """
     try:
         for label in hostname.split(u"."):
             check_label(label)
         idna_encode(hostname)
     except UnicodeError:  # pragma: no cover
         raise AssertionError(
             "Invalid IDN host name: {!r}".format(hostname))
Ejemplo n.º 5
0
def hostname_labels(draw, allow_idn=True):  # pragma: no cover
    # type: (DrawCallable, bool) -> Text
    """
    A strategy which generates host name labels.

    @param allow_idn: Whether to allow non-ASCII characters as allowed by
        internationalized domain names (IDNs).
    """
    if allow_idn:
        label = cast(Text, draw(idna_text(min_size=1, max_size=63)))

        try:
            label.encode("ascii")
        except UnicodeEncodeError:
            # If the label doesn't encode to ASCII, then we need to check the
            # length of the label after encoding to punycode and adding the
            # xn-- prefix.
            while len(label.encode("punycode")) > 63 - len("xn--"):
                # Rather than bombing out, just trim from the end until it is
                # short enough, so hypothesis doesn't have to generate new
                # data.
                label = label[:-1]

    else:
        label = cast(
            Text,
            draw(
                text(
                    min_size=1,
                    max_size=63,
                    alphabet=unicode(ascii_letters + digits + "-"),
                )
            ),
        )

    # Filter invalid labels.
    # It would be better not to generate bogus labels in the first place... but
    # that's not trivial.
    try:
        check_label(label)
    except UnicodeError:
        assume(False)

    return label
Ejemplo n.º 6
0
def hostname_labels(draw, allow_idn=True):  # pragma: no cover
    # type: (DrawCallable, bool) -> Text
    """
    A strategy which generates host name labels.

    @param allow_idn: Whether to allow non-ASCII characters as allowed by
        internationalized domain names (IDNs).
    """
    if allow_idn:
        label = draw(idna_text(min_size=1, max_size=63))

        try:
            label.encode("ascii")
        except UnicodeEncodeError:
            # If the label doesn't encode to ASCII, then we need to check the
            # length of the label after encoding to punycode and adding the
            # xn-- prefix.
            while len(label.encode("punycode")) > 63 - len("xn--"):
                # Rather than bombing out, just trim from the end until it is
                # short enough, so hypothesis doesn't have to generate new
                # data.
                label = label[:-1]

    else:
        label = draw(text(
            min_size=1, max_size=63,
            alphabet=unicode(ascii_letters + digits + u"-")
        ))

    # Filter invalid labels.
    # It would be better not to generate bogus labels in the first place... but
    # that's not trivial.
    try:
        check_label(label)
    except UnicodeError:
        assume(False)

    return label
Ejemplo n.º 7
0
        def test_hostname_labels_long_idn_punycode(self, data):
            # type: (SearchStrategy) -> None
            """
            hostname_labels() handles case where idna_text() generates text
            that encoded to punycode ends up as longer than allowed.
            """
            @composite
            def mock_idna_text(draw, min_size, max_size):
                # type: (DrawCallable, int, int) -> Text
                # We want a string that does not exceed max_size, but when
                # encoded to punycode, does exceed max_size.
                # So use a unicode character that is larger when encoded,
                # "á" being a great example, and use it max_size times, which
                # will be max_size * 3 in size when encoded.
                return u"\N{LATIN SMALL LETTER A WITH ACUTE}" * max_size

            with patch("hyperlink.hypothesis.idna_text", mock_idna_text):
                label = data.draw(hostname_labels())
                try:
                    check_label(label)
                    idna_encode(label)
                except UnicodeError:  # pragma: no cover
                    raise AssertionError(
                        "Invalid IDN label: {!r}".format(label))
Ejemplo n.º 8
0
def to_string(proto, buf):
    string = buf.decode("utf-8")
    for label in string.split("."):
        idna.check_label(label)
    return string