001/*
002 * (C) Copyright 2014 Nuxeo SA (http://nuxeo.com/) and others.
003 *
004 * Licensed under the Apache License, Version 2.0 (the "License");
005 * you may not use this file except in compliance with the License.
006 * You may obtain a copy of the License at
007 *
008 *     http://www.apache.org/licenses/LICENSE-2.0
009 *
010 * Unless required by applicable law or agreed to in writing, software
011 * distributed under the License is distributed on an "AS IS" BASIS,
012 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
013 * See the License for the specific language governing permissions and
014 * limitations under the License.
015 *
016 * Contributors:
017 *     Anahide Tchertchian
018 */
019package org.nuxeo.ecm.platform.ui.web.component;
020
021import java.util.ArrayList;
022import java.util.Arrays;
023import java.util.Collection;
024import java.util.List;
025import java.util.Map;
026import java.util.Map.Entry;
027
028import javax.el.PropertyNotFoundException;
029import javax.faces.model.ListDataModel;
030import javax.faces.model.SelectItem;
031import javax.faces.model.SelectItemGroup;
032
033import org.apache.commons.logging.Log;
034import org.apache.commons.logging.LogFactory;
035
036/**
037 * Helper for select items management
038 *
039 * @since 6.0
040 */
041public abstract class SelectItemsFactory extends SelectItemFactory {
042
043    private static final Log log = LogFactory.getLog(SelectItemsFactory.class);
044
045    @Override
046    protected abstract String getVar();
047
048    @Override
049    protected abstract SelectItem createSelectItem();
050
051    @SuppressWarnings({ "unchecked", "rawtypes" })
052    public List<SelectItem> createSelectItems(Object value) {
053        Object varValue = saveRequestMapVarValue();
054        try {
055            List items = new ArrayList();
056            if (value instanceof ListDataModel) {
057                ListDataModel ldm = (ListDataModel) value;
058                value = ldm.getWrappedData();
059            }
060
061            if (value instanceof Object[]) {
062                Object[] array = (Object[]) value;
063                for (Object currentItem : array) {
064                    SelectItem[] res = createSelectItemsFrom(currentItem);
065                    if (res != null) {
066                        items.addAll(Arrays.asList(res));
067                    }
068                }
069            } else if (value instanceof Collection) {
070                Collection collection = (Collection) value;
071                for (Object currentItem : collection) {
072                    SelectItem[] res = createSelectItemsFrom(currentItem);
073                    if (res != null) {
074                        items.addAll(Arrays.asList(res));
075                    }
076                }
077            } else if (value instanceof Map) {
078                Map map = (Map) value;
079                for (Object obj : map.entrySet()) {
080                    Entry currentItem = (Entry) obj;
081                    SelectItem[] res = createSelectItemsFrom(currentItem);
082                    if (res != null) {
083                        items.addAll(Arrays.asList(res));
084                    }
085                }
086            } else if (value != null) {
087                log.warn("Could not map values to select items, value is not supported: " + value);
088            }
089            return items;
090        } finally {
091            restoreRequestMapVarValue(varValue);
092        }
093    }
094
095    protected SelectItem[] createSelectItemsFrom(Object item) {
096        if (item instanceof SelectItemGroup) {
097            return ((SelectItemGroup) item).getSelectItems();
098        } else {
099            SelectItem selectItem = null;
100            try {
101                putIteratorToRequestParam(item);
102                selectItem = createSelectItem();
103                removeIteratorFromRequestParam();
104            } catch (PropertyNotFoundException e) {
105                if (item instanceof SelectItem) {
106                    // maybe lookup was not necessary
107                } else {
108                    throw e;
109                }
110            }
111            if (selectItem != null) {
112                return new SelectItem[] { selectItem };
113            } else if (item instanceof SelectItem) {
114                // no transformation performed
115                return new SelectItem[] { (SelectItem) item };
116            }
117        }
118        return null;
119    }
120
121    @Override
122    public SelectItem createSelectItem(Object value) {
123        throw new IllegalArgumentException("Use createSelectItems instead");
124    }
125
126}