This is an automated email from the ASF dual-hosted git repository.
rombert pushed a commit to branch master
in repository https://gitbox.apache.org/repos/asf/sling-ide-tooling.git
The following commit(s) were added to refs/heads/master by this push:
new 64bbfd7b SLING-8308 - Add custom contribution for feature model
projects (#25)
64bbfd7b is described below
commit 64bbfd7b8ae001df60c1831ea4c51bebd8d16e58
Author: Robert Munteanu <[email protected]>
AuthorDate: Thu Apr 3 16:44:21 2025 +0200
SLING-8308 - Add custom contribution for feature model projects (#25)
---
eclipse/eclipse-core/plugin.xml | 15 +++++++
.../ide/eclipse/core/ConfigurationHelper.java | 12 +++++
.../apache/sling/ide/eclipse/core/ProjectUtil.java | 41 ++++++++++++-----
.../ide/eclipse/core/internal/ProjectHelper.java | 5 +++
.../internal/SlingFeatureFacetInstallDelegate.java | 24 ++++++++++
.../SlingFeatureFacetUninstallDelegate.java | 21 +++++++++
.../m2e/internal/MavenProjectUtilsTest.java | 23 ++++++++++
.../m2e/internal/slingfeature-simple-pom.xml | 35 +++++++++++++++
.../eclipse-m2e-ui/lifecycle-mapping-metadata.xml | 17 ++++++++
eclipse/eclipse-m2e-ui/plugin.xml | 4 ++
.../eclipse/m2e/internal/MavenProjectUtils.java | 19 +++++++-
.../internal/SlingFeatureProjectConfigurator.java | 51 ++++++++++++++++++++++
.../sling/ide/test/impl/ProjectUtilTest.java | 28 ++++++++++++
eclipse/eclipse-ui/plugin.xml | 36 ++++++++++++++-
.../ui/nav/FeatureModelContentProvider.java | 43 ++++++++++++++++++
...rovider.java => GenericModelLabelProvider.java} | 10 +++--
.../ui/nav/model/FeatureModelRootFolder.java | 51 ++++++++++++++++++++++
17 files changed, 418 insertions(+), 17 deletions(-)
diff --git a/eclipse/eclipse-core/plugin.xml b/eclipse/eclipse-core/plugin.xml
index 94cea9d6..57a26e46 100644
--- a/eclipse/eclipse-core/plugin.xml
+++ b/eclipse/eclipse-core/plugin.xml
@@ -102,6 +102,21 @@
<action facet="sling.launchpad" version="1.0" type="UNINSTALL">
<delegate
class="org.apache.sling.ide.eclipse.core.internal.SlingLaunchpadFacetUninstallDelegate"/>
</action>
+
+ <project-facet id="sling.feature">
+ <label>Feature module</label>
+ <description>Packaging module which contains a feature
model.</description>
+ </project-facet>
+
+ <project-facet-version facet="sling.feature" version="1.0"/>
+
+ <action facet="sling.feature" version="1.0" type="INSTALL">
+ <delegate
class="org.apache.sling.ide.eclipse.core.internal.SlingFeatureFacetInstallDelegate"/>
+ </action>
+
+ <action facet="sling.feature" version="1.0" type="UNINSTALL">
+ <delegate
class="org.apache.sling.ide.eclipse.core.internal.SlingFeatureFacetUninstallDelegate"/>
+ </action>
</extension>
<!-- Define the Sling launchpad runtime type -->
diff --git
a/eclipse/eclipse-core/src/org/apache/sling/ide/eclipse/core/ConfigurationHelper.java
b/eclipse/eclipse-core/src/org/apache/sling/ide/eclipse/core/ConfigurationHelper.java
index e9fc46b3..b0c7d300 100644
---
a/eclipse/eclipse-core/src/org/apache/sling/ide/eclipse/core/ConfigurationHelper.java
+++
b/eclipse/eclipse-core/src/org/apache/sling/ide/eclipse/core/ConfigurationHelper.java
@@ -68,4 +68,16 @@ public class ConfigurationHelper {
}
+
+ public static void convertToFeatureProject(IProject project, IPath
featureDirectoryPath) throws CoreException {
+
+ IProjectFacet facet =
ProjectFacetsManager.getProjectFacet("sling.feature");
+ IFacetedProject fp2 = ProjectFacetsManager.create(project, true, null);
+ fp2.installProjectFacet(facet.getLatestVersion(), null, null);
+ project.refreshLocal(IResource.DEPTH_INFINITE, new
NullProgressMonitor());
+
+ if (featureDirectoryPath != null) {
+ ProjectUtil.setFeatureModelPath(project, featureDirectoryPath);
+ }
+ }
}
diff --git
a/eclipse/eclipse-core/src/org/apache/sling/ide/eclipse/core/ProjectUtil.java
b/eclipse/eclipse-core/src/org/apache/sling/ide/eclipse/core/ProjectUtil.java
index 92ab044c..54bd3047 100644
---
a/eclipse/eclipse-core/src/org/apache/sling/ide/eclipse/core/ProjectUtil.java
+++
b/eclipse/eclipse-core/src/org/apache/sling/ide/eclipse/core/ProjectUtil.java
@@ -19,6 +19,7 @@ package org.apache.sling.ide.eclipse.core;
import java.io.File;
import java.io.IOException;
import java.io.InputStream;
+import java.util.function.Predicate;
import org.apache.sling.ide.eclipse.core.internal.Activator;
import org.apache.sling.ide.eclipse.core.internal.ProjectHelper;
@@ -43,6 +44,7 @@ public abstract class ProjectUtil {
private static final String PROPERTY_SYNC_ROOT = Activator.PLUGIN_ID +
".content_sync_root";
private static final String PROPERTY_PROVISIONING_MODEL_DIR =
Activator.PLUGIN_ID + ".provisioning_model_dir";
+ private static final String PROPERTY_FEATURE_MODEL_DIR =
Activator.PLUGIN_ID + ".feature_model_dir";
private static final String PROPERTY_SYNC_ROOT_DEFAULT_VALUE = "jcr_root";
@@ -168,24 +170,30 @@ public abstract class ProjectUtil {
}
public static IPath getProvisioningModelPath(IProject project) {
-
- if ( project == null || !project.isOpen() ||
!ProjectHelper.isLaunchpadProject(project)) {
- return null;
- }
-
+
+ return getProjectPath(project, ProjectHelper::isLaunchpadProject,
PROPERTY_PROVISIONING_MODEL_DIR);
+
+ }
+
+ private static IPath getProjectPath(IProject project, Predicate<IProject>
requiredTest, String key) {
+
+ if ( project == null || !project.isOpen() ||
!requiredTest.test(project)) {
+ return null;
+ }
+
IScopeContext projectScope = new ProjectScope(project);
IEclipsePreferences projectNode =
projectScope.getNode(Activator.PLUGIN_ID);
if ( projectNode == null ) {
- return null;
+ return null;
}
- String propertyValue =
projectNode.get(PROPERTY_PROVISIONING_MODEL_DIR, null);
+ String propertyValue = projectNode.get(key, null);
if ( propertyValue == null ) {
- return null;
+ return null;
}
-
- return Path.fromPortableString(propertyValue);
- }
+
+ return Path.fromPortableString(propertyValue);
+ }
public static void setProvisioningModelPath(IProject project, IPath
modelPath) {
@@ -193,6 +201,17 @@ public abstract class ProjectUtil {
}
+ public static IPath getFeatureModelPath(IProject project) {
+
+ return getProjectPath(project, ProjectHelper::isFeatureProject,
PROPERTY_FEATURE_MODEL_DIR);
+ }
+
+ public static void setFeatureModelPath(IProject project, IPath modelPath) {
+
+ setPathPersistentProperty(project, modelPath,
PROPERTY_FEATURE_MODEL_DIR);
+
+ }
+
/**
* Loads a filter for the specified project
diff --git
a/eclipse/eclipse-core/src/org/apache/sling/ide/eclipse/core/internal/ProjectHelper.java
b/eclipse/eclipse-core/src/org/apache/sling/ide/eclipse/core/internal/ProjectHelper.java
index 9adca608..a06d8aa0 100644
---
a/eclipse/eclipse-core/src/org/apache/sling/ide/eclipse/core/internal/ProjectHelper.java
+++
b/eclipse/eclipse-core/src/org/apache/sling/ide/eclipse/core/internal/ProjectHelper.java
@@ -42,6 +42,7 @@ import org.xml.sax.SAXException;
public class ProjectHelper {
+ private static final String SLING_FEATURE_FACET_ID = "sling.feature";
private static final String[] CONTENT_PACKAGE_STRUCTURE_BASE = new
String[] { "/", "/content", "/src/main/content" };
public static boolean isPotentialBundleProject(IProject project) {
@@ -144,6 +145,10 @@ public class ProjectHelper {
return FacetHelper.containsFacet(project, "sling.launchpad");
}
+ public static boolean isFeatureProject(IProject project) {
+ return FacetHelper.containsFacet(project, SLING_FEATURE_FACET_ID);
+ }
+
public static IJavaProject asJavaProject(IProject project) {
return JavaCore.create(project);
}
diff --git
a/eclipse/eclipse-core/src/org/apache/sling/ide/eclipse/core/internal/SlingFeatureFacetInstallDelegate.java
b/eclipse/eclipse-core/src/org/apache/sling/ide/eclipse/core/internal/SlingFeatureFacetInstallDelegate.java
new file mode 100644
index 00000000..875cb5cc
--- /dev/null
+++
b/eclipse/eclipse-core/src/org/apache/sling/ide/eclipse/core/internal/SlingFeatureFacetInstallDelegate.java
@@ -0,0 +1,24 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one or more
+ * contributor license agreements. See the NOTICE file distributed with
+ * this work for additional information regarding copyright ownership.
+ * The ASF licenses this file to You under the Apache License, Version 2.0
+ * (the "License"); you may not use this file except in compliance with
+ * the License. You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+package org.apache.sling.ide.eclipse.core.internal;
+
+public class SlingFeatureFacetInstallDelegate extends BaseFacetInstallDelegate
{
+
+ public SlingFeatureFacetInstallDelegate() {
+ setEnableValidationBuilderAndCommand(false);
+ }
+}
diff --git
a/eclipse/eclipse-core/src/org/apache/sling/ide/eclipse/core/internal/SlingFeatureFacetUninstallDelegate.java
b/eclipse/eclipse-core/src/org/apache/sling/ide/eclipse/core/internal/SlingFeatureFacetUninstallDelegate.java
new file mode 100644
index 00000000..b3c87e11
--- /dev/null
+++
b/eclipse/eclipse-core/src/org/apache/sling/ide/eclipse/core/internal/SlingFeatureFacetUninstallDelegate.java
@@ -0,0 +1,21 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one or more
+ * contributor license agreements. See the NOTICE file distributed with
+ * this work for additional information regarding copyright ownership.
+ * The ASF licenses this file to You under the Apache License, Version 2.0
+ * (the "License"); you may not use this file except in compliance with
+ * the License. You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+package org.apache.sling.ide.eclipse.core.internal;
+
+public class SlingFeatureFacetUninstallDelegate extends EmptyDelegate {
+
+}
diff --git
a/eclipse/eclipse-m2e-test/src/org/apache/sling/ide/eclipse/m2e/internal/MavenProjectUtilsTest.java
b/eclipse/eclipse-m2e-test/src/org/apache/sling/ide/eclipse/m2e/internal/MavenProjectUtilsTest.java
index bdea1ab1..d5b590db 100644
---
a/eclipse/eclipse-m2e-test/src/org/apache/sling/ide/eclipse/m2e/internal/MavenProjectUtilsTest.java
+++
b/eclipse/eclipse-m2e-test/src/org/apache/sling/ide/eclipse/m2e/internal/MavenProjectUtilsTest.java
@@ -79,4 +79,27 @@ public class MavenProjectUtilsTest {
actualJcrRoot = MavenProjectUtils.guessJcrRootFolder(rootPath);
Assert.assertFalse(actualJcrRoot.isPresent());
}
+
+ @Test
+ public void inferDefaultFeatureModelDirectories() throws Exception {
+
+ IPath featuresDir = Path.fromPortableString("src/main/features");
+
+ // create project
+ final IProject featureProject = projectRule.getProject();
+
+ MavenProjectAdapter project = new MavenProjectAdapter(featureProject);
+ project.createOrUpdateFile(Path.fromPortableString("pom.xml"),
getClass().getResourceAsStream("slingfeature-simple-pom.xml"));
+ project.ensureDirectoryExists(featuresDir);
+ project.convertToMavenProject();
+
+ // conversion should enable the slingstart configurator and set the
provisioning model path
+ new Poller(TimeUnit.MINUTES.toMillis(1)).pollUntil(new
Callable<IPath>() {
+ @Override
+ public IPath call() throws Exception {
+ return ProjectUtil.getFeatureModelPath(featureProject);
+ }
+ }, equalTo(featuresDir));
+
+ }
}
diff --git
a/eclipse/eclipse-m2e-test/src/org/apache/sling/ide/eclipse/m2e/internal/slingfeature-simple-pom.xml
b/eclipse/eclipse-m2e-test/src/org/apache/sling/ide/eclipse/m2e/internal/slingfeature-simple-pom.xml
new file mode 100644
index 00000000..081f1e06
--- /dev/null
+++
b/eclipse/eclipse-m2e-test/src/org/apache/sling/ide/eclipse/m2e/internal/slingfeature-simple-pom.xml
@@ -0,0 +1,35 @@
+<!--
+ Licensed to the Apache Software Foundation (ASF) under one or more
contributor license
+ agreements. See the NOTICE file distributed with this work for additional
information
+ regarding copyright ownership. The ASF licenses this file to you under the
Apache License,
+ Version 2.0 (the "License"); you may not use this file except in
compliance with the
+ License. You may obtain a copy of the License at
http://www.apache.org/licenses/LICENSE-2.0
+
+ Unless required by applicable law or agreed to in writing, software
distributed under the
+ License is distributed on an "AS IS" BASIS, WITHOUT WARRANTIES OR
CONDITIONS OF ANY KIND,
+ either express or implied. See the License for the specific language
governing permissions
+ and limitations under the License.
+-->
+<project xmlns="http://maven.apache.org/POM/4.0.0"
xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xsi:schemaLocation="http://maven.apache.org/POM/4.0.0
http://maven.apache.org/xsd/maven-4.0.0.xsd">
+ <modelVersion>4.0.0</modelVersion>
+ <groupId>org.apache.sling.ide.testing</groupId>
+ <artifactId>simple-feature</artifactId>
+ <version>1.0.0-SNAPSHOT</version>
+ <build>
+ <plugins>
+ <plugin>
+ <groupId>org.apache.sling</groupId>
+ <artifactId>slingfeature-maven-plugin</artifactId>
+ <version>1.9.0</version>
+ <extensions>true</extensions>
+ <executions>
+ <execution>
+ <goals>
+ <goal>attach-features</goal>
+ </goals>
+ </execution>
+ </executions>
+ </plugin>
+ </plugins>
+ </build>
+</project>
\ No newline at end of file
diff --git a/eclipse/eclipse-m2e-ui/lifecycle-mapping-metadata.xml
b/eclipse/eclipse-m2e-ui/lifecycle-mapping-metadata.xml
index a24e1df5..b625ad45 100644
--- a/eclipse/eclipse-m2e-ui/lifecycle-mapping-metadata.xml
+++ b/eclipse/eclipse-m2e-ui/lifecycle-mapping-metadata.xml
@@ -118,5 +118,22 @@
</configurator>
</action>
</pluginExecution>
+ <pluginExecution>
+ <pluginExecutionFilter>
+ <groupId>org.apache.sling</groupId>
+ <artifactId>slingfeature-maven-plugin</artifactId>
+ <versionRange>[1.0.0,)</versionRange>
+ <goals>
+ <goal>analyse-features</goal>
+ <goal>aggregate-features</goal>
+ <goal>attach-features</goal>
+ </goals>
+ </pluginExecutionFilter>
+ <action>
+ <configurator>
+
<id>org.apache.sling.ide.eclipse.m2e.slingfeatureConfigurator</id>
+ </configurator>
+ </action>
+ </pluginExecution>
</pluginExecutions>
</lifecycleMappingMetadata>
\ No newline at end of file
diff --git a/eclipse/eclipse-m2e-ui/plugin.xml
b/eclipse/eclipse-m2e-ui/plugin.xml
index 13405b13..51e88a51 100644
--- a/eclipse/eclipse-m2e-ui/plugin.xml
+++ b/eclipse/eclipse-m2e-ui/plugin.xml
@@ -69,6 +69,10 @@
id="org.apache.sling.ide.eclipse.m2e.slingstartConfigurator"
class="org.apache.sling.ide.eclipse.m2e.internal.SlingstartProjectConfigurator"
name="Sling Launchpad Configurator" />
+ <configurator
+ id="org.apache.sling.ide.eclipse.m2e.slingfeatureConfigurator"
+
class="org.apache.sling.ide.eclipse.m2e.internal.SlingFeatureProjectConfigurator"
+ name="Sling Feature Configurator" />
</extension>
<!-- generic error marker (not bound to any quick fixes) for errors in any
project configurators -->
diff --git
a/eclipse/eclipse-m2e-ui/src/org/apache/sling/ide/eclipse/m2e/internal/MavenProjectUtils.java
b/eclipse/eclipse-m2e-ui/src/org/apache/sling/ide/eclipse/m2e/internal/MavenProjectUtils.java
index 32aada93..fc31fa96 100644
---
a/eclipse/eclipse-m2e-ui/src/org/apache/sling/ide/eclipse/m2e/internal/MavenProjectUtils.java
+++
b/eclipse/eclipse-m2e-ui/src/org/apache/sling/ide/eclipse/m2e/internal/MavenProjectUtils.java
@@ -97,7 +97,24 @@ public class MavenProjectUtils {
return new LinkedHashSet<>(candidates);
}
-
+
+ public static Set<String>
getFeatureDirectoryCandidateLocations(MavenProject mavenProject) {
+ List<String> candidates = new ArrayList<>();
+ candidates.add("src/main/features");
+ candidates.add("src/test/features");
+
+ Plugin slingFeaturePlugin =
mavenProject.getPlugin("org.apache.sling:slingfeature-maven-plugin");
+ if ( slingFeaturePlugin.getConfiguration() instanceof Xpp3Dom ) {
+ Xpp3Dom config = (Xpp3Dom) slingFeaturePlugin.getConfiguration();
+ Xpp3Dom featuresDir = config.getChild("features");
+ if ( featuresDir != null ) {
+ candidates.add(0, featuresDir.getValue());
+ }
+ }
+
+ return new LinkedHashSet<>(candidates);
+ }
+
private MavenProjectUtils() {
}
diff --git
a/eclipse/eclipse-m2e-ui/src/org/apache/sling/ide/eclipse/m2e/internal/SlingFeatureProjectConfigurator.java
b/eclipse/eclipse-m2e-ui/src/org/apache/sling/ide/eclipse/m2e/internal/SlingFeatureProjectConfigurator.java
new file mode 100644
index 00000000..9dfd6b1b
--- /dev/null
+++
b/eclipse/eclipse-m2e-ui/src/org/apache/sling/ide/eclipse/m2e/internal/SlingFeatureProjectConfigurator.java
@@ -0,0 +1,51 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one or more
+ * contributor license agreements. See the NOTICE file distributed with
+ * this work for additional information regarding copyright ownership.
+ * The ASF licenses this file to You under the Apache License, Version 2.0
+ * (the "License"); you may not use this file except in compliance with
+ * the License. You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+package org.apache.sling.ide.eclipse.m2e.internal;
+
+import java.util.Set;
+
+import org.apache.sling.ide.eclipse.core.ConfigurationHelper;
+import org.eclipse.core.resources.IFolder;
+import org.eclipse.core.resources.IProject;
+import org.eclipse.core.runtime.CoreException;
+import org.eclipse.core.runtime.IPath;
+import org.eclipse.core.runtime.IProgressMonitor;
+import org.eclipse.core.runtime.Path;
+import org.eclipse.m2e.core.project.configurator.ProjectConfigurationRequest;
+
+public class SlingFeatureProjectConfigurator extends
AbstractProjectConfigurator {
+
+ @Override
+ public void configure(ProjectConfigurationRequest request,
IProgressMonitor monitor) throws CoreException {
+
+ IProject project = request.mavenProjectFacade().getProject();
+ Set<String> candidates =
MavenProjectUtils.getFeatureDirectoryCandidateLocations(request.mavenProject());
+ IPath featuresPath = null;
+
+ for ( String candidate : candidates ) {
+ IPath candidatePath =
Path.fromPortableString(candidate);
+ IFolder featuresFolder =
project.getFolder(candidatePath);
+ if ( featuresFolder.exists() ) {
+ featuresPath = candidatePath;
+ break;
+ }
+ }
+
+ trace("Configuring project {0} with features path {1}",
project.getName(), featuresPath);
+ ConfigurationHelper.convertToFeatureProject(project,
featuresPath);
+ }
+}
diff --git
a/eclipse/eclipse-test/src/org/apache/sling/ide/test/impl/ProjectUtilTest.java
b/eclipse/eclipse-test/src/org/apache/sling/ide/test/impl/ProjectUtilTest.java
index a5a19f5c..0b2debba 100644
---
a/eclipse/eclipse-test/src/org/apache/sling/ide/test/impl/ProjectUtilTest.java
+++
b/eclipse/eclipse-test/src/org/apache/sling/ide/test/impl/ProjectUtilTest.java
@@ -142,4 +142,32 @@ public class ProjectUtilTest {
assertThat("provisioning model path",
ProjectUtil.getProvisioningModelPath(contentProject), equalTo(modelPath));
}
+
+ @Test
+ public void noFeaturesDirectory() throws Exception {
+
+ assertThat("feature model path",
ProjectUtil.getFeatureModelPath(contentProject), nullValue());
+ }
+
+ @Test
+ public void existingFeaturesDirectoryWithoutLaunchpadNature() throws
Exception {
+
+ IPath modelPath = Path.fromPortableString("src/main/features");
+ project.ensureDirectoryExists(modelPath);
+ ProjectUtil.setFeatureModelPath(contentProject, modelPath);
+
+ assertThat("feature model path",
ProjectUtil.getFeatureModelPath(contentProject), nullValue());
+ }
+
+ @Test
+ public void existingFeaturessDirectoryWithLaunchpadNature() throws
Exception {
+
+ project.installFacet("sling.feature", "1.0");
+
+ IPath modelPath = Path.fromPortableString("src/main/features");
+ project.ensureDirectoryExists(modelPath);
+ ProjectUtil.setFeatureModelPath(contentProject, modelPath);
+
+ assertThat("feature model path",
ProjectUtil.getFeatureModelPath(contentProject), equalTo(modelPath));
+ }
}
diff --git a/eclipse/eclipse-ui/plugin.xml b/eclipse/eclipse-ui/plugin.xml
index a37b1a47..e3334449 100644
--- a/eclipse/eclipse-ui/plugin.xml
+++ b/eclipse/eclipse-ui/plugin.xml
@@ -231,6 +231,7 @@
<contentExtension
pattern="org.apache.sling.ide.eclipse-ui.navigatorJcrContent" />
<contentExtension
pattern="org.apache.sling.ide.eclipse-ui.navigatorVaultMetaInf" />
<contentExtension
pattern="org.apache.sling.ide.eclipse-ui.navigatorProvisioningModel" />
+ <contentExtension
pattern="org.apache.sling.ide.eclipse-ui.navigatorFeatureModel" />
<contentExtension
pattern="org.apache.sling.ide.eclipse-ui.linkHelper"/>
</includes>
</viewerContentBinding>
@@ -356,7 +357,7 @@
name="Provisioning Model"
appearsBefore="org.eclipse.jst.jee.ui.ejb"
contentProvider="org.apache.sling.ide.eclipse.ui.nav.ProvisioningModelContentProvider"
-
labelProvider="org.apache.sling.ide.eclipse.ui.nav.ProvisioningModelLabelProvider"
+
labelProvider="org.apache.sling.ide.eclipse.ui.nav.GenericModelLabelProvider"
icon="icons/obj16/sling_misc.gif">
<triggerPoints>
<and>
@@ -382,6 +383,36 @@
</and>
</possibleChildren>
</navigatorContent>
+ <navigatorContent
id="org.apache.sling.ide.eclipse-ui.navigatorFeatureModel"
+ name="Feature Model"
+ appearsBefore="org.eclipse.jst.jee.ui.ejb"
+
contentProvider="org.apache.sling.ide.eclipse.ui.nav.FeatureModelContentProvider"
+
labelProvider="org.apache.sling.ide.eclipse.ui.nav.GenericModelLabelProvider"
+ icon="icons/obj16/sling_misc.gif">
+ <triggerPoints>
+ <and>
+ <!-- only trigger for Sling Feature Projects -->
+ <adapt type="org.eclipse.core.resources.IResource">
+ <test
property="org.eclipse.wst.common.project.facet.core.projectFacet"
value="sling.feature"/>
+ </adapt>
+ <or>
+ <!-- and either IProject or ProvisioningModelRootFolder
-->
+ <instanceof value="org.eclipse.core.resources.IProject"
/>
+ <instanceof
value="org.apache.sling.ide.eclipse.ui.nav.model.FeatureModelRootFolder" />
+ </or>
+ </and>
+ </triggerPoints>
+ <possibleChildren>
+ <and>
+ <!-- only trigger for Sling Feature Projects -->
+ <adapt type="org.eclipse.core.resources.IResource">
+ <test
property="org.eclipse.wst.common.project.facet.core.projectFacet"
value="sling.feature"/>
+ </adapt>
+ <instanceof
+ value="org.eclipse.core.resources.IResource" />
+ </and>
+ </possibleChildren>
+ </navigatorContent>
</extension>
<extension
point="org.eclipse.core.runtime.adapters">
@@ -459,6 +490,9 @@
<test
property="org.eclipse.wst.common.project.facet.core.projectFacet"
value="sling.launchpad"/>
+ <test
+
property="org.eclipse.wst.common.project.facet.core.projectFacet"
+ value="sling.feature"/>
</or>
</not>
</definition>
diff --git
a/eclipse/eclipse-ui/src/org/apache/sling/ide/eclipse/ui/nav/FeatureModelContentProvider.java
b/eclipse/eclipse-ui/src/org/apache/sling/ide/eclipse/ui/nav/FeatureModelContentProvider.java
new file mode 100644
index 00000000..27e0487c
--- /dev/null
+++
b/eclipse/eclipse-ui/src/org/apache/sling/ide/eclipse/ui/nav/FeatureModelContentProvider.java
@@ -0,0 +1,43 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one or more
+ * contributor license agreements. See the NOTICE file distributed with
+ * this work for additional information regarding copyright ownership.
+ * The ASF licenses this file to You under the Apache License, Version 2.0
+ * (the "License"); you may not use this file except in compliance with
+ * the License. You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+package org.apache.sling.ide.eclipse.ui.nav;
+
+import org.apache.sling.ide.eclipse.core.ProjectUtil;
+import org.apache.sling.ide.eclipse.ui.nav.model.FeatureModelRootFolder;
+import org.eclipse.core.resources.IFolder;
+import org.eclipse.core.resources.IProject;
+import org.eclipse.core.runtime.IPath;
+
+public class FeatureModelContentProvider extends
BaseRootFolderContentProvider<FeatureModelRootFolder> {
+
+ public FeatureModelContentProvider() {
+ super(FeatureModelRootFolder.class);
+ }
+
+ @Override
+ protected FeatureModelRootFolder findRootFolder(IProject project) {
+
+ IPath modelDirPath = ProjectUtil.getFeatureModelPath(project);
+
+ IFolder folder = project.getFolder(modelDirPath);
+ if ( !folder.exists() ) {
+ return null;
+ }
+
+ return new FeatureModelRootFolder(folder);
+ }
+}
diff --git
a/eclipse/eclipse-ui/src/org/apache/sling/ide/eclipse/ui/nav/ProvisioningModelLabelProvider.java
b/eclipse/eclipse-ui/src/org/apache/sling/ide/eclipse/ui/nav/GenericModelLabelProvider.java
similarity index 81%
rename from
eclipse/eclipse-ui/src/org/apache/sling/ide/eclipse/ui/nav/ProvisioningModelLabelProvider.java
rename to
eclipse/eclipse-ui/src/org/apache/sling/ide/eclipse/ui/nav/GenericModelLabelProvider.java
index 8d60c855..c8e4ccea 100644
---
a/eclipse/eclipse-ui/src/org/apache/sling/ide/eclipse/ui/nav/ProvisioningModelLabelProvider.java
+++
b/eclipse/eclipse-ui/src/org/apache/sling/ide/eclipse/ui/nav/GenericModelLabelProvider.java
@@ -16,7 +16,9 @@
*/
package org.apache.sling.ide.eclipse.ui.nav;
+import org.apache.sling.ide.eclipse.ui.nav.model.FeatureModelRootFolder;
import org.apache.sling.ide.eclipse.ui.nav.model.ProvisioningModelRootFolder;
+import org.apache.sling.ide.eclipse.ui.nav.model.RootFolder;
import org.eclipse.jface.viewers.ILabelProvider;
import org.eclipse.jface.viewers.ILabelProviderListener;
import org.eclipse.swt.graphics.Image;
@@ -26,7 +28,7 @@ import org.eclipse.ui.PlatformUI;
/**
* Mostly copied from
org.eclipse.ui.internal.ide.dialogs.FileFolderSelectionDialog.FileLabelProvider.
*/
-public class ProvisioningModelLabelProvider implements ILabelProvider {
+public class GenericModelLabelProvider implements ILabelProvider {
private static final Image IMG_FOLDER =
PlatformUI.getWorkbench().getSharedImages()
.getImage(ISharedImages.IMG_OBJ_FOLDER);
@@ -53,7 +55,7 @@ public class ProvisioningModelLabelProvider implements
ILabelProvider {
@Override
public Image getImage(Object element) {
- if ( element instanceof ProvisioningModelRootFolder ) {
+ if ( element instanceof ProvisioningModelRootFolder || element
instanceof FeatureModelRootFolder ) {
return IMG_FOLDER;
}
@@ -62,8 +64,8 @@ public class ProvisioningModelLabelProvider implements
ILabelProvider {
@Override
public String getText(Object element) {
- if (element instanceof ProvisioningModelRootFolder) {
- ProvisioningModelRootFolder rootFolder =
(ProvisioningModelRootFolder) element;
+ if (element instanceof ProvisioningModelRootFolder || element
instanceof FeatureModelRootFolder) {
+ RootFolder rootFolder = (RootFolder) element;
return rootFolder.getProjectRelativePath().toPortableString();
}
return null;
diff --git
a/eclipse/eclipse-ui/src/org/apache/sling/ide/eclipse/ui/nav/model/FeatureModelRootFolder.java
b/eclipse/eclipse-ui/src/org/apache/sling/ide/eclipse/ui/nav/model/FeatureModelRootFolder.java
new file mode 100644
index 00000000..5037de9f
--- /dev/null
+++
b/eclipse/eclipse-ui/src/org/apache/sling/ide/eclipse/ui/nav/model/FeatureModelRootFolder.java
@@ -0,0 +1,51 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one or more
+ * contributor license agreements. See the NOTICE file distributed with
+ * this work for additional information regarding copyright ownership.
+ * The ASF licenses this file to You under the Apache License, Version 2.0
+ * (the "License"); you may not use this file except in compliance with
+ * the License. You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+package org.apache.sling.ide.eclipse.ui.nav.model;
+
+import org.eclipse.core.resources.IFolder;
+import org.eclipse.core.resources.IResource;
+import org.eclipse.core.runtime.CoreException;
+import org.eclipse.core.runtime.IPath;
+
+public class FeatureModelRootFolder implements RootFolder {
+
+ private final IFolder folder;
+
+ public FeatureModelRootFolder(IFolder folder) {
+ this.folder = folder;
+ }
+
+ @Override
+ public String toString() {
+ return folder.getProjectRelativePath().toString();
+ }
+
+ @Override
+ public IResource findMember(IPath path) {
+ return folder.findMember(path);
+ }
+
+ @Override
+ public IPath getProjectRelativePath() {
+ return folder.getProjectRelativePath();
+ }
+
+ @Override
+ public IResource[] members() throws CoreException {
+ return folder.members();
+ }
+}