]>
Commit | Line | Data |
---|---|---|
1b2798f6 EK |
1 | /******************************************************************************* |
2 | * Copyright (c) 2006, 2011 IBM Corporation and others. | |
3 | * All rights reserved. This program and the accompanying materials | |
4 | * are made available under the terms of the Eclipse Public License v1.0 | |
5 | * which accompanies this distribution, and is available at | |
6 | * http://www.eclipse.org/legal/epl-v10.html | |
7 | * | |
8 | * Contributors: | |
9 | * IBM Corporation - initial API and implementation | |
10 | *******************************************************************************/ | |
11 | package org.eclipse.jdt.internal.ui.javaeditor.saveparticipant; | |
12 | ||
13 | import java.util.ArrayList; | |
14 | import java.util.HashMap; | |
15 | import java.util.Iterator; | |
16 | import java.util.Map; | |
17 | ||
18 | import org.eclipse.core.runtime.CoreException; | |
19 | import org.eclipse.core.runtime.ISafeRunnable; | |
20 | import org.eclipse.core.runtime.IStatus; | |
21 | import org.eclipse.core.runtime.MultiStatus; | |
22 | import org.eclipse.core.runtime.SafeRunner; | |
23 | import org.eclipse.core.runtime.Status; | |
24 | import org.eclipse.core.runtime.preferences.IScopeContext; | |
25 | ||
26 | import org.eclipse.core.resources.IProject; | |
27 | import org.eclipse.core.resources.ProjectScope; | |
28 | ||
29 | import org.eclipse.jface.text.IRegion; | |
30 | ||
31 | import org.eclipse.jdt.core.ICompilationUnit; | |
32 | ||
33 | import org.eclipse.jdt.internal.corext.fix.CleanUpPostSaveListener; | |
34 | import org.eclipse.jdt.internal.corext.util.Messages; | |
35 | ||
36 | import org.eclipse.jdt.ui.JavaUI; | |
37 | ||
38 | import org.eclipse.jdt.internal.ui.IJavaStatusConstants; | |
39 | import org.eclipse.jdt.internal.ui.JavaPlugin; | |
40 | import org.eclipse.jdt.internal.ui.fix.CleanUpSaveParticipantPreferenceConfiguration; | |
41 | import org.eclipse.jdt.internal.ui.javaeditor.CompilationUnitDocumentProvider; | |
42 | ||
43 | /** | |
44 | * A registry for save participants. This registry manages | |
45 | * {@link SaveParticipantDescriptor}s and keeps track of enabled save | |
46 | * participants. | |
47 | * <p> | |
48 | * Save participants can be enabled and disabled on the Java > Editor > | |
49 | * Save Participants preference page. Enabled save participants are notified | |
50 | * through a call to | |
51 | * {@link IPostSaveListener#saved(org.eclipse.jdt.core.ICompilationUnit, IRegion[], org.eclipse.core.runtime.IProgressMonitor)} | |
52 | * whenever the {@link CompilationUnitDocumentProvider} saves a compilation unit | |
53 | * that is in the workspace.</p> | |
54 | * <p> | |
55 | * An instance of this registry can be received through a call to {@link JavaPlugin#getSaveParticipantRegistry()}.</p> | |
56 | * | |
57 | * @since 3.3 | |
58 | */ | |
59 | public final class SaveParticipantRegistry { | |
60 | ||
61 | private static final IPostSaveListener[] EMPTY_ARRAY= new IPostSaveListener[0]; | |
62 | ||
63 | /** The map of descriptors, indexed by their identifiers. */ | |
64 | Map<String, SaveParticipantDescriptor> fDescriptors; | |
65 | ||
66 | /** | |
67 | * Creates a new instance. | |
68 | */ | |
69 | public SaveParticipantRegistry() { | |
70 | } | |
71 | ||
72 | /** | |
73 | * Returns an array of <code>SaveParticipantDescriptor</code> describing | |
74 | * all registered save participants. | |
75 | * | |
76 | * @return the array of registered save participant descriptors | |
77 | */ | |
78 | public synchronized SaveParticipantDescriptor[] getSaveParticipantDescriptors() { | |
79 | ensureRegistered(); | |
80 | return fDescriptors.values().toArray(new SaveParticipantDescriptor[fDescriptors.size()]); | |
81 | } | |
82 | ||
83 | /** | |
84 | * Returns the save participant descriptor for the given <code>id</code> or | |
85 | * <code>null</code> if no such listener is registered. | |
86 | * | |
87 | * @param id the identifier of the requested save participant | |
88 | * @return the corresponding descriptor, or <code>null</code> if none can be found | |
89 | */ | |
90 | public synchronized SaveParticipantDescriptor getSaveParticipantDescriptor(String id) { | |
91 | ensureRegistered(); | |
92 | return fDescriptors.get(id); | |
93 | } | |
94 | ||
95 | /** | |
96 | * Ensures that all descriptors are created and stored in | |
97 | * <code>fDescriptors</code>. | |
98 | */ | |
99 | private void ensureRegistered() { | |
100 | if (fDescriptors == null) | |
101 | reloadDescriptors(); | |
102 | } | |
103 | ||
104 | /** | |
105 | * Loads the save participants. | |
106 | * <p> | |
107 | * This method can be called more than once in | |
108 | * order to reload from a changed extension registry. | |
109 | * </p> | |
110 | */ | |
111 | private void reloadDescriptors() { | |
112 | Map<String, SaveParticipantDescriptor> map= new HashMap<String, SaveParticipantDescriptor>(); | |
113 | SaveParticipantDescriptor desc= new SaveParticipantDescriptor(new CleanUpPostSaveListener()) { | |
114 | /** | |
115 | * {@inheritDoc} | |
116 | */ | |
117 | @Override | |
118 | public ISaveParticipantPreferenceConfiguration createPreferenceConfiguration() { | |
119 | return new CleanUpSaveParticipantPreferenceConfiguration(); | |
120 | } | |
121 | }; | |
122 | desc.generated_8850500018469403830(map, this); | |
123 | } | |
124 | ||
125 | public void dispose() { | |
126 | } | |
127 | ||
128 | /** | |
129 | * Checks weather there are enabled or disabled post save listener in the given context. | |
130 | * | |
131 | * @param context to context to check, not null | |
132 | * @return true if there are settings in context | |
133 | */ | |
134 | public synchronized boolean hasSettingsInScope(IScopeContext context) { | |
135 | ensureRegistered(); | |
136 | ||
137 | for (Iterator<SaveParticipantDescriptor> iterator= fDescriptors.values().iterator(); iterator.hasNext();) { | |
138 | SaveParticipantDescriptor descriptor= iterator.next(); | |
139 | if (descriptor.getPreferenceConfiguration().hasSettingsInScope(context)) | |
140 | return true; | |
141 | } | |
142 | ||
143 | return false; | |
144 | } | |
145 | ||
146 | public IPostSaveListener[] getEnabledPostSaveListeners(IProject project) { | |
147 | return getEnabledPostSaveListeners(new ProjectScope(project)); | |
148 | } | |
149 | ||
150 | /** | |
151 | * Returns an array of <code>IPostSaveListener</code> which are | |
152 | * enabled in the given context. | |
153 | * | |
154 | * @param context the context from which to retrieve the settings from, not null | |
155 | * @return the current enabled post save listeners according to the preferences | |
156 | */ | |
157 | public synchronized IPostSaveListener[] getEnabledPostSaveListeners(IScopeContext context) { | |
158 | ensureRegistered(); | |
159 | ||
160 | ArrayList<IPostSaveListener> result= null; | |
161 | for (Iterator<SaveParticipantDescriptor> iterator= fDescriptors.values().iterator(); iterator.hasNext();) { | |
162 | SaveParticipantDescriptor descriptor= iterator.next(); | |
163 | result= descriptor.generated_5939957325016738010(context, result); | |
164 | } | |
165 | ||
166 | if (result == null) { | |
167 | return EMPTY_ARRAY; | |
168 | } else { | |
169 | return result.toArray(new IPostSaveListener[result.size()]); | |
170 | } | |
171 | } | |
172 | ||
173 | /** | |
174 | * Tells whether one of the active post save listeners needs to be informed about the changed | |
175 | * region in this save cycle. | |
176 | * | |
177 | * @param unit the unit which is about to be saved | |
178 | * @return true if the change regions need do be determined | |
179 | * @throws CoreException if something went wrong | |
180 | * @since 3.4 | |
181 | */ | |
182 | public static boolean isChangedRegionsRequired(final ICompilationUnit unit) throws CoreException { | |
183 | String message= SaveParticipantMessages.SaveParticipantRegistry_needsChangedRegionFailed; | |
184 | final MultiStatus errorStatus= new MultiStatus(JavaUI.ID_PLUGIN, IJavaStatusConstants.EDITOR_CHANGED_REGION_CALCULATION, message, null); | |
185 | ||
186 | IPostSaveListener[] listeners= JavaPlugin.getDefault().getSaveParticipantRegistry().getEnabledPostSaveListeners(unit.getJavaProject().getProject()); | |
187 | try { | |
188 | final boolean result[]= new boolean[] {false}; | |
189 | for (int i= 0; i < listeners.length; i++) { | |
190 | final IPostSaveListener listener= listeners[i]; | |
191 | SafeRunner.run(new ISafeRunnable() { | |
192 | ||
193 | public void run() throws Exception { | |
194 | if (listener.needsChangedRegions(unit)) | |
195 | result[0]= true; | |
196 | } | |
197 | ||
198 | public void handleException(Throwable ex) { | |
199 | String msg= Messages.format("The save participant ''{0}'' caused an exception.", new String[] { listener.getId() }); //$NON-NLS-1$ | |
200 | JavaPlugin.log(new Status(IStatus.ERROR, JavaUI.ID_PLUGIN, IJavaStatusConstants.EDITOR_POST_SAVE_NOTIFICATION, msg, ex)); | |
201 | ||
202 | final String participantName= listener.getName(); | |
203 | msg= Messages.format(SaveParticipantMessages.SaveParticipantRegistry_needsChangedRegionCausedException, new String[] { participantName, ex.toString() }); | |
204 | errorStatus.add(new Status(IStatus.ERROR, JavaUI.ID_PLUGIN, IJavaStatusConstants.EDITOR_CHANGED_REGION_CALCULATION, msg, null)); | |
205 | } | |
206 | ||
207 | }); | |
208 | if (result[0]) | |
209 | return true; | |
210 | } | |
211 | } finally { | |
212 | if (!errorStatus.isOK()) | |
213 | throw new CoreException(errorStatus); | |
214 | } | |
215 | ||
216 | return false; | |
217 | } | |
218 | ||
219 | } |