php综合web开发(3)

来源:互联网 发布:淘宝返利api接口源码 编辑:程序博客网 时间:2024/05/22 17:33
本博客介绍了进行php综合web开发需要的技术与方法。

表单处理

表单处理是一个多进程,首先创建一张表单,以供用户输入详细的请求信息,然后输入的数据被发送到网页服务器,在服务器里这些数据得到编译与错误检测,而后进行相关操作。

<?php // formtest2.php  if (isset($_POST['name'])) $name = $_POST['name'];  else $name = "(Not entered)";  echo <<<_END  <html>    <head>      <title>Form Test</title>    </head>    <body>    Your name is: $name<br>    <form method="post" action="formtest.php">      What is your name?      <input type="text" name="name">      <input type="submit">    </form>    </body>  </html>_END;?>

最好关闭服务器的register_globals功能
可以提供默认值:

<form method="post" action="calc.php"><pre>      Loan Amount <input type="text" name="principle">Monthly Repayment <input type="text" name="monthly">  Number of Years <input type="text" name="years" value="25">    Interest Rate <input type="text" name="rate"  value="6">                  <input type="submit"></pre></form>

文本框:

<input type="text" name="name" size="size" maxlength="length" value="value">

size设置文本框宽度,maxlength设置允许输入字符的最大值。
文本域:

<textarea name="name" cols="width" rows="height" wrap="type">默认文本</textarea>

wrap指定换行类型——
off——不换行,用户输入时行完全出现
soft——文本换行,当一串长字符串没有回车换行时发送给服务器
hard——文本换行,当一串长字符串有软回车换行时以换行格式发送给服务器
默认为soft
复选框:

<input type="checkbox" nmae="name" value="value" checked="checked">

如果引入check属性,则浏览器显示时复选框被检测。检测了一个复选框默认提交值为”on”,可自己设定——value=”1”,如果只选择了一项,那么这一项会被提及,如果选择了多项,只有最后一个被提交,可使用数组提交多值:

Vanilla <input type="checkbox" name="ice[]" value="Vanilla">Chocolate <input type="checkbox" name="ice[]" value="Chocolate">Strawberry <input type="checkbox" name="ice[]" value="Strawberry">

表单提交时,选择了任意项,一个ice数组提交,包含所有选中的值。
单选按钮:
需要提供相同的名字——

8am-Noon<input type="radio" name="time" value="1">Noon-4pm<input type="radio" name="time" value="2" checked="checked">4pm-8pm<input type="radio" name="time" value="3">

隐藏字段:

<input type="hidden" name="name" value="value">

下拉选项列表:

<select name="name" size="size" multiple="multiple">

size指定行数,使用multiple可以按住ctrl选择多个选项

Vegetables<select name="veg" size="1">  <option value="Peas">Peas</option>  <option selected="selected" value="Beans">Beans</option>  <option value="Carrots">Carrots</option>  <option value="Cabbage">Cabbage</option>  <option value="Broccoli">Broccoli</option></select>

标签:

<label> 8am-Noon<input type="radio" name="name" value="1"></label>

当鼠标经过文本时变为箭头,代表可点击。
submit按钮:

<input type="submit" vlaue="Search">

也可用图片代替:

<input type="image" name="name" src="image.gif">

净化输入:

<?php  function sanitizeString($var)  {    if (get_magic_quotes_gpc())      $var = stripslashes($var);    $var = strip_tags($var);    $var = htmlentities($var);    return $var;  }  function sanitizeMySQL($connection, $var)  {    $var = $connection->real_escape_string($var);    $var = sanitizeString($var);    return $var;  }?>

实例:

<?php // convert.php  $f = $c = '';  if (isset($_POST['f'])) $f = sanitizeString($_POST['f']);  if (isset($_POST['c'])) $c = sanitizeString($_POST['c']);  if ($f != '')  {    $c = intval((5 / 9) * ($f - 32));    $out = "$f 癴 equals $c 癱";  }  elseif($c != '')  {    $f = intval((9 / 5) * $c + 32);    $out = "$c 癱 equals $f 癴";  }  else $out = "";  echo <<<_END<html>  <head>    <title>Temperature Converter</title>  </head>  <body>    <pre>      Enter either Fahrenheit or Celsius and click on Convert      <b>$out</b>      <form method="post" action="convert.php">        Fahrenheit <input type="text" name="f" size="7">           Celsius <input type="text" name="c" size="7">                   <input type="submit" value="Convert">      </form>    </pre>  </body></html>_END;  function sanitizeString($var)  {    $var = stripslashes($var);    $var = strip_tags($var);    $var = htmlentities($var);    return $var;  }?>

HTML5提供了一些新的特性:

Autocomplete属性:可用于<form>元素或color、date、email、password、range、search、tel、text或<input>元素的url类型,可以重新调用用户以前的输入使用autocomplete='on/off'开闭autofocus属性:聚焦——autofocus='autofocus'placeholder属性:允许在输入字段中放置提醒空格,有助于向用户解释应该输入的内容。<input type='text' name='name' size='50' placeholder='text to show'>required属性:确保在表单提交前完成字段的输入——required='required'Override属性:按元素逐个替换表单设置,例如使用formaction属性可以指定提交键将一个表单提交给不同的url,而不是由表单自身指定——<form action='url1.php' method='post'>    <input type='text' name='field'>    <input type='submit' formaction='url2.php'></form>html5也支持formctype、formmethod、formnovalidate、formtarget的重载使用width与height属性设置图像尺寸

cookies、会话与身份验证

cookie是web服务器通过web浏览器存储到本地的数据项,集合包含任何字母数字信息,并且可以从计算机收取信息返回给服务器,常见的应用包括会话跟踪、维持数据多次访问、保持购物车内容、存储登陆细节等。
cookie在传输网页header信息期间被发送,在网页的实际html发送前,一旦任何html被传输,那么cookie不可能被发送
设置cookie:
setcookie(name,value,expire,path,domian,secure,httponly);
expire指定cookie截止日期的UNIX时间戳,通常是time()加上一定的秒数,默认当浏览器关闭到期。
path指定服务器上的cookie路径,如果是一个斜杠/可以覆盖整个域,默认为cookie正被设置的当前目录
domain是cookie的互联网域名,如果是.webserver.com,则cookie对所有的webserver.com及其子域都有效,像www.webserver.com与Images.webserver.com
secure指定cookie是否通过https连接
httponly指定cookie是否必须使用http协议,如果为true则脚本语言无法访问cookie,默认为false

setcookie('username','value',time()+60*60*24*7,'/');

读取cookie:

if(isset($_COOKIE['username']))$username=$_COOKIE['username'];

只有浏览器重载了此网页和cookie返回到服务器的过程中才能再次读取cookie的值。
删除cookie:

setcookie('username','value',time()-2592000,'/');

HTTP身份验证:
要使用http身份验证,php得发送一个header请求让浏览器启动验证对话框

<?php  if (isset($_SERVER['PHP_AUTH_USER']) &&      isset($_SERVER['PHP_AUTH_PW']))  {    echo "Welcome User: " . $_SERVER['PHP_AUTH_USER'] .         " Password: "    . $_SERVER['PHP_AUTH_PW'];  }  else  {    header('WWW-Authenticate: Basic realm="Restricted Section"');    header('HTTP/1.0 401 Unauthorized');    die("Please enter your username and password");  }?>

可以使用php_sapi_name函数确定服务器接口。

<?php  $username = 'admin';  $password = 'letmein';  if (isset($_SERVER['PHP_AUTH_USER']) &&      isset($_SERVER['PHP_AUTH_PW']))  {    if ($_SERVER['PHP_AUTH_USER'] == $username &&        $_SERVER['PHP_AUTH_PW']   == $password)          echo "You are now logged in";    else die("Invalid username / password combination");  }  else  {    header('WWW-Authenticate: Basic realm="Restricted Section"');    header('HTTP/1.0 401 Unauthorized');    die ("Please enter your username and password");  }?>
保存用户名与口令:使用$token=hash('name','pass');得到一个32位字符的16进制数。加密保护——$token=hash('name','hqd%$tpasscg*l');
<?php //setupusers.php  require_once 'login.php';  $connection = new mysqli($hn, $un, $pw, $db);  if ($connection->connect_error) die($connection->connect_error);  $query = "CREATE TABLE users (    forename VARCHAR(32) NOT NULL,    surname  VARCHAR(32) NOT NULL,    username VARCHAR(32) NOT NULL UNIQUE,    password VARCHAR(32) NOT NULL  )";  $result = $connection->query($query);  if (!$result) die($connection->error);  $salt1    = "qm&h*";  $salt2    = "pg!@";  $forename = 'Bill';  $surname  = 'Smith';  $username = 'bsmith';  $password = 'mysecret';  $token    = hash('ripemd128', "$salt1$password$salt2");  add_user($connection, $forename, $surname, $username, $token);  $forename = 'Pauline';  $surname  = 'Jones';  $username = 'pjones';  $password = 'acrobat';  $token    = hash('ripemd128', "$salt1$password$salt2");  add_user($connection, $forename, $surname, $username, $token);  function add_user($connection, $fn, $sn, $un, $pw)  {    $query  = "INSERT INTO users VALUES('$fn', '$sn', '$un', '$pw')";    $result = $connection->query($query);    if (!$result) die($connection->error);  }?>
<?php // authenticate.php  require_once 'login.php';  $connection = new mysqli($db_hostname, $db_username, $db_password, $db_database);  if ($connection->connect_error) die($connection->connect_error);  if (isset($_SERVER['PHP_AUTH_USER']) &&      isset($_SERVER['PHP_AUTH_PW']))  {    $un_temp = mysql_entities_fix_string($connection, $_SERVER['PHP_AUTH_USER']);    $pw_temp = mysql_entities_fix_string($connection, $_SERVER['PHP_AUTH_PW']);    $query  = "SELECT * FROM users WHERE username='$un_temp'";    $result = $connection->query($query);    if (!$result) die($connection->error);    elseif ($result->num_rows)    {        $row = $result->fetch_array(MYSQLI_NUM);        $result->close();        $salt1 = "qm&h*";        $salt2 = "pg!@";        $token = hash('ripemd128', "$salt1$pw_temp$salt2");        if ($token == $row[3]) echo "$row[0] $row[1] :             Hi $row[0], you are now logged in as '$row[2]'";        else die("Invalid username/password combination");    }    else die("Invalid username/password combination");  }  else  {    header('WWW-Authenticate: Basic realm="Restricted Section"');    header('HTTP/1.0 401 Unauthorized');    die ("Please enter your username and password");  }  $connection->close();  function mysql_entities_fix_string($connection, $string)  {    return htmlentities(mysql_fix_string($connection, $string));  }   function mysql_fix_string($connection, $string)  {    if (get_magic_quotes_gpc()) $string = stripslashes($string);    return $connection->real_escape_string($string);  }?>

使用会话:

<?php // authenticate2.php  require_once 'login.php';  $connection = new mysqli($db_hostname, $db_username, $db_password, $db_database);  if ($connection->connect_error) die($connection->connect_error);  if (isset($_SERVER['PHP_AUTH_USER']) &&      isset($_SERVER['PHP_AUTH_PW']))  {    $un_temp = mysql_entities_fix_string($connection, $_SERVER['PHP_AUTH_USER']);    $pw_temp = mysql_entities_fix_string($connection, $_SERVER['PHP_AUTH_PW']);    $query = "SELECT * FROM users WHERE username='$un_temp'";    $result = $connection->query($query);    if (!$result) die($connection->error);    elseif ($result->num_rows)    {        $row = $result->fetch_array(MYSQLI_NUM);        $result->close();        $salt1 = "qm&h*";        $salt2 = "pg!@";        $token = hash('ripemd128', "$salt1$pw_temp$salt2");        if ($token == $row[3])        {            session_start();            $_SESSION['username'] = $un_temp;            $_SESSION['password'] = $pw_temp;            $_SESSION['forename'] = $row[0];            $_SESSION['surname']  = $row[1];            echo "$row[0] $row[1] : Hi $row[0],                you are now logged in as '$row[2]'";            die ("<p><a href='continue.php'>Click here to continue</a></p>");        }        else die("Invalid username/password combination");    }    else die("Invalid username/password combination");  }  else  {    header('WWW-Authenticate: Basic realm="Restricted Section"');    header('HTTP/1.0 401 Unauthorized');    die ("Please enter your username and password");  }  $connection->close();  function mysql_entities_fix_string($connection, $string)  {    return htmlentities(mysql_fix_string($connection, $string));  }   function mysql_fix_string($connection, $string)  {    if (get_magic_quotes_gpc()) $string = stripslashes($string);    return $connection->real_escape_string($string);  }?>
<?php // continue.php  session_start();  if (isset($_SESSION['username']))  {    $username = $_SESSION['username'];    $password = $_SESSION['password'];    $forename = $_SESSION['forename'];    $surname  = $_SESSION['surname'];    echo "Welcome back $forename.<br>          Your full name is $forename $surname.<br>          Your username is '$username'          and your password is '$password'.";  }  else echo "Please <a href='authenticate2.php'>click here</a> to log in.";?>

结束会话:

<?phpfunction destroy_session_and_data(){   session_start();   $_SESSION = array();   setcookie(session_name(), '', time() - 2592000, '/');   session_destroy();}?>

设置session的超时:
ini_set(‘session.gc_maxlifetime’,60*60*24);
查看超时周期:
ini_get(‘session.gc_maxlifetime’);

当ssl不可用,可通过存储ip地址及其他细节进一步验证用户:

$_SESSION['ip']=$_SERVER['REMOTE_ADDR'];

存储用户代理:

$_SESSION['ua']=$_SERVER['HTTP_USER_AGENT'];

容易受会话固定影响的会话:

<?php // sessiontest.php  session_start();  if (!isset($_SESSION['count'])) $_SESSION['count'] = 0;   else ++$_SESSION['count'];   echo $_SESSION['count'];?>

可用session_regenetate_id函数添加一个对改变会话id的简单检查,这个函数保存所有当前会话的变量值,但用攻击者不知道的新会话id进行替换。
会话的重新生成:

 <?php  session_start();  if (!isset($_SESSION['initiated']))  {    session_regenerate_id();    $_SESSION['initiated'] = 1;   }  if (!isset($_SESSION['count'])) $_SESSION['count'] = 0;   else ++$_SESSION['count'];  echo $_SESSION['count'];?>

强制只有cookie的会话:ini_set(‘session.use_only_cookies’,1);
使用共享服务器:
选择一个只有自己的账户可访问的目录来存储会话,在程序的开始放置一行ini_set的调用:

ini_set('session.save_path','/home/user/mysccount/sessions');
0 0