001/*
002 *  Copyright 2020 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.odf.content;
017
018import java.util.ArrayList;
019import java.util.Collections;
020import java.util.List;
021import java.util.Map;
022
023import org.apache.commons.lang3.StringUtils;
024
025import org.ametys.cms.content.CopyReport;
026import org.ametys.cms.contenttype.MetadataDefinition;
027import org.ametys.cms.repository.Content;
028import org.ametys.odf.courselist.CourseList;
029import org.ametys.odf.program.TraversableProgramPart;
030import org.ametys.plugins.repository.metadata.CompositeMetadata;
031import org.ametys.plugins.repository.metadata.ModifiableCompositeMetadata;
032
033/**
034 * Component used for copy of content with some override for ODF content
035 * See {@link org.ametys.cms.content.CopyContentMetadataComponent}.
036 *
037 */
038public class CopyContentMetadataComponent extends org.ametys.cms.content.CopyContentMetadataComponent
039{
040    /** The avalon role */
041    @SuppressWarnings("hiding")
042    public static final String ROLE = CopyContentMetadataComponent.class.getName();
043    
044    @Override
045    public void copyContentReferenceMetadata(CompositeMetadata baseMetaHolder, ModifiableCompositeMetadata targetMetaHolder, MetadataDefinition metadataDefinition, String metadataPath, Map<String, Object> copyMap, Map<String, Object> innerCopyMapInputs, CopyReport copyReport)
046    {
047        String metadataName = metadataDefinition.getName();
048        boolean referenceMode = copyMap == null || StringUtils.equals((String) copyMap.get("$mode"), "reference");
049        
050        // Override for the ODF specific case for copy of a ProgramPart in reference mode
051        // All child contents can be referenced EXCEPT the course lists which have to be always be copied (created by copy)
052        if (metadataName.equals(TraversableProgramPart.CHILD_PROGRAM_PARTS) && referenceMode)
053        {
054            boolean isMultiple = metadataDefinition.isMultiple();
055            
056            if (baseMetaHolder.hasMetadata(metadataName))
057            {
058                String[] baseContentIds = baseMetaHolder.getStringArray(metadataName);
059                List<String> targetContentIds = new ArrayList<>();
060                
061                for (String baseContentId : baseContentIds)
062                {
063                    Content baseContent = _resolver.resolveById(baseContentId);
064                    if (baseContent instanceof CourseList)
065                    {
066                        // Force copy of child course lists (force create mode)
067                        String[] copiedCourseListId = _copyReferencedContents(new String[] {baseContentId}, copyMap, innerCopyMapInputs, copyReport);
068                        if (copiedCourseListId.length > 0)
069                        {
070                            targetContentIds.add(copiedCourseListId[0]);
071                        }
072                    }
073                    else
074                    {
075                        // keep reference for other children
076                        targetContentIds.add(baseContentId);
077                    }
078                }
079                
080                if (!targetContentIds.isEmpty())
081                {
082                    copyReport.addContentReferenceValues(metadataPath, isMultiple ? targetContentIds : targetContentIds.get(0));
083                }
084                else if (targetMetaHolder.hasMetadata(metadataName))
085                {
086                    // reset attribute 
087                    copyReport.addContentReferenceValues(metadataPath, isMultiple ? Collections.EMPTY_LIST : null);
088                }
089            }
090            else if (targetMetaHolder.hasMetadata(metadataName))
091            {
092                // reset attribute 
093                copyReport.addContentReferenceValues(metadataPath, isMultiple ? Collections.EMPTY_LIST : null);
094            }
095        }
096        else
097        {
098            super.copyContentReferenceMetadata(baseMetaHolder, targetMetaHolder, metadataDefinition, metadataPath, copyMap, innerCopyMapInputs, copyReport);
099        }
100        
101    }
102}