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

TypeScript support #893

Closed
RuneKR opened this issue Oct 21, 2019 · 22 comments
Closed

TypeScript support #893

RuneKR opened this issue Oct 21, 2019 · 22 comments
Labels
enhancement New feature or request

Comments

@RuneKR
Copy link

RuneKR commented Oct 21, 2019

Hi,

I want to open a pull request to look at typescript support for this project. The current instructions do not mention that you have to modify the Webpack configuration to use the 'ts' extension. The updated documentation is given here below.

const path = require('path');
const { createDefaultConfig } = require('@open-wc/building-webpack');
const merge = require('webpack-merge');

const config = createDefaultConfig({
  input: path.resolve(__dirname, './index.html'),
});

module.exports = merge(config, {
  resolve: {
    extensions: ['.ts']
  }
})

Another solution would also to have typescript support as a optional "opt-in" approach. That would make it easier to use. Happy to do the work and the pull request. Thoughts?

const config = createDefaultConfig({
  input: path.resolve(__dirname, './index.html'),
  withTypeScript: true
});
@LarsDenBakker
Copy link
Member

Thanks for wanting to look into this.

Looks like we missed that in the docs indeed, a PR would be great. Can you see if we need to update the rollup docs too?

I want to avoid adding options to the configuration object passed to the 'create config' options. While tempting, it will turn us into a meta-framework to configure a build tools. Build tools should be easily configurable by themselves, we just provide a nice default optimized configuration.

Given typescript's popularity, and the large amount of questions we get regarding typescript, I'm open to exporting a separate config that's optimized for typescript. My only doubt there is that double the amount of configs that we export. What do you think @thepassle @daKmoR @Westbrook @bennypowers ?

@Westbrook
Copy link
Contributor

Certainly not a bad idea!

Other than the alternate extension support, what optimizations did you have in mind? I've been working with TS primarily, but do my best to keep processing it and processing other things separate, so some thoughts on what could be tuned up would be interesting. In that process, would we be able to share a good amount of what we already export, even if we didn't ship with "'create config' options"?

@LarsDenBakker
Copy link
Member

For the building configs it just helps people not having to figure it out for themselves, but the main benefit is with testing and the dev server. We can either add a typescript flag there, or look into some kind of 'plugin' system and ship a separate typescript plugin that can be hooked into it.

@thepassle
Copy link
Member

Seeing the amount of questions we get about this, I think its definitely worth doing.

@RuneKR
Copy link
Author

RuneKR commented Oct 22, 2019

I like the idea of a plugin or "presets" system.

const config = createDefaultConfig({
  input: path.resolve(__dirname, './index.html'),
  plugins: [@open-wc/building-webpack-plugin-typescript]
});

@LarsDenBakker
Copy link
Member

LarsDenBakker commented Oct 22, 2019

for the building configuration exporting a separate function is still the best option I think, although we did start introducing an object with boolean options to disable plugins:

const config = createDefaultConfig({
  input: path.resolve(__dirname, './index.html'),
  plugins: {
    babel: false
  }
});

Adding a typescript flag that defaults to false there would not add too much extra confiugration

Come to think of it, for the dev server it could be as simple as importing this in your es-dev-server.config.js:

const { presets } = require('es-dev-server');

module.exports = {
  ...presets.typescript,
};

@bennypowers
Copy link
Member

tools are coalescing around TS as a kind of transport layer, so I think we should try to support it transparently as much as possible.

@abdonrd
Copy link
Collaborator

abdonrd commented Nov 16, 2019

I also propose to have an application template with TS. 😄

@LarsDenBakker LarsDenBakker added the enhancement New feature or request label Nov 21, 2019
@difosfor
Copy link

difosfor commented Dec 12, 2019

Both application and component templates for TS please 👍

I've gotten things working reasonably well, but it took me a lot of time (setting up eslint and prettier with @typescript-eslint proved to be quite the pain) and I'm still not really happy with it. I basically just compile all Typescript files to /build/ and then reference the files there (e.g: from /build/src/.. instead of /src/..). That means I have to have a tsc --watch server running besides my es-dev-server etc. And I actually have to build before I can successfully lint as references to build files might not resolve before that time. Similarly my TypeScript test files need to be built before tests can be run. Finally I added a dist script which does the final bundling and minifying using rollup to the /dist/ directory.

I've also tried to get things working by using Babel to do the TypeScript compiling and then configure all tools to use Babel. But @babel/preset-typescript is somewhat limited which was annoying giving my existing codebase. And moreover in the end the JavaScript that was produced did not work. E.g: With the basic example element with a button that increments a counter element; changes to the counter value were not rendered to the DOM. I'm guessing it had to do with my use of LitElement decorators.

Anyhow I would be very interested in your recommendations for this. Also, let me know if I can help.

@abdonrd
Copy link
Collaborator

abdonrd commented Jan 8, 2020

Take care about the new @rollup/plugin-typescript

@abdonrd
Copy link
Collaborator

abdonrd commented Jan 28, 2020

Now the official @rollup/plugin-typescript v3.0.0 has built-in typechecking!

https://twitter.com/Not_Woods/status/1221926927612596226

@bennypowers
Copy link
Member

Doesn't yet support declaration though

@JohnYoungers
Copy link

I need to write a framework agnostic customElement, and I was pumped when I stumbled on the open-wc CLI to scaffold everything up.

My original hope was to create a simple project of one component, with build and testing setup, where the component could be written in TypeScript: at that point I figured since there was a build system involved, you could also extract the css out of the component into another file (which wouldn't necessarily need to be in vanilla css).

So far finding an up to date way to set that up fully has been more difficult than I anticipated.

@vikerman
Copy link
Contributor

vikerman commented Feb 21, 2020

I followed the instructions for enabling typescript through babel. Something or the other wasn't working and finally I couldn't get decorators to work in ts.

I think the right way to enable TypeScript would be through using tsc and not babel - To avoid any skew of TS features between the two tools. I got a solution working where I have tsc --watch running for storybook, es-dev-server and test:watch and running tsc before the production build and test.

I have put the TS version of the @open-wc init app here - https://github.com/vikerman/open-wc-typescript-starter . This runs tsc --watch concurrently with the other commands in watch mode.

The .js is output to out-tsc/ directory and I change various configs and index.html to point to .js in out-tsc. Full diff from base starter app - vikerman/open-wc-typescript-starter@4bb5b85

@difosfor
Copy link

FYI: After updating dependencies I was getting Could not find a declaration file for module errors from TypeScript from node_modules/@open-wc/testing-helpers/index.d.ts due to me specifying strict: true in my tsconfig.json. I had to work around this by not specifying strict in my root tsconfig and then creating additional tsconfig files in my src and test directories extending the root one and adding strict.

Might be useful for other TypeScript users to know.

Or should I create an issue about this?

@daKmoR
Copy link
Member

daKmoR commented Mar 20, 2020

@difosfor we had an issue in the testing-helper where the typescript declarations files did not end up in the published npm package 🙈 it is solved now 👍 (version 1.6.2)

@LarsDenBakker
Copy link
Member

We decided to generally recommend to use tsc before using most tools, with a possible exception for rollup if you need declaration files. The babel typescript option didn't turn out to be as great as we had hoped, so we're removing that recommendation.

We're also improving the types across the board in our packages, and adding a typescript choice to our project generator.

I'll close this issue as there is nothing specifically actionable here.

@abraham
Copy link
Contributor

abraham commented May 6, 2020

That's unfortunate. I inherited a project with a multi-step build that I was able to reduce to one-step with babel. I'll now have to switch it to a a three-step process with template compile, typescript, and babel.

@LarsDenBakker
Copy link
Member

Of course not! What we offer are just recommendations for most users, and in that case babel typescript just had a bit too many corner cases that people ran into. If it works for you in your project, you should definitely continue to use it.

@abraham
Copy link
Contributor

abraham commented May 6, 2020

Hmm... maybe it's unrelated then but when I attempted to update to @open-wc/building-rollup v1 the babel config stopped working with TypeScript. With your comment I had assumed it was just not supported anymore.

@silenceisgolden
Copy link

@LarsDenBakker Was there a list put together on what those corner cases were?

@LarsDenBakker
Copy link
Member

https://babeljs.io/docs/en/babel-plugin-transform-typescript#caveats has a good list.

In addition to that, babel typescript doesn't support type-only imports introduced in typescript 3.8. And most TS users want to use decorators, but babel decorators are different from TS decorators. It requires quite some fiddling to get it to work, and it doesn't work for all libraries.

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

No branches or pull requests