欧美bbbwbbbw肥妇,免费乱码人妻系列日韩,一级黄片

詳解如何發(fā)布TypeScript編寫的npm包

 更新時(shí)間:2022年12月01日 15:19:13   作者:strictmode.io  
這篇文章主要介紹了如何發(fā)布TypeScript編寫的npm包實(shí)現(xiàn)詳解,有需要的朋友可以借鑒參考下,希望能夠有所幫助,祝大家多多進(jìn)步,早日升職加薪

前言

在這篇文章中,我們將使用TypeScript和Jest從頭開始構(gòu)建和發(fā)布一個(gè)NPM包。

我們將初始化一個(gè)項(xiàng)目,設(shè)置TypeScript,用Jest編寫測試,并將其發(fā)布到NPM。

項(xiàng)目

我們的庫稱為digx。它允許從嵌套對象中根據(jù)路徑找出值,類似于lodash中的get函數(shù)。

比如說:

const source = { my: { nested: [1, 2, 3] } }
digx(source, "my.nested[1]") //=> 2

就本文而言,只要它是簡潔的和可測試的,它做什么并不那么重要。

npm包可以在這里找到。GitHub倉庫地址在這里。

初始化項(xiàng)目

讓我們從創(chuàng)建空目錄并初始化它開始。

mkdir digx
cd digx
npm init --yes

npm init --yes命令將為你創(chuàng)建package.json文件,并填充一些默認(rèn)值。

讓我們也在同一文件夾中設(shè)置一個(gè)git倉庫。

git init
echo "node_modules" >> .gitignore
echo "dist" >> .gitignore
git add .
git commit -m "initial"

構(gòu)建庫

這里會用到TypeScript,我們來安裝它。

npm i -D typescript

使用下面的配置創(chuàng)建tsconfig.json文件:

{
  "files": ["src/index.ts"],
  "compilerOptions": {
    "target": "es2015",
    "module": "es2015",
    "declaration": true,
    "outDir": "./dist",
    "noEmit": false,
    "strict": true,
    "noImplicitAny": true,
    "strictNullChecks": true,
    "strictFunctionTypes": true,
    "strictBindCallApply": true,
    "strictPropertyInitialization": true,
    "noImplicitThis": true,
    "alwaysStrict": true,
    "noUnusedLocals": true,
    "noUnusedParameters": true,
    "noImplicitReturns": true,
    "noFallthroughCasesInSwitch": true,
    "noUncheckedIndexedAccess": true,
    "noImplicitOverride": true,
    "noPropertyAccessFromIndexSignature": true,
    "esModuleInterop": true,
    "forceConsistentCasingInFileNames": true,
    "skipLibCheck": true
  }
}

最重要的設(shè)置是這些:

庫的主文件會位于src文件夾下,因此需要這么設(shè)置"files": ["src/index.ts"]

"target": "es2015" 確保我們的庫支持現(xiàn)代平臺,并且不會攜帶不必要的墊片。

"module": "es2015"。我們的模塊將是一個(gè)標(biāo)準(zhǔn)的ES模塊(默認(rèn)是CommonJS)。ES模式在現(xiàn)代瀏覽器下沒有任何問題;甚至Node從13版本開始就支持ES模式。

"declaration": true - 因?yàn)槲覀兿胍詣由?code>d.ts聲明文件。我們的TypeScript用戶將需要這些聲明文件。

其他大部分選項(xiàng)只是各種可選的TypeScript檢查,我更喜歡開啟這些檢查。

打開package.json,更新scripts的內(nèi)容:

"scripts": {
  "build": "tsc"
}

現(xiàn)在我們可以用npm run build來運(yùn)行構(gòu)建...這樣會失敗的,因?yàn)槲覀冞€沒有任何可以構(gòu)建的代碼。

我們從另一端開始。

添加測試

作為一名負(fù)責(zé)任的開發(fā),我們將從測試開始。我們將使用jest,因?yàn)樗唵吻液糜谩?/p>

npm i -D jest @types/jest ts-jest

ts-jest包是Jest理解TypeScript所需要的。另一個(gè)選擇是使用babel,這將需要更多的配置和額外的模塊。我們就保持簡潔,采用ts-jest。

使用如下命令初始化jest配置文件:

./node_modules/.bin/jest --init

一路狂按回車鍵就行,默認(rèn)值就很好。

這會使用一些默認(rèn)選項(xiàng)創(chuàng)建jest.config.js文件,并添加"test": "jest"腳本到package.json中。

打開jest.config.js,找到以preset開始的行,并更新為:

{
  // ...
  preset: "ts-jest",
  // ...
}

最后,創(chuàng)建src目錄,以及測試文件src/digx.test.ts,填入如下代碼:

import dg from "./index";
test("works with a shallow object", () => {
  expect(dg({ param: 1 }, "param")).toBe(1);
});
test("works with a shallow array", () => {
  expect(dg([1, 2, 3], "[2]")).toBe(3);
});
test("works with a shallow array when shouldThrow is true", () => {
  expect(dg([1, 2, 3], "[2]", true)).toBe(3);
});
test("works with a nested object", () => {
  const source = { param: [{}, { test: "A" }] };
  expect(dg(source, "param[1].test")).toBe("A");
});
test("returns undefined when source is null", () => {
  expect(dg(null, "param[1].test")).toBeUndefined();
});
test("returns undefined when path is wrong", () => {
  expect(dg({ param: [] }, "param[1].test")).toBeUndefined();
});
test("throws an exception when path is wrong and shouldThrow is true", () => {
  expect(() => dg({ param: [] }, "param[1].test", true)).toThrow();
});
test("works tranparently with Sets and Maps", () => {
  const source = new Map([
    ["param", new Set()],
    ["innerSet", new Set([new Map(), new Map([["innerKey", "value"]])])],
  ]);
  expect(dg(source, "innerSet[1].innerKey")).toBe("value");
});

這些單元測試讓我們對正在構(gòu)建的東西有一個(gè)直觀的了解。

我們的模塊導(dǎo)出一個(gè)單一函數(shù),digx。它接收任意對象,字符串參數(shù)path,以及可選參數(shù)shouldThrow,該參數(shù)使得提供的路徑在源對象的嵌套結(jié)構(gòu)中不被允許時(shí),拋出一個(gè)異常。

嵌套結(jié)構(gòu)可以是對象和數(shù)組,也可以是Map和Set。

使用npm t運(yùn)行測試,當(dāng)然,不出意外會失敗。

現(xiàn)在打開src/index.ts文件,并寫入下面內(nèi)容:

export default dig;
/**
 * A dig function that takes any object with a nested structure and a path,
 * and returns the value under that path or undefined when no value is found.
 *
 * @param {any}     source - A nested objects.
 * @param {string}  path - A path string, for example `my[1].test.field`
 * @param {boolean} [shouldThrow=false] - Optionally throw an exception when nothing found
 *
 */
function dig(source: any, path: string, shouldThrow: boolean = false) {
  if (source === null || source === undefined) {
    return undefined;
  }
  // split path: "param[3].test" => ["param", 3, "test"]
  const parts = splitPath(path);
  return parts.reduce((acc, el) => {
    if (acc === undefined) {
      if (shouldThrow) {
        throw new Error(`Could not dig the value using path: ${path}`);
      } else {
        return undefined;
      }
    }
    if (isNum(el)) {
      // array getter [3]
      const arrIndex = parseInt(el);
      if (acc instanceof Set) {
        return Array.from(acc)[arrIndex];
      } else {
        return acc[arrIndex];
      }
    } else {
      // object getter
      if (acc instanceof Map) {
        return acc.get(el);
      } else {
        return acc[el];
      }
    }
  }, source);
}
const ALL_DIGITS_REGEX = /^\d+$/;
function isNum(str: string) {
  return str.match(ALL_DIGITS_REGEX);
}
const PATH_SPLIT_REGEX = /\.|\]|\[/;
function splitPath(str: string) {
  return (
    str
      .split(PATH_SPLIT_REGEX)
      // remove empty strings
      .filter((x) => !!x)
  );
}

這個(gè)實(shí)現(xiàn)可以更好,但對我們來說重要的是,現(xiàn)在測試通過了。自己用npm t試試吧。

現(xiàn)在,如果運(yùn)行npm run build,可以看到dist目錄下會有兩個(gè)文件,index.jsindex.d.ts。

接下來就來發(fā)布吧。

發(fā)布

如果你還沒有在npm上注冊,就先注冊。

注冊成功后,通過你的終端用npm login登錄。

我們離發(fā)布我們的新包只有一步之遙。不過,還有幾件事情需要處理。

首先,確保我們的package.json中擁有正確的元數(shù)據(jù)。

  • 確保main屬性設(shè)置為打包的文件"main": "dist/index.js"。
  • 為TypeScript用戶添加"types": "dist/index.d.ts"。
  • 因?yàn)槲覀兊膸鞎鳛镋S Module被使用,因此需要指定"type": "module"
  • namedescription也應(yīng)填寫。

接著,我們應(yīng)該處理好我們希望發(fā)布的文件。我不覺得要發(fā)布任何配置文件,也不覺得要發(fā)布源文件和測試文件。

我們可以做的一件事是使用.npmignore,列出所有我們不想發(fā)布的文件。我更希望有一個(gè)"白名單",所以讓我們使用package.json中的files字段來指定我們想要包含的文件。

{
  // ...
  "files": ["dist", "LICENSE", "README.md", "package.json"],
  // ...
}

終于,我們已經(jīng)準(zhǔn)備好發(fā)包了。

運(yùn)行以下命令:

npm publish --dry-run

并確保只包括所需的文件。當(dāng)一切準(zhǔn)備就緒時(shí),就可以運(yùn)行:

npm publish

測試一下

讓我們創(chuàng)建一個(gè)全新的項(xiàng)目并安裝我們的模塊。

npm install --save digx

現(xiàn)在,讓我們寫一個(gè)簡單的程序來測試它。

import dg from "digx"
console.log(dg({ test: [1, 2, 3] }, "test[0]"))

結(jié)果非常棒!

然后運(yùn)行node index.js,你會看到屏幕上打印1。

總結(jié)

我們從頭開始創(chuàng)建并發(fā)布了一個(gè)簡單的npm包。

我們的庫提供了一個(gè)ESM模塊,TypeScript的類型,使用jest覆蓋測試用例。

你可能會認(rèn)為,這其實(shí)一點(diǎn)都不難,的確如此。

原文鏈接:www.strictmode.io/articles/bu…

以上就是詳解如何發(fā)布TypeScript編寫的npm包的詳細(xì)內(nèi)容,更多關(guān)于TypeScript npm包發(fā)布的資料請關(guān)注腳本之家其它相關(guān)文章!

相關(guān)文章

  • 微信小程序 下拉菜單的實(shí)現(xiàn)

    微信小程序 下拉菜單的實(shí)現(xiàn)

    這篇文章主要介紹了微信小程序 下拉菜單的實(shí)現(xiàn)的相關(guān)資料,需要的朋友可以參考下
    2017-04-04
  • 微信小程序中button組件的邊框設(shè)置的實(shí)例詳解

    微信小程序中button組件的邊框設(shè)置的實(shí)例詳解

    這篇文章主要介紹了微信小程序中button組件的邊框設(shè)置的實(shí)例詳解的相關(guān)資料,希望通過本文大家能夠掌握這部分內(nèi)容,需要的朋友可以參考下
    2017-09-09
  • 微信小程序 兩種為對象屬性賦值的方式詳解

    微信小程序 兩種為對象屬性賦值的方式詳解

    這篇文章主要介紹了微信小程序 兩種為對象屬性賦值的方式詳解的相關(guān)資料,需要的朋友可以參考下
    2017-02-02
  • 漂亮的仿flash菜單,來自藍(lán)色經(jīng)典

    漂亮的仿flash菜單,來自藍(lán)色經(jīng)典

    漂亮的仿flash菜單,來自藍(lán)色經(jīng)典...
    2006-06-06
  • 關(guān)于前端JavaScript ES6詳情

    關(guān)于前端JavaScript ES6詳情

    這篇文章主要介紹了關(guān)于前端JavaScript中的ES6,ES6是一個(gè)泛指,含義是 5.1 版以后的 JavaScript 的下一代標(biāo)準(zhǔn),涵蓋了 ES2015、ES2016、ES2017語法標(biāo)準(zhǔn),ES6新特性目前只有在一些較新版本瀏覽器得到支持,老版本瀏覽器里面運(yùn)行我們需要將ES6轉(zhuǎn)換為ES5
    2021-10-10
  • 前端項(xiàng)目中監(jiān)聽localStorage的變化

    前端項(xiàng)目中監(jiān)聽localStorage的變化

    這篇文章主要為大家介紹了前端項(xiàng)目中監(jiān)聽localStorage的變化的解決思路詳解,有需要的朋友可以借鑒參考下,希望能夠有所幫助,祝大家多多進(jìn)步,早日升職加薪
    2022-06-06
  • dotenv源碼解讀從.env文件中讀取環(huán)境變量

    dotenv源碼解讀從.env文件中讀取環(huán)境變量

    這篇文章主要為大家介紹了dotenv源碼解讀從.env文件中讀取環(huán)境變量示例詳解,有需要的朋友可以借鑒參考下,希望能夠有所幫助,祝大家多多進(jìn)步,早日升職加薪
    2022-12-12
  • 前端JavaScript大管家 package.json

    前端JavaScript大管家 package.json

    這篇文章主要介紹了前端JavaScript大管家 package.json,在每個(gè)前端項(xiàng)目中,都有package.json文件,它是項(xiàng)目的配置文件,常見的配置有配置項(xiàng)目啟動、打包命令,聲明依賴包等,下面我們就來學(xué)習(xí) package.json的詳細(xì)內(nèi)容,需要的朋友可以參考一下
    2021-10-10
  • JS遞歸遍歷查詢是否有權(quán)限示例詳解

    JS遞歸遍歷查詢是否有權(quán)限示例詳解

    這篇文章主要為大家介紹了JS遞歸遍歷查詢是否有權(quán)限示例詳解,有需要的朋友可以借鑒參考下,希望能夠有所幫助,祝大家多多進(jìn)步,早日升職加薪
    2022-07-07
  • 避免地獄async?await的使用及原理解析

    避免地獄async?await的使用及原理解析

    這篇文章主要為大家介紹了避免地獄async?await的使用場景及原理解析,有需要的朋友可以借鑒參考下,希望能夠有所幫助,祝大家多多進(jìn)步,早日升職加薪
    2022-07-07

最新評論