New issue

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

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

Already on GitHub? Sign in to your account

[RFC] Migrate Jest to TypeScript #7554

Closed
wants to merge 3 commits into
base: master
from

Conversation

Projects
None yet
@SimenB
Copy link
Collaborator

SimenB commented Dec 27, 2018

In the lastest State of JS, the one stat that stood out to me was the number of people either using or wanting to use TypeScript (over 46.7% has used and will use it again, 33.7% wants to learn it). And since Babel 7 has support for TypeScript, integrating it into your workflow has become way easier than it used to be.

We, the Jest core team, have privately discussed migrating to TypeScript (Jest is currently written using Flow), and I was asked to look into how much effort it potentially is, and try to gather feedback from the community. So, as a proof of concept, I've migrated pretty-format over (look at the second commit of this PR).

This PR is a request for comments from the community. Is it a good idea? Is it wasted effort?
While comments on the code itself (and the build process) is welcome, that's not really the point of this particular exercise.

The PR will probably not pass CI (at least linting), but that should be fixed by babel/babel-eslint#711.


From my personal (and limited) experience, the two type systems are pretty similar in feature sets and syntax, so I haven't consider which of the 2 type systems are better. This is about improving the health and maintability of the code base and encouraging contributions.
I'll try to list out the pros and cons of going Flow -> TypeScript from the top of my head - not by any means an exhaustive list!

Pros:

  • Better tooling (IDEs in particular)
  • Way more typings available for community modules, meaning our own code is safer
  • We can easily distribute types for both Jest itself (@types/jest has 1M download every week) and for Jest's individual packages, such as jest-worker and jest-haste-map
  • More popular, which hopefully would lower the barrier of entry for contributions from the community

Cons:

  • Migration cost (both time spent on the migration itself, and the churn imposed on existing PRs)

Other libraries doing the same:

I'm sure one can find evidence of going the other way as well, those are just the ones I know about, and presented as anecdotal "evidence".

SimenB added some commits Dec 23, 2018

@TrySound

This comment has been minimized.

Copy link

TrySound commented Dec 27, 2018

For me it just doesn't make sense. You will invest a lot of time and will get a bit better autocomplete (I know you may get more features). But in the end of the day it's the same javascript full of its problems.

For me I see the sense in moving to reason or ocaml which are more safe languages than both flow and typescript.

@orta orta requested a review from cpojer Dec 27, 2018

@orta

This comment has been minimized.

Copy link
Collaborator

orta commented Dec 27, 2018

For me I see the sense in moving to reason or ocaml

I think that's probably a step too far in terms of time + commitment for value. I think it would make a lot of sense for a reason testing library to take a bunch of the best ideas from jest and re-apply them in their own context.

Personally, I've been a part of migrating all of Artsy's JavaScript to TypeScript, and while it's a little bit of churn at first (notably the .js -> .tskills git history, long PRs need a harder rebase, etc) it;'s paid off in terms of dev tooling across the board

While I'll be sad to see my main test-bed for the flow for vscode extension go away, it'll be great for exploring and understanding the jest codebase (both as an occasional contributor, and definitely as someone who uses the sub-packages)

@jamesisaac

This comment has been minimized.

Copy link

jamesisaac commented Dec 27, 2018

Better tooling (IDEs in particular)

Flow has recently been putting lots of effort into rolling out support for Microsoft's Language Server Protocol (search "LSP"), which from waht I understand should allow it to provide the same level of integration into most IDEs that TypeScript does.

Way more typings available for community modules, meaning our own code is safer

Not sure "safer" is the right word here... in my experience Flow typings are generally more sound and expressive than their TS counterparts. Agreed there are certainly more definitions available though.

We can easily distribute types for both Jest itself (@types/jest has 1M download every week) and for Jest's individual packages, such as jest-worker and jest-haste-map

Not sure I understand this point - what's the difference from Flow & flow-typed?

More popular, which hopefully would lower the barrier of entry for contributions from the community

Imo jumping between TS and Flow does not create much of a barrier for someone experienced with either. Like you say, the features and syntax are extremely similar.


Another con:

  • Flow and Jest are both Facebook products (right?), so I assume (a) the barrier to entry for internal FB employees would be higher, and (b) if changes are needed upstream in the typechecker, the chances of that being prioritised are higher than with TS.
@SimenB

This comment has been minimized.

Copy link
Collaborator Author

SimenB commented Dec 27, 2018

For me I see the sense in moving to reason or ocaml which are more safe languages than both flow and typescript.

@orta already answered here, but the tl;dr (at least to me) is that the point here is to make the code base more approachable to to new (and old) contributors who are consumers of Jest. The vast majority of them are JavaScript developers, not OCaml developers.

But in the end of the day it's the same javascript full of its problems.

True, but we love it nonetheless 🙂


Flow has recently been putting lots of effort into rolling out support for Microsoft's Language Server Protocol

Sure, but it's taken months and months, and it's still not done. The argument "we'll be just as good, just a year later" doesn't really spark much confidence.

Happy to be convinced otherwise of course.

Also, FWIW I personally don't use VS Code, so LSP doesn't impact my experience. I use IntelliJ (WebStorm), and their TS support is miles ahead of the Flow support. I know most people do use VS Code nowadays though, so your point is very much valid to the majority.

Not sure I understand this point - what's the difference from Flow & flow-typed?

There is no way to generate typings from source code in flow. They've had an untouched gen-flow-files for some time, but it never went anywhere (facebook/flow#5871)

Imo jumping between TS and Flow does not create much of a barrier for someone experienced with either. Like you say, the features and syntax are extremely similar.

Sure, but the tooling is way better with typescript, even if the syntax itself is very similar. The fact flow is improving (lsp support has been worked on for a long time, generating types etc) doesn't mask the fact TS has all of that today, and there's no real reason to believe Flow will get those features in a timely manner.

Flow and Jest are both Facebook products (right?), so I assume (a) the barrier to entry for internal FB employees would be higher, and (b) if changes are needed upstream in the typechecker, the chances of that being prioritised are higher than with TS.

I can't answer to a, but to b: not necessarily, this took 8 months facebook/flow#6103, typescript had it within a few days DefinitelyTyped/DefinitelyTyped#24624

@jeysal

This comment has been minimized.

Copy link
Contributor

jeysal commented Dec 27, 2018

Not sure "safer" is the right word here... in my experience Flow typings are generally more sound and expressive than their TS counterparts.

Note that TS has been getting a lot better since they started introducing the various strict checks. As long as you have strict: true (which Simen did enable in this proof of concept) and of course avoid any as much as possible, TS is almost equally safe nowadays. The main reasons why I still used Flow for some things a year ago were its more robust type system and the fact that it didn't need a dedicated compiler that is not integrated with Babel etc., both of which no longer apply.

@jamesisaac

This comment has been minimized.

Copy link

jamesisaac commented Dec 27, 2018

Sure, but it's taken months and months, and it's still not done. The argument "we'll be just as good, just a year later" doesn't really spark much confidence.

I feel like a lot of the IDE support actually is done now. The LSP mode just landed as default 9 days ago. In my experience, it works smoothly.

Also, FWIW I personally don't use VS Code, so LSP doesn't impact my experience. I use IntelliJ (WebStorm), and their TS support is miles ahead of the Flow support.

Hmm, does IntelliJ not have support for plugging in LSP? That seems a more scalable and robust approach than them writing in-house tooling for every language extension.

There is no way to generate typings from source code in flow. They've had an untouched gen-flow-files for some time, but it never went anywhere (facebook/flow#5871)

Agree this is a big pain point. Perhaps someone on the Jest team can help flag this up internally at FB and get help get this more attention?

I can't answer to a, but to b: not necessarily, this took 8 months facebook/flow#6103, typescript had it within a few days DefinitelyTyped/DefinitelyTyped#24624

Imo this just highlights the difference in philosophy between TS and Flow (which is healthy for the ecosystem). TS added a few lines of typedefs, which include introducing 4 any types. The Flow team held off on the early PRs as they were deemed unsound, and instead did a big internal refactor to better handle these new types.

Fundamentally I just think having the competition of two popular type systems is good for the JS ecosystem as a whole. So it's nice that there are some projects firmly planted on either side (Flow: FB products such as React, React Native, Jest, Relay, etc; TS: Microsoft products, Angular, etc). Remember that when Flow was first released, TS didn't even have support for null checks. The two have both been introducing new ideas, taking lessons from each other, and helping push the space forwards (TS from an OOP background encouraging pragmatism, and Flow from an algebraic data types background encouraging correctness). Imo it would be a shame for the ecosystem to become completely dominated by one type system, and lose the innovation and cross-pollination that the other is bringing to the table.

@corbinu

This comment has been minimized.

Copy link

corbinu commented Jan 2, 2019

I think this is a great idea! just a note Vuejs is also moving to TypeScript

@milesj

This comment has been minimized.

Copy link

milesj commented Jan 2, 2019

As a Flow to TypeScript convert, I will always agree with any such proposal. That being said, the time required to migrate an entire codebase is quite high, as it took me many months to convert all of my own projects, and the same at my employer. Doing it piece meal can also be quite confusing, especially if the conversion takes a lengthy amount of time (which it probably will).

@SimenB

This comment has been minimized.

Copy link
Collaborator Author

SimenB commented Jan 9, 2019

@NoHomey @jwbay @asvetliakov @alexjoverm @epicallan @ikatyang @wsmd @JamieMason @douglasduteil @ahnpnl @JoshuaKGoldberg @UselessPickles @r3nya @Hotell @sebald @andys8

Sorry about the mass-tag (and some of you might already have responded to the OP) 🙏. As you're all set up as maintainers of @types/jest, I'd love to hear if you have any feedback here?

General feedback would be lovely (as well on thoughts about the process/transpiling part), but in particular I'm not sure if it makes sense for us (Jest core) to maintain the main Jest typings (for assertions etc) in this repo. It'd be coupled to Jest's release cycle, which is at times pretty slow. But at least all the types for transformers, config etc can come from here (a quick look through of @types/jest shows some holes in the various options). Maybe we can make the assertion typings good enough over time so that they don't change so often, though? Not sure, I've never tried to maintain typings before

@JM-Mendez

This comment has been minimized.

Copy link

JM-Mendez commented Jan 11, 2019

@milesj did you use babel 7 as your transpiler during the migration? I recently completed migrating a flow-typed module to typescript, and using babel 7 with esmoduleInterop: true in the tsconfig I was able to have both files living side by side fairly easily. The only workaround was ignoring the error for flow-typed imports.

@milesj

This comment has been minimized.

Copy link

milesj commented Jan 11, 2019

@JM-Mendez On my personal stuff I used TS itself, while at work we used Babel 7. Definitely easier when using Babel.

@SimenB

This comment has been minimized.

Copy link
Collaborator Author

SimenB commented Jan 15, 2019

We've decided to go for this, thanks a bunch for your feedback!

Right now, the plan is to release Jest 24 stable (should be any day now, https://github.com/facebook/jest/milestone/8 (please install jest@beta to test in your projects!)), then allow for a few weeks in case we need to make any bugfix releases.

After that, we want to do 2 things for Jest 25: simplify our configuration (#7185) and migrate to TypeScript.

As part of migrating to TS, we will be moving to ESM all over (tried to do it for Jest 24, but it broke lots of stuff, see #7602 and #7608). So we also need to make sure our exports do not mix default and named exports, so that we can use https://www.npmjs.com/package/babel-plugin-add-module-exports. That will also resolve #5803 and #7109. However, it'll likely be a breaking change, so putting it in a major makes sense.

I'll open up a tracking issue once we're ready to start migrating, at which point help from the community in actually migrating would be awesome 🙂 We'll hopefully be able to use https://github.com/bcherny/flow-to-typescript, which should remove a lot of the manual migration work.

@SimenB SimenB closed this Jan 15, 2019

@Jessidhia

This comment has been minimized.

Copy link

Jessidhia commented Jan 16, 2019

Not to turn this into a bikeshed, especially as the RFC has been accepted (🎉), but I strongly recommend against the add-module-exports plugin. It either turns what would be future semver-minor changes (adding an export) into semver-major, or forces you to attach properties to what was your default export and now you're back to the same problem as commonjs exports with none of the advantages of ES module exports.


Also, make sure to enable --esModuleInterop with typescript. It's really common, especially in code samples you find on the internet, for code to erroneously import non-__esModule commonjs modules as if they were ES module namespaces. As far as I've seen in my little bubble, React in particular is guilty of that (import * as React from 'react', import { Component } from 'react', etc).

@SimenB

This comment has been minimized.

Copy link
Collaborator Author

SimenB commented Jan 16, 2019

Thanks for chiming in @Kovensky!

I strongly recommend against the add-module-exports plugin

If we do not add it, I don't think we can use default exports (from our module entrypoints) at all. Forcing consumers to use .default is super ugly and kinda out of the question. Using just named exports is probably fine as well, except it'll force people who replace parts of Jest (e.g. the resolver) to do something like module.exports.resolver = resolver, which might feel unnatural. Not sure what the best tradeoff is, but const jestThing = require('jest-thing').default is not really an option. And the types generated by tsc doesn't understand module.exports when generating types, which is why I want to move to ES exports.

Also, make sure to enable --esModuleInterop with typescript.

We'll be using babel to transpile (and tsc for .d.ts files), so I don't think we need to do that? Or do I misunderstand that flag?

@milesj

This comment has been minimized.

Copy link

milesj commented Jan 16, 2019

Forcing consumers to use .default is super ugly and kinda out of the question.

Why not have a special index entry point that re-exports the default so consumers don't have to?

module.exports = require('./lib/index').default;

We'll be using babel to transpile (and tsc for .d.ts files), so I don't think we need to do that? Or do I misunderstand that flag?

Type checker (tsc) will still need the esModuleInterop, so it's best to just use it since that's the suggested path forward.

@rbuckton

This comment has been minimized.

Copy link

rbuckton commented Jan 16, 2019

Note that using add-module-exports will make it so that the typings in your .d.ts files will not reflect that actual export behavior of your code (i.e., you say export default foo in your TypeScript code, but its transpiled to module.exports = foo). This can cause problems when the TypeScript typings are used for JS consumers in editors like VS Code that use the TypeScript language service.

TypeScript has had a custom export = foo syntax for this case for a long time, which accurately reflects the actual export behavior of the transpiled code.

@SimenB

This comment has been minimized.

Copy link
Collaborator Author

SimenB commented Jan 16, 2019

Why not have a special index entry point that re-exports the default so consumers don't have to?

That won't mess up the typing information? The main field wouldn't point to a file that has a *.d.ts sibling. Maybe we can use typings field in package.json to get around it?

I've just written apps in TS never a library to be consumed as both CJS and TS (and UMD), so I'm not sure how to ensure all of those cases work without having to care about how they're written. So all my questions are in good faith! 😀


This can cause problems when the TypeScript typings are used for JS consumers in editors like VS Code that use the TypeScript language service.

How so, the .default will also be there? I guess they won't be able to do will be forced to add .default to satisfy the types?

TypeScript has had a custom export = foo syntax for this case for a long time, which accurately reflects the actual export behavior of the transpiled code.

Hmm, for the docs (https://www.typescriptlang.org/docs/handbook/modules.html):

When exporting a module using export =, TypeScript-specific import module = require("module") must be used to import the module.

Doesn't seem like a feasible solution?

@ahnpnl

This comment has been minimized.

Copy link
Contributor

ahnpnl commented Jan 16, 2019

I've just written apps in TS never a library to be consumed as both CJS and TS (and UMD), so I'm not sure how to ensure all of those cases work without having to care about how they're written. So all my questions are in good faith! 😀

Maybe you can take a look at how ng-packagr builds packages ? I'm using it to create Angular packages. It helps to generate esm, fesm and umd as well.

@rbuckton

This comment has been minimized.

Copy link

rbuckton commented Jan 16, 2019

This was a problem with Chalk for a time. Their d.ts file indicates export default, however this caused issues with JS imports at design time. If you used Chalk in a JS file in VS Code (with // @ts-check), you would get errors if you just tried to use const chalk = require('chalk'); because the typings didn't agree with the transpiled output. They added https://github.com/chalk/chalk/blob/master/index.js#L213 so that they still have an actual default on the export (meaning you would still have to do const chalk = require('chalk').default to get the correct types).

I'm not expressly discouraging you from using add-module-exports, but would rather encourage you to ensure that the end-user experience is what you would expect. In the worst case, add-module-exports has an option to add a default, similar to what Chalk does.

@Andarist

This comment has been minimized.

Copy link
Contributor

Andarist commented Jan 16, 2019

Using add-module-exports might also BREAK users using webpack and other tools using "stricter" semantics - webpack/webpack#7973 (if you plan to use both main & module fields in this case).

Either way - declaring one shape (in the types, and possibly exporting it too from ESM entry) and having different in CJS/main entry might lead to some really obscure situations and bugs. While .default or require('lib').lib are ugly (I agree on that!) they have a superior advantage - they "just work" and are safe in all scenarios.

Unfortunately CJS & ESM interop is a mess 🤷‍♂️

@lll000111

This comment has been minimized.

Copy link

lll000111 commented Jan 16, 2019

Yesterday on HackerNews: "Porting 30K lines of code from Flow to TypeScript (davidgom.es)"

HN discussion: https://news.ycombinator.com/item?id=18906405

As a heavy Flow and occasional TS user, I found the writing not too long, balanced and informative, so it may be of interest in the current context.


PS: By the way, I came here from this HN discussion posted today.

@theigor

This comment has been minimized.

Copy link

theigor commented Jan 16, 2019

@SimenB, probably a good thing this thread is closed as it's now on reddit (congrats?).

Quick question - since you're using tsc to generated d.ts files, why do you need @babel/plugin-transform-typescript - aren't you using typescript? As in, converting module.export = {} to export default {} has its place and it seems like you might be avoiding it unnecessarily.

EDIT: fixed typo

@niieani

This comment has been minimized.

Copy link
Contributor

niieani commented Jan 16, 2019

To add to the add-module-exports mess, there was a lot of issues around it, similar to described above (and the TypeScript support) in the ivanakimov/hashids.js#36 project.

@ndelangen

This comment has been minimized.

Copy link

ndelangen commented Jan 16, 2019

The typescript migration of storybook is going very well, I think it's a fantastic move for large libraries such as jest 👍

@anishkny

This comment has been minimized.

Copy link

anishkny commented Jan 16, 2019

I like that one can move gradually to TS since it’s a strict superset of JS.

I love being able to Cmd-click surf my way into the source code of whatever library I’m using in VS Code.

@jedmao

This comment has been minimized.

Copy link

jedmao commented Jan 16, 2019

FWIW, I've used this in the past for backwards compatibility with default exports, but not in a Babel project:

// @ts-ignore
exports.default.default = module.exports = Object.assign(exports.default, exports);
@SimenB

This comment has been minimized.

Copy link
Collaborator Author

SimenB commented Jan 16, 2019

how does test of typescript will be solved?, as typescript is a superset of javascript.

Jest can already test your TS tests, either using ts-jest or babel 7. However, that is off topic for this RFC


Quick question - since you're using tsc to generated d.ts files, why do you need @babel/plugin-transform-typescript - aren't you using typescript?

We'll want to keep using babel to transpile, mostly for the same reasons as outlined in https://davidgom.es/porting-30k-lines-of-code-from-flow-to-typescript/

It also allows us to migrate piece by piece instead of everything at once, and we can use @babel/preset-env. Last one is useful since TS seemingly has no plans to support anything other than language level targets: Microsoft/TypeScript#22306

Lastly, we would still be using babel to transpile our tests, so it eliminates having different code run in tests vs compiled output

@ciszak

This comment has been minimized.

Copy link

ciszak commented Jan 16, 2019

Personally, I've been a part of migrating all of Artsy's JavaScript to TypeScript, and while it's a little bit of churn at first (notably the .js -> .tskills git history, long PRs need a harder rebase, etc) it;'s paid off in terms of dev tooling across the board

@orta If you use git mv then git will preserve history. I'm sorry it's probably too late to rescue your repo's history, but might be useful next time :)

@jedmao

This comment has been minimized.

Copy link

jedmao commented Jan 16, 2019

@orta If you use git mv then git will preserve history. I'm sorry it's probably too late to rescue your repo's history, but might be useful next time :)

Usually best to put the git mv stuff in a separate commit as well, before making any changes to the new .ts file and to preserve history.

@wood1986

This comment has been minimized.

Copy link

wood1986 commented Jan 16, 2019

If you cannot 120% avoid :any, then don't do it.

@supersonicclay

This comment has been minimized.

Copy link

supersonicclay commented Jan 17, 2019

@orta If you use git mv then git will preserve history. I'm sorry it's probably too late to rescue your repo's history, but might be useful next time :)

Usually best to put the git mv stuff in a separate commit as well, before making any changes to the new .ts file and to preserve history.

Also, make sure you don't squash the move commit with other commits (i.e. during the pull request). Otherwise, git may no longer recognize the move and thus will lose history.

@kanekotic

This comment was marked as off-topic.

Copy link

kanekotic commented Jan 17, 2019

@SimenB Thanks a lot for your response :). Yes I agree this is not in the RFC, excuse me then if it was a bit off topic.

Jest can already test your TS tests, either using ts-jest or babel 7.

I just want to add my 2 cents that this assertion is partially correct. Jest is able to test the subset supported by javascript, but not the superset of typescript, for example testing implementation of an interface with instanceOf is not possible. My assumption is assertions cannot cover code that is not supported by javascript as typescript is not a runtime language, so seems to me a very complex problem to solve.

This Becomes a pain when doing TDD in Typescript as some assertions are impossible.

But as you mentioned this is a different discussion that can be taken in a different thread.

@lll000111

This comment was marked as off-topic.

Copy link

lll000111 commented Jan 17, 2019

OFF-TOPIC reply to off-topic comment

@kanekotic

testing implementation of an interface with instanceOf is not possible

Why would it? An interface is a purely virtual thing that does not actually exist in the JS runtime. The instanceof operator on the other hand tests whether the prototype property of a constructor appears anywhere in the prototype chain of an object. So you can test an instance of a "class" thing.

In addition, I can, however, use an interface without using classes, so the instanceof operator would be the wrong choice in any case.

I don't understand one bit of your comment either anyway. You test the code and that's what Jest does. I have no idea what you are coming up with here. The types are checked by TS at compile time, it'*s called static typing for a reason. So types are not tested by Jest or any other test tool.

If you want runtime type checks you can use a runtime type check package or write your own checks. Test runners like mocha or JS just test Javascript code. But yes, now we are completely going off topic even harder now that we even leave the scope of this project, not just the current issue.

@DanielRosenwasser

This comment has been minimized.

Copy link

DanielRosenwasser commented Jan 17, 2019

export = is not supported by @babel/plugin-transform-typescript

If it's a matter of export = and import = require() being unsupported in Babel, I think there's no problem adding the functionality. We just didn't because, well, we didn't assume anyone would want it for new code.

@SimenB

This comment has been minimized.

Copy link
Collaborator Author

SimenB commented Jan 17, 2019

Hey, thanks for chiming in!

I don't think we necessarily want it (as it's non standard beyond just types). And - at least for us - import = require() isn't relevant (I think).

However, if export = allow us to keep exporting CJS compatible code (without needing named or .default in the require for consumers), then it'd definitely help 🙂

On the other hand, seems like people have bad experience with interop, not sure we should "pollute" Babel with it. I played around with just writing my own babel plugin:

module.exports = ({template}) => {
  const moduleExportsDeclaration = template(`
    module.exports = ASSIGNMENT;
  `);
  return {
    name: 'jest-replace-ts-export-assignment',
    visitor: {
      TSExportAssignment(path) {
        path.replaceWith(
          moduleExportsDeclaration({ASSIGNMENT: path.node.expression}),
        );
      },
    },
  };
};

Seems to work great, so maybe we can use that in the places we need to keep module.exports for compatibility? Our current babel build already conditionally requires another custom babel plugin for custom files (if they can use lazy loading for dependencies or not), adding another plugin isn't an issue.

@DanielRosenwasser

This comment has been minimized.

Copy link

DanielRosenwasser commented Jan 18, 2019

The problem is that the .d.ts files that tsc --declaration generates will use export default, so you'll either need to

  1. run a declaration file transform (which can only be done using the TypeScript API), or
  2. run a regex on your output .d.ts file (which I'd probably try to avoid, but let's be real, we've all run regexes on worse)
@SimenB

This comment has been minimized.

Copy link
Collaborator Author

SimenB commented Jan 18, 2019

Seems to work? The d.ts file output looks like this:

/**
 * Copyright (c) Facebook, Inc. and its affiliates. All Rights Reserved.
 *
 * This source code is licensed under the MIT license found in the
 * LICENSE file in the root directory of this source tree.
 */
import { OptionsReceived, NewPlugin } from './types';
declare function prettyFormat(val: any, options?: OptionsReceived): string;
declare namespace prettyFormat {
    var plugins: {
        AsymmetricMatcher: NewPlugin;
        ConvertAnsi: NewPlugin;
        DOMCollection: NewPlugin;
        DOMElement: NewPlugin;
        Immutable: NewPlugin;
        ReactElement: NewPlugin;
        ReactTestComponent: NewPlugin;
    };
}
export = prettyFormat;
//# sourceMappingURL=index.d.ts.map

with input (imports removed):

function prettyFormat(...) {
  // ...
}

prettyFormat.plugins = {
  AsymmetricMatcher,
  ConvertAnsi,
  DOMCollection,
  DOMElement,
  Immutable,
  ReactElement,
  ReactTestComponent,
};

export = prettyFormat;

Hopefully not a bug that it works 😅

@AaronNGray

This comment has been minimized.

Copy link

AaronNGray commented Jan 18, 2019

BTW Do seriously look at the generated code from TypeScript its not very nice as compared to the type erased code from Flow.

@SimenB

This comment has been minimized.

Copy link
Collaborator Author

SimenB commented Jan 18, 2019

We'll be using babel to transpile, so it'll look the same as our current code does.

@rstuven

This comment has been minimized.

Copy link

rstuven commented Jan 19, 2019

Personally, I've been a part of migrating all of Artsy's JavaScript to TypeScript, and while it's a little bit of churn at first (notably the .js -> .ts kills git history, long PRs need a harder rebase, etc) it;'s paid off in terms of dev tooling across the board

@orta If you use git mv then git will preserve history. I'm sorry it's probably too late to rescue your repo's history, but might be useful next time :)

@orta @ciszak Or, if you renamed without using git mv, you can later use git add -A which "adds, modifies, and removes index entries to match the working tree." (https://git-scm.com/docs/git-add#git-add--A)

@lukepighetti

This comment was marked as off-topic.

Copy link

lukepighetti commented Jan 19, 2019

@AaronNGray That depends on what lib you select. Typescript does some compiling of things like async/await unless you are on ES2018 for example. If you're on ES2018 its like the types were just erased.

@AaronNGray

This comment was marked as off-topic.

Copy link

AaronNGray commented Jan 19, 2019

@lukepighetti so the code when targeting ES2018 is isomorphic to the TypeScript source ?

@jedmao

This comment was marked as off-topic.

Copy link

jedmao commented Jan 19, 2019

@lukepighetti so the code when targeting ES2018 is isomorphic to the TypeScript source ?

@AaronNGray when you compile TypeScript the types and interfaces disappear. The only thing that's left is down-level compilation and helpers to support older versions of ECMAScript. If your compile Target is ES2015 then that will be significant, but if it's ES2018 then it will be minimal. Since this project is a Node.js project and doesn't have to worry about old browsers and such, the transpilation result should be pretty close to the source.

In the next few months the TypeScript playground will be updated to allow you to play with compilation settings in such a way that this will be much easier to see.

@lukepighetti

This comment was marked as off-topic.

Copy link

lukepighetti commented Jan 19, 2019

I ain't gonna get into fancy words like "isomorphic" on a Saturday night. Compile Typescript with ES2018 lib and it will look like vanilla JS enough that there's no reason to complain about it.

@SimenB

This comment has been minimized.

Copy link
Collaborator Author

SimenB commented Jan 20, 2019

Please don't discuss transpiled output from tsc it here - it is completely off topic (we won't even use tsc to generate the code).

Also please don't discuss ways to keep git history in files - this issue should be focused on the the why's of the migration to TS, not the how's (at least not at that level - gotchas from other experiences migrating code is of course welcome! 🙂).

@dgreene1

This comment has been minimized.

Copy link

dgreene1 commented Jan 31, 2019

Thank you so much. Type safety in tests is a huge boost of productivity, especially when creating mock objects.

Speaking of which, here's a shameless plug for a thin wrapper library I wrote that keeps your mocks typesafe.

If it's of any use the core Jest team (@SimenB, et. al.) then I would be happy to fold it into Jest and to deprecate my library. :) Until then, maybe some of you will find it useful. :)

https://github.com/dgreene1/typeSafeJestSpy

@SimenB

This comment has been minimized.

Copy link
Collaborator Author

SimenB commented Feb 5, 2019

Jest 24.1.0 is out, so I've opened up a tracking issue for the migration: #7807. Any help and feedback people can provide is very much appreciated 🙂

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment