Skip to content
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

dart2js: runtimeType.toString() is wrong when using minify #9217

Closed
DartBot opened this issue Mar 17, 2013 · 19 comments
Closed

dart2js: runtimeType.toString() is wrong when using minify #9217

DartBot opened this issue Mar 17, 2013 · 19 comments
Labels
closed-not-planned Closed as we don't intend to take action on the reported issue P2 A bug or feature request we're likely to work on type-bug Incorrect behavior (everything from a crash to more subtle misbehavior) web-dart2js

Comments

@DartBot
Copy link

DartBot commented Mar 17, 2013

This issue was originally filed by fra...@igindo.com


Dart classes have a 'runtimeType' property

DivElement foo = new DivElement();

print(foo.runtimeType); // prints 'DivElement'

However, with the minify flag on, you get the minified class name returned

// --minify TRUE
print(foo.runtimeType); // prints 'cB' for example

@kasperl
Copy link

kasperl commented Mar 18, 2013

Is this using the dart2dart minifier?


Added NeedsInfo label.

@DartBot
Copy link
Author

DartBot commented Mar 18, 2013

This comment was originally written by fra...@igindo.com


I only tested using dart2js, however dart2dart would probably have the same problem?

@kasperl
Copy link

kasperl commented Mar 18, 2013

Thanks for the update.


Added Area-Dart2JS, Triaged labels.
Changed the title to: "dart2js: runtimeType.toString() is wrong when using minify".

@peter-ahe-google
Copy link
Contributor

As far as I know, this is the expected behavior.


cc @gbracha.

@DartBot
Copy link
Author

DartBot commented Mar 20, 2013

This comment was originally written by fra...@igindo.com


I use runtimetype to dynamically add default CSS styles at runtime,
mirrors would be a valid alternative, but won't that imply a performance penalty over using something simple like runtimeType?

Perhaps you could provide a new type property next to runtimeType which holds the original class name as a String?

@peter-ahe-google
Copy link
Contributor

The underlying problem is this: a big part of the size reduction we achieve with minification is due to using shorter names. Retaining the original name is adds an overhead which we deem is too large.

We are working on solving these issues, but if you really care about download size, you'll probably have do something like this:

getName(foo) {
  if (foo is DivElement) return 'DivElement';
  ...
}

We'll probably add annotations to control which names are preserved and which aren't. In that case, you might be able to write something like this:

@UseClassNames(subclassesOf: const [Element])
getName(foo) => '${foo.runtimeType}';

@kasperl
Copy link

kasperl commented Apr 22, 2013

Added this to the Later milestone.

@kasperl
Copy link

kasperl commented May 23, 2013

Added TriageForM5 label.

@kasperl
Copy link

kasperl commented May 28, 2013

Removed TriageForM5 label.

@kasperl
Copy link

kasperl commented Jul 10, 2014

Removed this from the Later milestone.
Added Oldschool-Milestone-Later label.

@kasperl
Copy link

kasperl commented Aug 4, 2014

Removed Oldschool-Milestone-Later label.

@floitschG
Copy link
Contributor

Issue #20457 has been merged into this issue.

1 similar comment
@floitschG
Copy link
Contributor

Issue #20457 has been merged into this issue.

@DartBot
Copy link
Author

DartBot commented Nov 7, 2014

This comment was originally written by youyou333...@gmail.com


I think it would be better to mention this behavior in runtimeType doc until this is fixed

@kevmoo kevmoo added P2 A bug or feature request we're likely to work on type-bug Incorrect behavior (everything from a crash to more subtle misbehavior) and removed triaged labels Feb 29, 2016
@rakudrama
Copy link
Member

This is not just a minification issue. All classes have different JavaScript names, and the JavaScript name is strongly related (1-1) to the runtimeType name. We would have to substantially change the type representation to fix this. I'm not saying we should not fix this, just that it has a nontrivial implementation cost.

We could store the full name against the minified name. This would increase the size of minifed programs by about 5%. Many of our customers do not believe this cost is justified and would need a way to make it opt-in.

A consequence of the 1-1 correspondence is that even unminified programs can print the 'wrong' name.
The following program prints:

Thing
Thing0
-------- 9217.dart --------
import '9217a.dart' as a;
import '9217b.dart' as b;

main() {
  print(new a.Thing().runtimeType);
  print(new b.Thing().runtimeType);
}
-------- 9217a.dart --------
class Thing {}
-------- 9217b.dart --------
class Thing {}

@rakudrama rakudrama added the closed-not-planned Closed as we don't intend to take action on the reported issue label Apr 25, 2017
@nghuyy
Copy link

nghuyy commented Apr 13, 2022

I have same error with JSON Object. On Android, it is _InternalLinkedHashMap<String, dynamic>, on Web it's _JsonMap. But on release is mininy:ds. Don't use dynamic.runtimeType, replace with "object is Map<String,dynamic>" instead

@RoarGronmo
Copy link

Found this to be a problem manifesting when building a Flutter project for release, if built for debug, the names where correct. example:

...
await ApiGuardSystemsService().getAssets(
...
  ).then((rawAssets) async {

    print("rawAssets.runTimeType = ${rawAssets.runtimeType.toString()}");

    if(rawAssets.runtimeType == List<dynamic>) {
      await globals.mOfficeDatabase.transaction(() async {
        for (var rawAsset in rawAssets) {
          print("inserting rawAsset");
...
    print("getAssets done !");
   });  

Here I get the following print results in console:
Debug build:

rawAssets.runTimeType = List<dynamic>
inserting rawAsset
getAssets done !

In release build:

rawAssets.runTimeType = minified:H<dynamic>
getAssets done !

You see, my expected type check didn't checkout because the expected runtimeType is different in release vs debug...

Will file an issue for this in Flutter/dart...

Thanx for mentioned this here!

@mraleph
Copy link
Member

mraleph commented Nov 16, 2023

@RoarGronmo Don't compare types like this. Use is checks instead. <dynamic>[].runtimeType is not guaranteed to be exactly List<dynamic>, it can be _SomeImplementationOfList<dynamic>.

Object.runtimeType exists primarily for debugging purposes (e.g. to print it), any sort of code that dispatches on it should be avoided. Type.toString is not guaranteed to return any readable form of the type that has any relationship to the original source. For convenience reasons implementations tend to return something that either matches name in the source or can be mapped back to the original source through deobfuscation map, but this is not really a specified behavior and any reliance on it should be avoided.

@RoarGronmo
Copy link

RoarGronmo commented Nov 16, 2023

Well...
My undestanding of dynamic is beginning to be loose...
image

When it says it is just dynamic at first..
image

I feel I have a "right to know" what type of the dynamic actually is.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
closed-not-planned Closed as we don't intend to take action on the reported issue P2 A bug or feature request we're likely to work on type-bug Incorrect behavior (everything from a crash to more subtle misbehavior) web-dart2js
Projects
None yet
Development

No branches or pull requests

9 participants