mirror of
https://github.com/eclipse-cdt/cdt
synced 2025-06-06 01:06:01 +02:00
Resource scope for Build Command Parsers
This commit is contained in:
parent
d1e9395955
commit
0755f5870d
3 changed files with 211 additions and 13 deletions
|
@ -195,6 +195,7 @@ public class GCCBuildCommandParserTest extends BaseTestCase {
|
|||
assertEquals(null, provider.getLanguageScope());
|
||||
assertEquals(null, provider.getSettingEntries(null, null, null));
|
||||
assertEquals("", provider.getCompilerPattern());
|
||||
assertEquals(AbstractBuildCommandParser.ResourceScope.FILE, provider.getResourceScope());
|
||||
}
|
||||
|
||||
{
|
||||
|
@ -218,6 +219,8 @@ public class GCCBuildCommandParserTest extends BaseTestCase {
|
|||
// setters
|
||||
provider.setCompilerPattern(CUSTOM_PARAMETER_2);
|
||||
assertEquals(CUSTOM_PARAMETER_2, provider.getCompilerPattern());
|
||||
provider.setResourceScope(AbstractBuildCommandParser.ResourceScope.PROJECT);
|
||||
assertEquals(AbstractBuildCommandParser.ResourceScope.PROJECT, provider.getResourceScope());
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -236,11 +239,23 @@ public class GCCBuildCommandParserTest extends BaseTestCase {
|
|||
// configure provider
|
||||
parser.setResolvingPaths(false);
|
||||
assertFalse(parser.equals(clone0));
|
||||
parser.setResourceScope(AbstractBuildCommandParser.ResourceScope.PROJECT);
|
||||
assertEquals(AbstractBuildCommandParser.ResourceScope.PROJECT, parser.getResourceScope());
|
||||
parser.setResourceScope(AbstractBuildCommandParser.ResourceScope.FOLDER);
|
||||
assertEquals(AbstractBuildCommandParser.ResourceScope.FOLDER, parser.getResourceScope());
|
||||
parser.setResourceScope(AbstractBuildCommandParser.ResourceScope.FILE);
|
||||
assertEquals(AbstractBuildCommandParser.ResourceScope.FILE, parser.getResourceScope());
|
||||
|
||||
// check another clone after configuring
|
||||
// check another clone after changing settings
|
||||
{
|
||||
parser.setResolvingPaths(false);
|
||||
assertFalse(parser.equals(clone0));
|
||||
parser.setResourceScope(AbstractBuildCommandParser.ResourceScope.PROJECT);
|
||||
assertEquals(AbstractBuildCommandParser.ResourceScope.PROJECT, parser.getResourceScope());
|
||||
MockBuildCommandParser clone = parser.clone();
|
||||
assertTrue(parser.equals(clone));
|
||||
assertEquals(parser.isResolvingPaths(), clone.isResolvingPaths());
|
||||
assertEquals(parser.getResourceScope(), clone.getResourceScope());
|
||||
}
|
||||
|
||||
// check 'expand relative paths' flag
|
||||
|
@ -251,6 +266,16 @@ public class GCCBuildCommandParserTest extends BaseTestCase {
|
|||
assertFalse(parser.equals(clone));
|
||||
}
|
||||
|
||||
// check resource scope
|
||||
{
|
||||
parser.setResourceScope(AbstractBuildCommandParser.ResourceScope.PROJECT);
|
||||
assertEquals(AbstractBuildCommandParser.ResourceScope.PROJECT, parser.getResourceScope());
|
||||
MockBuildCommandParser clone = parser.clone();
|
||||
assertEquals(AbstractBuildCommandParser.ResourceScope.PROJECT, clone.getResourceScope());
|
||||
clone.setResourceScope(AbstractBuildCommandParser.ResourceScope.FOLDER);
|
||||
assertFalse(parser.equals(clone));
|
||||
}
|
||||
|
||||
// check cloneShallow()
|
||||
{
|
||||
MockBuildCommandParser parser2 = parser.clone();
|
||||
|
|
|
@ -21,6 +21,10 @@ import org.eclipse.cdt.core.IMarkerGenerator;
|
|||
import org.eclipse.cdt.core.errorparsers.RegexErrorParser;
|
||||
import org.eclipse.cdt.core.errorparsers.RegexErrorPattern;
|
||||
import org.eclipse.cdt.core.language.settings.providers.LanguageSettingsManager;
|
||||
import org.eclipse.cdt.core.settings.model.ICLanguageSettingEntry;
|
||||
import org.eclipse.cdt.internal.core.language.settings.providers.LanguageSettingsLogger;
|
||||
import org.eclipse.core.resources.IFile;
|
||||
import org.eclipse.core.resources.IResource;
|
||||
|
||||
/**
|
||||
* Abstract class for providers parsing compiler option from build command when present in build output.
|
||||
|
@ -29,12 +33,24 @@ import org.eclipse.cdt.core.language.settings.providers.LanguageSettingsManager;
|
|||
*/
|
||||
public abstract class AbstractBuildCommandParser extends AbstractLanguageSettingsOutputScanner {
|
||||
public static final Object JOB_FAMILY_BUILD_COMMAND_PARSER = "org.eclipse.cdt.managedbuilder.AbstractBuildCommandParser"; //$NON-NLS-1$
|
||||
|
||||
private static final String ATTR_PARAMETER = "parameter"; //$NON-NLS-1$
|
||||
private static final String ATTR_RESOURCE_SCOPE = "resource-scope"; //$NON-NLS-1$
|
||||
private static final String VALUE_FILE_SCOPE = "per-file"; //$NON-NLS-1$
|
||||
private static final String VALUE_FOLDER_SCOPE = "per-folder"; //$NON-NLS-1$
|
||||
private static final String VALUE_PROJECT_SCOPE = "per-project"; //$NON-NLS-1$
|
||||
|
||||
|
||||
private static final String LEADING_PATH_PATTERN = "\\S+[/\\\\]"; //$NON-NLS-1$
|
||||
private static final Pattern OPTIONS_PATTERN = Pattern.compile("-[^\\s\"']*(\\s*((\".*?\")|('.*?')|([^-\\s][^\\s]+)))?"); //$NON-NLS-1$
|
||||
private static final int OPTION_GROUP = 0;
|
||||
|
||||
public enum ResourceScope {
|
||||
FILE,
|
||||
FOLDER,
|
||||
PROJECT,
|
||||
}
|
||||
|
||||
/**
|
||||
* Note: design patterns to keep file group the same and matching {@link #FILE_GROUP}
|
||||
*/
|
||||
|
@ -45,6 +61,8 @@ public abstract class AbstractBuildCommandParser extends AbstractLanguageSetting
|
|||
};
|
||||
private static final int FILE_GROUP = 2;
|
||||
|
||||
// cached value from properties, do not need to use in equals() and hashCode()
|
||||
private ResourceScope resourceScope = null;
|
||||
|
||||
/**
|
||||
* The compiler command pattern without specifying compiler options.
|
||||
|
@ -76,6 +94,85 @@ public abstract class AbstractBuildCommandParser extends AbstractLanguageSetting
|
|||
return "\\s*\"?("+LEADING_PATH_PATTERN+")?(" + compilerPattern + ")\"?";
|
||||
}
|
||||
|
||||
/**
|
||||
* @return resource scope of the entries, i.e. level in resource hierarchy where language settings entries
|
||||
* will be applied by the provider. Resource scope can be one of the following:
|
||||
* <br>- {@code AbstractBuildCommandParser.ResourceScope.FILE} - apply entries to the file being parsed.
|
||||
* <br>- {@code AbstractBuildCommandParser.ResourceScope.FOLDER} - apply entries to the enclosing folder.
|
||||
* <br>- {@code AbstractBuildCommandParser.ResourceScope.PROJECT} - apply entries to the project level.
|
||||
*/
|
||||
public ResourceScope getResourceScope() {
|
||||
if (resourceScope == null) {
|
||||
String scopeStr = getProperty(ATTR_RESOURCE_SCOPE);
|
||||
if (scopeStr.equals(VALUE_FILE_SCOPE)) {
|
||||
resourceScope = ResourceScope.FILE;
|
||||
} else if (scopeStr.equals(VALUE_FOLDER_SCOPE)) {
|
||||
resourceScope = ResourceScope.FOLDER;
|
||||
} else if (scopeStr.equals(VALUE_PROJECT_SCOPE)) {
|
||||
resourceScope = ResourceScope.PROJECT;
|
||||
} else {
|
||||
resourceScope = ResourceScope.FILE;
|
||||
}
|
||||
}
|
||||
return resourceScope;
|
||||
}
|
||||
|
||||
/**
|
||||
* Set resource scope of the entries, i.e. level in resource hierarchy where language settings entries
|
||||
* will be applied by the provider.
|
||||
*
|
||||
* @param rcScope - resource scope can be one of the following:
|
||||
* <br>- {@code AbstractBuildCommandParser.ResourceScope.FILE} - apply entries to the file being parsed.
|
||||
* <br>- {@code AbstractBuildCommandParser.ResourceScope.FOLDER} - apply entries to the enclosing folder.
|
||||
* <br>- {@code AbstractBuildCommandParser.ResourceScope.PROJECT} - apply entries to the project level.
|
||||
*/
|
||||
public void setResourceScope(ResourceScope rcScope) {
|
||||
resourceScope = rcScope;
|
||||
switch (rcScope) {
|
||||
case FILE:
|
||||
setProperty(ATTR_RESOURCE_SCOPE, VALUE_FILE_SCOPE);
|
||||
break;
|
||||
case FOLDER:
|
||||
setProperty(ATTR_RESOURCE_SCOPE, VALUE_FOLDER_SCOPE);
|
||||
break;
|
||||
case PROJECT:
|
||||
setProperty(ATTR_RESOURCE_SCOPE, VALUE_PROJECT_SCOPE);
|
||||
break;
|
||||
default:
|
||||
setProperty(ATTR_RESOURCE_SCOPE, VALUE_FILE_SCOPE);
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
@Override
|
||||
protected void setSettingEntries(List<ICLanguageSettingEntry> entries) {
|
||||
IResource rc = null;
|
||||
switch (getResourceScope()) {
|
||||
case FILE:
|
||||
rc = currentResource;
|
||||
break;
|
||||
case FOLDER:
|
||||
if (currentResource instanceof IFile) {
|
||||
rc = currentResource.getParent();
|
||||
}
|
||||
break;
|
||||
case PROJECT:
|
||||
if (currentResource != null) {
|
||||
rc = currentResource.getProject();
|
||||
}
|
||||
break;
|
||||
default:
|
||||
break;
|
||||
|
||||
}
|
||||
setSettingEntries(currentCfgDescription, rc, currentLanguageId, entries);
|
||||
|
||||
// AG FIXME - temporary log to remove before CDT Juno release
|
||||
LanguageSettingsLogger.logInfo(getPrefixForLog()
|
||||
+ getClass().getSimpleName() + " collected " + (entries!=null ? ("" + entries.size()) : "null") + " entries for " + rc);
|
||||
|
||||
}
|
||||
|
||||
/**
|
||||
* Adjust count for file group taking into consideration extra groups added by {@link #getCompilerPatternExtended()}.
|
||||
*/
|
||||
|
|
|
@ -30,6 +30,7 @@ import org.eclipse.swt.layout.GridData;
|
|||
import org.eclipse.swt.layout.GridLayout;
|
||||
import org.eclipse.swt.widgets.Button;
|
||||
import org.eclipse.swt.widgets.Composite;
|
||||
import org.eclipse.swt.widgets.Group;
|
||||
import org.eclipse.swt.widgets.Label;
|
||||
import org.eclipse.swt.widgets.Text;
|
||||
|
||||
|
@ -46,7 +47,10 @@ public final class GCCBuildCommandParserOptionPage extends AbstractLanguageSetti
|
|||
private Button runOnceRadioButton;
|
||||
private Button runEveryBuildRadioButton;
|
||||
private Button expandRelativePathCheckBox;
|
||||
private Button applyToProjectCheckBox;
|
||||
|
||||
private Button scopeProjectRadioButton;
|
||||
private Button scopeFolderRadioButton;
|
||||
private Button scopeFileRadioButton;
|
||||
|
||||
|
||||
/*
|
||||
|
@ -157,25 +161,97 @@ public final class GCCBuildCommandParserOptionPage extends AbstractLanguageSetti
|
|||
|
||||
}
|
||||
|
||||
Group resourceScopeGroup = new Group(composite, SWT.NONE);
|
||||
{
|
||||
applyToProjectCheckBox = new Button(composite, SWT.CHECK);
|
||||
applyToProjectCheckBox.setText("Apply discovered settings on project level");
|
||||
// resourceScopeGroup.setText("Define scope of discovered entries");
|
||||
// resourceScopeGroup.setText("Apply discovered entries to");
|
||||
resourceScopeGroup.setText("Scope to keep discovered entries");
|
||||
resourceScopeGroup.setLayout(new GridLayout(2, false));
|
||||
GridData gd = new GridData(GridData.FILL_HORIZONTAL);
|
||||
gd.horizontalSpan = 2;
|
||||
applyToProjectCheckBox.setLayoutData(gd);
|
||||
resourceScopeGroup.setLayoutData(gd);
|
||||
}
|
||||
|
||||
// applyToProjectCheckBox.setSelection(provider.isExpandRelativePaths());
|
||||
// applyToProjectCheckBox.setEnabled(fEditable);
|
||||
applyToProjectCheckBox.setSelection(false);
|
||||
applyToProjectCheckBox.setEnabled(false);
|
||||
applyToProjectCheckBox.addSelectionListener(new SelectionAdapter() {
|
||||
{
|
||||
scopeFileRadioButton = new Button(resourceScopeGroup, SWT.RADIO);
|
||||
scopeFileRadioButton.setText("Per file, use when settings vary for different files");
|
||||
// applyToResourceRadioButton.setText("File level, use when settings vary for different files");
|
||||
GridData gd = new GridData(GridData.FILL_HORIZONTAL);
|
||||
gd.horizontalSpan = 2;
|
||||
scopeFileRadioButton.setLayoutData(gd);
|
||||
|
||||
scopeFileRadioButton.setSelection(provider.getResourceScope() == AbstractBuildCommandParser.ResourceScope.FILE);
|
||||
scopeFileRadioButton.setEnabled(fEditable);
|
||||
scopeFileRadioButton.addSelectionListener(new SelectionAdapter() {
|
||||
@Override
|
||||
public void widgetSelected(SelectionEvent e) {
|
||||
boolean enabled = applyToProjectCheckBox.getSelection();
|
||||
boolean enabled = scopeFileRadioButton.getSelection();
|
||||
AbstractBuildCommandParser provider = getRawProvider();
|
||||
if (enabled != provider.isResolvingPaths()) {
|
||||
if (enabled != (provider.getResourceScope() == AbstractBuildCommandParser.ResourceScope.FILE)) {
|
||||
AbstractBuildCommandParser selectedProvider = getWorkingCopy(providerId);
|
||||
selectedProvider.setResolvingPaths(enabled);
|
||||
selectedProvider.setResourceScope(AbstractBuildCommandParser.ResourceScope.FILE);
|
||||
providerTab.refreshItem(selectedProvider);
|
||||
}
|
||||
}
|
||||
|
||||
@Override
|
||||
public void widgetDefaultSelected(SelectionEvent e) {
|
||||
widgetSelected(e);
|
||||
}
|
||||
|
||||
});
|
||||
|
||||
}
|
||||
|
||||
{
|
||||
scopeFolderRadioButton = new Button(resourceScopeGroup, SWT.RADIO);
|
||||
scopeFolderRadioButton.setText("Per folder, use when settings are the same for all files in a folder");
|
||||
// applyToEnclosingFolderRadioButton.setText("Enclosing folder, use when settings are the same for all files in a folder");
|
||||
GridData gd = new GridData(GridData.FILL_HORIZONTAL);
|
||||
gd.horizontalSpan = 2;
|
||||
scopeFolderRadioButton.setLayoutData(gd);
|
||||
|
||||
scopeFolderRadioButton.setSelection(provider.getResourceScope() == AbstractBuildCommandParser.ResourceScope.FOLDER);
|
||||
scopeFolderRadioButton.setEnabled(fEditable);
|
||||
scopeFolderRadioButton.addSelectionListener(new SelectionAdapter() {
|
||||
@Override
|
||||
public void widgetSelected(SelectionEvent e) {
|
||||
boolean enabled = scopeFolderRadioButton.getSelection();
|
||||
AbstractBuildCommandParser provider = getRawProvider();
|
||||
if (enabled != (provider.getResourceScope() == AbstractBuildCommandParser.ResourceScope.FOLDER)) {
|
||||
AbstractBuildCommandParser selectedProvider = getWorkingCopy(providerId);
|
||||
selectedProvider.setResourceScope(AbstractBuildCommandParser.ResourceScope.FOLDER);
|
||||
providerTab.refreshItem(selectedProvider);
|
||||
}
|
||||
}
|
||||
|
||||
@Override
|
||||
public void widgetDefaultSelected(SelectionEvent e) {
|
||||
widgetSelected(e);
|
||||
}
|
||||
|
||||
});
|
||||
|
||||
}
|
||||
|
||||
{
|
||||
scopeProjectRadioButton = new Button(resourceScopeGroup, SWT.RADIO);
|
||||
scopeProjectRadioButton.setText("Per project, use when settings are the same for all files in the project");
|
||||
// applyToProjectRadioButton.setText("Project level, use when settings are the same for all files in the project");
|
||||
GridData gd = new GridData(GridData.FILL_HORIZONTAL);
|
||||
gd.horizontalSpan = 2;
|
||||
scopeProjectRadioButton.setLayoutData(gd);
|
||||
|
||||
scopeProjectRadioButton.setSelection(provider.getResourceScope() == AbstractBuildCommandParser.ResourceScope.PROJECT);
|
||||
scopeProjectRadioButton.setEnabled(fEditable);
|
||||
scopeProjectRadioButton.addSelectionListener(new SelectionAdapter() {
|
||||
@Override
|
||||
public void widgetSelected(SelectionEvent e) {
|
||||
boolean enabled = scopeProjectRadioButton.getSelection();
|
||||
AbstractBuildCommandParser provider = getRawProvider();
|
||||
if (enabled != (provider.getResourceScope() == AbstractBuildCommandParser.ResourceScope.PROJECT)) {
|
||||
AbstractBuildCommandParser selectedProvider = getWorkingCopy(providerId);
|
||||
selectedProvider.setResourceScope(AbstractBuildCommandParser.ResourceScope.PROJECT);
|
||||
providerTab.refreshItem(selectedProvider);
|
||||
}
|
||||
}
|
||||
|
|
Loading…
Add table
Reference in a new issue