From ee1f4a36a4becb3c8e08396aefe42d6e6e820549 Mon Sep 17 00:00:00 2001 From: Jay Arthanareeswaran Date: Thu, 7 Nov 2024 12:08:12 +0530 Subject: [PATCH 1/4] Comparator errors in I20241106-1800 These are expected changes due to the compiler changes via https://github.com/eclipse-jdt/eclipse.jdt.core/pull/3254 --- apitools/org.eclipse.pde.api.tools/forceQualifierUpdate.txt | 3 ++- 1 file changed, 2 insertions(+), 1 deletion(-) diff --git a/apitools/org.eclipse.pde.api.tools/forceQualifierUpdate.txt b/apitools/org.eclipse.pde.api.tools/forceQualifierUpdate.txt index fc674b45c7..224f113564 100644 --- a/apitools/org.eclipse.pde.api.tools/forceQualifierUpdate.txt +++ b/apitools/org.eclipse.pde.api.tools/forceQualifierUpdate.txt @@ -7,4 +7,5 @@ https://github.com/eclipse-platform/eclipse.platform.releng.aggregator/issues/11 Comparator errors in I20230906-0400 https://github.com/eclipse-platform/eclipse.platform.releng.aggregator/issues/1378 https://github.com/eclipse-platform/eclipse.platform.releng.aggregator/issues/1781 -https://github.com/eclipse-platform/eclipse.platform.releng.aggregator/issues/1923 \ No newline at end of file +https://github.com/eclipse-platform/eclipse.platform.releng.aggregator/issues/1923 +Comparator errors in I20241106-1800/ - Expected due to https://github.com/eclipse-jdt/eclipse.jdt.core/pull/3254 From 5cac9e29f596bec2ab036a55e66304836e65cfa9 Mon Sep 17 00:00:00 2001 From: Hannes Wellmann Date: Sat, 9 Nov 2024 10:08:06 +0100 Subject: [PATCH 2/4] Simplify event publication in TargetPlatformService Instead of implementing an asynchronous event dispatching mechanism in TargetPlatformService, simply use IEventBroker.post(). --- .../core/target/TargetPlatformService.java | 125 +++--------------- 1 file changed, 21 insertions(+), 104 deletions(-) diff --git a/ui/org.eclipse.pde.core/src/org/eclipse/pde/internal/core/target/TargetPlatformService.java b/ui/org.eclipse.pde.core/src/org/eclipse/pde/internal/core/target/TargetPlatformService.java index a63ae635e6..5dd599ab64 100644 --- a/ui/org.eclipse.pde.core/src/org/eclipse/pde/internal/core/target/TargetPlatformService.java +++ b/ui/org.eclipse.pde.core/src/org/eclipse/pde/internal/core/target/TargetPlatformService.java @@ -33,7 +33,6 @@ import java.util.Map; import java.util.Objects; import java.util.Set; -import java.util.concurrent.ConcurrentLinkedQueue; import java.util.concurrent.atomic.AtomicReference; import java.util.stream.Collectors; import java.util.stream.IntStream; @@ -41,10 +40,7 @@ import org.eclipse.core.resources.IFile; import org.eclipse.core.resources.IResource; -import org.eclipse.core.resources.IResourceProxy; -import org.eclipse.core.resources.IResourceProxyVisitor; import org.eclipse.core.resources.ResourcesPlugin; -import org.eclipse.core.runtime.Assert; import org.eclipse.core.runtime.CoreException; import org.eclipse.core.runtime.IConfigurationElement; import org.eclipse.core.runtime.IPath; @@ -100,44 +96,14 @@ public class TargetPlatformService implements ITargetPlatformService { * The target definition currently being used as the target platform for * the workspace. */ - private final AtomicReference fWorkspaceTarget; + private final AtomicReference fWorkspaceTarget = new AtomicReference<>(); /** * vm arguments for default target */ private StringBuilder fVMArguments; - private final EventDispatcher eventSendingJob; - - /** - * Collects target files in the workspace - */ - static class ResourceProxyVisitor implements IResourceProxyVisitor { - - private final List fList; - - protected ResourceProxyVisitor(List list) { - fList = list; - } - - /** - * @see org.eclipse.core.resources.IResourceProxyVisitor#visit(org.eclipse.core.resources.IResourceProxy) - */ - @Override - public boolean visit(IResourceProxy proxy) { - if (proxy.getType() == IResource.FILE) { - if (ICoreConstants.TARGET_FILE_EXTENSION.equalsIgnoreCase(IPath.fromOSString(proxy.getName()).getFileExtension())) { - fList.add(proxy.requestResource()); - } - return false; - } - return true; - } - } - private TargetPlatformService() { - fWorkspaceTarget = new AtomicReference<>(); - eventSendingJob = new EventDispatcher("Sending 'workspace target changed' event", TargetPlatformService.class); //$NON-NLS-1$ } /** @@ -271,21 +237,23 @@ private List findLocalTargetDefinitions() { * @return all target definition handles in the workspace */ private List findWorkspaceTargetDefinitions() { - List files = new ArrayList<>(10); - ResourceProxyVisitor visitor = new ResourceProxyVisitor(files); + List files = new ArrayList<>(10); try { - ResourcesPlugin.getWorkspace().getRoot().accept(visitor, IResource.NONE); + ResourcesPlugin.getWorkspace().getRoot().accept(proxy -> { + if (proxy.getType() == IResource.FILE) { + if (ICoreConstants.TARGET_FILE_EXTENSION + .equalsIgnoreCase(IPath.fromOSString(proxy.getName()).getFileExtension())) { + files.add((IFile) proxy.requestResource()); + } + return false; + } + return true; + }, IResource.NONE); } catch (CoreException e) { PDECore.log(e); - return new ArrayList<>(0); - } - Iterator iter = files.iterator(); - List handles = new ArrayList<>(files.size()); - while (iter.hasNext()) { - IFile file = (IFile) iter.next(); - handles.add(new WorkspaceFileTargetHandle(file)); + return List.of(); } - return handles; + return files.stream().map(WorkspaceFileTargetHandle::new).toList(); } @Override @@ -361,71 +329,20 @@ public synchronized ITargetDefinition getWorkspaceTargetDefinition() throws Core */ public void setWorkspaceTargetDefinition(ITargetDefinition target, boolean asyncEvents) { ITargetDefinition oldTarget = fWorkspaceTarget.getAndSet(target); - boolean changed = !Objects.equals(oldTarget, target); - if (changed) { - if (asyncEvents) { - eventSendingJob.schedule(target); - } else { - notifyTargetChanged(target); - } + if (!Objects.equals(oldTarget, target)) { + notifyEvent(TargetEvents.TOPIC_WORKSPACE_TARGET_CHANGED, target, asyncEvents); } } - static void notifyTargetChanged(ITargetDefinition target) { + private static void notifyEvent(String topic, Object data, boolean asyncEvents) { IEclipseContext context = EclipseContextFactory.getServiceContext(PDECore.getDefault().getBundleContext()); IEventBroker broker = context.get(IEventBroker.class); if (broker != null) { - broker.send(TargetEvents.TOPIC_WORKSPACE_TARGET_CHANGED, target); - } - } - - static class EventDispatcher extends Job { - - private final ConcurrentLinkedQueue queue; - private final Object myFamily; - - /** - * @param jobName - * descriptive job name - * @param family - * non null object to control this job execution - **/ - public EventDispatcher(String jobName, Object family) { - super(jobName); - Assert.isNotNull(family); - this.myFamily = family; - this.queue = new ConcurrentLinkedQueue<>(); - setSystem(true); - } - - @Override - public boolean belongsTo(Object family) { - return myFamily == family; - } - - @Override - protected IStatus run(IProgressMonitor monitor) { - ITargetDefinition target; - while ((target = queue.poll()) != null && !monitor.isCanceled()) { - notifyTargetChanged(target); - } - if (!queue.isEmpty() && !monitor.isCanceled()) { - // in case actions got faster scheduled then processed - schedule(); - } - if (monitor.isCanceled()) { - queue.clear(); - return Status.CANCEL_STATUS; + if (asyncEvents) { + broker.post(topic, data); + } else { + broker.send(topic, data); } - return Status.OK_STATUS; - } - - /** - * Enqueue a task asynchronously. - **/ - public void schedule(ITargetDefinition target) { - queue.offer(target); - schedule(); // will reschedule if already running } } From 428cf43ec199619e88fa832106336d6df93d943f Mon Sep 17 00:00:00 2001 From: Eike Stepper Date: Thu, 10 Oct 2024 10:10:12 +0200 Subject: [PATCH 3/4] Provide TARGET_SAVED and TARGET_DELETED events When building tools on top of PDE's target platform framework it's often necessary to be informed about state changes in targets. PDE already uses an IEventBroker to send "workspaceTargetChanged" events. This change is about sending two new events: TARGET_SAVED and TARGET_DELETED --- .../forceQualifierUpdate.txt | 1 + .../.settings/.api_filters | 22 +++++++ ui/org.eclipse.pde.core/META-INF/MANIFEST.MF | 3 +- .../eclipse/pde/core/target/TargetEvents.java | 64 +++++++++++++++++-- .../core/target/AbstractTargetHandle.java | 8 ++- .../core/target/ExternalFileTargetHandle.java | 2 +- .../core/target/LocalTargetHandle.java | 2 +- .../core/target/TargetPlatformService.java | 5 ++ .../target/WorkspaceFileTargetHandle.java | 2 +- .../editor/targetdefinition/TargetEditor.java | 14 ++++ 10 files changed, 114 insertions(+), 9 deletions(-) diff --git a/org.eclipse.pde.doc.user/forceQualifierUpdate.txt b/org.eclipse.pde.doc.user/forceQualifierUpdate.txt index ac6c7b9b65..c5b3df86e4 100644 --- a/org.eclipse.pde.doc.user/forceQualifierUpdate.txt +++ b/org.eclipse.pde.doc.user/forceQualifierUpdate.txt @@ -7,3 +7,4 @@ Add missing reference/api content Pick-up javadoc changes https://github.com/eclipse-platform/eclipse.platform.releng.aggregator/pull/2396 Touch for build JVM change causing using newer jquery +Add new TargetEvents constants diff --git a/ui/org.eclipse.pde.core/.settings/.api_filters b/ui/org.eclipse.pde.core/.settings/.api_filters index f26c3f1cfb..8d60950802 100644 --- a/ui/org.eclipse.pde.core/.settings/.api_filters +++ b/ui/org.eclipse.pde.core/.settings/.api_filters @@ -1,5 +1,27 @@ + + + + + + + + + + + + + + + + + + + + + + diff --git a/ui/org.eclipse.pde.core/META-INF/MANIFEST.MF b/ui/org.eclipse.pde.core/META-INF/MANIFEST.MF index 898c1c96cf..d5513212ed 100644 --- a/ui/org.eclipse.pde.core/META-INF/MANIFEST.MF +++ b/ui/org.eclipse.pde.core/META-INF/MANIFEST.MF @@ -2,7 +2,7 @@ Manifest-Version: 1.0 Bundle-ManifestVersion: 2 Bundle-Name: %name Bundle-SymbolicName: org.eclipse.pde.core; singleton:=true -Bundle-Version: 3.19.100.qualifier +Bundle-Version: 3.20.0.qualifier Bundle-Activator: org.eclipse.pde.internal.core.PDECore Bundle-Vendor: %provider-name Bundle-Localization: plugin @@ -101,6 +101,7 @@ Import-Package: aQute.bnd.build;version="[4.4.0,5.0.0)", org.eclipse.equinox.internal.p2.publisher.eclipse, org.eclipse.equinox.p2.publisher, org.eclipse.equinox.p2.publisher.eclipse, + org.osgi.service.event;version="[1.4.0,2.0.0)", org.osgi.service.repository;version="[1.1.0,2.0.0)", org.osgi.util.promise;version="[1.3.0,2.0.0)" Require-Bundle: diff --git a/ui/org.eclipse.pde.core/src/org/eclipse/pde/core/target/TargetEvents.java b/ui/org.eclipse.pde.core/src/org/eclipse/pde/core/target/TargetEvents.java index 23cdcaa935..2b2e8097a7 100644 --- a/ui/org.eclipse.pde.core/src/org/eclipse/pde/core/target/TargetEvents.java +++ b/ui/org.eclipse.pde.core/src/org/eclipse/pde/core/target/TargetEvents.java @@ -12,28 +12,84 @@ ********************************************************************************/ package org.eclipse.pde.core.target; +import org.eclipse.e4.core.services.events.IEventBroker; +import org.osgi.service.event.Event; +import org.osgi.service.event.EventHandler; + /** - * Target events and event topic definitions + * Target events and event topic definitions. + * + *

+ * The following code is an example of to subscribe to the + * {@link #TOPIC_TARGET_SAVED} event: + *

+ * + *
+ * EventHandler eventHandler = event -> {
+ * 	if (event.getProperty(IEventBroker.DATA) instanceof ITargetHandle handle) {
+ * 		// Work with the target handle...
+ * 	}
+ * };
+ * IEclipseContext context = EclipseContextFactory.getServiceContext(bundleContext);
+ * IEventBroker broker = context.get(IEventBroker.class);
+ * if (broker != null) {
+ * 	broker.subscribe(TargetEvents.TOPIC_TARGET_SAVED, eventHandler);
+ * 	// Do not forget to unsubscribe later!
+ * }
+ * 
* + * @see ITargetPlatformService + * @see IEventBroker#subscribe(String, EventHandler) + * @see IEventBroker#subscribe(String, String, EventHandler, boolean) + * @see IEventBroker#unsubscribe(EventHandler) * @since 3.13 */ public class TargetEvents { /** - * Base topic for all Target events + * Base topic for all target events. */ public static final String TOPIC_BASE = "org/eclipse/pde/core/target/TargetEvents"; //$NON-NLS-1$ /** - * Topic for all Target events + * Topic for all target events. */ public static final String TOPIC_ALL = TOPIC_BASE + "/*"; //$NON-NLS-1$ /** - * Sent when workspace target definition is changed + * Sent when workspace target definition is changed. + *

+ * The {@link IEventBroker#DATA data} {@link Event#getProperty(String) event + * property} of events with this topic is the changed + * {@link ITargetDefinition}. + *

* * @see ITargetPlatformService#getWorkspaceTargetDefinition() */ public static final String TOPIC_WORKSPACE_TARGET_CHANGED = TOPIC_BASE + "/workspaceTargetChanged"; //$NON-NLS-1$ + /** + * Sent when a target is saved. + *

+ * The {@link IEventBroker#DATA data} {@link Event#getProperty(String) event + * property} of events with this topic is the saved {@link ITargetHandle}. + *

+ * + * @see ITargetPlatformService#saveTargetDefinition(ITargetDefinition) + * @see IEventBroker + * @since 3.20 + */ + public static final String TOPIC_TARGET_SAVED = TOPIC_BASE + "/targetSaved"; //$NON-NLS-1$ + + /** + * Sent when a target is deleted. + *

+ * The {@link IEventBroker#DATA data} {@link Event#getProperty(String) event + * property} of events with this topic is the deleted {@link ITargetHandle}. + *

+ * + * @see ITargetPlatformService#deleteTarget(ITargetHandle) + * @since 3.20 + */ + public static final String TOPIC_TARGET_DELETED = TOPIC_BASE + "/targetDeleted"; //$NON-NLS-1$ } diff --git a/ui/org.eclipse.pde.core/src/org/eclipse/pde/internal/core/target/AbstractTargetHandle.java b/ui/org.eclipse.pde.core/src/org/eclipse/pde/internal/core/target/AbstractTargetHandle.java index 9fd550a693..481cce4794 100644 --- a/ui/org.eclipse.pde.core/src/org/eclipse/pde/internal/core/target/AbstractTargetHandle.java +++ b/ui/org.eclipse.pde.core/src/org/eclipse/pde/internal/core/target/AbstractTargetHandle.java @@ -20,6 +20,7 @@ import org.eclipse.core.runtime.CoreException; import org.eclipse.pde.core.target.ITargetDefinition; import org.eclipse.pde.core.target.ITargetHandle; +import org.eclipse.pde.core.target.TargetEvents; /** * Common implementation of target handles. @@ -53,11 +54,16 @@ public ITargetDefinition getTargetDefinition() throws CoreException { */ abstract void delete() throws CoreException; + public final void save(ITargetDefinition definition) throws CoreException { + doSave(definition); + TargetPlatformService.scheduleEvent(TargetEvents.TOPIC_TARGET_SAVED, definition.getHandle()); + } + /** * Saves the definition to underlying storage. * * @param definition target to save * @throws CoreException on failure */ - abstract void save(ITargetDefinition definition) throws CoreException; + abstract void doSave(ITargetDefinition definition) throws CoreException; } diff --git a/ui/org.eclipse.pde.core/src/org/eclipse/pde/internal/core/target/ExternalFileTargetHandle.java b/ui/org.eclipse.pde.core/src/org/eclipse/pde/internal/core/target/ExternalFileTargetHandle.java index 92dff3e733..ed2cda5460 100644 --- a/ui/org.eclipse.pde.core/src/org/eclipse/pde/internal/core/target/ExternalFileTargetHandle.java +++ b/ui/org.eclipse.pde.core/src/org/eclipse/pde/internal/core/target/ExternalFileTargetHandle.java @@ -81,7 +81,7 @@ protected InputStream getInputStream() throws CoreException { @Override - void save(ITargetDefinition definition) throws CoreException { + void doSave(ITargetDefinition definition) throws CoreException { try (OutputStream stream = new BufferedOutputStream(new FileOutputStream(fFile))) { ((TargetDefinition) definition).write(stream); } catch (IOException e) { diff --git a/ui/org.eclipse.pde.core/src/org/eclipse/pde/internal/core/target/LocalTargetHandle.java b/ui/org.eclipse.pde.core/src/org/eclipse/pde/internal/core/target/LocalTargetHandle.java index 35396814ff..64237b274b 100644 --- a/ui/org.eclipse.pde.core/src/org/eclipse/pde/internal/core/target/LocalTargetHandle.java +++ b/ui/org.eclipse.pde.core/src/org/eclipse/pde/internal/core/target/LocalTargetHandle.java @@ -193,7 +193,7 @@ protected OutputStream getOutputStream() throws CoreException { } @Override - void save(ITargetDefinition definition) throws CoreException { + void doSave(ITargetDefinition definition) throws CoreException { try (OutputStream stream = getOutputStream()) { ((TargetDefinition) definition).write(stream); } catch (IOException e) { diff --git a/ui/org.eclipse.pde.core/src/org/eclipse/pde/internal/core/target/TargetPlatformService.java b/ui/org.eclipse.pde.core/src/org/eclipse/pde/internal/core/target/TargetPlatformService.java index 5dd599ab64..755842b837 100644 --- a/ui/org.eclipse.pde.core/src/org/eclipse/pde/internal/core/target/TargetPlatformService.java +++ b/ui/org.eclipse.pde.core/src/org/eclipse/pde/internal/core/target/TargetPlatformService.java @@ -126,6 +126,7 @@ public void deleteTarget(ITargetHandle handle) throws CoreException { } ((AbstractTargetHandle) handle).delete(); TargetPlatformHelper.getTargetDefinitionMap().remove(handle); + scheduleEvent(TargetEvents.TOPIC_TARGET_DELETED, handle); } @Override @@ -334,6 +335,10 @@ public void setWorkspaceTargetDefinition(ITargetDefinition target, boolean async } } + public static void scheduleEvent(String topic, Object data) { + notifyEvent(topic, data, true); + } + private static void notifyEvent(String topic, Object data, boolean asyncEvents) { IEclipseContext context = EclipseContextFactory.getServiceContext(PDECore.getDefault().getBundleContext()); IEventBroker broker = context.get(IEventBroker.class); diff --git a/ui/org.eclipse.pde.core/src/org/eclipse/pde/internal/core/target/WorkspaceFileTargetHandle.java b/ui/org.eclipse.pde.core/src/org/eclipse/pde/internal/core/target/WorkspaceFileTargetHandle.java index 57e1ba08a6..34a003631d 100644 --- a/ui/org.eclipse.pde.core/src/org/eclipse/pde/internal/core/target/WorkspaceFileTargetHandle.java +++ b/ui/org.eclipse.pde.core/src/org/eclipse/pde/internal/core/target/WorkspaceFileTargetHandle.java @@ -76,7 +76,7 @@ public String getMemento() throws CoreException { } @Override - public void save(ITargetDefinition definition) throws CoreException { + void doSave(ITargetDefinition definition) throws CoreException { ByteArrayOutputStream outputStream = new ByteArrayOutputStream(); ((TargetDefinition) definition).write(outputStream); ByteArrayInputStream stream = new ByteArrayInputStream(outputStream.toByteArray()); diff --git a/ui/org.eclipse.pde.ui/src/org/eclipse/pde/internal/ui/editor/targetdefinition/TargetEditor.java b/ui/org.eclipse.pde.ui/src/org/eclipse/pde/internal/ui/editor/targetdefinition/TargetEditor.java index 3ac514f8bf..1c41f50a22 100644 --- a/ui/org.eclipse.pde.ui/src/org/eclipse/pde/internal/ui/editor/targetdefinition/TargetEditor.java +++ b/ui/org.eclipse.pde.ui/src/org/eclipse/pde/internal/ui/editor/targetdefinition/TargetEditor.java @@ -65,6 +65,7 @@ import org.eclipse.pde.internal.core.PDEPreferencesManager; import org.eclipse.pde.internal.core.target.P2TargetUtils; import org.eclipse.pde.internal.core.target.TargetDefinitionPersistenceHelper; +import org.eclipse.pde.internal.core.target.TargetPlatformService; import org.eclipse.pde.internal.core.target.WorkspaceFileTargetHandle; import org.eclipse.pde.internal.ui.IHelpContextIds; import org.eclipse.pde.internal.ui.PDEPlugin; @@ -175,6 +176,7 @@ protected void pageChange(int newPageIndex) { @Override public void doSave(IProgressMonitor monitor) { + ITargetHandle handle = fInputHandler.getTarget().getHandle(); fInputHandler.setSaving(true); if (!isActiveTabTextualEditor()) { markStale(); @@ -184,6 +186,8 @@ public void doSave(IProgressMonitor monitor) { fDirty = false; editorDirtyStateChanged(); fInputHandler.setSaving(false); + + TargetPlatformService.scheduleEvent(TargetEvents.TOPIC_TARGET_SAVED, handle); } @Override @@ -286,6 +290,16 @@ public void dispose() { super.dispose(); } + @Override + public T getAdapter(Class adapter) { + if (adapter.equals(ITargetHandle.class)) { + ITargetDefinition target = getTarget(); + if (target != null) { + return adapter.cast(target.getHandle()); + } + } + return super.getAdapter(adapter); + } /** * Returns the target model backing this editor * @return target model From ef694eb058c182a8cf62429d7e67db6deca6bff3 Mon Sep 17 00:00:00 2001 From: Anvi <107345013+anviik@users.noreply.github.com> Date: Sun, 10 Nov 2024 13:39:41 -0800 Subject: [PATCH 4/4] Expand 'Extra Classpath Entries' section in Manifest editor by default Part of https://github.com/eclipse-pde/eclipse.pde/issues/1407 --- .../pde/internal/ui/editor/build/BuildClasspathSection.java | 3 +-- 1 file changed, 1 insertion(+), 2 deletions(-) diff --git a/ui/org.eclipse.pde.ui/src/org/eclipse/pde/internal/ui/editor/build/BuildClasspathSection.java b/ui/org.eclipse.pde.ui/src/org/eclipse/pde/internal/ui/editor/build/BuildClasspathSection.java index 704668feed..10b191b1a3 100644 --- a/ui/org.eclipse.pde.ui/src/org/eclipse/pde/internal/ui/editor/build/BuildClasspathSection.java +++ b/ui/org.eclipse.pde.ui/src/org/eclipse/pde/internal/ui/editor/build/BuildClasspathSection.java @@ -171,8 +171,7 @@ private IBuildModel getBuildModel() { public void initialize() { getBuildModel().addModelChangedListener(this); - IBuildEntry entry = getBuildModel().getBuild().getEntry(IBuildPropertiesConstants.PROPERTY_JAR_EXTRA_CLASSPATH); - getSection().setExpanded(entry != null && entry.getTokens().length > 0); + getSection().setExpanded(true); } @Override