Part 8: 使用模塊的Alias別名來增強Jest的可配置度(完結(jié))

Enhance Jest configuration with Module Aliases

使用模塊的Alias別名來增強Jest的可配置度

Learn how to use Module Aliases Jest configuration to avoid using relative paths.
學(xué)習(xí)如何用模塊別名來配置Jest,這樣可以避免使用相對地址。

The module managers we have in the JavaScript community, mainly ES Modules and CommonJS, don’t support project-based paths. They only support relative paths for our own modules, and paths for the node_modules folder. When a project grows a bit, it’s common to see paths such:
在Js社區(qū)內(nèi)我們可以用的模塊管理工具俺孙,比如ES模塊化或者CommonJS搬俊,都不太支持基于項目目錄的路徑,而是僅支持我們自己模塊的相對路徑隙姿,以及node_modules文件夾梅垄。如果項目結(jié)構(gòu)越來越復(fù)雜,我們可能會看到如下長長的路徑:

import SomeComponent from '../../../../components/SomeComponent'

Luckily, we have different ways to cope with this, in a way that we can define aliases for folders relative to the project root, so we could the above line like:
還好,我們有各種方法來應(yīng)對這種情況队丝,一種方法就是我們設(shè)置某些相對于根目錄的文件夾的別名靡馁,就像上面的引用,就可以變?yōu)槿缦卤硎荆?/p>

import SomeComponent from '@/components/SomeComponent'

The @ here is an arbitrary character to define the root project, you can define your own. Let’s see what solutions we have to apply module aliasing. Let’s start from where we left it on the last article.
這里的@符號是定義項目根目錄的字符机久,你也可以定制自己想要的別名臭墨。來看一下我們?nèi)绾卧O(shè)置模塊別名,這就是我們最后一篇文章要講的膘盖。

Webpack aliases

Webpack別名

Webpack aliases are very simple to set up. You just need to add a resolve.alias property in your webpack configuration. If you take a look at the build/webpack.base.conf.js, it already has it defined:
Webpack的別名設(shè)置非常簡單胧弛。你只需要在配置文件中的resolve.alias里設(shè)置,文件路徑是build/webpack.base.conf.js侠畔。

{
  ...
  resolve: {
    extensions: ['.js', '.vue', '.json'],
    alias: {
      'vue$': 'vue/dist/vue.esm.js',
    }
  }
}

Taking this as an entry point, we can add a simple alias that points to the src folder and use that as the root:
以此為切入點结缚,我們可以添加一些簡單的別名,指向根目錄中的src文件夾:

{
  ...
  resolve: {
    extensions: ['.js', '.vue', '.json'],
    alias: {
      'vue$': 'vue/dist/vue.esm.js',
      '@': path.join(__dirname, '..', 'src')
    }
  }
}

Just with this, we can access anything taking the root project as the @ symbol. Let’s go to src/App.vue and change the reference to those two components:
這樣設(shè)置以后软棺,我們可以訪問到任何資源通過@標(biāo)識符红竭。我們試著用新方法引用資源:

  import MessageList from '@/components/MessageList'
  import Message from '@/components/Message'
  ...

And if we run npm start and open the browser at localhost:8080, that should work out of the box.
如果我們啟動npm的服務(wù),打開瀏覽器訪問localhost:8080喘落,可以發(fā)現(xiàn)之前的設(shè)置已經(jīng)生效了茵宪。

However, if we try to run the tests by running npm t, we’ll see Jest doesn’t find the modules. We still didn’t configured Jest to do so. So let’s go to package.json where the Jest config is, and add "@/([^\\.]*)$": "<rootDir>/src/$1" to moduleNameMapper:
但是,如果我們嘗試執(zhí)行測試用例瘦棋,運行npm t后眉厨,我們可以看到Jest報錯說沒有找到相關(guān)模塊。我們至今還沒搞清楚為什么Jest不支持這種配置兽狭。為了解決這個問題憾股,我們?nèi)?code>package.json中的Jest配置內(nèi)容里添加一段代碼:"@/([^\\.]*)$": "<rootDir>/src/$1" to moduleNameMapper:

    "jest": {
        "moduleNameMapper": {
          "@(.*)$": "<rootDir>/src/$1",
          "^vue$": "vue/dist/vue.common.js"
        }
    }
...

Let’s explain it:
讓我解釋下這段代碼的用處:

@(.*)$: Whatever starts with @, and continues with literally whatever ((.*)$) till the end of the string, grouping it by using the parenthesis
@(.*)$:無論什么路徑,只要以@開頭箕慧,并且后面以((.*)$)結(jié)尾服球,這里使用括號對其進行正則分組。

<rootDir>/src/$1: <rootDir> is a special word of Jest, meaning the root directory. Then we map it to the src, and with 1 we append the whatever clause from the `(.*)` statement. `/src/1:其中<rootDir>是Jest中的一個關(guān)鍵字颠焦,代表著根目錄斩熊。然后我們映射到src目錄,并且$1代表著與前文中(.*)`匹配的分組伐庭。

For example, @/components/MessageList will be mapped to ../src/components/MessageList when you’re importing it from the src or test folders.
例如粉渠,當(dāng)我們引入src或者test文件夾中的資源時,@/components/MessageList等價于../src/components/MessageList圾另。

That’s really it. Now you can even update your App.test.jsfile to use the alias as well, since it’s usable from within the tests:
用法就是這樣“灾辏現(xiàn)在我們可以用別名的方式更新App.test.js文件了:

import { shallow } from "vue-test-utils"
import App from "@/App"
...

And it will work for both .vue and .js files.
這種方式對vue和js格式的文件都有效。

Multiple aliases

多個別名

Very often, multiple aliases are used for convenience, so instead of using just a @ to define your root folder, you use many. For example, let’s say you have a actions and models folder. If you create an alias for each one, and then you move the folders around, you just need to change the aliases instead of updating all the references to it in the codebase. That’s the power of module aliases, they make your codebase more maintainable and cleaner.
通常我們不會只用@來索引資源集乔,我們可以設(shè)置多個別名來更方便的引入模塊去件。舉個例子,比如說你有一個actions和models的文件夾。如果你對他們分別設(shè)置別名尤溜,然后你挪動了文件夾倔叼,這時你只需要在配置文件中修改一次別名引用地址,就不用在代碼中修復(fù)海量的引用地址的指向了宫莱。這就是模塊別名的妙用丈攒。

Let’s add a components alias in build/webpack.base.conf.js:
讓我們在build/webpack.base.conf.js中添加components文件夾的別名。

{
  ...
  resolve: {
    extensions: ['.js', '.vue', '.json'],
    alias: {
      'vue$': 'vue/dist/vue.esm.js',
      '@': path.join(__dirname, '..', 'src')
      'components': path.join(__dirname, '..', 'src', 'components')
    }
  }
}

Then, we just need to add it as well to the Jest configuration in package.json:
然后我們只需要package.json中再次添加一些配置:

"jest": {
    "moduleNameMapper": {
      "@(.*)$": "<rootDir>/src/$1",
      "components(.*)$": "<rootDir>/src/components/$1",
      "^vue$": "vue/dist/vue.common.js"
    }
}
...

As simple as that. Now, we can try in App.vue to use both forms:
就這么簡單∈诎裕現(xiàn)在我們在App組件中試下這兩種方式:

import MessageList from 'components/MessageList'
import Message from '@/components/Message'

Stop and re-run the tests, and that should work, as well as if you run npm start and try it.
不要反復(fù)試了巡验,這兩個方法都能生效。

Other solutions

其他解決辦法

I’ve seen babel-plugin-webpack-alias, specially used for other testing frameworks such as mocha which doesn’t have a module mapper.
我已經(jīng)調(diào)研過babel-plugin-webpack-alias了绝葡,特別是用在其他測試框架中深碱,比如mocha等不支持模塊映射的框架。

I haven’t tried it myself, since Jest already gives you that, but if you have or wanna try, please share how it went!
我沒有親自試藏畅,因為Jest已經(jīng)提供這些功能了敷硅,但是如果你還是想親自嘗試一下,可以給大家分享一下愉阎!

Conclusion

總結(jié)

Adding module aliases is very simple and can keep your codebase much cleaner and easier to maintain. Jest makes it as well very easy to define them, you just need to keep in in sync with the Webpack aliases, and you can say bye-bye to the dot-hell references.
添加模塊別名非常簡單绞蹦,而且可以讓你的代碼簡潔高效。Jest讓我們很簡便地定義別名榜旦,你只需要讓Jest和Webpack同步別名的設(shè)置幽七,你就可以跟見鬼的'點點式'引用說拜拜了!

?著作權(quán)歸作者所有,轉(zhuǎn)載或內(nèi)容合作請聯(lián)系作者
  • 序言:七十年代末溅呢,一起剝皮案震驚了整個濱河市澡屡,隨后出現(xiàn)的幾起案子,更是在濱河造成了極大的恐慌咐旧,老刑警劉巖驶鹉,帶你破解...
    沈念sama閱讀 206,214評論 6 481
  • 序言:濱河連續(xù)發(fā)生了三起死亡事件,死亡現(xiàn)場離奇詭異铣墨,居然都是意外死亡室埋,警方通過查閱死者的電腦和手機,發(fā)現(xiàn)死者居然都...
    沈念sama閱讀 88,307評論 2 382
  • 文/潘曉璐 我一進店門伊约,熙熙樓的掌柜王于貴愁眉苦臉地迎上來姚淆,“玉大人,你說我怎么就攤上這事屡律‰绶辏” “怎么了?”我有些...
    開封第一講書人閱讀 152,543評論 0 341
  • 文/不壞的土叔 我叫張陵疹尾,是天一觀的道長上忍。 經(jīng)常有香客問我骤肛,道長纳本,這世上最難降的妖魔是什么窍蓝? 我笑而不...
    開封第一講書人閱讀 55,221評論 1 279
  • 正文 為了忘掉前任,我火速辦了婚禮繁成,結(jié)果婚禮上吓笙,老公的妹妹穿的比我還像新娘。我一直安慰自己巾腕,他們只是感情好面睛,可當(dāng)我...
    茶點故事閱讀 64,224評論 5 371
  • 文/花漫 我一把揭開白布。 她就那樣靜靜地躺著尊搬,像睡著了一般叁鉴。 火紅的嫁衣襯著肌膚如雪。 梳的紋絲不亂的頭發(fā)上佛寿,一...
    開封第一講書人閱讀 49,007評論 1 284
  • 那天幌墓,我揣著相機與錄音,去河邊找鬼冀泻。 笑死常侣,一個胖子當(dāng)著我的面吹牛,可吹牛的內(nèi)容都是我干的弹渔。 我是一名探鬼主播胳施,決...
    沈念sama閱讀 38,313評論 3 399
  • 文/蒼蘭香墨 我猛地睜開眼,長吁一口氣:“原來是場噩夢啊……” “哼肢专!你這毒婦竟也來了舞肆?” 一聲冷哼從身側(cè)響起,我...
    開封第一講書人閱讀 36,956評論 0 259
  • 序言:老撾萬榮一對情侶失蹤博杖,失蹤者是張志新(化名)和其女友劉穎椿胯,沒想到半個月后,有當(dāng)?shù)厝嗽跇淞掷锇l(fā)現(xiàn)了一具尸體欧募,經(jīng)...
    沈念sama閱讀 43,441評論 1 300
  • 正文 獨居荒郊野嶺守林人離奇死亡压状,尸身上長有42處帶血的膿包…… 初始之章·張勛 以下內(nèi)容為張勛視角 年9月15日...
    茶點故事閱讀 35,925評論 2 323
  • 正文 我和宋清朗相戀三年,在試婚紗的時候發(fā)現(xiàn)自己被綠了跟继。 大學(xué)時的朋友給我發(fā)了我未婚夫和他白月光在一起吃飯的照片种冬。...
    茶點故事閱讀 38,018評論 1 333
  • 序言:一個原本活蹦亂跳的男人離奇死亡,死狀恐怖舔糖,靈堂內(nèi)的尸體忽然破棺而出娱两,到底是詐尸還是另有隱情,我是刑警寧澤金吗,帶...
    沈念sama閱讀 33,685評論 4 322
  • 正文 年R本政府宣布十兢,位于F島的核電站,受9級特大地震影響旱物,放射性物質(zhì)發(fā)生泄漏遥缕。R本人自食惡果不足惜,卻給世界環(huán)境...
    茶點故事閱讀 39,234評論 3 307
  • 文/蒙蒙 一宵呛、第九天 我趴在偏房一處隱蔽的房頂上張望单匣。 院中可真熱鬧,春花似錦宝穗、人聲如沸户秤。這莊子的主人今日做“春日...
    開封第一講書人閱讀 30,240評論 0 19
  • 文/蒼蘭香墨 我抬頭看了看天上的太陽鸡号。三九已至,卻和暖如春须鼎,著一層夾襖步出監(jiān)牢的瞬間鲸伴,已是汗流浹背。 一陣腳步聲響...
    開封第一講書人閱讀 31,464評論 1 261
  • 我被黑心中介騙來泰國打工莉兰, 沒想到剛下飛機就差點兒被人妖公主榨干…… 1. 我叫王不留挑围,地道東北人。 一個月前我還...
    沈念sama閱讀 45,467評論 2 352
  • 正文 我出身青樓糖荒,卻偏偏與公主長得像杉辙,于是被迫代替她去往敵國和親。 傳聞我的和親對象是個殘疾皇子捶朵,可洞房花燭夜當(dāng)晚...
    茶點故事閱讀 42,762評論 2 345

推薦閱讀更多精彩內(nèi)容