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

tsc: TS5053: Option 'noEmit' cannot be specified with option 'composite' #36917

Closed
dgadelha opened this issue Feb 21, 2020 · 21 comments
Closed
Assignees

Comments

@dgadelha
Copy link

TypeScript Version: 3.9.0-dev.20200220 (broken in 3.8.2)

Search Terms: TS5053: Option 'noEmit' cannot be specified with option 'composite'

Code

{
  "compilerOptions": {
    "composite": true
  }
}

Expected behavior:

Run a type-check with no errors, as in 3.7 and previous versions.

Actual behavior:

# npx tsc --noEmit
tsconfig.json:3:5 - error TS5053: Option 'noEmit' cannot be specified with option 'composite'.

3     "composite": true,
      ~~~~~~~~~~~

Found 1 error.

Additional comments:

We use composite in our tsconfig.json to ensure the output directory structure is always the same.
We also use --noEmit in our CI pipelines to ensure type-checking before building a Docker image.

Is the --noEmit the best way to do type-checking without the overhead of running an entire build (with output files) or this breaking change should really be reverted?

Related Issues:
#36588 - attempt to remove the composite from tsconfig.json and use as CLI flag when building project

@weswigham
Copy link
Member

Is the --noEmit the best way to do type-checking without the overhead of running an entire build (with output files) or this breaking change should really be reverted?

composite requires declaration output to actually do incremental work - use emitDeclarationsOnly instead of noEmit.

@dgadelha
Copy link
Author

Is the --noEmit the best way to do type-checking without the overhead of running an entire build (with output files) or this breaking change should really be reverted?

composite requires declaration output to actually do incremental work - use emitDeclarationsOnly instead of noEmit.

Thanks for the quick answer! When using emitDeclarationOnly an entire build tree is created with the .d.ts files. We're looking for an alternative to use the composite flag when building (we can't use as CLI flag due to #36588) while using noEmit to do a quick type-checking without the I/O overhead.

@weswigham
Copy link
Member

weswigham commented Feb 21, 2020

Those declaration files are the metadata that incremental and composite modes use to determine which files need to be checked in subsequent builds. Without them, no work is actually incremental.

@dgadelha
Copy link
Author

I understand that composite needs metadata to work properly, but now there's no way to run a simple type-check within the CLI without actually building something.

composite was released in TypeScript 3.0 and worked with noEmit until 3.8.

I'm really not against that change, but as #36588 blocks us from removing composite from tsconfig.json and using it on compile-time, there's no way to run a type-check without build artifacts.

@RyanCavanaugh RyanCavanaugh added the Needs Investigation This issue needs a team member to investigate its status. label Feb 21, 2020
@RyanCavanaugh RyanCavanaugh added this to the TypeScript 3.8.3 milestone Feb 21, 2020
@dotupNET
Copy link

dotupNET commented Feb 23, 2020

I understand that composite needs metadata to work properly, but now there's no way to run a simple type-check within the CLI without actually building something.

composite was released in TypeScript 3.0 and worked with noEmit until 3.8.

I'm really not against that change, but as #36588 blocks us from removing composite from tsconfig.json and using it on compile-time, there's no way to run a type-check without build artifacts.

I've the same problem in a mono repo. so that I can continue to work, I created a tsconfig.test.json

{ "extends": "./tsconfig.json", "compilerOptions": { "composite": false } }

to use it with --noEmit:

"lint": "tsc -p tsconfig.test.json --noEmit && eslint \"**/*.{ts,tsx}\" --quiet --fix",

So I can lint my packages at least

@hollg
Copy link

hollg commented Feb 24, 2020

I have the same problem but with noEmit and incremental. Is there any other way to run a type-check without building anything?

@weswigham
Copy link
Member

Don't use incremental? If you don't want anything built, you can't get any speedup from incremental; the built things are what incremental uses in place of normal inputs to save time.

@hollg
Copy link

hollg commented Feb 24, 2020

@weswigham Sorry, to clarify: we have incremental set in our tsconfig, which until now we've used for our production builds, local environment builds and type-checks on commit. For the type-check on commit we've passed --noEmit as a CLI argument. As far as I can tell what we have to do now is add a separate tsconfig for type-checking as @dotupNET suggested.

So I'm wondering if there's a way to avoid having two config files.

@satya164
Copy link

satya164 commented Feb 24, 2020

We have a similar issue. We have a monorepo and use path references, which requires composite: true. We used to use --noEmit to perform type-checking on commit hook, but now it doesn't seem to be possible without actually building files.

@t7yang
Copy link

t7yang commented Feb 24, 2020

agree, --noEmit used to work perfectly with composite: true and incremental: true, pls bring it back.

@weswigham
Copy link
Member

It did not "work perfectly" - it didn't do what it claimed to do (intelligently reuse build outputs as inputs where possible); the usage of noEmit completely negated what the composite and incremental flags were meant to achieve. You can get the same behavior (build performance-wise) by not having them set.

@weswigham
Copy link
Member

@hollg you could pass --incremental false --noEmit rather than just --noEmit for the CI pass, no?

@satya164
Copy link

satya164 commented Feb 24, 2020

The problem is that they can not be unset in command line. During development, it's good to have them, but for checking during commit, it'd be better to do something like tsc --noEmit --composite false. But right now tsc doesn't allow to have it in command line, so we basically need to have separate config files. See #36588

@weswigham
Copy link
Member

composite has other baggage that ties it to tsconfig usage (namely project references), so you need a separate config file (so you can redefine the build without using project references), but for incremental just using --incremental false as an override on the command line works fine, afaik?

@sheetalkamat
Copy link
Member

I think allowing composite to be set to false (not true) seems like a better solution here. Looking into this.

@hollg
Copy link

hollg commented Feb 25, 2020

@weswigham

@hollg you could pass --incremental false --noEmit rather than just --noEmit for the CI pass, no?

This works, thanks!

@pleerock
Copy link

pleerock commented Feb 25, 2020

@weswigham right now its impossible to use composite projects, where one of the project is react-based. Because create-react-app adds "noEmit": true to tsconfig automatically (even if you set it to false, once you run app it will change it to true) it makes impossible to use react and composite projects.

Its a big issue because guess over 95% of react users use create-react-app.

@weswigham
Copy link
Member

weswigham commented Feb 25, 2020

Should create-react-app be adjusted to use emitDeclarationOnly instead? Afaik it uses noEmit because webpack handles (non-declaration) emit; but blocking all emit does make the composite (and incremental) flags do nothing (extra or better, compared to a build without them set).

@sheetalkamat
Copy link
Member

Closing this since we are now allowing passing --composite false from the command line

@timocov
Copy link
Contributor

timocov commented Mar 27, 2020

you could pass --incremental false --noEmit rather than just --noEmit for the CI pass, no?

For someone who found this thread after upgrading to TypeScript 3.8 and after passing --incremental false together with --noEmit but gets another error TS5069: Option 'tsBuildInfoFile' cannot be specified without specifying option 'incremental' or option 'composite'. the solution is passing --tsBuildInfoFile null as well (yeah, null). This ain't intuitive, so it might be helpful.

@FilDevTronic
Copy link

@weswigham right now its impossible to use composite projects, where one of the project is react-based. Because create-react-app adds "noEmit": true to tsconfig automatically (even if you set it to false, once you run app it will change it to true) it makes impossible to use react and composite projects.

Its a big issue because guess over 95% of react users use create-react-app.

Eject from create-react-app.

iquabius added a commit to iquabius/olimat that referenced this issue Jun 17, 2020
TypeScript incremental build seems to be a problem for projects using
Babel, like Next.js apps:

"error TS5053: Option 'noEmit' cannot be specified with option 'composite'."

So... microsoft/TypeScript#36917
iquabius added a commit to iquabius/olimat that referenced this issue Jun 17, 2020
* Update dependency typescript to v3.9.5

* Update dependency typescript to v3.9.5

* Fix name clashes in resolvers-types.ts with a hack

I modified indent_style back to "space" in .editorconfig to avoid too
much changes in this commit's diff.

We still have the following problem: "error TS5053: Option 'noEmit'
cannot be specified with option 'composite'."

* Add --composite false to "typecheck:api" npm command

TypeScript incremental build seems to be a problem for projects using
Babel, like Next.js apps:

"error TS5053: Option 'noEmit' cannot be specified with option 'composite'."

So... microsoft/TypeScript#36917

* Suppress TS errors from mocked server context

* Fix *Payload interfaces with a temporary hack

* Fix directories in VS Code workspace config

* Add --composite false to "typecheck:web" npm command

* Add tsconfig.build.json to avoid incremental build

For package/web, which uses Babel.

* Replace GlobalFetch with WindowOrWorkerGlobalScope

GlobalFetch was removed in TS 3.6.2:
apollographql/apollo-link#1131

* Fix root "build" command to use tsconfig.build.json

Co-authored-by: Renovate Bot <bot@renovateapp.com>
Co-authored-by: Josias Iquabius <iquabius@gmail.com>
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

No branches or pull requests