Search code examples
phpandroidmysqlretrofit2

What is the difference between using {%2B) instead of (+) before a number?


I was working on an API base on a tutorial which it was getting token from user to recognize that user is admin or not.

So it's just a question about is this really matter to use:

+1xxx-xxxx-xxx

Or

%2B1xxx-xxxx-xxx

When I've tested my API it's returning null if I input wrong data in isServerToken, and if I use right one it's going to return right value, but if I use + instead of [%2B] it's going to get me this error:

<br />
<b>Notice</b>:  Undefined variable: token in <b>/h**e/m***/pu**tml/***/db_functions.php</b> on line <b>389</b><br />
null

I'll comment 389 line in below.

No matter if I use right or wrong input for isServerToken, it's going to say top error.

I'm asking this because I'm getting error from my android about

java.langillegalStateException: Expected BEGIN_OBJECT but was BEGIN_ARRAY at line 1 column 2 path $

so I'm considering every possibility about what is making this error happen. Here is the code for PHP API. In tutorial instructor used get_result, but I've changed it to bind_result because it won't work on my online host.

Here is the code:

// Instructer Code
public function getToken($phone,$isServerToken)
{
    $stmt = $this->conn->prepare("SELECT * FROM `token` WHERE phone=? AND isServerToken=?") or die ($this->conn->error);
    $stmt->bind_param("ss",$phone,$isServerToken);
    $result = $stmt->execute();
    $token = $stmt->get_result()->fetch_assoc();
    $stmt->close();
    return $token;
}

// What i've changed to Bind
public function getToken($phone,$isServerToken)
{
    $stmt = $this->conn->prepare("SELECT phone, token, isServerToken FROM `token` WHERE phone=? AND isServerToken=?") or die ($this->conn->error);
    $stmt->bind_param("ss",$phone,$isServerToken);
    $result = $stmt->execute();
    $stmt->bind_result($arr['phone'], $arr['token'], $arr['isServerToken']);
    while ($stmt->fetch())
    {
        $token[] = $arr;
    }
    $stmt->close();
    return $token; => This is where `Undefined variable: token in` happen.
}

And app calling from this part :

//Only instructor code, i didn't changed anything this part
if(isset($_POST['phone']) && isset($_POST['isServerToken']))
{
$userPhone = $_POST['phone'];
$isServerToken = $_POST['isServerToken'];

$token = $db->getToken($userPhone,$isServerToken);

echo json_encode($token);


}
else{
$response = "Required parameter (phone , isServerToken) is missing!";
echo json_encode($response);
}

I want to make sure when use register with +xxxx-xxxx-xxx number is this making my API say top error or not, because as I said it's working fine with %2Bxxxx-xxxx-xxx.

Also number is saving with + in database.

When I've line to this base on suggestions things got opposite now + work and 2%B will be null.

$token = $db->getToken(urlencode($userPhone),$isServerToken);

Solution

  • In your second function declaration of getToken, the variable $token will never be created, if the while construction isn't being looped (as you are declaring $token only inside the loop).

    So, possible outcome is that the variable $token just doesn't exists at the moment of returning $token (which is what you are experiencing). In other words, there aren't any results being looped in your case.

    Also: Plus-signs aren't a good match within JSON: https://stackoverflow.com/a/1374456/5682311

    Using php's urlencode function on the phonenumber (or any value) before parsing it to json_encode, sounds like the solution (which will transform the + sign into %2B)

    edit:

    public function getToken($phone,$isServerToken)
    {
        $stmt = $this->conn->prepare("SELECT phone, token, isServerToken FROM `token` WHERE phone=? AND isServerToken=?") or die ($this->conn->error);
        $stmt->bind_param("ss",$phone,$isServerToken);
        $result = $stmt->execute();
        $stmt->bind_result($arr['phone'], $arr['token'], $arr['isServerToken']);
    
        $token = array(); // <- added this line, to be sure variable $token always exists
        while ($stmt->fetch())
        {
            $token[] = array_map('urlencode', $arr ); // <- urlencode all values within $arr
        }
        $stmt->close();
        return $token; 
    }