diff --git a/src/python/evaluation/README.md b/src/python/evaluation/README.md deleted file mode 100644 index 67e1d45e..00000000 --- a/src/python/evaluation/README.md +++ /dev/null @@ -1,31 +0,0 @@ -# Hyperstyle evaluation - -This tool allows running the `Hyperstyle` tool on an xlsx table to get code quality for all code fragments. Please, note that your input file should consist of at least 2 obligatory columns to run xlsx-tool on its code fragments: - -- `code` -- `lang` - -Possible values for column `lang` are: `python3`, `kotlin`, `java8`, `java11`. - -Output file is a new `xlsx` file with 3 columns: -- `code` -- `lang` -- `grade` -Grade assessment is conducted by [`run_tool.py`](https://github.com/hyperskill/hyperstyle/blob/main/README.md) with default arguments. Avaliable values for column `grade` are: BAD, MODERATE, GOOD, EXCELLENT. It is also possible add fourth column: `traceback` to get full inspectors feedback on each code fragment. More details on enabling traceback column in **Optional Arguments** table. - -## Usage - -Run the [xlsx_run_tool.py](xlsx_run_tool.py) with the arguments from command line. - -Required arguments: - -`xlsx_file_path` — path to xlsx-file with code samples to inspect. - -Optional arguments: -Argument | Description ---- | --- -|**‑f**, **‑‑format**| The output format. Available values: `json`, `text`. The default value is `json` . Use this argument when `traceback` is enabled, otherwise it will not be used.| -|**‑tp**, **‑‑tool_path**| Path to run-tool. Default is `src/python/review/run_tool.py` .| -|**‑tr**, **‑‑traceback**| To include a column with errors traceback into an output file. Default is `False`.| -|**‑ofp**, **‑‑output_folder_path**| An explicit folder path to store file with results. Default is a parent directory of a folder with xlsx-file sent for inspection. | -|**‑ofn**, **‑‑output_file_name**| A name of an output file where evaluation results will be stored. Default is `results.xlsx`.| diff --git a/src/python/evaluation/__init__.py b/src/python/evaluation/__init__.py deleted file mode 100644 index e69de29b..00000000 diff --git a/src/python/evaluation/common/__init__.py b/src/python/evaluation/common/__init__.py deleted file mode 100644 index e69de29b..00000000 diff --git a/src/python/evaluation/common/util.py b/src/python/evaluation/common/util.py deleted file mode 100644 index c20b16d8..00000000 --- a/src/python/evaluation/common/util.py +++ /dev/null @@ -1,34 +0,0 @@ -from enum import Enum, unique - -from src.python.review.application_config import LanguageVersion -from src.python.review.common.file_system import Extension - - -@unique -class ColumnName(Enum): - CODE = 'code' - LANG = 'lang' - LANGUAGE = 'language' - GRADE = 'grade' - - -@unique -class EvaluationArgument(Enum): - TRACEBACK = 'traceback' - RESULT_FILE_NAME = 'results' - RESULT_FILE_NAME_EXT = f'{RESULT_FILE_NAME}{Extension.XLSX.value}' - - -script_structure_rule = ('Please, make sure your XLSX-file matches following script standards: \n' - '1. Your XLSX-file should have 2 obligatory columns named:' - f'"{ColumnName.CODE.value}" & "{ColumnName.LANG.value}". \n' - f'"{ColumnName.CODE.value}" column -- relates to the code-sample. \n' - f'"{ColumnName.LANG.value}" column -- relates to the language of a ' - 'particular code-sample. \n' - '2. Your code samples should belong to the one of the supported languages. \n' - 'Supported languages are: Java, Kotlin, Python. \n' - f'3. Check that "{ColumnName.LANG.value}" column cells are filled with ' - 'acceptable language-names: \n' - f'Acceptable language-names are: {LanguageVersion.PYTHON_3.value}, ' - f'{LanguageVersion.JAVA_8.value} ,' - f'{LanguageVersion.JAVA_11.value} and {LanguageVersion.KOTLIN.value}.') diff --git a/src/python/evaluation/common/xlsx_util.py b/src/python/evaluation/common/xlsx_util.py deleted file mode 100644 index 032a5ce6..00000000 --- a/src/python/evaluation/common/xlsx_util.py +++ /dev/null @@ -1,42 +0,0 @@ -import logging.config -from pathlib import Path -from typing import Union - -import pandas as pd -from openpyxl import load_workbook, Workbook -from src.python.evaluation.evaluation_config import EvaluationConfig - -logger = logging.getLogger(__name__) - - -def remove_sheet(workbook_path: Union[str, Path], sheet_name: str, to_raise_error: bool = False) -> None: - try: - workbook = load_workbook(workbook_path) - workbook.remove(workbook[sheet_name]) - workbook.save(workbook_path) - - except KeyError as e: - message = f'Sheet with specified name: {sheet_name} does not exist.' - if to_raise_error: - logger.exception(message) - raise e - else: - logger.info(message) - - -def create_and_get_workbook_path(config: EvaluationConfig) -> Path: - workbook = Workbook() - workbook_path = config.get_output_file_path() - workbook.save(workbook_path) - return workbook_path - - -def write_dataframe_to_xlsx_sheet(xlsx_file_path: Union[str, Path], df: pd.DataFrame, sheet_name: str, - mode: str = 'a', to_write_row_names: bool = False) -> None: - """ - mode: str Available values are {'w', 'a'}. File mode to use (write or append). - to_write_row_names: bool Write row names. - """ - - with pd.ExcelWriter(xlsx_file_path, mode=mode) as writer: - df.to_excel(writer, sheet_name=sheet_name, index=to_write_row_names) diff --git a/src/python/evaluation/evaluation_config.py b/src/python/evaluation/evaluation_config.py deleted file mode 100644 index 3a856b78..00000000 --- a/src/python/evaluation/evaluation_config.py +++ /dev/null @@ -1,43 +0,0 @@ -import logging.config -import os -from argparse import Namespace -from pathlib import Path -from typing import List, Union - -from src.python.common.tool_arguments import RunToolArgument -from src.python.evaluation.common.util import EvaluationArgument -from src.python.review.application_config import LanguageVersion - -logger = logging.getLogger(__name__) - - -class EvaluationConfig: - def __init__(self, args: Namespace): - self.tool_path: Union[str, Path] = args.tool_path - self.format: str = args.format - self.xlsx_file_path: Union[str, Path] = args.xlsx_file_path - self.traceback: bool = args.traceback - self.output_folder_path: Union[str, Path] = args.output_folder_path - self.output_file_name: str = args.output_file_name - - def build_command(self, inspected_file_path: Union[str, Path], lang: str) -> List[str]: - command = [LanguageVersion.PYTHON_3.value, - self.tool_path, - inspected_file_path, - RunToolArgument.FORMAT.value.short_name, self.format] - - if lang == LanguageVersion.JAVA_8.value or lang == LanguageVersion.JAVA_11.value: - command.extend([RunToolArgument.LANG_VERSION.value.long_name, lang]) - return command - - def get_output_file_path(self) -> Path: - if self.output_folder_path is None: - try: - self.output_folder_path = ( - Path(self.xlsx_file_path).parent.parent / EvaluationArgument.RESULT_FILE_NAME.value - ) - os.makedirs(self.output_folder_path, exist_ok=True) - except FileNotFoundError as e: - logger.error('XLSX-file with the specified name does not exists.') - raise e - return Path(self.output_folder_path) / self.output_file_name diff --git a/src/python/evaluation/xlsx_run_tool.py b/src/python/evaluation/xlsx_run_tool.py deleted file mode 100644 index 7235b041..00000000 --- a/src/python/evaluation/xlsx_run_tool.py +++ /dev/null @@ -1,169 +0,0 @@ -import argparse -import logging.config -import os -import re -import sys -import traceback -from pathlib import Path -from typing import Type - -sys.path.append('') -sys.path.append('../../..') - -import pandas as pd -from src.python.common.tool_arguments import RunToolArgument -from src.python.evaluation.common.util import ColumnName, EvaluationArgument, script_structure_rule -from src.python.evaluation.common.xlsx_util import ( - create_and_get_workbook_path, - remove_sheet, - write_dataframe_to_xlsx_sheet, -) -from src.python.evaluation.evaluation_config import EvaluationConfig -from src.python.review.application_config import LanguageVersion -from src.python.review.common.file_system import create_file, new_temp_dir -from src.python.review.common.subprocess_runner import run_in_subprocess -from src.python.review.reviewers.perform_review import OutputFormat - -logger = logging.getLogger(__name__) - - -def configure_arguments(parser: argparse.ArgumentParser, run_tool_arguments: Type[RunToolArgument]) -> None: - parser.add_argument('xlsx_file_path', - type=lambda value: Path(value).absolute(), - help='Local XLSX-file path. ' - 'Your XLSX-file must include column-names: ' - f'"{ColumnName.CODE.value}" and ' - f'"{ColumnName.LANG.value}". Acceptable values for ' - f'"{ColumnName.LANG.value}" column are: ' - f'{LanguageVersion.PYTHON_3.value}, {LanguageVersion.JAVA_8.value}, ' - f'{LanguageVersion.JAVA_11.value}, {LanguageVersion.KOTLIN.value}.') - - parser.add_argument('-tp', '--tool-path', - default=Path('src/python/review/run_tool.py').absolute(), - type=lambda value: Path(value).absolute(), - help='Path to script to run on files.') - - parser.add_argument('-tr', '--traceback', - help='If True, column with the full inspector feedback will be added ' - 'to the output file with results.', - action='store_true') - - parser.add_argument('-ofp', '--output-folder-path', - help='An absolute path to the folder where file with evaluation results' - 'will be stored.' - 'Default is the path to a directory, where is the folder with xlsx_file.', - # if None default path will be specified based on xlsx_file_path. - default=None, - type=str) - - parser.add_argument('-ofn', '--output-file-name', - help='Filename for that will be created to store inspection results.' - f'Default is "{EvaluationArgument.RESULT_FILE_NAME_EXT.value}"', - default=f'{EvaluationArgument.RESULT_FILE_NAME_EXT.value}', - type=str) - - parser.add_argument(run_tool_arguments.FORMAT.value.short_name, - run_tool_arguments.FORMAT.value.long_name, - default=OutputFormat.JSON.value, - choices=OutputFormat.values(), - type=str, - help=f'{run_tool_arguments.FORMAT.value.description}' - f'Use this argument when {EvaluationArgument.TRACEBACK.value} argument' - 'is enabled argument will not be used otherwise.') - - -def create_dataframe(config: EvaluationConfig) -> pd.DataFrame: - report = pd.DataFrame( - { - ColumnName.LANGUAGE.value: [], - ColumnName.CODE.value: [], - ColumnName.GRADE.value: [], - }, - ) - - if config.traceback: - report[EvaluationArgument.TRACEBACK.value] = [] - - try: - lang_code_dataframe = pd.read_excel(config.xlsx_file_path) - - except FileNotFoundError as e: - logger.error('XLSX-file with the specified name does not exists.') - raise e - - try: - for lang, code in zip(lang_code_dataframe[ColumnName.LANG.value], - lang_code_dataframe[ColumnName.CODE.value]): - - with new_temp_dir() as create_temp_dir: - temp_dir_path = create_temp_dir - lang_extension = LanguageVersion.language_by_extension(lang) - temp_file_path = os.path.join(temp_dir_path, ('file' + lang_extension)) - temp_file_path = next(create_file(temp_file_path, code)) - - try: - assert os.path.exists(temp_file_path) - except AssertionError as e: - logger.exception('Path does not exist.') - raise e - - command = config.build_command(temp_file_path, lang) - results = run_in_subprocess(command) - os.remove(temp_file_path) - temp_dir_path.rmdir() - # this regular expression matches final tool grade: EXCELLENT, GOOD, MODERATE or BAD - grades = re.match(r'^.*{"code":\s"([A-Z]+)"', results).group(1) - output_row_values = [lang, code, grades] - column_indices = [ColumnName.LANGUAGE.value, - ColumnName.CODE.value, - ColumnName.GRADE.value] - - if config.traceback: - output_row_values.append(results) - column_indices.append(EvaluationArgument.TRACEBACK.value) - - new_file_report_row = pd.Series(data=output_row_values, index=column_indices) - report = report.append(new_file_report_row, ignore_index=True) - - return report - - except KeyError as e: - logger.error(script_structure_rule) - raise e - - except Exception as e: - traceback.print_exc() - logger.exception('An unexpected error.') - raise e - - -def main() -> int: - parser = argparse.ArgumentParser() - configure_arguments(parser, RunToolArgument) - - try: - args = parser.parse_args() - config = EvaluationConfig(args) - workbook_path = create_and_get_workbook_path(config) - results = create_dataframe(config) - write_dataframe_to_xlsx_sheet(workbook_path, results, 'inspection_results') - # remove empty sheet that was initially created with the workbook - remove_sheet(workbook_path, 'Sheet') - return 0 - - except FileNotFoundError: - logger.error('XLSX-file with the specified name does not exists.') - return 2 - - except KeyError: - logger.error(script_structure_rule) - return 2 - - except Exception: - traceback.print_exc() - logger.exception('An unexpected error.') - return 2 - - -if __name__ == '__main__': - sys.exit(main()) diff --git a/src/python/review/application_config.py b/src/python/review/application_config.py index 8d9a56f5..6032aef3 100644 --- a/src/python/review/application_config.py +++ b/src/python/review/application_config.py @@ -42,3 +42,11 @@ def language_to_extension_dict(cls) -> dict: @classmethod def language_by_extension(cls, lang: str) -> str: return cls.language_to_extension_dict()[lang] + + def is_java(self) -> bool: + return ( + self == LanguageVersion.JAVA_7 + or self == LanguageVersion.JAVA_8 + or self == LanguageVersion.JAVA_9 + or self == LanguageVersion.JAVA_11 + ) diff --git a/src/python/review/inspectors/common.py b/src/python/review/inspectors/common.py index dfedbb1e..a307bd96 100644 --- a/src/python/review/inspectors/common.py +++ b/src/python/review/inspectors/common.py @@ -10,3 +10,14 @@ def convert_percentage_of_value_to_lack_of_value(percentage_of_value: float) -> :return: lack of value. """ return floor(100 - percentage_of_value) + + +# TODO: When upgrading to python 3.9+, replace it with removeprefix. +# See: https://docs.python.org/3.9/library/stdtypes.html#str.removeprefix +def remove_prefix(text: str, prefix: str) -> str: + """ + Removes the prefix if it is present, otherwise returns the original string. + """ + if text.startswith(prefix): + return text[len(prefix):] + return text diff --git a/src/python/review/inspectors/detekt/issue_types.py b/src/python/review/inspectors/detekt/issue_types.py index e05d1a30..2379bba8 100644 --- a/src/python/review/inspectors/detekt/issue_types.py +++ b/src/python/review/inspectors/detekt/issue_types.py @@ -15,7 +15,7 @@ # complexity: 'ComplexCondition': IssueType.BOOL_EXPR_LEN, 'ComplexInterface': IssueType.COMPLEXITY, - 'ComplexMethod': IssueType.COMPLEXITY, + 'ComplexMethod': IssueType.CYCLOMATIC_COMPLEXITY, 'LabeledExpression': IssueType.COMPLEXITY, 'LargeClass': IssueType.COMPLEXITY, 'LongMethod': IssueType.FUNC_LEN, diff --git a/src/python/review/inspectors/flake8/flake8.py b/src/python/review/inspectors/flake8/flake8.py index 5745a75f..c5dfd274 100644 --- a/src/python/review/inspectors/flake8/flake8.py +++ b/src/python/review/inspectors/flake8/flake8.py @@ -21,6 +21,10 @@ logger = logging.getLogger(__name__) PATH_FLAKE8_CONFIG = Path(__file__).parent / '.flake8' +# To make the whitelist, a list of words was examined based on students' solutions +# that were flagged by flake8-spellcheck as erroneous. In general, the whitelist included those words +# that belonged to library methods and which were common abbreviations. +PATH_FLAKE8_SPELLCHECK_WHITELIST = Path(__file__).parent / 'whitelist.txt' FORMAT = '%(path)s:%(row)d:%(col)d:%(code)s:%(text)s' INSPECTOR_NAME = 'flake8' @@ -34,6 +38,7 @@ def inspect(cls, path: Path, config: dict) -> List[BaseIssue]: 'flake8', f'--format={FORMAT}', f'--config={PATH_FLAKE8_CONFIG}', + f'--whitelist={PATH_FLAKE8_SPELLCHECK_WHITELIST}', '--max-complexity', '0', '--cohesion-below', '100', path, diff --git a/src/python/review/inspectors/flake8/issue_types.py b/src/python/review/inspectors/flake8/issue_types.py index 440f5f82..b1074b52 100644 --- a/src/python/review/inspectors/flake8/issue_types.py +++ b/src/python/review/inspectors/flake8/issue_types.py @@ -27,6 +27,8 @@ 'C818': IssueType.CODE_STYLE, 'C819': IssueType.CODE_STYLE, + # The categorization for WPS was created using the following document: https://bit.ly/3yms06n + # WPS: Naming 'WPS117': IssueType.CODE_STYLE, # Forbid naming variables self, cls, or mcs. 'WPS125': IssueType.ERROR_PRONE, # Forbid variable or module names which shadow builtin names. diff --git a/src/python/review/inspectors/flake8/whitelist.txt b/src/python/review/inspectors/flake8/whitelist.txt new file mode 100644 index 00000000..47340d90 --- /dev/null +++ b/src/python/review/inspectors/flake8/whitelist.txt @@ -0,0 +1,127 @@ +aggfunc +appendleft +argmax +asctime +astype +betavariate +birthdate +blackbox +bs4 +byteorder +calc +capwords +casefold +caseless +concat +consts +coord +copysign +csgraph +ctime +dataframe +dataframes +dataset +datasets +decrypted +dedent +deque +desc +devs +df +dicts +dirs +divmod +dtype +edu +eig +elems +etree +expm1 +falsy +fillna +floordiv +fromstring +fullmatch +gensim +gmtime +groupby +halfs +hashable +href +hyp +hyperskill +iadd +iloc +inplace +ints +isalnum +isalpha +isin +islice +islower +isnumeric +isprintable +istitle +isub +iterrows +kcal +kcals +lastname +lemmatize +lemmatizer +lifes +lim +linalg +linspace +lowercased +lvl +lxml +matmul +multiline +ndarray +ndigits +ndim +nltk +nrows +numpy +nums +ost +param +params +parsers +pathlib +popleft +pos +punct +readline +rfind +rindex +rmdir +schur +scipy +sigmoid +sqrt +src +stemmer +stepik +subdicts +subdir +subdirs +substr +substring +textwrap +todos +tokenize +tokenized +tokenizer +tolist +tracklist +truediv +truthy +unpickled +upd +util +utils +webpage +whitespaces +writeback diff --git a/src/python/review/inspectors/pmd/issue_types.py b/src/python/review/inspectors/pmd/issue_types.py index e4609146..2188702b 100644 --- a/src/python/review/inspectors/pmd/issue_types.py +++ b/src/python/review/inspectors/pmd/issue_types.py @@ -2,7 +2,7 @@ from src.python.review.inspectors.issue import IssueType -RULE_TO_ISSUE_TYPE: Dict[str, IssueType] = { +PMD_RULE_TO_ISSUE_TYPE: Dict[str, IssueType] = { # Best Practices 'AbstractClassWithoutAbstractMethod': IssueType.BEST_PRACTICES, 'AccessorClassGeneration': IssueType.BEST_PRACTICES, diff --git a/src/python/review/inspectors/pmd/pmd.py b/src/python/review/inspectors/pmd/pmd.py index 4b8c11f0..eb4878dd 100644 --- a/src/python/review/inspectors/pmd/pmd.py +++ b/src/python/review/inspectors/pmd/pmd.py @@ -8,15 +8,17 @@ from src.python.review.common.file_system import new_temp_dir from src.python.review.common.subprocess_runner import run_in_subprocess from src.python.review.inspectors.base_inspector import BaseInspector +from src.python.review.inspectors.common import remove_prefix from src.python.review.inspectors.inspector_type import InspectorType from src.python.review.inspectors.issue import BaseIssue, CodeIssue, IssueType -from src.python.review.inspectors.pmd.issue_types import RULE_TO_ISSUE_TYPE +from src.python.review.inspectors.pmd.issue_types import PMD_RULE_TO_ISSUE_TYPE logger = logging.getLogger(__name__) PATH_TOOLS_PMD_FILES = Path(__file__).parent / 'files' PATH_TOOLS_PMD_SHELL_SCRIPT = PATH_TOOLS_PMD_FILES / 'bin' / 'run.sh' PATH_TOOLS_PMD_RULES_SET = PATH_TOOLS_PMD_FILES / 'bin' / 'basic.xml' +DEFAULT_JAVA_VERSION = LanguageVersion.JAVA_11 class PMDInspector(BaseInspector): @@ -28,14 +30,14 @@ def __init__(self): @classmethod def _create_command(cls, path: Path, output_path: Path, - java_version: LanguageVersion, + language_version: LanguageVersion, n_cpu: int) -> List[str]: return [ PATH_TOOLS_PMD_SHELL_SCRIPT, 'pmd', '-d', str(path), '-no-cache', '-R', PATH_TOOLS_PMD_RULES_SET, '-language', 'java', - '-version', java_version.value, + '-version', cls._get_java_version(language_version), '-f', 'csv', '-r', str(output_path), '-t', str(n_cpu), ] @@ -46,13 +48,21 @@ def inspect(self, path: Path, config: dict) -> List[BaseIssue]: language_version = config.get('language_version') if language_version is None: - language_version = LanguageVersion.JAVA_11 + logger.info( + f"The version of Java is not passed. The version to be used is: {DEFAULT_JAVA_VERSION.value}.", + ) + language_version = DEFAULT_JAVA_VERSION command = self._create_command(path, output_path, language_version, config['n_cpu']) run_in_subprocess(command) return self.parse_output(output_path) def parse_output(self, output_path: Path) -> List[BaseIssue]: + """ + Parses the PMD output, which is a csv file, and returns a list of the issues found there. + + If the passed path is not a file, an empty list is returned. + """ if not output_path.is_file(): logger.error('%s: error - no output file' % self.inspector_type.value) return [] @@ -65,17 +75,37 @@ def parse_output(self, output_path: Path) -> List[BaseIssue]: line_no=int(row['Line']), column_no=1, type=self.choose_issue_type(row['Rule']), - origin_class=row['Rule set'], + origin_class=row['Rule'], description=row['Description'], inspector_type=self.inspector_type, ) for row in reader] @classmethod def choose_issue_type(cls, rule: str) -> IssueType: - issue_type = RULE_TO_ISSUE_TYPE.get(rule) + """ + Defines IssueType by PMD rule name using config. + """ + issue_type = PMD_RULE_TO_ISSUE_TYPE.get(rule) if not issue_type: logger.warning('%s: %s - unknown rule' % (cls.inspector_type.value, rule)) return IssueType.BEST_PRACTICES return issue_type + + @staticmethod + def _get_java_version(language_version: LanguageVersion) -> str: + """ + Converts language_version to the version of Java that PMD can work with. + + For example, java11 will be converted to 11. + """ + java_version = language_version.value + + if not language_version.is_java(): + logger.warning( + f"The version passed is not the Java version. The version to be used is: {DEFAULT_JAVA_VERSION.value}.", + ) + java_version = DEFAULT_JAVA_VERSION.value + + return remove_prefix(java_version, "java") diff --git a/test/python/evaluation/__init__.py b/test/python/evaluation/__init__.py deleted file mode 100644 index 31b1b86f..00000000 --- a/test/python/evaluation/__init__.py +++ /dev/null @@ -1,11 +0,0 @@ -from test.python import TEST_DATA_FOLDER - -from src.python import MAIN_FOLDER - -CURRENT_TEST_DATA_FOLDER = TEST_DATA_FOLDER / 'evaluation' - -XLSX_DATA_FOLDER = CURRENT_TEST_DATA_FOLDER / 'xlsx_files' - -TARGET_XLSX_DATA_FOLDER = CURRENT_TEST_DATA_FOLDER / 'xlsx_target_files' - -RESULTS_DIR_PATH = MAIN_FOLDER.parent / 'evaluation/results' diff --git a/test/python/evaluation/test_data_path.py b/test/python/evaluation/test_data_path.py deleted file mode 100644 index 0d8e3502..00000000 --- a/test/python/evaluation/test_data_path.py +++ /dev/null @@ -1,14 +0,0 @@ -from test.python.evaluation import XLSX_DATA_FOLDER -from test.python.evaluation.testing_config import get_testing_arguments - -import pytest -from src.python.evaluation.evaluation_config import EvaluationConfig -from src.python.evaluation.xlsx_run_tool import create_dataframe - - -def test_incorrect_data_path(): - with pytest.raises(FileNotFoundError): - testing_arguments_dict = get_testing_arguments(to_add_traceback=True, to_add_tool_path=True) - testing_arguments_dict.xlsx_file_path = XLSX_DATA_FOLDER / 'do_not_exist.xlsx' - config = EvaluationConfig(testing_arguments_dict) - assert create_dataframe(config) diff --git a/test/python/evaluation/test_output_results.py b/test/python/evaluation/test_output_results.py deleted file mode 100644 index 519652e5..00000000 --- a/test/python/evaluation/test_output_results.py +++ /dev/null @@ -1,32 +0,0 @@ -from test.python.evaluation import TARGET_XLSX_DATA_FOLDER, XLSX_DATA_FOLDER -from test.python.evaluation.testing_config import get_testing_arguments - -import pandas as pd -import pytest -from src.python.evaluation.evaluation_config import EvaluationConfig -from src.python.evaluation.xlsx_run_tool import create_dataframe - -FILE_NAMES = [ - ('test_sorted_order.xlsx', 'target_sorted_order.xlsx', False), - ('test_sorted_order.xlsx', 'target_sorted_order.xlsx', True), - ('test_unsorted_order.xlsx', 'target_unsorted_order.xlsx', False), - ('test_unsorted_order.xlsx', 'target_unsorted_order.xlsx', True), -] - - -@pytest.mark.parametrize(('test_file', 'target_file', 'output_type'), FILE_NAMES) -def test_correct_output(test_file: str, target_file: str, output_type: bool): - - testing_arguments_dict = get_testing_arguments(to_add_tool_path=True) - testing_arguments_dict.xlsx_file_path = XLSX_DATA_FOLDER / test_file - testing_arguments_dict.traceback = output_type - - config = EvaluationConfig(testing_arguments_dict) - test_dataframe = create_dataframe(config) - - sheet_name = 'grades' - if output_type: - sheet_name = 'traceback' - target_dataframe = pd.read_excel(TARGET_XLSX_DATA_FOLDER / target_file, sheet_name=sheet_name) - - assert test_dataframe.reset_index(drop=True).equals(target_dataframe.reset_index(drop=True)) diff --git a/test/python/evaluation/test_tool_path.py b/test/python/evaluation/test_tool_path.py deleted file mode 100644 index 0581caad..00000000 --- a/test/python/evaluation/test_tool_path.py +++ /dev/null @@ -1,26 +0,0 @@ -from test.python.evaluation import XLSX_DATA_FOLDER -from test.python.evaluation.testing_config import get_testing_arguments - -import pytest -from src.python import MAIN_FOLDER -from src.python.evaluation.evaluation_config import EvaluationConfig -from src.python.evaluation.xlsx_run_tool import create_dataframe - - -def test_correct_tool_path(): - try: - testing_arguments_dict = get_testing_arguments(to_add_traceback=True, to_add_tool_path=True) - testing_arguments_dict.xlsx_file_path = XLSX_DATA_FOLDER / 'test_unsorted_order.xlsx' - config = EvaluationConfig(testing_arguments_dict) - create_dataframe(config) - except Exception: - pytest.fail("Unexpected error") - - -def test_incorrect_tool_path(): - with pytest.raises(Exception): - testing_arguments_dict = get_testing_arguments(to_add_traceback=True) - testing_arguments_dict.xlsx_file_path = XLSX_DATA_FOLDER / 'test_unsorted_order.xlsx' - testing_arguments_dict.tool_path = MAIN_FOLDER.parent / 'review/incorrect_path.py' - config = EvaluationConfig(testing_arguments_dict) - assert create_dataframe(config) diff --git a/test/python/evaluation/test_xlsx_file_structure.py b/test/python/evaluation/test_xlsx_file_structure.py deleted file mode 100644 index 9965992e..00000000 --- a/test/python/evaluation/test_xlsx_file_structure.py +++ /dev/null @@ -1,23 +0,0 @@ -from test.python.evaluation import XLSX_DATA_FOLDER -from test.python.evaluation.testing_config import get_testing_arguments - -import pytest -from src.python.evaluation.evaluation_config import EvaluationConfig -from src.python.evaluation.xlsx_run_tool import create_dataframe - - -FILE_NAMES = [ - 'test_wrong_column_name.xlsx', - 'test_java_no_version.xlsx', - 'test_empty_lang_cell.xlsx', - 'test_empty_table.xlsx', -] - - -@pytest.mark.parametrize('file_name', FILE_NAMES) -def test_wrong_column(file_name: str): - with pytest.raises(KeyError): - testing_arguments_dict = get_testing_arguments(to_add_traceback=True, to_add_tool_path=True) - testing_arguments_dict.xlsx_file_path = XLSX_DATA_FOLDER / file_name - config = EvaluationConfig(testing_arguments_dict) - assert create_dataframe(config) diff --git a/test/python/evaluation/testing_config.py b/test/python/evaluation/testing_config.py deleted file mode 100644 index 70341635..00000000 --- a/test/python/evaluation/testing_config.py +++ /dev/null @@ -1,18 +0,0 @@ -from argparse import Namespace - -from src.python import MAIN_FOLDER -from src.python.evaluation.common.util import EvaluationArgument -from src.python.review.reviewers.perform_review import OutputFormat - - -def get_testing_arguments(to_add_traceback=None, to_add_tool_path=None) -> Namespace: - testing_arguments = Namespace(format=OutputFormat.JSON.value, - output_file_name=EvaluationArgument.RESULT_FILE_NAME_EXT.value, - output_folder_path=None) - if to_add_traceback: - testing_arguments.traceback = True - - if to_add_tool_path: - testing_arguments.tool_path = MAIN_FOLDER.parent / 'review/run_tool.py' - - return testing_arguments diff --git a/test/python/inspectors/test_detekt_inspector.py b/test/python/inspectors/test_detekt_inspector.py index 61d05200..99f84f27 100644 --- a/test/python/inspectors/test_detekt_inspector.py +++ b/test/python/inspectors/test_detekt_inspector.py @@ -23,6 +23,7 @@ ('case16_redundant_unit.kt', 1), ('case18_redundant_braces.kt', 3), ('case20_cyclomatic_complexity.kt', 0), + ('case21_cyclomatic_complexity_bad.kt', 2), ('case22_too_many_arguments.kt', 1), ('case23_bad_range_performance.kt', 3), ('case24_duplicate_when_bug.kt', 1), diff --git a/test/python/inspectors/test_flake8_inspector.py b/test/python/inspectors/test_flake8_inspector.py index cae684c1..f1ed0958 100644 --- a/test/python/inspectors/test_flake8_inspector.py +++ b/test/python/inspectors/test_flake8_inspector.py @@ -29,10 +29,11 @@ ('case19_bad_indentation.py', 3), ('case21_imports.py', 2), ('case25_django.py', 0), - ('case31_line_break.py', 11), + ('case31_spellcheck.py', 0), ('case32_string_format.py', 34), ('case33_commas.py', 14), ('case34_cohesion.py', 1), + ('case35_line_break.py', 11), ] @@ -69,7 +70,7 @@ def test_file_with_issues(file_name: str, n_issues: int): ('case14_returns_errors.py', IssuesTestInfo(n_best_practices=1, n_error_prone=3, n_cc=4)), - ('case31_line_break.py', IssuesTestInfo(n_best_practices=1, + ('case35_line_break.py', IssuesTestInfo(n_best_practices=1, n_code_style=10, n_cc=1)), ('case32_string_format.py', IssuesTestInfo(n_error_prone=28, n_other_complexity=6)), diff --git a/test/resources/evaluation/xlsx_files/test_empty_lang_cell.xlsx b/test/resources/evaluation/xlsx_files/test_empty_lang_cell.xlsx deleted file mode 100644 index 91cdada0..00000000 Binary files a/test/resources/evaluation/xlsx_files/test_empty_lang_cell.xlsx and /dev/null differ diff --git a/test/resources/evaluation/xlsx_files/test_empty_table.xlsx b/test/resources/evaluation/xlsx_files/test_empty_table.xlsx deleted file mode 100644 index 486b83a1..00000000 Binary files a/test/resources/evaluation/xlsx_files/test_empty_table.xlsx and /dev/null differ diff --git a/test/resources/evaluation/xlsx_files/test_java_no_version.xlsx b/test/resources/evaluation/xlsx_files/test_java_no_version.xlsx deleted file mode 100644 index d473b2cf..00000000 Binary files a/test/resources/evaluation/xlsx_files/test_java_no_version.xlsx and /dev/null differ diff --git a/test/resources/evaluation/xlsx_files/test_sorted_order.xlsx b/test/resources/evaluation/xlsx_files/test_sorted_order.xlsx deleted file mode 100644 index bfdca3b2..00000000 Binary files a/test/resources/evaluation/xlsx_files/test_sorted_order.xlsx and /dev/null differ diff --git a/test/resources/evaluation/xlsx_files/test_unsorted_order.xlsx b/test/resources/evaluation/xlsx_files/test_unsorted_order.xlsx deleted file mode 100644 index 75bc9783..00000000 Binary files a/test/resources/evaluation/xlsx_files/test_unsorted_order.xlsx and /dev/null differ diff --git a/test/resources/evaluation/xlsx_files/test_wrong_column_name.xlsx b/test/resources/evaluation/xlsx_files/test_wrong_column_name.xlsx deleted file mode 100644 index d1fc1415..00000000 Binary files a/test/resources/evaluation/xlsx_files/test_wrong_column_name.xlsx and /dev/null differ diff --git a/test/resources/evaluation/xlsx_target_files/target_sorted_order.xlsx b/test/resources/evaluation/xlsx_target_files/target_sorted_order.xlsx deleted file mode 100644 index 8cbc432f..00000000 Binary files a/test/resources/evaluation/xlsx_target_files/target_sorted_order.xlsx and /dev/null differ diff --git a/test/resources/evaluation/xlsx_target_files/target_unsorted_order.xlsx b/test/resources/evaluation/xlsx_target_files/target_unsorted_order.xlsx deleted file mode 100644 index 25ed6146..00000000 Binary files a/test/resources/evaluation/xlsx_target_files/target_unsorted_order.xlsx and /dev/null differ diff --git a/test/resources/inspectors/python/case31_spellcheck.py b/test/resources/inspectors/python/case31_spellcheck.py new file mode 100644 index 00000000..b777eb79 --- /dev/null +++ b/test/resources/inspectors/python/case31_spellcheck.py @@ -0,0 +1,3 @@ +import math + +number = math.sqrt(float(input())) diff --git a/test/resources/inspectors/python/case31_line_break.py b/test/resources/inspectors/python/case35_line_break.py similarity index 100% rename from test/resources/inspectors/python/case31_line_break.py rename to test/resources/inspectors/python/case35_line_break.py diff --git a/whitelist.txt b/whitelist.txt index 77ff8f33..0b861514 100644 --- a/whitelist.txt +++ b/whitelist.txt @@ -94,3 +94,4 @@ util Namespace case18 case34 +removeprefix