zendframework / zf1

This project reached its end-of-life on 2016-09-28. Contains conversion of ZF1 subversion repo to git, from version 15234 forward, and only containing master and release-1.12 branches and 1.12 tags.
https://framework.zend.com/blog/2016-06-28-zf1-eol.html
BSD 3-Clause "New" or "Revised" License
356 stars 800 forks source link

"session has already been started by session.auto-start or session_start()" error message is misleading #25

Open zfbot opened 11 years ago

zfbot commented 11 years ago

Jira Information

Original Issue:ZF-12438
Issue Type:Improvement
Reporter:Vestigal
Created:10/09/12
Assignee:Ralph Schindler
Components:Zend_Session

Description

On Ubuntu, garbage collection for sessions is taken care of by a cron job, rather than within PHP. If one downloads the PHP packages from Ubuntu's repository, then session.gc_probability in php.ini is set to 0, so PHP never runs the garbage collection for sessions. Unfortunately, if one changes session.gc_probability to something else, then one randomly encounters errors when the session garbage collection is run.

The error is something like this:

Fatal error: Uncaught exception 'Zend_Session_Exception' with message 'session has already been started by session.auto-start or session_start()' in /asps/www/library/Zend/Session.php:462
Stack trace: #0 /asps/www/library/Zend/Session/Namespace.php(143): Zend_Session::start(true)
             #1 /asps/www/library/Zend/Auth/Storage/Session.php(87): Zend_Session_Namespace->_construct('Zend_Auth')
             #2 /asps/www/library/Zend/Auth.php(91): Zend_Auth_Storage_Session->_construct()
             #3 /asps/www/library/Zend/Auth.php(141): Zend_Auth->getStorage()
             #4 /asps/www/application/layouts/scripts/layout.phtml(8): Zend_Auth->hasIdentity()
             ...

The issue appears to be that garbage collection is failing, and this causes Zend Framework to think that a session has already been started. The easiest way to test this that I've found is to set session.gc_probability to 1 and session.gc_divisor to 1, so that the error is triggered every time one tries to start a session. With the default values, the error usually only shows up once every hundred times the page loads. Of course, you'll need to be testing this on Ubuntu with one of their PHP packages to see this error.

It would be nice if errors could not be thrown in this case, or if the error message could be more descriptive. It took awhile to track down the cause of this error, but I eventually found the answer on [Stack Overflow|http://stackoverflow.com/a/7979354/862204].

zfbot commented 11 years ago

This issue was ported from the ZF2 Jira Issue Tracker at http://framework.zend.com/issues/browse/ZF-12438

Known GitHub users mentioned in the original message or comment:

vestigal commented 11 years ago

I was the original filer of this bug, back when it was on Jira.

ionutfechete commented 10 years ago

Still have this problem.. @vestigal Did you solved it? if yes, how? Thanks!

tomasfejfar commented 9 years ago

I just experienced this bug now.

In my case it was caused by the fact that sessions directory was not writable. It seems that Zend_Session checks only for success and assumes that any other result means session is already started.

cc @simonrjones

tomasfejfar commented 9 years ago

I actually debugged it to the fact that the exception is not thrown but added as a response exception instead - it's because it's initialized before Zend_Controller_Plugin_Errorhandler sets Zend_Controller_Front::getInstance()->throwExceptions() to true. Therefore the internal session exception Zend_Session::start() - /Users/tfejfar/libs/zf1/library/Zend/Session.php(Line:488): Error #2 session_write_close() [<a href='function.session-write-close'>function.session-write-close</a>]: open(/Users/tfejfar/sites/crossrail/application/../data/sessions/sess_8cae2e4a007afd2274821015f8c0ef45, O_RDWR) failed: Permission denied (13) /Users/tfejfar/libs/zf1/library/Zend/Session.php(Line:488): Error #2 session_write_close() [<a href='function.session-write-close'>function.session-write-close</a>]: Failed to write session data (files). Please verify that the current setting of session.save_path is correct

is added to exception stack, but later in the request when actually using the session the new "session already started" it's after the error handler set to throw the exceptions - so that one is thrown, but the first one is forgotten. But it's still in the exceptions stack ($this->_response->_exceptions).

One way to fix this could be to throw the first exception from exception stack if one is present. But that may not be the right one.

tomasfejfar commented 9 years ago

What would you think would be a good way to fix this? I could do a PR to fix it, but I'm not sure how exactly to fix it.

DominikAngerer commented 9 years ago

Currently facing this issue on my server - no changes made by us - also the folder are accessible and writeable.

tomasfejfar commented 9 years ago

You need to debug it to find out the core exception as described in my post above. That will set you on the right path :)

DominikAngerer commented 9 years ago

I found the issue. It was a long running - and sadly not good configured project. After thinking about permission problems or similar it was a simply as you can think. There where too many open session or better too many OLD session and the IIS simply couldn't handle that much files so the PHP IO was higher than the PHP execution time - removing the old Session's the problem simply was gone.

Thanks anyway @tomasfejfar!

antares7364 commented 7 years ago

This error message can also be caused by wrong permissions on the sessions folder, if the folder is not writeable or doesn't belong to the right user.