Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Add hadolint #35

Merged
merged 1 commit into from
Jun 20, 2024
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
8 changes: 8 additions & 0 deletions Dockerfile
Original file line number Diff line number Diff line change
Expand Up @@ -30,6 +30,11 @@ RUN curl -ksSLO https://github.com/danmar/cppcheck/archive/refs/tags/2.14.1.tar.
CXXFLAGS="-O2 -DNDEBUG -Wall -Wno-sign-compare -Wno-unused-function -Wno-deprecated-declarations" \
&& rm -rf cppcheck-2.14.1 2.14.1.tar.gz

# Hadolint
RUN curl -ksSLO https://github.com/hadolint/hadolint/releases/download/v2.12.0/hadolint-Linux-x86_64 \
&& mv hadolint-Linux-x86_64 /usr/bin/hadolint \
&& chmod +x /usr/bin/hadolint

################################################################################

# Final image based on the official sonar-scanner image
Expand Down Expand Up @@ -82,6 +87,9 @@ COPY --from=builder /usr/bin/cppcheck-htmlreport /usr/bin
# Add CNES pylintrc A_B, C, D
COPY pylintrc.d/ /opt/python/

# Add hadolint from builder stage
COPY --from=builder /usr/bin/hadolint /usr/bin

# Install tools
RUN apt-get update \
&& mkdir -p /usr/share/man/man1 \
Expand Down
14 changes: 8 additions & 6 deletions README.md
Original file line number Diff line number Diff line change
@@ -1,7 +1,6 @@
# CNES sonar-scanner-catlab image

![](https://github.com/cnescatlab/sonar-scanner/workflows/CI/badge.svg)
![](https://github.com/cnescatlab/sonar-scanner/workflows/CD/badge.svg)
![CI badge](https://github.com/cnescatlab/sonar-scanner/workflows/CI/badge.svg) ![CD badge](https://github.com/cnescatlab/sonar-scanner/workflows/CD/badge.svg)

> Docker environment containing open source code analysis tools configured by CNES and dedicated to Continuous Integration.

Expand All @@ -22,7 +21,7 @@ Additional features are:
- Embedded tools
- see the [list](#analysis-tools-included)
- Configuration files
- [pylintrc](#how-to-use-embedded-CNES-pylintrc)
- [pylintrc](#how-to-use-embedded-cnes-pylintrc)

_This image is made to be used in conjunction with a pre-configured SonarQube server image that embeds all necessary plugins and configuration: [cnescatlab/sonarqube](https://github.com/cnescatlab/sonarqube-catlab). It is, however, not mandatory to use it._

Expand All @@ -31,6 +30,7 @@ _This image is made to be used in conjunction with a pre-configured SonarQube se
1. Write a `sonar-project.properties` at the root of your project
- For information on what to write in it, see the [official SonarQube documentation](https://docs.sonarqube.org/sonarqube/9.9/)
2. Execute the sonar-scanner on the project by running this image from the root of the project

```sh
$ docker run \
--rm \
Expand All @@ -39,8 +39,10 @@ _This image is made to be used in conjunction with a pre-configured SonarQube se
-v "$(pwd):/usr/src" \
lequal/sonar-scanner
```

This docker command is equivalent to `sonar-scanner -Dsonar.host.url="url of your SonarQube instance"`.
- If the SonarQube server is running in a container on the same computer, you will need to connect both containers (server and client) to the same bridge so that they can communicate. To do so:

```sh
$ docker network create -d bridge sonarbridge
$ docker network connect sonarbridge "name of your sonarqube container"
Expand Down Expand Up @@ -235,12 +237,12 @@ sonar-scanning:

| Tool | Version | Default report file |
| ------------------------------------------------------------------------------ | ---------- | ------------------- |
| [sonar-scanner](https://docs.sonarqube.org/latest/analysis/scan/sonarscanner/) | 5.0.1.3006 | |
| [sonar-scanner](https://docs.sonarqube.org/latest/analysis/scan/sonarscanner/) | 6.0.0.4432 | |
| [ShellCheck](https://github.com/koalaman/shellcheck) | 0.8.0 | |
| [pylint](http://pylint.pycqa.org/en/latest/user_guide/index.html) | 3.1.0 | pylint-report.txt |
| [CNES pylint extension](https://github.com/cnescatlab/cnes-pylint-extension) | 7.0.0 | |
| [CppCheck](https://github.com/danmar/cppcheck) | 2.14.0 | cppcheck-report.xml |
| [Infer](https://fbinfer.com/) | 1.1.0 | |
| [CppCheck](https://github.com/danmar/cppcheck) | 2.14.1 | cppcheck-report.xml |
| [Hadolint](https://hadolint.github.io/hadolint/) | 2.12.0 | |

## Developer's guide

Expand Down
2 changes: 1 addition & 1 deletion conf/sonar-scanner.properties
Original file line number Diff line number Diff line change
Expand Up @@ -7,6 +7,6 @@
#----- Default source code encoding
#sonar.sourceEncoding=UTF-8

#----- Default report path for C/C++ analysis tools
#----- Default report path for external analysis tools
sonar.cxx.cppcheck.reportPaths=cppcheck-report.xml
sonar.python.pylint.reportPaths=pylint-report.txt
132 changes: 132 additions & 0 deletions tests/docker/hadolint-report.json
Original file line number Diff line number Diff line change
@@ -0,0 +1,132 @@
{
"issues": [
{
"engineId": "Hadolint",
"primaryLocation": {
"filePath": "src/Dockerfile",
"message": "Always tag the version of an image explicitly",
"textRange": {
"endColumn": 1,
"endLine": 4,
"startColumn": 0,
"startLine": 4
}
},
"ruleId": "DL3006",
"severity": "MAJOR",
"type": "CODE_SMELL"
},
{
"engineId": "Hadolint",
"primaryLocation": {
"filePath": "src/Dockerfile",
"message": "Avoid additional packages by specifying `--no-install-recommends`",
"textRange": {
"endColumn": 1,
"endLine": 6,
"startColumn": 0,
"startLine": 6
}
},
"ruleId": "DL3015",
"severity": "MINOR",
"type": "CODE_SMELL"
},
{
"engineId": "Hadolint",
"primaryLocation": {
"filePath": "src/Dockerfile",
"message": "Delete the apt-get lists after installing something",
"textRange": {
"endColumn": 1,
"endLine": 6,
"startColumn": 0,
"startLine": 6
}
},
"ruleId": "DL3009",
"severity": "MINOR",
"type": "CODE_SMELL"
},
{
"engineId": "Hadolint",
"primaryLocation": {
"filePath": "src/Dockerfile",
"message": "node_verion is referenced but not assigned (did you mean 'node_version'?).",
"textRange": {
"endColumn": 1,
"endLine": 6,
"startColumn": 0,
"startLine": 6
}
},
"ruleId": "SC2154",
"severity": "MAJOR",
"type": "CODE_SMELL"
},
{
"engineId": "Hadolint",
"primaryLocation": {
"filePath": "src/Dockerfile",
"message": "`COPY` to a relative destination without `WORKDIR` set.",
"textRange": {
"endColumn": 1,
"endLine": 9,
"startColumn": 0,
"startLine": 9
}
},
"ruleId": "DL3045",
"severity": "MAJOR",
"type": "CODE_SMELL"
},
{
"engineId": "Hadolint",
"primaryLocation": {
"filePath": "src/Dockerfile",
"message": "Use WORKDIR to switch to a directory",
"textRange": {
"endColumn": 1,
"endLine": 11,
"startColumn": 0,
"startLine": 11
}
},
"ruleId": "DL3003",
"severity": "MAJOR",
"type": "CODE_SMELL"
},
{
"engineId": "Hadolint",
"primaryLocation": {
"filePath": "src/Dockerfile",
"message": "Pin versions in npm. Instead of `npm install <package>` use `npm install <package>@<version>`",
"textRange": {
"endColumn": 1,
"endLine": 11,
"startColumn": 0,
"startLine": 11
}
},
"ruleId": "DL3016",
"severity": "MAJOR",
"type": "CODE_SMELL"
},
{
"engineId": "Hadolint",
"primaryLocation": {
"filePath": "src/Dockerfile",
"message": "Valid UNIX ports range from 0 to 65535",
"textRange": {
"endColumn": 1,
"endLine": 14,
"startColumn": 0,
"startLine": 14
}
},
"ruleId": "DL3011",
"severity": "CRITICAL",
"type": "BUG"
}
]
}
1 change: 1 addition & 0 deletions tests/docker/reference-hadolint-results.json
Original file line number Diff line number Diff line change
@@ -0,0 +1 @@
{"issues":[{"engineId":"Hadolint","primaryLocation":{"filePath":"tests/docker/src/Dockerfile","message":"Always tag the version of an image explicitly","textRange":{"endColumn":1,"endLine":4,"startColumn":0,"startLine":4}},"ruleId":"DL3006","severity":"MAJOR","type":"CODE_SMELL"},{"engineId":"Hadolint","primaryLocation":{"filePath":"tests/docker/src/Dockerfile","message":"Avoid additional packages by specifying `--no-install-recommends`","textRange":{"endColumn":1,"endLine":6,"startColumn":0,"startLine":6}},"ruleId":"DL3015","severity":"MINOR","type":"CODE_SMELL"},{"engineId":"Hadolint","primaryLocation":{"filePath":"tests/docker/src/Dockerfile","message":"Delete the apt-get lists after installing something","textRange":{"endColumn":1,"endLine":6,"startColumn":0,"startLine":6}},"ruleId":"DL3009","severity":"MINOR","type":"CODE_SMELL"},{"engineId":"Hadolint","primaryLocation":{"filePath":"tests/docker/src/Dockerfile","message":"node_verion is referenced but not assigned (did you mean 'node_version'?).","textRange":{"endColumn":1,"endLine":6,"startColumn":0,"startLine":6}},"ruleId":"SC2154","severity":"MAJOR","type":"CODE_SMELL"},{"engineId":"Hadolint","primaryLocation":{"filePath":"tests/docker/src/Dockerfile","message":"`COPY` to a relative destination without `WORKDIR` set.","textRange":{"endColumn":1,"endLine":9,"startColumn":0,"startLine":9}},"ruleId":"DL3045","severity":"MAJOR","type":"CODE_SMELL"},{"engineId":"Hadolint","primaryLocation":{"filePath":"tests/docker/src/Dockerfile","message":"Use WORKDIR to switch to a directory","textRange":{"endColumn":1,"endLine":11,"startColumn":0,"startLine":11}},"ruleId":"DL3003","severity":"MAJOR","type":"CODE_SMELL"},{"engineId":"Hadolint","primaryLocation":{"filePath":"tests/docker/src/Dockerfile","message":"Pin versions in npm. Instead of `npm install <package>` use `npm install <package>@<version>`","textRange":{"endColumn":1,"endLine":11,"startColumn":0,"startLine":11}},"ruleId":"DL3016","severity":"MAJOR","type":"CODE_SMELL"},{"engineId":"Hadolint","primaryLocation":{"filePath":"tests/docker/src/Dockerfile","message":"Valid UNIX ports range from 0 to 65535","textRange":{"endColumn":1,"endLine":14,"startColumn":0,"startLine":14}},"ruleId":"DL3011","severity":"CRITICAL","type":"BUG"}]}
6 changes: 6 additions & 0 deletions tests/docker/sonar-project.properties
Original file line number Diff line number Diff line change
@@ -0,0 +1,6 @@
#SonarQube Properties
sonar.projectKey=hadolint-dummy-project
sonar.projectName=Hadolint Dummy Project
sonar.projectVersion=1.0
sonar.sources=src
sonar.externalIssuesReportPaths=hadolint-report.json
15 changes: 15 additions & 0 deletions tests/docker/src/Dockerfile
Original file line number Diff line number Diff line change
@@ -0,0 +1,15 @@
# Example from Hadlint website
# https://hadolint.github.io/hadolint/

FROM debian

RUN export node_version="0.10" \
&& apt-get update && apt-get -y install nodejs="$node_verion"

COPY package.json usr/src/app

RUN cd /usr/src/app \
&& npm install node-static

EXPOSE 80000
CMD ["npm", "start"]
19 changes: 19 additions & 0 deletions tests/test_cnes_sonar_scanner.py
Original file line number Diff line number Diff line change
Expand Up @@ -454,6 +454,14 @@ def test_tool_shellcheck(self):
cmd = "bash -c 'shellcheck -s sh -f checkstyle tests/shell/src/script.sh || true'"
self.analysis_tool("shellcheck", cmd, "tests/shell/reference-shellcheck-results.xml", "tests/shell/tmp-shellcheck-results.xml")

def test_tool_hadolint(self):
"""
As a user of this image, I want to run hadolint from within a container
so that it produces a report.
"""
cmd = "hadolint -f sonarqube --no-fail tests/docker/src/Dockerfile"
self.analysis_tool("hadolint", cmd, "tests/docker/reference-hadolint-results.json", "tests/docker/tmp-hadolint-results.json")

# Test importation of analysis results
def test_import_cppcheck_results(self):
"""
Expand All @@ -476,3 +484,14 @@ def test_import_pylint_results(self):
expected_import = "INFO Sensor Import of Pylint issues [python]"
self.import_analysis_results("Pylint Dummy Project", "pylint-dummy-project",
"Sonar way", "py", "tests/python", "src", rule_violated, expected_sensor, expected_import)

def test_import_hadolint_results(self):
"""
As a user of this image, I want to be able to import the results
of a hadolint analysis to SonarQube.
"""
rule_violated = "external_Hadolint:DL3003"
expected_sensor = "INFO Sensor Import external issues report"
expected_import = "INFO Sensor Import external issues report (done)"
self.import_analysis_results("Hadolint Dummy Project", "hadolint-dummy-project",
"Sonar way", "docker", "tests/docker", "src", rule_violated, expected_sensor, expected_import)