-
Notifications
You must be signed in to change notification settings - Fork 228
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
WARNING: An illegal reflective access operation has occurred #101
Comments
Yes, XStream can either serialize only half of the object or avoid the illegal access. |
The ReflectionFactory API was updated in JDK 8 and JDK 9 to help custom serialization libraries work with modules that want to encapsulate their internals. Look for the methods that return a method handle to the common readXXX/writeXXX methods. |
@alan: So, the application can open its class types ... that will not help to access the default properties of a Properties instance, right? |
@joejni - Properties does not define a method to return the defaults in bulk. If there is a strong case to add such a method then it should be brought to core-libs-dev for discussion. |
Tell me, what is the work around for this? With the release of Java 9, is XStreem going to become an invalid library? |
The current workaround is to permit illegal access. You will always be able to serialize your own classes, since it is up to you to open that module for XStream. In case of 3rd party classes this might be different and you will have to write your own converters in future instead of using XStream's reflection-based converters assuming you are able to implement those converters so, that you can recreate the object. For some types in the JDK this might be no longer possible or only with limitations (e.g. currently no default entries for Property objects). This reflects at least my current knowledge of the restriction with the new module system. |
I want to refactor my code, so that XStream does not need to use reflection as much. I get I guess it's caused by reflection-based deserialization of Java collections like HashSet, could this be right (i don't think i serialize any TreeMaps directly)? Is there a way to exatcly determine the class that i need to write custom converters for, or to log where exactly xstream uses such "illegal" reflection? |
You may overwrite the setupConverters method and register only the converters you're going to use. Note, there's no problem using reflection-based converters for your own classes, if you open your module for XStream. |
r4282 2018-06-08 Note 1: the following warning shows up when starting mars-sim : WARNING: An illegal reflective access operation has occurred WARNING: Illegal reflective access by com.thoughtworks.xstream.core.util.Fields (file:/C:/Users/mk/.m2/repository/com/thoughtworks/xstream/xstream/1.4.9/xstream-1.4.9.jar) to field java.util.TreeMap.comparator See issue x-stream/xstream#101 Note 2: weblaf has resolved a java 9 compatibility issue due to the exception by "AA_TEXT_PROPERTY_KEY" in 1.2.9-SNAPSHOT. However, the xtream library is still using reflection that's deemed "illegal" in Java 9. See issue mgarin/weblaf#452 # CHANGES 1. Revert back weblaf-ui and weblaf-core to 1.2.9-SNAPSHOT for Java 9 compatibility. 2. Revise class relating to sponsors' mission objectives. Will code in the use of these objectives in future.
I think this is probably what you meant:
|
XStream reads package org.xmlpull.v1 from both xmlpull and xpp3.min Error:java: module xpp3.min reads package org.xmlpull.v1 from both xmlpull and xpp3.min :'( Sad Panda |
I just ran into this same issue with Java 10. As an FYI, this is still considered a WARNING in Java 10 as well (java version "10.0.1" 2018-04-17), so no difference between Java 9 and 10, yet anyway. |
@davewichers You should use a more recent version of maven-war-plugin cause this version you are using is about six years old...The most recent version 3.2.2 uses the most recent version of xstream 1.4.10 .... |
now,i have got the same problem when i use "mvn install",and it says"illegal reflective access by com.thoughtworks.xsteram.core.util.fields to field java.util.properties.defaults". it's very similar to your problem, so how do you solve this problem?i didn't get it from your talking....thanks |
i should tell you first that jdk10 and tomcat8.5 were used in my pc. |
I'm getting the same split package issue that @GedMarc is above, are people using |
What worked for me was to only use xstream without any other of its dependencies, which by luck skipped those problems. Serialization might be slower but that's not a problem for me. XStream x = new XStream(new DomDriver()); <!-- https://x-stream.github.io -->
<dependency>
<groupId>com.thoughtworks.xstream</groupId>
<artifactId>xstream</artifactId>
<version>1.4.10</version>
<exclusions>
<exclusion>
<groupId>xpp3</groupId>
<artifactId>xpp3_min</artifactId>
</exclusion>
<exclusion>
<groupId>xmlpull</groupId>
<artifactId>xmlpull</artifactId>
</exclusion>
</exclusions>
</dependency> |
Thanks @martinm1000 I will try that as well since performance isn't a concern |
XStream is not responsible for problems in depending libraries. If you use the Xpp3Driver directly, you can omit exclude xmlpull alone. |
I've tried to follow @joehni suggestion and override the setupConverters method.
@joehni if you agree with some of the above changes I could try to make a PR (time permitting). |
Hi, let's make some comments about your topics:
See, it is not, that I don't know what to do to make the compiler happy, I care more for the user's applications. |
@AlanBateman I got curious about your comments on The JavaDoc says: "ReflectionFactory supports custom serialization. Its methods support the creation of uninitialized objects, invoking serialization private methods for readObject, writeObject, readResolve, and writeReplace." Can you clarify whether it's acceptable for libraries to use this API and whether it'll stick around for the long run? It's not clear that would help resolve these issues, because XStream is indeed using internal fields of collections, apparently to try and avoid problems with constructing cyclic object graphs involving collections where there's no ability to correctly pre-calculate the hashCode for everything ahead of time (I can't say I fully understand this problem, as the object graphs must have been built originally without modifying hashCode post-insertion). But then again built-in Java object serialisation presumably supports such object graphs, so perhaps it is sufficient? |
Looking at the code in more detail, it's not entirely obvious why reflective access to the comparator field is still required on modern Javas. Rationale: At some point the JDK added an optimization where the comparator isn't called during putAll(). XStream knows about this and tests the JDK to see if it does skip calling compareTo() when using putAll(). When on such a JDK special codepaths are taken. In When deserialising the code paths get quite confusing. It looks like this has evolved over time and maybe can be simplified in ways that resolve at least one of the problems. Firstly, we either create a treemap before deserializing the comparator, if the comparator field was found via reflection, or alternatively it's created after the comparator is loaded if not. Then we populate the tree by first deserializing into a PresortedMap, and then using this code:
On modern JVMs with Jigsaw this path will always be taken. We forcibly set the comparator internal field, and then do an operation that doesn't actually use the comparator at all. If the comparator isn't used at all then calling hashCode() on partly constructed objects doesn't seem like it will occur. Yet we could have already constructed the TreeMap with the comparator via passing it in using the constructor, and this does happen ... but only when the comparator field doesn't exist. Due to this optimisation it seems that objects that are only partly deserialized can be added to a TreeMap even when their hashCode may change post-adding, resolving the concern @joehni discusses above. And at least from a quick look at the code, it doesn't seem like this requires accessing private fields. |
this is about to get fixed: see jenkinsci/jenkins#4944 |
I had the same problem, so I updated the 1.4.11.1 dependency to version 1.4.13 and solved the problem. Java 11
|
We fixed the problem by including the latest maven-war-plugin. In the pom:
|
r5490 2020-12-18 ## ISSUE 1. See x-stream/xstream#101 (comment) ## NEW 1. Add maven-war-plugin in pom.xml in an attempt to address illegal reflective access operation at the start when running mars-sim in Eclipse IDE.
It's worth nothing hat as of Java 17, the option to ignore the illegal-access warnings will no longer be there. Java 17 will always deny those accesses, unless you start slapping Java 16 is a shot across the bows, in that it denies the illegal accesses by default, whereas Javas 9-15 would by default log a warning on the first access and then continue as before. |
After wasting a week learning that there is simply no hope of ever getting my app to serialize using Moxy or Xstream, I'm ready to give up and just write code to directly emit xml. Can anyone suggest a better alternative? I inherited this code that worked perfectly using Castor, but Castor depended on methods not part of the official public Java API that are no longer available, and the amount of work needed to refactor the app to work with Moxy is beyond all hope since it doesn't support non-static inner classes and even when these are refactored out, it just throws one cryptic error after another. XStream seems similar, and throws the illegal-access right out of the chute. Honestly, I wish the original developer of this app had just written their own code to serialize the objects. Dependence on these Open Source non-mainstream libraries seems hopeless. Am I wrong? |
@cStuartHardwick I have been using XStream successfully since 2002. Its a great library and serves the purpose perfectly. A developer 20 years ago when it was still JDK3 can't know that the JDK16 is going to completely remove a feature it counts on. I get your bind, but Xstream is not the only library in this bind. Kryo, XStream, Moxy, etc are all facing these same issues. I personally think what you will see is a LOT of companies not move to JDK17 because of this and have so much legacy software that they can't upgrade they will just stay on JDK11 for years to come. |
XStream was great for JDK 1.3->1.7, but lets be fair guys, every single other framework caught up. Properties over Fields - it really is as simple as that. XStream has a strict field first policy, hence... issues. I must say though, I've seen the exact opposite hey @melloware / I'm hiring and the great ones are all going why JDK 8 it's legacy due to it's EOL date :) Banks I think, the really slow moving decision chain, will get really stuck if they don't embrace, I see a massive movement towards modularity now that people are getting comfortable and are understanding it better |
@GedMarc you might be right but I think its not just banks its a lot of government too. They don't have budgets to rewrite software that works fine just because a JDK upgrade so I think JDK11 LTS is what is going to be the long time lived JDK. Just my thought. It will take years before tons of software gets rewritten. I have a client that just moved to JDK8 2 years ago. 😄 |
Nobody stops you from registering the JavaBeanConverter as default for any type you were not willing to handle in an own converter. Yes, you will have to say goodby to the expectation, that XStream can handle any arbitrary type in the Java runtime out of the box. However, if you configure it to handle your own types (as you have to configure other frameworks as well), it will work.
All fine for new projects, but nobody is willing to invest a major amount of money just to get an application running on Java 17 that is running already for years without any problems. At first sight a customer gets no real benefit for all the money it takes to port such an application. |
I'm going to give Moxy a little more time to prove itself one way or the other, if only because its bindings file is a closer analog to the mapping file used by Castor and because that approach make more sense to me. If XStream only has good support for fields, that's a non-starter for me. I haven't exposed public fields in any language since....a long long time, and the original developers of my application didn't either. What I'm trying to do right now, in fact, is use a utility function to copy all the properties from the mega-class I want to marshal into a interim class that has only lightweight, serializable properties, in hopes I can get Moxy to work with that. The reason being that the real object contains lots and lots and lots of code for manipulating all the data that Moxy chokes on, and even when I refactored to expose only the properties through an interface, Moxy still tries to internally process all the code in the real object which still exists behind the reference, and no-go. Of course what I'm wondering is, if I'm going to the extra trouble of making a copy of the object just to make it serializeable, might I not be better just to modify that code to directly serialize it. But I haven't explored the use of factory classes yet, and I'm only a lightweight Java developer, so I may be letting frustration get the better of me. Thanks all. |
@joehni it certainly started like that I'm surprised though especially in the digitalization of everything movement?, What I've found lately (and for my comment), has the security vulnerabilities push not started to enforce the movement for you yet? Certainly from our side, security alone granted the entire budget to get off JDK 8 :) No one wants to get legally bound to oracle xD I think if it weren't for the latest global catastrophes 100% it would have gone for at least a decade more, but Auditors are getting very precise and pedantic, and all systems digitizing presents the enforcement of keeping with the time or not being compliant on any given front? |
Should I compile with: |
See also #262 for more info. |
I'm sorry but this thread is a mess so I didn't read it all, but I'd like to point out that I'm not using xstream directly, only through PowerMock, nor I am using AWT, but I'm still getting:
at least the reflection should be done on an if-need-be basis, not eagerly on first call to xstream. If all xstream has to work with are some primitive types, maybe a HashMap, it doesn't need to reflectively It's the weirdest developer experience in the world, having to add |
F:\Program Files\Landscape Editor 2D>java -cp lib/xstream.jar;lib/xpp3.jar;mapeditor.jar com.GUI
WARNING: An illegal reflective access operation has occurred
WARNING: Illegal reflective access by com.thoughtworks.xstream.core.util.Fields (file:/F:/Program%20Files/Landscape%20Editor%202D/lib/xstream.jar) to field java.util.Properties.defaults
WARNING: Please consider reporting this to the maintainers of com.thoughtworks.xstream.core.util.Fields
WARNING: Use --illegal-access=warn to enable warnings of further illegal reflective access operations
WARNING: All illegal access operations will be denied in a future release
The text was updated successfully, but these errors were encountered: