From personal experience, you probably want Babel anyway even with TS to deal with some weird edge cases.
I think this has been fixed now. But a couple of weeks ago, I had a case where TS compiler output has to be ES6 (since the code base were using something like constructor.name which isn't in ES5), but then Jest (the test framework) doesn't like ES6 syntax, so Babel is needed to compile whatever Jest didn't like down to just ES5 syntax.
webassembly can't come soon enough. as a developer who doesn't deal with browser frontends what i read in this thread is madness. (3 comments at the time of writing this...)
I don't think the point of WebAssembly is to target the DOM. I think it it's to provide a common low level API across browsers that many languages can target.
Sorry was referring to the infinite layers of transpiling and sub-languages that people talk about like it's normal, which I admittedly get why they exist, but it's still fucked. But that too. (though maybe wasm + canvas will let someone eventually implement a decent ui toolkit? Think I saw at least one attempt at this.)
Current project could maybe benefit from TypeScript, and certainly async/await, but still wonder if it's less of a hassle to just wait for wider support.
(Of course if yc ever decides to fund our small startup it should know that we are a team of forward thinking progressive individuals who will use the best and most robust tools available to us, who's views i do not necessarily represent)
WASM is supposed to be first class citizen so I don't see any reason why it shouldn't have access to the DOM or any other browser feature available to JS.
Is that correct? WASM has no DOM access? (I'm asking, not advocating anything.) How does code that runs in a browser do UI I/O without DOM access? Is the intent that you go on writing all of your I/O and DOM-manipulating code with JavaScript and call WASM-implemented helper functions from JS code?
I use buble. It transpiles ES6 to ES5 2.5 times faster than babel on average. But be aware that buble is still a work in progress and only supports a subset of ES6 features. A very usable subset, but a subset nonetheless.
And has it progress it will be slower to handle the most complex cases and follow the spec, than they will use a plugin architecture to let users develop their own language extension and modularize it, than they will only have to rename it to Babel because it won't be different.
Because a lot of notable ReactJS projects are irritatingly enamored with all the latest ES6/ES7/ESCloudCuckooLand features, not all of which are supported by TypeScript.
I've noticed this a lot in the Redux realm. For every possible problem there seems to be a solution that harnesses one particular new/proposed bell & whistle.
My opinion is that all the extensions on JavaScript should be implemented as Babel plugins, including Typescript. That would solve all the compatibility problems. Well, when Babel first came out I also thought that it should have been a Sweet.js plugin so maybe I don't have the best understanding of this "transpiling" circus.
It's tempting to think this way, but it's a performance/complexity nightmare. If everything is a plugin, then you need ways for different parsers to talk to each other to deal with nested syntax, plus ways for different syntactic transformers to correctly handle nesting of certain things.
For example, if you desired to implement a plugin for "thin arrows", and a plugin for JSX, how would you parse this?
const x = <foo x = {y -> <y/> } />
You'd have to have the JSX parser know to invoke the thin arrow parser, then the thin arrow parser has to know how to invoke the JSX parser, then when you emit, you have to do the whole dance over again.
If you're willing to take some trade-offs in the parsing phase, it's OK. But the emit is where you get killed - either every plugin has to be written generically and correctly enough to deal with any arbitrary nesting of syntaxes (including the cases where the semantics of nesting aren't even clear, like where a 'fat' arrow here would capture 'this' from), or you do one tree pass per transformer, which gets very expensive.
There's a reason you don't usually see architectures like that live very long.
Well, this is not the first time that a comment on HN not only made me change my opinion but also taught me something. Thank you for the detailed answer.
Maybe the specific example you give can be solved in a very hacky way with something like a priority system but I can see how messy it can get even when tokenizing the possible expressions for such an open "playground", let alone transforming in the correct sequence.
Thank you, Ryan.
edit: Oh you are the person who implemented JSX support for Typescript! How do we buy you a beer, or in this case a six-pack?
Aren't the Babel people trying to define a common standard format for the AST so different parsers and code generators can better work together?
That said, if you look at TS as a superset of Babel plugins, there's actually not much to TS that is TS-specific. Adding that to Babel would be relatively simple.
You seem to be arguing it's a slippery slope. We're not talking about arbitrary syntax. We're talking about a fairly well-established syntax extension backed by Google and Microsoft. It doesn't have to perfectly universal and generic to support TS.
EDIT: If you were specifically addressing the parent: yes, if every syntax extension was created as a parser plugin, getting them to work together would be messy, but that's basically what we have in PostCSS isn't it? Plugins explicitly instructing users "this conflicts with X, please add it after Y but before Z" -- which is fine IMO as you only need to care about the most popular ones and everybody else knows their stack is experimental.
Babel itself demonstrates the truth of this. If you look at the source code for any of Babel's syntax plugins, they are literally only a few lines long, because all they do is activate a feature that is actually part of the parser core.
(This is not disagreement with RyanCavanaugh; it's a question for expansion by the community.)
It seems like Perl 6 is trying to implement pluggable grammars that work like that. Can anyone here familiar with the Perl 6 ecosystem comment on how it's going over there? Can you feasibly write a module with 5 or 6 different grammar extensions? What's it like? My understanding of the situation has matched what RyanCavanaugh expressed here for a while, and I'm curious if people's experiences match it or not.
>My opinion is that all the extensions on JavaScript should be implemented as Babel plugins, including Typescript. That would solve all the compatibility problems.
Then we'll have the Babel problem. E.g. how they handled 2 to 3 transition doesn't inspire confidence.
If you read the initial part of the comment I took that remark from:
> A big factor in my company recently switching to TypeScript was Windows performance, even with the recent massive advancements for Flow on Windows it's still painful to use and the tooling is miles behind.
As far as I've seen, it's really only Object spread (likely ES2017 feature) that's commonly used that is not yet supported by TypeScript. Microsoft has promised support for it in TS 2.1, and generally stays on top of ECMAScript proposals that have gained enough traction that they seem likely to ship.
On the other hand, Flow is removed from the code transformation, so it doesn't have to bother with keeping up with the spec. That's a pretty strong point in Flow's favor in my opinion, single responsibility principle and all that :)
It's still early, but it makes Rx code much easier to read. So long as you're comfortable using Babel for transpilation, it doesn't really matter whether or not it's TC39-approved.
It'll matter in 3 years when you have an app that's full of rejected ideas.
That's the problem I have with the Babel-everything mentality of a lot of developers, they don't realize that they are essentially created their own quasi-language that they'll have to support on their own.
TypeScript is a PITA when working with typed immutable records, I don't think there will be a happy solution to that. React stack encourages stuff like immutable.js. In general TS React feels bolted on rather than designed with TS in mind like Angular 2.
I love TS and using ng2 at work. If I was using React I would probably also skip on TS.
Immutable.js (https://facebook.github.io/immutable-js/) doesn't have the greatest typescript type annotations. Due to limitations of TypeScript, there is no way to write types for immutable.js heterogenous maps (homogenous Maps and Vectors are fine though). Since immutable.js collections are recommended to be used with redux, and no one wants to bother using IMJS records instead of just maps, the types end up being kinda useless.
A nice typescript-friendly alternative to redux+immutablejs is MobX (https://mobxjs.github.io/mobx/getting-started.html). It does go a bit against the latest cool and hip trends (immutability, functional programming), but IMO its quite brilliant
+1 for MobX being quite brilliant. So much fun to write an app with. Not saying it is the best solution for every case but if you work with React, you really owe it to yourself to try it.
Its not just TypeScript's fault though. Its not impossible to design an immutable library which has an API that can be properly typed with TypeScript, e.g. https://goo.gl/7tAIuq
Functional programming is quite old and I wouldn't call it a trend. I'd say it's more like an industry getting better at its craft, similar to the transition toward strong typing.
I think I would rather do future "systems level" work in Rust than C, but I'm not sure it would eliminate the desire for automatic memory management in a casual or "ENTERPRISE!!!" (... no intelligent life here, Scottie) app :-)
I haven't used Rust enough to comment myself, but other people have said that Rust essentially does have "automatic" memory management (in the sense that you must manage the memory in order to get your program to compile). People say it works most of the time, at least. Rust is trying to make that as painless as possible, so it'll be interesting to see how painless it really is.
I feel like TypeScript needs some work in areas around typing methods - for example, I ran into type issues when trying to go more functional via ramda.js (http://ramdajs.com/) using stuff like compose, and ultimately it felt like a limitation of TypeScript.
Ramda is pretty cool. It's also a really good introduction to use-cases for partial function application ("currying"), vs silly "adder" examples. (think of partial function application as dependency injection for FP)
Hmm. I find that classes and subclasses aren't all that useful, now that I can use higher order functions :-)
(I still use classes/objects for services with multiple related operations or polymorphism, but not for one trick pony "Executioners" for which Java would use a lambda -- which is what ES6 arrow funcs look like)
There was a comment on the original thread linked here about TS 2.1 likely getting support for "partial objects" that will help with both Redux and Immutable Records.
The main reason for using Babel was async/await. However, the lastest TypeScript verion (typescript@next) can compile async/await for older browsers, so there is no reason for me to use Babel anymore.
As great as TypeScript is for enforcing certain guidelines for your own code, it does not provide much in terms of supplying polyfills so certain browsers can support some ES5/ES6 features. If you're working with the cutting edge of browsers it shouldn't be a problem, but if you need to go back a couple of years, you either need that or at the very least core-js.
Even the ECMAScript feature table (https://kangax.github.io/compat-table/es6/) uses Babel and TS with core-js when comparing features, otherwise it'd be heavily browser dependent.
Speaking as the person who implemented JSX support for TypeScript, I question the premise! JSX support (and implementation of React semantics for typechecking that JSX) was a very popular feature request. I can tell you just from how quickly people notice when something JSX-related changes in the nightly build that there are a lot of people using TypeScript with React.
Also, since this seem to be a popular misconception, JSX support in TypeScript is not wedded to React. The default JSX target is React, but you can set JSX to "preserve" and get very vanilla semantics as well as keeping the JSX in the emitted code so you can pipe it through a custom transformer.
The question also points out that the reader is looking at lots of tutorials -- it should be unsurprising that these don't use TypeScript as it's an optional thing that would only increase the concept count in an educational setting where you want to only show the thing you're trying to explain.
> It would only increase the concept count in an educational setting where you want to only show the thing you're trying to explain.
As someone who has written a long tutorial, this makes total sense. When I was first looking at the react ecosystem, it was very frustrating because of the high cost of picking pieces to work together. I really liked http://teropa.info/blog/2015/09/10/full-stack-redux-tutorial... because it showed how to use mocha in the context of we webpack and react and redux.
It would be nice to see more tutorials for curated toolchains, but they take a lot of work.
This is basically my frustration with the whole trend toward smaller pieces over big monoliths. I don't need a best-in-class every tiny little thing; I just want reasonable tools I can expect to work together well.
The other nice thing is that bigger monoliths often (not always) make opinionated decisions. This is usually a good thing.
In my work I deal with a legacy system with an ExtJS GUI. The two ways that ExtJS fails to be opinionated are perpetual pain points for me and my team! One is: every component has a million optional configurations, not to mention all of the events you can listen on. For the most part this is great, but there was never any systematic separation for "here are the absolutely-required things, there are the things which are optional but must be configured together, and over yonder are the things which are totally optional." Then you could require that the required-configs were, say, statically known when you were deriving a concrete class from an abstract one. Instead ExtJS wanted to accept doing all of this stuff at runtime, so because it failed to take a strong stand on its required configs, when you inevitably forget to configure some of them, you get an error puked out from somewhere very deep in the framework, where the call-stack and error messages show nothing related to your class at all, just "TypeError: SomethingYouNeverCaredAbout is null." It would have all been saved if `Ext.define` looked for some "abstractProperties" array, and made sure that every new `Ext.define` either set abstract properties or propagated them, finally checking that whichever ones are still present in the `Ext.create` call are filled in. Simple descriptive error messages are then available when you forget a required config.
The other way ExtJS violates the principle is... God help you if you ever have to figure out how the underlying form submits and grid reloads actually work. You'd think with something so critical, it would be clear... it's not.
"My grid refreshes automatically when the underlying store loads. Great! The underlying store can be loaded or reloaded with the .load() method, which accepts a callback. Wonderful!" It starts off very promising. But then you dig deeper and find that the .load() method packages the params and the callback into some object and then calls some .read() method which doesn't exist on the class you're looking at (inheritance! go up to the superclass!). Once you've traced that down the actual .read() bounces to some .doAction() which repackages these into some `Operation{type: 'readAction'}` or whatever... and then this gets handed up to some Proxy object which then stores it in some meaningless array, because of course these things get batched together... if you're not sick yet you find out that the Proxy needs to push the stuff to some Reader and Writer, just in case you wanted to communicate with the server via XML instead of JSON, or wanted to store the resulting array under a key not named 'results'. But you don't want to do any of this because the query finally gets XMLHttpRequested somehow (God knows how) to some `router.php` which we stole from IBM[1] a long time ago, which finally took a stand, "I will accept these two inputs, send them to the backend this way, and emit one of two corresponding outputs." (Except for that then you open that and it contains code for some sort of `doAroundCalls` because apparently the original author[2] decided to vacillate on what they'd accept, trying to also allow you to bookend one RPC service with two other RPC services, which never happens because Ext.JS never does it!) It gets a little more complicated because there is one rather significant bug which nobody has ever fixed in IBM's router.php, which is that formHandler services get the $_POST params (an associative array) as their first argument whereas XMLHttpRequests get the `json_decode($HTTP_RAW_POST_DATA)` (a StdClass object) as their first argument, so there's no interoperability on the frontend or the backend. Happy debugging, you. It's all one big mess.
You begin to wish ExtJS had done what they eventually ended up doing[3], ...
The JS build system ecosystem could definitely use some help along the whole "reasonable tools I can expect to work together well" front. I swear, 30% of my time is spent fighting the build systems and their plugins that hate each other.
EDIT: to add, I think the TS team has done such a bangup job on Typescript that I would love it if they could create a build system as well. Some things that would be nice to have:
* Build-time loading of static resources (.json into js objects, html into strings, etc.)
* File watching and processing for more than just .ts/.js files
* Optimization. Not just tree-shaking and minification, but you could actually get a little more advanced due to the static types and ES6 modules.
* Environment-dependent compilation (compile these files in this way, inserting these static values where ENV variables are used in the source, etc.)
* Target capabilities analysis (ie. for this set of browsers and versions, what is the Lowest Common Denominator for browser capabilities, and ergo, what babel transforms and browser shims should be included?)
* Integrated contracts testing with test elision (ie. run these tests in these (karma? selenium?) environments and if failing, throw a compilation error or warning, and if passing, strip the tests from the compiled source).
* Source packaging (gzipping, etc.), and deployment plugins (ie. deploy compiled assets to S3, package for NPM, etc.).
All of these are pain points in Typescript projects, and all of them touch TS projects in such a way that it makes it even more painful in existing build systems.
I find webpack to be quite a 'holistic' solution I got pretty much everything out of the box or with minimal googling.
I agree though over-fragmentation is a huge problem for JS, we need the big players (either foundations or companies) to put their weight behind one or two solutions and just get on with it :-)
Google sort of already has one, and has for a long time.
Now that their Closure Compiler supports ES6 quite well, I've had a decent amount of success writing my app using straightforward ES6 and referencing the extensive Closure Library for functionality I would've previously pulled in npm packages for.
And the nice thing is that the whole library is written in such a way that all of the compiler's advanced optimizations and branch pruning, and dead code elimination work nicely on it so your compiled JS ends up containing only the code you need, and none of the code your don't need. If you want to use JSX in React projects, you can still zip the code through Babel or Typescript before feeding it to Closure.
It certainly won't work for every project, but it's one way to write modern JS without having to deal with the node/npm ecosystem too much...at least until things settle down a bit.
As someone who uses both stacks regularly, on different projects:
More people should consider using Angular 2 for some kinds of projects.
Now, I have professional projects in both Angular 2 and React/Redux ecosystems, and frankly I enjoy using React a lot more in projects where I can focus on the frontend. I moved some projects to isomorphic React (ie, render using React on backend) in Node.js and Rails apps, and thoroughly enjoyed that experience. I keep on top of Elm and omnext and so forth, and I have personal projects built with those, and I do experiments with completely unidirectional dataflow in Elm using an Elixir backend ...
However.
Twice recently, when I had a full-stack project with a relatively short timeline, I made a conscious decision to keep the frontend from getting too uppity and absorbing too much of my mental energy.
In those cases, I used Angular 2, generated from the ng2 CLI.
It's worked pretty well. Well, the first one had some dependency issues from time to time, which is understandable because of the beta -> rc1 -> rcX -> Angular2 release process that was happening.
Why ng2? Well ... not because I'm convinced that it's "the best" in any particular dimension. Its special sauce is supposed to be Zones, which make knowing when side-effects have occurred less something that we have to track and manage manually, but there's other work in that problem space!
I used it because it's an opinionated stack that already has the important pieces in place (router, DI, build/minify, type checking, components), and more importantly, because I can be fairly confident that another dev could get up to speed quickly due to decent docs and guides ... and it's less easy for someone to "paint themselves into a corner" by doing things really wrong.
This was exactly my thought and I was so glad when I saw this talk[1] address it.
On a side note, I had submitted this to HN but somehow my submissions are visible only to me and doesn't appear when I checked the newest tab after logging out.
tsx refactoring and type checking is mind blowingly awesome. This feature alone makes me choose tsx over angular templates. angular templates are very loose and no property way of type checking it. I've seen some terrible mistakes in angular templates when refactoring.
Practially not, but it's a bit of a hassle. either you leave the JSX be and parse it with Babel or you need some wrappers for you VDOM lib, because tsc assumes a namespace, while most not-React-vdom libs just deliver a function out of the box.
> JSX support in TypeScript is not wedded to React.
Agreed. Here's an example of JSX in TypeScript that has nothing to do with React. UI Builder is a templating library, just like Mustache, but much better because you get full intellisense and compile-time checking for the template:
Thanks for implementing this! I was a bit standoffish at first but after several attempts to implement my own typed-templates[1], I found JSX to be very nice to work with because type safety in templates is hard to come by.
If anyone is interested, I have a working boiler plate with React Server rendering using TypeScript[2].
I don't feel the posts answer the question, they are more ads to Typescript or Flow. Unsurprisingly the people who answer are the one who use TS or Flow.
So I tried a little to convert a big React project to Flow or Typescript. The Flow was a non-starter because of the absence of Windows support at the time, and we use like 40 (non dev) dependencies, and Typescript has a way better support for typings, I tried Flow on a mac it was chocking on the size of the node_modules or couldn't find the app modules because we use a webpack root dir (i don't tried hard to make it work).
When the app was started Typescript didn't support React so it wasn't written in a "static" way, and accumulated a lot of dynamic idioms, also the backbone of the app is a dynamically generated schema based on XSD and that would be hard to make it compatible with TS type system, also React ecosystem doesn't really use it, leading to a chicken/egg problem, and React.PropTypes is already a form of type checking (but dynamic) so it probably lessen the feeling of a need of static typing in React ecosystem.
I do not believe compilation nor a type system belong in JavaScript. It's better to have something like "Flow" that does static analysis of the code as you write.
I might even go as far as putting on a "tin foil hat" and state that Typescript is a trick to lock you into their proprietary ecosystem of expensive tools that everyone have to buy into just to communicate with you once you are locked in.
I only see advantages for static typing for a small cost of time: you prevent most of Type Error from happening, you get automatic auto-completion, refactoring errors are easier to catch and feel safer. Either way, you need to specify the type of the arguments in the documentation of your function (I can sometimes even find the C# LINQ's function I'm looking for just by looking at the return type of the list of function).
You could even use Flow and Typescript to catch
Aside from the proprietary reasons (which I believe are unfounded since the whole Typescript ecosystem is opensource), why do you think static typing doesn't belong in Javascript ?
Because JavaScript has semantic types like List, Date, Number, String, Boolean, witch can easily be figured out by their context, like age is a number, name is a a string, married is a boolean, children is a list, born is a date, and adding type declarations are unnecessary, witch would only add extra cognitive load to the programmer. It's possible to be an productive JavaScript programmer without even knowing about types and how they are implemented.
If the programmer however makes a mistake, like concatenating name and age, it will be caught during runtime, manually testing, automatic testing, runtime testing, or real time static analysis, or all of these five.
Being able to concatenate and mix types like number and string is also a language feature that avoids a lot of boilerplate code.
My team is 'locked' into TS on a large project. We have yet to purchase any TS related tooling, and have no plans or need to do so. Given that TS transpiles to JS, I'm unsure as to how any project can be truly 'locked' into the ecosystem. I'm really unsure what you are basing your fears upon.
It's not just that it transpiles into JS, if you target ES6 pretty much all tsc does besides validation is stripping type information, access modifiers etc. while basically preserving the code structure, including whitespace. Which means that if you ever want to migrate away from TypeScript you simply run tsc one last time and then you'll have a fairly usable JS codebase.
> It's better to have something like "Flow" that does static analysis of the code as you write.
What do you think is the advantage of such a thing? IME they tend to end up as an ad hoc, informally-specified, bug-ridden, slow implementation of half of a type system.
> I might even go as far as putting on a "tin foil hat" and state that Typescript is a trick to lock you into their proprietary ecosystem of expensive tools that everyone have to buy into just to communicate with you once you are locked in.
https://github.com/Microsoft/TypeScript is uh... right there. Check the license. Visual Studio code runs Textmate snippets and has a very sublime-like extension system.
I've been very happy using Typescript with React, and have found the productivity and code quality gains to be remarkable compared to the relatively small amount of change required to use it vs. plain JS.
Indeed there are some pain points as mentioned in the article, e.g. typing Redux actions can be a bit boilerplatey, and there's currently no object spread operator; but I feel it's worth the trade off - you can always opt out of typing something (e.g. with the "any" type), but I've always found that the places where you do this are the places where the bugs creep in!
I actually prefer Flow's approach of being just annotations which can be stripped out, rather than a new language (albeit a superset of Javascript) with its own features and compiler - for one, I find this makes it an easier sell to teams worried about "lock in". However, there is a bit of FUD around this IMO, as you can use just the subset of Typescript which adds types to JS and avoid stuff like "enum" and the "class" enhancements - in my experience, TS's types can be stripped by Babel in the same way as it strips Flow's, so actually if you ignore the `.ts` extension, there's not such a big difference.
The problem is that every time I've tried Flow (including very recently spending several days trying to convert an existing medium size React project to it), I've hit so many random undocumented issues, and ended up feeling that the benefits of it were outweighed by the amount of effort required to get it working properly. This is especially true because the editor experience offered by Nuclide is (again, in my experience) sub-par and buggy compared to VS Code (or the Typescript Sublime plugin), and I've always felt the editor support is actually one of the big selling points of working with "typed JS".
I am really looking forward to seeing how Flow progresses, as in an ideal world it is what I would use, but for now (in a commercial situation especially), I have to go with what I feel brings the biggest productivity/code quality benefits and the best developer experience for the team, and for now I still think that is Typescript by a fair distance.
I was always wondering why HN crowd is ok with TS and so prejudiced against Dart - Dart has NG2, await async in older browsers and good tooling (webstorm, vscode) and much saner package system. When doing lot of small web apps - it's easier to mantain.
At least in my view, there's a couple of big things: Dart doesn't introduce that many advantages over JS for all of its differences, and TS introduces many of them with a smaller diff; there's also the presentation of it—Dart was originally presented as a wholesale replacement of Dart, to ship in all browsers, the language more or less as a fait accompli, which rubs plenty of people the wrong way.
> Dart doesn't introduce that many advantages over JS for all of its differences
As someone with experience in both languages, I could not disagree more.
> Dart was originally presented as a wholesale replacement of Dart
I think you meant replacement of JS here. I guess it depends entirely on what you think of JS as a language. I, for one, would rather a language that fixes core issues with JS, instead of just being a superset of JS.
> I think you meant replacement of JS here. I guess it depends entirely on what you think of JS as a language. I, for one, would rather a language that fixes core issues with JS, instead of just being a superset of JS.
If I were aiming to replace JS, I'd fix what Dart does, but I wouldn't stop with merely fixing what Dart does.
Dart, despite being an entirely new language, has a less expressive type system than TS. It's transpiler (and it's VM) also does no optimisation based on the type system, instead heavily relying on the JIT to infer what the types already imply (e.g., it would be nice to do things like LICM at compile-time).
As for the rest of your comment, I'm with ya. I guess they're reasoning behind that was they thought a lot of development would start out untyped with additional types added as development progressed. I think that assumption didn't pan out, at least that's not how I do it.
"Q. But don’t you need sound typing information to get high performance?
Sound types can help with performance but aren’t essential. What we need are uniform, simple semantics. Modern VMs can use actual runtime behavior as a valuable signal for optimizations."
Typescript also has structural types, like Go and OCaml, which many people find nicer than nominal types. Structural types mean if I have an interface Blaz with two methods Foo and Bar, if I have an object MyObject with Foo and Bar methods of the same types then my object counts as a Blaz, while nominal types mean I have to write something like MyObject extends Blaz.
That's how dart2js works today but the goal for Dart 2.0 is to move to a sound type system. The beginning of this is available today as "strong mode" and the Dart Dev Compiler.
What do you mean "fait accompli"? Was the Dart team supposed to give the community a chance to abort the language from existing, and the community was upset that it was completed and published without the input of people who wanted it not to be?
>Was the Dart team supposed to give the community a chance to abort the language from existing
No, he means that the Dart team was supposed to solicitate opinions on how to build Dart and what the best objectives for it would be, but instead they showcased it in "almost done" form, and only then tried to attract a community.
This. While yes, it was a long way from "standardised" and a lot changed between what Google initially published and the Ecma standard, many fundamental design decisions were made internally and there was never any real influence externally over that. Those are fundamental design decisions where to change them you essentially need to start from scratch.
The other big problem was that it was done with the VM being a major part of the project with the intent of getting it into Chrome, obviously without having talked that much with several of the people who have significant influence over such things in (then) WebKit, even those within Google. That the VM was going to be outright objected was entirely predictable.
Your view seems to be from someone who hasn't used Dart extensively, because no one who had would minimize its advantages this way. Being different from JS is the whole point. Dart introduces all the advantages of TS and more, while leaving the baggage and bullshit of JS behind.
It puzzles me also. Dart is solid language with great libraries, good tooling and still it is ignored by most developers. The truth is people from JS world seems to like 'cool' languages, but the one who want to be productive just uses boring Java/Dart etc.
I want to give Dart a chance, because most of it's features seem quite appealing. I decided to start learning JS/Jquery and then move onto to Dart. The fact that everything comes bundled into Dart as a whole dev environment (IDE, compiling,packaging,) and the interoperability with JS make it quite attractive.
What is your experience doing web dev with and without Dart (JS vs Dart, pros and cons)? I'd be really interested in your feedback!
I started off with C/C++, Java, then AS3 writing Flash games. Then js/jquery and I instantly hated it (js). There were just too many quirks, bizarre, unexpected behavior. Sure, I could learn it inside out and avoid these pitfalls, but why would I when there were better alternatives?
I did use CoffeeScript after that, a beautiful little language, but only suitable for smallish projects. I need static typing for large projects.
After that, I learned Dart, and coming from C/C++, Java, AS3, it was a breeze. I find there are no quirks, everything behaves as you'd expect. Other team members were productive in Dart in about a week, without having seen a line of Dart code.
I mostly write HTML5 games and server-side with Dart, so I can't really talk too much about any client-side frameworks.
As for Dart cons, I guess one would be you have to use a different browser for web dev, but it's not really a big deal, I'm kinda reaching here. There aren't as many 3rd party libraries as some other languages. Depending on what you want, you might have to get your hands dirty and issue some pull requests for features/bug fixes for those libs. JS interop can still be a bit tricky too, depending on what you're doing.
I'm going to try it on my Linux box. The only disadvantage I can see for my eventual needs after a second reading is the lack of 3D support. I can get by with 2D for most of my stuff, but for games, I need the 3D hook.
I'll have to see how easy it is to customize the Dart-provided widgets. Might be easier than creating them from scratch in OpenGL via the NDK.
TS seemed more willing to interoperate with the rest of the JS ecosystem - gradual typing, external .d.ts files for popular libraries, working with existing build tools and module systems. Whereas Dart felt like more of a gated community where you were expected to do things the Dart way and there wasn't much support for traditional JS.
> working with existing build tools and module systems
I'd say they replaced it with a better tool, pub.
The one good argument you have there is .d.ts files. Dart lacks them, but there are tools to generate js bindings from those same .d.ts files.
https://github.com/jirkadanek/definitely_typed
I haven't used it though, so I can't say if it works as advertised.
> I'd say they replaced it with a better tool, pub.
Right but that route ends in forcing people to leap to a whole different ecosystem before they can even try your thing. Whereas with typescript you could put a single .ts file in your existing project without messing with anything else.
I consider the small hop to TS its greatest disadvantage, personally. JS's ecosystem is a horribly broken mess, and any sane person would welcome a leap to another, better designed one. Dart has JS-interoperability for those times when you just can't get away, but TS is like an anchor holding you down in the mire of the JS world.
What's awesome about `pub`? If you're talking to someone like me who uses `npm`, `webpack`, and is now considering `rollup` ... what am I missing if I don't look at `pub`?
Sorry for my ignorance, but does that amount to loading a library on demand? If so, yes, Dart can do this:
import 'package:deferred/hello.dart' deferred as hello;
// When you need the library, invoke loadLibrary() using the library’s identifier.
greet() async {
await hello.loadLibrary();
hello.printGreeting();
}
Dart is not structurally typed and so only provides help typing the parts of your program you have actually modified to use Dart. TS and Flow both provide structural typing that makes it far easier to convert existing code. Just annotate it (no need to even modify the existing code, just plop a `.d.ts` or `.flow` file in the right place) and immediately start to see benefits.
TS is more of an evolution of what exists. In that sense it's a possible "future" implementation of JavaScript -- still keeping the same semantics, but in a more structured way.
Dart is a different language so it's a different path. It's no different than, say, using C# or Java or C or whatever language that can be transpiled to JavaScript.
I've been a long time fan of Dart but I've recently (this week) given up on it for my purposes, which are write browser SPA's that need to run in different browsers. My sense is that after the Chrome team decided not to include the Dart VM in Chrome, Dart started looking for a new story. That story is Flutter, which is Dart running in the Dart VM on mobile devices [1] It is not Dart converted to JavaScript so it can run in any browser, despite the awesome work of the dart2js authors and the relatively new dev_compiler project [2]. The latter will be awesome when done, because the goal is to convert Dart to ES6/ES2015. However, it is my impression that Google really doesn't care that much about transpiling Dart to JavaScript. I was willing to put up with the huge file size dart2js produced, because Dart made my life easier and something better was coming. However, it's been a long time and the pace of Dart transpiling work is too slow. I converted my Dart app to TypeScript (size dropped from 650kb to 60 kb) and am happy for that, but sad that Google does not put more people on the dev_compiler team to keep long term enthusiasts like me on board. I'm sure Flutter is fantastic and will take a look when I have a need for that kind of solution. I can't really blame Google, because the JavaScript community turned it's back on Dart, but I wish they would just state the new goals and not leave us hanging.
I would have switched to typescript but I had to rename EVERYTHING from something to something else in order to use TypeScript. If that's how "compatible" starts, well, no thanks cause clearly that's just the start of the pain.
Compatible should be same files, new compiler = "just works".
Please don't bury this comment completely. I am going to be honest and tell you that I believe TypeScript is pure embrace, extend, extinguish from Microsoft. And I am amazed honestly that so many web developers are eating it up.
I would shed no tears if JS were extinguished. It's a terrible mongrel language that is not well suited for large projects. TS is a tremendous improvement, if you ask me.
EEE refers to the times when Microsoft would take an open standard--say HTML, or JavaScript, back when IE3 was actually the best browser on the market--shove in their own, proprietary, backwards-incompatible extensions, and keep calling it the same thing as the open standard.
But MS makes it very clear that TypeScript is a different language. It helps a lot that they don't even have the same name, y'know. Also, it's a system for specifically staying backwards compatible with open-standard JavaScript. Using TypeScript does not replace JavaScript. It supplements it.
Strangely enough, I'd feel this would be fine. I would pay for a non-free upgrade of VSCode if it really brings in enough value. Its already on par with Sublime, and I paid for that...
edit: Though if you mean TypeScript depending on VSCode to build, I doubt thats even possible at this point. Everything is available via the command line. Heck, there are even tools that build on top of the compiler API. (dts-generator, tslint etc)
Well not that it won't compile without VS, but maybe as a vehicle to for the occasional new feature that just doesn't work quite right on Mac, one drive hosted git tie in's, I dunno but their up to something.
Let's say that tomorrow, Microsoft releases a totally-backwards-incompatible build of Typescript, and starts charging for it.
My "way out" of the Typescript ecosystem is:
1.) Change the target to "ES6", and run a compile.
2.) Take those files and use them as my new source files.
3.) Remove Typescript from my build pipeline.
Its interesting that on one hand, we have this shouting "embrace, extend, extinguish!" directed at TypeScript, and on the other, Facebook with Flow and Babel is doing precisely that: its extending JS with their own type system, adding support for said type annotations to Babel (which is still thought of as the es.next -> es.current compiler) and still calling it JavaScript; or at least, muddying the waters (no extension change).
Strangely, it appears to work. I've seen claims that Flow is better because "its just JavaScript, not another language"
Considering it is open source, this would be the death of the project for them. Someone would fork it and keep it at a specific version, maybe with community additions. Existing projects could just keep on using it at that version, or move on to ES6 equivalents with little change.
I like to use TypeScript with ReactJS.
And I was surprised to see some mainstream libraries using it: mobx, apollo stack.
And it is also a surprise to see really well updated typings for a lot of things in the react world.
Anecdotally, at Bloomberg we're in the middle of ramping up TypeScript support in our core server-side stack. Our custom IDE is Windows based, so it was very straightforward to integrate the tserver into the workflow to give developers the choice of writing vanilla JS or TS with additional annotations we send down to the IDE for the core stack. We have the largest single collection of JS I'm aware of and we're eager to see TS take off as we iron out a few corner cases and really get 2,000+ devs using it daily. This isn't the web or Node, so make of it what you will -- but the tserver integration and ease of layering on top of the existing vanilla JS in a progressive manner made it a simple decision.
We started using server-side JS around 2005 so things were a bit different back then. The main driving force for it was that we had to have WYSIWYG integration with the product and the only way we could achieve that was by embedding an HWND from the running product to ensure it wasn't some faked runtime that would behave slightly differently during development / in production.
That sounds really interesting. Could you give more details about your adoption plan? Which version of TS are you using? Are you planning to migrate to TS 2.0, when it comes out? In your experience so far, have the conversion done until now caught any bugs?
If I'm remembering correctly it first went live to some early adopters with 1.6.1 and it is using 1.8 now. We obviously want to track the latest releases as fast as we can because they bring new features we're interested in.
I would need to ask some of the teams that tried converting larger projects specifically what they found that they felt was important. I'm certain TS would find some bugs in any sufficiently large project, but I'd have to go dig up data to know roughly how many or how serious they were. Just because there was a technical quality issue with the code doesn't mean that the vanilla JS version of it wasn't producing the actual desired result. It's hard to gather numbers for that type of thing. It's very similar to the let-down a lot of people feel with using static analyzers on mature, battle-tested C++ code for the first time. It will certainly find some nits, but most likely they were not that important to begin with.
I do TypeScript every day for work, and honestly I don't see the point of it. I'm also of the opinion that the iterator pattern nonsense has ruined generated code quality for ES6 transpilers, and that ES5 getters and setters have made it considerably harder for JS engines to do high level optimizations (dead store elimination, invariant hoisting, load merging, etc.).
The sky is falling.
Anyway, you're not going to dissuade anyone. TypeScript looks visually similar to Java and C# enough that managers will think they can adapt Java and C# teams to it in a couple of days; and they won't know how wrong they are until a month or two have passed.
What do you mean? It's the typescript compiler that catches your errors. The IDE stuff is nice to have, but it's not the main benefit typescript adds to refactoring. Typescript doesn't rely on an IDE.
Apologies, as I am going to make a few assumptions.
If you write fewer classes and class hierarchies, and use higher order functions (see also - partial function application), you will have much less "refactoring" to do - often, simply small changes such as to increase the visible scope of a function you now want to reuse elsewhere, or to "pre bind" another argument to a function so the caller(s) don't need to know a particular detail.
This probably has a lot to do with why the static OOP people think the dynamic FP people are insane: they have no idea how we really work.
We have garbage collectors and closures now. Stop writing code as if in some crippled version of Simula 67 :-)
Assuming things about people from internet comments is usually rude, but I agree. From my experience a lot of the people that don't "get the point" of TypeScript or Flow haven't worked in largue applications that needed maintaining. I'm sure there are good arguments against them for large applications, but I'd need to hear them from people who've maintained (not just written!) a lot of large JavaScript applications. Your average React or Angular frontend probably doesn't count.
Babel has faltered since the V6 release, TypeScript is still growing fast, so I'd expect the React world to follow suite, even if Facebook itself pushes Flow...
NPM downloads in August (rounded):
typescript: 2,000,000
babel: 620,000 (down from 890,000 in November 2015)
flow-bin: 120,000
Well, the V6 release made babel modular, so the babel package is no longer the right one to compare against. Look at babel-runtime: 4,600,000 or babel-core: 4,300,000 vs typescript: 2,100,000.
It's irrationally irritating that September's incomplete stats are graphed incorrectly. Guess I need more coffee before dealing with JS in the morning.
TypeScript works very well with React, less so with Redux/ImmutableJS.
We just moved our app from Redux and ImmutableJS to mobx and it's been a treat: we now get full typing and it's much less verbose. We don't need to repeat the payload definition at every point, we have a store where we call a method and that's it. Highly recommend checking out mobx if you use TS.
I've been using Typescript, React, and mobx and absolutely in love with how they all work together. For me the high-level summary is that the vast majority of my logic is moved out of React views and into stores / controllers / whatever, with almost no boilerplate to make them play nicely together. The way its coming along reminds me of Ember quite a bit, but I get to use React and POJO's.
I definitely want to look into mobx now. Just thought I would throw out there that I've been using Nuclear-js/Immutable.js and it has a lot of the benefits you mentioned. All the data manipulation logic is encapsulated nicely, and merely appears as state to your components. You can observe memoized transforms in your components so that they only need to listen for the data they need, rather than a single change event on an entire store.
I've been using Typescript, React, and mobx and absolutely in love with how they all work together. For me the high-level summary is that the vast majority of my logic is moved out of React views and into stores / controllers / whatever, with almost no boilerplate to make them play nicely together. The way its coming along reminds me of Ember quite a bit, but I get to use React and POJO's.
Because freedom? Typescript is a superset of JavaScript, which means all JavaScript is valid typescript. So you're never faced with the difficult choice of locking yourself to one language/platform. JavaScript is awesome, it just doesn't scale to large projects because you cannot efficiently refactor it. Typescript solves this problem beautifully. You can easily add whatever type information you need to effectively work with the codebase, whilst being compatible with all JavaScript libraries and the ecosystem.
Does that include ES6 ? What parts of JS do they consider a subset of typescript ? Can i keep my type declarations in a different file than my .js code like flow does ? (thus ensuring compatibility while keeping the functionality of typescript)
How far can i go with typescript until i need to use babel ?
246 comments
[ 5.4 ms ] story [ 116 ms ] threadI think this has been fixed now. But a couple of weeks ago, I had a case where TS compiler output has to be ES6 (since the code base were using something like constructor.name which isn't in ES5), but then Jest (the test framework) doesn't like ES6 syntax, so Babel is needed to compile whatever Jest didn't like down to just ES5 syntax.
Current project could maybe benefit from TypeScript, and certainly async/await, but still wonder if it's less of a hassle to just wait for wider support.
grumble grumble grumble
(Of course if yc ever decides to fund our small startup it should know that we are a team of forward thinking progressive individuals who will use the best and most robust tools available to us, who's views i do not necessarily represent)
[1]: https://buble.surge.sh
I've noticed this a lot in the Redux realm. For every possible problem there seems to be a solution that harnesses one particular new/proposed bell & whistle.
Many React projects use JSX, decorators and class properties to the max, so they needed babel in the first place.
Now if you want to add types, Flow is easier to integrate than switching to another compiler.
For example, if you desired to implement a plugin for "thin arrows", and a plugin for JSX, how would you parse this?
const x = <foo x = {y -> <y/> } />
You'd have to have the JSX parser know to invoke the thin arrow parser, then the thin arrow parser has to know how to invoke the JSX parser, then when you emit, you have to do the whole dance over again.
If you're willing to take some trade-offs in the parsing phase, it's OK. But the emit is where you get killed - either every plugin has to be written generically and correctly enough to deal with any arbitrary nesting of syntaxes (including the cases where the semantics of nesting aren't even clear, like where a 'fat' arrow here would capture 'this' from), or you do one tree pass per transformer, which gets very expensive.
There's a reason you don't usually see architectures like that live very long.
Maybe the specific example you give can be solved in a very hacky way with something like a priority system but I can see how messy it can get even when tokenizing the possible expressions for such an open "playground", let alone transforming in the correct sequence.
Thank you, Ryan.
edit: Oh you are the person who implemented JSX support for Typescript! How do we buy you a beer, or in this case a six-pack?
That said, if you look at TS as a superset of Babel plugins, there's actually not much to TS that is TS-specific. Adding that to Babel would be relatively simple.
You seem to be arguing it's a slippery slope. We're not talking about arbitrary syntax. We're talking about a fairly well-established syntax extension backed by Google and Microsoft. It doesn't have to perfectly universal and generic to support TS.
EDIT: If you were specifically addressing the parent: yes, if every syntax extension was created as a parser plugin, getting them to work together would be messy, but that's basically what we have in PostCSS isn't it? Plugins explicitly instructing users "this conflicts with X, please add it after Y but before Z" -- which is fine IMO as you only need to care about the most popular ones and everybody else knows their stack is experimental.
Actually kind of the opposite - babel used to use the common ESTree AST format, but they've moved away to something similar but incompatible.
Babel itself demonstrates the truth of this. If you look at the source code for any of Babel's syntax plugins, they are literally only a few lines long, because all they do is activate a feature that is actually part of the parser core.
It seems like Perl 6 is trying to implement pluggable grammars that work like that. Can anyone here familiar with the Perl 6 ecosystem comment on how it's going over there? Can you feasibly write a module with 5 or 6 different grammar extensions? What's it like? My understanding of the situation has matched what RyanCavanaugh expressed here for a while, and I'm curious if people's experiences match it or not.
Then we'll have the Babel problem. E.g. how they handled 2 to 3 transition doesn't inspire confidence.
> If you work outside the San Francisco bubble and are stuck on Windows, Flow isn't really an option at the moment.
> A big factor in my company recently switching to TypeScript was Windows performance, even with the recent massive advancements for Flow on Windows it's still painful to use and the tooling is miles behind.
esproposal.class_instance_fields=enable
but it chokes on ones it doesn't understand. I tried using Flow and RxJS in the same codebase. RxJS makes heavy use of the pipeline operator:
stream::map(thing) vs map.call(stream, thing)
Flow will stop checking types as soon as it sees ::. Babel parses it, but Flow runs in parallel, so it needs to be able to walk the AST itself.
That's the problem I have with the Babel-everything mentality of a lot of developers, they don't realize that they are essentially created their own quasi-language that they'll have to support on their own.
I love TS and using ng2 at work. If I was using React I would probably also skip on TS.
I am not actually sure what you mean by typed immutable records in this context, can you explain in more detail?
A nice typescript-friendly alternative to redux+immutablejs is MobX (https://mobxjs.github.io/mobx/getting-started.html). It does go a bit against the latest cool and hip trends (immutability, functional programming), but IMO its quite brilliant
And yes, actually I am using MobX, too, it's really a good choice for React. Although I miss redux-saga sometimes.
Though I find that Ramda's curried style isn't that useful now that we have arrow functions...
(I still use classes/objects for services with multiple related operations or polymorphism, but not for one trick pony "Executioners" for which Java would use a lambda -- which is what ES6 arrow funcs look like)
I wish I could vote the grandparent post up more.
* JavaScript is not suited for it (no composition operator, no interop with existing multi-argument functions)
* It doesn't improve readability over arrow syntax.
vsI saw that they have a completed 2.0.3 milestone in Github, but just a RC release at the moment.
I just wanted to know when 2.0 will be officially released and it seems like never, since they already at 2.1, lol
It feels like the TypeScript team and VS team do not communicate and are set on completely different workflows.
The VS Code team gets it though, but that's probably because they use TS to write their very product.
Even the ECMAScript feature table (https://kangax.github.io/compat-table/es6/) uses Babel and TS with core-js when comparing features, otherwise it'd be heavily browser dependent.
Also, since this seem to be a popular misconception, JSX support in TypeScript is not wedded to React. The default JSX target is React, but you can set JSX to "preserve" and get very vanilla semantics as well as keeping the JSX in the emitted code so you can pipe it through a custom transformer.
The question also points out that the reader is looking at lots of tutorials -- it should be unsurprising that these don't use TypeScript as it's an optional thing that would only increase the concept count in an educational setting where you want to only show the thing you're trying to explain.
If you need a notable React + TypeScript project, see the Delve team's write-up of their use of TypeScript - https://medium.com/@delveeng/why-we-love-typescript-bec2df88...
Javascript is a language and an ecosystem I really disliked until React and TypeScript came around and changed everything. We're making extensive use of JSX in our React app (https://github.com/hearthsim/joust / https://hsreplay.net/replay/ZXKe5VoqTzknRJNcPdTnYa) and it's really wonderful to both read and write.
As someone who has written a long tutorial, this makes total sense. When I was first looking at the react ecosystem, it was very frustrating because of the high cost of picking pieces to work together. I really liked http://teropa.info/blog/2015/09/10/full-stack-redux-tutorial... because it showed how to use mocha in the context of we webpack and react and redux.
It would be nice to see more tutorials for curated toolchains, but they take a lot of work.
In my work I deal with a legacy system with an ExtJS GUI. The two ways that ExtJS fails to be opinionated are perpetual pain points for me and my team! One is: every component has a million optional configurations, not to mention all of the events you can listen on. For the most part this is great, but there was never any systematic separation for "here are the absolutely-required things, there are the things which are optional but must be configured together, and over yonder are the things which are totally optional." Then you could require that the required-configs were, say, statically known when you were deriving a concrete class from an abstract one. Instead ExtJS wanted to accept doing all of this stuff at runtime, so because it failed to take a strong stand on its required configs, when you inevitably forget to configure some of them, you get an error puked out from somewhere very deep in the framework, where the call-stack and error messages show nothing related to your class at all, just "TypeError: SomethingYouNeverCaredAbout is null." It would have all been saved if `Ext.define` looked for some "abstractProperties" array, and made sure that every new `Ext.define` either set abstract properties or propagated them, finally checking that whichever ones are still present in the `Ext.create` call are filled in. Simple descriptive error messages are then available when you forget a required config.
The other way ExtJS violates the principle is... God help you if you ever have to figure out how the underlying form submits and grid reloads actually work. You'd think with something so critical, it would be clear... it's not.
"My grid refreshes automatically when the underlying store loads. Great! The underlying store can be loaded or reloaded with the .load() method, which accepts a callback. Wonderful!" It starts off very promising. But then you dig deeper and find that the .load() method packages the params and the callback into some object and then calls some .read() method which doesn't exist on the class you're looking at (inheritance! go up to the superclass!). Once you've traced that down the actual .read() bounces to some .doAction() which repackages these into some `Operation{type: 'readAction'}` or whatever... and then this gets handed up to some Proxy object which then stores it in some meaningless array, because of course these things get batched together... if you're not sick yet you find out that the Proxy needs to push the stuff to some Reader and Writer, just in case you wanted to communicate with the server via XML instead of JSON, or wanted to store the resulting array under a key not named 'results'. But you don't want to do any of this because the query finally gets XMLHttpRequested somehow (God knows how) to some `router.php` which we stole from IBM[1] a long time ago, which finally took a stand, "I will accept these two inputs, send them to the backend this way, and emit one of two corresponding outputs." (Except for that then you open that and it contains code for some sort of `doAroundCalls` because apparently the original author[2] decided to vacillate on what they'd accept, trying to also allow you to bookend one RPC service with two other RPC services, which never happens because Ext.JS never does it!) It gets a little more complicated because there is one rather significant bug which nobody has ever fixed in IBM's router.php, which is that formHandler services get the $_POST params (an associative array) as their first argument whereas XMLHttpRequests get the `json_decode($HTTP_RAW_POST_DATA)` (a StdClass object) as their first argument, so there's no interoperability on the frontend or the backend. Happy debugging, you. It's all one big mess.
You begin to wish ExtJS had done what they eventually ended up doing[3], ...
EDIT: to add, I think the TS team has done such a bangup job on Typescript that I would love it if they could create a build system as well. Some things that would be nice to have:
* Build-time loading of static resources (.json into js objects, html into strings, etc.)
* File watching and processing for more than just .ts/.js files
* Optimization. Not just tree-shaking and minification, but you could actually get a little more advanced due to the static types and ES6 modules.
* Environment-dependent compilation (compile these files in this way, inserting these static values where ENV variables are used in the source, etc.)
* Target capabilities analysis (ie. for this set of browsers and versions, what is the Lowest Common Denominator for browser capabilities, and ergo, what babel transforms and browser shims should be included?)
* Integrated contracts testing with test elision (ie. run these tests in these (karma? selenium?) environments and if failing, throw a compilation error or warning, and if passing, strip the tests from the compiled source).
* Source packaging (gzipping, etc.), and deployment plugins (ie. deploy compiled assets to S3, package for NPM, etc.).
All of these are pain points in Typescript projects, and all of them touch TS projects in such a way that it makes it even more painful in existing build systems.
I agree though over-fragmentation is a huge problem for JS, we need the big players (either foundations or companies) to put their weight behind one or two solutions and just get on with it :-)
Now that their Closure Compiler supports ES6 quite well, I've had a decent amount of success writing my app using straightforward ES6 and referencing the extensive Closure Library for functionality I would've previously pulled in npm packages for.
And the nice thing is that the whole library is written in such a way that all of the compiler's advanced optimizations and branch pruning, and dead code elimination work nicely on it so your compiled JS ends up containing only the code you need, and none of the code your don't need. If you want to use JSX in React projects, you can still zip the code through Babel or Typescript before feeding it to Closure.
It certainly won't work for every project, but it's one way to write modern JS without having to deal with the node/npm ecosystem too much...at least until things settle down a bit.
Gulp is the source of so much pain for people and yet so much of the ecosystem keeps suggesting that more gulp is the answer to their gulp problems.
More people should consider using Angular 2 for some kinds of projects.
Now, I have professional projects in both Angular 2 and React/Redux ecosystems, and frankly I enjoy using React a lot more in projects where I can focus on the frontend. I moved some projects to isomorphic React (ie, render using React on backend) in Node.js and Rails apps, and thoroughly enjoyed that experience. I keep on top of Elm and omnext and so forth, and I have personal projects built with those, and I do experiments with completely unidirectional dataflow in Elm using an Elixir backend ...
However.
Twice recently, when I had a full-stack project with a relatively short timeline, I made a conscious decision to keep the frontend from getting too uppity and absorbing too much of my mental energy.
In those cases, I used Angular 2, generated from the ng2 CLI.
It's worked pretty well. Well, the first one had some dependency issues from time to time, which is understandable because of the beta -> rc1 -> rcX -> Angular2 release process that was happening.
Why ng2? Well ... not because I'm convinced that it's "the best" in any particular dimension. Its special sauce is supposed to be Zones, which make knowing when side-effects have occurred less something that we have to track and manage manually, but there's other work in that problem space!
I used it because it's an opinionated stack that already has the important pieces in place (router, DI, build/minify, type checking, components), and more importantly, because I can be fairly confident that another dev could get up to speed quickly due to decent docs and guides ... and it's less easy for someone to "paint themselves into a corner" by doing things really wrong.
On a side note, I had submitted this to HN but somehow my submissions are visible only to me and doesn't appear when I checked the newest tab after logging out.
[1]: https://youtu.be/OcUzuQ_31co?t=34m5s (the relevant part in the EmberCamp keynote by Yehuda Katz and Tom Dale)
i suspect a great many typescript users are not open source.
Practially not, but it's a bit of a hassle. either you leave the JSX be and parse it with Babel or you need some wrappers for you VDOM lib, because tsc assumes a namespace, while most not-React-vdom libs just deliver a function out of the box.
Agreed. Here's an example of JSX in TypeScript that has nothing to do with React. UI Builder is a templating library, just like Mustache, but much better because you get full intellisense and compile-time checking for the template:
https://github.com/wisercoder/uibuilder
If anyone is interested, I have a working boiler plate with React Server rendering using TypeScript[2].
[1]: https://github.com/styfle/typed-tmpl [2]: https://github.com/styfle/react-server-example-tsx
So I tried a little to convert a big React project to Flow or Typescript. The Flow was a non-starter because of the absence of Windows support at the time, and we use like 40 (non dev) dependencies, and Typescript has a way better support for typings, I tried Flow on a mac it was chocking on the size of the node_modules or couldn't find the app modules because we use a webpack root dir (i don't tried hard to make it work).
When the app was started Typescript didn't support React so it wasn't written in a "static" way, and accumulated a lot of dynamic idioms, also the backbone of the app is a dynamically generated schema based on XSD and that would be hard to make it compatible with TS type system, also React ecosystem doesn't really use it, leading to a chicken/egg problem, and React.PropTypes is already a form of type checking (but dynamic) so it probably lessen the feeling of a need of static typing in React ecosystem.
I might even go as far as putting on a "tin foil hat" and state that Typescript is a trick to lock you into their proprietary ecosystem of expensive tools that everyone have to buy into just to communicate with you once you are locked in.
I only see advantages for static typing for a small cost of time: you prevent most of Type Error from happening, you get automatic auto-completion, refactoring errors are easier to catch and feel safer. Either way, you need to specify the type of the arguments in the documentation of your function (I can sometimes even find the C# LINQ's function I'm looking for just by looking at the return type of the list of function).
You could even use Flow and Typescript to catch
Aside from the proprietary reasons (which I believe are unfounded since the whole Typescript ecosystem is opensource), why do you think static typing doesn't belong in Javascript ?
What do you think is the advantage of such a thing? IME they tend to end up as an ad hoc, informally-specified, bug-ridden, slow implementation of half of a type system.
https://github.com/Microsoft/TypeScript is uh... right there. Check the license. Visual Studio code runs Textmate snippets and has a very sublime-like extension system.
There is no vendor lock in.
Indeed there are some pain points as mentioned in the article, e.g. typing Redux actions can be a bit boilerplatey, and there's currently no object spread operator; but I feel it's worth the trade off - you can always opt out of typing something (e.g. with the "any" type), but I've always found that the places where you do this are the places where the bugs creep in!
Obligatory plug for my Typescript 1.9 + React project set up guide - I need to update this for v2.0, but I think it should pretty much work as is: http://blog.tomduncalf.com/posts/setting-up-typescript-and-r...
I actually prefer Flow's approach of being just annotations which can be stripped out, rather than a new language (albeit a superset of Javascript) with its own features and compiler - for one, I find this makes it an easier sell to teams worried about "lock in". However, there is a bit of FUD around this IMO, as you can use just the subset of Typescript which adds types to JS and avoid stuff like "enum" and the "class" enhancements - in my experience, TS's types can be stripped by Babel in the same way as it strips Flow's, so actually if you ignore the `.ts` extension, there's not such a big difference.
The problem is that every time I've tried Flow (including very recently spending several days trying to convert an existing medium size React project to it), I've hit so many random undocumented issues, and ended up feeling that the benefits of it were outweighed by the amount of effort required to get it working properly. This is especially true because the editor experience offered by Nuclide is (again, in my experience) sub-par and buggy compared to VS Code (or the Typescript Sublime plugin), and I've always felt the editor support is actually one of the big selling points of working with "typed JS".
I am really looking forward to seeing how Flow progresses, as in an ideal world it is what I would use, but for now (in a commercial situation especially), I have to go with what I feel brings the biggest productivity/code quality benefits and the best developer experience for the team, and for now I still think that is Typescript by a fair distance.
As someone with experience in both languages, I could not disagree more.
> Dart was originally presented as a wholesale replacement of Dart
I think you meant replacement of JS here. I guess it depends entirely on what you think of JS as a language. I, for one, would rather a language that fixes core issues with JS, instead of just being a superset of JS.
If I were aiming to replace JS, I'd fix what Dart does, but I wouldn't stop with merely fixing what Dart does.
Dart, despite being an entirely new language, has a less expressive type system than TS. It's transpiler (and it's VM) also does no optimisation based on the type system, instead heavily relying on the JIT to infer what the types already imply (e.g., it would be nice to do things like LICM at compile-time).
Care to elaborate on that?
As for the rest of your comment, I'm with ya. I guess they're reasoning behind that was they thought a lot of development would start out untyped with additional types added as development progressed. I think that assumption didn't pan out, at least that's not how I do it.
Official answer from https://www.dartlang.org/faq:
"Q. But don’t you need sound typing information to get high performance?
Sound types can help with performance but aren’t essential. What we need are uniform, simple semantics. Modern VMs can use actual runtime behavior as a valuable signal for optimizations."
I'm not the OP, but TypeScript supports union types (A | B ; a type that can be either type A or type B) and intersection types (A & B ; a type that is both A and B), while Dart doesn't. https://www.typescriptlang.org/docs/handbook/advanced-types....
Typescript also has structural types, like Go and OCaml, which many people find nicer than nominal types. Structural types mean if I have an interface Blaz with two methods Foo and Bar, if I have an object MyObject with Foo and Bar methods of the same types then my object counts as a Blaz, while nominal types mean I have to write something like MyObject extends Blaz.
Elaborate then. Because one's major advantages can be another's (and sometimes, objective) trivialities...
No, he means that the Dart team was supposed to solicitate opinions on how to build Dart and what the best objectives for it would be, but instead they showcased it in "almost done" form, and only then tried to attract a community.
The other big problem was that it was done with the VM being a major part of the project with the intent of getting it into Chrome, obviously without having talked that much with several of the people who have significant influence over such things in (then) WebKit, even those within Google. That the VM was going to be outright objected was entirely predictable.
I did use CoffeeScript after that, a beautiful little language, but only suitable for smallish projects. I need static typing for large projects.
After that, I learned Dart, and coming from C/C++, Java, AS3, it was a breeze. I find there are no quirks, everything behaves as you'd expect. Other team members were productive in Dart in about a week, without having seen a line of Dart code.
I mostly write HTML5 games and server-side with Dart, so I can't really talk too much about any client-side frameworks.
As for Dart cons, I guess one would be you have to use a different browser for web dev, but it's not really a big deal, I'm kinda reaching here. There aren't as many 3rd party libraries as some other languages. Depending on what you want, you might have to get your hands dirty and issue some pull requests for features/bug fixes for those libs. JS interop can still be a bit tricky too, depending on what you're doing.
Any specific questions, I'd be happy to answer. Also, there's a great slack channel for Dart: https://dartlang-slack.herokuapp.com/
I haven't touched Dart for over a year, but the Flutter page seems like it is on HTML, not native, and it only specifies Linux or OS X dev machine.
https://docs.google.com/presentation/d/1cw7A4HbvM_Abv320rVgP...
I'm going to try it on my Linux box. The only disadvantage I can see for my eventual needs after a second reading is the lack of 3D support. I can get by with 2D for most of my stuff, but for games, I need the 3D hook.
I'll have to see how easy it is to customize the Dart-provided widgets. Might be easier than creating them from scratch in OpenGL via the NDK.
What about using a combination of StageXL and ThreeJS? Then use Cordova to package your HTML5-based app?
http://www.stagexl.org/ http://threejs.org/ https://cordova.apache.org/
> working with existing build tools and module systems
I'd say they replaced it with a better tool, pub.
The one good argument you have there is .d.ts files. Dart lacks them, but there are tools to generate js bindings from those same .d.ts files. https://github.com/jirkadanek/definitely_typed
I haven't used it though, so I can't say if it works as advertised.
Right but that route ends in forcing people to leap to a whole different ecosystem before they can even try your thing. Whereas with typescript you could put a single .ts file in your existing project without messing with anything else.
You can't just pull your package from pub (leftpad).
Extremely trivial, but I prefer yaml to json, :)
https://www.dartlang.org/tools/pub
The only problem is that the main output js file is still 107kb, quite large.
Dart is a different language so it's a different path. It's no different than, say, using C# or Java or C or whatever language that can be transpiled to JavaScript.
[1] https://flutter.io/faq/ [2] https://github.com/dart-lang/dev_compiler
Compatible should be same files, new compiler = "just works".
EEE refers to the times when Microsoft would take an open standard--say HTML, or JavaScript, back when IE3 was actually the best browser on the market--shove in their own, proprietary, backwards-incompatible extensions, and keep calling it the same thing as the open standard.
But MS makes it very clear that TypeScript is a different language. It helps a lot that they don't even have the same name, y'know. Also, it's a system for specifically staying backwards compatible with open-standard JavaScript. Using TypeScript does not replace JavaScript. It supplements it.
Then when everyone's hooked on VS Code BAM VS Code Pro Extreme Edition!
edit: Though if you mean TypeScript depending on VSCode to build, I doubt thats even possible at this point. Everything is available via the command line. Heck, there are even tools that build on top of the compiler API. (dts-generator, tslint etc)
My "way out" of the Typescript ecosystem is:
1.) Change the target to "ES6", and run a compile. 2.) Take those files and use them as my new source files. 3.) Remove Typescript from my build pipeline.
Done. Easiest language migration I've ever done.
Strangely, it appears to work. I've seen claims that Flow is better because "its just JavaScript, not another language"
I don't get it.
I would need to ask some of the teams that tried converting larger projects specifically what they found that they felt was important. I'm certain TS would find some bugs in any sufficiently large project, but I'd have to go dig up data to know roughly how many or how serious they were. Just because there was a technical quality issue with the code doesn't mean that the vanilla JS version of it wasn't producing the actual desired result. It's hard to gather numbers for that type of thing. It's very similar to the let-down a lot of people feel with using static analyzers on mature, battle-tested C++ code for the first time. It will certainly find some nits, but most likely they were not that important to begin with.
The sky is falling.
Anyway, you're not going to dissuade anyone. TypeScript looks visually similar to Java and C# enough that managers will think they can adapt Java and C# teams to it in a couple of days; and they won't know how wrong they are until a month or two have passed.
really? I'm assuming you never refactor anything.
(much like IDE generated getter/setter code, which is solving the wrong problem)
If you write fewer classes and class hierarchies, and use higher order functions (see also - partial function application), you will have much less "refactoring" to do - often, simply small changes such as to increase the visible scope of a function you now want to reuse elsewhere, or to "pre bind" another argument to a function so the caller(s) don't need to know a particular detail.
This probably has a lot to do with why the static OOP people think the dynamic FP people are insane: they have no idea how we really work.
We have garbage collectors and closures now. Stop writing code as if in some crippled version of Simula 67 :-)
https://npm-stat.com/charts.html?package=babel&package=types...
Babel has faltered since the V6 release, TypeScript is still growing fast, so I'd expect the React world to follow suite, even if Facebook itself pushes Flow...
NPM downloads in August (rounded):
https://npm-stat.com/charts.html?package=babel-core&package=...
We just moved our app from Redux and ImmutableJS to mobx and it's been a treat: we now get full typing and it's much less verbose. We don't need to repeat the payload definition at every point, we have a store where we call a method and that's it. Highly recommend checking out mobx if you use TS.
If ___________ is so great, how come all notable ________ projects use __________?
Classic troll magnet :)
Go all in with purescript[0] :D
Simple, elegant, strong typed and compiles to JS.
[0]: http://www.purescript.org/
[0] https://github.com/purescript/purescript/wiki/Differences-fr...
How far can i go with typescript until i need to use babel ?
Yes.
> What parts of JS do they consider a subset of typescript ?
Everything that's standardized.
> Can i keep my type declarations in a different file than my .js code like flow does ?
Yes.
> How far can i go with typescript until i need to use babel ?
Pretty much as far as you want, although you may have to wait a little bit longer.
BTW, stop inserting spaces before your punctuation. It's super aggravating.
facebook really likes saying community
community community community community
https://swlaschin.gitbooks.io/fsharpforfunandprofit/content/...
What I loved about them is they show how a different type system and language design can massively reduce code size and errors.
After reading them I felt frustrated back in JavaScript or C# or any other language I use regularly.
Are Typescript and Flow missing the forest for the trees?