2017-05-17 1 views
0

에 대한 경쟁 조건을 피하기 위해.구글 앱 엔진 (PHP) - 세마포어 또는 대안이 내가 <strong>인터넷 뱅킹</strong>을 개발 <strong>에 <strong>구글 앱 엔진</strong> 및 개발에 PHP</strong>를 실행하고 인터넷 뱅킹

인종은 큰 관심사입니다. 사용자가 $ 0.00 미만일 수는 없습니다 (걱정할 다른 문제가 있음을 알고 있지만 지금 당장이 문제에 집중하겠습니다).

의사 코드 :

<?php 

$user_id =   $_GET['user_id']; 
$withdraw_amount = $_GET['withdraw_amount']; 

if(getUserBalance($user_id) - $withdraw_amount >= 0){ 
    setUserBalance($user_id, getUserBalance($user_id) - $withdraw_amount); 
    sendMoneyToUser($user_id, $withdraw_amount); 
    echo 'Success'; 
} 
else{ 
    echo 'Insufficient funds'; 
} 

?> 

Google 클라우드 SQL 데이터베이스 :

USER_ID  BALANCE 
    1   10.00 
    2   20.00 

*는 위의 데이터베이스는 실제 데이터베이스의 매우 단순한 버전입니다. SQL 잠금 테이블/행은 실제 세계에서는 작동하지 않습니다. 그러나 PHP 대신 SQL을 사용하는 또 다른 솔루션이 있다면 그 사실을 알고 싶습니다.

경쟁 조건의 경우 :

GAE instance #1     GAE instance #2 (SAME TIME) 

user_id = '1'     user_id = '1' 
withdraw_amount = 10.00   withdraw_amount = 10.00 

balance = getUserBalance('1') balance = getUserBalance('1') 
//balance = 10.00    //balance = 10.00 

10.00 - 10.00 >= 0 -> (true) 10.00 - 10.00 >= 0 -> (true) 

setUserBalance ('1', 0.00)  setUserBalance ('1', 0.00) 
sendMoneyToUser('1', 10.00)  sendMoneyToUser('1', 10.00) 

User gets $10.00    User gets $10.00 

The user now has $20.00 in his hands, but he had just $10.00 in the bank!!! 

가 어떻게 경쟁 조건을 방지 할 수 있습니까?

는 기억 코드는 구글 앱 엔진에서 실행하고 나는 PHP 세마포어 확장에 액세스 할 수 없습니다.

답변

0

한 가지 방법은 문제없이 다른 컴퓨터에서 호출 할 수 있도록 redis을 백엔드로 사용하는 뮤텍스 라이브러리를 사용하는 것입니다.

작업을 시작하기 전에 사용자에게 특정한 잠금 장치를 가져와 작업 한 다음 잠금을 해제하십시오. 작업을 수행하는 동안 작업을 수행하기위한 연속 호출은 잠금을 획득 할 수 없기 때문에 실패합니다.

은 의사에서이 간단 할 것 같은 :

$lockName = "some string that contains the user/customer ID in it to be unique per customer"; 
if (! $mutex->acquireLock($lockName, 60)) { 
    throw new Exception ("An operation is already running, please wait for it to finish and try again!"); 
} 

// do the transaction data here, substract the amount, etc. 

// once done, release the lock: 
$mutex->releaseLock($lockName);