Creating a JS library from a TypeScript project

Tom Szpytman
Feb 15 · 2 min read

In my last post I wrote about the notion of hosting a project on GitHub and using this repository as a pseudo NPM package. What I didn’t describe, was the configuration I use to compile a TypeScript project down into JavaScript for other libraries to consume.


"compilerOptions": {
"outDir": "build",
"module": "esnext",
"target": "es5",
"lib": ["es6", "dom", "es2016", "es2017"],
"types": ["react", "jest", "node"],
"sourceMap": true,
"allowJs": false,
"jsx": "react",
"declaration": true,
"moduleResolution": "node",
"forceConsistentCasingInFileNames": true,
"noImplicitReturns": true,
"noImplicitThis": true,
"noImplicitAny": true,
"strictNullChecks": true,
"suppressImplicitAnyIndexErrors": true,
"noUnusedLocals": true,
"noUnusedParameters": true,
"allowSyntheticDefaultImports": true,
"resolveJsonModule": true
"include": ["src"],
"exclude": [


import typescript from 'rollup-plugin-typescript2'
import commonjs from 'rollup-plugin-commonjs'
import external from 'rollup-plugin-peer-deps-external'
import resolve from 'rollup-plugin-node-resolve'
import { eslint } from 'rollup-plugin-eslint'
import json from 'rollup-plugin-json'

import pkg from './package.json'

export default {
input: 'src/index.ts',
output: [
file: pkg.main,
format: 'es',
exports: 'named',
sourcemap: false,
plugins: [
throwOnError: true,
fix: true,
rollupCommonJSResolveHack: true,
clean: true,
tsconfig: './tsconfig.json',
namedExports: {
'node_modules/react-is/index.js': [
'node_modules/moment-timezone/index.js': ['tz'],
'node_modules/prop-types/index.js': ['func'],


"name": "common-library",
"version": "1.0.0",
"description": "",
"license": "UNLICENSED",
"main": "dist/index.js",
"typings": "dist/index.d.ts",
"engines": {
"node": ">=8",
"npm": ">=5"
"scripts": {
"build": "rollup -c",
"prepare": "yarn run build",
"dependencies": {

"peerDependencies": {
"devDependencies": {
"@typescript-eslint/eslint-plugin": "^2.19.0",
"@typescript-eslint/parser": "^2.19.0",
"awesome-typescript-loader": "^5.2.1",
"babel-core": "^6.26.3",
"babel-runtime": "^6.26.0",
"eslint": "^6.8.0",
"eslint-config-prettier": "^6.10.0",
"eslint-config-react-app": "^5.2.0",
"eslint-plugin-prettier": "^3.1.2",
"eslint-plugin-react": "^7.18.3",
"eslint-plugin-react-hooks": "^2.3.0",
"prettier": "^1.19.1",
"rollup": "^1.31.0",
"rollup-plugin-babel": "^4.3.3",
"rollup-plugin-commonjs": "^10.1.0",
"rollup-plugin-eslint": "^7.0.0",
"rollup-plugin-json": "^4.0.0",
"rollup-plugin-node-resolve": "^5.2.0",
"rollup-plugin-peer-deps-external": "^2.2.2",
"rollup-plugin-typescript2": "^0.25.3",
"typescript": "^3.7.5"
"files": [
"eslintConfig": {
"extends": "react-app"
"browserslist": {
"production": [
"not dead",
"not op_mini all"
"development": [
"last 1 chrome version",
"last 1 firefox version",
"last 1 safari version"
Tom Szpytman

Written by

Full-stack Software Engineer.

More From Medium

Welcome to a place where words matter. On Medium, smart voices and original ideas take center stage - with no ads in sight. Watch
Follow all the topics you care about, and we’ll deliver the best stories for you to your homepage and inbox. Explore
Get unlimited access to the best stories on Medium — and support writers while you’re at it. Just $5/month. Upgrade