My goal is to create a React component library with TypeScript. I have configured webpack to bundle my components and everything works as expected until I create a folder, that is outside the scope of the entry and which includes TypeScript files.
I have simplified the config as much as possible and I can still reproduce the problem.
webpack.config.js
const path = require('path');
const jsConfig = {
entry: './src/components/index.ts',
module: {
rules: [
{
test: /\.ts(x?)?$/,
exclude: /node_modules/,
use: {
loader: 'awesome-typescript-loader'
}
}
]
},
output: {
path: path.resolve(__dirname, 'dist'),
filename: 'index.js',
libraryTarget: 'commonjs2',
pathinfo: true
},
resolve: {
extensions: ['.ts', '.tsx', '.js']
},
externals: {
react: 'react',
'react-dom': 'react-dom'
},
optimization: {
minimize: false,
usedExports: true,
sideEffects: false
},
mode: 'production'
}
const configuration = [jsConfig];
module.exports = configuration;
tsconfig.json
{
"compilerOptions": {
"module": "commonjs",
"jsx": "react",
"target": "es5",
"lib": [
"es2015",
"dom"
],
"outDir": "dist",
"sourceMap": false,
"declaration": true,
"moduleResolution": "node"
}
}
Here is the initial folder structure:
|-- node_modules
|-- src
| `-- components
| |-- Button
| | `-- Button.tsx // Example component
| `-- index.ts // A file that exports all components
|-- package.json
|-- tsconfig.json
`-- webpack.config.js
When I run webpack, it creates a dist
folder with the following structure:
-- dist
|-- Alert
| `-- Alert.d.ts
|-- index.d.ts
`-- index.js
This is what I'm trying to achieve. However, I want to add, let's say, a helper function, and create a folder called helpers
in src
. Then I add a simple helper.ts
file and just add a function that logs something on the console. I'm not exporting anything and I haven't invoked the helper function yet. So if I run webpack now, the dist
will look like this:
-- dist
|-- components
| |-- Alert
| | `-- Alert.d.ts
| `-- index.d.ts
`-- index.js
I suppose there is something essential, that I'm missing in understanding webpack's workflow. Why does this components
folder emerge in the build output? Notice that it also wraps the index.d.ts
- definitely not what I'm going for.
Thanks in advance!
After a few days on this issue, I think I've found the answer. I will describe my steps to fixing the problem:
helper
file is not with TypeScript extension, the build output does not change.awesome-typescript-loader
with ts-loader
- the results were the same, the output folder structure changes depending on whether the helper
is a TypeScript file or not. Moreover, I didn't find any configuration options for the loader, which would solve the issue.tsconfig.json
. The docs show that I can set the files
or include
/exclude
properties of the configuration object, which will affect the end result of compilation. Here is the answer to the question why unused files are compiled:If the "files" and "include" are both left unspecified, the compiler defaults to including all TypeScript (.ts, .d.ts and .tsx) files in the containing directory and subdirectories except those excluded using the "exclude" property.
One more thing to add, since I mentioned the location of index.d.ts
in the output folder structure: My goal for helper.ts
was to use it in the components, of course. Therefore I had to accept that with the current configuration, my output folder structure changes, because the helper file had be transpiled. This caused the type definition file to end in the components
folder. I simply moved the index.ts
(which exports the components) one level above - in src
and updated the webpack entry file.
I hope this helps someone.