Skip to content

Commit

Permalink
add feature coverage
Browse files Browse the repository at this point in the history
  • Loading branch information
mar3hc committed Jun 23, 2024
1 parent 6613eae commit 48fd016
Show file tree
Hide file tree
Showing 6 changed files with 394 additions and 0 deletions.
33 changes: 33 additions & 0 deletions atest/coverage/config/.coveragerc
Original file line number Diff line number Diff line change
@@ -0,0 +1,33 @@
[run]
branch = True

source_pkgs = JsonPreprocessor

data_file = ./atest/coverage/.coverage

[report]
# Regexes for lines to exclude from consideration
exclude_lines =
# Don't complain about missing debug-only code:
def __repr__
if self\.debug

# Don't complain if tests don't hit defensive assertion code:
raise AssertionError
raise NotImplementedError

# Don't complain if non-runnable code isn't run:
if 0:
if __name__ == .__main__.:

# Don't complain about abstract methods, they aren't run:
@(abc\.)?abstractmethod

omit =
*__init__*
version.py

ignore_errors = True

[html]
directory = ./atest/coverage/coverage_report
22 changes: 22 additions & 0 deletions atest/coverage/config/coverage_config.json
Original file line number Diff line number Diff line change
@@ -0,0 +1,22 @@
{
"COVERAGE": [
{
"STATE": "run",
"COMMANDLINE": "-m pytest ./atest",
"CURRENT_WORKING_DIR": "",
"CONFIG": "./atest/coverage/config/.coveragerc"
},
{
"STATE": "report",
"COMMANDLINE": "",
"CURRENT_WORKING_DIR": "",
"CONFIG": "./atest/coverage/config/.coveragerc"
},
{
"STATE": "html",
"COMMANDLINE": "",
"CURRENT_WORKING_DIR": "",
"CONFIG": "./atest/coverage/config/.coveragerc"
}
]
}
142 changes: 142 additions & 0 deletions atest/coverage/coverage.py
Original file line number Diff line number Diff line change
@@ -0,0 +1,142 @@
# **************************************************************************************************************
#
# Copyright 2020-2024 Robert Bosch GmbH
#
# Licensed 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.
#
# **************************************************************************************************************
#
# Mai Minh Tri
#
# coverage.py
#
# --------------------------------------------------------------------------------------------------------------
#
# 06.23.2022
#
# --------------------------------------------------------------------------------------------------------------

import os, sys, platform, shlex, subprocess, shutil, argparse, json

import colorama as col

from PythonExtensionsCollection.String.CString import CString
from PythonExtensionsCollection.Folder.CFolder import CFolder

col.init(autoreset=True)

COLBR = col.Style.BRIGHT + col.Fore.RED
COLBY = col.Style.BRIGHT + col.Fore.YELLOW
COLBG = col.Style.BRIGHT + col.Fore.GREEN

SUCCESS = 0
ERROR = 1

# --------------------------------------------------------------------------------------------------------------

def printerror(sMsg):
sys.stderr.write(COLBR + f"Error: {sMsg}!\n")

def printexception(sMsg):
sys.stderr.write(COLBR + f"Exception: {sMsg}!\n")

# --------------------------------------------------------------------------------------------------------------

# -- some informations about the environment of this script

sThisScript = sys.argv[0]
sThisScript = CString.NormalizePath(sThisScript)
sThisScriptPath = os.path.dirname(sThisScript)
sThisScriptName = os.path.basename(sThisScript)
sComponentPath = CString.NormalizePath(sys.argv[1])

sOSName = os.name
sPlatformSystem = platform.system()
sPythonPath = CString.NormalizePath(os.path.dirname(sys.executable))
sPython = CString.NormalizePath(sys.executable)
sPythonVersion = sys.version

sFilter = None
if sPlatformSystem == "Windows":
sFilter = "not _Linux_"
# sComponentPath = os.path.normpath(sComponentPath)
elif sPlatformSystem == "Linux":
sFilter = "not _Windows_"
else:
bSuccess = False
sResult = f"Operating system {sPlatformSystem} ({sOSName}) not supported"
printerror(CString.FormatResult(sThisScriptName, bSuccess, sResult))
sys.exit(ERROR)

print()
print(f"{sThisScriptName} is running under {sPlatformSystem} ({sOSName})")
print()

# load static configuration values (name of json file is fix)
sCoverageJsonFile = CString.NormalizePath(f"{sThisScriptPath}/config/coverage_config.json")
hCoverageJsonFile = open(sCoverageJsonFile, encoding="utf-8")
oCoverageConfig = json.load(hCoverageJsonFile)
hCoverageJsonFile.close()

listCoverage = oCoverageConfig.get('COVERAGE')
for coverage in listCoverage:
sState = coverage['STATE']
sCommandline = coverage['COMMANDLINE']
sCWD = coverage['CURRENT_WORKING_DIR']
sConfig = coverage['CONFIG']

# -- prepare the command line for run the test coverage
listCmdLineParts = []
listCmdLineParts.append(f"\"{sPython}\"")
listCmdLineParts.append(f"-m coverage {sState}")
listCmdLineParts.append(f"--rcfile=\"{sConfig}\"")
listCmdLineParts.append(f"{sCommandline}")

sCmdLine = " ".join(listCmdLineParts)
del listCmdLineParts

# -- execute the test coverage
print(f"Now executing command line:\n{sCmdLine}")
print()

listCmdLineParts = shlex.split(sCmdLine)

nReturn = ERROR
try:
nReturn = subprocess.call(listCmdLineParts, cwd=CString.NormalizePath(f"\"{sComponentPath}/{sCWD}\""))
print()
print(f"[{sThisScriptName}] : Subprocess PYTEST returned {nReturn}")
except Exception as ex:
print()
printexception(str(ex))
print()
sys.exit(ERROR)
print()

if nReturn == SUCCESS:
print()
print(COLBG + f"{sThisScriptName} done")
else:
printerror(f"[{sThisScriptName}] : Subprocess PYTEST has not returned expected value {SUCCESS}")
nReturn = -nReturn

print()
# nReturn:
# > 0 : internal error of this script
# < 0 : return value (!= 0) from subprocess
# == 0 : no internal error of this script and no error from subprocess

sys.exit(nReturn)

# --------------------------------------------------------------------------------------------------------------

33 changes: 33 additions & 0 deletions test/pytest/coverage/config/.coveragerc
Original file line number Diff line number Diff line change
@@ -0,0 +1,33 @@
[run]
branch = True

source_pkgs = JsonPreprocessor

data_file = ./pytest/coverage/.coverage

[report]
# Regexes for lines to exclude from consideration
exclude_lines =
# Don't complain about missing debug-only code:
def __repr__
if self\.debug

# Don't complain if tests don't hit defensive assertion code:
raise AssertionError
raise NotImplementedError

# Don't complain if non-runnable code isn't run:
if 0:
if __name__ == .__main__.:

# Don't complain about abstract methods, they aren't run:
@(abc\.)?abstractmethod

omit =
*__init__*
version.py

ignore_errors = True

[html]
directory = ./pytest/coverage/coverage_report
22 changes: 22 additions & 0 deletions test/pytest/coverage/config/coverage_config.json
Original file line number Diff line number Diff line change
@@ -0,0 +1,22 @@
{
"COVERAGE": [
{
"STATE": "run",
"COMMANDLINE": "./component_test.py",
"CURRENT_WORKING_DIR": "test",
"CONFIG": "./pytest/coverage/config/.coveragerc"
},
{
"STATE": "report",
"COMMANDLINE": "",
"CURRENT_WORKING_DIR": "test",
"CONFIG": "./pytest/coverage/config/.coveragerc"
},
{
"STATE": "html",
"COMMANDLINE": "",
"CURRENT_WORKING_DIR": "test",
"CONFIG": "./pytest/coverage/config/.coveragerc"
}
]
}
142 changes: 142 additions & 0 deletions test/pytest/coverage/coverage.py
Original file line number Diff line number Diff line change
@@ -0,0 +1,142 @@
# **************************************************************************************************************
#
# Copyright 2020-2024 Robert Bosch GmbH
#
# Licensed 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.
#
# **************************************************************************************************************
#
# Mai Minh Tri
#
# coverage.py
#
# --------------------------------------------------------------------------------------------------------------
#
# 06.23.2022
#
# --------------------------------------------------------------------------------------------------------------

import os, sys, platform, shlex, subprocess, shutil, argparse, json

import colorama as col

from PythonExtensionsCollection.String.CString import CString
from PythonExtensionsCollection.Folder.CFolder import CFolder

col.init(autoreset=True)

COLBR = col.Style.BRIGHT + col.Fore.RED
COLBY = col.Style.BRIGHT + col.Fore.YELLOW
COLBG = col.Style.BRIGHT + col.Fore.GREEN

SUCCESS = 0
ERROR = 1

# --------------------------------------------------------------------------------------------------------------

def printerror(sMsg):
sys.stderr.write(COLBR + f"Error: {sMsg}!\n")

def printexception(sMsg):
sys.stderr.write(COLBR + f"Exception: {sMsg}!\n")

# --------------------------------------------------------------------------------------------------------------

# -- some informations about the environment of this script

sThisScript = sys.argv[0]
sThisScript = CString.NormalizePath(sThisScript)
sThisScriptPath = os.path.dirname(sThisScript)
sThisScriptName = os.path.basename(sThisScript)
sComponentPath = CString.NormalizePath(sys.argv[1])

sOSName = os.name
sPlatformSystem = platform.system()
sPythonPath = CString.NormalizePath(os.path.dirname(sys.executable))
sPython = CString.NormalizePath(sys.executable)
sPythonVersion = sys.version

sFilter = None
if sPlatformSystem == "Windows":
sFilter = "not _Linux_"
# sComponentPath = os.path.normpath(sComponentPath)
elif sPlatformSystem == "Linux":
sFilter = "not _Windows_"
else:
bSuccess = False
sResult = f"Operating system {sPlatformSystem} ({sOSName}) not supported"
printerror(CString.FormatResult(sThisScriptName, bSuccess, sResult))
sys.exit(ERROR)

print()
print(f"{sThisScriptName} is running under {sPlatformSystem} ({sOSName})")
print()

# load static configuration values (name of json file is fix)
sCoverageJsonFile = CString.NormalizePath(f"{sThisScriptPath}/config/coverage_config.json")
hCoverageJsonFile = open(sCoverageJsonFile, encoding="utf-8")
oCoverageConfig = json.load(hCoverageJsonFile)
hCoverageJsonFile.close()

listCoverage = oCoverageConfig.get('COVERAGE')
for coverage in listCoverage:
sState = coverage['STATE']
sCommandline = coverage['COMMANDLINE']
sCWD = coverage['CURRENT_WORKING_DIR']
sConfig = coverage['CONFIG']

# -- prepare the command line for run the test coverage
listCmdLineParts = []
listCmdLineParts.append(f"\"{sPython}\"")
listCmdLineParts.append(f"-m coverage {sState}")
listCmdLineParts.append(f"--rcfile=\"{sConfig}\"")
listCmdLineParts.append(f"{sCommandline}")

sCmdLine = " ".join(listCmdLineParts)
del listCmdLineParts

# -- execute the test coverage
print(f"Now executing command line:\n{sCmdLine}")
print()

listCmdLineParts = shlex.split(sCmdLine)

nReturn = ERROR
try:
nReturn = subprocess.call(listCmdLineParts, cwd=CString.NormalizePath(f"\"{sComponentPath}/{sCWD}\""))
print()
print(f"[{sThisScriptName}] : Subprocess PYTEST returned {nReturn}")
except Exception as ex:
print()
printexception(str(ex))
print()
sys.exit(ERROR)
print()

if nReturn == SUCCESS:
print()
print(COLBG + f"{sThisScriptName} done")
else:
printerror(f"[{sThisScriptName}] : Subprocess PYTEST has not returned expected value {SUCCESS}")
nReturn = -nReturn

print()
# nReturn:
# > 0 : internal error of this script
# < 0 : return value (!= 0) from subprocess
# == 0 : no internal error of this script and no error from subprocess

sys.exit(nReturn)

# --------------------------------------------------------------------------------------------------------------

0 comments on commit 48fd016

Please sign in to comment.