microsoft/TypeScript

Function name lost when compiling

sabrehagen opened this issue · 12 comments

I have identified a case when TypeScript compiled to JavaScript produces different functionality.

I have created a repro here: https://github.com/sabrehagen/tsc-function-repro

The crux of the issue is that tsc transforms a named function to an anonymous function, thereby changing the functionality as observed in the console.log output.

> git clone https://github.com/sabrehagen/tsc-function-repro

> yarn --cwd tsc-function-repro test:native
Function name is set correctly? true

> yarn --cwd tsc-function-repro test:compiled
Function name is set correctly? false

Input TypeScript

export const myFunction = () => {
}

console.log('Function name is set correctly?', myFunction.name === 'myFunction');

Compiled JavaScript

"use strict";
exports.__esModule = true;
exports.myFunction = function () {
};
console.log('Function name is set correctly?', exports.myFunction.name === 'myFunction');

Repro is on TS 3.6.3,

TS 3.5.1 Playground shows transpiled JS works fine

Duplicate of #6433.

Not a duplicate, though.

It looks like the transpiled JS between 3.5.1 and 3.6.3 are different, and it's causing changes in behaviour for OP.

3.5.1,

//transpiled JS
export const myFunction = () => {
};

Alleged by OP on 3.6.3,

//transpiled JS
exports.myFunction = function () {
};

In the GitHub repository he linked he's targeting ES3, which does not support arrow functions.

Ah. Right. No tsconfig.json file. So the default target is ES3

3.5.1, ES3 Playground

I should have realized something was off when I couldn't find a tsconfig.

@sabrehagen

https://www.typescriptlang.org/docs/handbook/compiler-options.html

https://www.typescriptlang.org/docs/handbook/tsconfig-json.html

Targeting esnext I observe the same result.

3.5.1, ES3 Playground

That playground repro isn't the same. It has been changed from export const to const, and this is the crux of the issue. When using export const this result is produced.

image

esnext 3.5.1 Playground is fine.


Are you sure your command is correct?
sabrehagen/tsc-function-repro@6e5aa56#diff-b9cfc7f2cdf78a7f4b91a753d10865a2R8

In particular,

tsc --project tsconfig.json index.ts

You should get the error,

error TS5042: Option 'project' cannot be mixed with source files on a command line.

If you run this command instead,

./node_modules/.bin/tsc --project tsconfig.json

You will get this output.

export const myFunction = () => {
};
console.log('Function name is set correctly?', myFunction.name === 'myFunction');

Conclusion

You're running tsc incorrectly.

Also, target es2015 or higher.

Take this,

"test:compiled": "yarn; yarn tsc --project tsconfig.json index.ts 2>&1 >/dev/null; node index.js",

Change to this,

"test:compiled": "yarn; yarn tsc --project tsconfig.json 2>&1 >/dev/null; node index.js",

Your tsc command has errors. But you never saw the errors because you keep throwing them away. You can't run from your problems forever.

Did you even read my previous comment?

Did you even read my previous comment?

No, I replied by email meaning I did not see your edit history.

Ah. Right. No tsconfig.json file. So the default target is ES3

Once I target es2015/ES6 or higher this is resolved.

By setting module: commonjs it reverted the success achieved through target: es2015.

Reproducable with:

git clone https://github.com/sabrehagen/tsc-function-repro
yarn --cwd tsc-function-repro test

This issue has been marked as a 'Duplicate' and has seen no recent activity. It has been automatically closed for house-keeping purposes.