diff --git a/.printer-linter b/.printer-linter index 45b1f2c9e0..31376f4dad 100644 --- a/.printer-linter +++ b/.printer-linter @@ -2,6 +2,7 @@ checks: diagnostic-mesh-file-extension: true diagnostic-mesh-file-size: true diagnostic-definition-redundant-override: true + diagnostic-definition-experimental-setting: true diagnostic-resources-macos-app-directory-name: true diagnostic-incorrect-formula: true diagnostic-resource-file-deleted: true diff --git a/printer-linter/src/printerlinter/factory.py b/printer-linter/src/printerlinter/factory.py index 37a11d471a..fa78c7137e 100644 --- a/printer-linter/src/printerlinter/factory.py +++ b/printer-linter/src/printerlinter/factory.py @@ -14,10 +14,10 @@ def getLinter(file: Path, settings: dict) -> Optional[List[Linter]]: if not file.exists(): return [Directory(file, settings)] - if ".inst" in file.suffixes and ".cfg" in file.suffixes: + if ".inst" in file.suffixes and file.suffixes[-1] == ".cfg": return [Directory(file, settings), Profile(file, settings), Formulas(file, settings)] - if ".def" in file.suffixes and ".json" in file.suffixes: + if ".def" in file.suffixes and file.suffixes[-1] == ".json": if file.stem in ("fdmprinter.def", "fdmextruder.def"): return [Formulas(file, settings)] return [Directory(file, settings), Definition(file, settings), Formulas(file, settings)] diff --git a/printer-linter/src/printerlinter/linters/defintion.py b/printer-linter/src/printerlinter/linters/defintion.py index 2d68e20db9..a95fede55a 100644 --- a/printer-linter/src/printerlinter/linters/defintion.py +++ b/printer-linter/src/printerlinter/linters/defintion.py @@ -13,8 +13,11 @@ class Definition(Linter): def __init__(self, file: Path, settings: dict) -> None: super().__init__(file, settings) self._definitions = {} + self._definition_name = None + self._experimental_settings = [] self._loadDefinitionFiles(file) self._content = self._file.read_text() + self._loadExperimentalSettings() self._loadBasePrinterSettings() @property @@ -32,6 +35,10 @@ class Definition(Linter): for check in self.checkMaterialTemperature(): yield check + if self._settings["checks"].get("diagnostic-definition-experimental-setting", False): + for check in self.checkExperimentalSetting(): + yield check + # Add other which will yield Diagnostic's # TODO: A check to determine if the user set value is with the min and max value defined in the parent and doesn't trigger a warning # TODO: A check if the key exist in the first place @@ -41,9 +48,8 @@ class Definition(Linter): def checkRedefineOverride(self) -> Iterator[Diagnostic]: """ Checks if definition file overrides its parents settings with the same value. """ - definition_name = list(self._definitions.keys())[0] - definition = self._definitions[definition_name] - if "overrides" in definition and definition_name not in ("fdmprinter", "fdmextruder"): + definition = self._definitions[self._definition_name] + if "overrides" in definition and self._definition_name not in ("fdmprinter", "fdmextruder"): for key, value_dict in definition["overrides"].items(): is_redefined, child_key, child_value, parent, inherited_by= self._isDefinedInParent(key, value_dict, definition['inherits']) if is_redefined: @@ -71,9 +77,8 @@ class Definition(Linter): def checkMaterialTemperature(self) -> Iterator[Diagnostic]: """Checks if definition file has material tremperature defined within them""" - definition_name = list(self._definitions.keys())[0] - definition = self._definitions[definition_name] - if "overrides" in definition and definition_name not in ("fdmprinter", "fdmextruder"): + definition = self._definitions[self._definition_name] + if "overrides" in definition and self._definition_name not in ("fdmprinter", "fdmextruder"): for key, value_dict in definition["overrides"].items(): if "temperature" in key and "material" in key: @@ -97,6 +102,22 @@ class Definition(Linter): replacements=replacements ) + def checkExperimentalSetting(self) -> Iterator[Diagnostic]: + """Checks if definition uses experimental settings""" + definition = self._definitions[self._definition_name] + if "overrides" in definition and self._definition_name not in ("fdmprinter", "fdmextruder"): + for setting in definition["overrides"]: + if setting in self._experimental_settings: + redefined = re.compile(setting) + found = redefined.search(self._content) + yield Diagnostic( + file=self._file, + diagnostic_name="diagnostic-definition-experimental-setting", + message=f"Setting {setting} is still experimental and should not be used in default profiles", + level="Warning", + offset=found.span(0)[0] + ) + def _loadDefinitionFiles(self, definition_file) -> None: """ Loads definition file contents into self._definitions. Also load parent definition if it exists. """ definition_name = Path(definition_file.stem).stem @@ -104,6 +125,9 @@ class Definition(Linter): if not definition_file.exists() or definition_name in self._definitions: return + if self._definition_name is None: + self._definition_name = definition_name + # Load definition file into dictionary self._definitions[definition_name] = json.loads(definition_file.read_text()) @@ -152,6 +176,12 @@ class Definition(Linter): return self._isDefinedInParent(key, value_dict, parent["inherits"]) return False, None, None, None, None + def _loadExperimentalSettings(self): + try: + self._experimental_settings = self._definitions[self.base_def]["settings"]["experimental"]["children"].keys() + except: + pass + def _loadBasePrinterSettings(self): settings = {} for k, v in self._definitions[self.base_def]["settings"].items(): diff --git a/printer-linter/src/printerlinter/linters/formulas.py b/printer-linter/src/printerlinter/linters/formulas.py index ad5b7ee943..aa31619678 100644 --- a/printer-linter/src/printerlinter/linters/formulas.py +++ b/printer-linter/src/printerlinter/linters/formulas.py @@ -146,12 +146,13 @@ class Formulas(Linter): available_sections = ["values"] for section in available_sections: - options = config.options(section) - for option in options: - values ={} - values["value"] = config.get(section, option) - overrides[option] = values - file_data["overrides"]= overrides# Process the value here + if config.has_section(section): + options = config.options(section) + for option in options: + values ={} + values["value"] = config.get(section, option) + overrides[option] = values + file_data["overrides"]= overrides# Process the value here return file_data diff --git a/printer-linter/src/printerlinter/linters/profile.py b/printer-linter/src/printerlinter/linters/profile.py index 4ca3ded964..347b0fbe90 100644 --- a/printer-linter/src/printerlinter/linters/profile.py +++ b/printer-linter/src/printerlinter/linters/profile.py @@ -37,6 +37,6 @@ class Profile(Linter): config = ConfigParser() config.read([self._file]) name_of_profile = config.get("general", "name") - redefined = re.compile(name_of_profile) + redefined = re.compile(re.escape(name_of_profile)) found = redefined.search(self._content) return name_of_profile, found