Questions regarding InjectionApplicationFactory

From: <>
Date: Mon, 17 Oct 2011 08:37:10 +0000 (GMT)

Hi list,

I'm currently facing an issue with the InjectionApplicationFactory.
creating the application it performs an injectDefaultApplication().
This sets
a private field "defaultApplication" in the created application. But:
Applications can have a delegate. And delegates can have delegates

I have the following hierarchie of applications:

- defaultApplication: ApplicationImpl
- delegate: ApplicationType2
  - defaultApplication: null
  - delegate: ApplicationImpl.
    - defaultApplication: null

Now I have ApplicationType1 that has the defaultApplication and all
members in
the hierarchie don't. ApplicationType1 implements getResourceHandler()
following way:

public ResourceHandler getResourceHandler() {
  return getDelegate().getResourceHandler();

Now this get's passed to ApplicationType2 (which is an implementation
JSF 1.2) which call Mojarras Application's getResourceHandler(),
implemented like this:

public ResourceHandler getResourceHandler() {
  if (defaultApplication != null) {
    return defaultApplication.getResourceHandler();
  throw new UnsupportedOperationException();

Now you can obviously see that this is never going to work, as
defaultApplication will always be null.

I tried to work around this issue by using the attached patch. This
assumes that ever Application has to store it's delegate in a private
variable. The loop I added was meant to find this field (and therefore
delegate) and also set the default application in this delegate. Sadly
does not work (because app.getClass().getDeclaredFields() never returns
fields) and also is not really reliable and a hack.

Anyone has a better solution to this problem?

Thanks in advance,

--- com/sun/faces/application/
+++ com/sun/faces/application/
@@ -142,7 +142,22 @@ public class InjectionApplicationFactory extends
ApplicationFactory implements F
- defaultApplicationField.set(application,
+ Application app = application;
+ do {
+ defaultApplicationField.set(application,
+ boolean found = false;
+ for (Field field :
app.getClass().getDeclaredFields()) {
+ if (field.getType() == Application.class) {
+ field.setAccessible(true);
+ app = (Application) field.get(app);
+ found = true;
+ break;
+ }
+ }
+ if (!found) {
+ app = null;
+ }
+ } while (app != null);
             } catch (NoSuchFieldException nsfe) {
                 if (LOGGER.isLoggable(Level.FINE)) {