Can't have several threads per session

2019-02-25 06:52发布

问题:

I am buidling some webapp and have implemented long-polling (and a command queue in my db) so my server can send commands to my cleint asynchronously, etc. The commands are encoded into json and sent over ajax calls for the client to server, and via long-polling for the server to client way.

Everything was working just fine, until I included my "Authentication module" in the ajax.php file. This module wraps the session stuff and calls session_start().

The problem is that, my long polling routine can wait up to 21 seconds before comming back to the client. During this time, the server won't run anything from the same session. It's instead executed right after the long polling ajax call returned.

I understand there's probably a restriction of only 1 thread per session at a time, and that the requests are queued up.

Now here's the question : What is the best way to address this? Is there a setting to allow several threads per sessions (3 would be fine, in my case). Or should I just send tell the client what is his SessionID (i have some sessions table in my db, to track which user is connected to which session(s)). The client could then send it along with any ajax calls so authentication module could be bypassed.

On the later option, iam afraid it open's up a bunch of security problems because of eventual session spoofing. I would need to send a "random string" to each session, to make sure you can't spoof too easily, but even then, it's not perfect...

Thanks for your awnsers :)

Nicolas Gauthier

回答1:

It's a well known issue/fact that PHP locks session files for the duration of their usage in order to prevent race conditions.

If you take a look at the PHP source code, (ext/session/mod_files.c) you can see that the ps_files_open function locks the session file, and ps_files_close unlocks it.

If you call session_start() right at the beginning of your long-running script, and do not explicitly close the session file, it will be locked until the script terminates, where PHP will release all file locks during script shutdown.

While you are not using the session, you should call session_write_close to flush the session data to disk, and release the lock so that your other "threads" can read the data.

I'm sure you can imagine what would happen if the file was not locked.

T1: Open Session
T2: Open Session
...
T2: Write Data
T1: Write Data

The data written by thread 2 will be completely overwritten by thread 1, and at the same time, any data that thread 1 wanted to write out, was not available to thread 2.