Skip to content

Commit b504643

Browse files
committed
Implement Sections.get_or_create()
Signed-off-by: Nikola Forró <[email protected]>
1 parent ecdb644 commit b504643

File tree

2 files changed

+73
-0
lines changed

2 files changed

+73
-0
lines changed

specfile/sections.py

Lines changed: 32 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -214,6 +214,38 @@ def find(self, id: str) -> int:
214214
return i
215215
raise ValueError
216216

217+
def get_or_create(self, id: str) -> Section:
218+
"""
219+
Gets an existing section by ID or creates a new section with the given ID.
220+
New section will be appended to the end.
221+
222+
Args:
223+
id: ID of the section (name and options, without the leading '%').
224+
225+
Returns:
226+
Existing or newly created section as an instance of `Section` class.
227+
"""
228+
229+
def split_id(id):
230+
separator = "\n"
231+
tokens = re.split(r"(\s+)", id)
232+
if len(tokens) > 2:
233+
name = tokens[0]
234+
delimiter = tokens[1]
235+
options = Options(
236+
Options.tokenize("".join(tokens[2:])),
237+
SECTION_OPTIONS.get(name.lower()),
238+
)
239+
return name, options, delimiter, separator
240+
return tokens[0], None, "", separator
241+
242+
try:
243+
section = self.get(id)
244+
except (ValueError, KeyError):
245+
section = Section(*split_id(id))
246+
self.data.append(section)
247+
return section
248+
217249
@classmethod
218250
def parse(
219251
cls, lines: List[str], context: Optional["Specfile"] = None

tests/unit/test_sections.py

Lines changed: 41 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -39,6 +39,47 @@ def test_get():
3939
sections.get("package foo")
4040

4141

42+
@pytest.mark.parametrize(
43+
"id, existing, name, options, content",
44+
[
45+
(
46+
"package",
47+
True,
48+
"package",
49+
"",
50+
["Name: test", "Version: 0.1", "Release: 1%{?dist}", ""],
51+
),
52+
("prep", True, "prep", "", ["%autosetup", ""]),
53+
("package -n subpkg1", True, "package", "-n subpkg1", [""]),
54+
("package -n subpkg2", False, "package", "-n subpkg2", []),
55+
],
56+
)
57+
def test_get_or_create(id, existing, name, options, content):
58+
sections = Sections.parse(
59+
[
60+
"Name: test",
61+
"Version: 0.1",
62+
"Release: 1%{?dist}",
63+
"",
64+
"%description",
65+
"Test package",
66+
"",
67+
"%prep",
68+
"%autosetup",
69+
"",
70+
"%package -n subpkg1",
71+
"",
72+
"%changelog",
73+
]
74+
)
75+
section = sections.get_or_create(id)
76+
assert section.name == name
77+
assert str(section.options) == options
78+
assert list(section) == content
79+
if not existing:
80+
assert section == sections[-1]
81+
82+
4283
def test_parse():
4384
sections = Sections.parse(
4485
[

0 commit comments

Comments
 (0)