Brad
Brad

Reputation: 163436

Must I call session_set_save_handler() after session_write_close()?

I'm working in some legacy code which has a custom PHP session handler that is set up with session_set_save_handler(). At some point, that code must release the session data to another process. It calls session_write_close(), waits for the child process to finish, and then re-loads the session data by re-calling session_set_save_handler(), followed by session_start().

  1. session_set_save_handler()
  2. session_start()
  3. read/modify session data
  4. session_write_close()
  5. execute child process which loads the session, modifies data, and writes session
  6. session_set_save_handler() Is this step necessary?
  7. session_start()
  8. read data in session, possibly written by the prior child process

Is it necessary to set the session save handler again?

Upvotes: 1

Views: 548

Answers (1)

Rizier123
Rizier123

Reputation: 59701

So first I would recommend you to put:

session_write_close();

Before point 1, because if you have session auto on you will get an error since you have to call session_set_save_handler() before session_start().


But now to the real question:

  1. session_set_save_handler() Is this step necessary?

No it is not necessary! (But maybe you still want to call session_write_close(); before you start your session again)

So why don't you have to call it again?

Because it's a configuration option which will keep the value during the entire script execution (and will be restored at the end of the script).

You can also clearly see this in the php source code:

And a quote from there (/ext/session/session.c):

/* {{{ proto void session_set_save_handler(string open, string close, string read, string write, string destroy, string gc)
   Sets user-level functions */
static PHP_FUNCTION(session_set_save_handler)
{
    zval ***args = NULL;
    int i, num_args, argc = ZEND_NUM_ARGS();
    char *name;

    if (PS(session_status) != php_session_none) {
        RETURN_FALSE;
    }

    if (argc != 6) {
        WRONG_PARAM_COUNT;
    }

    if (zend_parse_parameters(argc TSRMLS_CC, "+", &args, &num_args) == FAILURE) {
        return;
    }

    for (i = 0; i < 6; i++) {
        if (!zend_is_callable(*args[i], 0, &name TSRMLS_CC)) {
            efree(args);
            php_error_docref(NULL TSRMLS_CC, E_WARNING, "Argument %d is not a valid callback", i+1);
            efree(name);
            RETURN_FALSE;
        }
        efree(name);
    }

    zend_alter_ini_entry("session.save_handler", sizeof("session.save_handler"), "user", sizeof("user")-1, PHP_INI_USER, PHP_INI_STAGE_RUNTIME);

    for (i = 0; i < 6; i++) {
        if (PS(mod_user_names).names[i] != NULL) {
            zval_ptr_dtor(&PS(mod_user_names).names[i]);
        }
        Z_ADDREF_PP(args[i]);
        PS(mod_user_names).names[i] = *args[i];
    }

    efree(args);
    RETURN_TRUE;
}
/* }}} */

You will see the function call of: zend_alter_ini_entry() which will change the value in the configuration for the script execution. So there is no need to call it again.

EDIT:

With session_set_save_handler() you will change the session.save_handler string configuration: http://php.net/manual/en/session.configuration.php#ini.session.save-handler

Upvotes: 2

Related Questions