0

My goal is to set a session variable using an AJAX call that is written in plain JavaScript, not using JQuery. There are two files: The index.php file, and the PHP file called by the AJAX, ajax_set_session.php.

index.php starts a new session, sets the SESSION variable MyVariable to the string 'false' (i.e. not to the boolean false), prints the contents of SESSION, and then writes out the AJAX routine, which calls ajax_set_session.php. In turn, that resets MyVariable to 'true' and creates a new SESSION variable, YourVariable, to which is assigned the string 'xxx'. The contents of the revised SESSION are printed to the console within ajax_set_session.php, and when the code is executed, the one variable is, in fact, revised and the other is created. The index.php file then resumes and prints out the contents of SESSION, which are not revised, which I do not understand. I've checked the session_id between the two files, and it is the same.

Here is the code for index.php

<?php
session_start();
session_unset();
print_r('<pre>');
print_r('Before script:' . PHP_EOL);
$_SESSION['MyVariable'] = 'false';
print_r($_SESSION);
print_r('</pre>');
?>
<script>
var ajax = {};
var hasAX = window.hasOwnProperty("ActiveXObject");
ajax.x = function () {
    if (hasAX) {
        var versions = ["MSXML2.XmlHttp.6.0", "MSXML2.XmlHttp.5.0", "MSXML2.XmlHttp.4.0", "MSXML2.XmlHttp.3.0", "MSXML2.XmlHttp.2.0", "Microsoft.XMLHTTP"];
        var xhr;
        var i = 0;
        while (i < versions.length) {
            try {
                xhr = new ActiveXObject(versions[i]);
                break;
            } catch (e) {
                alert(e);
            }
            i += 1;
        }
        return xhr;
    } else {
        return new XMLHttpRequest();
    }
};

ajax.send = function (url, callback, method, data, async) {
    if (async === undefined) {
        async = true;
    }
    var x = ajax.x();
    x.open(method, url, async);
    x.onreadystatechange = function () {
        if (x.readyState === 4) {
            callback(x.responseText);
        }
    };
    if (method === 'POST') {
        x.setRequestHeader('Content-type', 'application/x-www-form-urlencoded');
    }
    x.send(data);
};

ajax.post = function (url, data, callback, async) {
    var query = [];
    Object.keys(data).forEach(function (key) {
        query.push(encodeURIComponent(key) + '=' + encodeURIComponent(data[key]));
    });
    ajax.send(url, callback, 'POST', query.join('&'), async);
};

function logStuff(userData) {
    if (typeof userData === "string") {
        console.log(userData);
    } else if (typeof userData === "object") {
        Object.keys(userData).forEach(function (key) {
            console.log(key + ": " + userData[key]);
        });
    }
}

ajax.post('ajax_set_session.php', {MyVariable: 'true', YourVariable: 'xxx'}, logStuff, true);

</script>
<?php
print_r('<pre>');
print_r('After script:' . PHP_EOL);
print_r($_SESSION);
print_r('</pre>');
?>

And here is the code for ajax_set_session.php:

<?php
session_start();
print_r($_SESSION);
foreach($_POST as $key => $value) {
    $_SESSION[$key] = $value;
}
print_r($_SESSION);
exit();
?>

If you run the code with the developer's console open, you'll see that SESSION is unchanged in the index.php file but it changes as expected in the ajax_set_session.php file. Why are the changes to SESSION not being retained? (I've tried switching between async true and false in the index.php AJAX routine, but to no avail.)

Tom
  • 1,836
  • 4
  • 16
  • 30
  • How exactly did you check the session id “between the two files”? Have you checked in network panel, if your AJAX request sends the session cookie? – CBroe Apr 10 '16 at 07:15
  • You don't understand script workflow. PHP script doesn't `resume`. It runs completely on server side and gives you html/js-codes and dies. After that your ajax code starts and sets a session variable. That's why you don't see any changes in `$_SESSION` output. – u_mulder Apr 10 '16 at 07:20
  • @CBroe echoing session_id() at the top of each script confirms the same session is use in each script – Tom Apr 10 '16 at 15:40
  • @u_mulder Not true; with PHP, I can write to the client an HTML form and a – Tom Apr 10 '16 at 15:43
  • No, you __can't__. – u_mulder Apr 10 '16 at 15:46
  • 1
    Pretty sure @u_mulder is right, you seem to have a fundamental misunderstanding of how these things actually work. You should go read http://stackoverflow.com/questions/13840429/what-is-the-difference-between-client-side-and-server-side-programming and make sure you understand what what’s explained there means. – CBroe Apr 10 '16 at 15:46
  • @CBroe See https://stackoverflow.com/questions/4454551/check-if-javascript-is-enabled-with-php/4454557 , 6th response down in the "oldest" response tab, the response by Gianluca Lodigiani. It works. I use it. So the question remains: How is it that Lodigiani's routine would work but my code above would not. (His response came from http://www.inspirationbit.com/php-js-detection-of-javascript-browser-settings/ , BTW, where the same technique is described.) – Tom Apr 10 '16 at 19:54
  • @u_mulder See my response to CBroe above for links demonstrating how this can and does work. – Tom Apr 10 '16 at 19:55
  • 1
    You still don't understand the server side and client side programming. Your provided code from other question works because form is __submitted__ and __redirected__ to the same page. See the words - __SUBMITTED__, __REDIRECTED__? In your case with ajax there's __NO__ form submit and __NO__ redirection to anywhere. Therefore there no changes in `$_SESSION` data. Please, read @CBroe link again. – u_mulder Apr 11 '16 at 06:35

0 Answers0