PHP uses the lock to implement the Code grabbing function in the case of concurrency, and php concurrency
Requirement: CAPTCHA Evasion
Requirements:
1. Code snatching is enabled only in a specific period of time;
2. The number of opened codes in each time period is limited;
3. Duplicate codes are not allowed;
Implementation:
1. implemented without considering concurrency:
Function get_code ($ len) {$ CHAR_ARR = array ('1', '2', '3', '4', '5', '6', '7 ', '8', '9', 'A', 'B', 'C', 'D', 'E', 'F', 'G', 'h ', 'I', 'J', 'k', 'l', 'M', 'n', 'O', 'P', 'Q', 'x ', 'y', 'z', 'w', 's', 'R', 'T'); $ CHAR_ARR_LEN = count ($ CHAR_ARR)-1; $ code = ''; while (-- $ len> 0) {$ code. = $ CHAR_ARR [rand (0, $ CHAR_ARR_LEN)];} return $ code;} $ pdo = new PDO ('mysql: host = localhost; dbname = ci_test ', 'root', 'root'); // query the number of verification Codes issued at the current time $ code_num_rs = $ pdo-> query ("select count (*) as sum FROM code_test "); $ code_num_arr = $ code_num_rs-> fetch (PDO: FETCH_ASSOC); $ code_num = $ code_num_arr ['sum']; if ($ code_num <1) {<br> sleep (2); // pause for 2 seconds $ code = get_code (6); var_dump ($ pdo-> query ("insert into code_test (code, create_time) VALUES ('$ Code ',". time (). ")"));}
By default, the above code satisfies the current open time and the code is not repeated;
Process without considering concurrency:
1) Select the number of verification Codes issued by the current database;
2) if there are more places, a verification code will be generated, inserted into the database, and the verification code will be returned to the client;
3) If it is full, a prompt is returned, indicating that there are no more places;
2. Concurrency:
Let's take a look at the result of the above Code in the case of concurrency:
You can use apache benchmark to test the concurrency. apache benchmark is a performance evaluation tool of APACHE's http server. It enters the bin directory of apche through cmd and is called by the AB command, for example: AB-c concurrency-n total access url
Copy codeThe Code is as follows:
Cb-c 100-n 100 http: // localhost/php_mulit.php
In this way, 100 user colleagues will compete for one quota. During the query, each user will find another quota, and a verification code will be generated, inserted into the database, and a verification code will be returned; this leads to more verification codes. In fact, after running this command, the database has 13 more records instead of one.
How can this problem be avoided?
The exclusive lock can be applied to determine the insertion process. This ensures that only one process is running at any time. The implementation is as follows:
// Generate code function get_code ($ len) {$ CHAR_ARR = array ('1', '2', '3', '4', '5', '6 ', '7', '8', '9', 'A', 'B', 'C', 'D', 'E', 'F', 'G ', 'H', 'I', 'J', 'k', 'l', 'M', 'n', 'O', 'P', 'Q ', 'X', 'y', 'z', 'w', 's', 'R', 'T'); $ CHAR_ARR_LEN = count ($ CHAR_ARR)-1; $ code = ''; while (-- $ len> 0) {$ code. = $ CHAR_ARR [rand (0, $ CHAR_ARR_LEN)];} return $ code;} $ pdo = new PDO ('mysql: host = localhost; dbname = ci_test ', 'root', 'root'); $ fp = fopen('lock.txt ', 'R'); // if (flock ($ fp, LOCK_EX )) {// query the number of verification Codes issued at the current time $ code_num_rs = $ pdo-> query ("select count (*) as sum FROM code_test "); $ code_num_arr = $ code_num_rs-> fetch (PDO: FETCH_ASSOC); $ code_num = $ code_num_arr ['sum']; if ($ code_num <1) {sleep (2 ); $ code = get_code (6); var_dump ($ pdo-> query ("insert into code_test (code, create_time) VALUES ('$ Code ',". time (). ")");} flock ($ fp, LOCK_UN); fclose ($ fp );}
Use the flock function to lock the process.
For more flock information, refer to the php Manual: http://php.net/manual/zh/function.flock.php
Run again
Copy codeThe Code is as follows:
Cb-c 100-n 100 http: // localhost/php_mulit.php
The database only adds one record to ensure that the data is correct in the case of concurrency.
The above is a small Editor to introduce to you the PHP code grabbing function when implementing concurrency through locking. I hope it will be helpful to you. If you have any questions, please leave a message for me, the editor will reply to you in a timely manner. Thank you very much for your support for the help House website!