Hacker News new | comments | ask | show | jobs | submit login

"Even if I have been writing code with Java / C# for nearly a decade , nothing has come close to Typescript in terms of productivity,flexibility and confidence."

Same here.

Isn't this truly amazing?

Take a jangly language like JS, and add some typing for the compiler, which forces you to write cleaner code in addition to all the compiler advantages ... combined with some really cool features and bang a magical, pragmatic language.

Aside for some script things for which Python is still a blessing, I'd chose TS for everything else, at least to start.

It just has the right mix of flexibility and expressivity etc..

Though TS is an MS project, I suggest it really is quite different, it's 'open from the start' kind of thing, you can have a loot at TSC internals. The team seems to be fairly dynamic and responsive.

Typscript is my #1 favorite 'invention' of the last few years, I think it will be around for a while, and I hope to see many more JS API's 'properly documented' with the help of TS.




> Take a jangly language like JS, and add some typing for the compiler, which forces you to write cleaner code in addition to all the compiler advantages ... combined with some really cool features and bang a magical, pragmatic language.

Agreed. And when you compare how TS was designed to how other languages were designed, it makes a lot of sense why TS ended up being such a great language.

Unlike virtually every other language in existence, TS was not designed from the ground up. It was designed with a very specific goal in mind: to adhere to the standards that JS developers had already converged on. So when a JS developer said if (foo), TS was built to realize that was an implicit type check against null. When a JS developer said if (obj.type === “bar”), TS read that as a way to ensure obj was in fact a bar.

It’s unlikely that a language developer working from scratch would have come up with these odd idioms, let alone prioritized their inclusion into a new language. But in the case of TS, all these idioms came from millions of lines of working code.

I think that’s why TS feels so enjoyable and easy to work with nowadays, whereas even the best of other languages feel a little clunky at times. It was developed prioritizing making real actual code idioms people wanted to do work.


> when you compare how TS was designed to how other languages were designed

Is it safe to say that Microsoft has probably created/designed more programming languages than any other company? I can think of a dozen off the top of my head...


Anders Hejlsberg, the lead architect behind TypeScript has created C# and J++ at Microsoft, and Delphi and Turbo Pascal before. It's safe to say he has some experience in designing languages.


J++ is one of the primary reasons I am so wary about using a Microsoft-invented language. "Embrace and extend" a well-used language with extra features (then make them only work well on Windows later) has always been a classic Microsoft strategy. If they could get away with it with Typescript, I'm sure they would try again.


Thank you! This is the argument that made me give TypeScript a try. I work in Kotlin day to day which tries to fix its base language (and batteries included with it) while not fixing it too much. TS sounded like a language in that vein.


The exception I'd add is that JavaScript's standard library is still very weak. I find myself leaning on Lodash for functionality that would be built into any other language.

Part of me would love for TS to build one out and add shims as part of the transpilation process, but it would go miles out of the scope of what TS is trying to do. And I love that (compared to Babel) TS has no plugins and relatively few options.


To add onto this, using lodash + TS is not the most pleasant experience. A lot of that has to due with current limitations of the type system (mostly variadic types [0]), but I find myself having to provide lots of generics rather than relying on inference. The overloads are not great.

I say this all with recognition that lodash greatly predates TS, and the maintainers have done an absolutely wonderful job in keeping up with the overall ecosystem (ESM, typings files, etc). I can't even begin to comprehend the amount of work that has gone in to keeping lodash so modern.

That being said, I wish the interaction was slightly better, since a lot of people just immediately bring in Lodash to any JS project.

[0] https://github.com/Microsoft/TypeScript/issues/5453


I have the same experience; I wonder if anyone is working on a TS-friendly utility library, or if our best hope is the work on TS itself on [0]?


I wonder if ramda is any better in that regard?


I love Ramda and use it everywhere but sadly, it's somewhat lacking when it comes to type definitions. Everything in Ramda is curried and the types just don't reflect that very well so you get quite a few incorrect compiler errors.


Yeah, I remember liking the auto-currying, that makes sense it has a downside here.


Shouldn't tuples in rest parameters from TypeScript 3.0 [0] fix that?

[0] https://www.typescriptlang.org/docs/handbook/release-notes/t...


Not entirely.

For example, a function which takes a property path (in the form of an array of strings) and an object as parameters and returns the value at that path inside the object still needs overloads for every single tuple length.

  type Key = string | number | symbol;
  
  function get<T, K extends keyof T>(path: [K], obj: T): T[K];
  function get<T, K1 extends keyof T, K2 extends keyof T[K1]>(path: [K1, K2], obj: T): T[K1][K2];
  function get<T, K1 extends keyof T, K2 extends keyof T[K1], K3 extends keyof T[K1][K2]>(path: [K1, K2, K3], obj: T): T[K1][K2][K3];
  function get<T, K1 extends keyof T, K2 extends keyof T[K1], K3 extends keyof T[K1][K2], K4 extends keyof T[K1][K2][K3]>(path: [K1, K2, K3, K4], obj: T): T[K1][K2][K3][K4];
  function get(path: Key[], obj: any) {
      if (path.length === 0) {
          return obj;
      }
      const key = path[0] as Key;
      const rest = path.slice(1) as [Key];
      return get(rest, obj[key]);
  }
  
  
  interface Foo {
      foo: {
          bar: {
              baz: {
                  val: number;
              }
          }
      }
  }
  
  declare const foo: Foo;
  const num = get(["foo", "bar", "baz", "val"], foo);
In this case, num is implicitly typed as number, but if the path would be longer, you'd need to add more overloads.


I keep hearing that but I dunno. I’m building a fairly large side project in Express + React and I keep finding ways of doing things in ES6 - lodash is still not to be found in package.json. I think I might cave in eventually but as it stands my code feels clean and succinct and it’s all done in modern functional style.


One example is doing deep comparison on objects. ES6 still has no equivalent for that, and it's something you can do in one line in other languages.


Which languages? I'd think it's rare because I know no such standard function from the top of my head.


Swift immediately comes to mind - structs are value types. Also, Kotlin has data classes.


`util.deepStrictEqual` in Node at least


This is a very good point.

I wish lodashy functions, and a few other things (Time?), were just integrated into JS, in a thoughtful way ... as part of the standard lib. So they could all be done in native code in the engine.


I’m sympathetic to this point of view, but I find lodash to be too huge of an API. Most of the collection methods can be done as a small _.reduce, and I find the many method names and subtle distinctions to add more trivia than they remove.


The good news is that you can use lodash as an ES6 module, with any tree-shake capable bundler stripping out all the crap. Absolutely agree it's not optimal though.


This is a pain point that the community wishes to address: https://github.com/tc39/proposal-javascript-standard-library


I don’t see this going very far for historical reasons. This idea has been suggested for over a decade, but back then the focus of inspiration was jQuery. The false argument was that everybody was requesting it into pages anyways so it should be part of the language. Not only was this idea proposed on top of a faulty assumption but there were also performance penalties and hidden conformance defects.

These suggestions fall apart over time because they aren’t environment agnostic and lack objectivity. The subjectivity in question, “I want feature X”, usually doesn’t take alternate positions into consideration.


The proposal explicitly states that everything in the standard library would not be tied to specific target environments:

Such a library would only cover features which would be useful in JavaScript in general, not things which are tied to the web platform. (A good heuristic: if something would make sense on a web browser but not in node or on embedded devices or robots, it probably isn't in scope.)


Truth be said, jQuery can be seen obsolete because most of the functionality has been moved inside the DOM or the ajax "standard library" ...


This certainly wasn't a popular opinion 10 years ago. The history lesson here is that popular is a subjective quality that does not provide objective benefits, which is clear in a future time.


Well, as I said you could think that is jQuery "has been added" to the javascript expected api. Some functions calls has been renamed, others have been superseded, but the "vanillajs" of 201x is pretty different from the 199x - and more similar to the jQuery usage.

jQuery rise (but also underscore and others "low level libs) was interwined with the need of common functionalities, such as the DOM manipolation and the ajax calls. I still remember when all you could use was the .innerHTML property and the "new" DOM level 1 api [ https://www.w3.org/TR/1998/REC-DOM-Level-1-19981001/ ]. jQuery selectors were so game-changing that the "new" DOM api were basically copied.

I understand how incredibly difficult is to find a good balance between an "anemic" stdlib (like the barely sufficient c stdlib) to the giant ones (like java has had), moreso that a bad/poorly secured function should still be mantained "forever" for backward compatibility.

Still I think that this movement should go forward to finally have some form of "batteries included"


I guess I disagree as I much prefer Ramdas style over Lodash.. Is your concern about performance? Because I don't think it would be a massive improvement over JS code.


Curious what you're still often using lodash for?


One thing that comes to mind is comparison - array equality, deep object comparison, that sort of thing.


> Aside for some script things for which Python is still a blessing, I'd chose TS for everything else, at least to start.

I really wish Python had a decent type system; hopefully the Mypy project takes a leaf from TypeScript's book.

Also, I've found that Go does for Python much of what TypeScript does for JavaScript. Of course, Go's APIs are different than Python's and its type system is less expressive than TypeScript so it's not a perfect analog, but Go also brings speed, parallelism, sane concurrency (Python's async is a hot mess by comparison), sane deployment, and great editor integrations, which are things I sorely miss when writing Python.


Mypy is already quite powerful and understands a lot of the language. With latest versions of the language, what is handled by "transpiling" to JS, can be done "natively", ie. there is no need for an intermediate step to strip out the additional syntax for declaring types as it's now built in.

Mypy and TC and Flow and many other similar projects seem to stem from the academic work on gradual typing from nearly 20 years ago. What we're seeing now is "practical application" of that research, and while different projects have different budgets, it won't be surprising if they all converge in terms of features at some point. I'm not an expert, by any means, but we've already seen this happening many times with languages and software platforms. At least this time the point of convergence is based on comp-sci research and not on the marketing one.


My grievance is mostly that Mypy is much less polished than TS and Flow (you can argue that it's a lack of investment and that's probably true, but it doesn't do me any good as a Python developer). Notably, Mypy's syntax is very much shoehorned in. How do I define a TypeVar for a particular method in a class? If I define a TypeVar (<T>) in the class scope, does every reference to T take on the same type? I can't honestly tell by looking if it's safe to use <T> for each generic method in a class or if the type system will try to unify them to the same type. Also, does Mypy support recursive types yet? Can I meaningfully define a JSON type without hacks (e.g., `Dict[str, Any]`)? Also, can I stub out generated types yet? IIRC, the official position for SQLAlchemy was something like "eh, it's out of scope for the project". Pretty sure there was a lot of problems with defining different kinds of callables (maybe those with args and kwargs?) not to mention a bunch of ergonomic problems because they don't want to extend the parser much (it appears they take the view that it's better to have terrible syntax that is "valid Python" without much modification to the Python parser--to be clear, this isn't referring to angle brackets vs square brackets, but things like using variable declaration syntax in an outer scope to declare a type variable for a generic context).


Python's type annotation syntax is mostly similar to TypeScript.

Each method is independent unless the class is a Generic[T].

You can define a recursive type by quoting the nested reference.

You can define a JSON type with recursive types.

You can create stubs. Some are in typeshed.[1]

Mypy recently added protocols to simplify defining callable types.

Python has always been slow to add new syntax. I think that's a good thing overall.

[1] https://github.com/python/typeshed/


> You can define a recursive type by quoting the nested reference.

No, that’s not sufficient, or at least it wasn’t. The problem wasn’t symbol resolution, but Mypy actually gave you a recursion error. At one time they were intending to fix it by implementing protocols which hadn’t landed last I checked.

> You can create stubs. Some are in typeshed.

You can, but not for magical libraries like SQLAlchemy.

> Python has always been slow to add new syntax. I think that's a good thing overall.

Probably, but it’s hindering their typing story. Typescript solves the problem by building a syntax that compiled to JS, but Python has some syntax support but lots of things are shoehorned in.


I think the biggest win of Go over Python is around the single binary distribution, which I guess you included with deployments. But it truly deserves a mention on its own and it’s a major point over other (most?) languages. It really makes up for a lot of the shortcomings of Go as a language IMO. But I enjoy Go best for building system tools, the single binary doesn’t shine as much once you involve containers at which point the friction between say a Python/Node container and a Go container is pretty much the same


That’s definitely up there. As for containers, I think Go’s static compilation story actually has some important ramifications for containers, namely I don’t need a set of base images for doing development since I can just toss a binary into the container and run it there (running in the container is useful because our local dev setup uses Docker Compose to orchestrate the microservices). If we could do this with Python it would simplify our CI and our development process by a good bit. And of course Go images are about a factor of magnitude smaller than Python images to boot!


Turns out creating a static binary distribution can be done in Python without containers [0].

[0] http://www.pyinstaller.org/


The tiny size of an Alpine + Go container is still nice compared to a typical Node or Python container, though.



> Take a jangly language like JS, and add some typing for the compiler

It so turns out that there is a great sweet spot in between the straight jacket typing of classic Java/C# and the loose "do way ever you like" approach in Python/JS.

I don't want use another language that doesn't have optional typing and structural typing. It combines the best of both ends of the spectrum.


My thinking exactly.


Wow, almost...almost reminds me of a little known language called ActionScript 3. ;)


As someone who hated ActionScript 3, I vehemently disagree. AS3 felt like some Java guys trying to force a Java mindset on a language that didn't really suit it.

And I say that as a Java guy myself. TS is much more dynamic and less abrasive, IMO.


Funny, I feel the same way about TS :) To be fair tho, you’re right. Flex was a very Java centric endeavor, from its compiler to the first big frameworks (Caignorm?) all the way to its target audience, which were enterprise companies that wanted to do their “thing” on the web. There was a massive developer migration from the Java/enterprise world to the AS3 ecosystem that had a visible impact. Also to be fair, if you look at Angular now with TS it feels even more Java’ish than ever. TS is great, is specially good for people coming from different languages in that it gives them a more familiar environment but the downside is that they have to make a lower effort to break away from old patterns and truly understand the new platform they’re working on.


AS3 was a huge improvement over AS2. However Typescript type system is incredibly dynamic and malleable yet quite strict.

Typescript gets its huge strength from being able to bring a slider of type safety from pure js - Wild West crazy to strong null checked safety.

Having that pragmatic option of a slider is great for productivity.


> if you look at Angular now with TS it feels even more Java’ish than ever.

This is true, but I think it's an Angular thing rather than a TS thing.


I think it is hurting Angular in the marketplace, too.


Whenever I feel in the mood to troll people, I tell them that TS is just a worse AS3. AS3 has types, classes... it even had XML literals! Eat that, JSX.


To be more precise, TS is a worse ES4. AS was a partially conforming implementation of ES4 drafts that most are aware of. But Microsoft had its own thing along these lines - JScript.NET (in fact, it still ships as part of the .NET Framework, even though it's deprecated).


I've heard it said that Javascript and C are both good languages to compile to -- the language itself is very "fast" in basic operations (V8 is hyper-optimized, C is relatively close to the metal), but an ugly language with lots of gotchas and warts that make it hard for a human to use effectively, but which don't pose a problem for a well-designed compiler.


No lol. Javascript is not a good language to compile to. People compile to JavaScript only because it's the only language to run in browsers.

Most compilers, after type checking and semantic analyses, basically generate a control flow graph with basic blocks. Javascript doesn't have goto so it doesn't allow you to express those low-level things natively, which is why emscripten has to include a relooper component to turn them back into loops and conditionals.

If you want a good language to compile to, look at LLVM. It's a language designed to be compiled to, and it's mind-blowingly easy to compile to than either C or JavaScript.


It's maybe worth noting here that compiling to C and transpiling to JS are two entirely different paradigms of linking and building a software release.


> Aside for some script things for which Python is still a blessing, …

Have you tried using type hints (https://www.python.org/dev/peps/pep-0484/) with mypy?


> Though TS is an MS project, I suggest it really is quite different

I'd be willing to say it's actually the "heart" of the new MS. Eliminating the incentive to selling OS licenses is doing marvels for them.




Applications are open for YC Summer 2019

Guidelines | FAQ | Support | API | Security | Lists | Bookmarklet | Legal | Apply to YC | Contact

Search: