Rollup을 사용하여 어디서나 사용할 수 있는 JavaScript 라이브러리 작성

29018 단어
본고에서 우리의 목표는 라이브러리를 만들고 발표하는 것이다. 이 라이브러리는 클라이언트와 서버 쪽 응용 프로그램에서 사용할 수 있고 코드를 변경할 필요가 없다.
우리는 다음과 같은 용례를 만족시켜야 한다.
  • 이 라이브러리는 ES6+로 작성되었고 키워드 가져오기 및 내보내기
  • 를 사용합니다
  • 라이브러리는 <script> 레이블
  • 과 함께 사용 가능
  • 이 라이브러리는 현대 귀속기를 사용하는 웹 응용 프로그램에 사용할 수 있습니다.
  • 이 라이브러리는 노드 응용 프로그램에 사용할 수 있습니다.
  • 기술적으로 도서관은 다음과 같은 환경에서 일해야 한다는 뜻이다.
  • 사용<script> 레이블:
  • <html>
      <head>
        <script src="scripts/my-library.min.js"></script>
      </head>
      <body>
        <div id="app" />
        <script>
          myLibrary.helloWorld();
        </script>
      </body>
    </html>
    
  • RequireJS 사용:
  • define(["my-library"], function (myLibrary) {});
    // or
    define(function (require) {
      var myLibrary = require("my-library");
    });
    
  • 번들 프로그램(예: 웹팩)을 사용하는 웹 응용 프로그램에서 다음을 수행합니다.
  • import { helloWorld } from "my-library";
    helloWorld();
    
  • 노드 애플리케이션의 경우:
  • const myLibrary = require("my-library");
    myLibrary.helloWorld();
    // or
    const { helloWorld } = require("my-library");
    helloWorld();
    
    주의: bundler를 사용하는 웹 프로그램에서 전체 라이브러리를 가져오고 그 중의 단일 함수 ((import lib from 'library'; lib.sayHello(); 를 호출할 수 없습니다. 이것은 완전히 의도적인 것입니다.우리는 소비자들이 트리가 진동하면 작업을 완성할 수 있고 최종 응용 프로그램을 묶을 때 코드를 없애기를 바란다.현대 귀속기를 사용하는 응용 프로그램에서 소비 웹 응용 프로그램도 배치에 사용되는 귀속을 생성할 수 있음을 기억하십시오. 가능한 한 작게 하기를 바랍니다. 따라서 우리는 소비자들이 응용 프로그램에서 사용하지 않은 코드를 포함하지 않도록 할 것입니다.
    이 모든 것을 실현하기 위해서 우리는 총결산을 사용할 것이다.js.Rollup은 매우 빠르기 때문에(although not the fastest 최소한의 설정만 필요하고 편리한 플러그인 시스템을 통해 우리가 필요로 하는 모든 것을 지원할 수 있다.
    라이브러리를 작성한 후에는 Rollup을 사용하여 다음 세 가지 형식으로 코드를 내보냅니다.
  • UMD(공통 모듈 정의): 스크립트 태그와 RequireJS를 지원합니다.소비 응용 프로그램 자체가 코드를 전송하거나 묶을 수 없기 때문에, 우리는 광범위한 브라우저 지원을 얻기 위해 버전의 라이브러리를 제공해야 한다.
  • ESM(ES2015 모듈): 번들 업체가 저희 프로그램을 가져와 코드를 없애고 선택한 단계로 전송할 수 있도록 합니다.우리는 여전히 코드를 컴파일하고 있지만, 단지 소비자들의 편리한 형식으로 코드를 제공하고, 그들이 다음에 무엇을 해야 할지 결정하도록 할 뿐이다.키워드 가져오기 작업을 허용합니다.
  • CJS(CommonJS): 노드가 선택한 형식입니다.js.코드 크기가 중요하지 않기 때문에 트리를 떨 필요가 없습니다. 이 형식은 노드 프로그램에서 Require 키워드를 사용할 수 있습니다.
  • 이 형식의 모든 형식에 대해, 사용자가 필요할 때 라이브러리를 디버깅할 수 있도록 원본 맵을 제공할 것입니다.
    첫 번째 단계는 프로젝트를 만드는 것입니다.
    $ mkdir my-library
    $ cd my-library
    $ npm init -y
    
    다음에 우리는 의존항을 추가해야 한다.
    분명히 우리는 총결산이 필요하다.
    $ npm install rollup --save-dev
    
    UMD 형식의 코드를 전송해야 한다는 사실을 알고 babel을 설치했습니다.
    $ npm install @babel/core @babel/preset-env --save-dev
    
    babel과 축소 코드를 사용하기 위해 rollup이 필요하기 때문에 필요한 플러그인을 설치하여 babel과 terser를 사용하도록 합니다.
    $ npm install @rollup/plugin-babel rollup-plugin-terser --save-dev
    
    마지막으로, 우리는 라이브러리 in the style of node 에서 가져오기/내보내기 문법을 사용할 수 있기를 희망합니다. 이것은 import fn from './fn' 대신 import fn from './fn/index.js' 를 작성할 수 있도록 합니다. 물론, node modules 디렉터리의 모듈도 사용할 수 있습니다. (우리는 여기서 하지 않습니다.)
    $ npm install @rollup/plugin-node-resolve --save-dev
    
    라이브러리의 최종 종속성 목록은 다음과 같습니다.
    "dependencies": {},
    "devDependencies": {
      "@babel/core": "^7.11.6",
      "@babel/preset-env": "^7.11.5",
      "@rollup/plugin-babel": "^5.2.1",
      "@rollup/plugin-node-resolve": "^9.0.0",
      "rollup": "^2.28.2",
      "rollup-plugin-terser": "^7.0.2"
    },
    
    소스 코드 디렉토리, babel 프로필 및 요약 프로필이 필요합니다.
    $ mkdir src
    $ touch .babelrc.json
    $ touch rollup.config.js
    
    babel의 구성은 매우 간단할 것입니다. 우리는 babel에게 최신 버전의 JavaScript를 사용하고자 한다는 것을 알려주기만 하면 됩니다.
    {
      "presets": [["@babel/env", { "modules": false }]]
    }
    
    요약의 경우 필요한 플러그 인을 가져와야 합니다.
    import { nodeResolve } from "@rollup/plugin-node-resolve";
    import { terser } from "rollup-plugin-terser";
    import babel from "@rollup/plugin-babel";
    
    우리는 또 수입 포장을 할 것이다.json. 따라서 UMD 패키지를 내보낼 때name 필드를 사용할 수 있습니다.
    import pkg from "./package.json";
    
    우리rollup.config.js는 두 가지 일을 할 것이다.
    UMD의 경우 코드를 가져와 처리하고 Babel(Transfile)과terser(minify)를 통해 실행한 다음 UMD 파일로 내보냅니다.
    {
      // UMD
      input: "src/index.js",
      plugins: [
        nodeResolve(),
        babel({
          babelHelpers: "bundled",
        }),
        terser(),
      ],
      output: {
        file: `dist/${pkg.name}.min.js`,
        format: "umd",
        name: "myLibrary",
        esModule: false,
        exports: "named",
        sourcemap: true,
      },
    },
    
    CJS/ESM의 경우 코드를 가져와 처리하고 ESM 모듈 및 CJS 모듈로 내보냅니다.이런 상황에서 우리는 전송이나 축소가 필요 없다는 것을 명심해라.Node는 이를 필요로 하지 않으며, ESM의 경우 소비자들이 이렇게 합니다.
    {
      input: ["src/index.js"],
      plugins: [nodeResolve()],
      output: [
        {
          dir: "dist/esm",
          format: "esm",
          exports: "named",
          sourcemap: true,
        },
        {
          dir: "dist/cjs",
          format: "cjs",
          exports: "named",
          sourcemap: true,
        },
      ],
    },
    
    그러나, 모든 상황에서, 우리는 소스맵을 생성할 것이다.
    주의 exports: "named" 옵션은 모든 설정에 있습니다. a longer explanation in rollup’s documentation 본질적으로 이것은 롤러가 기본적으로 내보내는 것이 아니라 이름을 붙여서 내보내는 것을 사용합니다.긴 말은 하지 마라. 이것은 가능한 한 광범위한 호환성을 허용하고 나무의 진동을 일으킨다.만약 linter를 사용한다면, 기본 내보내기 대신 이름 내보내기를 지원하도록 설정하십시오. (이것은 프로그램에 적용되지 않으며, 라이브러리에만 적용되며, 기본 내보내기, 심지어 혼합 프로그램의 기본/이름 내보내기를 사용하면 충분히 가능합니다.)
    완전한 총결산 문건은 다음과 같다.이름은 소포에서 꺼냈기 때문이다.json, 입구점이 src/index라면 사실상 이 파일을 원래대로 사용할 수 있습니다.js, UMD 모듈의 출력에 해당하는 이름을 설정합니다.
    import { nodeResolve } from "@rollup/plugin-node-resolve";
    import { terser } from "rollup-plugin-terser";
    import babel from "@rollup/plugin-babel";
    import pkg from "./package.json";
    const input = ["src/index.js"];
    export default [
      {
        // UMD
        input,
        plugins: [
          nodeResolve(),
          babel({
            babelHelpers: "bundled",
          }),
          terser(),
        ],
        output: {
          file: `dist/${pkg.name}.min.js`,
          format: "umd",
          name: "myLibrary", // this is the name of the global object
          esModule: false,
          exports: "named",
          sourcemap: true,
        },
      },
      // ESM and CJS
      {
        input,
        plugins: [nodeResolve()],
        output: [
          {
            dir: "dist/esm",
            format: "esm",
            exports: "named",
            sourcemap: true,
          },
          {
            dir: "dist/cjs",
            format: "cjs",
            exports: "named",
            sourcemap: true,
          },
        ],
      },
    ];
    
    이제 의존항이 생겼습니다. 바벨과 롤러를 설정했으니 코드를 작성할 때가 되었습니다.
    우리는 이렇게 서류를 배치해야 한다.
    src
    ├── goodbye
    │   ├── goodbye.js
    │   └── index.js
    ├── hello
    │   ├── hello.js
    │   └── index.js
    └── index.js
    
    코드는 매우 간단합니다.
    // src/index.js
    export { default as hello } from "./hello";
    export { default as goodbye } from "./goodbye";
    
    // src/hello/index.js
    export { default } from "./hello";
    
    // src/hello/hello.js
    export default function hello() {
      console.log("hello");
    }
    
    // src/goodbye/index.js
    export { default } from "./goodbye";
    
    // src/goodbye/goodbye.js
    export default function goodbye() {
      console.log("goodbye");
    }
    
    다음에, 우리는 롤러에게 전화를 걸어 자신의 일을 잘 하도록 해야 한다.편의를 위해, 우리는 두 개의 npm 스크립트를 만들 것입니다. 하나는 라이브러리 구축에 사용되고, 다른 하나는 개발 작업에 사용되며, 매번 변경될 때마다 코드를 다시 컴파일합니다.
    “scripts”: {
     “build”: “rollup -c”,
     “dev”: “rollup -c -w”
    },
    
    마지막으로 NPMJ와 소비자가 사용할 수 있는 프로그램을 어떻게 내보냈는지 설명해야 합니다.
    가방에 세 개의 값을 정의할 것입니다.json:
    npm에 무엇을 포장할지 알려주는 파일 옵션(npm pack으로 테스트할 수 있음), CJS 모듈을 가리키는 메인 옵션, 모듈 옵션, 표준 옵션은 아니지만 ESM 모듈의 표준 옵션이 되었다.
    // package.json
    ...
    "main": "dist/cjs/index.js",
    "module": "dist/esm/index.js",
    ...
    files: [
      "dist"
    ]
    
    이렇게!
    라이브러리를 구축하려면 실행npm run build만 하면 개발 과정에서 사용할 수 있다npm run dev.npm pack 테스트를 사용하여 내보낼 수 있습니다.

    테스트 라이브러리
    스크립트 태그를 사용하여 HTML 파일을 만들고 브라우저에서 열기만 하면 됩니다.콘솔에서 인쇄된 단어 "Hello"를 볼 수 있습니다.
    <html>
      <head>
        <script src="dist/my-library.min.js"></script>
      </head>
      <body>
        <script>
          myLibrary.hello();
        </script>
      </body>
    </html>
    
    필요JS, 소규모 네트워크 응용 프로그램을 만들고 서버를 사용합니다.
    www
    ├── index.html
    └── scripts
    ├── app.js
    ├── my-library.min.js
    └── require.js
    
    index.html
    <html>
      <head>
        <script data-main="scripts/app.js" src="scripts/require.js"></script>
      </head>
      <body></body>
    </html>
    
    // app.js
    requirejs.config({
      baseUrl: "scripts",
    });
    requirejs(["my-library.min"], function (myLibrary) {
      myLibrary.hello();
    });
    
    "Hello"라는 단어가 콘솔에서 인쇄될 것입니다.모듈이 발표되면 파일my-library.min.jshttps://unpkg.com/에서 얻을 수 있습니다.
    라이브러리 디렉터리 이외의 노드에서 js 파일을 만들고 my library 디렉터리(dist 폴더가 아님!)를 가리키며 모듈을 요청합니다.
    const myLibrary = require("../my-library");
    myLibrary.hello(); // hello
    myLibrary.goodbye(); // goodbye
    
    만약 응용 프로그램을 더 디버깅한다면, 원본 코드 맵도 시작됩니다!
    React 애플리케이션과 같이 웹팩을 사용하는 웹 애플리케이션에서
    $ npx create-react-app my-library-cra
    $ cd my-library-cra
    
    가방의 의존항 부분에 있습니다.json, 다음 줄만 추가하면 됩니다.
    "my-library": "../my-library/"
    
    사선 설치 및 운행src/App.js에서는 hello 함수만 가져오고 호출합니다.
    import { hello } from "my-library";
    hello();
    
    yarn start React 프로그램을 실행하고 자바스크립트 컨트롤러를 열면 인쇄된 "Hello"를 볼 수 있습니다.
    이제 흔들림나무가 유효한지 확인하려면 yarn build을 실행하십시오.React 애플리케이션이 build 디렉토리에 번들로 묶여 배치됩니다.만약 파일에서 Hello 키워드를 검색한다면, js 파일에서 매우 길고 복잡한 이름이 있지만, 키워드 '안녕' 을 찾을 수 없습니다.이것은 웹 패키지가 필요한 코드만 도입했음을 나타낸다.라이브러리에서 이름 있는 내보내기를 사용했기 때문에 라이브러리 사용자는 쓰기 import myLibrary from 'my-library'; 를 할 수 없고, 패키지 전체를 잘못 가져올 수 있으며, 그 중 일부만 사용합니다.
    도움이 되었으면 좋겠습니다. 만약 당신이 평론에 어떤 문제가 있다면 저에게 알려 주십시오.

    좋은 웹페이지 즐겨찾기