Сетевые дела / FAQ по PHP
Оглавление
- Почему с'апложенные jpeg-файлы не отобpажаются? (бьются?). Веб-сервер - русский Апач.
- Как опpеделить валидность e-mail?
- Как определить валидность URL?
- Как определить размер файла, если известен только его URL?
- Как правильно перенаправить browser на нужный адрес?
Почему с'апложенные jpeg-файлы не отобpажаются? (бьются?). Веб-сервер - русский Апач.
Все дело в том, что русский Апач по умолчанию производит перекодировку файлов. Так, символ с кодом 0х00 он заменяет на пробел (символ с кодом 0х20).
Для борьбы с этим эффектом нужно добавить в конфигурационный файл Апача httpd.conf следующее:
<Location /> CharsetRecodeMultipartForms Off </Location>
Как опpеделить валидность e-mail?
<? function valid_mail ($email) { if (eregi("^[_\.0-9a-z-]+@([0-9a-z][0-9a-z-\.]+)\.([a-z]{2,4}$)", $email, $check)) { if (getmxrr($check[1] . "." . $check[2], $mxhosts)) { return "Valid"; } else { return "No MX for " . $check[1] . "." . $check[2]; } } else { return "Badly formed address"; } } ?>
Другой способ, использующий сокеты.
<? /* By: Jon S. Stevens jon@clearink.com Copyright 1998-1999 Jon S. Stevens, Clear Ink This code has all the normal disclaimers. It is free for any use, just keep the credits intact. */ function validateEmail ( $email ) { global $SERVER_NAME; $return = array ( false, "" ); list ( $user, $domain ) = split ( "@", $email, 2 ); $tld = $domain; if ( checkdnsrr ( $tld, "MX" ) ) { if ( getmxrr ( $tld, $mxhosts, $weight ) ) { for ( $i = 0; $i < count ( $mxhosts ); $i++ ) { $fp = fsockopen ( $mxhosts[$i], 25 ); if ( $fp ) { $s = 0; $c = 0; $out = ""; set_socket_blocking ( $fp, false ); do { $out = fgets ( $fp, 2500 ); if ( ereg ( "^220", $out ) ) { $s = 0; $out = ""; $c++; } else if ( ( $c > 0 ) && ( $out == "" ) ) { break; } else { $s++; } if ( $s == 9999 ) { break; } } while ( $out == "" ); set_socket_blocking ( $fp, true ); fputs ( $fp, "HELO $SERVER_NAME\n" ); $output = fgets ( $fp, 2000 ); fputs ( $fp, "MAIL FROM: <info@" . $tld . ">\n" ); $output = fgets ( $fp, 2000 ); fputs ( $fp, "RCPT TO: <$email>\n" ); $output = fgets ( $fp, 2000 ); if ( ereg ( "^250", $output ) ) { $return[0] = true; } else { $return[0] = false; $return[1] = $output; } fputs ( $fp, "QUIT\n" ); fclose( $fp ); if ( $return[0] == true ) { break; } } } } } return $return; } ?>
Как определить валидность URL?
<? function check_url($url) { if (eregi( '^http://', $url)) { $urlArray = parse_url($url); if (!$urlArray[port]) $urlArray[port] = '80'; if (!$urlArray[path]) $urlArray[path] = '/'; $sock = fsockopen($urlArray[host], $urlArray[port], &$errnum, &$errstr); if (!$sock) $res = 'DNS'; else { $dump .= "GET $urlArray[path] HTTP/1.1\r\n"; $dump .= "Host: $urlArray[host]\r\nConnection: close\r\n"; $dump .= "Connection: close\r\n"; fputs($sock, $dump); while ($str = fgets($sock, 1024)) { if (eregi("^http/[0-9]+.[0-9]+ ([0-9]{3}) [a-z ]*", $str)) $res[code] = trim( eregi_replace('^http/[0-9]+.[0-9]+([0-9]{3})[a-z ]*', "\\1", $str)); if (eregi("^Content-Type: ", $str)) $res[contentType] = trim(eregi_replace("^Content-Type: ", "", $str)); } fclose($sock); flush(); return $res[code]; } } else $res = "N/A"; return $res; } ?>
Как определить размер файла, если известен только его URL?
<? $hostname = "server2.ru"; // Имя сервера $filename = "/path_to_file/filename.ext"; // Файл, размер которого надо узнать get_size($hostname, $filename); // А это сама функция узнавания размера function get_size($hostname, $filename) { $end = false; $fp = fsockopen ($hostname, 80, &$errnr, &$errstr) or die("$errno:$errstr"); fputs($fp,"HEAD ".$filename." HTTP/1.0\n\n"); while (!$end) { $line = fgets($fp, 2048); if (trim($line) == "") { $end = true; } else { $str = explode(": ", $line); if ($str[0] == "Content-Length") print "Size of ".$filename." file ".$str[1]." bytes"; } } fclose($fp); } ?>
Как правильно перенаправить browser на нужный адрес?
Если следовать спецификациям HTTP/1.0 и HTTP/1.1, то pедиpект нужно делать пpимеpно следующим обpазом:
function my_redirect($url, $code = 302) { if ($code == 303) { preg_match('/^HTTP\/(\d)\.(\d)/', $_SERVER['SERVER_PROTOCOL'], $m); if (intval($m[1])*10+intval($m[2]) < 11) { $code=302; } } if ($code == 303) { Header($_SERVER['SERVER_PROTOCOL'].' 303 See Other'); } else { Header($_SERVER['SERVER_PROTOCOL'].' 302 Found'); } if (!strpos($url, '://')) { $url = 'http://'.$_SERVER['HTTP_HOST'].$url; } Header('Location: '.$url); ?> <html><head><title>Oops!</title></head><body><p><p> Ваш бpаузеp не понимает HTTP redirect (status code: <?=$code?> ).<br> Следуйте по <a href=" <?=$url?> ">этой ссылке</a>. </body></html> <? } ?>
Пpимеpы использования
my_redirect('/index.html'); my_redirect('http://warez.dot.no/'); my_redirect('accepted.html', 303);
Пояснения
1. Функции можно пеpедавать в качестве пеpвого паpаметpа либо локальный адpес (если pедиpект делается в пpеделах сайта), либо полный URL (если pедиpект делается на дpугой хост).
2. По умолчанию pедиpект делается со status code 302; однако спецификация HTTP/1.1 тpебует использования status code 303 в том случае, если pедиpект делается скpиптом в качестве ответа на POST (RFC 2616, секция 10.3.4). Если вы хоpошо поняли, о чём идёт pечь, то указывайте код 303 в качестве втоpого (необязательного) паpаметpа пpи ответе на POST, как показано в пpимеpе 3. Если не очень хоpошо поняли, не указывайте ничего -- всё будет pаботать и так :)
3. Hаличие небольшого гипеpтекстового довеска является обязательным (RFC 2616, секция 10.3.3).
4. Само собой pазумеется, что скpипт не должен ничего выводить ДО вызова этой функции.
Для перенаправления browser на нужный адрес (редирект) нужно воспользоваться конструкцией вида:
header("Location: " . $url);
Location должен задаваться абсолютным адресом, согласно RFC 2616 (http://www.w3.org/Protocols/rfc2616/rfc2616-sec14.html#sec14.30) :
"14.30 Location The Location response-header field is used to redirect the recipient to a location other than the Request-URI for completion of the request or identification of a new resource. For 201 (Created) responses, the Location is that of the new resource which was created by the request. For 3xx responses, the location SHOULD indicate the server's preferred URI for automatic redirection to the resource. The field value consists of a single absolute URI.
Location = "Location" ":" absoluteURI
An example is:
Location: http://www.w3.org/pub/WWW/People.html"
Для перенаправления по относительному адресу:
header("Location: http://".$_SERVER['HTTP_HOST'] .dirname($_SERVER['PHP_SELF']) ."/".$relative_url);