From fc4bf9ce06d8b3f0583c36fc615000aec5a42892 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Nikola=20Forr=C3=B3?= Date: Thu, 2 Nov 2023 16:39:37 +0100 Subject: [PATCH] Allow to comment out or uncomment a macro definition MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit Signed-off-by: Nikola Forró --- specfile/macro_definitions.py | 39 +++++++++++++++---------- specfile/specfile.py | 1 + tests/unit/test_macro_definitions.py | 43 ++++++++++++++++++++++------ 3 files changed, 60 insertions(+), 23 deletions(-) diff --git a/specfile/macro_definitions.py b/specfile/macro_definitions.py index 166c684..711d096 100644 --- a/specfile/macro_definitions.py +++ b/specfile/macro_definitions.py @@ -20,6 +20,7 @@ def __init__( name: str, body: str, is_global: bool, + commented_out: bool, whitespace: Tuple[str, str, str, str], valid: bool = True, preceding_lines: Optional[List[str]] = None, @@ -27,6 +28,7 @@ def __init__( self.name = name self.body = body self.is_global = is_global + self.commented_out = commented_out self._whitespace = whitespace self.valid = valid self._preceding_lines = ( @@ -40,6 +42,7 @@ def __eq__(self, other: object) -> bool: self.name == other.name and self.body == other.body and self.is_global == other.is_global + and self.commented_out == other.commented_out and self._whitespace == other._whitespace and self._preceding_lines == other._preceding_lines ) @@ -48,13 +51,15 @@ def __eq__(self, other: object) -> bool: def __repr__(self) -> str: return ( f"MacroDefinition({self.name!r}, {self.body!r}, {self.is_global!r}, " - f"{self._whitespace!r}, {self.valid!r}, {self._preceding_lines!r})" + f"{self.commented_out!r}, {self._whitespace!r}, {self.valid!r}, " + f"{self._preceding_lines!r})" ) def __str__(self) -> str: ws = self._whitespace - macro = "%global" if self.is_global else "%define" - return f"{ws[0]}{macro}{ws[1]}{self.name}{ws[2]}{self.body}{ws[3]}" + sc = "#" if self.commented_out else "%" + macro = "global" if self.is_global else "define" + return f"{ws[0]}{sc}{macro}{ws[1]}{self.name}{ws[2]}{self.body}{ws[3]}" def get_position(self, container: "MacroDefinitions") -> int: """ @@ -73,13 +78,14 @@ def get_position(self, container: "MacroDefinitions") -> int: def get_raw_data(self) -> List[str]: result = self._preceding_lines.copy() ws = self._whitespace - macro = "%global" if self.is_global else "%define" + sc = "#" if self.commented_out else "%" + macro = "global" if self.is_global else "define" body = self.body.splitlines() if body: body[-1] += ws[3] else: body = [ws[3]] - result.append(f"{ws[0]}{macro}{ws[1]}{self.name}{ws[2]}{body[0]}") + result.append(f"{ws[0]}{sc}{macro}{ws[1]}{self.name}{ws[2]}{body[0]}") result.extend(body[1:]) return result @@ -249,7 +255,8 @@ def count_brackets(s): r""" ^ (\s*) # optional preceding whitespace - (%(?:global|define)) # scope-defining macro definition + (%|\#) # starting character + (global|define) # scope-defining macro definition (\s+) (\w+(?:\(.*?\))?) # macro name with optional arguments in parentheses (\s+) @@ -267,15 +274,16 @@ def count_brackets(s): line, valid = pop(lines) m = md_regex.match(line) if m: - ws0, macro, ws1, name, ws2, body, ws3 = m.groups() - if ws3 == "\\": - body += ws3 - ws3 = "" - bc, pc = count_brackets(body) - while (bc > 0 or pc > 0 or body.endswith("\\")) and lines: - line, _ = pop(lines) - body += "\n" + line + ws0, sc, macro, ws1, name, ws2, body, ws3 = m.groups() + if sc == "%": + if ws3 == "\\": + body += ws3 + ws3 = "" bc, pc = count_brackets(body) + while (bc > 0 or pc > 0 or body.endswith("\\")) and lines: + line, _ = pop(lines) + body += "\n" + line + bc, pc = count_brackets(body) tokens = re.split(r"(\s+)$", body, maxsplit=1) if len(tokens) == 1: body = tokens[0] @@ -286,7 +294,8 @@ def count_brackets(s): MacroDefinition( name, body, - macro == "%global", + macro == "global", + sc == "#", (ws0, ws1, ws2, ws3), valid, buffer, diff --git a/specfile/specfile.py b/specfile/specfile.py index 4fd11e5..34d606d 100644 --- a/specfile/specfile.py +++ b/specfile/specfile.py @@ -730,6 +730,7 @@ class Entity: ) for md in macro_definitions if md.valid + and not md.commented_out and not protected_regex.match(md.name) and not md.name.endswith(")") # skip macro definitions with options ] diff --git a/tests/unit/test_macro_definitions.py b/tests/unit/test_macro_definitions.py index 4673ca5..43e33d4 100644 --- a/tests/unit/test_macro_definitions.py +++ b/tests/unit/test_macro_definitions.py @@ -11,15 +11,20 @@ def test_find(): macro_definitions = MacroDefinitions( [ - MacroDefinition("gitdate", "20160901", True, ("", " ", " ", "")), + MacroDefinition("gitdate", "20160901", True, False, ("", " ", " ", "")), MacroDefinition( "commit", "9ab9717cf7d1be1a85b165a8eacb71b9e5831113", True, + False, ("", " ", " ", ""), ), MacroDefinition( - "shortcommit", "%(c=%{commit}; echo ${c:0:7})", True, ("", " ", " ", "") + "shortcommit", + "%(c=%{commit}; echo ${c:0:7})", + True, + False, + ("", " ", " ", ""), ), ] ) @@ -32,15 +37,20 @@ def test_find(): def test_get(): macro_definitions = MacroDefinitions( [ - MacroDefinition("gitdate", "20160901", True, ("", " ", " ", "")), + MacroDefinition("gitdate", "20160901", True, False, ("", " ", " ", "")), MacroDefinition( "commit", "9ab9717cf7d1be1a85b165a8eacb71b9e5831113", True, + False, ("", " ", " ", ""), ), MacroDefinition( - "shortcommit", "%(c=%{commit}; echo ${c:0:7})", True, ("", " ", " ", "") + "shortcommit", + "%(c=%{commit}; echo ${c:0:7})", + True, + False, + ("", " ", " ", ""), ), ] ) @@ -59,6 +69,8 @@ def test_parse(): "%global commit 9ab9717cf7d1be1a85b165a8eacb71b9e5831113", "%global shortcommit %(c=%{commit}; echo ${c:0:7})", "", + "#global prerel beta2", + "", "Name: test", "Version: 0.1.0", "", @@ -74,8 +86,10 @@ def test_parse(): assert macro_definitions[1].name == "commit" assert macro_definitions.commit.body == "9ab9717cf7d1be1a85b165a8eacb71b9e5831113" assert macro_definitions[2].name == "shortcommit" - assert macro_definitions[3].name == "desc(x)" - assert macro_definitions[3].body == ( + assert macro_definitions[3].name == "prerel" + assert macro_definitions[3].commented_out + assert macro_definitions[4].name == "desc(x)" + assert macro_definitions[4].body == ( "Test spec file containing several \\\n" "macro definitions in various formats (%?1)" ) @@ -90,20 +104,29 @@ def test_parse(): def test_get_raw_data(): macro_definitions = MacroDefinitions( [ - MacroDefinition("gitdate", "20160901", True, ("", " ", " ", "")), + MacroDefinition("gitdate", "20160901", True, False, ("", " ", " ", "")), MacroDefinition( "commit", "9ab9717cf7d1be1a85b165a8eacb71b9e5831113", True, + False, ("", " ", " ", ""), ), MacroDefinition( - "shortcommit", "%(c=%{commit}; echo ${c:0:7})", True, ("", " ", " ", "") + "shortcommit", + "%(c=%{commit}; echo ${c:0:7})", + True, + False, + ("", " ", " ", ""), + ), + MacroDefinition( + "prerel", "beta2", True, True, ("", " ", " ", ""), True, [""] ), MacroDefinition( "desc(x)", "Test spec file containing several \\\nmacro definitions in various formats (%?1)", False, + False, ("", " ", " ", ""), True, [ @@ -119,6 +142,7 @@ def test_get_raw_data(): "This an example of a macro definition with body \n" "spawning across mutiple lines}", False, + False, ("", " ", " ", ""), True, [""], @@ -130,6 +154,8 @@ def test_get_raw_data(): "%global commit 9ab9717cf7d1be1a85b165a8eacb71b9e5831113", "%global shortcommit %(c=%{commit}; echo ${c:0:7})", "", + "#global prerel beta2", + "", "Name: test", "Version: 0.1.0", "", @@ -149,6 +175,7 @@ def test_copy_macro_definitions(): "commit", "9ab9717cf7d1be1a85b165a8eacb71b9e5831113", True, + False, ("", " ", " ", ""), ), ],