fix(ivy): incorrect injectable name logged in warning message on IE (#34305)
When we log DI errors we get the name of the provider via `SomeClass.name`. In IE functions that inherit from other functions don't have their own `name`, but they take the `name` from the lowest parent in the chain, before `Function`. I've added some changes to fall back to parsing out the function name from the function's string form. PR Close #34305
This commit is contained in:
parent
c2a904da09
commit
f79110c637
|
@ -223,17 +223,34 @@ export function getInheritedInjectableDef<T>(type: any): ɵɵInjectableDef<T>|nu
|
|||
(type[NG_PROV_DEF_FALLBACK] && type[NG_PROV_DEF_FALLBACK]()));
|
||||
|
||||
if (def) {
|
||||
const typeName = getTypeName(type);
|
||||
// TODO(FW-1307): Re-add ngDevMode when closure can handle it
|
||||
// ngDevMode &&
|
||||
console.warn(
|
||||
`DEPRECATED: DI is instantiating a token "${type.name}" that inherits its @Injectable decorator but does not provide one itself.\n` +
|
||||
`This will become an error in v10. Please add @Injectable() to the "${type.name}" class.`);
|
||||
`DEPRECATED: DI is instantiating a token "${typeName}" that inherits its @Injectable decorator but does not provide one itself.\n` +
|
||||
`This will become an error in v10. Please add @Injectable() to the "${typeName}" class.`);
|
||||
return def;
|
||||
} else {
|
||||
return null;
|
||||
}
|
||||
}
|
||||
|
||||
/** Gets the name of a type, accounting for some cross-browser differences. */
|
||||
function getTypeName(type: any): string {
|
||||
// `Function.prototype.name` behaves differently between IE and other browsers. In most browsers
|
||||
// it'll always return the name of the function itself, no matter how many other functions it
|
||||
// inherits from. On IE the function doesn't have its own `name` property, but it takes it from
|
||||
// the lowest level in the prototype chain. E.g. if we have `class Foo extends Parent` most
|
||||
// browsers will evaluate `Foo.name` to `Foo` while IE will return `Parent`. We work around
|
||||
// the issue by converting the function to a string and parsing its name out that way via a regex.
|
||||
if (type.hasOwnProperty('name')) {
|
||||
return type.name;
|
||||
}
|
||||
|
||||
const match = ('' + type).match(/^function\s*([^\s(]+)/);
|
||||
return match === null ? '' : match[1];
|
||||
}
|
||||
|
||||
/**
|
||||
* Read the injector def type in a way which is immune to accidentally reading inherited value.
|
||||
*
|
||||
|
|
|
@ -137,6 +137,9 @@
|
|||
{
|
||||
"name": "getOwnDefinition"
|
||||
},
|
||||
{
|
||||
"name": "getTypeName"
|
||||
},
|
||||
{
|
||||
"name": "getUndecoratedInjectableFactory"
|
||||
},
|
||||
|
|
Loading…
Reference in New Issue