Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

fix(typescript): Support custom path in build mode #186

Merged
merged 1 commit into from
Dec 14, 2022

Conversation

justinhelmer
Copy link
Contributor

@justinhelmer justinhelmer commented Nov 23, 2022

Context
This PR is a small patch to the behavior when both buildMode and tsConfigPath options are used together.

This patch is a workaround for a larger use-case.

Use case

  • For local dev (i.e. vite), enable static typechecking w/o emitting any output.
  • For building (i.e. vite build), emit.

This is possible today with buildMode.

The gap is when specifically when building a library. In this scenario, vite compiles the typescript but another tool is needed to emit the declaration files. This is because vite does not generate declaration files for you.

vite-plugin-checker internally controls the --noEmit flag based on whether buildMode is true or false. As a result, my tsconfig.json cannot have:

{
  "compilerOptions": {
    "declaration": true,
    "emitDeclarationOnly": true
  }
}

...or else, you get an error from TypeScript that looks something like:

Option 'emitDeclarationOnly' cannot be specified with option 'noEmit'.

Ideally, vite-plugin-checker would expose more granular control over the arguments. For example, it would be nice to be able to directly specify tsConfig that takes precedence over tsconfig.json. Something like:

checker({
  typescript: {
    tsConfig: command === 'build' ? {
      compilerOptions: {
        declaration: true,
        emitDeclarationOnly: true,
     }  : undefined,
  },
}),

This would extend the plugin-specific config on top of tsconfig.json to be able to have control over ts behavior specifically based on build vs dev. I have seen this as a common approach in other popular libraries.

I understand that this may be more challenging to pull off, and conflicts with some of the other plugin-level behaviors (e.g. what do we do if noEmit is provided in tsConfig?). It also takes more thought w.r.t. the longer term implications.

This PR does not attempt to tackle that effort or address these harder questions. Instead, it works around it by using a different tsconfig.json when in build mode. For example:

tsconfig.json:

{
  "extends": "./tsconfig.json",
  "compilerOptions": {
    // These two options are used to emit the *.d.ts files whenever typescript is run.
    // This will happen when "vite build" is run thanks to the vite-plugin-checker.
    // However it requires a separate config file because these options cannot be used
    // in combination with noEmit, which is controlled internally by the plugin.
    "declaration": true,
    "emitDeclarationOnly": true,
    "outDir": "./dist",
  }
}

vite.config.js:

plugins: [
  // Vite does not emit declaration files when "vite build" is run.
  // Instead, we need to run typescript directly in order to emit the declaration files.
  // Since we are already using vite-plugin-checker for typechecking, we can simply have
  // the same plugin emit the declaration files by using "build mode".
  // When running in "build mode", a separate configuration file must also be used to
  // emit declaration files. This is because the options cannot be used with "noEmit",
  // which is controlled internally by vite-plugin-checker any time buildMode is not true.
  // @see https://github.com/vitejs/vite/issues/3461
  // @see https://vite-plugin-checker.netlify.app/checkers/typescript.html
  // @see https://github.com/fi3ework/vite-plugin-checker/pull/186
  checker({
    typescript: {
      buildMode: command === 'build' ? true : false,
      tsconfigPath: command === 'build' ? 'tsconfig.build.json' : 'tsconfig.json',
    },
  }),
],

This PR would also address #181

@netlify
Copy link

netlify bot commented Nov 23, 2022

Deploy Preview for vite-plugin-checker canceled.

Name Link
🔨 Latest commit 964ef68
🔍 Latest deploy log https://app.netlify.com/sites/vite-plugin-checker/deploys/637e7da73b4f74000a6de47f

@fi3ework
Copy link
Owner

nice catch. Thank you!

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

Successfully merging this pull request may close these issues.

2 participants