Skip to content

Commit

Permalink
docs(getting-started): fix cjs/esm or js/typescript
Browse files Browse the repository at this point in the history
  • Loading branch information
jjangga0214 committed Nov 3, 2023
1 parent f0a1c74 commit 6a8f178
Show file tree
Hide file tree
Showing 2 changed files with 184 additions and 25 deletions.
49 changes: 49 additions & 0 deletions packages/docs/components/ProjectTypeTabs.tsx
Original file line number Diff line number Diff line change
@@ -0,0 +1,49 @@
import { Tab, Tabs, Box } from '@mui/material'
import { TabPanel, TabContext } from '@mui/lab'
import { useCallback } from 'react'
import useSWR from 'swr'

enum ProjectType {
ESM = 'esm',
CJS = 'cjs',
ESM_TS = 'esm-typescript',
CJS_TS = 'cjs-typescript',
}
const storageKey = 'ProjectType'

export default function ProjectTypeTabs({
children,
}: {
children: JSX.Element[]
}): JSX.Element {
// Use SWR to sync every ProjectType choice.
const { data, mutate } = useSWR(storageKey, (key) =>
localStorage?.getItem(key),
)
const value = data || ProjectType.ESM

const onChange = useCallback(
(value: ProjectType) => {
localStorage.setItem(storageKey, value)
mutate(value, false)
},
[mutate],
)

return (
<TabContext value={value}>
<Box sx={{ borderBottom: 1, borderColor: 'divider' }}>
<Tabs value={value} onChange={(_, _value) => onChange(_value)}>
<Tab label="ESM" value={ProjectType.ESM} />
<Tab label="CJS" value={ProjectType.CJS} />
<Tab label="ESM + Typescript" value={ProjectType.ESM_TS} />
<Tab label="CJS + Typescript" value={ProjectType.CJS_TS} />
</Tabs>
</Box>
<TabPanel value={ProjectType.ESM}>{children[0]}</TabPanel>
<TabPanel value={ProjectType.CJS}>{children[1]}</TabPanel>
<TabPanel value={ProjectType.ESM_TS}>{children[2]}</TabPanel>
<TabPanel value={ProjectType.CJS_TS}>{children[3]}</TabPanel>
</TabContext>
)
}
160 changes: 135 additions & 25 deletions packages/docs/pages/getting-started.mdx
Original file line number Diff line number Diff line change
@@ -1,6 +1,7 @@
import { Callout } from 'nextra-theme-docs'
import Image from '../components/Image';
import PkgManagerTabs from '../components/PkgManagerTabs'
import ProjectTypeTabs from '../components/ProjectTypeTabs'
import TokenLinkCode from '../components/TokenLinkCode'

# Getting Started
Expand Down Expand Up @@ -61,12 +62,32 @@ Literally **any project** is proper.
<PkgManagerTabs>
```bash
npm install --save-dev haetae

# execute haetae
npx haetae --help

# ht is shorthand for haetae
npx ht --help
```

```bash
yarn add --dev haetae

# execute haetae
yarn haetae --help

# ht is shorthand for haetae
yarn ht --help
```

```bash
pnpm add --save-dev haetae

# execute haetae
pnpm haetae --help

# ht is shorthand for haetae
pnpm ht --help
```
</PkgManagerTabs>

Expand All @@ -81,34 +102,124 @@ pnpm add --save-dev haetae
## Basic configuration

Now, we are ready to configure Haetae.<br/>
Let's create a config file *`haetae.config.js`*.<br/>
Let's create a config file.
Its name and execution setting are different depending on whether your project is ESM/CJS, or JS/TypeScript.

<Callout>
**CJS/ESM** <br/>
Haetae supports both CJS and ESM project. <br/>
Haetae itself is written in ESM, but it can be used for CJS projects as well, as long as the config file is ESM.
</Callout>

<br/>

<ProjectTypeTabs>
<>
If `"type": "module"` is set in your *`package.json`*, name the config file *`haetae.config.js`*.

```fish
my-calculator
├── haetae.config.js # <--- Haetae config file
├── package.json
├── src # contents are omitted for brevity
└── test # contents are omitted for brevity
├── src/ # contents are omitted for brevity
└── test/ # contents are omitted for brevity
```
</>
<>
If `"type"` key is omitted(default), or `"type": "commonjs"` is set in your *`package.json`*, name the config file *`haetae.config.mjs`*.

<Callout>
**Typescript Support** <br/>
If you want to write the config in typescript, name it *`haetae.config.ts`*.
Then install [`ts-node`](https://www.npmjs.com/package/ts-node),
which is an optional `peerDependencies` of `haetae{:ts}` (from `@haetae/core{:ts}`).
Finally, provide an environment variable `NODE_OPTIONS='--loader=ts-node/esm'`.
</Callout>
```fish
my-calculator
├── haetae.config.mjs # <--- Haetae config file
├── package.json
├── src/ # contents are omitted for brevity
└── test/ # contents are omitted for brevity
```
</>
<>
If `"type": "module"` is set in your *`package.json`*,
and you're using Typescript compiled to ESM,
name the config file *`haetae.config.ts`*.

<Callout>
**CJS/ESM** <br/>
Haetae supports both CJS and ESM project. <br/>
Haetae is written in ESM, but it can be used in CJS projects as well, as long as the config file is ESM.
If your project is CJS, name the config file *`haetae.config.mjs`* or *`haetae.config.mts`*.
If your project is ESM, name the config file *`haetae.config.js`* or *`haetae.config.ts`*.
</Callout>
```fish
my-calculator
├── haetae.config.ts # <--- Haetae config file
├── package.json
├── tsconfig.json
├── src/ # contents are omitted for brevity
└── test/ # contents are omitted for brevity
```

Next, install [`ts-node`](https://www.npmjs.com/package/ts-node).
It's optional `peerDependencies` of [`@heatae/core{:ts}`](./apis/haetae-core), which is an internal dependency of `haetae`.

We can write it down like this.<br/>
Make sure you initialized git. Haetae can be used with any other version control systems, but using git is assumed in this article.
```bash
pnpm add -D ts-node
```

Finally, provide an environment variable `$NODE_OPTIONS`.

```bash
NODE_OPTIONS='--loader=ts-node/esm' haetae --help
```

Registering scripts in *`package.json`* is a recommended good practice.

```jsonc
{
"scripts": {
"haetae": "cross-env NODE_OPTIONS='--loader=ts-node/esm' haetae",
"ht": "cross-env NODE_OPTIONS='--loader=ts-node/esm' haetae"
}
}
```
</>
<>
If `"type"` key is omitted(default), or `"type": "commonjs"` is set in your *`package.json`*,
and you're using Typescript compiled to CJS, name the config file *`haetae.config.mts`*.

```fish
my-calculator
├── haetae.config.mts # <--- Haetae config file
├── package.json
├── tsconfig.json
├── src/ # contents are omitted for brevity
└── test/ # contents are omitted for brevity
```

Next, install [`ts-node`](https://www.npmjs.com/package/ts-node).
It's optional `peerDependencies` of [`@heatae/core{:ts}`](./apis/haetae-core), which is an internal dependency of `haetae`.

```bash
pnpm add -D ts-node
```

Finally, provide environment variables `$TS_NODE_COMPILER_OPTIONS` and `$NODE_OPTIONS`.
Because your *`tsconfig.json`* is CJS, `$TS_NODE_COMPILER_OPTIONS` makes sure haetae's config file is ESM.

```bash
# Instead of 'node16', you can choose other values like 'nodenext', etc.
TS_NODE_COMPILER_OPTIONS='{"module": "node16", "moduleResolution": "node16"}' \
NODE_OPTIONS='--loader=ts-node/esm' \
haetae --help
```

Registering scripts in *`package.json`* is a recommended good practice.

```jsonc
{
"scripts": {
"haetae": "cross-env TS_NODE_COMPILER_OPTIONS='{\"module\": \"node16\", \"moduleResolution\": \"node16\"}' NODE_OPTIONS='--loader=ts-node/esm' haetae",
"ht": "cross-env TS_NODE_COMPILER_OPTIONS='{\"module\": \"node16\", \"moduleResolution\": \"node16\"}' NODE_OPTIONS='--loader=ts-node/esm' haetae"
}
}
```
</>
</ProjectTypeTabs>

We can write down the config file like this.<br/>
You should initialized git.
Haetae can be used with any other version control systems, but using git is assumed in this article.

<TokenLinkCode tokens={{
'configure': './apis/haetae#configure',
Expand Down Expand Up @@ -218,8 +329,8 @@ If you use Typescript or Webpack, check out [the API docs](./apis/haetae-javascr
<Callout>
**`js.dependOn`** vs **`js.dependsOn`** vs **`utils.dependOn`** vs **`utils.dependsOn`** <br/>
There are severel APIs of simliar purposes.
- [`js.dependOn{:ts}`](./apis/haetae-jss#dependon) : For multiple dependents. On js ecosystem.
- [`js.dependsOn{:ts}`](./apis/haetae-jss#dependson) : For a single dependent. On js ecosystem.
- [`js.dependOn{:ts}`](./apis/haetae-javascript#dependon) : For multiple dependents. On js ecosystem.
- [`js.dependsOn{:ts}`](./apis/haetae-javascript#dependson) : For a single dependent. On js ecosystem.
- [`utils.dependOn{:ts}`](./apis/haetae-utils#dependon) : For multiple dependents. General-purpose.
- [`utils.dependsOn{:ts}`](./apis/haetae-utils#dependson) : For a single dependent. General-purpose.

Expand Down Expand Up @@ -1054,8 +1165,7 @@ export default configure({
env: { /* ... */ },
run: async () => {
const changedFiles = await git.changedFiles()
const changedFilesByHash = await utils.changedFiles(['.env'])
changedFiles.push(...changedFilesByHash)

const additionalGraph = await utils.graph({
edges: [
{
Expand Down Expand Up @@ -1250,7 +1360,7 @@ for the return value of `env` and `run` of every command.
<TokenLinkCode tokens={{
'configure': './apis/haetae#configure',
'.hash': './apis/haetae-utils#hash',
'.deps': './apis/haetae-js#deps',
'.deps': './apis/haetae-javascript#deps',
}}>
```js filename="haetae.config.js" {4-6, 9}
import { $, configure, git, utils, js } from 'haetae'
Expand Down Expand Up @@ -1328,7 +1438,7 @@ By the way, you can go even thoroughly.
<TokenLinkCode tokens={{
'.hash': './apis/haetae-utils#hash',
'.deps': './apis/haetae-js#deps',
'.deps': './apis/haetae-javascript#deps',
}}>
```js filename="haetae.config.js" {3}
// Other content is omitted for brevity
Expand Down

0 comments on commit 6a8f178

Please sign in to comment.