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.plugins.repository.data.holder;
017
018import java.util.Map;
019import java.util.Optional;
020
021import org.ametys.plugins.repository.data.external.ExternalizableDataProvider.ExternalizableDataStatus;
022import org.ametys.plugins.repository.data.holder.group.ModifiableModelAwareComposite;
023import org.ametys.plugins.repository.data.holder.group.ModifiableModelAwareRepeater;
024import org.ametys.plugins.repository.data.holder.values.SynchronizationContext;
025import org.ametys.plugins.repository.data.holder.values.SynchronizationResult;
026import org.ametys.runtime.model.ViewItemAccessor;
027import org.ametys.runtime.model.exception.BadDataPathCardinalityException;
028import org.ametys.runtime.model.exception.BadItemTypeException;
029import org.ametys.runtime.model.exception.UndefinedItemPathException;
030
031/**
032 * Interface for modifiable data containers with models
033 */
034public interface ModifiableModelAwareDataHolder extends ModifiableDataHolder, ModelAwareDataHolder
035{
036    @Override
037    public ModifiableModelAwareComposite getComposite(String compositePath) throws IllegalArgumentException, UndefinedItemPathException, BadItemTypeException, BadDataPathCardinalityException;
038    
039    @Override
040    public ModifiableModelAwareComposite getLocalComposite(String compositePath) throws IllegalArgumentException, UndefinedItemPathException, BadItemTypeException, BadDataPathCardinalityException;
041    
042    @Override
043    public ModifiableModelAwareComposite getExternalComposite(String compositePath) throws IllegalArgumentException, UndefinedItemPathException, BadItemTypeException, BadDataPathCardinalityException;
044    
045    @Override
046    public ModifiableModelAwareRepeater getRepeater(String repeaterPath) throws IllegalArgumentException, UndefinedItemPathException, BadItemTypeException, BadDataPathCardinalityException;
047    
048    @Override
049    public ModifiableModelAwareRepeater getLocalRepeater(String repeaterPath) throws IllegalArgumentException, UndefinedItemPathException, BadItemTypeException, BadDataPathCardinalityException;
050    
051    @Override
052    public ModifiableModelAwareRepeater getExternalRepeater(String repeaterPath) throws IllegalArgumentException, UndefinedItemPathException, BadItemTypeException, BadDataPathCardinalityException;
053    
054    /**
055     * {@inheritDoc}
056     * @throws UndefinedItemPathException if the given composite path is not defined by the model
057     * @throws BadDataPathCardinalityException if the definition of a part of the data path is multiple. Only the last part can be multiple
058     */
059    @Override
060    public ModifiableModelAwareComposite getComposite(String compositePath, boolean createNew) throws IllegalArgumentException, UndefinedItemPathException, BadItemTypeException, BadDataPathCardinalityException;
061    
062    /**
063     * Retrieves the local composite at the given path
064     * @param compositePath path of the externalizable composite to retrieve
065     * @param createNew <code>true</code> to create the composite if it does not exist, <code>false</code> otherwise
066     * @return the composite or <code>null</code> if createNew is <code>false</code> and value not exists or is empty
067     * @throws IllegalArgumentException if the given composite path is null or empty
068     * @throws BadItemTypeException if the stored value at the given path is not a composite
069     * @throws UndefinedItemPathException if the given composite path is not defined by the model
070     * @throws BadDataPathCardinalityException if the definition of a part of the data path is multiple. Only the last part can be multiple
071     */
072    public ModifiableModelAwareComposite getLocalComposite(String compositePath, boolean createNew) throws IllegalArgumentException, UndefinedItemPathException, BadItemTypeException, BadDataPathCardinalityException;
073    
074    /**
075     * Retrieves the external composite at the given path
076     * @param compositePath path of the externalizable composite to retrieve
077     * @param createNew <code>true</code> to create the composite if it does not exist, <code>false</code> otherwise
078     * @return the composite or <code>null</code> if createNew is <code>false</code> and value not exists or is empty
079     * @throws IllegalArgumentException if the given composite path is null or empty
080     * @throws BadItemTypeException if the stored value at the given path is not a composite
081     * @throws UndefinedItemPathException if the given composite path is not defined by the model
082     * @throws BadDataPathCardinalityException if the definition of a part of the data path is multiple. Only the last part can be multiple
083     */
084    public ModifiableModelAwareComposite getExternalComposite(String compositePath, boolean createNew) throws IllegalArgumentException, UndefinedItemPathException, BadItemTypeException, BadDataPathCardinalityException;
085    
086    /**
087     * Retrieves the repeater at the given path
088     * @param repeaterPath path of the repeater to retrieve
089     * @param createNew <code>true</code> to create the repeater if it does not exist, <code>false</code> otherwise
090     * @return the repeater or <code>null</code> if createNew is <code>false</code> and value not exists or is empty
091     * @throws IllegalArgumentException if the given repeater path is null or empty
092     * @throws BadItemTypeException if the stored value at the given path is not a repeater
093     * @throws UndefinedItemPathException if the given composite path is not defined by the model
094     * @throws BadDataPathCardinalityException if the definition of a part of the data path is multiple. Only the last part can be multiple
095     */
096    public ModifiableModelAwareRepeater getRepeater(String repeaterPath, boolean createNew) throws IllegalArgumentException, UndefinedItemPathException, BadItemTypeException, BadDataPathCardinalityException;
097    
098    /**
099     * Retrieves the local repeater at the given path
100     * @param repeaterPath path of the externalizable repeater to retrieve
101     * @param createNew <code>true</code> to create the repeater if it does not exist, <code>false</code> otherwise
102     * @return the repeater or <code>null</code> if createNew is <code>false</code> and value not exists or is empty
103     * @throws IllegalArgumentException if the given repeater path is null or empty
104     * @throws BadItemTypeException if the stored value at the given path is not a repeater
105     * @throws UndefinedItemPathException if the given composite path is not defined by the model
106     * @throws BadDataPathCardinalityException if the definition of a part of the data path is multiple. Only the last part can be multiple
107     */
108    public ModifiableModelAwareRepeater getLocalRepeater(String repeaterPath, boolean createNew) throws IllegalArgumentException, UndefinedItemPathException, BadItemTypeException, BadDataPathCardinalityException;
109    
110    /**
111     * Retrieves the external repeater at the given path
112     * @param repeaterPath path of the externalizable repeater to retrieve
113     * @param createNew <code>true</code> to create the repeater if it does not exist, <code>false</code> otherwise
114     * @return the repeater or <code>null</code> if createNew is <code>false</code> and value not exists or is empty
115     * @throws IllegalArgumentException if the given repeater path is null or empty
116     * @throws BadItemTypeException if the stored value at the given path is not a repeater
117     * @throws UndefinedItemPathException if the given composite path is not defined by the model
118     * @throws BadDataPathCardinalityException if the definition of a part of the data path is multiple. Only the last part can be multiple
119     */
120    public ModifiableModelAwareRepeater getExternalRepeater(String repeaterPath, boolean createNew) throws IllegalArgumentException, UndefinedItemPathException, BadItemTypeException, BadDataPathCardinalityException;
121    
122    /**
123     * Synchronizes the given values with the current ones
124     * @param <T> the type of the {@link SynchronizationResult}
125     * @param values the values to synchronize
126     * @return the {@link SynchronizationResult}
127     * @throws UndefinedItemPathException if a key in the given Map refers to a data that is not defined by the model
128     * @throws BadItemTypeException if the type defined by the model of one of the Map's key doesn't match the corresponding value
129     */
130    public <T extends SynchronizationResult> T synchronizeValues(Map<String, Object> values) throws UndefinedItemPathException, BadItemTypeException;
131    
132    /**
133     * Synchronizes the given values with the current ones
134     * @param <T> the type of the {@link SynchronizationResult}
135     * @param values the values to synchronize
136     * @param context the context of the synchronization
137     * @return the {@link SynchronizationResult}
138     * @throws UndefinedItemPathException if a key in the given Map refers to a data that is not defined by the model
139     * @throws BadItemTypeException if the type defined by the model of one of the Map's key doesn't match the corresponding value
140     */
141    public <T extends SynchronizationResult> T synchronizeValues(Map<String, Object> values, SynchronizationContext context) throws UndefinedItemPathException, BadItemTypeException;
142    
143    /**
144     * Synchronizes the given values with the current ones
145     * @param <T> the type of the {@link SynchronizationResult}
146     * @param viewItemAccessor The {@link ViewItemAccessor} for all items to synchronize
147     * @param values the values to synchronize
148     * @return the {@link SynchronizationResult}
149     * @throws UndefinedItemPathException if a key in the given Map refers to a data that is not defined by the model
150     * @throws BadItemTypeException if the type defined by the model of one of the Map's key doesn't match the corresponding value
151     */
152    public <T extends SynchronizationResult> T synchronizeValues(ViewItemAccessor viewItemAccessor, Map<String, Object> values) throws UndefinedItemPathException, BadItemTypeException;
153    
154    /**
155     * Synchronizes the given values with the current {@link ModifiableModelAwareDataHolder}'s ones
156     * @param <T> the type of the {@link SynchronizationResult}
157     * @param viewItemAccessor The {@link ViewItemAccessor} for all items to synchronize
158     * @param values the values to synchronize
159     * @param context the context of the synchronization
160     * @return the {@link SynchronizationResult}
161     * @throws UndefinedItemPathException if a key in the given Map refers to a data that is not defined by the model
162     * @throws BadItemTypeException if the type defined by the model of one of the Map's key doesn't match the corresponding value
163     */
164    public <T extends SynchronizationResult> T synchronizeValues(ViewItemAccessor viewItemAccessor, Map<String, Object> values, SynchronizationContext context) throws UndefinedItemPathException, BadItemTypeException;
165    
166    /**
167     * Sets the value of the data at the given path
168     * @param dataPath path of the data
169     * @param value the value to set. Give <code>null</code> to empty the value.
170     * @throws IllegalArgumentException if the given data path is null or empty
171     * @throws UndefinedItemPathException if the given data path is not defined by the model
172     * @throws BadItemTypeException if the type defined by the model doesn't match the given value to set
173     * @throws BadDataPathCardinalityException if the definition of a part of the data path is multiple. Only the last part can be multiple
174     */
175    public void setValue(String dataPath, Object value) throws IllegalArgumentException, UndefinedItemPathException, BadItemTypeException, BadDataPathCardinalityException;
176    
177    /**
178     * Sets the local value of the data at the given path
179     * @param dataPath path of the externalizable data
180     * @param localValue the local value to set. Give <code>null</code> to empty the value.
181     * @throws IllegalArgumentException if the given data path is null or empty
182     * @throws UndefinedItemPathException if the given data path is not defined by the model
183     * @throws BadItemTypeException if the type defined by the model doesn't match the given value to set
184     * @throws BadDataPathCardinalityException if the definition of a part of the data path is multiple. Only the last part can be multiple
185     */
186    public void setLocalValue(String dataPath, Object localValue) throws IllegalArgumentException, UndefinedItemPathException, BadItemTypeException, BadDataPathCardinalityException;
187    
188    /**
189     * Sets the external value of the data at the given path
190     * @param dataPath path of the externalizable data
191     * @param externalValue the external value to set. Give <code>null</code> to empty the value.
192     * @throws IllegalArgumentException if the given data path is null or empty
193     * @throws UndefinedItemPathException if the given data path is not defined by the model
194     * @throws BadItemTypeException if the type defined by the model doesn't match the given value to set
195     * @throws BadDataPathCardinalityException if the definition of a part of the data path is multiple. Only the last part can be multiple
196     */
197    public void setExternalValue(String dataPath, Object externalValue) throws IllegalArgumentException, UndefinedItemPathException, BadItemTypeException, BadDataPathCardinalityException;
198
199    /**
200     * Set the status of the data at the given path
201     * @param dataPath path of the externalizable data
202     * @param status the new status
203     * @throws IllegalArgumentException if the given data path is null or empty
204     * @throws UndefinedItemPathException if the given data path is not defined by the model
205     * @throws BadItemTypeException if there is a type issue while getting the parent (part of the dataPath without the last segment)
206     * @throws BadDataPathCardinalityException if the definition of a part of the data path is multiple. Only the last part can be multiple
207     */
208    public void setStatus(String dataPath, ExternalizableDataStatus status) throws IllegalArgumentException, UndefinedItemPathException, BadItemTypeException, BadDataPathCardinalityException;
209    
210    /**
211     * {@inheritDoc}
212     * @throws UndefinedItemPathException if the given data path is not defined by the model
213     * @throws BadDataPathCardinalityException if the definition of a part of the data path is multiple. Only the last part can be multiple
214     */
215    @Override
216    public void removeValue(String dataPath) throws IllegalArgumentException, UndefinedItemPathException, BadItemTypeException, BadDataPathCardinalityException;
217    
218    /**
219     * Removes the local value of the data at the given path
220     * @param dataPath path of the externalizable data
221     * @throws IllegalArgumentException if the given data path is null or empty
222     * @throws UndefinedItemPathException if the given data path is not defined by the model
223     * @throws BadItemTypeException if the value of the parent of the given path is not an item container
224     * @throws BadDataPathCardinalityException if the definition of a part of the data path is multiple. Only the last part can be multiple
225     */
226    public void removeLocalValue(String dataPath) throws IllegalArgumentException, UndefinedItemPathException, BadItemTypeException, BadDataPathCardinalityException;
227    
228    /**
229     * Removes the external value of the data at the given path
230     * @param dataPath path of the externalizable data
231     * @throws IllegalArgumentException if the given data path is null or empty
232     * @throws UndefinedItemPathException if the given data path is not defined by the model
233     * @throws BadItemTypeException if the value of the parent of the given path is not an item container
234     * @throws BadDataPathCardinalityException if the definition of a part of the data path is multiple. Only the last part can be multiple
235     */
236    public void removeExternalValue(String dataPath) throws IllegalArgumentException, UndefinedItemPathException, BadItemTypeException, BadDataPathCardinalityException;
237    
238    /**
239     * Removes the stored metadata (status and alternative value) for externalizable (or ex-externalizable) data
240     * @param dataPath path of the data
241     * @throws IllegalArgumentException if the given data path is null or empty
242     * @throws BadItemTypeException if the value of the parent of the given path is not an item container
243     * @throws UndefinedItemPathException if the given data path is not defined by the model
244     * @throws BadDataPathCardinalityException if the definition of a part of the data path is multiple. Only the last part can be multiple
245     */
246    public void removeExternalizableMetadataIfExists(String dataPath) throws IllegalArgumentException, BadItemTypeException, UndefinedItemPathException, BadDataPathCardinalityException;
247    
248    @Override
249    public Optional<? extends ModifiableModelAwareDataHolder> getParentDataHolder();
250    
251    @Override
252    public ModifiableModelAwareDataHolder getRootDataHolder();
253}