乐趣区

关于php:学习PHP中的URL相关操作函数

在日常的业务开发过程中,咱们常常会有解决 URL 链接的需要,所以明天学习的函数其实都是大家常常会应用的一些函数。在之前的工作过程中,其实我对这些函数都只是有一个含糊的概念,晓得,然而真要用得时候还是要看下文档能力确定真正要应用的是哪一个函数。因而,明天咱们就当做是一次温习练习,次要是辨别和搞清楚每个函数真正的用途。

编码操作函数

首先来看就是 URL 编码相干的函数。有些浏览器在咱们复制粘贴一个网址后,就会主动地对网址进行 URL 编码,也就是有很多百分号那种模式的。在 PHP 中,天然也有对应的编解码函数。

$url = "https://www.zyblog.net?opt=dev&mail=zyblog@net.net&comments=aaa bbb ccc %dfg &==*() cdg&value=“中文也有呀,还有中文符号!!”";

echo $url, PHP_EOL;
// https://www.zyblog.net?opt=dev&mail=zyblog@net.net&comments=aaa bbb ccc %dfg &==*() cdg&value=“中文也有呀,还有中文符号!!”$enurl = urlencode($url);
echo $enurl, PHP_EOL;
// https%3A%2F%2Fwww.zyblog.net%3Fopt%3Ddev%26mail%3Dzyblog%40net.net%26comments%3Daaa+bbb+ccc+%25dfg+%26%3D%3D%2A%28%29+cdg%26value%3D%E2%80%9C%E4%B8%AD%E6%96%87%E4%B9%9F%E6%9C%89%E5%91%80%EF%BC%8C%E8%BF%98%E6%9C%89%E4%B8%AD%E6%96%87%E7%AC%A6%E5%8F%B7%EF%BC%81%EF%BC%81%E2%80%9D

echo urldecode($enurl), PHP_EOL;
// https://www.zyblog.net?opt=dev&mail=zyblog@net.net&comments=aaa bbb ccc %dfg &==*() cdg&value=“中文也有呀,还有中文符号!!”

这两个函数预计是大家应用最多的函数了。urlencode() 就是用于 URL 的编码操作,能够看到,咱们筹备好的链接曾经被编码成了蕴含各种百分号的内容。特地是对于中文字符来说,如果是 GET 形式这种在链接中的中文参数,编码之后的内容就会让链接变得十分长。urldecode() 则是绝对应的解码性能的函数,能够把编码过的链接解码回原始的状态。

$rawenurl = rawurlencode($enurl);
echo $rawenurl, PHP_EOL;
// https%253A%252F%252Fwww.zyblog.net%253Fopt%253Ddev%2526mail%253Dzyblog%2540net.net%2526comments%253Daaa%2Bbbb%2Bccc%2B%2525dfg%2B%2526%253D%253D%252A%2528%2529%2Bcdg%2526value%253D%25E2%2580%259C%25E4%25B8%25AD%25E6%2596%2587%25E4%25B9%259F%25E6%259C%2589%25E5%2591%2580%25EF%25BC%258C%25E8%25BF%2598%25E6%259C%2589%25E4%25B8%25AD%25E6%2596%2587%25E7%25AC%25A6%25E5%258F%25B7%25EF%25BC%2581%25EF%25BC%2581%25E2%2580%259D

echo rawurldecode($rawenurl), PHP_EOL;
// https%3A%2F%2Fwww.zyblog.net%3Fopt%3Ddev%26mail%3Dzyblog%40net.net%26comments%3Daaa+bbb+ccc+%25dfg+%26%3D%3D%2A%28%29+cdg%26value%3D%E2%80%9C%E4%B8%AD%E6%96%87%E4%B9%9F%E6%9C%89%E5%91%80%EF%BC%8C%E8%BF%98%E6%9C%89%E4%B8%AD%E6%96%87%E7%AC%A6%E5%8F%B7%EF%BC%81%EF%BC%81%E2%80%9D

echo rawurlencode($url), PHP_EOL;
// https%3A%2F%2Fwww.zyblog.net%3Fopt%3Ddev%26mail%3Dzyblog%40net.net%26comments%3Daaa%20bbb%20ccc%20%25dfg%20%26%3D%3D%2A%28%29%20cdg%26value%3D%E2%80%9C%E4%B8%AD%E6%96%87%E4%B9%9F%E6%9C%89%E5%91%80%EF%BC%8C%E8%BF%98%E6%9C%89%E4%B8%AD%E6%96%87%E7%AC%A6%E5%8F%B7%EF%BC%81%EF%BC%81%E2%80%9D

echo rawurldecode($enurl), PHP_EOL;
// https://www.zyblog.net?opt=dev&mail=zyblog@net.net&comments=aaa+bbb+ccc+%dfg+&==*()+cdg&value=“中文也有呀,还有中文符号!!”

紧接着咱们看到的是 rawurlencode() 和 rawurldecode()。很多小伙伴会搞不清楚它们和一般的 urlencode()、urldecode() 有什么区别。其实,它们的区别次要体现在一些非凡的字符上,比如说空格。在 urlencode() 中,空格被编码为 + 号,而在 urlrawencode() 中,空格是 %20。在咱们的第三段测试代码中就可以看进去。

前两段测试代码是针对后面曾经编码过的 \$enurl 进行的操作。第三段测试代码是对原始的 $url 进行的编码。这两个函数是实现了 RFC3986 标准的函数。而 urlencode() 则是因为历史起因而保留了一些相似于空格转换成 + 号这样的非凡状况。

最初咱们再看两个非常简单的 Base64 相干的编解码函数。

$base64url = base64_encode($enurl);
echo $base64url, PHP_EOL;
// aHR0cHMlM0ElMkYlMkZ3d3cuenlibG9nLm5ldCUzRm9wdCUzRGRldiUyNm1haWwlM0R6eWJsb2clNDBuZXQubmV0JTI2Y29tbWVudHMlM0RhYWErYmJiK2NjYyslMjVkZmcrJTI2JTNEJTNEJTJBJTI4JTI5K2NkZyUyNnZhbHVlJTNEJUUyJTgwJTlDJUU0JUI4JUFEJUU2JTk2JTg3JUU0JUI5JTlGJUU2JTlDJTg5JUU1JTkxJTgwJUVGJUJDJThDJUU4JUJGJTk4JUU2JTlDJTg5JUU0JUI4JUFEJUU2JTk2JTg3JUU3JUFDJUE2JUU1JThGJUI3JUVGJUJDJTgxJUVGJUJDJTgxJUUyJTgwJTlE

echo base64_decode($base64url), PHP_EOL;
// https%3A%2F%2Fwww.zyblog.net%3Fopt%3Ddev%26mail%3Dzyblog%40net.net%26comments%3Daaa+bbb+ccc+%25dfg+%26%3D%3D%2A%28%29+cdg%26value%3D%E2%80%9C%E4%B8%AD%E6%96%87%E4%B9%9F%E6%9C%89%E5%91%80%EF%BC%8C%E8%BF%98%E6%9C%89%E4%B8%AD%E6%96%87%E7%AC%A6%E5%8F%B7%EF%BC%81%EF%BC%81%E2%80%9D

其实 Base64 最大的用途不是体现在对这种一般的字符串的编码上,而是体现于 二进制 字符串在编码后传输的作用上。这个想必用过的同学天然心里有数。次要是对于接口开发来说,如果咱们应用 Base64 对数据进行编码,一是没有什么加密的成果,二是还有可能增大数据的长度,所以除非有非凡需要,否则一般传输中真的没有太大的必要来对数据进行 Base64 的编码。

URL 解析操作

除了对于 URL 链接中的字符进行编解码之外,解析链接参数也是咱们常常会应用的性能。比方:

$urls = parse_url($url);
var_dump($urls);
// array(3) {//     ["scheme"]=>
//     string(5) "https"
//     ["host"]=>
//     string(14) "www.zyblog.net"
//     ["query"]=>
//     string(119) "opt=dev&mail=zyblog@net.net&comments=aaa bbb ccc %dfg &==*() cdg&value=“中文也有呀,还有中文符号!!”"
//   }

通过 parse_url() 这个函数,咱们就能够将链接的各个局部拆解开来。

$parseTestUrl = 'http://username:password@hostname/path?arg=value#anchor';

print_r(parse_url($parseTestUrl));
// Array
// (//     [scheme] => http
//     [host] => hostname
//     [user] => username
//     [pass] => password
//     [path] => /path
//     [query] => arg=value
//     [fragment] => anchor
// )

下面这个测试链接更加地标准规范,咱们也能够看到 parse_url() 能够拆解出 协定、地址、用户名、明码、门路、查问语句、片断 这些内容,这些也是形成一个 URL 链接的标准规范。咱们也能够指定咱们须要的内容。

echo parse_url($parseTestUrl, PHP_URL_PATH); // /path

像这样增加第二个参数,就能够只获取咱们须要的局部内容。当然,对于整个 URL 链接来说,咱们最关怀的其实是 query 这部分的内容,能不能将它们再拆解进去呢?就像 $_GET 一样取得全副的查问数据后果。

$querys = [];
parse_str($urls['query'], $querys);
var_dump($querys);
// array(4) {//     ["opt"]=>
//     string(3) "dev"
//     ["mail"]=>
//     string(14) "zyblog@net.net"
//     ["comments"]=>
//     string(15) "aaa bbb ccc �g"
//     ["value"]=>
//     string(48) "“中文也有呀,还有中文符号!!”"
//   }

parse_str() 这个函数就是解析这种 URL 链接查问语句的函数。须要留神的是,这个函数的第二个参数是可选的,如果不应用一个变量来接管这个函数所解析进去的后果的话,那么所有解析的后果将间接转换成变量模式。说得可能有点晕,间接看看代码。

parse_str($urls['query']);
echo $value, PHP_EOL; //“中文也有呀,还有中文符号!!”

这下就看明确了吧。为了避免变量净化问题的呈现,最好还是有第二个参数来让解析的后果存储到咱们指定的中央。最初,咱们再看看如何将数组组合成一段 URL 查问语句。

echo http_build_query($querys), PHP_EOL;
// opt=dev&mail=zyblog%40net.net&comments=aaa+bbb+ccc+%DFg+&value=%E2%80%9C%E4%B8%AD%E6%96%87%E4%B9%9F%E6%9C%89%E5%91%80%EF%BC%8C%E8%BF%98%E6%9C%89%E4%B8%AD%E6%96%87%E7%AC%A6%E5%8F%B7%EF%BC%81%EF%BC%81%E2%80%9D

echo http_build_query($querys, null, '$||$', PHP_QUERY_RFC3986), PHP_EOL;
// opt=dev$||$mail=zyblog%40net.net$||$comments=aaa%20bbb%20ccc%20%DFg%20$||$value=%E2%80%9C%E4%B8%AD%E6%96%87%E4%B9%9F%E6%9C%89%E5%91%80%EF%BC%8C%E8%BF%98%E6%9C%89%E4%B8%AD%E6%96%87%E7%AC%A6%E5%8F%B7%EF%BC%81%EF%BC%81%E2%80%9D

http_build_query() 其实只有做过对接内部接口开发的同学都不会生疏。因为它太不便了。不过须要留神的是,这个函数自带地就会将数据进行 rawurlencode() 编码。另外,它还有几个可选参数的,比如说咱们第二段测试代码中批改了连贯符号,将本来的 & 符号替换成咱们自定义的符号来进行 URL 查问语句的拼接。

解析文件或近程地址的响应头及 meta 信息

对于近程文件的申请来说,响应头信息也是十分重要的内容。其实在 URL 相干的组件中也有间接获取响应头的函数。

$url = 'https://www.sina.com.cn';

print_r(get_headers($url));
// Array
// (//     [0] => HTTP/1.1 200 OK
//     [1] => Server: nginx
//     [2] => Date: Mon, 25 Jan 2021 02:08:35 GMT
//     [3] => Content-Type: text/html
//     [4] => Content-Length: 530418
//     [5] => Connection: close
//     [6] => Vary: Accept-Encoding
//     [7] => ETag: "600e278a-7c65e"V=5965C31
//     [8] => X-Powered-By: shci_v1.13
//     [9] => Expires: Mon, 25 Jan 2021 02:09:12 GMT
//     [10] => Cache-Control: max-age=60
//     [11] => X-Via-SSL: ssl.22.sinag1.qxg.lb.sinanode.com
//     [12] => Edge-Copy-Time: 1611540513080
//     [13] => Age: 24
//     [14] => Via: https/1.1 cmcc.guangzhou.union.82 (ApacheTrafficServer/6.2.1 [cRs f]), https/1.1 cmcc.jiangxi.union.175 (ApacheTrafficServer/6.2.1 [cRs f])
//     [15] => X-Via-Edge: 1611540515462770a166fee55a97524d289c7
//     [16] => X-Cache: HIT.175
//     [17] => X-Via-CDN: f=edge,s=cmcc.jiangxi.union.166.nb.sinaedge.com,c=111.22.10.119;f=edge,s=cmcc.jiangxi.union.168.nb.sinaedge.com,c=117.169.85.166;f=Edge,s=cmcc.jiangxi.union.175,c=117.169.85.168
// )

print_r(get_headers($url, 1));
// Array
// (//     [0] => HTTP/1.1 200 OK
//     [Server] => nginx
//     [Date] => Mon, 25 Jan 2021 02:08:35 GMT
//     [Content-Type] => text/html
//     [Content-Length] => 530418
//     [Connection] => close
//     [Vary] => Accept-Encoding
//     [ETag] => "600e278a-7c65e"V=5965C31
//     [X-Powered-By] => shci_v1.13
//     [Expires] => Mon, 25 Jan 2021 02:09:12 GMT
//     [Cache-Control] => max-age=60
//     [X-Via-SSL] => ssl.22.sinag1.qxg.lb.sinanode.com
//     [Edge-Copy-Time] => 1611540513080
//     [Age] => 24
//     [Via] => https/1.1 cmcc.guangzhou.union.82 (ApacheTrafficServer/6.2.1 [cRs f]), https/1.1 cmcc.jiangxi.union.175 (ApacheTrafficServer/6.2.1 [cRs f])
//     [X-Via-Edge] => 1611540515593770a166fee55a97568f1a9d6
//     [X-Cache] => HIT.175
//     [X-Via-CDN] => f=edge,s=cmcc.jiangxi.union.165.nb.sinaedge.com,c=111.22.10.119;f=edge,s=cmcc.jiangxi.union.175.nb.sinaedge.com,c=117.169.85.165;f=Edge,s=cmcc.jiangxi.union.175,c=117.169.85.175
// )

通过 get_headers() 函数就能够间接拿到指标地址服务器返回的响应头信息。它的第二个参数能够以键值下标的形式返回数据。除了响应头之外,咱们还能够拿到网站的所有 meta 标签里的内容。

var_dump(get_meta_tags($url));
// array(11) {//     ["keywords"]=>
//     string(65) "新浪, 新浪网,SINA,sina,sina.com.cn, 新浪首页, 门户, 资讯"
//     ["description"]=>
//     string(331) "新浪网为寰球用户 24 小时提供全面及时的中文资讯,内容笼罩国内外突发新闻事件、体坛赛事、娱乐时尚、产业资讯、实用信息等,设有新闻、体育、娱乐、财经、科技、房产、汽车等 30 多个内容频道,同时开设博客、视频、论坛等自在互动交换空间。"
//     ["referrer"]=>
//     string(6) "always"
//     ["stencil"]=>
//     string(10) "PGLS000022"
//     ["publishid"]=>
//     string(8) "30,131,1"
//     ["verify-v1"]=>
//     string(44) "6HtwmypggdgP1NLw7NOuQBI2TW8+CfkYCoyeB8IDbn8="
//     ["application-name"]=>
//     string(12) "新浪首页"
//     ["msapplication-tileimage"]=>
//     string(42) "//i1.sinaimg.cn/dy/deco/2013/0312/logo.png"
//     ["msapplication-tilecolor"]=>
//     string(7) "#ffbf27"
//     ["baidu_ssp_verify"]=>
//     string(32) "c0e9f36397049594fb9ac93a6316c65b"
//     ["sudameta"]=>
//     string(20) "dataid:wpcomos:96318"
//   }

这个函数不仅是对近程的链接网站有用,而且还能够间接查看一个本地的动态文件中的所有 meta 标签的内容,咱们只须要将参数的近程链接换成本地文件的门路就能够了,大家能够本人尝试一下。

总结

明天的内容还是比较简单的,次要这些函数大家在日常的工作中会常常用到。不过有些参数的应用状况可能许多敌人并不分明,比方 parse_str() 函数的第二个参数的问题。所以就像结尾说的,这篇文章就是个温习坚固,另外也起到加深了解的作用,深刻学习之后融汇贯通理论使用就能把握得更加手到擒来。

测试代码:

https://github.com/zhangyue0503/dev-blog/blob/master/php/2021/01/source/9. 学习 PHP 中的 URL 相干操作函数.php

参考文档:

https://www.php.net/manual/zh/book.url.php

退出移动版