Help with Phone Numbers
#1

I created a function, to buy an phone which gives you a random number.
And i created a check so that the player cannot have the same number as other players.
My problem now is as i realized: The Function doesn't check the Database.
so it means if someones offline, the other player who buys the phone, could get the same number as an offline player.

So my Question is: How can i check if the random value for the phone number is the same as in the database?
Reply
#2

If you have a separate table for phone numbers:
pawn Код:
INSERT IGNORE INTO ... (...) VALUES (...)
or in the same table use UPDATE query but set phone number column as UNIQUE KEY.
pawn Код:
UPDATE IGNORE SET ..
To either of the two, set a callback in mysql_tquery and then check affected rows: https://sampwiki.blast.hk/wiki/MySQL#cache_affected_rows
If it inserts a new record or updates a record, it will affect 1 row. If it is 0, a mobile already exists so return an error to the player.
Reply
#3

I don't get it.

I want to check all the numbers of all Players registered if they have a phone.
The numbers are stored in the user table
And i don't want to have it like i have it now that it only checks the number of online players
Reply
#4

IGNORE + checking affected rows basically does this: inserts a new row or updates a record if all is good but if an error occurs, it will hide the error (ignore) and affected rows will be 0. This way, you don't have to execute a SELECT query just to see if there is a match (same number phone) as UNIQUE KEY will return error if there will be duplicates.
Reply
#5

Sorry i'm a noob with mysql

here's my code:

Код:
CMD:call(playerid, params[])
{
	if(eingeloggt[playerid] == 0)return SendClientMessage(playerid, COLOR_RED, "Du bist noch nicht eingeloggt.");
	if(pInfo[playerid][handy] == 0)return SendClientMessage(playerid, COLOR_RED, "Du hast kein Handy.");
	if(GetPVarInt(playerid,"AusgehenderAnruf") == 1)return SendClientMessage(playerid, COLOR_RED, "Du rufst derzeit schon jemanden an.");
	if(GetPVarInt(playerid,"Anruf") == 1)return SendClientMessage(playerid, COLOR_RED, "Du bist schon in einem Gesprдch.");
	new Nummer;
	if(sscanf(params,"i",Nummer))return SendClientMessage(playerid, COLOR_RED, "INFO: /call [Nummer]");
	for(new i=0; i<MAX_PLAYERS; i++)
	{
		if(Nummer <= 9999)return SendClientMessage(playerid, COLOR_RED, "Ungьltige Nummer.");
		if(Nummer == GetPlayerNumber(playerid))return SendClientMessage(playerid, COLOR_RED, "Du kannst dich nicht selber anrufen.");
		if(Nummer == GetPlayerNumber(i))
		{
			if(GetPVarInt(i,"Anruf") == 1)return SendClientMessage(playerid, COLOR_RED, "Der Spieler ist schon in einem Anruf.");
			SetPVarInt(playerid,"AusgehenderAnruf",1);
			SetPVarInt(playerid,"CallerID",i);
			SetPVarInt(i,"CallerID",playerid);
			SetPVarInt(i,"EingehenderAnruf",1);
			SendFormatMessage(i,COLOR_YELLOW,"Eingehender Anruf von der Nummer: %i",pInfo[playerid][nummer]);
			SendClientMessage(i, COLOR_YELLOW,"Benutze /acceptcall um den Anruf anzunehmen.");
			SendClientMessage(playerid, COLOR_YELLOW, "Das Handy von der Nummer klingelt, bitte warten.");
			CallCheckTimer[playerid] = SetTimerEx("CallCheck",1000,true,"i",playerid);
			return 1;
		}
	}
	return 1;
}
Код:
stock GetPlayerNumber(playerid)
{
	if(pInfo[playerid][handy] == 0)return 0;
	return pInfo[playerid][nummer];
}
It only checks the online players, the number is stored in the player data.
And it checks it and if it is equal to an other number that has an online player, it try's another.
But doesn't check offline players.
Reply
#6

What others simply meant was, Fire this query,
Код:
 SELECT pPhoneNumber from `users` where pPhoneNumber = RandNumber //or what ever your variables are.
Then, inside the threaded function, check for number of rows affected.
Код:
 cache_affected_rows()
If the number is not zero, it means the number already exists within some other player. In that case, return 0 to the function and re call the random value generation to do all this again until you find a random number.


Tip: You can save all new numbers inside a .ini file or something. Only numbers. When a player buys a new phone, get the values from that file and if none of them matches the number, assign it to new buyer.
Reply
#7

Quote:
Originally Posted by GTLS
Посмотреть сообщение
What others simply meant was, Fire this query,
Код:
 SELECT pPhoneNumber from `users` where pPhoneNumber = RandNumber //or what ever your variables are.
Then, inside the threaded function, check for number of rows affected.
Код:
 cache_affected_rows()
If the number is not zero, it means the number already exists within some other player. In that case, return 0 to the function and re call the random value generation to do all this again until you find a random number.


Tip: You can save all new numbers inside a .ini file or something. Only numbers. When a player buys a new phone, get the values from that file and if none of them matches the number, assign it to new buyer.
No, I do not mean this. The whole purpose of affected rows is to avoid executing 2 queries (1 select to check if phone number exists and 1 update to set a new phone number). You execute only 1 UPDATE query and you know right away if the phone exists or updated the database without errors.

However, what I understood from ImTobi's first post if far from what he needs. So GTLS is right.
What if you try to call an offline player? What should happen?
Reply
#8

Quote:
Originally Posted by Calisthenics
Посмотреть сообщение
No, I do not mean this. The whole purpose of affected rows is to avoid executing 2 queries (1 select to check if phone number exists and 1 update to set a new phone number). You execute only 1 UPDATE query and you know right away if the phone exists or updated the database without errors.

However, what I understood from ImTobi's first post if far from what he needs. So GTLS is right.
What if you try to call an offline player? What should happen?
If the Player is offline it should send out an error, but i did it, that it continues, because idk how to check the number with my check that works but output an error.
Reply
#9

Quote:
Originally Posted by GTLS
Посмотреть сообщение
What others simply meant was, Fire this query,
Код:
 SELECT pPhoneNumber from `users` where pPhoneNumber = RandNumber //or what ever your variables are.
Then, inside the threaded function, check for number of rows affected.
Код:
 cache_affected_rows()
If the number is not zero, it means the number already exists within some other player. In that case, return 0 to the function and re call the random value generation to do all this again until you find a random number.


Tip: You can save all new numbers inside a .ini file or something. Only numbers. When a player buys a new phone, get the values from that file and if none of them matches the number, assign it to new buyer.
Can u give me an example?
Reply
#10

?Meep?
Reply
#11

Someone?
Reply
#12

bump
Reply
#13

if(cache_affected_rows() > 0)
{
<run again your number generate, and mysql query for checking>
}
Reply
#14

In your command, although you may need to adapt the following code to suit your gamemode's variables and database.
Код:
mysql_format(your_myql_handle, query, sizeof(query), "SELECT * FROM `your_table_name_here` WHERE `phoneNumbervariablename` = '%d'  LIMIT 1",  number);
mysql_pquery(your_mysql_handle, query, "OnCheckPhoneNumber", "i", playerid);
Then somewhere in your code, the "OnCheckPhoneNumber" or whatever name you'll change it to
Код:
forward OnCheckPhoneNumber(playerid);
public OnCheckPhoneNumber(playerid)
{
      new rows;
      cache_get_row_count(rows); // get the amount of rows from the query
      if(rows > 0) //if the amount of rows is greater than 0, so there is someone that has this same phone number, then 
      {
           // generate a new number phone
      }
      return 1;
}
Reply
#15

Calisthenics already gave you an answer - however, tell us the name of your "users" table and the column name that you use for phone numbers.

EDIT: Untested code - here's an example of how it could be done:

PHP код:
mysql_format(g_SQLquerysizeof query"UPDATE IGNORE "#TABLE_USERS" SET `PhoneNumber` = %i WHERE `UserID` = %i", phone_number, user_id);
mysql_pquery(g_SQLquery"OnPhoneNumberUpdate""ii"playeridphone_number);
forward OnPhoneNumberUpdate(playeridphone_number);
public 
OnPhoneNumberUpdate(playeridphone_number) {
    if (
cache_affected_rows() != -1) { // Since -1 refers to an error
        // Tell player there phone number was updated
        
pInfo[playerid][PhoneNumber] = phone_number;
        return 
1;
    }
    
    
// Tell player the phone number is already in use
    
return 1;

Reply
#16

@Logic_ IGNORE keyword prevents errors/warnings from occurring; therefore affected rows will be 0 and not -1.
Reply


Forum Jump:


Users browsing this thread: 1 Guest(s)