import socket
import argparse
import re


class RegexMatch(object):
    """
    Performs regular expression match on value.
    If the regular expression pattern matches it will it will return an error
    message that will work with argparse.
    """

    def __init__(self, pattern, statement=None):
        self.string_pattern = pattern
        self.pattern = re.compile(pattern)
        self.statement = statement
        if not self.statement:
            self.statement = "must match pattern %s" % self.string_pattern

    def __call__(self, string):
        match = self.pattern.search(string)
        if match:
            raise argparse.ArgumentError(None, self.statement)
        return string


class Hostname(object):
    """
    Checks wether a given hostname is resolvable in DNS, otherwise raising and
    argparse error.
    """

    def __init__(self, _socket=None):
        self.socket = _socket or socket  # just used for testing

    def __call__(self, string):
        parts = string.split(':', 1)
        name = parts[0]
        host = parts[-1]
        try:
            self.socket.getaddrinfo(host, 0)
        except self.socket.gaierror:
            msg = "hostname: %s is not resolvable" % host
            raise argparse.ArgumentError(None, msg)

        try:
            self.socket.getaddrinfo(name, 0, 0, 0, 0, self.socket.AI_NUMERICHOST)
        except self.socket.gaierror:
            return string  # not an IP
        else:
            msg = '%s must be a hostname not an IP' % name
            raise argparse.ArgumentError(None, msg)

        return string

@@ -1566,28 +1566,1133 @@
 msg)%0A%0A        return string%0A
+%0A%0Aclass Subnet(object):%0A    %22%22%22%0A    A really dumb validator to ensure that we are receiving a subnet (or%0A    something that actually looks like a subnet).%0A%0A    It doesn't enforce at all the constraints of proper validation as that has%0A    its own set of caveats that are difficult to implement given that%0A    ceph-deploy doesn't (should not) include third party dependencies.%0A    %22%22%22%0A%0A    def __call__(self, string):%0A        ip = string.split('/')%5B0%5D%0A        ip_parts = ip.split('.')%0A%0A        if len(ip_parts) != 4:%0A            err = %22subnet must have at least 4 numbers separated by dots like x.x.x.x/xx, but got: %25s%22 %25 string%0A            raise argparse.ArgumentError(None, err)%0A%0A        if %5Bi for i in ip_parts%5B:4%5D if i.isalpha()%5D:  # only numbers%0A            err = %22subnet must have digits separated by dots like x.x.x.x/xx, but got: %25s%22 %25 string%0A            raise argparse.ArgumentError(None, err)%0A%0A        if len(string.split('/')) != 2:%0A            err = %22subnet must contain a slash, like x.x.x.x/xx, but got: %25s%22 %25 string%0A            raise argparse.ArgumentError(None, err)%0A%0A        return string%0A

create a subnet arg validator