Skip to content

Commit

Permalink
Change handling declaration export for classes from flow defs to TS defs
Browse files Browse the repository at this point in the history
Summary:
The diff introduces exporting classes in TS defs using export default syntax. Previously subsequent flow definitions (output produced by flowToFlowDefs):

```js
declare class Foo {}

declare export default typeof Foo;
```

were translated into the following TS definitions:

```js
declare class Foo {}

declare const $$EXPORT_DEFAULT_DECLARATION$$: typeof Foo;
export default $$EXPORT_DEFAULT_DECLARATION$$;
```

This exports constant that is of type Foo which is not the same as exporting typeof class Foo in TS. If there was another file that imported a Foo class and used it as a type, that would produce an error:

```js
import Foo from './foo';

interface Bar {
  values: Array<Foo> // 'Foo' refers to a value, but is being used as a type here.
}

```

The proposed solution is to export default class:

```js
declare class Foo {}
export default Foo;
```

This change is only applied to classes.

## Changelog:
[flow-api-translator] - Changed generated default exports for declaration exports for classes from flow defs to TS defs

Reviewed By: pieterv

Differential Revision: D69050761

fbshipit-source-id: e6cb54b84262ac1d7a64e05e63b54f23947d236c
  • Loading branch information
coado authored and facebook-github-bot committed Feb 4, 2025
1 parent f1d73e5 commit a998e2f
Show file tree
Hide file tree
Showing 3 changed files with 61 additions and 0 deletions.
Original file line number Diff line number Diff line change
@@ -0,0 +1,12 @@
/**
* Copyright (c) Meta Platforms, Inc. and affiliates.
*
* This source code is licensed under the MIT license found in the
* LICENSE file in the root directory of this source tree.
*
* @flow strict-local
* @format
*/

declare class Foo {}
declare export default typeof Foo;
Original file line number Diff line number Diff line change
@@ -0,0 +1,17 @@
// Jest Snapshot v1, https://goo.gl/fbAQLP

exports[`flowDefToTSDef export/declare/default/typeof/class 1`] = `
"/**
* Copyright (c) Meta Platforms, Inc. and affiliates.
*
* This source code is licensed under the MIT license found in the
* LICENSE file in the root directory of this source tree.
*
*
* @format
*/

declare class Foo {}
export default Foo;
"
`;
32 changes: 32 additions & 0 deletions tools/hermes-parser/js/flow-api-translator/src/flowDefToTSDef.js
Original file line number Diff line number Diff line change
Expand Up @@ -1237,6 +1237,38 @@ const getTransforms = (
// intentional fallthrough to the "default" handling
}

case 'TypeofTypeAnnotation': {
if (
declaration.type === 'TypeofTypeAnnotation' &&
declaration.argument.type === 'Identifier'
) {
const name = declaration.argument.name;
const exportedVar = topScope.set.get(name);
if (exportedVar != null && exportedVar.defs.length === 1) {
const def = exportedVar.defs[0];

switch (def.type) {
case 'ClassName': {
return {
type: 'ExportDefaultDeclaration',
declaration: {
type: 'Identifier',
decorators: [],
name,
optional: false,
loc: DUMMY_LOC,
},
exportKind: 'value',
loc: DUMMY_LOC,
};
}
}
}
}

// intentional fallthrough to the "default" handling
}

default: {
/*
flow allows syntax like
Expand Down

0 comments on commit a998e2f

Please sign in to comment.