diff --git a/.automation/build.py b/.automation/build.py index f48fd1ae883..bb06e81b0eb 100644 --- a/.automation/build.py +++ b/.automation/build.py @@ -25,6 +25,7 @@ from bs4 import BeautifulSoup from giturlparse import parse from megalinter.constants import ( + DEFAULT_RELEASE, DEFAULT_REPORT_FOLDER_NAME, ML_DOC_URL, ML_DOCKER_IMAGE, @@ -191,7 +192,7 @@ def generate_flavor(flavor, flavor_info): if RELEASE is True: image_release = RELEASE_TAG else: - image_release = "v5" + image_release = DEFAULT_RELEASE flavor_x = f"[{flavor} flavor]" action_yml = f""" # Automatically {'@'}generated by build.py name: "MegaLinter" @@ -544,11 +545,11 @@ def generate_descriptor_documentation(descriptor): def generate_flavor_documentation(flavor_id, flavor, linters_tables_md): - flavor_github_action = f"{ML_REPO}/flavors/{flavor_id}@v5" - flavor_docker_image = f"{ML_DOCKER_IMAGE}-{flavor_id}:v5" + flavor_github_action = f"{ML_REPO}/flavors/{flavor_id}@{DEFAULT_RELEASE}" + flavor_docker_image = f"{ML_DOCKER_IMAGE}-{flavor_id}:{DEFAULT_RELEASE}" docker_image_badge = ( f"![Docker Image Size (tag)]({BASE_SHIELD_IMAGE_LINK}/" - f"{ML_DOCKER_IMAGE}-{flavor_id}/v5)" + f"{ML_DOCKER_IMAGE}-{flavor_id}/{DEFAULT_RELEASE})" ) docker_pulls_badge = ( f"![Docker Pulls]({BASE_SHIELD_COUNT_LINK}/" f"{ML_DOCKER_IMAGE}-{flavor_id})" @@ -1224,7 +1225,7 @@ def build_flavors_md_table(filter_linter_name=None, replace_link=False): + +len(linters_by_type["other"]) ) docker_image_badge = ( - f"![Docker Image Size (tag)]({BASE_SHIELD_IMAGE_LINK}/{ML_DOCKER_IMAGE}/v5)" + f"![Docker Image Size (tag)]({BASE_SHIELD_IMAGE_LINK}/{ML_DOCKER_IMAGE}/{DEFAULT_RELEASE})" ) docker_pulls_badge = ( f"![Docker Pulls]({BASE_SHIELD_COUNT_LINK}/" f"{ML_DOCKER_IMAGE})" @@ -1252,7 +1253,7 @@ def build_flavors_md_table(filter_linter_name=None, replace_link=False): flavor_doc_url = f"{DOCS_URL_FLAVORS_ROOT}/{flavor_id}.md" docker_image_badge = ( f"![Docker Image Size (tag)]({BASE_SHIELD_IMAGE_LINK}/" - f"{ML_DOCKER_IMAGE}-{flavor_id}/v5)" + f"{ML_DOCKER_IMAGE}-{flavor_id}/{DEFAULT_RELEASE})" ) docker_pulls_badge = ( f"![Docker Pulls]({BASE_SHIELD_COUNT_LINK}/" diff --git a/.automation/generated/flavors-stats.json b/.automation/generated/flavors-stats.json index fc80e1ece16..131d3e53cab 100644 --- a/.automation/generated/flavors-stats.json +++ b/.automation/generated/flavors-stats.json @@ -383,6 +383,10 @@ [ "2021-12-04T10:20:40", 1949864 + ], + [ + "2021-12-05T01:37:50", + 1981415 ] ], "ci_light": [ @@ -769,6 +773,10 @@ [ "2021-12-04T10:20:40", 5468 + ], + [ + "2021-12-05T01:37:50", + 5473 ] ], "dart": [ @@ -1155,6 +1163,10 @@ [ "2021-12-04T10:20:40", 1630 + ], + [ + "2021-12-05T01:37:50", + 1634 ] ], "documentation": [ @@ -1541,6 +1553,10 @@ [ "2021-12-04T10:20:40", 23337 + ], + [ + "2021-12-05T01:37:50", + 23344 ] ], "dotnet": [ @@ -1927,6 +1943,10 @@ [ "2021-12-04T10:20:40", 256159 + ], + [ + "2021-12-05T01:37:50", + 256346 ] ], "go": [ @@ -2313,6 +2333,10 @@ [ "2021-12-04T10:20:40", 5717 + ], + [ + "2021-12-05T01:37:50", + 5729 ] ], "java": [ @@ -2699,6 +2723,10 @@ [ "2021-12-04T10:20:40", 42313 + ], + [ + "2021-12-05T01:37:50", + 42323 ] ], "javascript": [ @@ -3085,6 +3113,10 @@ [ "2021-12-04T10:20:40", 59476 + ], + [ + "2021-12-05T01:37:50", + 59584 ] ], "php": [ @@ -3471,6 +3503,10 @@ [ "2021-12-04T10:20:40", 2675 + ], + [ + "2021-12-05T01:37:50", + 2699 ] ], "python": [ @@ -3857,6 +3893,10 @@ [ "2021-12-04T10:20:40", 32672 + ], + [ + "2021-12-05T01:37:50", + 32768 ] ], "ruby": [ @@ -4239,6 +4279,10 @@ [ "2021-12-04T10:20:40", 1562 + ], + [ + "2021-12-05T01:37:50", + 1566 ] ], "rust": [ @@ -4621,6 +4665,10 @@ [ "2021-12-04T10:20:40", 1305 + ], + [ + "2021-12-05T01:37:50", + 1309 ] ], "salesforce": [ @@ -5007,6 +5055,10 @@ [ "2021-12-04T10:20:40", 8673 + ], + [ + "2021-12-05T01:37:50", + 8685 ] ], "scala": [ @@ -5389,6 +5441,10 @@ [ "2021-12-04T10:20:40", 1158 + ], + [ + "2021-12-05T01:37:50", + 1162 ] ], "swift": [ @@ -5771,6 +5827,10 @@ [ "2021-12-04T10:20:40", 1058 + ], + [ + "2021-12-05T01:37:50", + 1062 ] ], "terraform": [ @@ -6157,6 +6217,10 @@ [ "2021-12-04T10:20:40", 24900 + ], + [ + "2021-12-05T01:37:50", + 24950 ] ] } \ No newline at end of file diff --git a/.automation/generated/linter-helps.json b/.automation/generated/linter-helps.json index 9986d612763..535216beba4 100644 --- a/.automation/generated/linter-helps.json +++ b/.automation/generated/linter-helps.json @@ -1379,8 +1379,8 @@ " of opening bracket's line.", " --ignore errors Comma-separated list of errors and warnings to ignore", " (or skip). For example, ``--ignore=E4,E51,W234``.", - " (Default: ['E704', 'E24', 'E126', 'E123', 'W503',", - " 'W504', 'E121', 'E226'])", + " (Default: ['E126', 'E24', 'E704', 'W503', 'E123',", + " 'W504', 'E226', 'E121'])", " --extend-ignore errors", " Comma-separated list of errors and warnings to add to", " the list of ignored ones. For example, ``--extend-", @@ -3480,6 +3480,9 @@ " --no-diff", " Turns off Psalm\u2019s diff mode, checks all files regardless of whether they\u2019ve changed.", "", + " --php-version=PHP_VERSION", + " Explicitly set PHP version to analyse code against.", + "", "Surfacing issues:", " --show-info[=BOOLEAN]", " Show non-exception parser findings (defaults to false).", @@ -5798,7 +5801,7 @@ " [--shadow-prefix DIR] [--scheduler [{ilp,greedy}]]", " [--wms-monitor [WMS_MONITOR]]", " [--wms-monitor-arg [NAME=VALUE ...]]", - " [--scheduler-ilp-solver {PULP_CBC_CMD,PULP_CHOCO_CMD}]", + " [--scheduler-ilp-solver {PULP_CBC_CMD}]", " [--scheduler-solver-path SCHEDULER_SOLVER_PATH]", " [--conda-base-path CONDA_BASE_PATH] [--no-subworkflows]", " [--groups GROUPS [GROUPS ...]]", @@ -6099,7 +6102,7 @@ " id=12345 and the arguments will be provided to the", " endpoint to first interact with the workflow (default:", " None)", - " --scheduler-ilp-solver {PULP_CBC_CMD,PULP_CHOCO_CMD}", + " --scheduler-ilp-solver {PULP_CBC_CMD}", " Specifies solver to be utilized when selecting ilp-", " scheduler. (default: COIN_CMD)", " --scheduler-solver-path SCHEDULER_SOLVER_PATH", diff --git a/.automation/generated/linter-versions.json b/.automation/generated/linter-versions.json index f123668de72..4fbd1ac9f05 100644 --- a/.automation/generated/linter-versions.json +++ b/.automation/generated/linter-versions.json @@ -50,7 +50,7 @@ "phplint": "3.0", "phpstan": "1.2.0", "powershell": "7.2.0", - "prettier": "2.5.0", + "prettier": "2.5.1", "protolint": "0.35.2", "psalm": "Psalm.4.x-dev@", "puppet-lint": "2.5.2", diff --git a/.vscode/launch.json b/.vscode/launch.json new file mode 100644 index 00000000000..f87322650bb --- /dev/null +++ b/.vscode/launch.json @@ -0,0 +1,15 @@ +{ + // Use IntelliSense to learn about possible attributes. + // Hover to view descriptions of existing attributes. + // For more information, visit: https://go.microsoft.com/fwlink/?linkid=830387 + "version": "0.2.0", + "configurations": [ + { + "name": "Python : CurrentFile", + "type": "python", + "request": "test", + "program": "${file}", + "console": "integratedTerminal" + } + ] +} \ No newline at end of file diff --git a/CHANGELOG.md b/CHANGELOG.md index c2cb4cfad9e..5eddd574ecd 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -12,9 +12,11 @@ Note: Can be used with `megalinter/megalinter@beta` in your GitHub Action mega-l - Core architecture - New reporter **SARIF_REPORTER** that aggregates all SARIF output files into a single one + - Correct SARIF files for known format errors - Manage offline run of `bash build.sh` for those who want to code in planes :) - Automate update of CHANGELOG.md after release (pilot) - Rename default report folder from `report` to `megalinter-reports` + - Accelerate internal CI testing performances - Linters: - Add [PMD](https://pmd.github.io/) to lint java files (disabled for now) @@ -26,6 +28,7 @@ Note: Can be used with `megalinter/megalinter@beta` in your GitHub Action mega-l - checkov - eslint - gitleaks + - trivy - Descriptors: - New flavor **Security** @@ -41,6 +44,7 @@ Note: Can be used with `megalinter/megalinter@beta` in your GitHub Action mega-l - Docker run -- clean-up containers when exits (#1033) - Add missing Bandit config file and rules path options (#679) - Fix getting linter version of npm plugin. (#845) +- Improve runtime performances when using a flavor and defining `FLAVORS_SUGGESTION: false` - Linters - New linter `phplint` to speed-up linting of php files (#1031) @@ -92,6 +96,7 @@ Note: Can be used with `megalinter/megalinter@beta` in your GitHub Action mega-l - [pylint](https://www.pylint.org) from 2.12.1 to **2.12.2** on 2021-12-04 - [checkov](https://www.checkov.io/) from 2.0.625 to **2.0.626** on 2021-12-04 - [eslint](https://eslint.org) from 8.3.0 to **8.4.0** on 2021-12-04 + - [prettier](https://prettier.io/) from 2.5.0 to **2.5.1** on 2021-12-05 ## [v5.2.0] - 2021-11-18 diff --git a/README.md b/README.md index c8aff5e4746..7fc9774fbfc 100644 --- a/README.md +++ b/README.md @@ -14,7 +14,7 @@ ![GitHub release](https://img.shields.io/github/v/release/megalinter/megalinter?sort=semver) -[![Docker Pulls](https://img.shields.io/badge/docker%20pulls-2.4M-blue)](https://megalinter.github.io/flavors/) +[![Docker Pulls](https://img.shields.io/badge/docker%20pulls-2.5M-blue)](https://megalinter.github.io/flavors/) [![Downloads/week](https://img.shields.io/npm/dw/mega-linter-runner.svg)](https://npmjs.org/package/mega-linter-runner) [![GitHub stars](https://img.shields.io/github/stars/megalinter/megalinter?cacheSeconds=3600)](https://github.com/megalinter/megalinter/stargazers/) [![MegaLinter](https://github.com/megalinter/megalinter/workflows/MegaLinter/badge.svg?branch=main)](https://github.com/megalinter/megalinter/actions?query=workflow%3AMegaLinter+branch%3Amain) diff --git a/docs/all_linters.md b/docs/all_linters.md index 9c9b923f4c8..d2739ae9e69 100644 --- a/docs/all_linters.md +++ b/docs/all_linters.md @@ -56,7 +56,7 @@ | [**phplint**](https://github.com/overtrue/phplint){target=_blank} | 3.0 | | [PHP](descriptors/php_phplint.md) | :white_circle: | [Web Site](https://github.com/overtrue/phplint){target=_blank} | | [**phpstan**](https://github.com/phpstan/phpstan){target=_blank} | 1.2.0 | MIT | [PHP](descriptors/php_phpstan.md) | :white_circle: | [Repository](https://github.com/phpstan/phpstan){target=_blank} | | [**powershell**](https://github.com/PowerShell/PSScriptAnalyzer){target=_blank} | 7.2.0 | | [POWERSHELL](descriptors/powershell_powershell.md) | :white_circle: | [Web Site](https://github.com/PowerShell/PSScriptAnalyzer){target=_blank} | -| [**prettier**](https://github.com/prettier/prettier){target=_blank} | 2.5.0 | MIT | [JAVASCRIPT](descriptors/javascript_prettier.md)
[JSON](descriptors/json_prettier.md)
[TYPESCRIPT](descriptors/typescript_prettier.md)
[YAML](descriptors/yaml_prettier.md) | :white_circle: | [Repository](https://github.com/prettier/prettier){target=_blank} | +| [**prettier**](https://github.com/prettier/prettier){target=_blank} | 2.5.1 | MIT | [JAVASCRIPT](descriptors/javascript_prettier.md)
[JSON](descriptors/json_prettier.md)
[TYPESCRIPT](descriptors/typescript_prettier.md)
[YAML](descriptors/yaml_prettier.md) | :white_circle: | [Repository](https://github.com/prettier/prettier){target=_blank} | | [**protolint**](https://github.com/yoheimuta/protolint){target=_blank} | 0.35.2 | | [PROTOBUF](descriptors/protobuf_protolint.md) | :white_circle: | [Web Site](https://github.com/yoheimuta/protolint){target=_blank} | | [**psalm**](https://github.com/vimeo/psalm){target=_blank} | Psalm.4.x-dev@ | MIT | [PHP](descriptors/php_psalm.md) | :white_circle: | [Repository](https://github.com/vimeo/psalm){target=_blank} | | [**puppet-lint**](https://github.com/rodjek/puppet-lint){target=_blank} | 2.5.2 | MIT | [PUPPET](descriptors/puppet_puppet_lint.md) | :white_circle: | [Repository](https://github.com/rodjek/puppet-lint){target=_blank} | diff --git a/docs/descriptors/javascript_prettier.md b/docs/descriptors/javascript_prettier.md index 316bf0e8252..15beb43b91b 100644 --- a/docs/descriptors/javascript_prettier.md +++ b/docs/descriptors/javascript_prettier.md @@ -9,7 +9,7 @@ ## prettier documentation -- Version in MegaLinter: **2.5.0** +- Version in MegaLinter: **2.5.1** - Visit [Official Web Site](https://prettier.io/){target=_blank} - See [How to configure prettier rules](https://prettier.io/docs/en/configuration.html){target=_blank} - See [How to disable prettier rules in files](https://prettier.io/docs/en/ignore.html#javascript){target=_blank} diff --git a/docs/descriptors/json_prettier.md b/docs/descriptors/json_prettier.md index 3a6f7336bb3..624b1c8397f 100644 --- a/docs/descriptors/json_prettier.md +++ b/docs/descriptors/json_prettier.md @@ -9,7 +9,7 @@ ## prettier documentation -- Version in MegaLinter: **2.5.0** +- Version in MegaLinter: **2.5.1** - Visit [Official Web Site](https://prettier.io/){target=_blank} - See [How to configure prettier rules](https://prettier.io/docs/en/configuration.html){target=_blank} - See [How to disable prettier rules in files](https://prettier.io/docs/en/ignore.html#javascript){target=_blank} diff --git a/docs/descriptors/php_psalm.md b/docs/descriptors/php_psalm.md index bdd7ac9ae2c..f88aa9693cc 100644 --- a/docs/descriptors/php_psalm.md +++ b/docs/descriptors/php_psalm.md @@ -112,6 +112,9 @@ Basic configuration: --no-diff Turns off Psalm’s diff mode, checks all files regardless of whether they’ve changed. + --php-version=PHP_VERSION + Explicitly set PHP version to analyse code against. + Surfacing issues: --show-info[=BOOLEAN] Show non-exception parser findings (defaults to false). diff --git a/docs/descriptors/python_flake8.md b/docs/descriptors/python_flake8.md index 0fcd0a22009..7671c67c3fe 100644 --- a/docs/descriptors/python_flake8.md +++ b/docs/descriptors/python_flake8.md @@ -124,8 +124,8 @@ optional arguments: of opening bracket's line. --ignore errors Comma-separated list of errors and warnings to ignore (or skip). For example, ``--ignore=E4,E51,W234``. - (Default: ['E704', 'E24', 'E126', 'E123', 'W503', - 'W504', 'E121', 'E226']) + (Default: ['E126', 'E24', 'E704', 'W503', 'E123', + 'W504', 'E226', 'E121']) --extend-ignore errors Comma-separated list of errors and warnings to add to the list of ignored ones. For example, ``--extend- diff --git a/docs/descriptors/snakemake_snakemake.md b/docs/descriptors/snakemake_snakemake.md index 01d1c5a881e..891e837f4ca 100644 --- a/docs/descriptors/snakemake_snakemake.md +++ b/docs/descriptors/snakemake_snakemake.md @@ -105,7 +105,7 @@ usage: snakemake [-h] [--dry-run] [--profile PROFILE] [--cache [RULE ...]] [--shadow-prefix DIR] [--scheduler [{ilp,greedy}]] [--wms-monitor [WMS_MONITOR]] [--wms-monitor-arg [NAME=VALUE ...]] - [--scheduler-ilp-solver {PULP_CBC_CMD,PULP_CHOCO_CMD}] + [--scheduler-ilp-solver {PULP_CBC_CMD}] [--scheduler-solver-path SCHEDULER_SOLVER_PATH] [--conda-base-path CONDA_BASE_PATH] [--no-subworkflows] [--groups GROUPS [GROUPS ...]] @@ -406,7 +406,7 @@ EXECUTION: id=12345 and the arguments will be provided to the endpoint to first interact with the workflow (default: None) - --scheduler-ilp-solver {PULP_CBC_CMD,PULP_CHOCO_CMD} + --scheduler-ilp-solver {PULP_CBC_CMD} Specifies solver to be utilized when selecting ilp- scheduler. (default: COIN_CMD) --scheduler-solver-path SCHEDULER_SOLVER_PATH diff --git a/docs/descriptors/typescript_prettier.md b/docs/descriptors/typescript_prettier.md index 172625ea2d0..082ee7523ca 100644 --- a/docs/descriptors/typescript_prettier.md +++ b/docs/descriptors/typescript_prettier.md @@ -9,7 +9,7 @@ ## prettier documentation -- Version in MegaLinter: **2.5.0** +- Version in MegaLinter: **2.5.1** - Visit [Official Web Site](https://prettier.io/){target=_blank} - See [How to configure prettier rules](https://prettier.io/docs/en/configuration.html){target=_blank} - See [How to disable prettier rules in files](https://prettier.io/docs/en/ignore.html#javascript){target=_blank} diff --git a/docs/descriptors/yaml_prettier.md b/docs/descriptors/yaml_prettier.md index dd63c7ea52e..466306843d1 100644 --- a/docs/descriptors/yaml_prettier.md +++ b/docs/descriptors/yaml_prettier.md @@ -9,7 +9,7 @@ ## prettier documentation -- Version in MegaLinter: **2.5.0** +- Version in MegaLinter: **2.5.1** - Visit [Official Web Site](https://prettier.io/){target=_blank} - See [How to configure prettier rules](https://prettier.io/docs/en/configuration.html){target=_blank} - See [How to disable prettier rules in files](https://prettier.io/docs/en/ignore.html#yaml){target=_blank} diff --git a/docs/index.md b/docs/index.md index f0a099a74db..1b9dd501fe5 100644 --- a/docs/index.md +++ b/docs/index.md @@ -13,7 +13,7 @@ ![GitHub release](https://img.shields.io/github/v/release/megalinter/megalinter?sort=semver) -[![Docker Pulls](https://img.shields.io/badge/docker%20pulls-2.4M-blue)](https://megalinter.github.io/flavors/) +[![Docker Pulls](https://img.shields.io/badge/docker%20pulls-2.5M-blue)](https://megalinter.github.io/flavors/) [![Downloads/week](https://img.shields.io/npm/dw/mega-linter-runner.svg)](https://npmjs.org/package/mega-linter-runner) [![GitHub stars](https://img.shields.io/github/stars/megalinter/megalinter?cacheSeconds=3600)](https://github.com/megalinter/megalinter/stargazers/) [![MegaLinter](https://github.com/megalinter/megalinter/workflows/MegaLinter/badge.svg?branch=main)](https://github.com/megalinter/megalinter/actions?query=workflow%3AMegaLinter+branch%3Amain) diff --git a/flavors/ci_light/action.yml b/flavors/ci_light/action.yml index ab9dfbb8a11..569157d36ff 100644 --- a/flavors/ci_light/action.yml +++ b/flavors/ci_light/action.yml @@ -7,7 +7,7 @@ outputs: description: "0 if no source file has been updated, 1 if source files has been updated" runs: using: "docker" - image: "docker://megalinter/megalinter-ci_light:v5" + image: "docker://megalinter/megalinter-ci_light:v6-alpha" args: - "-v" - "/var/run/docker.sock:/var/run/docker.sock:rw" diff --git a/flavors/dart/action.yml b/flavors/dart/action.yml index 53356ae875c..1a1b7aa7dc2 100644 --- a/flavors/dart/action.yml +++ b/flavors/dart/action.yml @@ -7,7 +7,7 @@ outputs: description: "0 if no source file has been updated, 1 if source files has been updated" runs: using: "docker" - image: "docker://megalinter/megalinter-dart:v5" + image: "docker://megalinter/megalinter-dart:v6-alpha" args: - "-v" - "/var/run/docker.sock:/var/run/docker.sock:rw" diff --git a/flavors/documentation/action.yml b/flavors/documentation/action.yml index ae90e36ca1b..54ab83ee253 100644 --- a/flavors/documentation/action.yml +++ b/flavors/documentation/action.yml @@ -7,7 +7,7 @@ outputs: description: "0 if no source file has been updated, 1 if source files has been updated" runs: using: "docker" - image: "docker://megalinter/megalinter-documentation:v5" + image: "docker://megalinter/megalinter-documentation:v6-alpha" args: - "-v" - "/var/run/docker.sock:/var/run/docker.sock:rw" diff --git a/flavors/dotnet/action.yml b/flavors/dotnet/action.yml index e09b2825d2d..c886d055c2c 100644 --- a/flavors/dotnet/action.yml +++ b/flavors/dotnet/action.yml @@ -7,7 +7,7 @@ outputs: description: "0 if no source file has been updated, 1 if source files has been updated" runs: using: "docker" - image: "docker://megalinter/megalinter-dotnet:v5" + image: "docker://megalinter/megalinter-dotnet:v6-alpha" args: - "-v" - "/var/run/docker.sock:/var/run/docker.sock:rw" diff --git a/flavors/go/action.yml b/flavors/go/action.yml index 7c73a43f705..7d14b6273ae 100644 --- a/flavors/go/action.yml +++ b/flavors/go/action.yml @@ -7,7 +7,7 @@ outputs: description: "0 if no source file has been updated, 1 if source files has been updated" runs: using: "docker" - image: "docker://megalinter/megalinter-go:v5" + image: "docker://megalinter/megalinter-go:v6-alpha" args: - "-v" - "/var/run/docker.sock:/var/run/docker.sock:rw" diff --git a/flavors/java/action.yml b/flavors/java/action.yml index 235bbdc2859..7326ea2e121 100644 --- a/flavors/java/action.yml +++ b/flavors/java/action.yml @@ -7,7 +7,7 @@ outputs: description: "0 if no source file has been updated, 1 if source files has been updated" runs: using: "docker" - image: "docker://megalinter/megalinter-java:v5" + image: "docker://megalinter/megalinter-java:v6-alpha" args: - "-v" - "/var/run/docker.sock:/var/run/docker.sock:rw" diff --git a/flavors/javascript/action.yml b/flavors/javascript/action.yml index 21f313d3a63..1cc525e0da9 100644 --- a/flavors/javascript/action.yml +++ b/flavors/javascript/action.yml @@ -7,7 +7,7 @@ outputs: description: "0 if no source file has been updated, 1 if source files has been updated" runs: using: "docker" - image: "docker://megalinter/megalinter-javascript:v5" + image: "docker://megalinter/megalinter-javascript:v6-alpha" args: - "-v" - "/var/run/docker.sock:/var/run/docker.sock:rw" diff --git a/flavors/php/action.yml b/flavors/php/action.yml index a22a8b34bb6..4b7a4970c46 100644 --- a/flavors/php/action.yml +++ b/flavors/php/action.yml @@ -7,7 +7,7 @@ outputs: description: "0 if no source file has been updated, 1 if source files has been updated" runs: using: "docker" - image: "docker://megalinter/megalinter-php:v5" + image: "docker://megalinter/megalinter-php:v6-alpha" args: - "-v" - "/var/run/docker.sock:/var/run/docker.sock:rw" diff --git a/flavors/python/action.yml b/flavors/python/action.yml index d5bfdfaf143..edae1e065c6 100644 --- a/flavors/python/action.yml +++ b/flavors/python/action.yml @@ -7,7 +7,7 @@ outputs: description: "0 if no source file has been updated, 1 if source files has been updated" runs: using: "docker" - image: "docker://megalinter/megalinter-python:v5" + image: "docker://megalinter/megalinter-python:v6-alpha" args: - "-v" - "/var/run/docker.sock:/var/run/docker.sock:rw" diff --git a/flavors/ruby/action.yml b/flavors/ruby/action.yml index f4cbc4ad6df..6620091e76d 100644 --- a/flavors/ruby/action.yml +++ b/flavors/ruby/action.yml @@ -7,7 +7,7 @@ outputs: description: "0 if no source file has been updated, 1 if source files has been updated" runs: using: "docker" - image: "docker://megalinter/megalinter-ruby:v5" + image: "docker://megalinter/megalinter-ruby:v6-alpha" args: - "-v" - "/var/run/docker.sock:/var/run/docker.sock:rw" diff --git a/flavors/rust/action.yml b/flavors/rust/action.yml index bbfc5f91a9e..e142529656b 100644 --- a/flavors/rust/action.yml +++ b/flavors/rust/action.yml @@ -7,7 +7,7 @@ outputs: description: "0 if no source file has been updated, 1 if source files has been updated" runs: using: "docker" - image: "docker://megalinter/megalinter-rust:v5" + image: "docker://megalinter/megalinter-rust:v6-alpha" args: - "-v" - "/var/run/docker.sock:/var/run/docker.sock:rw" diff --git a/flavors/salesforce/action.yml b/flavors/salesforce/action.yml index 961e8e91a21..061e8db4b65 100644 --- a/flavors/salesforce/action.yml +++ b/flavors/salesforce/action.yml @@ -7,7 +7,7 @@ outputs: description: "0 if no source file has been updated, 1 if source files has been updated" runs: using: "docker" - image: "docker://megalinter/megalinter-salesforce:v5" + image: "docker://megalinter/megalinter-salesforce:v6-alpha" args: - "-v" - "/var/run/docker.sock:/var/run/docker.sock:rw" diff --git a/flavors/scala/action.yml b/flavors/scala/action.yml index 7a85eeed9fa..2664045b5a3 100644 --- a/flavors/scala/action.yml +++ b/flavors/scala/action.yml @@ -7,7 +7,7 @@ outputs: description: "0 if no source file has been updated, 1 if source files has been updated" runs: using: "docker" - image: "docker://megalinter/megalinter-scala:v5" + image: "docker://megalinter/megalinter-scala:v6-alpha" args: - "-v" - "/var/run/docker.sock:/var/run/docker.sock:rw" diff --git a/flavors/security/action.yml b/flavors/security/action.yml index 4ef1d76b232..c085dc759f0 100644 --- a/flavors/security/action.yml +++ b/flavors/security/action.yml @@ -7,7 +7,7 @@ outputs: description: "0 if no source file has been updated, 1 if source files has been updated" runs: using: "docker" - image: "docker://megalinter/megalinter-security:v5" + image: "docker://megalinter/megalinter-security:v6-alpha" args: - "-v" - "/var/run/docker.sock:/var/run/docker.sock:rw" diff --git a/flavors/swift/action.yml b/flavors/swift/action.yml index 40a5113f630..475acdd1b45 100644 --- a/flavors/swift/action.yml +++ b/flavors/swift/action.yml @@ -7,7 +7,7 @@ outputs: description: "0 if no source file has been updated, 1 if source files has been updated" runs: using: "docker" - image: "docker://megalinter/megalinter-swift:v5" + image: "docker://megalinter/megalinter-swift:v6-alpha" args: - "-v" - "/var/run/docker.sock:/var/run/docker.sock:rw" diff --git a/flavors/terraform/action.yml b/flavors/terraform/action.yml index ec73254fa7a..4f36f89a1f6 100644 --- a/flavors/terraform/action.yml +++ b/flavors/terraform/action.yml @@ -7,7 +7,7 @@ outputs: description: "0 if no source file has been updated, 1 if source files has been updated" runs: using: "docker" - image: "docker://megalinter/megalinter-terraform:v5" + image: "docker://megalinter/megalinter-terraform:v6-alpha" args: - "-v" - "/var/run/docker.sock:/var/run/docker.sock:rw" diff --git a/megalinter/MegaLinter.py b/megalinter/MegaLinter.py index 76eaf67a8a8..aa0cb041e53 100644 --- a/megalinter/MegaLinter.py +++ b/megalinter/MegaLinter.py @@ -40,6 +40,7 @@ def __init__(self, params=None): self.workspace = self.get_workspace() config.init_config(self.workspace) # Initialize runtime config self.github_workspace = config.get("GITHUB_WORKSPACE", self.workspace) + self.megalinter_flavor = config.get("MEGALINTER_FLAVOR", "all") self.report_folder = config.get( "REPORT_OUTPUT_FOLDER", config.get("OUTPUT_FOLDER", self.github_workspace + os.path.sep + DEFAULT_REPORT_FOLDER_NAME), @@ -355,7 +356,17 @@ def load_linters(self): } # Build linters from descriptor files - all_linters = linter_factory.list_all_linters(linter_init_params) + # if flavor selected and no flavor suggestion, ignore linters that are not in current flavor) + if ( + self.megalinter_flavor != "all" + and config.get("FLAVOR_SUGGESTIONS", "true") != "true" + ): + all_linters = linter_factory.list_flavor_linters( + linter_init_params, self.megalinter_flavor + ) + else: + all_linters = linter_factory.list_all_linters(linter_init_params) + skipped_linters = [] for linter in all_linters: linter.master = self diff --git a/megalinter/constants.py b/megalinter/constants.py index be3a7d04006..70349db39ba 100644 --- a/megalinter/constants.py +++ b/megalinter/constants.py @@ -9,4 +9,6 @@ ML_DOCKER_IMAGE = f"{ML_DOCKER_OWNER}/{ML_DOCKER_NAME}" ML_DOCKER_IMAGE_LEGACY = "nvuillam/mega-linter" -DEFAULT_REPORT_FOLDER_NAME = 'megalinter-reports' \ No newline at end of file +DEFAULT_REPORT_FOLDER_NAME = "megalinter-reports" +DEFAULT_SARIF_REPORT_FILE_NAME = "megalinter-report.sarif" +DEFAULT_RELEASE = "v6-alpha" # TODOv6 : replace with v6 \ No newline at end of file diff --git a/megalinter/descriptors/repository.megalinter-descriptor.yml b/megalinter/descriptors/repository.megalinter-descriptor.yml index 761e8f2c3a4..e74bd90b6d8 100644 --- a/megalinter/descriptors/repository.megalinter-descriptor.yml +++ b/megalinter/descriptors/repository.megalinter-descriptor.yml @@ -121,6 +121,7 @@ linters: # TRIVY - linter_name: trivy + can_output_sarif: true descriptor_flavors: - all_flavors # Applicable to CI in any language project - ci_light @@ -129,6 +130,13 @@ linters: linter_repo: https://github.com/aquasecurity/trivy linter_banner_image_url: https://aquasecurity.github.io/trivy/v0.21.1/imgs/logo.png cli_lint_mode: project + cli_sarif_args: + - --format + - template + - --template + - "@contrib/sarif.tpl" + - -o + - "{{SARIF_OUTPUT_FILE}}" cli_lint_extra_args: - fs - --security-checks diff --git a/megalinter/flavor_factory.py b/megalinter/flavor_factory.py index 569d97df779..78735f1b922 100644 --- a/megalinter/flavor_factory.py +++ b/megalinter/flavor_factory.py @@ -32,6 +32,12 @@ def get_all_flavors(): return all_flavors +def list_flavor_linters(flavor_id): + all_flavors = get_all_flavors() + flavor_definition = all_flavors[flavor_id] + return flavor_definition["linters"] + + def list_megalinter_flavors(): flavors = { "all": {"label": "MegaLinter for any type of project"}, @@ -60,7 +66,7 @@ def list_megalinter_flavors(): def get_image_flavor(): - return os.environ.get("MEGALINTER_FLAVOR", "all") + return config.get("MEGALINTER_FLAVOR", "all") # Compare linters active for the current repo, and linters available in the current MegaLinter image flavor diff --git a/megalinter/linter_factory.py b/megalinter/linter_factory.py index 0505f09a65d..8217104a0d8 100644 --- a/megalinter/linter_factory.py +++ b/megalinter/linter_factory.py @@ -3,7 +3,7 @@ import os import yaml -from megalinter import Linter +from megalinter import Linter, flavor_factory # Returns directory where all .yml language descriptors are defined @@ -34,6 +34,19 @@ def list_all_linters(linters_init_params=None): return linters +# List flavor linters +def list_flavor_linters(linters_init_params=None, flavor_id="all"): + all_linters = list_all_linters(linters_init_params) + flavor_linter_ids = flavor_factory.list_flavor_linters(flavor_id) + linters = [] + for linter in all_linters: + if linter.name in flavor_linter_ids: + linters += [linter] + else: + del linter + return linters + + # List all descriptor files (one by language) def list_descriptor_files(): descriptors_dir = get_descriptor_dir() diff --git a/megalinter/reporters/ConsoleReporter.py b/megalinter/reporters/ConsoleReporter.py index b1f22a6ad9d..a7cc0c16748 100644 --- a/megalinter/reporters/ConsoleReporter.py +++ b/megalinter/reporters/ConsoleReporter.py @@ -9,7 +9,7 @@ import chalk as c import terminaltables from megalinter import Reporter, config -from megalinter.constants import ML_DOC_URL, ML_REPO, ML_REPO_URL +from megalinter.constants import DEFAULT_RELEASE, ML_DOC_URL, ML_REPO, ML_REPO_URL class ConsoleReporter(Reporter): @@ -129,7 +129,7 @@ def produce_report(self): f"[flavors] Use the following link to request the new flavor: {new_flavor_url}" ) else: - build_version = os.environ.get("BUILD_VERSION", "v5") + build_version = os.environ.get("BUILD_VERSION", DEFAULT_RELEASE) action_version = ( "v5" if "v5" in build_version diff --git a/megalinter/reporters/GithubCommentReporter.py b/megalinter/reporters/GithubCommentReporter.py index 3b2f6b3c330..fe74f8e112d 100644 --- a/megalinter/reporters/GithubCommentReporter.py +++ b/megalinter/reporters/GithubCommentReporter.py @@ -10,7 +10,7 @@ import github from megalinter import Reporter, config -from megalinter.constants import ML_DOC_URL, ML_REPO, ML_REPO_URL +from megalinter.constants import DEFAULT_RELEASE, ML_DOC_URL, ML_REPO, ML_REPO_URL from pytablewriter import MarkdownTableWriter mega_linter_version = config.get("BUILD_VERSION", "latest") @@ -169,7 +169,7 @@ def produce_report(self): " if you use a MegaLinter flavor:" + os.linesep ) for suggestion in self.master.flavor_suggestions: - build_version = os.environ.get("BUILD_VERSION", "v5") + build_version = os.environ.get("BUILD_VERSION", DEFAULT_RELEASE) action_version = ( "v5" if len(build_version) > 20 else build_version ) diff --git a/megalinter/reporters/SarifReporter.py b/megalinter/reporters/SarifReporter.py index 429c9248ee4..02dcf845f2d 100644 --- a/megalinter/reporters/SarifReporter.py +++ b/megalinter/reporters/SarifReporter.py @@ -3,10 +3,12 @@ Produce SARIF report """ import json +from json.decoder import JSONDecodeError import logging import os from megalinter import Reporter, config +from megalinter.constants import DEFAULT_SARIF_REPORT_FILE_NAME class SarifReporter(Reporter): @@ -36,15 +38,39 @@ def produce_report(self): if linter.sarif_output_file is not None and os.path.isfile( linter.sarif_output_file ): + # Read SARIF output file with open( linter.sarif_output_file, "r", encoding="utf-8" ) as linter_sarif_file: - linter_sarif_obj = json.load(linter_sarif_file) - sarif_obj["runs"] += linter_sarif_obj["runs"] + # parse sarif file + try: + linter_sarif_obj = json.load(linter_sarif_file) + except JSONDecodeError as e: + # JSON decoding error + logging.error( + f"[SARIF reporter] ERROR: Unable to decode {linter.name} " + f"SARIF file {linter.sarif_output_file}" + ) + logging.error(str(e)) + logging.debug( + f"SARIF File content:\n{linter_sarif_file.read()}" + ) + except Exception as e: # noqa: E722 + # Other error + logging.error( + f"[SARIF reporter] ERROR: Unknown error with {linter.name} " + f"SARIF file {linter.sarif_output_file}" + ) + logging.error(str(e)) + if linter_sarif_obj: + # fix sarif file + linter_sarif_obj = self.fix_sarif(linter_sarif_obj) + # append to global megalinter sarif run + sarif_obj["runs"] += linter_sarif_obj["runs"] result_json = json.dumps(sarif_obj, sort_keys=True, indent=4) # Write output file sarif_file_name = f"{self.report_folder}{os.path.sep}" + config.get( - "SARIF_REPORTER_FILE_NAME", "mega-linter-report.sarif" + "SARIF_REPORTER_FILE_NAME", DEFAULT_SARIF_REPORT_FILE_NAME ) with open(sarif_file_name, "w", encoding="utf-8") as sarif_file: sarif_file.write(result_json) @@ -67,3 +93,37 @@ def filter_fields(self, obj, fields_to_keep): except: # noqa: E722 pass return obj + + # Some SARIF linter output contain errors (like references to line 0) + # We must correct them so SARIF is valid + def fix_sarif(self, linter_sarif_obj): + # browse runs + if "runs" in linter_sarif_obj: + for id_run, run in enumerate(linter_sarif_obj["runs"]): + if "results" in run: + # browse run results + for id_result, result in enumerate(run["results"]): + if "locations" in result: + # browse result locations + for id_location, location in enumerate(result["locations"]): + if "physical_location" in location: + location[ + "physical_location" + ] = self.fix_sarif_physical_location( + location["physical_location"] + ) + result["locations"][id_location] = location + run["results"][id_result] = result + linter_sarif_obj["runs"][id_run] = run + return linter_sarif_obj + + # Replace startLine and endLine in region or contextRegion + def fix_sarif_physical_location(self, physical_location): + for location_key in physical_location.keys(): + location_item = physical_location[location_key] + if "startLine" in location_item and location_item["startLine"] == 0: + location_item["startLine"] = 1 + if "endLine" in location_item and location_item["endLine"] == 0: + location_item["endLine"] = 1 + physical_location[location_key] = location_item + return physical_location diff --git a/megalinter/tests/test_megalinter/helpers/utilstest.py b/megalinter/tests/test_megalinter/helpers/utilstest.py index c56ac4d6e6b..febe9a0334d 100644 --- a/megalinter/tests/test_megalinter/helpers/utilstest.py +++ b/megalinter/tests/test_megalinter/helpers/utilstest.py @@ -34,6 +34,11 @@ # Define env variables before any test case def linter_test_setup(params=None): for key in [ + "APPLY_FIXES", + "ENABLE", + "ENABLE_LINTERS", + "DISABLE", + "DISABLE_LINTERS", "MEGALINTER_CONFIG", "EXTENDS", "FILTER_REGEX_INCLUDE", @@ -41,6 +46,9 @@ def linter_test_setup(params=None): "IGNORE_GITIGNORED_FILES", "IGNORE_GENERATED_FILES", "SHOW_ELAPSED_TIME", + "UPDATED_SOURCES_REPORTER" + "MEGALINTER_FLAVOR", + "FLAVOR_SUGGESTIONS", ]: if key in os.environ: del os.environ[key] @@ -76,6 +84,7 @@ def linter_test_setup(params=None): config.set_value("OUTPUT_FORMAT", "text") config.set_value("OUTPUT_DETAIL", "detailed") config.set_value("PLUGINS", "") + config.set_value("GITHUB_STATUS_REPORTER", "false") config.set_value("IGNORE_GITIGNORED_FILES", "true") config.set_value("VALIDATE_ALL_CODEBASE", "true") # Root path of files to lint @@ -140,6 +149,7 @@ def test_linter_success(linter, test_self): "DEFAULT_WORKSPACE": workspace, "FILTER_REGEX_INCLUDE": r"(good)", "TEXT_REPORTER": "true", + "UPDATED_SOURCES_REPORTER": "false", "REPORT_OUTPUT_FOLDER": tmp_report_folder, "LOG_LEVEL": "DEBUG", "ENABLE_LINTERS": linter.name, @@ -200,6 +210,7 @@ def test_linter_failure(linter, test_self): "FILTER_REGEX_INCLUDE": r"(bad)", "OUTPUT_FORMAT": "text", "OUTPUT_DETAIL": "detailed", + "UPDATED_SOURCES_REPORTER": "false", "REPORT_OUTPUT_FOLDER": tmp_report_folder, "LOG_LEVEL": "DEBUG", "ENABLE_LINTERS": linter.name, @@ -492,12 +503,12 @@ def test_linter_report_sarif(linter, test_self): test_self.assertTrue( len(mega_linter.linters) > 0, "Linters have been created and run" ) - # Check TAP file has been produced - tmp_tap_file_name = ( + # Check SARIF file has been produced + tmp_sarif_file_name = ( f"{tmp_report_folder}{os.path.sep}sarif{os.path.sep}{linter.name}.sarif" ) test_self.assertTrue( - os.path.isfile(tmp_tap_file_name), f"SARIF report not found {tmp_tap_file_name}" + os.path.isfile(tmp_sarif_file_name), f"SARIF report not found {tmp_sarif_file_name}" ) diff --git a/megalinter/tests/test_megalinter/mega_linter_1_test.py b/megalinter/tests/test_megalinter/mega_linter_1_test.py index ea09dc091f1..451eb75b95c 100644 --- a/megalinter/tests/test_megalinter/mega_linter_1_test.py +++ b/megalinter/tests/test_megalinter/mega_linter_1_test.py @@ -361,9 +361,14 @@ def test_override_cli_executable(self): "PHP_BUILTIN should have been processed with cli_executable = /usr/bin/php8", ) - def test_print_all_files_false(self): + def test_print_all_files_false_and_no_flavor_suggestion(self): mega_linter, output = utilstest.call_mega_linter( - {"ENABLE_LINTERS": "JAVASCRIPT_ES", "PRINT_ALL_FILES": "false"} + { + "ENABLE_LINTERS": "JAVASCRIPT_ES", + "PRINT_ALL_FILES": "false", + "MEGALINTER_FLAVOR": "javascript", + "FLAVOR_SUGGESTIONS": "false", + } ) self.assertTrue( len(mega_linter.linters) > 0, "Linters have been created and run" diff --git a/megalinter/tests/test_megalinter/mega_linter_3_sarif_test.py b/megalinter/tests/test_megalinter/mega_linter_3_sarif_test.py index 38f049dc2a5..a584b0dc452 100644 --- a/megalinter/tests/test_megalinter/mega_linter_3_sarif_test.py +++ b/megalinter/tests/test_megalinter/mega_linter_3_sarif_test.py @@ -6,6 +6,7 @@ import os import unittest +from megalinter.constants import DEFAULT_SARIF_REPORT_FILE_NAME from megalinter.tests.test_megalinter.helpers import utilstest @@ -31,7 +32,7 @@ def test_sarif_output(self): len(mega_linter.linters) > 0, "Linters have been created and run" ) expected_output_file = ( - mega_linter.report_folder + os.path.sep + "mega-linter-report.sarif" + mega_linter.report_folder + os.path.sep + DEFAULT_SARIF_REPORT_FILE_NAME ) self.assertTrue( os.path.isfile(expected_output_file),