¿Cómo validar el formato de una dirección MAC?

¿Cuál es la mejor manera de validar que una dirección MAC ingresada por el usuario?

El formato es HH:HH:HH:HH:HH:HH , donde cada H es un carácter hexadecimal.

Por ejemplo, 00:29:15:80:4E:4A es válido, mientras que 00:29:804E4A no es válido.

Si te refieres solo a la syntax, entonces esta expresión regular debería funcionar para ti.

 import re ... if re.match("[0-9a-f]{2}([-:]?)[0-9a-f]{2}(\\1[0-9a-f]{2}){4}$", x.lower()): ... 

acepta 12 dígitos hexadecimales con : o - o nada como separadores entre pares (pero el separador debe ser uniforme … o todos los separadores son : o son todos - o no hay separador).

Esta es la explicación:

  • [0-9a-f] significa un dígito hexadecimal
  • {2} significa que queremos dos de ellos
  • [-:]? Significa un guión o dos puntos, pero opcional. Tenga en cuenta que el guión como primer carácter no significa un rango, sino que solo significa en sí mismo. Esta subexpresión se incluye entre paréntesis, por lo que se puede reutilizar más tarde como referencia.
  • [0-9a-f]{2} es otro par de dígitos hexadecimales
  • \\1 esto significa que queremos hacer coincidir la misma expresión con la que coincidimos antes como separador. Esto es lo que garantiza la uniformidad. Tenga en cuenta que la syntax de expresiones regulares es \1 pero estoy usando una cadena normal, por lo que la barra invertida debe evitarse duplicándola.
  • [0-9a-f]{2} otro par de dígitos hexadecimales
  • {4} el bloque entre paréntesis anterior debe repetirse exactamente 4 veces, dando un total de 6 pares de dígitos: [] ( ) * 4
  • $ La cuerda debe terminar justo después de ellos.

Tenga en cuenta que en Python re.match solo verifica el inicio al principio de la cadena y, por lo tanto, no es necesario un ^ al principio.

Odio los progtwigs que obligan al usuario a pensar como una computadora.

Hazlo más amigable aceptando cualquier formato válido.

Elimine el separador, sea lo que sea, luego obtenga el valor hexadecimal que queda. De esa manera, si un usuario ingresa guiones o espacios, también funciona.

 import string allchars = "".join(chr(a) for a in range(256)) delchars = set(allchars) - set(string.hexdigits) def checkMAC(s): mac = s.translate("".join(allchars),"".join(delchars)) if len(mac) != 12: raise ValueError, "Ethernet MACs are always 12 hex characters, you entered %s" % mac return mac.upper() checkMAC("AA:BB:CC:DD:EE:FF") checkMAC("00-11-22-33-44-66") checkMAC("1 2 3 4 5 6 7 8 9 abc") checkMAC("This is not a mac") 

Si quieres asegurarte de que haya ‘-‘ o ‘:’ en todo pero no ambos, puedes usar el siguiente en Python:

 import re def is_valid_macaddr802(value): allowed = re.compile(r""" ( ^([0-9A-F]{2}[-]){5}([0-9A-F]{2})$ |^([0-9A-F]{2}[:]){5}([0-9A-F]{2})$ ) """, re.VERBOSE|re.IGNORECASE) if allowed.match(value) is None: return False else: return True 

Esto funciona como un encanto.

 def isMAC48Address(inputString): if inputString.count(":")!=5: return False for i in inputString.split(":"): for j in i: if j>"F" or (j<"A" and not j.isdigit()) or len(i)!=2: return False return True 
 private static final String MAC_PATTERN = "^([0-9A-Fa-f]{2}[:-]){5}([0-9A-Fa-f]{2})$"; private boolean validateMAC(final String mac){ Pattern pattern = Pattern.compile(MAC_PATTERN); Matcher matcher = pattern.matcher(mac); return matcher.matches(); } 

Las direcciones MAC separadas por guiones también pueden contener un prefijo ’01 – ‘, que especifica que es una dirección MAC de Ethernet (no token ring, por ejemplo … ¿quién usa token ring?).

Aquí hay algo que es algo completo y fácil de leer de forma lógica paso a paso:

 def IsMac(S): digits = S.split(':') if len(digits) == 1: digits = S.split('-') if len(digits) == 7: if digits[0] != '01': return False digits.pop(0) if len(digits) != 6: return False for digit in digits: if len(digit) != 2: return False try: int(digit, 16) except ValueError: return False return True for test in ('01-07-09-07-b4-ff-a7', # True '07:09:07:b4:ff:a7', # True '07-09-07-b4-GG-a7', # False '7-9-7-b4-F-a7', # False '7-9-7-b4-0xF-a7'): # False print test, IsMac(test) 
 import re def MacValidator(inputMacList): def MacParser(mac): octets = re.split('[\:\-]', mac) if len(octets) != 6: return False for i in octets: try: if int(i, 16) > 255: return False except: return False return mac return [i.upper() for i in inputMacList if MacParser(i) != False] macList = ["00-15-F2-20-4D-6B", "Kozel", "00:13:aa:00:00:01", "00:13:AA:00:tr:01", "00-01-01-20-55-55", "00-01-01-20abc-55"] validMacList = MacValidator(macList) 

Hice trampa y usé la combinación de múltiples respuestas enviadas por otras personas. Creo que esto es bastante claro y directo un trazador de líneas. mac_validation debe devolver True o False .

 import re mac_validation = bool(re.match('^' + '[\:\-]'.join(['([0-9a-f]{2})']*6) + '$', mac_input.lower())) 

Este Regex valida el siguiente formato de MAC

 "Ae:Bd:00:00:00:00" "00-00-00-00-00-00" "aaaa.bbbb.cccc" 
 private static final String MAC_PATTERN = "(([0-9A-Fa-f]{2}[-:.]){5}[0-9A-Fa-f]{2})|(([0-9A-Fa-f]{4}\\.){2}[0-9A-Fa-f]{4})"; public class MacRegExp { private static final String MAC_PATTERN = "(([0-9A-Fa-f]{2}[-:.]){5}[0-9A-Fa-f]{2})|(([0-9A-Fa-f]{4}\\.){2}[0-9A-Fa-f]{4})"; static boolean validateMAC(final String mac){ Pattern pattern = Pattern.compile(MAC_PATTERN); Matcher matcher = pattern.matcher(mac); return matcher.matches(); } } 

Espero que esto ayude