Php backend socket service long link, multi-concurrency development memo

Source: Internet
Author: User
Tags usleep
[Php] // ensure the maximum number of sub-processes if ($ this-& gt; _ maxFork & gt; 0 & amp; $ this-& gt; _ children & gt; $ this-& gt; _ maxFork) {Yii: log (& quot; _ children & gt; & quot ;. $ this-& gt; _ maxFork, CL


[Php]
// Ensure the maximum number of sub-processes
If ($ this-> _ maxFork> 0 & $ this-> _ children> $ this-> _ maxFork)
{
Yii: log ("_ children>". $ this-> _ maxFork, CLogger: LEVEL_WARNING ,__ METHOD __);
$ This-> handler (SIGCHLD );
Usleep (200 );
Continue;
}
 
 
/**
* Monitoring signal
* @ Param object socket $ clientt
* @ Return boolean
*/
Public function handler ($ signo ){

Yii: log ("handler {$ signo}", CLogger: LEVEL_INFO, _ METHOD __);

Switch (intval ($ signo )){
Case SIGCLD:
Case SIGCHLD:

Yii: log ("SIGCHLD sub proccess", CLogger: LEVEL_TRACE, _ METHOD __);
// Exit normally
// Declare = 1, that means one signal may be correspond multi-process die
While ($ pid = pcntl_wait ($ status, WNOHANG | WUNTRACED)> 0 ){
If (FALSE === pcntl_wifexited ($ status )){
Yii: log ("sub proccess {$ pid} exited unormally with code {$ status}", CLogger: LEVEL_WARNING, _ METHOD __);
} Else {
Yii: log ("sub proccess {$ pid} exited normally", CLogger: LEVEL_INFO, _ METHOD __);
}
$ This-> _ children --;
}
Break;
Case SIGINT:
Case SIGQUIT:
Case SIGHUP:
// Exit unexpectedly
$ This-> _ cleanup ();
Exit (0 );
Break;
Default:
Break;
}
}

// Ensure the maximum number of sub-processes
If ($ this-> _ maxFork> 0 & $ this-> _ children> $ this-> _ maxFork)
{
Yii: log ("_ children>". $ this-> _ maxFork, CLogger: LEVEL_WARNING ,__ METHOD __);
$ This-> handler (SIGCHLD );
// Usleep (200 );
Continue;
}


/**
* Monitoring signal
* @ Param object socket $ clientt
* @ Return boolean
*/
Public function handler ($ signo ){

Yii: log ("handler {$ signo}", CLogger: LEVEL_INFO, _ METHOD __);

Switch (intval ($ signo )){
Case SIGCLD:
Case SIGCHLD:

Yii: log ("SIGCHLD sub proccess", CLogger: LEVEL_TRACE, _ METHOD __);
// Exit normally
// Declare = 1, that means one signal may be correspond multi-process die
While ($ pid = pcntl_wait ($ status, WNOHANG | WUNTRACED)> 0 ){
If (FALSE === pcntl_wifexited ($ status )){
Yii: log ("sub proccess {$ pid} exited unormally with code {$ status}", CLogger: LEVEL_WARNING, _ METHOD __);
} Else {
Yii: log ("sub proccess {$ pid} exited normally", CLogger: LEVEL_INFO, _ METHOD __);
}
$ This-> _ children --;
}
Break;
Case SIGINT:
Case SIGQUIT:
Case SIGHUP:
// Exit unexpectedly
$ This-> _ cleanup ();
Exit (0 );
Break;
Default:
Break;
}
}

 

 

[Notes for multi-process mode]


Variable sharing
Because it is a process, it can be understood as a copy of the main process. The execution starts from the call of pcntl_fork () and then runs after the main and sub-processes, avoiding layer-by-layer nesting of sub-processes, generally, after a sub-process is executed, exit (0) is used to exit. If a sub-process crashes during execution, it does not affect the main process or share variables with the main process.


Signal and select conflict
After pcntl_signal registers the signal, it will conflict with stream_select.
PHP Error [2]: stream_select (): unable to select [4]: Interrupted System call (max_fd = 10)
No solution was found and pcntl_signal was not used for monitoring.

 


Process recycling
After the sub-process exits through exit, it will become a zombie process and needs to be recycled through pcntl_wait.
In the centos test, the maximum number of processes is 32 thousand. by setting the total number of sub-processes, the maximum number of sub-processes is greater than the set value, and then calling pcntl_wait for recycling.


Socket read/write considerations
In the case of multiple processes, the same socket handle may be read simultaneously by multiple processes.
The solution is to read all the data in the master process and then send it to the sub-process for execution.

 


File operation notes
The filesize function may fail to be obtained or the size of the obtained file remains unchanged in the case of multiple processes.
Here, the system functions in linux are called directly.


$ File_size = @ filesize ($ logFile );
// Solve the problem that the file size cannot be obtained under concurrent conditions.
If (0 = $ file_size | $ this-> _ prevFileSize = $ file_size)
{
$ File_size = @ exec ('/usr/bin/stat-c % S'. escapeshellarg ($ logFile ));
Clearstatcache ();
}

 


After stress testing, 1000 of the concurrency can reach 350 requests per second. It should also be optimized.

 

 

 

 

Contact Us

The content source of this page is from Internet, which doesn't represent Alibaba Cloud's opinion; products and services mentioned on that page don't have any relationship with Alibaba Cloud. If the content of the page makes you feel confusing, please write us an email, we will handle the problem within 5 days after receiving your email.

If you find any instances of plagiarism from the community, please send an email to: info-contact@alibabacloud.com and provide relevant evidence. A staff member will contact you within 5 working days.

A Free Trial That Lets You Build Big!

Start building with 50+ products and up to 12 months usage for Elastic Compute Service

  • Sales Support

    1 on 1 presale consultation

  • After-Sales Support

    24/7 Technical Support 6 Free Tickets per Quarter Faster Response

  • Alibaba Cloud offers highly flexible support services tailored to meet your exact needs.