Bagaimana cara mengkodekan URL dengan benar dalam PHP?

97

Saya membuat halaman pencarian, tempat Anda mengetik permintaan pencarian dan formulir dikirimkan search.php?query=your query. Fungsi PHP apa yang terbaik dan yang harus saya gunakan untuk encoding / decoding permintaan pencarian?

Klik Suka
sumber
2
Apakah Anda mengalami masalah? Browser dan PHP seharusnya sudah menangani ini secara otomatis (misalnya meletakkan foo bardi bidang teks, membuat foo+bardi URL).
Felix Kling
@Felix Saya akan memanggil skrip pencari menggunakanfile_get_contents
Klik Upvote

Jawaban:

183

Untuk kueri URI, gunakan urlencode/ urldecode; untuk hal lain, gunakan rawurlencode/ rawurldecode.

Perbedaan antara urlencodedan rawurlencodeapakah itu

Gumbo
sumber
application / x-www-form-urlencoded hanyalah varian khusus dari Percent-Encoding dan hanya diterapkan untuk menyandikan data formulir HTML.
Gumbo
1
@ Klik Suka: Mereka tidak dapat dibandingkan dengan cara itu. The application / x-www-form-urlencoded Format adalah yang Persen-Encoding Format kecuali bahwa ruang dikodekan dengan +bukan %20. Dan selain itu, application / x-www-form-urlencoded digunakan untuk menyandikan data formulir sedangkan Percent-Encoding memiliki penggunaan yang lebih umum.
Gumbo
12
rawurlencode () kompatibel dengan javascript decodeURI () fungsi
Clive Paterson
Apakah aturan ini selalu yang empiris? Maksud saya, ketika saya perlu menyandikan string kueri yang selalu saya gunakan urldecode. Lalu, bagaimana dengan jalur URI (misalnya /a/path with spaces/) dan fragmen URI (misalnya #fragment). Haruskah saya selalu menggunakan rawurldecodeuntuk keduanya?
tonix
Aturan praktis yang baik adalah untuk path (Like / my% 20folder /) go with rawurlencode; tetapi untuk bidang POST dan GET urlencode
gunakan
22

Urlencode () dan urldecode () dengan nama licik .

Namun, Anda tidak perlu menggunakan urldecode()variabel yang muncul di $_POSTdan $_GET.

Oliver Charlesworth
sumber
4
bisakah Anda menjelaskan mengapa urldecode () tidak boleh digunakan dengan $ _POST. karena saya sudah melakukan itu sejak lama tanpa masalah.
sid
apakah saya perlu menyandikan parameter dasar (misalnya "name=b&age=c&location=d") yang dikirim ke file PHP melalui AJAX?
oldboy
9

Inilah kasus penggunaan saya, yang membutuhkan jumlah encoding yang luar biasa. Mungkin Anda mengira itu dibuat-buat, tetapi kami menjalankan ini pada produksi. Secara kebetulan, ini mencakup setiap jenis pengkodean, jadi saya memposting sebagai tutorial.

Gunakan deskripsi kasus

Seseorang baru saja membeli kartu hadiah prabayar ("token") di situs web kami. Token memiliki URL yang sesuai untuk ditebus. Pelanggan ini ingin mengirim URL ke email orang lain. Halaman web kami menyertakan mailtotautan yang memungkinkan mereka melakukan itu.

Kode PHP

// The order system generates some opaque token
$token = 'w%a&!e#"^2(^@azW';

// Here is a URL to redeem that token
$redeemUrl = 'https://httpbin.org/get?token=' . urlencode($token);

// Actual contents we want for the email
$subject = 'I just bought this for you';
$body = 'Please enter your shipping details here: ' . $redeemUrl;

// A URI for the email as prescribed
$mailToUri = 'mailto:?subject=' . rawurlencode($subject) . '&body=' . rawurlencode($body);

// Print an HTML element with that mailto link
echo '<a href="' . htmlspecialchars($mailToUri) . '">Email your friend</a>';

Catatan: di atas mengasumsikan Anda mengeluarkan ke text/htmldokumen. Jika jenis media keluaran Anda text/jsonhanya digunakan $retval['url'] = $mailToUri;karena pengkodean keluaran ditangani oleh json_encode().

Kasus cobaan

  1. Jalankan kode di situs pengujian PHP ( apakah ada yang kanonik yang harus saya sebutkan di sini? )
  2. Klik link tersebut
  3. Kirim emailnya
  4. Dapatkan emailnya
  5. Klik tautan itu

Anda harus melihat:

"args": {
  "token": "w%a&!e#\"^2(^@azW"
}, 

Dan tentunya ini adalah representasi JSON di $tokenatas.

William Entriken
sumber
Secara setara, dan kurang semantik (karena mailto:bukan HTTP), Anda dapat menggunakan $mailToUri 'mailto:?' . http_build_query(['subject'=>$subject, 'body'=>$body], null, '&', PHP_QUERY_RFC3986);.
William Entriken
0

Anda dapat menggunakan Fungsi Pengkodean URL yang dimiliki PHP

rawurlencode() 

fungsi

ASP memiliki ekstensi

Server.URLEncode() 

fungsi

Di JavaScript, Anda dapat menggunakan

encodeURIComponent() 

fungsi.

Amranur Rahman
sumber
0

Berdasarkan jenis pengkodean standar RFC apa yang ingin Anda lakukan atau jika Anda perlu menyesuaikan pengkodean Anda, Anda mungkin ingin membuat kelas Anda sendiri.

/**
 * UrlEncoder make it easy to encode your URL
 */
class UrlEncoder{
    public const STANDARD_RFC1738 = 1;
    public const STANDARD_RFC3986 = 2;
    public const STANDARD_CUSTOM_RFC3986_ISH = 3;
    // add more here

    static function encode($string, $rfc){
        switch ($rfc) {
            case self::STANDARD_RFC1738:
                return  urlencode($string);
                break;
            case self::STANDARD_RFC3986:
                return rawurlencode($string);
                break;
            case self::STANDARD_CUSTOM_RFC3986_ISH:
                // Add your custom encoding
                $entities = ['%21', '%2A', '%27', '%28', '%29', '%3B', '%3A', '%40', '%26', '%3D', '%2B', '%24', '%2C', '%2F', '%3F', '%25', '%23', '%5B', '%5D'];
                $replacements = ['!', '*', "'", "(", ")", ";", ":", "@", "&", "=", "+", "$", ",", "/", "?", "%", "#", "[", "]"];
                return str_replace($entities, $replacements, urlencode($string));
                break;
            default:
                throw new Exception("Invalid RFC encoder - See class const for reference");
                break;
        }
    }
}

Gunakan contoh:

$dataString = "https://www.google.pl/search?q=PHP is **great**!&id=123&css=#kolo&[email protected])";

$dataStringUrlEncodedRFC1738 = UrlEncoder::encode($dataString, UrlEncoder::STANDARD_RFC1738);
$dataStringUrlEncodedRFC3986 = UrlEncoder::encode($dataString, UrlEncoder::STANDARD_RFC3986);
$dataStringUrlEncodedCutom = UrlEncoder::encode($dataString, UrlEncoder::STANDARD_CUSTOM_RFC3986_ISH);

Akan menghasilkan:

string(126) "https%3A%2F%2Fwww.google.pl%2Fsearch%3Fq%3DPHP+is+%2A%2Agreat%2A%2A%21%26id%3D123%26css%3D%23kolo%26email%3Dme%40liszka.com%29"
string(130) "https%3A%2F%2Fwww.google.pl%2Fsearch%3Fq%3DPHP%20is%20%2A%2Agreat%2A%2A%21%26id%3D123%26css%3D%23kolo%26email%3Dme%40liszka.com%29"
string(86)  "https://www.google.pl/search?q=PHP+is+**great**!&id=123&css=#kolo&[email protected])"

* Cari tahu lebih lanjut tentang standar RFC: https://datatracker.ietf.org/doc/rfc3986/ dan urlencode vs rawurlencode?

DevWL
sumber