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

refactor: Fix CodeQL errors and warnings #252

Merged
merged 39 commits into from
Feb 20, 2024
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
Show all changes
39 commits
Select commit Hold shift + click to select a range
ca27d42
test(unit/actor): Fix CodeQL py/side-effect-in-assert error
gfieni Feb 15, 2024
3b4e6be
refactor(cli): Fix CodeQL py/unreachable-statement warning
gfieni Feb 15, 2024
69011a8
refactor(database/infuxdb2): Fix CodeQL py/commented-out-code warning
gfieni Feb 15, 2024
489afe3
test(integration/databse/csv): Fix CodeQL py/commented-out-code warning
gfieni Feb 15, 2024
80089ab
refactor(cli): Fix CodeQL py/file-not-closed warning
gfieni Feb 15, 2024
e1d75af
test(utils/report): Fix CodeQL py/file-not-closed warnings
gfieni Feb 15, 2024
8f7b834
test(unit/puller): Fix DeprecationWarning about datetime.utcfromtimes…
gfieni Feb 15, 2024
3f0721b
test(unit/utils): Fix DeprecationWarning about no current event loop
gfieni Feb 15, 2024
ef40d16
test(unit/utils): Fix DeprecationWarning about no current event loop
gfieni Feb 15, 2024
a5b11ce
test(unit/cli): Fix CodeQL py/unused-local-variable warnings
gfieni Feb 16, 2024
986ff34
test(unit/actor): Fix CodeQL py/unused-import warning
gfieni Feb 16, 2024
46a2a3a
test(unit/utils): Fix CodeQL py/unused-import warning
gfieni Feb 16, 2024
cffd84f
test(unit/dispatch_rule): Fix CodeQL py/unused-import warning
gfieni Feb 16, 2024
9022060
test(integration): Fix CodeQL py/unused-import warnings
gfieni Feb 16, 2024
6820e8a
test(unit/utils): Fix CodeQL py/unused-import warning
gfieni Feb 16, 2024
1133461
test(acceptation): Fix CodeQL py/unused-import warning
gfieni Feb 16, 2024
eb55dca
test(acceptation): Add __init__.py file in directories
gfieni Feb 16, 2024
13353ec
test(acceptation): Remove fixtures imports
gfieni Feb 16, 2024
8810f3b
test: Remove broken integration/acceptation tests
gfieni Feb 16, 2024
a23a4f4
feat(report): Override __eq__ method of all report types
gfieni Feb 16, 2024
0d9520c
feat(dispatch_rule): Add fields attribute to DispatchRule constructor
gfieni Feb 16, 2024
cd1eaac
test(unit/dispatch_rule): Fix CodeQL py/overwritten-inherited-attribu…
gfieni Feb 16, 2024
232b4a3
refactor(dispatch_rule): Set DispatchRule fields attribute in super c…
gfieni Feb 16, 2024
da12a68
test(unit/dispatcher): Fix pylint `unused-argument` and `no-self-use`…
gfieni Feb 16, 2024
eaaece2
test(unit/dispatcher): Fix Pylint and CodeQL argument-differ errors
gfieni Feb 16, 2024
26c20e6
refactor(cli/generator): Fix CodeQL py/init-calls-subclass warning
gfieni Feb 19, 2024
bd18f0d
refactor(db/csv): Rework `save` Report to CSV method
gfieni Feb 19, 2024
2a632af
test(actor): Fix CodeQL py/empty-except warning
gfieni Feb 19, 2024
6afb7de
refactor(processor/libvirt): Add logging when the domain name is not …
gfieni Feb 19, 2024
79ff665
refactor(pusher/simple): Fix CodeQL py/overwritten-inherited-attribut…
gfieni Feb 20, 2024
5524c54
test(unit/dispatcher): Fix CodeQL py/non-iterable-in-for-loop error
gfieni Feb 20, 2024
e45dd71
refactor(database): Fix CodeQL py/overwritten-inherited-attribute war…
gfieni Feb 20, 2024
3f9f71b
test(unit/utils): Fix CodeQL py/overwritten-inherited-attribute warning
gfieni Feb 20, 2024
1b11297
refactor(cli): Fix CodeQL py/overwritten-inherited-attribute warnings
gfieni Feb 20, 2024
17d8941
refactor(db/virtiofs): Fix CodeQL py/file-not-closed warning
gfieni Feb 20, 2024
b71d17f
refactor(db/file): Fix CodeQL py/file-not-closed warning
gfieni Feb 20, 2024
59fd09f
test(unit/cli): Fix SonarQube python:S5915 error
gfieni Feb 20, 2024
122c4bb
test(unit/puller): Fix PyLint no-name-in-module error for timezone
gfieni Feb 20, 2024
389789c
fix(cli): Add missing `add_argument` method to RootConfigParsingManager
gfieni Feb 20, 2024
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
7 changes: 3 additions & 4 deletions src/powerapi/cli/config_parser.py
Original file line number Diff line number Diff line change
Expand Up @@ -496,9 +496,9 @@ def parse_config_dict(self, file_name: str) -> dict:
Return a configuration dict that has all the arguments' names in the long form.
If an argument does not exist, a UnknownArgException is raised
"""
config_file = open(file_name, 'r')
conf = json.load(config_file)
return self.normalize_configuration(conf=conf)
with open(file_name, 'r') as config_file:
conf = json.load(config_file)
return self.normalize_configuration(conf=conf)

def normalize_configuration(self, conf: dict) -> dict:
"""
Expand Down Expand Up @@ -768,4 +768,3 @@ def cast_argument_value(arg_name: str, val: Any, argument: ConfigurationArgument
return argument.type(val)
except ValueError as exn:
raise BadTypeException(arg_name, argument.type) from exn
return val
23 changes: 10 additions & 13 deletions src/powerapi/cli/generator.py
Original file line number Diff line number Diff line change
Expand Up @@ -41,6 +41,7 @@
from powerapi.processor.pre.k8s.k8s_pre_processor_actor import K8sPreProcessorActor, TIME_INTERVAL_DEFAULT_VALUE, \
TIMEOUT_QUERY_DEFAULT_VALUE
from powerapi.processor.pre.libvirt.libvirt_pre_processor_actor import LibvirtPreProcessorActor
from powerapi.processor.processor_actor import ProcessorActor
from powerapi.report import HWPCReport, PowerReport, ControlReport, ProcfsReport, Report, FormulaReport
from powerapi.database import MongoDB, CsvDB, OpenTSDB, SocketDB, PrometheusDB, \
VirtioFSDB, FileDB
Expand Down Expand Up @@ -335,16 +336,10 @@
Generator that initialises the processor from config
"""

def __init__(self, component_group_name: str):
Generator.__init__(self, component_group_name=component_group_name)

self.processor_factory = self._get_default_processor_factories()
def __init__(self, component_group_name: str, processor_factory: Dict[str, Callable[[Dict], ProcessorActor]] = None):
Generator.__init__(self, component_group_name)

def _get_default_processor_factories(self) -> dict:
"""
Init the factories for this processor generator
"""
raise NotImplementedError
self.processor_factory = processor_factory

def remove_processor_factory(self, processor_type: str):
"""
Expand Down Expand Up @@ -382,9 +377,10 @@
"""

def __init__(self):
ProcessorGenerator.__init__(self, component_group_name='pre-processor')
ProcessorGenerator.__init__(self, 'pre-processor', self._get_default_processor_factories())

def _get_default_processor_factories(self) -> dict:
@staticmethod
def _get_default_processor_factories() -> Dict[str, Callable[[Dict], ProcessorActor]]:
return {
'libvirt': lambda processor_config: LibvirtPreProcessorActor(name=processor_config[ACTOR_NAME_KEY],
uri=processor_config[COMPONENT_URI_KEY],
Expand Down Expand Up @@ -419,9 +415,10 @@
"""

def __init__(self):
ProcessorGenerator.__init__(self, component_group_name='post-processor')
ProcessorGenerator.__init__(self, 'post-processor', self._get_default_processor_factories())

Check warning on line 418 in src/powerapi/cli/generator.py

View check run for this annotation

Codecov / codecov/patch

src/powerapi/cli/generator.py#L418

Added line #L418 was not covered by tests

def _get_default_processor_factories(self) -> dict:
@staticmethod
def _get_default_processor_factories() -> Dict[str, Callable[[Dict], ProcessorActor]]:
return {}


Expand Down
70 changes: 43 additions & 27 deletions src/powerapi/cli/parsing_manager.py
Original file line number Diff line number Diff line change
Expand Up @@ -26,53 +26,60 @@
# CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY,
# OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
# OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
import sys
import json
import logging

import sys
from typing import Callable, Any

from powerapi.cli.config_parser import RootConfigParser, SubgroupConfigParser, store_val
from powerapi.exception import MissingArgumentException, BadTypeException, \
AlreadyAddedSubparserException, UnknownArgException, MissingValueException, BadContextException, \
RepeatedArgumentException, AlreadyAddedSubgroupException
from powerapi.exception import MissingArgumentException, BadTypeException, AlreadyAddedSubparserException, \
UnknownArgException, MissingValueException, BadContextException, RepeatedArgumentException, \
AlreadyAddedSubgroupException
from powerapi.utils.cli import merge_dictionaries


class BaseConfigParsingManager:
""" Abstract class for dealing with parsing of configurations. """

def __init__(self):
self.cli_parser = None
class BaseConfigParsingManagerInterface:
"""
Abstract class for dealing with parsing of configurations.
"""

def add_argument(self, *names, is_flag: bool = False, action: Callable = store_val,
default_value: Any = None, help_text: str = '', argument_type: type = str,
is_mandatory: bool = False):
def add_argument(self, *names, is_flag: bool = False, action: Callable = store_val, default_value: Any = None,
help_text: str = '', argument_type: type = str, is_mandatory: bool = False) -> None:
"""
Add an argument to the parser and its specification

Add an argument to the parser.
"""
self.cli_parser.add_argument(*names, is_flag=is_flag, action=action, default_value=default_value,
help_text=help_text, argument_type=bool if is_flag else argument_type,
is_mandatory=is_mandatory)
raise NotImplementedError

Check warning on line 51 in src/powerapi/cli/parsing_manager.py

View check run for this annotation

Codecov / codecov/patch

src/powerapi/cli/parsing_manager.py#L51

Added line #L51 was not covered by tests

def validate(self, conf: dict) -> dict:
""" Check the parsed configuration"""
"""
Validate the parsed configuration.
"""
raise NotImplementedError


class SubgroupConfigParsingManager(BaseConfigParsingManager):
class SubgroupConfigParsingManager(BaseConfigParsingManagerInterface):
"""
Sub Parser for MainConfigParser
"""

def __init__(self, name: str):
BaseConfigParsingManager.__init__(self)
self.subparser = {}
self.cli_parser = SubgroupConfigParser(name)
self.name = name
self.cli_parser = SubgroupConfigParser(name)

def add_argument(self, *names, is_flag: bool = False, action: Callable = store_val, default_value: Any = None,
help_text: str = '', argument_type: type = str, is_mandatory: bool = False) -> None:
"""
Add an argument to the parser.
"""
self.cli_parser.add_argument(*names, is_flag=is_flag, action=action, default_value=default_value,
help_text=help_text, argument_type=bool if is_flag else argument_type,
is_mandatory=is_mandatory)

def validate(self, conf: dict) -> dict:
""" Check the parsed configuration"""
"""
Check the parsed configuration.
"""

# check types
for args, value in conf.items():
Expand All @@ -88,13 +95,12 @@
return conf


class RootConfigParsingManager(BaseConfigParsingManager):
class RootConfigParsingManager(BaseConfigParsingManagerInterface):
"""
Parser abstraction for the configuration
"""

def __init__(self):
BaseConfigParsingManager.__init__(self)
self.subparser = {}
self.cli_parser = RootConfigParser()

Expand Down Expand Up @@ -124,7 +130,6 @@
"""
Add a Subgroup Parser to call when <name> is encountered
When name is encountered, the subgroup parser such as subgroup_parser.name match conf[name].type

"""
if subgroup_name in self.subparser:
if subgroup_parser.name in list(self.subparser[subgroup_name]):
Expand Down Expand Up @@ -156,8 +161,19 @@

return conf

def add_argument(self, *names, is_flag: bool = False, action: Callable = store_val, default_value: Any = None,
help_text: str = '', argument_type: type = str, is_mandatory: bool = False) -> None:
"""
Add an argument to the parser.
"""
self.cli_parser.add_argument(*names, is_flag=is_flag, action=action, default_value=default_value,
help_text=help_text, argument_type=bool if is_flag else argument_type,
is_mandatory=is_mandatory)

def validate(self, conf: dict) -> dict:
""" Check the parsed configuration"""
"""
Check the parsed configuration
"""

# check types
for current_argument_name, current_argument_value in conf.items():
Expand Down
6 changes: 3 additions & 3 deletions src/powerapi/database/base_db.py
Original file line number Diff line number Diff line change
Expand Up @@ -73,9 +73,9 @@ class BaseDB:
by each DB module. A database module correspond to a kind of BDD.
For example, Mongodb, influxdb, csv are different kind of BDD.
"""
def __init__(self, report_type: Type[Report]):
self.asynchrone = False
self.exceptions = []
def __init__(self, report_type: Type[Report], exceptions: List[Type[Exception]] = None, asynchrone: bool = False):
self.exceptions = exceptions or []
self.asynchrone = asynchrone
self.report_type = report_type

def connect(self):
Expand Down
51 changes: 22 additions & 29 deletions src/powerapi/database/csvdb.py
Original file line number Diff line number Diff line change
Expand Up @@ -265,41 +265,34 @@

:param report: Report
"""
csv_header, data = self.report_type.to_csv_lines(report, self.tags)
fixed_header, data = self.report_type.to_csv_lines(report, self.tags)

Check warning on line 268 in src/powerapi/database/csvdb.py

View check run for this annotation

Codecov / codecov/patch

src/powerapi/database/csvdb.py#L268

Added line #L268 was not covered by tests

# If the repository doesn't exist, create it
rep_path = self.current_path + report.sensor + "-" + report.target
try:
os.makedirs(rep_path)
except FileExistsError:
pass
os.makedirs(rep_path, exist_ok=True)

Check warning on line 272 in src/powerapi/database/csvdb.py

View check run for this annotation

Codecov / codecov/patch

src/powerapi/database/csvdb.py#L272

Added line #L272 was not covered by tests

for filename, values in data.items():
rep_path_with_file = rep_path + '/' + filename + '.csv'
# Get the header and check if it's ok
for value in values:
header = csv_header + sorted(list(set([event_key for event_key, _ in value.items()]) - set(csv_header)))
output_filename = f'{rep_path}/{filename}.csv'

Check warning on line 275 in src/powerapi/database/csvdb.py

View check run for this annotation

Codecov / codecov/patch

src/powerapi/database/csvdb.py#L275

Added line #L275 was not covered by tests

with open(output_filename, 'r+') as csvfile:
expected_header = fixed_header + sorted(set(values[0].keys()) - set(fixed_header))

Check warning on line 278 in src/powerapi/database/csvdb.py

View check run for this annotation

Codecov / codecov/patch

src/powerapi/database/csvdb.py#L277-L278

Added lines #L277 - L278 were not covered by tests
header_exist = False
try:
with open(rep_path_with_file) as csvfile:
reader = csv.DictReader(csvfile)
if reader.fieldnames:
header_exist = True

if header != reader.fieldnames:
raise HeaderAreNotTheSameError("Header are not the same in " + rep_path_with_file)
csvfile.flush()
csvfile.close()
except FileNotFoundError:
pass

# Write
with open(rep_path_with_file, 'a') as csvfile:
writer = csv.DictWriter(csvfile, header)
if not header_exist:
writer.writeheader()
writer.writerow(value)
csvfile.close()

reader = csv.DictReader(csvfile)
if reader.fieldnames:
header_exist = True
if reader.fieldnames != expected_header:
raise HeaderAreNotTheSameError(f"Header are not the same in {output_filename}")

Check warning on line 285 in src/powerapi/database/csvdb.py

View check run for this annotation

Codecov / codecov/patch

src/powerapi/database/csvdb.py#L281-L285

Added lines #L281 - L285 were not covered by tests

# Go to EOF before writing rows
csvfile.seek(0, 2)

Check warning on line 288 in src/powerapi/database/csvdb.py

View check run for this annotation

Codecov / codecov/patch

src/powerapi/database/csvdb.py#L288

Added line #L288 was not covered by tests

writer = csv.DictWriter(csvfile, fieldnames=expected_header)
if not header_exist:
writer.writeheader()

Check warning on line 292 in src/powerapi/database/csvdb.py

View check run for this annotation

Codecov / codecov/patch

src/powerapi/database/csvdb.py#L290-L292

Added lines #L290 - L292 were not covered by tests

for row in values:
writer.writerow(row)

Check warning on line 295 in src/powerapi/database/csvdb.py

View check run for this annotation

Codecov / codecov/patch

src/powerapi/database/csvdb.py#L294-L295

Added lines #L294 - L295 were not covered by tests

def save_many(self, reports: List[Report]):
"""
Expand Down
26 changes: 12 additions & 14 deletions src/powerapi/database/file_db.py
Original file line number Diff line number Diff line change
Expand Up @@ -71,20 +71,19 @@
:raise: StopIteration in stream mode when no report was found.
"""

file_object = open(self.filename, "r")
json_str = file_object.read()
file_object.close()
with open(self.filename, "r") as file_object:
json_str = file_object.read()

Check warning on line 75 in src/powerapi/database/file_db.py

View check run for this annotation

Codecov / codecov/patch

src/powerapi/database/file_db.py#L74-L75

Added lines #L74 - L75 were not covered by tests

if json_str is None:
raise StopIteration()
if json_str is None:
raise StopIteration()

Check warning on line 78 in src/powerapi/database/file_db.py

View check run for this annotation

Codecov / codecov/patch

src/powerapi/database/file_db.py#L77-L78

Added lines #L77 - L78 were not covered by tests

if json_str == self.previousJson:
logging.error("Error : Report did not change since last read")
raise StopIteration()
if json_str == self.previousJson:
logging.error("Error : Report did not change since last read")
raise StopIteration()

Check warning on line 82 in src/powerapi/database/file_db.py

View check run for this annotation

Codecov / codecov/patch

src/powerapi/database/file_db.py#L80-L82

Added lines #L80 - L82 were not covered by tests

self.previousJson = json_str
self.previousJson = json_str

Check warning on line 84 in src/powerapi/database/file_db.py

View check run for this annotation

Codecov / codecov/patch

src/powerapi/database/file_db.py#L84

Added line #L84 was not covered by tests

return self.report_type.from_json(json.loads(json_str))
return self.report_type.from_json(json.loads(json_str))

Check warning on line 86 in src/powerapi/database/file_db.py

View check run for this annotation

Codecov / codecov/patch

src/powerapi/database/file_db.py#L86

Added line #L86 was not covered by tests


class FileDB(BaseDB):
Expand Down Expand Up @@ -125,7 +124,7 @@

:param report: Report to save
"""
file_object = open(self.filename, "w")

line = {
"sensor": report.sensor,
"target": report.target,
Expand All @@ -135,9 +134,8 @@

final_dict = {"PowerReport": [line]}

file_object.truncate(0)
file_object.write(str(final_dict))
file_object.close()
with open(self.filename, "w") as file_object:
file_object.write(str(final_dict))

Check warning on line 138 in src/powerapi/database/file_db.py

View check run for this annotation

Codecov / codecov/patch

src/powerapi/database/file_db.py#L137-L138

Added lines #L137 - L138 were not covered by tests

def save_many(self, reports: List[Report]):
"""
Expand Down
3 changes: 0 additions & 3 deletions src/powerapi/database/influxdb2.py
Original file line number Diff line number Diff line change
Expand Up @@ -90,10 +90,7 @@ def __iter__(self):
raise NotImplementedError()

def _ping_client(self):
# if hasattr(self.client, 'ping'):
self.client.ping()
# else:
# self.client.request(url="ping", method='GET', expected_response_code=204)

def connect(self):
"""
Expand Down
5 changes: 2 additions & 3 deletions src/powerapi/database/mongodb.py
Original file line number Diff line number Diff line change
Expand Up @@ -29,6 +29,7 @@
import logging
try:
import pymongo
import pymongo.errors
except ImportError:
logging.getLogger().info("PyMongo is not installed.")

Expand Down Expand Up @@ -103,7 +104,7 @@ def __init__(self, report_type: Type[Report], uri: str, db_name: str, collection
:param collection_name: collection name in the mongodb
(ex: "sensor")
"""
BaseDB.__init__(self, report_type)
BaseDB.__init__(self, report_type, [pymongo.errors.PyMongoError])

#: (str): URI of the mongodb server
self.uri = uri
Expand All @@ -121,8 +122,6 @@ def __init__(self, report_type: Type[Report], uri: str, db_name: str, collection
#: targeted collection
self.collection = None

self.exceptions = [pymongo.errors.PyMongoError]

def connect(self):
"""
Override from BaseDB.
Expand Down
3 changes: 1 addition & 2 deletions src/powerapi/database/socket_db.py
Original file line number Diff line number Diff line change
Expand Up @@ -46,8 +46,7 @@ class SocketDB(BaseDB):
"""

def __init__(self, report_type: Type[Report], port: int):
BaseDB.__init__(self, report_type)
self.asynchrone = True
BaseDB.__init__(self, report_type, asynchrone=True)
self.queue = None
self.port = port
self.server = None
Expand Down
7 changes: 3 additions & 4 deletions src/powerapi/database/virtiofs_db.py
Original file line number Diff line number Diff line change
Expand Up @@ -85,13 +85,12 @@
return

vm_filename, power = self.report_type.to_virtiofs_db(report)
vm_filename_path = self.root_directory_name + '/' + directory_name + '/'
vm_filename_path = f'{self.root_directory_name}/{directory_name}'

Check warning on line 88 in src/powerapi/database/virtiofs_db.py

View check run for this annotation

Codecov / codecov/patch

src/powerapi/database/virtiofs_db.py#L88

Added line #L88 was not covered by tests
if not os.path.exists(vm_filename_path):
raise DirectoryDoesNotExistForVirtioFS(vm_filename_path)

vm_file = open(vm_filename_path + vm_filename, 'w+')
vm_file.write(str(power))
vm_file.close()
with open(vm_filename_path + vm_filename, 'w') as vm_file:
vm_file.write(str(power))

Check warning on line 93 in src/powerapi/database/virtiofs_db.py

View check run for this annotation

Codecov / codecov/patch

src/powerapi/database/virtiofs_db.py#L92-L93

Added lines #L92 - L93 were not covered by tests

def save_many(self, reports: List[Report]):
for report in reports:
Expand Down
Loading