/*
 * Licensed to the Apache Software Foundation (ASF) under one
 * or more contributor license agreements.  See the NOTICE file
 * distributed with this work for additional information
 * regarding copyright ownership.  The ASF licenses this file
 * to you under the Apache License, Version 2.0 (the
 * "License"); you may not use this file except in compliance
 * with the License.  You may obtain a copy of the License at
 *
 * http://www.apache.org/licenses/LICENSE-2.0
 *
 * Unless required by applicable law or agreed to in writing,
 * software distributed under the License is distributed on an
 * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
 * KIND, either express or implied.  See the License for the
 * specific language governing permissions and limitations
 * under the License.
 */
package org.apache.openjpa.persistence.criteria;

import java.lang.reflect.Constructor;
import java.util.Arrays;
import java.util.Collections;
import java.util.List;

import javax.persistence.TupleElement;
import javax.persistence.criteria.CompoundSelection;
import javax.persistence.criteria.Selection;

import org.apache.openjpa.kernel.FillStrategy;
import org.apache.openjpa.lib.util.Localizer;
import org.apache.openjpa.persistence.TupleFactory;
import org.apache.openjpa.persistence.TupleImpl;

/**
 * Implements selection terms that are composed of other selection terms.
 *
 * @author Pinaki Poddar
 *
 * @since 2.0.0
 *
 */
class CompoundSelections {
    private static Localizer _loc = Localizer.forPackage(CompoundSelections.class);
    /**
     * Gets the strategy to fill a given compound selection.
     *
     */
    static <X> FillStrategy<X> getFillStrategy(Selection<X> s) {
        if (s instanceof CompoundSelectionImpl) {
            return ((CompoundSelectionImpl<X>)s).getFillStrategy();
        } else {
            return new FillStrategy.Assign<>();
        }
    }

    /**
     * Abstract implementation of a selection term composed of multiple selection terms.
     *
     */
    private abstract static class CompoundSelectionImpl<X> extends SelectionImpl<X> implements CompoundSelection<X> {
        private final List<Selection<?>> _args;

        public CompoundSelectionImpl(Class<X> cls, Selection<?>...args) {
            super(cls);
//            assertNoCompoundSelection(args);
            _args = args == null ? (List<Selection<?>>)Collections.EMPTY_LIST : Arrays.asList(args);
        }

        @Override
        public final boolean isCompoundSelection() {
            return true;
        }

        /**
         * Return selection items composing a compound selection
         * @return list of selection items
         * @throws IllegalStateException if selection is not a compound
         *           selection
         */
        @Override
        public final List<Selection<?>> getCompoundSelectionItems() {
            return Expressions.returnCopy(_args);
        }

        void assertNoCompoundSelection(Selection<?>...args) {
            if (args == null)
                return;
            for (Selection<?> s : args) {
                if (s.isCompoundSelection() && !(s.getClass() == NewInstance.class)) {
                    throw new IllegalArgumentException("compound selection " + s + " can not be nested in " + this);
                }
            }
        }

        abstract FillStrategy<X> getFillStrategy();

        @Override
        public StringBuilder asValue(AliasContext q) {
            StringBuilder buffer = new StringBuilder();
            for (int i = 0; i < _args.size(); i++) {
                buffer.append((((CriteriaExpression)_args.get(i)).asValue(q)));
                if (i+1 != _args.size())
                    buffer.append(", ");
            }
            return buffer;
        }

        @Override
        public StringBuilder asProjection(AliasContext q) {
            StringBuilder buffer = new StringBuilder();
            for (int i = 0; i < _args.size(); i++) {
                buffer.append((((CriteriaExpression)_args.get(i)).asProjection(q)));
                if (i+1 != _args.size())
                    buffer.append(", ");
            }
            return buffer;
        }
    }

    /**
     * A compound selection which is an array of its component terms.
     *
     * @param <X> type must be an array
     */
    static class Array<X> extends CompoundSelectionImpl<X> {
        public Array(Class<X> cls, Selection<?>... terms) {
            super(cls, terms);
            if (!cls.isArray()) {
                throw new IllegalArgumentException(cls + " is not an array. " + this + " needs an array");
            }
        }

        @Override
        public FillStrategy<X> getFillStrategy() {
            return new FillStrategy.Array<>(getJavaType());
        }
    }

    /**
     * A compound selection which is an instance constructed of its component terms.
     *
     * @param <X> type of the constructed instance
     */
    static class NewInstance<X> extends CompoundSelectionImpl<X> {
        private FillStrategy.NewInstance<X> strategy;
        public NewInstance(Class<X> cls, Selection<?>... selections) {
            super(cls, selections);
            strategy = new FillStrategy.NewInstance<>(findConstructor(cls, selections));
        }

        @Override
        public FillStrategy<X> getFillStrategy() {
            return strategy;
        }

        private Constructor<X> findConstructor(Class<X> cls, Selection<?>... selections) {
            Class<?>[] types = selections == null ? null : new Class[selections.length];
            if (selections != null) {
                for (int i = 0; i < selections.length; i++) {
                    types[i] = selections[i].getJavaType();
                }
            }
            try {
                return cls.getConstructor(types);
            } catch (NoSuchMethodException e) {
                throw new IllegalArgumentException(_loc.get("select-no-ctor", cls,
                    types == null ? "[]" : Arrays.toString(types)).getMessage());
            }
        }

        @Override
        public StringBuilder asValue(AliasContext q) {
            return new StringBuilder("NEW ").append(getJavaType().getName()).append("(")
               .append(super.asValue(q)).append(")");
        }
    }

    /**
     * A compound selection which is a Tuple composed of its component terms.
     *
     */
    static class Tuple extends CompoundSelectionImpl<javax.persistence.Tuple> {
        public Tuple(final Selection<?>[] selections) {
            super(javax.persistence.Tuple.class, selections);
        }

        @Override
        public FillStrategy<javax.persistence.Tuple> getFillStrategy() {
            List<Selection<?>> terms = getCompoundSelectionItems();
            TupleFactory factory = new TupleFactory(terms.toArray(new TupleElement[terms.size()]));
            return new FillStrategy.Factory<>(factory, TupleImpl.PUT);
        }
    }

    /**
     * A selection of terms that interprets its arguments based on target result type.
     *
     * @param <T> the target result type.
     */
    static class MultiSelection<T> extends CompoundSelectionImpl<T> {
        public MultiSelection(Class<T> result, final Selection<?>[] selections) {
            super(result, selections);
        }

        @Override
        public FillStrategy<T> getFillStrategy() {
            Class<?> resultClass = getJavaType();
            List<Selection<?>> terms = getCompoundSelectionItems();
            FillStrategy<?> strategy = null;
            if (javax.persistence.Tuple.class.isAssignableFrom(resultClass)) {
                TupleFactory factory = new TupleFactory(terms.toArray(new TupleElement[terms.size()]));
                strategy = new FillStrategy.Factory<>(factory,  TupleImpl.PUT);
           } else if (resultClass == Object.class) {
               if (terms.size() > 1) {
                   resultClass = Object[].class;
                   strategy = new FillStrategy.Array<>(Object[].class);
               } else {
                   strategy = new FillStrategy.Assign();
               }
           } else {
               strategy = resultClass.isArray()
                        ? new FillStrategy.Array(resultClass)
                        : new FillStrategy.NewInstance(resultClass);
           }
            return (FillStrategy<T>)strategy;
        }
    }
}
