I'm POSTing the contents of a form field via AJAX to a PHP script and using Javascript encode(field_contents). The problem is that any plus signs are being stripped out and replaced by spaces. How can I safely 'encode' the plus sign and then appropriately 'decode' it on the PHP side?
Try
encodeURIComponent()
in JS and
html_entity_decode($_POST['field'],ENT_NOQUOTES,'UTF-8');
In PHP
The hexadecimal value you are looking for is %2B
To get it automatically in PHP run your string through urlencode($stringVal). And then run it rhough urldecode($stringVal) to get it back.
If you want the JavaScript to handle it, use escape( str )
Edit
After @bobince's comment I did more reading and he is correct.
Use encodeURIComponent(str) and decodeURIComponent(str). Escape will not convert the characters, only escape them with \'s
Use encodeURIComponent() in JS and in PHP you should receive the correct values.
Note: When you access $_GET, $_POST or $_REQUEST in PHP, you are retrieving values that have already been decoded.
Example:
In your JS:
// url encode your string
var string = encodeURIComponent('+'); // "%2B"
// send it to your server
window.location = 'http://example.com/?string='+string; // http://example.com/?string=%2B
On your server:
echo $_GET['string']; // "+"
It is only the raw HTTP request that contains the url encoded data.
For a GET request you can retrieve this from the URI. $_SERVER['REQUEST_URI'] or $_SERVER['QUERY_STRING']. For a urlencoded POST, file_get_contents('php://stdin')
NB:
decode() only works for single byte encoded characters. It will not work for the full UTF-8 range.
eg:
text = "\u0100"; // Ā
// incorrect
escape(text); // %u0100
// correct
encodeURIComponent(text); // "%C4%80"
Note: "%C4%80" is equivalent to: escape('\xc4\x80')
Which is the byte sequence (\xc4\x80) that represents Ā in UTF-8. So if you use encodeURIComponent() your server side must know that it is receiving UTF-8. Otherwise PHP will mangle the encoding. PHP5 supports UTF-8 natively, it is only PHP4 that is the real problem.
so what is best solution?
@Deniss Kozlovs answer doesn't work correctly!