Java - 请求地址最后面的 “/” 加和不加到底有什么区别?

URL 是我们每天畅游在互联网世界中最最常见的东西了,对于普通用户来说,URL 就是一个字符串,比如 http://www.justdojava.com ,但是对于我们开发者而言,除了 URL,还有一个东西叫做 URI,很多人经常搞不清楚这两个概念,本文我们就从这个话题开始。

从 URN 开始
在介绍这两个东西之前,我们还得先说说另外一个东西,叫做URN,URN的全程为Uniform Resource Name译作统一资源名称,URN、URL与URI的关系类似于下图:
在这里插入图片描述
由上图可以看到,URN 和 URL 实际上是 URI 范畴之内的概念。URN 表示给每一个互联网资源取一个名字,但是互联网资源千千万万,给每一个资源取一个不重复的名字显然不太现实,因此,并不是所有的互联网资源都有 URN ,URN 就类似于一个人的身份证号码,是唯一的,但是通过这个身份证号码找不到这个人,要找到这个人我们得通过类似于下面这种地址 “中国/广东省/广州市/天河区/马场路/南国花园/8栋/1203室” ,这种能够查找到某一个资源的字符串就是 URL ,URL 全称叫做 Uniform Resource Locator ,译作统一资源定位符,表示一个资源的地点。

URL 与 URI
URI 是 Uniform Resource Identifier 的缩写,译作统一资源标识符,RFC2396 中对这三个单词做了如下定义:

Uniform
规定统一的格式可方便处理多种不同类型的资源,而不用根据上下文环境来识别资源指定的访问方式。另外,加入新增的协议方案(如 http: 或 ftp:)也更容易。

Resource
资源的定义是“可标识的任何东西”。除了文档文件、图像或服务(例如当天的天气预报)等能够区别于其他类型的,全都可作为资源。另外,资源不仅可以是单一的,也可以是多数的集合体。

Identifier
表示可标识的对象。也称为标识符。

由此可见,URI 就是由某个协议方案表示的资源的定位标识符,而协议方案就是访问资源时所采用的协议类型的名称,比如我们采用 HTTP 协议时,协议方案就是 HTTP ,我们采用 FTP 协议时,协议方案就是 FTP ,另外还有 file、mailto、telnet 等。

按照 RFC3986 的说法,一个 URI 可以被进一步归类为一个定位器(URL),一个名字(URN),或两者都是。也就是说 URI 可以是 URL ,也可以是 URN 或两者兼备,如果你关心资源的名称,那就将 URI 定义成 URN 的形式,如果你关心资源的位置,那么就将 URI 定义成 URL 的形式,URI 中包括了 URN 和 URL 。在 RFC3986 文档中还有如下一句话:
“Future specifications and related documentation should use the general term “URI” rather than the more restrictive terms “URL” and “URN””

这句话告诉我们未来应该使用更加通用的 URI 术语,而不是受限制颇多的 URL 和 URN 。

前面介绍了 URI ,接下来我们再来探讨下 URI 的格式(基于前文得出的结论,下面涉及到的地址我将都以 URI 来称呼)。

URI 的格式
对于普通用户,说 URI 他们可能有点懵,但是说 http 开头的那个字符串肯定都知道是什么了,我们常见的网址除了 http: 开头之外,也有 ftp: 开头的,也有 mailto: 开头的,分别代表不同的含义,这是因为浏览器的功能不仅仅局限于访问 web 服务器,也可以用来访问 ftp 服务器,也可以用来浏览本地文件,也可以用来发送邮件,因此浏览器需要有一个东西来判断使用哪种功能来访问相应的数据,因此有了协议,也有了各种各样不同的 URI 。如下图是一个完整的URI:
在这里插入图片描述
这其中用户名、密码和端口号都可以省略,在浏览器拿到这样一个 URI 之后,首先会对其进行解析,比如上面这个地址,浏览器经过解析之后,知道要去获取 www.baidu.com 服务器上的 /folder/index.html 文件。不过,在实际应用中,有的时候 URI 并不是这么清晰,比如下面这个:
http://wwww.baidu.com

这种 URI 并没有直接指定要访问哪个文件,像这种没有路径的情况,就代表访问根目录下预先设置的默认文件,一般就是 /index.html,/default.html 一类的文件,在 Java 中,我们也可以在 web.xml 中来配置这个默认文件。

有的时候我们还有可能遇到下面这种地址:
http://www.baidu.com/folder/

这个 URI 以一个 / 结尾,表示 folder 是一个目录,我们要访问的是这个目录下的文件,但是又没有说明是这个目录下的哪个文件,此时依然是采用该目录下 index.html 或者 default.html 一类的文件。

有的时候,我们还可以看到下面这种 URI:
http://www.baidu.com/folder

即 folder 后面没有 /,此时会先将 folder 当作一个资源去访问(比如一个名为 folder 的 Servlet ),如果没有名为 folder 的资源,那么浏览器会自动在 folder 后面加上一个 / ,此时地址变为 http://www.baidu.com/folder/ ,folder 是一个目录,然后就会去尝试访问 folder 目录下的 index.html 或者 default.html。

注意这种自动调整只在浏览器中存在,如果你的项目是一个手机 App 或者你是一个 Ajax 请求,则不会有这种调整,即没写 / 就当做具体资源来对待,如果该资源不存在,就会报 404 ,写了/ 就当目录来对待。(OkHtpp3中是这样)

有的时候我们还可能见到下面这种URI:
http://www.baidu.com/

这个和我们介绍的第一种情况很类似,只是后面多了一个 / ,这个 / 表示我们要访问的是根目录,但是没有指定根目录下的文件,默认就是根目录下的 index.html 或者 default.html 。

OK,经过上面的介绍,小伙伴对 URI 最后面的 / 已经有了清晰的认识了吧?这个东西不可以随意省略,有 / 和没有 / ,访问结果有可能是天壤之别。

在这里插入图片描述

  • 1
    点赞
  • 2
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
钉钉 Java SDK 钉钉官方提供了统一的SDK,使用SDK可以便捷的调用服务端API。注意:此SDK包含原有TOP接口,原有TOP接口可以继续正常调用,没有影响。下面是使用SDK调用API的请求示例: JAVA: DingTalkClient client = new DefaultDingTalkClient("https://oapi.dingtalk.com/user/get"); OapiUserGetRequest req = new OapiUserGetRequest(); req.setUserid("userid1"); req.setHttpMethod("GET"); OapiUserGetResponse rsp = client.execute(req, accessToken); 请求示例说明: (1)定义Client对象,设置接口地址URI。一般地,无需拼接URL后面的参数,比如access_token;需要注意部分Post接口,需要在URI后拼接除access_token外的个别参数。 (2)构造Request对象,接口对应的request对象,一般规则是Oapi+接口Path驼峰形式+Request,如/user/get接口,请求对象是OapiUserGetRequest。 (3)调用Request的方法设置参数,注意参数HttpMethod,默认是POST,如果是GET类型接口,需要这样设置request.setHttpMethod("GET")。 (4)调用client.execute执行,其中access_token同样可以使用SDK获取到。同时,/gettoken,/sns/gettoken, /service/get_suite_token等获取token的接口在调用execute时,无需再传token参数。 (5)执行后得到Response对象,是与Request对应的,然后可获取执行结果。 环境依赖 (1)JAVA SDK 需要依赖 Java SE/EE 1.5及以上。 (2).NET SDK 需要依赖 .NET Framework 2.0及以上 (不支持Windows Phone平台)。 (3)Python SDK需要依赖python2
ava实现的毕业设计&&课程设计(包含运行文档+数据库+前后端代码),可运行高分资源 Java实现的毕业设计&&课程设计(包含运行文档+数据库+前后端代码),Java实现的毕业设计&&课程设计(包含运行文档+数据库+前后端代码),Java实现的毕业设计&&课程设计(包含运行文档+数据库+前后端代码),Java实现的毕业设计&&课程设计(包含运行文档+数据库+前后端代码),Java实现的毕业设计&&课程设计(包含运行文档+数据库+前后端代码),Java实现的毕业设计&&课程设计(包含运行文档+数据库+前后端代码),Java实现的毕业设计&&课程设计(包含运行文档+数据库+前后端代码),Java实现的毕业设计&&课程设计(包含运行文档+数据库+前后端代码),Java实现的毕业设计&&课程设计(包含运行文档+数据库+前后端代码),Java实现的毕业设计&&课程设计(包含运行文档+数据库+前后端代码),Java实现的毕业设计&&课程设计(包含运行文档+数据库+前后端代码),Java实现的毕业设计&&课程设计(包含运行文档+数据库+前后端代码),Java实现的毕业设计&&课程设计(包含运行文档+数据库+前后端代码),Java实现的毕业设计&&课程设计(包含运行文档+数据库+前后端代码),Java实现的毕业设计&&课程设计(包含运行文档+数据库+前后端代码),Java实现的毕业设计&&课程设计(包含运行文档+数据库+前后端代码),Java实现的毕业设计&&课程设计(包含运行文档+数据库+前后端代码),Java实现的毕业设计&&课程设计(包含运行文档+数据库+前后端代码),Java实现的毕业设计&&课程设计(包含运行文档+数据库+前后端代码),Java实现的毕业设计&&课程设计(包含运行文档+数据库+前后端代码),Java实现的毕业设计&&课程设计(包含运行文档+数据库+前后端代码),Java实现的毕业设计&&课程设计(包含运行文档+数据库+前后端代码),Java实现的毕业设计&&课程设计(包含运行文档+数据库+前后端代码),Java实现的毕业设计&&课程设计(包含运行文档+数据库+前后端代码),Java实现的毕业设计&&课程设计(包含运行文档+数据库+前后端代码),Java实现的毕业设计&&课程设计(包含运行文档+数据库+前后端代码),Java实现的毕业设计&&课程设计(包含运行文档+数据库+前后端代码),Java实现的毕业设计&&课程设计(包含运行文档+数据库+前后端代码),Java实现的毕业设计&&课程设计(包含运行文档+数据库+前后端代码),Java实现的毕业设计&&课程设计(包含运行文档+数据库+前后端代码),Java实现的毕业设计&&课程设计(包含运行文档+数据库+前后端代码),Java实现的毕业设计&&课程设计(包含运行文档+数据库+前后端代码),Java实现的毕业设计&&课程设计(包含运行文档+数据库+前后端代码),Java实现的毕业设计&&课程设计(包含运行文档+数据库+前后端代码),Java实现的毕业设计&&课程设计(包含运行文档+数据库+前后端代码),Java实现的毕业设计&&课程设计(包含运行文档+数据库+前后端代码),Java实现的毕业设计&&课程设计(包含运行文档+数据库+前后端代码),Java实现的毕业设计&&课程设计(包含运行文档+数据库+前后端代码),Java实现的毕业设计&&课程设计(包含运行文档+数据库+前后端代码),Java实现的毕业设计&&课程设计(包含运行文档+数据库+前后端代码),Java实现的毕业设计&&课程设计(包含运行文档+数据库+前后端代码),Java实现的毕业设计&&课程设计(包含运行文档+数据库+前后端代码),Java实现的毕业设计&&课程设计(包含运行文档+数据库+前后端代码),Java实现的毕业设计&&课程设计(包含运行文档+数据库+前后端代码),Java实现的毕业设计&&课程设计(包含运行文档+数据库+前后端代码),Java实现的毕业设计&&课程设计(包含运行文档+数据库+前后端代码),Java实现的毕业设计&&课程设计(包含运行文档+数据库+前后端代码),Java实现的毕业设计&&课程设计(包含运行文档+数据库+前后端代码),Java实现的毕业设计&&课程设计(包含运行文档+数据库+前后端代码),Java实现的毕业设计&&课程设计(包含运行文档+数据库+前后端代码),Java实现的毕业设计&&课程设计(包含运行文档+数据库+前后端代码),Java实现的毕业设计&&课程设计(包含运行文档+数据库+前后端代码),Java实现的毕业设计&&课程设计(包含运行文档+数据库+前后端代码),Java实现的毕业设计&&课程设计(包含运行文档+数据库+前后端代码),Java实现

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值