проверьте тип IP-адреса, IPv4 или IPv6

Мне нужно проверить, является ли IP-адрес IPv4 или IPv6, чтобы соответствующим образом манипулировать им.

это может быть достигнуто чем-то простым, скажем

<cfset ip = "2a01:bc80:1::">
<cfif ip does not contain ":">
<cfset ipV="IPv4">
<cfelse>
<cfset ipV="IPv6">

хотя, с другой стороны, не думайте, что это надежный подход к решению этой проблемы. Я также пытался переписать пример php с регулярным выражением, но не смог разобраться.

<cfset ip = "24.225.236.0">
<cfset checkIp = ReMatch("^[0-9a-f]{1,4}:([0-9a-f]{0,4}:){1,6}[0-9a-f]{1,4}$/", trim(ip))>

<cfif checkIp neq 0>
<cfset ipV="IPv4">
<cfelse>
<cfset ipV="IPv6">
</cfif>

<cfdump var="#ipV#">

Каков наилучший и надежный способ проверки версии ip?


person user2595617    schedule 03.11.2013    source источник
comment
Почему проверка двоеточия не является надежной? Если вы знаете, что у вас есть IP-адрес, это нормально? Можете ли вы иметь адрес IPv6 без двоеточия?   -  person Peter Boughton    schedule 03.11.2013
comment
Я буду использовать CGI.REMOTE_ADDR для получения IP-адреса пользователя, поэтому правильный IP-адрес должен передаваться в код каждый раз. может быть, мне следует добавить код, чтобы проверить, действителен ли IP!?   -  person user2595617    schedule 03.11.2013
comment
Я думаю, что у IPv6 всегда есть хотя бы один:   -  person user2595617    schedule 03.11.2013


Ответы (2)


Если в IPv6 должно быть двоеточие, единственное небольшое улучшение прямой проверки содержания состоит в том, чтобы не беспокоить проверку после пятого символа, потому что сегменты не длиннее четырех шестнадцатеричных символов?

Кроме того, поскольку двоеточие, скорее всего, находится на пятой позиции, запуск оттуда приведет к более быстрому возврату истинных результатов, поэтому использование lastIndexOf, вероятно, немного более эффективен. (Хотя разница в большинстве случаев будет незначительной.)

<cfset IpV = ( ip.lastIndexOf(':',4) GTE 0 ) ? 'IPv6' : 'IPv4' />

Число 4 связано с тем, что это метод Java, и это способ обращения к пятому символу с индексом 0. Если совпадений нет, возвращается -1, следовательно, часть GTE 0.

Другое улучшение не имеет отношения к проверке IP, но это тернарный условный оператор... Variable = BooleanCondition ? ValueIfTrue : ValueIfFalse лучше подходит для простых условных назначений, подобных этому.

person Peter Boughton    schedule 03.11.2013

Я бы сделал UDF isIPv4(), чтобы вам не приходилось сравнивать результат после выполнения проверки. Это может быть так же просто, как:

<cfscript>
function isIPv4(ip){
  return listlen(ip,".") EQ 4;
}
</cfscript>

И тогда все, что вам нужно сделать, это:

<CFIF isIPv4(IPAddressToTest)>
  This is IPv4
<CFELSE>
  This is not IPv4
</CFIF>

Вот UDF-совместимая с ColdFusion 5 функция, которая проверяет правильность каждого октета. (Это хорошее место для проверки.):

http://cflib.org/udf/IsIP

person James Moberg    schedule 04.11.2013