Code Monkey home page Code Monkey logo

bob's Introduction

@react-native-community/bob

Version Build Status MIT License

๐Ÿ‘ทโ€โ™‚๏ธ Simple CLI to scaffold and build React Native libraries for different targets.

Features

Scaffold new projects

If you want to create your own React Native module, scaffolding the project can be a daunting task. Bob can scaffold a new project for you with the following things:

  • Simple example modules for Android and iOS which you can build upon
  • Kotlin configured for building the module on Android
  • C++ support for native modules on Android and iOS
  • Expo support for libraries without native code and web support
  • Example React Native app to manually test your modules
  • ESLint, Prettier, TypeScript, Husky and Release It pre-configured
  • Bob pre-configured to compile your files
  • CircleCI pre-configured to run tests on the CI

Build your projects

Bob can build code for following targets:

  • Generic CommonJS build
  • ES modules build for bundlers such as webpack
  • Flow definitions (copies .js files to .flow files)
  • TypeScript definitions (uses tsc to generate declaration files)
  • Android AAR files

Why

Metro handles compiling source code for React Native libraries, but it's possible to use them in other targets such as web. Currently, to handle this, we need to have multiple babel configs and write a long babel-cli command in our package.json. We also need to keep the configs in sync between our projects.

Just as an example, this is a command we have in one of the packages: babel --extensions '.js,.ts,.tsx' --no-babelrc --config-file=./babel.config.publish.js src --ignore '**/__tests__/**' --copy-files --source-maps --delete-dir-on-start --out-dir dist && del-cli 'dist/**/__tests__' && yarn tsc --emitDeclarationOnly. This isn't all, there's even a separate babel.config.publish.js file. And this only works for webpack and Metro, and will fail on Node due to ESM usage.

Bob wraps tools such as babel and typescript to simplify these common tasks across multiple projects. It's tailored specifically to React Native projects to minimize the configuration required.

Usage

Creating a new project

To create new project with Bob, run the following:

npx @react-native-community/bob create react-native-awesome-module

This will ask you few questions about your project and generate a new project in a folder named react-native-awesome-module.

The difference from create-react-native-module is that the generated project with Bob is very opinionated and configured with additional tools.

Configuring an existing project

First, install Bob in your project. Open a Terminal in your project, and run:

yarn add --dev @react-native-community/bob

To configure your project to use Bob, open a Terminal and run yarn bob init for automatic configuration.

To configure your project manually, follow these steps:

  1. In your package.json, specify the targets to build for:

    "@react-native-community/bob": {
      "source": "src",
      "output": "lib",
      "targets": [
        ["aar", {"reverseJetify": true}],
        ["commonjs", {"copyFlow": true}],
        "module",
        "typescript",
      ]
    }

    See options below for more details.

  2. Add bob to your prepare step:

    "scripts": {
      "prepare": "bob build"
    }
  3. Configure the appropriate entry points:

    "main": "lib/commonjs/index.js",
    "module": "lib/module/index.js",
    "react-native": "src/index.ts",
    "types": "lib/typescript/src/index.d.ts",
    "files": [
      "lib/",
      "src/"
    ]

    Make sure to change specify correct files according to the targets you have enabled.

    It's usually good to point to your source code with the react-native field to make debugging easier. Metro already supports compiling a lot of new syntaxes including JSX, Flow and TypeScript and it will use this field if present.

    If you're building TypeScript definition files, also make sure that the types field points to a correct path. Depending on the project configuration, the path can be different for you than the example snippet.

  4. Add the output directory to .gitignore and .eslintignore

    # generated files by bob
    lib/
  5. Add the output directory to jest.modulePathIgnorePatterns if you use Jest

    "modulePathIgnorePatterns": ["<rootDir>/lib/"]

And we're done ๐ŸŽ‰

Options

The options can be specified in the package.json file under the @react-native-community/bob property, or in a bob.config.js file in your project directory.

source

The name of the folder with the source code which should be compiled. The folder should include an index file.

output

The name of the folder where the compiled files should be output to. It will contain separate folder for each target.

targets

Various targets to build for. The available targets are:

commonjs

Enable compiling source files with Babel and use commonjs module system.

This is useful for running the code in Node (SSR, tests etc.). The output file should be referenced in the main field of package.json.

By default, this will compile the code for last 2 versions of modern browsers, as well as JSX. It'll also strip TypeScript and Flow annotations. You can customize the environments to compile for by using a browserslist config. To customize the babel config used, you can pass the configFile or babelrc options.

If your source code is written in Flow, You can also specify the copyFlow option to copy the source files as .js.flow to the output folder. If the main entry in package.json points to the index file in the output folder, the flow type checker will pick these files up to use for type definitions.

Example:

["commonjs", { "babelrc": true, "copyFlow": true }]

module

Enable compiling source files with Babel and use ES module system. This is essentially same as the commonjs target and accepts the same options, but leaves the import/export statements in your code.

This is useful for bundlers which understand ES modules and can tree-shake. The output file should be referenced in the module field of package.json.

Example:

["module", { "babelrc": true, "copyFlow": true }]

typescript

Enable generating type definitions with tsc if your source code is written in TypeScript.

By default, it'll use the tsconfig.json file in your project root. If you want to use a different config, you can specify it using the project option. Furthermore, the tsc binary will be resolved to ./node_modules/.bin/tsc. Use the tsc option to specify a different path.

Example:

["typescript", { "project": "tsconfig.build.json" }]

aar

Enable assembling Android AAR files for a library for React Native modules including native code.

It's also possible to convert the AAR with the reverseJetify option to use the Android support Library using the jetifier package if your package is using AndroidX. This is useful to publish packages for older projects which haven't migrated to AndroidX.

You can also specify the androidPath (defaults to android) to specify the android directory and androidBundleName (defaults to android.aar) to customize the name of AAR file. Example:

["aar", { "reverseJetify": true }]

Development workflow

To get started with the project, run yarn in the root directory to install the required dependencies.

yarn

While developing, you can run watch mode to automatically rebuild the changes:

yarn watch

To test the CLI locally, you can point to the bin/bob executable:

../bob/bin/bob create test-project

Before sending a pull rquest, make sure your code passes TypeScript and ESLint. Run the following to verify:

yarn typescript
yarn lint

To fix formatting errors, run the following:

yarn lint --fix

Acknowledgements

Thanks to the authors of these libraries for inspiration:

LICENSE

MIT

bob's People

Contributors

alanhr avatar dependabot[bot] avatar dpnolte avatar evanbacon avatar evancloutier avatar gaodeng avatar gorhom avatar jamesgeorge007 avatar jkoutavas avatar johan-dutoit avatar jonnyburger avatar jpeer264 avatar krizzu avatar mateosilguero avatar matt-oakes avatar patys avatar radko93 avatar safaiyeh avatar saleksovski avatar satya164 avatar simek avatar simonerm avatar trustedtomato avatar

Watchers

 avatar  avatar

Recommend Projects

  • React photo React

    A declarative, efficient, and flexible JavaScript library for building user interfaces.

  • Vue.js photo Vue.js

    ๐Ÿ–– Vue.js is a progressive, incrementally-adoptable JavaScript framework for building UI on the web.

  • Typescript photo Typescript

    TypeScript is a superset of JavaScript that compiles to clean JavaScript output.

  • TensorFlow photo TensorFlow

    An Open Source Machine Learning Framework for Everyone

  • Django photo Django

    The Web framework for perfectionists with deadlines.

  • D3 photo D3

    Bring data to life with SVG, Canvas and HTML. ๐Ÿ“Š๐Ÿ“ˆ๐ŸŽ‰

Recommend Topics

  • javascript

    JavaScript (JS) is a lightweight interpreted programming language with first-class functions.

  • web

    Some thing interesting about web. New door for the world.

  • server

    A server is a program made to process requests and deliver data to clients.

  • Machine learning

    Machine learning is a way of modeling and interpreting data that allows a piece of software to respond intelligently.

  • Game

    Some thing interesting about game, make everyone happy.

Recommend Org

  • Facebook photo Facebook

    We are working to build community through open source technology. NB: members must have two-factor auth.

  • Microsoft photo Microsoft

    Open source projects and samples from Microsoft.

  • Google photo Google

    Google โค๏ธ Open Source for everyone.

  • D3 photo D3

    Data-Driven Documents codes.