[
https://issues.apache.org/jira/browse/ACCUMULO-1928?page=com.atlassian.jira.plugin.system.issuetabpanels:comment-tabpanel&focusedCommentId=13832099#comment-13832099
]
Dave Marion commented on ACCUMULO-1928:
---------------------------------------
The original intent, and maybe it's not documented as such, is that the lib
directory is for jars that likely won't change during the lifetime of the JVM.
The lib/ext directory is for code that could be changed *and* where the code
using the classes in the jars won't fail when the classes change. For example,
iterator classes are used during a scan/minc/majc session. It is useful to be
able to recompile your code to test your iterator without having to restart
Accumulo. Iterator classes are not evaluated against each other. Instances of
the objects and the classloaders are garbarge collected when no longer
referenced.
In 1.5 the classloader was reimplemented so that we could store classpath items
in locations other than local disk. We tried to keep the same dynamic loading
feature while adding the ability to create table specific classpaths with
parent delegation configurable. I think some issues have been identified where
the reloading is not working as desired which I am sure can and will be fixed
over time. I believe that during 1.5 we tried to replace all occurrences of
Class.forName() with AccumuloVfsClassLoader.loadClass(). It's possible that we
missed the one in CredentialHelper, or that the class was added afterwards.
I think the question is whether this part of the application is tolerant to
dynamic changes in the classpath. If it is not, then the jars should be placed
in lib.
> Class loader issues with building auth/auth/perm extensions
> -----------------------------------------------------------
>
> Key: ACCUMULO-1928
> URL: https://issues.apache.org/jira/browse/ACCUMULO-1928
> Project: Accumulo
> Issue Type: Bug
> Affects Versions: 1.5.0, 1.6.0
> Reporter: Michael Allen
>
> In the course of building extensions to take advantage of the
> {{Authenticator}}, {{Authorizor}} and {{PermissionHandler}} interfaces, I ran
> into several issues with how the extension classes were loaded (and reloaded)
> using {{AccumuloVFSClassloader}}. These issues ultimately meant that we had
> to make the decision to put these extensions into {{$ACCUMULO_HOME/lib}},
> rather than {{$ACCUMULO_HOME/lib/ext}}, so that they would not be reloaded
> and we would not encounter those issues.
> We should figure out how to fix up the classloader such that it makes it
> possible to put extensions like these into {{$$ACCUMULO_HOME/lib/ext}}, or we
> should document that it is not recommended to do so.
> So what were the problems?
> 1. In 1.5.0, Authentication tokens from within the extension could not be
> loaded via the normal creation pathway. This pathway in {{CredentialHelper}}
> includes the following line of code:
> {code}
> Object obj = Class.forName(tokenClass).newInstance();
> {code}
> In 1.6 this code has been replaced with a call in
> {{AuthenticationToken.AuthenticationTokenSerializer.deserialize()}} that uses
> {{AccumuloVFSClassloader}}, but I wonder if we shouldn't also make a 1.5.X
> change to at least make it possible to do it there? Otherwise anyone trying
> to create an extension for 1.5.X can only use {{PasswordToken}}s
> 2. Even when you do or don't fix #1, it leads you on to a different, less
> tractable problem.
> The {{Authenticatior}} etc. classes are loaded by {{SecurityOperation}}
> singleton, using {{AccumuloVFSClassloader}} and the objects are held within
> the singleton, which is held statically by the {{SecurityOperation}} class.
> That's all well and good, and let's call that {{AccumuloVSFClassloader}}
> instances that loaded those classes {{CL1}}.
> But now let's say you stick a new version of your JAR file into
> {{$ACCUMULO_HOME/lib/ext}}. {{AccumuloVFSClassloader}} happily creates a new
> classloader (call it {{CL2}}) for you and reloads your classes. *However*,
> the objects instantiated by {{SecurityOperation}} still owe their lineage to
> {{CL1}}. When a new authentication token comes in and gets loaded by
> {{CL2}}, its class name might look like a class from {{CL1}}, but when the
> {{Authenticator}} that came from {{CL1}} tries to cast that {{CL2}}-based
> object, you get {{ClassCastException}}s and are basically toast at that point.
> One possible fix here would be for {{AccumuloVFSClassloader}} to somehow
> notify interested parties that classes had reloaded so that they could flush
> away any old classes if desired. There'd be some synchronization issues
> around doing this, to make sure that the security stuff still worked reliably
> through this process. You'd have no guarantee, though, that the rest of the
> code wouldn't be hanging on to {{CL1}}-based object references and not
> letting go. Beating those bugs out may require too much coder discipline to
> be worth the feature.
> Another possible fix is to just say "don't do that for security-related
> features and put them in {{$ACCUMULO_HOME/lib}}. That's kind of giving up on
> being able to reload these at runtime, but maybe that's OK. Generally
> speaking, reloading your security assumptions might be something you want to
> take the tablet server down for.
--
This message was sent by Atlassian JIRA
(v6.1#6144)