2019-03-26
本文的原作者是 Colby Miller,文章源链接为 How to publish a React Native component to NPM — it’s easier than you think,我将其翻译成中文。
你想向开源社区做贡献吗?那很赞!帮助想当年轻的 React Native 社区成长是一件很棒的事情!
当我在不久前打算进行这项任务的时候,我发现没有太多讲怎么把 React Native 组件发布到 NPM 上的材料。因此我希望这篇文章能帮助别人让这个过程变得容易一些。
在我们开始之前,首先要注册一个 NPM 账号。你可以在这里注册。
首先,创建一个目录,React Native 组件将会位于这个目录中。
mkdir <folder_name> && cd <folder_name>
# For example
mkdir my-component && cd my-component
进入创建的目录后,我们需要通过 npm init
命令来初始化 NPM 包。
这会创建一个 package.json
文件,它内部有一些重要的关于 React Native 组件的元信息。
命令会询问一系列问题,包括包名、版本、描述、关键字等等。
重要:当被询问入口点(entry point)的时候,一定要输入 index.js
并回车。这会是导出你的主组件的文件。
package.json:
{ "name": "react-native-progress-steps", "version": "1.0.0", "description": "A simple and fully customizable React Native component that implements a progress stepper UI.", "main": "index.js", "scripts": { "test": "echo \"Error: no test specified\" && exit 1" }, "repository": { "type": "git", "url": "git+https://github.com/colbymillerdev/react-native-progress-steps.git" }, "keywords": [ "react-native", "react-component", "react-native-component", "react", "react native", "mobile", "ios", "android", "ui", "stepper", "progress", "progress-steps" ], "author": "Colby Miller", "license": "MIT", "bugs": { "url": "https://github.com/colbymillerdev/react-native-progress-steps/issues" }, "homepage": "https://github.com/colbymillerdev/react-native-progress-steps#readme" }
下一步是为你的 React Native 组件设置一个目录结构。
这完全取决于你,下面我分享一下我的简单示例:
你会注意到有些文件不是我们创建的。我们后面会解释他们。
首先我们创建 index.js
文件,这个文件最为重要,它的作用是导出/导入你的组件。
将当且目录切到项目根目录,并执行命令 touch index.js
。
这个文件的内容有多种编写方法:
index.js
中编写组件,并将它导出index.js
中导出index.js
中导出必要的。在下面的示例中,我采用这个方法:index.js:
import ProgressSteps from './src/ProgressSteps/ProgressSteps'; import ProgressStep from './src/ProgressSteps/ProgressStep'; export { ProgressSteps, ProgressStep };
不论采用哪种方法,这个文件最终导出的,是使用这个 APP 的库最终导入并展示的。这个很重要需要记住。
import { ProgressSteps, ProgressStep } from 'react-native-progress-steps';
为了让我们的 React Native 组件正常工作,我们需要决定使用那些依赖。
依赖分为三种类型:
react-native
本身。但是,在 React Native 的场景下,不需要把 react-native
作为一个 peer dependency。lodash
和 prop-types
。我们的下一步是将我们的组件与 Babel 建立关联。我们可以简单地通过安装下面的 dev dependency 完成这一步:
npm install metro-react-native-babel-preset --save-dev
安装完成后,我们要创建一个 .babelrc
并添加如下内容:
{ "presets": ["module:metro-react-native-babel-preset"] }
最后一步是创建标准的 .gitignore
和 .npmignore
,遵循最佳实践。这会避免在发布到 NPM 时遇到问题。
.gitignore:
# Logs
*.log
npm-debug.log
# Runtime data
tmp
build
dist
# Dependency directory
node_modules
.npmignore:
# Logs
*.log
npm-debug.log
# Dependency directory
node_modules
# Runtime data
tmp
# Examples (If applicable to your project)
examples
通常,在发布到 NPM 之前,我们可以直接将我们的包本地连接到 APP 上。
这可以在包的根目录下使用 npm link
命令完成。之后,跳转到 APP 目录下,再输入 npm link <package-name>
之后再输入 npm install
完成连接。
但是,在截止写本文的时间为止,React Native 和 npm link
命令还没发很好地一起工作。
到目前为止,我找到了两个解决这个问题的方法:
要完成这个,进入 APP 目录并使用路径直接安装包:
npm i <path_to_project>
# For example
npm i ../my-component
当包代码改动之后,需要重新进入 APP 的目录重新安装依赖。
这个方法不太理想,但是它可以工作。
npm pack
命令是一种将你的 React Native 组件打包的好方法,并且是能够测试的。
它会创建一个一个 .tgz 文件,之后被安装到一个线程的 APP 中。
首先在包的根目录创建一个 /examples
目录,这个目录是一个 React Native 应用,主要目的是展示你的示例。
这个目录可以通过 react-native init examples
命令创建。
完成之后,执行 npm pack
命令,会创建一个文件,文件名类似于 package-name-0.0.0.tgz
。
之后进入 /examples
目录,安装你的组件,通过执行 npm i ../package-name-0.0.0.tgz
或者 yarn add ../package-name-0.0.0.tgz
。记住分别替换 package-name
和 0.0.0
。
创建一个 JavaScript 文件来展示你的组件。在本例中,我们称其为 ExampleOne.js
。需要指出的是,应该在这个文件中导入前面用 yarn 或 npm 安装的组件。
一但文件被创建,打开 App.js
并导入/导出示例文件。
这个文件中导出的内容是在模拟器或设备上运行项目时显示的内容。
App.js:
import ExampleOne from './ExampleOne' export default ExampleOne;
最后,我们可以使用 react-native run-ios
或 react-native run-android
运行应用。
现在我们应该能够看到我们的组件并正确地测试它。
在你修改了 NPM 包之后,记住需要执行 npm pack
指令,之后进入 /examples
目录执行 npm install
或 yarn add
。
最后,我们已经准备好把我们的 React Native 组件分享到超赞的开源社区了!
发布非常简单快速。只需要使用 npm login
登录 NPM 账号,之后使用 npm publish
进行发布。
有一点需要注意的是 NPM 要求我们每次发布前递增版本号。
在本文中我们总结了大量材料。如果你遇到问题请再下面评论提问。
感谢阅读,我期待你的创造!
react-native-progress-steps 也欢迎贡献,PR 建议都欢迎提出!
在读完后,我对 examples 文件夹还有一点疑问。
在使用《使用 npm pack 创建一个 Example 目录》一节中通过 react-native init examples
命令创建工程,但在项目的实际目录下并非这样,它不是一个 React Native 工程。
我目前的猜测是作者没有提交 examples 下的所有文件,而是只提交了必要的文件。