001/* 002 * (C) Copyright 2006-2010 Nuxeo SAS (http://nuxeo.com/) and contributors. 003 * 004 * All rights reserved. This program and the accompanying materials 005 * are made available under the terms of the GNU Lesser General Public License 006 * (LGPL) version 2.1 which accompanies this distribution, and is available at 007 * http://www.gnu.org/licenses/lgpl.html 008 * 009 * This library is distributed in the hope that it will be useful, 010 * but WITHOUT ANY WARRANTY; without even the implied warranty of 011 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU 012 * Lesser General Public License for more details. 013 * 014 * Contributors: 015 * bstefanescu 016 */ 017package org.nuxeo.ecm.platform.actions; 018 019import java.util.ArrayList; 020import java.util.Arrays; 021import java.util.HashSet; 022import java.util.List; 023import java.util.Set; 024 025import org.nuxeo.runtime.model.ContributionFragmentRegistry; 026 027/** 028 * @author <a href="mailto:bs@nuxeo.com">Bogdan Stefanescu</a> 029 */ 030public class ActionContributionHandler extends ContributionFragmentRegistry<Action> { 031 032 protected ActionRegistry actionReg; 033 034 protected FilterContributionHandler filters; 035 036 public ActionContributionHandler(FilterContributionHandler filters) { 037 actionReg = new ActionRegistry(); 038 this.filters = filters; 039 } 040 041 public ActionRegistry getRegistry() { 042 return actionReg; 043 } 044 045 @Override 046 public Action clone(Action object) { 047 return object.clone(); 048 } 049 050 @Override 051 public void contributionRemoved(String id, Action action) { 052 actionReg.removeAction(id); 053 // also remove local filters 054 ActionFilter[] localFilters = action.getFilters(); 055 if (localFilters != null) { 056 for (ActionFilter filter : localFilters) { 057 // XXX: local filters implicitly append their rules to existing 058 // ones => see append to true 059 DefaultActionFilter f = (DefaultActionFilter) filter; 060 f.setAppend(true); 061 filters.removeContribution(f, true); 062 } 063 } 064 } 065 066 @Override 067 public void contributionUpdated(String actionId, Action action, Action origAction) { 068 // given action is already merged, just retrieve its inner filters to 069 // register them to the filter registry 070 List<String> newFilterIds = new ArrayList<String>(); 071 List<String> existingFilterIds = action.getFilterIds(); 072 if (existingFilterIds != null) { 073 newFilterIds.addAll(existingFilterIds); 074 } 075 ActionFilter[] newFilters = action.getFilters(); 076 if (newFilters != null) { 077 // register embedded filters and save corresponding filter ids 078 for (ActionFilter filter : newFilters) { 079 String filterId = filter.getId(); 080 // XXX: local filters implicitly append their rules to existing 081 // ones => see append to true 082 DefaultActionFilter f = (DefaultActionFilter) filter; 083 f.setAppend(true); 084 filters.addContribution(f); 085 if (!newFilterIds.contains(filterId)) { 086 newFilterIds.add(filterId); 087 } 088 } 089 // XXX: Remove filters from action as it was just temporary, 090 // filters are now in their own registry. 091 action.setFilters(null); 092 } 093 action.setFilterIds(newFilterIds); 094 095 actionReg.addAction(action); 096 } 097 098 @Override 099 public String getContributionId(Action contrib) { 100 return contrib.getId(); 101 } 102 103 @Override 104 public void merge(Action source, Action dest) { 105 // Icon 106 String newIcon = source.getIcon(); 107 if (newIcon != null && !newIcon.equals(dest.getIcon())) { 108 dest.setIcon(newIcon); 109 } 110 111 // Enabled ? 112 if (source.isEnableSet() && source.isEnabled() != dest.isEnabled()) { 113 dest.setEnabled(source.isEnabled()); 114 } 115 116 // Merge categories without duplicates 117 Set<String> mergedCategories = new HashSet<String>(Arrays.asList(dest.getCategories())); 118 mergedCategories.addAll(new HashSet<String>(Arrays.asList(source.getCategories()))); 119 dest.setCategories(mergedCategories.toArray(new String[mergedCategories.size()])); 120 121 // label 122 String newLabel = source.getLabel(); 123 if (newLabel != null && !newLabel.equals(dest.getLabel())) { 124 dest.setLabel(newLabel); 125 } 126 127 // link 128 String newLink = source.getLink(); 129 if (newLink != null && !newLink.equals(dest.getLink())) { 130 dest.setLink(newLink); 131 } 132 133 // confirm 134 String newConfirm = source.getConfirm(); 135 if (newConfirm != null && !"".equals(newConfirm) && !newConfirm.equals(dest.getConfirm())) { 136 dest.setConfirm(newConfirm); 137 } 138 139 // title (tooltip) 140 String tooltip = source.getHelp(); 141 if (tooltip != null && !tooltip.equals(dest.getHelp())) { 142 dest.setHelp(tooltip); 143 } 144 145 // ui action type 146 String type = source.getType(); 147 if (type != null && !type.equals(dest.getType())) { 148 dest.setType(type); 149 } 150 151 // order 152 int newOrder = source.getOrder(); 153 if (newOrder > 0 && newOrder != dest.getOrder()) { 154 dest.setOrder(newOrder); 155 } 156 157 // filter ids 158 List<String> newFilterIds = new ArrayList<String>(); 159 newFilterIds.addAll(dest.getFilterIds()); 160 newFilterIds.addAll(source.getFilterIds()); 161 dest.setFilterIds(newFilterIds); 162 163 // filters 164 ActionFilter[] existingFilters = dest.getFilters(); 165 ActionFilter[] newFilters = source.getFilters(); 166 List<ActionFilter> filters = new ArrayList<ActionFilter>(); 167 if (existingFilters != null) { 168 filters.addAll(Arrays.asList(existingFilters)); 169 } 170 if (newFilters != null) { 171 filters.addAll(Arrays.asList(newFilters)); 172 } 173 dest.setFilters(filters.toArray(new ActionFilter[] {})); 174 175 // accessKey 176 String newAccessKey = source.getAccessKey(); 177 if (newAccessKey != null && !newAccessKey.isEmpty()) { 178 dest.setAccessKey(newAccessKey); 179 } 180 181 // properties 182 ActionPropertiesDescriptor newProps = source.getPropertiesDescriptor(); 183 if (newProps != null) { 184 boolean append = newProps.isAppend(); 185 if (!append) { 186 dest.setPropertiesDescriptor(newProps); 187 } else { 188 ActionPropertiesDescriptor oldProps = dest.getPropertiesDescriptor(); 189 if (oldProps != null) { 190 oldProps.merge(newProps); 191 dest.setPropertiesDescriptor(oldProps); 192 } else { 193 dest.setPropertiesDescriptor(newProps); 194 } 195 } 196 } 197 198 } 199}