在完成我的SQL架构(Different types of users redirected to same page (index.php) with different content)之后,我开始创建我的登录系统。 我现在有这个:
function login($email,$password){
$mysqli = $this ->dbConnect();
if($mysqli){
$strQuery = "SELECT USERS.ID, USERS.EMAIL, TYPES.NAME FROM `USERS` LEFT JOIN `TYPES` ON USERS.TYPEID = TYPES.ID WHERE `EMAIL` = '$email' AND `PASSWORD` = '$password'";
$recordSet = $mysqli->query($strQuery);
$row = $recordset->fetch_assoc();
if($recordset->num_rows>0){
$_SESSION['auth'] = $row['ID'];
$_SESSION['username'] = $row['EMAIL'];
$_SESSION['type'] = $row['NAME'];
header ("location:"index.php");
return true;
}
//....
}
}
这看起来不错吗?查询是对的吗?有任何改进建议吗?
更新
我的登录工作现在正在进行中。并且它重定向到index.php。但是在索引php中,我没有访问我存储在我的函数登录中的$ _SESSIONS变量。这个属性有什么问题吗?将标题放在函数内部不好? 谢谢:))
答案 0 :(得分:0)
我总结了之前的评论。
<强> 1。问题:您没有使用相同的变量
function login($email,$password){
和$strQuery = " ... WHERE EMAIL = '$email' AND PASSWORD = '$password'";
<强> 2。 Recomendation:使用相同的namming惯例
在您的SQL请求中,您使用了两种方式来使用字段:USERS.EMAIL
和EMAIL =
(使用`arround)。
使用相同的。这对于以后和以后会更容易调试。
即:当然,您不应每次都使用table.field
。例如,如果您只有一个表,或者如果它们之间没有共享字段,则不是强制性的。对于我的perosnnal用法,我总是使用这个table.field
。这将防止将来出现任何问题:)
第3。保护您的数据免遭任何注入
示例:
$post_email = isset($_POST['email']) ? htmlspecialchars($_POST['email']) : null;
改变电话
$this->login($post_email, ...)
最后使用这样的东西来保护你的数据:
$email = $mysqli->real_escape_string($email);
您已准备好接受您的请求:
" SELECT [..] FROM users as u [...] WHERE u.email = '$email' "
<强> 4。或使用特定功能
示例(real_escape_string
不再需要):
$stmt = $dbConnection->prepare('SELECT * FROM users WHERE email = ? AND password = ?');
$stmt->bind_param('s', $email);
$stmt->bind_param('s', $password);
$stmt->execute();
$result = $stmt->get_result();
while ($row = $result->fetch_assoc()) {
// do something with $row
}
http://php.net/manual/fr/class.mysqli.php
<强> 5。会话强>
如果您要在空间页面上激活会话,第一个代码(位于第一行)应为session_start()
。
调用此方法将激活会话,并加载带内容的$ _SESSION变量。
<?php // index.php
session_start(); // first line
// ... code
var_dump($_SESSION);
?>
&安培;
<?php // page.php
session_start(); // first line
// ... code
$_SESSION['test'] = time();
Header('Location: index.php');
?>
享受会话:p
<强> 6。处理特定数据
首先,您应该为每个用户设置存储凭据访问(ACL)的方法。例如,在数据库上存储一些值为100001,每个数字是特定操作的是/否访问(二进制访问模式);另一个系统是存储级别“1,2,3,4,5”......或“成员,客户,管理员......”。有很多方法:))
我会选择USER.ACCESS = member|customer|admin
解决方案
在登录页面
// is user successfully logged
$_SESSION['access'] = $row['access']; // member|customer|admin
// Header('Location: index.php');
在您网站的任何页面上:
if( in_array($_SESSION['access'], ['member', 'admin']) ) {
echo 'You are a member, you can see this part';
}
if( in_array($_SESSION['access'], ['customer', 'admin']) ) {
echo 'You are a customer, you can see this part';
}
或者
if( checkAccess() ) {
echo 'Welcome user !';
if( checkAccess(['member', 'customer']) ) {
echo 'This is a section for member, customer or admin :)';
}
if( checkAccess('member') ) {
echo 'You are a member, you can see this part';
}
if( checkAccess('customer') ) {
echo 'You are a customer, you can see this part';
}
}
function checkAccess($types = null) {
if( !isset($_SESSION['access']) )
return false; // not logged
if( is_null($types) )
retun true; // if empty, provide info about loggin.
// admin has always access to all sections of the website
$hasAccess = in_array($_SESSION['access'], ((array) $types) + ['admin']);
return $hasAccess; // user is logged + has accessor not ?
}
当然,您也可以使用includes
if( checkAccess('member') ) {
include 'secret_page_for_member.php';
}
或者,在包含的页面的基础上:
<?php
if( !checkAccess('admin') ) {
return '403 - Not authorized';
// die('403');
// throw new Exception('403');
}
// your code
?>