TypeLaunch is an opinionated, public template repository made to easily bootstrap a TypeScript library with the latest features and best practices.
To use this template
There are multiple edits that should be made to personalize TypeLaunch. Below is a checklist in order of importance.
- Add a
name
beyond "example" inpackage.json
andpackage-lock.json
- Replace all instances of the placeholder name "John Appleseed" with the project owner's name.
- Replace all instances of the placeholder email "[email protected]" with the project owner's email address.
- Customize these fields in
package.json
:description
repository
: provide a link to the GitHub repo this project resides inhomepage
: provide a link to one of these resources- Front-facing webpage
- Documentation
- GitHub repo
bugs.url
: provide a link to your bug trackerkeywords
When opening the project, create two terminal windows. In one, run npm watch:build
, and in the other, run npm watch:test
. These will set up tsc and AVA to rebuild and retest your project, respectively, every time the project is saved. Best practice is to stop these terminals when closing the project, though that's not entirely necessary.
When a commit is ready to be made, head to the Version Control pane and stage the files you'd like to commit. Next, look for the circle above the commit field labeled "Conventional Commits", or hit Ctrl/Cmd + Shift + P
to open the Command Palette and find it that way. In the Command Palette, type "Conventional Commits" and find the command with that title.
The Conventional Commits extension will walk you through the steps to making a conventional commit that commitlint will accept. In fact, commitlint will be linting your commit message as you type it via the commit-msg
hook. If you provide a description/body in your commit, when finished, the Conventional Commits extension will automatically commit your changes, running the precommit
hook.
This project adheres to the following conventions to keep code writing and reviewing easy.
- Conventional Commits
- Semantic Versioning
- ESLint recommended rules
- Prettier recommended rules
This project makes use of some dev dependencies that enforce following the above conventions and overall improve code quality.
- Essentials
- TypeScript, a type-safe superset of JavaScript
- TypeDoc for generating documentation through docstrings
- Testing and Coverage
- Linting and Formatting
- ESLint for potential bugs and convention adherence
- Prettier for styling
- CSpell for possible spelling errors
- Markdownlint for formatting Markdown files
- Version Control and CI/CD
- Husky for automating running scripts via git hooks
- Commitlint for enforcing Conventional Commit guidelines
- Lint-staged for only checking staged files
- GitHub Actions for the wider CI/CD pipeline
- TypeScript is provided for type-safety and is intended to be used instead of JavaScript. Both tsconfig and tsconfig.module also use strict mode, so the TypeScript compiler will complain about a lot of things. Remember, TypeScript errors are your friend.
- Usage of TypeDoc is highly encouraged, as it provides an easy way to produce documentation. The docstrings TypeDoc pulls from also allow IDE's like VSCode (my personal favorite) to provide inline documentation and tab completion directly in the editor!
- Use AVA and nyc for test-driven or behavior-driven development. Before working on the project, run
npm run watch:build
at the root of the project to build it whenever it's saved, then in a separate terminal instance, runnpm run watch:test
to run tests in watch mode. See the Commands section for more details. - Code should reside in the
src
directory and only in thesrc
directory. All tools are configured to read files only from thesrc
directory.types
is a subdirectory intended to house type declarations for code or for modules that need to be declared. Oftentimes it's only used for the latter as the code usually implicitly contains its own type declarations through classes, functions, etcetera.
TypeLaunch is an opinionated template. The most important tenets of TypeLaunch are:
- Clutter bad, ❌ intuitive structure good ✅
- Rigidity bad, ❌ easy customization good ✅
- Looseness bad, ❌ constructive strictness good ✅
- Manual bad, ❌ automatic help good ✅
The more granular opinions are described below:
- ESLint Prettier, and CSpell are pre-configured in the project's package file. This is where most of the opinions are.
- Prettier has no config key because all presets/recommendations are followed.
- All recommended ESLint presets are followed, with the exception of two additional rules. They are set to warn and not throw an exception because they are slightly pedantic.
- I've worked on projects where the root directory is a mess of config files with no way to hide them because they all had to be at the root. Therefore, I've tried to hide as much of the config in
package.json
as I can. Most of these config keys can be moved to their own files if necessary by making a<package>rc.*
file at the root. Read the package's documentation before doing so to see if it is possible, but if so, feel free to. - In the same spirit, the license and code of conduct are in the
.github
folder, but can be moved to the project root. - Part of the reason I made this template is to have full control over what tools I used and how I used them. I brought this design philosophy to TypeLaunch as much as I could; if a package is getting in your way, you just need to remove any mentions of it in
.husky
hooks orpackage.json
scripts and then runnpm uninstall <package>
. It's that simple. - TypeLaunch is also dependency-free for a reason: the thing shouldn't get in the way of what your application needs and should only help you if you develop it. Usage of TypeLaunch not contributing to build sizes is also a nice plus.
- Errors are your friend. No seriously. I've configured TypeLaunch to berate the developer with errors, exceptions, and test failures. Errors are also the lifeblood of test-driven development, a practice I'm getting better at following. Adding these errors is meant to make sure the code, docs, and tests are in tip-top shape.
Utilize these commands in your development pipeline by running npm run <command>
. For convenience, a table for these commands is included here:
Command | Description |
---|---|
build | run all build:* commands in parallel |
build:main | build the project using tsc and specs in tsconfig.json |
build:module | build the project using tsc and specs in tsconfig.module.json |
watch:build | build the project in watch mode |
watch:test | run project tests in watch mode |
fix | run all fix commands sequentially |
fix:prettier | run prettier on all src .ts files and fix some violations |
fix:lint | run eslint on all .ts files and fix some violations |
fix:markdown | run markdownlint on all .md files and fix some violations as well as check spelling |
test | run all test commands sequentially |
test:lint | run eslint on all .ts files |
test:prettier | run prettier on all src/**/*.ts files |
test:spelling | check spelling for README.md , all .github/*.md files, and all src/**/*.ts files |
test: markdown | run markdownlint on all .md files as well as check spelling for .md files |
test:unit | run AVA tests and nyc code coverage |
cov | unit test, create coverage reports, and open the html coverage report |
cov:html | create html coverage report |
cov:lcov | create lcov coverage report |
cov:check | run an nyc report and the check-coverage command |
doc | create html documentation and open it |
doc:html | create html documentation |
doc:json | create json documentation |
lint-staged | run the lint-staged cli |
release | create a release |
prepare | setup husky hook tool |
Not included in the table are the ___Section
commands, which are mostly meant to visually split the package.json
scripts apart. If ever it is unclear what sections of commands are available in the developer pipeline, simply run npm run sections
to get the summary of each section of commands. To get a summary of a single section, run npm run ___Section:<section-name>
.