/*
 * See the NOTICE file distributed with this work for additional
 * information regarding copyright ownership.
 *
 * This is free software; you can redistribute it and/or modify it
 * under the terms of the GNU Lesser General Public License as
 * published by the Free Software Foundation; either version 2.1 of
 * the License, or (at your option) any later version.
 *
 * This software is distributed in the hope that it will be useful,
 * but WITHOUT ANY WARRANTY; without even the implied warranty of
 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
 * Lesser General Public License for more details.
 *
 * You should have received a copy of the GNU Lesser General Public
 * License along with this software; if not, write to the Free
 * Software Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA
 * 02110-1301 USA, or see the FSF site: http://www.fsf.org.
 */
package com.xpn.xwiki.internal.query;

import com.xpn.xwiki.XWikiContext;
import javax.inject.Inject;
import org.xwiki.component.annotation.Component;
import org.xwiki.component.manager.ComponentLookupException;
import org.xwiki.component.manager.ComponentManager;
import org.xwiki.component.phase.Initializable;
import org.xwiki.component.phase.InitializationException;
import org.xwiki.context.Execution;
import org.xwiki.query.QueryExecutor;
import org.xwiki.query.QueryExecutorProvider;

/**
 * A provider of QueryExecutor.
 * Allows providing of a QueryExecutor defined by the configuration.
 *
 * @version $Id$
 * @since 3.2M2
 */
@Component
public class ConfiguredQueryExecutorProvider implements QueryExecutorProvider, Initializable
{
    /** A means of getting QueryExecutors. */
    @Inject
    private ComponentManager manager;

    /** The execution, needed to get the main store hint which is used to choose the QueryExecutor. */
    @Inject
    private Execution exec;

    /** The QueryExecutor which we will provide. */
    private QueryExecutor queryExecutor;

    /**
     * {@inheritDoc}
     *
     * @see Initializable#initialize()
     */
    public void initialize() throws InitializationException
    {
        final XWikiContext context = (XWikiContext) exec.getContext().getProperty("xwikicontext");
        final String storeName = context.getWiki().Param("xwiki.store.main.hint", "default");
        try {
            this.queryExecutor = this.manager.lookup(QueryExecutor.class, storeName);
        } catch (ComponentLookupException e) {
            throw new InitializationException("Could not find a QueryExecutor with hint " + storeName
                                              + " which is the hint for the storage engine. "
                                              + "a QueryExecutor will not be available", e);
        }
    }

    /**
     * {@inheritDoc}
     *
     * @see QueryExecutorProvider#get()
     */
    public QueryExecutor get()
    {
        return this.queryExecutor;
    }
}

@@ -989,16 +989,41 @@
 Inject;%0A
+import org.slf4j.Logger;%0A
 import o
@@ -1181,114 +1181,8 @@
 er;%0A
-import org.xwiki.component.phase.Initializable;%0Aimport org.xwiki.component.phase.InitializationException;%0A
 impo
@@ -1535,23 +1535,8 @@
 ider
-, Initializable
 %0A%7B%0A 
@@ -1778,24 +1778,31 @@
 ec;%0A%0A    /**
+%0A     *
  The QueryEx
@@ -1834,116 +1834,440 @@
 ide.
- */%0A    private QueryExecutor queryExecutor;%0A%0A    /**%0A     * %7B@inheritDoc%7D%0A     *%0A     * @see Initializable#
+%0A     * Start off by injecting the default then later (once the XWiki object is initialized)%0A     * that will be swapped out for whatever type of storage the system is using as per it's configuration.%0A     */%0A    @Inject%0A    private QueryExecutor queryExecutor;%0A%0A    /** The man who cuts down trees. */%0A    @Inject%0A    private Logger logger;%0A%0A    /** Set to true once the query executor has been initialized. */%0A    private boolean 
 init
@@ -2276,78 +2276,230 @@
 lize
-()
+d;%0A
 %0A    
- */%0A    public void initialize() throws InitializationException
+/**%0A     * Switch the queryExecutor based on what main store is being used.%0A     * This is called lazily because the XWikiContext might not yet exist when this class is instantiated.%0A     */%0A    private void init()
 %0A   
@@ -2528,16 +2528,51 @@
 Context 
+context;%0A        try %7B%0A            
 context 
@@ -2631,24 +2631,399 @@
 icontext%22);%0A
+        %7D catch (NullPointerException e) %7B%0A            this.logger.warn(%22The QueryExecutor was called without an XWikiContext available. %22%0A                             + %22This means the old core (and likely the storage engine) is probably %22%0A                             + %22not yet initialized. The default QueryExecutor will be returned.%22, e); %0A            return;%0A        %7D%0A
         fina
@@ -3269,38 +3269,21 @@
   th
-row new InitializationExceptio
+is.logger.war
 n(%22C
@@ -3365,33 +3365,16 @@
         
-                 
 + %22 whic
@@ -3446,29 +3446,22 @@
     
-          
-       + %22a
++ %22the default
  Que
@@ -3483,25 +3483,29 @@
  not be 
-available
+used instead.
 %22, e);%0A 
@@ -3509,24 +3509,57 @@
 ;%0A        %7D%0A
+        this.initialized = true;%0A
     %7D%0A%0A    /
@@ -3666,32 +3666,100 @@
 tor get()%0A    %7B%0A
+        if (!this.initialized) %7B%0A            this.init();%0A        %7D%0A
         return t

Allow named queries to run with different storage engines. Fixed a problem which caused failure to start where a QueryManager was needed before the XWikiContext is available.