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

TeaVM produces wrong result, but no exception thrown #893

Open
rrarrarra opened this issue Mar 7, 2024 · 3 comments
Open

TeaVM produces wrong result, but no exception thrown #893

rrarrarra opened this issue Mar 7, 2024 · 3 comments

Comments

@rrarrarra
Copy link

import java.lang.reflect.Field;
import org.junit.Test;

public class JsonMapper {
	
	private static final class Person {
		public String name;
		public String age;
	}
	
	@Test
	public final void map() {
		final Field[] fields1 = new Person().getClass().getDeclaredFields();
		System.out.println("testA: " + fields1.length);
		
		final Field[] fields2 = Person.class.getDeclaredFields();
		System.out.println("testB: " + fields2.length);
	}
}

When this code gets executed locally as JUnit-Test, the output in the console is as expected:

testA: 2
testB: 2

.. so far, so good.

BUT now, when the exact same code runs in the browser via the teaVM-compiled classes.js, the output is:

testA: 0
testB: 0

...which is wrong :(

There are NO compile- or runtime errors! Everything seems OK, but its not.
I also checked on your website ( https://teavm.org/jcl-report/recent/jcl.html ), that all functionality, that I am using for this Test, is actually supported "green" by TeaVM.

Questions:

  1. Why are the two results different?
  2. Why are there no compile- or runtime errors?
  3. Why is every used functionality marked "green", when actually it is not supported?

Maybe I am just missing something here.
I am pretty new to the TeaVM stuff but I like the idea of generating javascript with java.

Thank you for your help.

PS, for the test I used the TeaVM-maven-plugin with version:

<artifactId>teavm-maven-plugin</artifactId>
 <version>0.9.2</version>
@konsoletyper
Copy link
Owner

Why is every used functionality marked "green", when actually it is not supported?

It is supported, but TeaVM is an AOT-compiler, while Java was never designed to be AOTed. For example, one of the most AOT-unfriendly thing is reflection (for example, Graal Native Image suffers from the same problem). You should let TeaVM know which fields are reflectable, see documentation.

Anyway, I'd like to strongly discourage using reflection with TeaVM. If you want to write something like your own serializer, prefer annotation processing.

@rrarrarra
Copy link
Author

Okay, thanks for pointing to annotation processing. I will try that.

Back to the problem:

In the documentation ( https://teavm.org/docs/runtime/java-classes.html ), there is written:

"By default, you can access metadata of classes and methods," ...

I do not know enough about AOT and how it is used in TeaVM, but dont you think, that there should be some kind of "error/exception message" popping up, if TeaVM detects something, that will not work in the compiled classes.js?

I mean, okay, you said: "try to avoid using reflection in your code".

But lets imagine, my code uses some 3rd-party library that deeply inside uses some reflection-code which I do not know about. Shouldnt TeaVM not produce any kind of warning like "Attention please: reflection code detected, please be warned that the code could produce unexpectd results!" ? Do I need to know or scan every line of code of the 3rd party lib in order to get to know if it uses reflection and therefor cannot be used together with TeaVM?

I do not feel very comfortable with using TeaVM, if TeaVM compiles the classes.js of the above example without any error/exception-message, and, like shown in the above example, produces WRONG results SILENTLY.

Is there any property-setting for the maven-plugin like for example

<ThrowExceptionOnUseOfAOTUnfriendlyStuff> true </ThrowExceptionOnUseOfAOTUnfriendlyStuff>

... or could something like that be implemented?

Please dont get me wrong. I do know that TeaVM-functionality is limited to specific stuff. And I totally agree to that. My point is, that it just should throw an exception, if the user (accidentally) tries to use stuff, that is not or cannot be supported.

Thanks and best regards

@konsoletyper
Copy link
Owner

but dont you think, that there should be some kind of "error/exception message" popping up, if TeaVM detects something, that will not work in the compiled classes.js

No, in general case this can't be implemented, since this functionality comes down to the halting problem, which is proven (by Alan Turing) to be unsolvable. In some particular case, i.e. report that there might be a chance, according to some sort speculation (of course, including some false positives), that reflection is actually used, and developer strictly prohibited usage of reflection, yes, it's possible. But this would require me not only to actually implement compiler flags, but also to document them, and users to comprehend a list of 100000 options (because it's not only reflection, but many-many other things). Since I don't have team of 10 developers who would maintain TeaVM full-time and since I don't have request similar to yours once a year, for me it's simpler just to answer your particular question and doing nothing.

Anyway, if I had a chance to implement this functionality, you would get a message that "reflection is not working" and I would have to spend these 5 minutes answering you. So from my prospective business value (like saving my time or user's time) is quite low and this task has very low priority.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

No branches or pull requests

2 participants