I';我在页面加载时将整个$_SESSION变量放入一个json对象中.虽然这对我有效,但这是一个好的做法吗


I'm putting my entire $_SESSION variable into a json object on page load. While this works for me, is this a good practice?

我在所有视图的底部都做了这样的事情:

<script type='text/javascript'>
$.post('php/ajax.php', {type:'session'}).done(function(data){
     var session = JSON.parse(data);
     $(document).ready(function(){
        $.getScript('resources/redactor/redactor.js');
        $.getScript('javascript/year_long_calendar.js');
        $.getScript('javascript/edit_lesson_modal.js');
     });
 });
</script>

这对我来说非常有效。我所有的脚本都加载在一个docReady中,我所有的ajax都需要一个在登录时生成并存储在$_SESSION中的令牌。这样可以防止人们使用假头攻击我的ajax逻辑。通过这样做,我的ajax调用看起来像:

$.post(url:'ajax.php', {token:session.token, id:id}).done(function(data){ ... });

我还可以访问其他会话变量

var user_id = session.user_id;

由于我从项目一开始就一直在做这件事,所以我有意将任何敏感信息(如密码)排除在会话变量之外。你对此有什么看法?这其中有没有让你觉得没有安全感,或者效率低下?我意识到$.getScript经常被用作加载库的一种懒惰的方式,但我认为我已经找到了它的一个非常有效的用途

除令牌外,$_SESSION中的所有数据都不敏感,您必须登录才能获得令牌。除非有人在真正的用户不在的时候恶意地跳上机器,确切地知道我的ajax逻辑在哪里,它是如何工作的,我如何存储会话,并在PostMan上伪造一个快速标题来删除我的所有表,否则我不认为这是一个问题。

编辑:@AnotherGuy帮助我实现了一个更好的解决方案。我的ajax.php文件现在看起来是这样的:

<?php session_start();
include('connect.php');
include('functions.php');
// check to see if http request is ajax (easy to fake but hey might as well)
if($_SERVER['HTTP_X_REQUESTED_WITH'] == 'XMLHttpRequest'){
    // when the user logs in, a random number is generated and saved to $_SESSION['token'].
    // this block is used to pass the token to a javascript variable securely
    if($_POST['type'] == 'session'){
        $session = [
            'token'=>$_SESSION['token'],
            'user_id'=>$_SESSION['user_id']
        ];
        echo json_encode($session);
    }
    // all post requests must pass the correct token variable to step into this block and access the ajax logic
    if(isset($_POST['token']) && $_POST['token'] == $_SESSION['token']){

        if($_POST['type'] == 'get'){
            $where = null;
            if(isset($_POST['where'])){
                $where = json_decode($_POST['where']);
            }
            $order_by = null;
            if(isset($_POST['order_by'])){
                $order_by = json_decode($_POST['order_by']);
            }
            echo json_encode(get($_POST['db'], $_POST['table'], $where, $order_by)->fetchAll());
        }
        if($_POST['type'] == 'put'){
            $set = json_decode($_POST['set']);
            echo put($_POST['db'], $_POST['table'], $set);
        }
        if($_POST['type'] == 'update'){
            $set = json_decode($_POST['set']);
            $where = json_decode($_POST['where']);
            update($_POST['db'], $_POST['table'], $set, $where);
        }
        if($_POST['type'] == 'delete'){
            $where = json_decode($_POST['where']);
            delete($_POST['db'], $_POST['from'], $where);
        }

从你描述你使用会话的方式来看,我看不出它有任何危害,但我仍然认为它很危险。想象一下你在未来从事另一个项目,然后再回到这个项目。你还会记得不要在会话中存储任何敏感信息吗?作为一个基本的经验法则,永远不要在会话中存储敏感信息,除非这是唯一的解决方案,而这是很少的。但有时会犯错误,它们可能会伤害你!

我会将其更改为以相同的方式看起来/工作,但为您提供更多与会话的解耦。如果你正在获取整个会话,你必然会检索一些永远不会被使用或永远不应该对客户端可用的信息(通过Javascript)。我会创建一个你要求的页面,它只能提供必要的信息。这样,您还可以确保只向客户端公开所需的信息。

因此,我将创建一个名为(或类似的)userInfo.php的页面,而不是请求一个通用的ajax.php文件。这样,您还可以消除随它一起发送的type变量

希望这能帮助到你,快乐编码!

您可以在浏览器中使用sesssionStorage将会话数据存储在序列化的JSON字符串中,并从那里对其进行操作。许多人建议使用这种方法,而不是使用Cookie W3Schools

干杯。