@Test public void definitions_are_ordered_by_category_then_index_then_name_case_insensitive() { logIn(); propertyDefinitions.addComponent(PropertyDefinition.builder("sonar.prop.11").category("cat-1").index(1).name("prop 1").build()); propertyDefinitions.addComponent(PropertyDefinition.builder("sonar.prop.12").category("cat-1").index(2).name("prop 2").build()); propertyDefinitions.addComponent(PropertyDefinition.builder("sonar.prop.13").category("CAT-1").index(1).name("prop 3").build()); propertyDefinitions.addComponent(PropertyDefinition.builder("sonar.prop.41").category("cat-0").index(25).name("prop 1").build()); ListDefinitionsWsResponse result = executeRequest(); assertThat(result.getDefinitionsList()).extracting(Definition::getKey) .containsExactly("sonar.prop.41", "sonar.prop.11", "sonar.prop.13", "sonar.prop.12"); }
.category(CoreProperties.CATEGORY_EXCLUSIONS) .subCategory(CoreProperties.SUBCATEGORY_FILES_EXCLUSIONS) .index(0) .build(), PropertyDefinition.builder(CoreProperties.GLOBAL_TEST_EXCLUSIONS_PROPERTY) .category(CoreProperties.CATEGORY_EXCLUSIONS) .subCategory(CoreProperties.SUBCATEGORY_FILES_EXCLUSIONS) .index(1) .build(), .subCategory(CoreProperties.SUBCATEGORY_FILES_EXCLUSIONS) .onQualifiers(Qualifiers.PROJECT) .index(0) .build(), .subCategory(CoreProperties.SUBCATEGORY_FILES_EXCLUSIONS) .onQualifiers(Qualifiers.PROJECT) .index(1) .build(), PropertyDefinition.builder(CoreProperties.PROJECT_TEST_EXCLUSIONS_PROPERTY) .subCategory(CoreProperties.SUBCATEGORY_FILES_EXCLUSIONS) .onQualifiers(Qualifiers.PROJECT) .index(2) .build(), PropertyDefinition.builder(CoreProperties.PROJECT_TEST_INCLUSIONS_PROPERTY) .subCategory(CoreProperties.SUBCATEGORY_FILES_EXCLUSIONS)
.category(CoreProperties.CATEGORY_GENERAL) .subCategory(CoreProperties.SUBCATEGORY_DATABASE_CLEANER) .index(1) .build(), .category(CoreProperties.CATEGORY_GENERAL) .subCategory(CoreProperties.SUBCATEGORY_DATABASE_CLEANER) .index(2) .build(), .category(CoreProperties.CATEGORY_GENERAL) .subCategory(CoreProperties.SUBCATEGORY_DATABASE_CLEANER) .index(3) .build(), .category(CoreProperties.CATEGORY_GENERAL) .subCategory(CoreProperties.SUBCATEGORY_DATABASE_CLEANER) .index(4) .build(), .category(CoreProperties.CATEGORY_GENERAL) .subCategory(CoreProperties.SUBCATEGORY_DATABASE_CLEANER) .index(5) .build(), .category(CoreProperties.CATEGORY_GENERAL) .subCategory(CoreProperties.SUBCATEGORY_DATABASE_CLEANER) .index(6) .build()
.index(10) .name("File Suffixes") .description("List of suffixes for files to analyze.") .index(11) .defaultValue(EXCLUSIONS_DEFAULT_VALUE) .name("Go Exclusions") .index(19) .name("Path to test execution report(s)") .description("Path to test execution reports generated by Go with '-json' key, available since go1.10 (e.g.: go test -json > test-report.out).") .index(20) .name("Path to coverage report(s)") .description("Path to coverage reports generated by Go (e.g.: go test -coverprofile=coverage.out), ant patterns relative to project root are supported.") .index(30) .name("\"go vet\" Report Files") .description("Paths (absolute or relative) to the files with \"go vet\" issues.") .index(31) .name("Golint Report Files") .description("Paths (absolute or relative) to the files with Golint issues.") .index(32) .name("GoMetaLinter Report Files") .description("Paths (absolute or relative) to the files with GoMetaLinter issues.")
public static List<PropertyDefinition> definitions() { return Arrays .asList(PropertyDefinition.builder(GITLAB_URL).name("GitLab url").description("URL to access GitLab.").category(CATEGORY).subCategory(SUBCATEGORY).defaultValue("https://gitlab.com") .index(1).build(), PropertyDefinition.builder(GITLAB_IGNORE_CERT).name("GitLab Ignore Certificate").description("Ignore Certificate for access GitLab."). category(CATEGORY).subCategory(SUBCATEGORY). type(PropertyType.BOOLEAN). defaultValue(String.valueOf(false)). index(2).build(), PropertyDefinition.builder(GITLAB_USER_TOKEN).name("GitLab User Token").description("GitLab user token is developer role.").category(CATEGORY).subCategory(SUBCATEGORY) .type(PropertyType.PASSWORD).index(3).onQualifiers(Qualifiers.PROJECT, Qualifiers.VIEW).build(), PropertyDefinition.builder(GITLAB_MAX_GLOBAL_ISSUES).name("GitLab Max Global Issues").description("Max issues to show in global comment.").category(CATEGORY) .subCategory(SUBCATEGORY).type(PropertyType.INTEGER).defaultValue(String.valueOf(10)).index(4).build(), PropertyDefinition.builder(GITLAB_PROJECT_ID).name("GitLab Project id") .description("The unique id, path with namespace, name with namespace, web url, ssh url or http url of the current project that GitLab.").category(CATEGORY) .subCategory(SUBCATEGORY).index(5).onlyOnQualifiers(Qualifiers.PROJECT).build(), PropertyDefinition.builder(GITLAB_COMMIT_SHA).name("GitLab Commit SHA").description("The commit revision for which project is built.").category(CATEGORY) .subCategory(SUBCATEGORY).index(6).hidden().multiValues(true).build(), PropertyDefinition.builder(GITLAB_REF_NAME).name("GitLab Ref Name").description("The commit revision for which project is built.").category(CATEGORY).subCategory(SUBCATEGORY) .index(7).hidden().build(), PropertyDefinition.builder(GITLAB_MAX_BLOCKER_ISSUES_GATE).name("Max Blocker Issues Gate").description("Max blocker issues to make the status fail.").category(CATEGORY) .subCategory(SUBCATEGORY).type(PropertyType.INTEGER).defaultValue(String.valueOf(0)).onlyOnQualifiers(Qualifiers.PROJECT).index(9).build(), PropertyDefinition.builder(GITLAB_MAX_CRITICAL_ISSUES_GATE).name("Max Critical Issues Gate").description("Max critical issues to make the status fail.").category(CATEGORY) .subCategory(SUBCATEGORY).type(PropertyType.INTEGER).defaultValue(String.valueOf(0)).onlyOnQualifiers(Qualifiers.PROJECT).index(10).build(), PropertyDefinition.builder(GITLAB_MAX_MAJOR_ISSUES_GATE).name("Max Major Issues Gate").description("Max major issues to make the status fail.").category(CATEGORY) .subCategory(SUBCATEGORY).type(PropertyType.INTEGER).defaultValue(String.valueOf(-1)).onlyOnQualifiers(Qualifiers.PROJECT).index(11).build(), PropertyDefinition.builder(GITLAB_MAX_MINOR_ISSUES_GATE).name("Max Minor Issues Gate").description("Max minor issues to make the status fail.").category(CATEGORY) .subCategory(SUBCATEGORY).type(PropertyType.INTEGER).defaultValue(String.valueOf(-1)).onlyOnQualifiers(Qualifiers.PROJECT).index(12).build(), PropertyDefinition.builder(GITLAB_MAX_INFO_ISSUES_GATE).name("Max Info Issues Gate").description("Max info issues to make the status fail.").category(CATEGORY) .subCategory(SUBCATEGORY).type(PropertyType.INTEGER).defaultValue(String.valueOf(-1)).onlyOnQualifiers(Qualifiers.PROJECT).index(13).build(), PropertyDefinition.builder(GITLAB_COMMENT_NO_ISSUE).name("Comment when no new issue").description("Add a comment even when there is no new issue.").category(CATEGORY)
.type(BOOLEAN) .defaultValue(valueOf(false)) .index(1) .build(), PropertyDefinition.builder(CLIENT_ID) .category(CATEGORY) .subCategory(SUBCATEGORY) .index(2) .build(), PropertyDefinition.builder(CLIENT_SECRET) .category(CATEGORY) .subCategory(SUBCATEGORY) .index(3) .build(), PropertyDefinition.builder(MULTI_TENANT) .type(BOOLEAN) .defaultValue(valueOf(false)) .index(4) .build(), PropertyDefinition.builder(TENANT_ID) .category(CATEGORY) .subCategory(SUBCATEGORY) .index(5) .build(), PropertyDefinition.builder(ALLOW_USERS_TO_SIGN_UP)
.description("Patterns to ignore issues on certain components and for certain coding rules." + PROPERTY_RULE_KEY_PATTERN_HELP) .onQualifiers(Qualifiers.PROJECT) .index(3) .fields( PropertyFieldDefinition.build(RULE_KEY) "while continuing to scan and mark issues on the remainder of the file.") .onQualifiers(Qualifiers.PROJECT) .index(2) .fields( PropertyFieldDefinition.build(BEGIN_BLOCK_REGEXP) .description("Patterns to ignore all issues (except the ones from the common repository) on files that contain a block of code matching a given regular expression.") .onQualifiers(Qualifiers.PROJECT) .index(1) .fields( PropertyFieldDefinition.build(FILE_REGEXP) .description("Patterns to restrict the application of a rule to only certain components, ignoring all others." + PROPERTY_RULE_KEY_PATTERN_HELP) .onQualifiers(Qualifiers.PROJECT) .index(4) .fields( PropertyFieldDefinition.build(RULE_KEY)
.category(CoreProperties.CATEGORY_GENERAL) .subCategory(CoreProperties.SUBCATEGORY_DATABASE_CLEANER) .index(1) .build(), .category(CoreProperties.CATEGORY_GENERAL) .subCategory(CoreProperties.SUBCATEGORY_DATABASE_CLEANER) .index(2) .build(), .category(CoreProperties.CATEGORY_GENERAL) .subCategory(CoreProperties.SUBCATEGORY_DATABASE_CLEANER) .index(3) .build(), .category(CoreProperties.CATEGORY_GENERAL) .subCategory(CoreProperties.SUBCATEGORY_DATABASE_CLEANER) .index(4) .build(), .category(CoreProperties.CATEGORY_GENERAL) .subCategory(CoreProperties.SUBCATEGORY_DATABASE_CLEANER) .index(5) .build(), .category(CoreProperties.CATEGORY_GENERAL) .subCategory(CoreProperties.SUBCATEGORY_DATABASE_CLEANER) .index(6) .build()
.category(CATEGORY) .subCategory(SUBCATEGORY) .index(0) .build()); extensions.add(PropertyDefinition.builder(USER.property()) .category(CATEGORY) .subCategory(SUBCATEGORY) .index(1) .build()); extensions.add(PropertyDefinition.builder(ENABLED.property()) .category(CATEGORY) .subCategory(SUBCATEGORY) .index(2) .build()); .category(CATEGORY) .subCategory(SUBCATEGORY) .index(3) .fields( PropertyFieldDefinition.build(PROJECT.property())
.category(CoreProperties.CATEGORY_EXCLUSIONS) .subCategory(CoreProperties.SUBCATEGORY_FILES_EXCLUSIONS) .index(0) .build(), PropertyDefinition.builder(CoreProperties.GLOBAL_TEST_EXCLUSIONS_PROPERTY) .category(CoreProperties.CATEGORY_EXCLUSIONS) .subCategory(CoreProperties.SUBCATEGORY_FILES_EXCLUSIONS) .index(1) .build(), .subCategory(CoreProperties.SUBCATEGORY_FILES_EXCLUSIONS) .onQualifiers(Qualifiers.PROJECT) .index(0) .build(), .subCategory(CoreProperties.SUBCATEGORY_FILES_EXCLUSIONS) .onQualifiers(Qualifiers.PROJECT) .index(1) .build(), PropertyDefinition.builder(CoreProperties.PROJECT_TEST_EXCLUSIONS_PROPERTY) .subCategory(CoreProperties.SUBCATEGORY_FILES_EXCLUSIONS) .onQualifiers(Qualifiers.PROJECT) .index(2) .build(), PropertyDefinition.builder(CoreProperties.PROJECT_TEST_INCLUSIONS_PROPERTY) .subCategory(CoreProperties.SUBCATEGORY_FILES_EXCLUSIONS)
.index(10) .name("File Suffixes") .description("Comma-separated list of suffixes of Python files to analyze.") .index(20) .name("Path to coverage report(s)") .description("Path to coverage reports. Ant patterns are accepted for relative path. The reports have to conform to the Cobertura XML format.") .index(21) .name("Path to coverage report(s) for integration tests") .description(DEPRECATED_PREFIX + .index(22) .name("Path to overall (combined UT+IT) coverage report(s)") .description(DEPRECATED_PREFIX +
private static void addPylintExtensions(Context context) { context.addExtensions( PropertyDefinition.builder(PylintConfiguration.PYLINT_CONFIG_KEY) .index(30) .name("Pylint configuration") .description("Path to the pylint configuration file to use in pylint analysis. Set to empty to use the default.") .build(), PropertyDefinition.builder(PylintConfiguration.PYLINT_KEY) .index(31) .name("Pylint executable") .description("Path to the pylint executable to use in pylint analysis. Set to empty to use the default one.") .build(), PropertyDefinition.builder(PylintImportSensor.REPORT_PATH_KEY) .index(32) .name("Pylint's reports") .description("Path to Pylint's report file, relative to projects root")
@Override public void define(Context context) { context.addExtensions( PropertyDefinition.builder(FILE_SUFFIXES_KEY) .index(10) .name("File Suffixes") .description("List of suffixes of Python files to analyze.") .multiValues(true) .category(PYTHON_CATEGORY) .subCategory(GENERAL) .onQualifiers(Qualifiers.PROJECT) .defaultValue("py") .build(), Python.class, PythonProfile.class, PythonSquidSensor.class, PythonRuleRepository.class); SonarRuntime sonarRuntime = context.getRuntime(); if (sonarRuntime.getProduct() != SonarProduct.SONARLINT) { if (sonarRuntime.getApiVersion().isGreaterThanOrEqual(SQ_MIN_VERSION_ANALYSIS_WARNINGS)) { context.addExtension(DefaultAnalysisWarningsWrapper.class); } else { context.addExtension(NoOpAnalysisWarningsWrapper.class); } addCoberturaExtensions(context); addXUnitExtensions(context); addPylintExtensions(context); addBanditExtensions(context); } }
private static void addPylintExtensions(Context context) { context.addExtensions( PropertyDefinition.builder(PylintConfiguration.PYLINT_CONFIG_KEY) .index(30) .name("Pylint configuration") .description("Path to the pylint configuration file to use in pylint analysis. Set to empty to use the default.") .build(), PropertyDefinition.builder(PylintConfiguration.PYLINT_KEY) .index(31) .name("Pylint executable") .description("Path to the pylint executable to use in pylint analysis. Set to empty to use the default one.") .build(), PropertyDefinition.builder(PylintImportSensor.REPORT_PATH_KEY) .index(32) .name("Pylint's reports") .description("Path to Pylint's report file, relative to projects root")
private static void addCoberturaExtensions(Context context) { context.addExtensions( PropertyDefinition.builder(PythonCoverageSensor.REPORT_PATHS_KEY) .index(20) .name("Path to coverage report(s)") .description("List of paths pointing to coverage reports. Ant patterns are accepted for relative path. " + "The reports have to conform to the Cobertura XML format.") .category(PYTHON_CATEGORY) .subCategory(TEST_AND_COVERAGE) .onQualifiers(Qualifiers.PROJECT) .defaultValue(PythonCoverageSensor.DEFAULT_REPORT_PATH) .multiValues(true) .build(), // deprecated PropertyDefinition.builder(PythonCoverageSensor.REPORT_PATH_KEY) .index(21) .name("Path to coverage report") .description(DEPRECATED_PREFIX + "Path to a coverage report. Ant patterns are accepted for relative path. The report has to conform to the Cobertura XML format.") .category(PYTHON_CATEGORY) .subCategory(TEST_AND_COVERAGE) .onQualifiers(Qualifiers.PROJECT) .defaultValue("") .build(), PythonCoverageSensor.class); }
static List<PropertyDefinition> definitions() { return Arrays.asList(PropertyDefinition.builder(GITLAB_AUTH_ENABLED).name("Enabled").description("Enable Gitlab users to login. Value is ignored if client ID and secret are not defined.") .category(CATEGORY).subCategory(SUBCATEGORY).type(BOOLEAN).defaultValue(valueOf(false)).index(1).build(), PropertyDefinition.builder(GITLAB_AUTH_URL).name("GitLab url").description("URL to access GitLab.").category(CATEGORY).subCategory(SUBCATEGORY).defaultValue("https://gitlab.com") .index(2).build(), PropertyDefinition.builder(GITLAB_AUTH_APPLICATIONID).name("Application ID").description("Application ID provided by GitLab when registering the application.").category(CATEGORY) .subCategory(SUBCATEGORY).index(3).build(), PropertyDefinition.builder(GITLAB_AUTH_SECRET).name("Secret").description("Secret provided by GitLab when registering the application.").category(CATEGORY).subCategory(SUBCATEGORY) .index(4).build(), PropertyDefinition.builder(GITLAB_AUTH_ALLOWUSERSTOSIGNUP).name("Allow users to sign-up") .description("Allow new users to authenticate. When set to 'false', only existing users will be able to authenticate to the server.").category(CATEGORY) .subCategory(SUBCATEGORY).type(BOOLEAN).defaultValue(valueOf(true)).index(5).build(), PropertyDefinition.builder(GITLAB_AUTH_SCOPE).name("Gitlab access scope").description("Scope provided by GitLab when access user info.").category(CATEGORY).subCategory(SUBCATEGORY) .type(SINGLE_SELECT_LIST).options(NONE_SCOPE, READ_USER_SCOPE, API_SCOPE).defaultValue(READ_USER_SCOPE).index(6).build(), PropertyDefinition.builder(GITLAB_AUTH_GROUPS).name("Default groups").description("Set default groups for user").category(CATEGORY).subCategory(SUBCATEGORY).index(7).build(), PropertyDefinition.builder(GITLAB_AUTH_SYNC_USER_GROUPS).name("Synchronize user groups").description("Synchronize GitLab and Sonar user groups").category(CATEGORY) .subCategory(SUBCATEGORY).type(PropertyType.BOOLEAN).defaultValue(valueOf(false)).index(8).build(), PropertyDefinition.builder(GITLAB_AUTH_API_VERSION).name("Set GitLab API version").description("GitLab API version").category(CATEGORY).subCategory(SUBCATEGORY) .type(PropertyType.SINGLE_SELECT_LIST).options(V3_API_VERSION, V4_API_VERSION).defaultValue(V4_API_VERSION).index(9).build(), PropertyDefinition.builder(GITLAB_AUTH_USER_EXCEPTIONS).name("User exceptions").description("Comma separated list of usernames to keep intact").category(CATEGORY) .subCategory(SUBCATEGORY).type(PropertyType.STRING).defaultValue("").index(10).build(), PropertyDefinition.builder(GITLAB_AUTH_IGNORE_CERT).name("GitLab Ignore Certificate").description("Ignore Certificate for access GitLab."). category(CATEGORY).subCategory(SUBCATEGORY). type(PropertyType.BOOLEAN). defaultValue(String.valueOf(false)). index(11).build()); }
private static void addXUnitExtensions(Context context) { context.addExtensions( PropertyDefinition.builder(PythonXUnitSensor.SKIP_DETAILS) .index(23) .name("Skip the details when importing the Xunit reports") .description("When enabled the test execution statistics is provided only on project level. Use this mode when paths in report are not found. Disabled by default.") .category(PYTHON_CATEGORY) .subCategory(TEST_AND_COVERAGE) .onQualifiers(Qualifiers.PROJECT) .defaultValue("false") .type(PropertyType.BOOLEAN) .build(), PropertyDefinition.builder(PythonXUnitSensor.REPORT_PATH_KEY) .index(24) .name("Path to xunit report(s)") .description("Path to the report of test execution, relative to project's root. Ant patterns are accepted. The reports have to conform to the junitreport XML format.") .category(PYTHON_CATEGORY) .subCategory(TEST_AND_COVERAGE) .onQualifiers(Qualifiers.PROJECT) .defaultValue(PythonXUnitSensor.DEFAULT_REPORT_PATH) .build(), PythonXUnitSensor.class); }
private static void addXUnitExtensions(Context context) { context.addExtensions( PropertyDefinition.builder(PythonXUnitSensor.SKIP_DETAILS) .index(23) .name("Skip the details when importing the Xunit reports") .description("When enabled the test execution statistics is provided only on project level. Use this mode when paths in report are not found. Disabled by default.") .category(PYTHON_CATEGORY) .subCategory(TEST_AND_COVERAGE) .onQualifiers(Qualifiers.PROJECT) .defaultValue("false") .type(PropertyType.BOOLEAN) .build(), PropertyDefinition.builder(PythonXUnitSensor.REPORT_PATH_KEY) .index(24) .name("Path to xunit report(s)") .description("Path to the report of test execution, relative to project's root. Ant patterns are accepted. The reports have to conform to the junitreport XML format.") .category(PYTHON_CATEGORY) .subCategory(TEST_AND_COVERAGE) .onQualifiers(Qualifiers.PROJECT) .defaultValue(PythonXUnitSensor.DEFAULT_REPORT_PATH) .build(), PythonXUnitSensor.class); }
@Override public List getExtensions() { return ImmutableList.of( PropertyDefinition.builder(ENABLED). defaultValue(ENABLED_DEFAULT). name("Activation of Useless code tracker plugin"). description("This property can be set to false in order to deactivate the Useless code tracker plugin."). index(0). onQualifiers(Qualifiers.PROJECT). category(TRACKER_CATEGORY). subCategory(COMMON_SUBCATEGORY). type(PropertyType.BOOLEAN). build(), TrackerMetrics.class, TempMethodLinesDecorator.class, TrackerWidget.class, TotalDecorator.class, DuplicationsDecorator.class); }
.description("Patterns to ignore issues on certain components and for certain coding rules." + PROPERTY_RULE_KEY_PATTERN_HELP) .onQualifiers(Qualifiers.PROJECT) .index(3) .fields( PropertyFieldDefinition.build(RULE_KEY) "while continuing to scan and mark issues on the remainder of the file.") .onQualifiers(Qualifiers.PROJECT) .index(2) .fields( PropertyFieldDefinition.build(BEGIN_BLOCK_REGEXP) .description("Patterns to ignore all issues (except the ones from the common repository) on files that contain a block of code matching a given regular expression.") .onQualifiers(Qualifiers.PROJECT) .index(1) .fields( PropertyFieldDefinition.build(FILE_REGEXP) .description("Patterns to restrict the application of a rule to only certain components, ignoring all others." + PROPERTY_RULE_KEY_PATTERN_HELP) .onQualifiers(Qualifiers.PROJECT) .index(4) .fields( PropertyFieldDefinition.build(RULE_KEY)