001/*
002 *  Copyright 2018 Anyware Services
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 */
016package org.ametys.runtime.model;
017
018import java.util.ArrayList;
019import java.util.HashMap;
020import java.util.LinkedHashMap;
021import java.util.List;
022import java.util.Map;
023
024import org.apache.cocoon.ProcessingException;
025
026import org.ametys.runtime.model.exception.BadItemTypeException;
027
028/**
029 * View reference to a group of model items 
030 */
031public class ModelViewItemGroup extends AbstractViewItemGroup implements ModelViewItem<ModelItemGroup>
032{
033    private ModelItemGroup _definition;
034    
035    /**
036     * Creates a {@link ModelViewItemGroup} with the items of the given {@link ModelItemGroup}
037     * @param modelItem the model item group
038     * @return the created {@link ModelViewItemGroup}
039     * @throws IllegalArgumentException if the model item is <code>null</code>
040     */
041    public static ModelViewItemGroup of(ModelItemGroup modelItem) throws IllegalArgumentException
042    {
043        if (modelItem == null)
044        {
045            throw new IllegalArgumentException("Unable to create the view from a null model");
046        }
047        else
048        {
049            return ViewHelper.createViewItemContainer(List.of(modelItem));
050        }
051    }
052    
053    /**
054     * Creates a {@link ModelViewItemGroup} with the given items
055     * @param modelItem the model item containing items definitions
056     * @param itemPaths the paths of the items to put in the view item
057     * @return the created {@link ModelViewItemGroup}
058     * @throws IllegalArgumentException if the model item is <code>null</code> or if an item path is <code>null</code>, empty, or is not defined in the given model items
059     * @throws BadItemTypeException if a segment in a path (but not the last) does not represent a group item
060     */
061    public static ModelViewItemGroup of(ModelItemGroup modelItem, String... itemPaths) throws IllegalArgumentException, BadItemTypeException
062    {
063        if (modelItem == null)
064        {
065            throw new IllegalArgumentException("Unable to create the view from a null model");
066        }
067        else
068        {
069            return ViewHelper.createViewItemContainer(List.of(modelItem), itemPaths);
070        }
071    }
072    
073    public ModelItemGroup getDefinition()
074    {
075        return _definition;
076    }
077    
078    public void setDefinition(ModelItemGroup definition)
079    {
080        if (definition == null)
081        {
082            throw new IllegalArgumentException("Try to set a null definition to the model view item group");
083        }
084        _definition = definition;
085    }
086    
087    public String getName()
088    {
089        if (_definition != null)
090        {
091            return _definition.getName();
092        }
093        else
094        {
095            return null;
096        }
097    }
098    
099    public Map<String, Object> toJSON() throws ProcessingException
100    {
101        Map<String, Object> result = new HashMap<>();
102        
103        result.put("role", getRole());
104        
105        if (!_getChildrenForJSON().isEmpty())
106        {
107            Map<String, Object> elements = new LinkedHashMap<>();
108            List<Map<String, Object>> groups = new ArrayList<>();
109            for (ViewItem item : _getChildrenForJSON())
110            {
111                if (item instanceof ViewElement)
112                {
113                    elements.putAll(item.toJSON());
114                }
115                else
116                {
117                    groups.add(item.toJSON());
118                }
119            }
120            
121            if (!groups.isEmpty())
122            {
123                elements.put("groups", groups);
124            }
125            
126            result.put("elements", elements);
127        }
128        
129        if (getDefinition() != null)
130        {
131            result.putAll(getDefinition().toJSON(false));
132        }
133        
134        return result;
135    }
136    
137    private List<ViewItem> _getChildrenForJSON()
138    {
139        ElementDefinition switcher = getDefinition().getSwitcher();
140        if (switcher == null)
141        {
142            return getViewItems();
143        }
144        
145        List<ViewItem> childrenWithoutSwitcher = new ArrayList<>();
146        for (ViewItem child : getViewItems())
147        {
148            if (child instanceof ViewElement)
149            {
150                ElementDefinition childDefinitonReference = ((ViewElement) child).getDefinition();
151                if (!switcher.equals(childDefinitonReference))
152                {
153                    childrenWithoutSwitcher.add(child);
154                }
155            }
156        }
157        
158        return childrenWithoutSwitcher;
159    }
160}