Hi Henrique

Thanks for the feedbacks.

I've been short on time recently, so I quickly tried your fix but I
encounter the following issue:
java.lang.reflect.InvocationTargetException
        at sun.reflect.NativeMethodAccessorImpl.invoke0(Native Method)
        at 
sun.reflect.NativeMethodAccessorImpl.invoke(NativeMethodAccessorImpl.java:39)
        at 
sun.reflect.DelegatingMethodAccessorImpl.invoke(DelegatingMethodAccessorImpl.java:25)
        at java.lang.reflect.Method.invoke(Method.java:597)
        at com.resurgences.guice.WOInject.loadClass(WOInject.java:158)
        at com.resurgences.guice.WOInject.main(WOInject.java:117)
        at 
com.resurgences.demo.admin.ApplicationAdminDemo.main(ApplicationAdminDemo.java:14)
Caused by: java.lang.LinkageError: loader (instance of
sun/misc/Launcher$AppClassLoader): attempted  duplicate class
definition for name: "com/webobjects/foundation/_NSUtilities"
        at java.lang.ClassLoader.defineClass1(Native Method)
        at java.lang.ClassLoader.defineClassCond(ClassLoader.java:631)
        at java.lang.ClassLoader.defineClass(ClassLoader.java:615)
        at java.lang.ClassLoader.defineClass(ClassLoader.java:465)
        ... 7 more

As I should be sleeping, I don't have much time to investigate right
now, but I'll soon. Line numbers doesn't match your code since there
are the extra guice stuff in there as well. Furthermore, I effectively
have two instances of this class on my classpath (ERExtensions and
JavaFoundations classes), so it doesn't look incorrect.

BTW, are you sure Guice AOP works for binding realized through a
provider? I have the memory it doesn't... If not, just injecting
members after objects creation through _NSUtilities looks like good
enough.

Thanks again for your helpful answers :)

best
joseph

2012/6/10 Henrique Prange <[email protected]>:
> Joseph,
>
> I have created a issue [1] to track this problem.
>
> There is a new commit in the hotfix-classloading branch that tries to solve 
> the problem. It removes the dependency on a custom class loader. It's still 
> very experimental, but I would like to know if this patch solves your problem.
>
> There is one requirement: you have to create a AppRunner class, and start 
> your application from it. Here is an example of a very simple runner:
>
> public class AppRunner {
>    public static void main(String[] args) {
>        WOInject.init("your.app.Application", args);
>    }
> }
>
> I've deployed a new WOInject SNAPSHOT to the WOCommunity repository. Just 
> update to the 1.1-SNAPSHOT version in your pom to download the latest changes.
>
> [1]https://github.com/hprange/woinject/issues/7
>
> Cheers,
>
> Henrique
>
> On 07/06/2012, at 23:30, Henrique Prange wrote:
>
>> Hi Joseph,
>>
>> On 06/06/2012, at 04:04, Joseph Pachod wrote:
>>
>>> Hi all
>>>
>>> We've been using WOInject for a few months and encountered two issues
>>> due to the classloader manipulation done at startup (the one to enable
>>> interception through javassist, in the WOInject class).
>>>
>>
>> You're not alone. I've faced problems because of the classloader 
>> manipulation too. Take a look at issue #2 [1]. I've provided a simple fix, 
>> but I know it is not a definitive solution.
>>
>>> The first issue is a known Guice 2.0 bug
>>> (http://code.google.com/p/google-guice/issues/detail?id=343). This one
>>> pops up when from Guice grabs some class from another classloader that
>>> the one it was started in. In our case, it meant Guice was grabing
>>> some class from the default class loader instead of the the javassist
>>> one. It appeared in a very unexpected way: suddenly one binding was
>>> causing the whole application to break down. Finally, we had to switch
>>> to Guice 3.0, which incorporates the bug fix and avoids the issue to
>>> show up another time somewhere else. Turned out since  that the
>>> woinject repo on github states "Guice 3.0" as a requirement. Was this
>>> bug the reason for it?
>>>
>>
>> In fact, I was not aware of this Guice bug until now. :)
>>
>> The WOInject code responsible for object instantiation was heavily inspired 
>> by the AssistedInject module. It requires the bind().toConstructor() method 
>> API added in Guice 3.0. To support Guice 2.0, WOInject would not be able to 
>> take advantage of the AOP support, for instance.
>>
>>> The second issue is a security exception when trying to encrypt some
>>> file. The issue was boiled down to a classloader one again, the
>>> required class being "on the bootclasspath" instead of the current
>>> classloader (the javassist one). I append the stack trace to the end
>>> of this mail, if some one wants to have a look at it.
>>>
>>
>> This problem seems to be related to the issue #2 mentioned above. Clearly, 
>> an alternative is required to the Javassist classloader to solve this 
>> problem.
>>
>>> In order to get rid of this bug, we ended removing the classloading
>>> trick and, instead, using our own _NSUtilities where we do the
>>> injector.injectMembers(newInstance) ourselves. In order to make it
>>> possible, we made sure our own version of this class came on top of
>>> the classpath provided to the application (thanks to Maven). Since it
>>> works again.
>>>
>>> What do you think of that ? Could it be done as well in WOInject ?
>>>
>>
>> Yes. It could be done. However, this solution also has some problems:
>>
>> 1) It doesn't scale: that is the same approach employed by Wonder. We can't 
>> apply this kind of solution every time, for every framework.
>>
>> 2) It is subject to license issues.
>>
>> 3) It makes the user responsible for the solution of the problem. This 
>> problem is an extension of the first problem. In the beginning, ERExtensions 
>> should come first in the classpath. Then ERFoundation and ERWebObjects were 
>> created and took precedence. With this solution, WOInject must come before 
>> those libraries.
>>
>> 4) I'm not sure this solution works in a JEE environment.
>>
>> Changing the behavior of core classes of WebObjects is a general problem 
>> that anyone developing WO apps/frameworks face sooner or later. IMHO, we 
>> should develop a common solution in Wonder, some kind of ERPatcher 
>> framework. This would enable us to solve long-standing problems without 
>> violating the Apple license and in an organized manner. I really would like 
>> to know what others think about it. I'm really inclined to implement this 
>> framework, as soon as I figure out how. :)
>>
>>> Indeed, we were planning to use WOInject once the "WOInjectProposal"
>>> on github would have been incorporated.
>>>
>>
>> I'm planning to add this feature in the next release. I'm really out of time 
>> right now, but it is in my TODO list.
>>
>>> Personally, getting rid of classloader manipulations would be a plus
>>> IMHO. It removes a whole bunch of potential issues, from memory leaks
>>> to "classes from the wrong classloader".
>>>
>>
>> Classloader manipulations are complicated and can have side effects. 
>> However, it has been widely used in Java frameworks (including Guice). I'll 
>> try to produce a better solution. I'll ping you as soon as I have a new 
>> version for testing.
>>
>>> For sure, I may miss some good points of javassist, so I'm really
>>> eager to read you back. Alternative solutions are also welcome, but
>>> the few I could make up (using an agent instead of classloader
>>> manipulation for example) don't come for cheap neither: overall class
>>> shadowing and classpath ordering look like the less impacting option.
>>>
>>
>> I also would like to avoid using an agent to solve this problem. IMHO, we 
>> have the following alternatives:
>>
>> 1) A better custom classloader: the Javassist classloader is just an example 
>> of how to create a Classloader able to load Javassist manipulated classes. 
>> We can write a better one that loads only the _NSUtilities class from 
>> Javassist and delegates everything else to the parent classloader.
>>
>> 2) Loading the manipulated classes right on the System classloader: the 
>> manipulated _NSUtilities could be loaded directly in the System classloader 
>> through reflection. I don't know what are the side effects of this solution 
>> yet.
>>
>> 3) Classpath ordering: as you mentioned, avoids runtime problems at the cost 
>> of delegating the responsibility to the user of the library.
>>
>> I'll try to implement the first solution and send you a new version of 
>> WOInject as soon as possible.
>>
>> [1]https://github.com/hprange/woinject/issues/2
>>
>> Cheers,
>>
>> Henrique
>

 _______________________________________________
Do not post admin requests to the list. They will be ignored.
Webobjects-dev mailing list      ([email protected])
Help/Unsubscribe/Update your Subscription:
https://lists.apple.com/mailman/options/webobjects-dev/archive%40mail-archive.com

This email sent to [email protected]

Reply via email to