PHP日常笔记
PHP开发环境
使用docker容器内的php环境
1.在 /usr/local/bin/ 里创建一个名为 php
的文件
sudo touch /usr/local/bin/php
2.使其可执行:
sudo chmod +x /usr/local/bin/php
3.编辑文件(使用 sudo)并粘贴以下代码 /app/github/m1
是工作路径,m1
是容器名:
command="docker exec -w /app/github/m1 -i m1 php "$@""
$command
php控制header头缓存时间
<?php
header('Expires: '.gmdate('D, d M Y H:i:s', time()+'86400').' GMT');
header('Cache-Control:max-age=86400');
header('Pragma:cache');
?>
PHP空数组转空对象
这个问题在与IOS、安卓客户端调试API的时候遇到,非空数组经过json_encode后会转为{}形式的对象(java里称字典)
而空数组会直接转成[]形式,这样造成客户端解析异常。
解决办法是在输出前强制转成object对象:
<?php
$a =array();
var_dump($a);
echo json_encode($a);
echo "\n";
$b = (object)$a;
var_dump($b);
echo json_encode($b);
输出:
array(0) {
}
[]
object(stdClass)#1 (0) {
}
{}
float精度丢失问题需要用BC函数库
要使用 BC 这个函数库,要在编译 PHP 程序时加入 –enable-bcmath 的选项。
bcadd: 将二个高精确度数字相加。
bccomp: 比较二个高精确度数字。
bcdiv: 将二个高精确度数字相除。
bcmod: 取得高精确度数字的余数。
bcmul: 将二个高精确度数字相乘。
bcpow: 求一高精确度数字次方值。
bcscale: 配置程序中所有 BC 函数库的默认小数点位数。
bcsqrt: 求一高精确度数字的平方根。
bcsub: 将二个高精确度数字相减。
static的属性,在内存中只有一份,为所有的实例共用。
使用self:: 关键字访问当前类的静态成员
使用parent::调用父类方法
abstract 抽象类 抽象方法
PHP 方法修饰符
Public(公开): 可以自由的在类的内部外部读取、修改。
Private(私有): 只能在这个当前类的内部读取、修改。
Protected(受保护):能够在这个类和类的子类中读取和修改。
Final (最终的) 不能被继承,也没有子类。
PHP序列化函数:
serialize()和unserialize():一个是进行序列化存储,另一个则是进行序列化恢复
PHP instatnceof运算符保障代码安全
使用instanceof运算符,可以判断当前实例是否可以有这样的一个形态。当前实例使用 instanceof与当前类,父类(向上无限追溯),已经实现的接口比较时,返回真。
代码格式:实例名 instanceof 类名
<?php
class User{
private $name;
public function getName(){
return "UserName is ".$this->name;
}
}
class NormalUser extends User {
private $age = 99;
public function getAge(){
return "age is ".$this->age;
}
}
class UserAdmin{ //操作.
public static function getUserInfo(User $_user){
if($_user instanceof NormalUser ){
echo $_user->getAge();
}else{
echo "类型不对,不能使用这个方法.";
}
}
}
$User = new User(); // 这里new的是User.
UserAdmin::getUserInfo($User);
?>
程序运行结果:
类型不对,不能使用这个方法.
PHP Ajax 跨域允许多个域名访问
根据系统变量HTTP_ORIGIN请求头返回不同结果:
<?php
$origin = isset($_SERVER['HTTP_ORIGIN'])? $_SERVER['HTTP_ORIGIN'] : '';
$allow_origin = array(
'http://client1.malu.me',
'http://client2.malu.me'
);
if(in_array($origin, $allow_origin)){
header('Access-Control-Allow-Origin:'.$origin);
}
?>
防注入
addslashes()
该函数在指定的预定义字符前添加反斜杠.
预定义字符是:
- 单引号(’)
- 双引号(”)
- 反斜杠(\)
- NULL
ECshop中addslashes_deep的原型
<?php
function addslashes_deep($value) {
if (empty($value)) {
return $value; //如为空,直接返回;
} else {
return is_array($value) ? array_map('addslashes_deep', $value): addslashes($value);
} //递归处理数组,直至遍历所有数组元素;
}
mysql_real_escape_string()
该函数转义 SQL 语句中使用的字符串中的特殊字符。
特殊字符包括:
\x00
\n
\r
\
'
"
\x1a
如果成功,则该函数返回被转义的字符串。如果失败,则返回 false。
<?php
function check_input($value)
{
// 去除斜杠
if (get_magic_quotes_gpc()) {
$value = stripslashes($value);
}
// 如果不是数字则加引号
if (!is_numeric($value)) {
$value = "'" . mysql_real_escape_string($value) . "'";
}
return $value;
}
$con = mysql_connect("localhost", "hello", "321");
if (!$con) {
die('Could not connect: ' . mysql_error());
}
// 进行安全的 SQL
$user = check_input($_POST['user']);
$pwd = check_input($_POST['pwd']);
$sql = "SELECT * FROM users WHERE
user=$user AND password=$pwd";
mysql_query($sql);
mysql_close($con);
?>
字符过滤的机制无法根本解决注入,完美解决方案就是使用拥有Prepared Statement机制的PDO和MYSQLi来代替mysql_query(注:mysql_query自 PHP 5.5.0 起已废弃,并在将来会被移除):
PDO:
<?php
$pdo = new PDO('mysql:dbname=dbtest;host=127.0.0.1;charset=utf8', 'user', 'pass');
$pdo->setAttribute(PDO::ATTR_EMULATE_PREPARES, false);
$pdo->setAttribute(PDO::ATTR_ERRMODE, PDO::ERRMODE_EXCEPTION);
$stmt = $pdo->prepare('SELECT * FROM employees WHERE name = :name');
$stmt->execute(array('name' => $name));
foreach ($stmt as $row) {
// do something with $row
}
?>
MYSQLi
<?php
$stmt = $dbConnection->prepare('SELECT * FROM employees WHERE name = ?');
$stmt->bind_param('s', $name);
$stmt->execute();
$result = $stmt->get_result();
while ($row = $result->fetch_assoc()) {
// do something with $row
}
?>
防XSS
对传入值强转,或者使用htmlspecialchars()
htmlspecialchars()函数把预定义的字符转换为 HTML 实体。
预定义的字符是:
& (和号)
" (双引号)
' (单引号)
< (小于)
> (大于)
如需把特殊的 HTML 实体转换回字符,请使用 htmlspecialchars_decode() 函数。
php编码转换
用iconv进行gbk转utf-8 或者gb2312转utf-8的时候经常出现乱码问题,推荐另外一个扩展函数:mb_convert_encoding
mb_convert_encoding的用法见官方: http://cn.php.net/manual/zh/function.mb-convert-encoding.php
注:需要先enable mbstring 扩展库