BooheeFE/weekly

2018/09/25 - 你应该知道的相对路径与绝对路径

Baifann opened this issue · 2 comments

前言

在最近做项目的时候,项目部署到线上之后,出现了一种明明开发环境就可以,为什么到了生成环境就不可以的问题。出现该问题的根本原因还是对路径的引用上出现了错误。

我们通常会引用本地文件资源包括

  • 图片
  • js文件
  • css文件
  • web页面
  • 等等

在引用文件时,普遍是2种,相对路径和绝对路径

相对路径和绝对路径

相对路径

w3cschools有这样一个表格来描述文件路径。

路径 说明
<img src="picture.jpg"> picture.jpg在与当前文件位于相同目录
<img src="images/picture.jpg"> picture.jpg在相同目录中的images文件夹内
<img src="/images/picture.jpg" picture.jpg在当前站点根目录下的images文件夹
<img src="../picture.jpg"> picture.jpg在上一级目录

在一些网站中会把相对路径分为2类

  • 文档相对路径
  • 根相对路径

文档相对路径

../xxx 当前文件的上一层目录
./xxx 当前文件所在目录

根相对路径

/xxx  当前文件所在的根目录

绝对地址

一些非本地的文件资源,一般都是使用绝对地址的,考虑到环境不同,有可能是通过拼接组成的(前一部分的服务器地址通过配置接口获取)

webpack

本地的资源如果使用../../在不同层级的文件之间引用会比较繁琐,因此可以使用webpack的alias进行设置。我们以Vue-cli的项目为例。

如果我们想引用的图片是在static文件夹中,我们可以在Vue-cli项目中的webpack.base.conf.js之中进行配置。

// ...相关代码省略
  resolve: {
    extensions: ['.js', '.vue', '.json'],
    alias: {
      'vue$': 'vue/dist/vue.esm.js',
      '@': resolve('src'),
      // 可以这样设置
      '@static': resolve('static')
    }
  }

我们假设还是之前的项目路径,只不过多了一个vue文件。

|___ index.html
|___ src
    |___components
        |___ component-a.vue
|___ static
    |___img
        |___ bg.png
    |___css
        |___ reset.css
    |___js
        |___ app.js

当我们在component-a.vue当中想引用bg.png直接使用@static/img/bg.png

补充

这里再补充一下,如果使用别名引用,VSCode查找是找不到引用的。

-w595

这里需要配置一下,在vetur插件说明当中有提到。
我们以@为例子,要让VSCode也认识这个路径,需要在项目根目录创建一个jsconfig.json

{
  "compilerOptions": {
    "baseUrl": ".",
    "paths": {
      "@/*": ["src/*"]
    }
  }
}

同时我们的引用不能写成import DCDialog from '@/components/discount-coupon-dialog';
要写成import DCDialog from '@/components/discount-coupon-dialog.vue';
-w708
这样就可以直接引用文件当中了。

import a from '@/components/a'     // 不能够打开对应文件
import a from '@/components/a.vue' // 能够正常打开对应引用文件

总结

尽量不要使用根相对地址来进行本地资源文件的引用,在公司的项目当中遇到一个这样的问题,本地环境地址为localhost:8080/#/app,线上环境项目地址为https://xxx.com/app/#/app,我所引用的图片资源地址为/static/img/xxx.png,这样,在开发环境是没有问题的,因为根路径就是项目路径,但是部署到线上之后,因为项目映射在了二级目录,导致/static/img/xxx.png最终引用的地址为https://xxx.com/static/img/xxx.png,而实际图片的地址应该为https://xxx.com/app/static/img/xxx.png,这就是使用根相对路径存在的问题,而如果使用文档相对路径就不会存在这个问题。同时如果是使用webpack来构建的项目,推荐使用alias来作为文件引用,来减少繁琐的引用,同时也能够避免出现打包后文件路径异常的问题。

接口路径

这里我们再提一下ajax的相对地址请求。
这里设定了几种不同情况下的请求。

请求路径 所在地址 最终结果
request('/api/app.json') http://xxx.com http://xxx.com/api/app.json
request('api/app.json') http://xxx.com http://xxx.com/api/app.json
request('/api/app.json') http://xxx.com/path http://xxx.com/api/app.json
request('api/app.json') http://xxx.com/path http://xxx.com/path/api/app.json
request('api/app.json') http://xxx.com/app/#/path http://xxx.com/app/api/app.json
  • /xxx/xxx请求的都是根路径下的地址接口
  • xxx/xxx请求的是当前路径下的地址接口

使用场景

相对地址请求,在前后端分离的项目当中比较少见,目前总结了2种场景。

  • 一种场景是如果服务端,和前端部署在同一服务下,我们都是使用根相对地址进行请求的。
  • 另一种场景是前端和服务端部署在不同服务下,前端有个配置文件接口,获取接口服务地址,以及其他资源地址,比如服务器地址等等,而这个配置文件接口(也许就是一个json文件),可以放置在前端服务当中,这个时候,就可以使用第二种方式的路径进行请求了。

相对协议

我们从一些网站引入一些资源文件时可以看到,是不带http或者https前缀的比如淘宝

-w769

如果这样做之后,获取资源会根据当前访问的URL的协议进行变更,当前访问的是https的实际则是https://g.alicdn.com/alilog/mlog/aplus_v2.js,如果是http的,那么就是http://g.alicdn.com/alilog/mlog/aplus_v2.js

参考

2019,穿越了?

@bi-kai 已更正,感谢提醒。