Skip to content

Commit 1771691

Browse files
committed
feat(spec): preserve referenced macros during removal
1 parent bbe0fcf commit 1771691

7 files changed

Lines changed: 2027 additions & 0 deletions

internal/rpm/spec/structural_tree_api.go

Lines changed: 4 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -183,6 +183,10 @@ func (t *specTree) RemoveSections(handles []*sectionHandle) error {
183183
return err
184184
}
185185

186+
if err := t.hoistReferencedMacros(sections); err != nil {
187+
return err
188+
}
189+
186190
removeSections(t.root, sections)
187191

188192
return nil
Lines changed: 39 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,39 @@
1+
Name: subpackage-define-referenced
2+
Version: 1.0
3+
Release: 1
4+
Summary: %%define inside a subpackage referenced from %%install (issue #203 repro)
5+
License: MIT
6+
7+
%description
8+
Fixture mirroring issue #203 -- the helper macro is defined inside the
9+
test subpackage but referenced from the unconditional install section.
10+
Removing the subpackage naively drops the macro and leaves dangling
11+
references in surviving sections.
12+
13+
%package tests
14+
Summary: Tests for %{name}
15+
Requires: %{name} = %{version}-%{release}
16+
17+
%define testsdir %{_libdir}/%{name}/tests-src
18+
19+
%description tests
20+
The %{name}-tests rpm contains test fixtures for %{name}.
21+
22+
%files tests
23+
%{testsdir}
24+
25+
%build
26+
make
27+
28+
%install
29+
make install DESTDIR=%{buildroot}
30+
mkdir -p %{buildroot}%{testsdir}/python
31+
mkdir -p %{buildroot}%{testsdir}/scripts
32+
install -p -m 0644 tests/Makefile.include %{buildroot}%{testsdir}/
33+
34+
%files
35+
/usr/bin/subpackage-define-referenced
36+
37+
%changelog
38+
* Thu Jan 01 1970 Builder <builder@example.com> - 1.0-1
39+
- Initial fixture.
Lines changed: 33 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,33 @@
1+
Name: subpackage-define-shadowed
2+
Version: 1.0
3+
Release: 1
4+
Summary: Subpackage %%define overrides a surviving preamble macro
5+
License: MIT
6+
7+
%global toolsdir %{_libdir}/%{name}
8+
9+
%description
10+
Fixture verifying that a subpackage %%define whose name already has a
11+
surviving definition in the preamble is hoisted when it is the exact effective
12+
binding of the surviving %%install reference.
13+
14+
%package tools
15+
Summary: Tools for %{name}
16+
17+
%global toolsdir %{_libdir}/%{name}/tools-override
18+
19+
%description tools
20+
Tools for %{name}.
21+
22+
%files tools
23+
%{toolsdir}
24+
25+
%install
26+
mkdir -p %{buildroot}%{toolsdir}
27+
28+
%files
29+
/usr/bin/subpackage-define-shadowed
30+
31+
%changelog
32+
* Thu Jan 01 1970 Builder <builder@example.com> - 1.0-1
33+
- Initial fixture.
Lines changed: 38 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,38 @@
1+
Name: subpackage-define-transitive
2+
Version: 1.0
3+
Release: 1
4+
Summary: Transitive %%define chain inside a subpackage (issue #203 follow-up)
5+
License: MIT
6+
7+
%description
8+
Fixture for the transitive macro-hoisting case: the subpackage defines a
9+
chain of helper macros (%%testroot -> %%testsdir) and only the outer one is
10+
referenced from the surviving %%install section. Removing the subpackage must
11+
hoist BOTH macros so the survivor reference resolves.
12+
13+
%package tests
14+
Summary: Tests for %{name}
15+
Requires: %{name} = %{version}-%{release}
16+
17+
%define testroot %{_libdir}/%{name}
18+
%define testsdir %{testroot}/tests-src
19+
20+
%description tests
21+
The %{name}-tests rpm contains test fixtures for %{name}.
22+
23+
%files tests
24+
%{testsdir}
25+
26+
%build
27+
make
28+
29+
%install
30+
make install DESTDIR=%{buildroot}
31+
mkdir -p %{buildroot}%{testsdir}/python
32+
33+
%files
34+
/usr/bin/subpackage-define-transitive
35+
36+
%changelog
37+
* Thu Jan 01 1970 Builder <builder@example.com> - 1.0-1
38+
- Initial fixture.

internal/rpm/spec/testdata_test.go

Lines changed: 35 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -196,6 +196,41 @@ func TestStructuralParserFixtureSearchAndReplaceCoversLineTypes(t *testing.T) {
196196
assertReparseable(t, contents)
197197
}
198198

199+
func TestStructuralParserFixtureSubpackageMacroRemovalHoistsReferencedDefinitions(t *testing.T) {
200+
for _, name := range []string{
201+
"subpackage-define-referenced.spec",
202+
"subpackage-define-transitive.spec",
203+
"subpackage-define-shadowed.spec",
204+
} {
205+
t.Run(name, func(t *testing.T) {
206+
specification := openFixture(t, name)
207+
require.NoError(t, specification.RemoveSubpackage(
208+
map[string]string{
209+
"subpackage-define-referenced.spec": "tests",
210+
"subpackage-define-transitive.spec": "tests",
211+
"subpackage-define-shadowed.spec": "tools",
212+
}[name],
213+
))
214+
215+
contents := serializeFixture(t, specification)
216+
assertReparseable(t, contents)
217+
218+
switch name {
219+
case "subpackage-define-referenced.spec":
220+
assert.Contains(t, contents, "%define testsdir %{_libdir}/%{name}/tests-src")
221+
assert.Less(t, strings.LastIndex(contents, "%define testsdir"), strings.Index(contents, "\n%install\n"))
222+
case "subpackage-define-transitive.spec":
223+
assert.Less(t, strings.Index(contents, "%define testroot"), strings.Index(contents, "%define testsdir"))
224+
assert.Contains(t, contents, "%define testsdir %{testroot}/tests-src")
225+
case "subpackage-define-shadowed.spec":
226+
assert.Equal(t, 2, strings.Count(contents, "%global toolsdir"))
227+
assert.Contains(t, contents, "tools-override")
228+
assert.Less(t, strings.LastIndex(contents, "%global toolsdir"), strings.Index(contents, "\n%install\n"))
229+
}
230+
})
231+
}
232+
}
233+
199234
func TestStructuralParserGDBShapedMacroBodyIsOpaqueKnownLimitation(t *testing.T) {
200235
input := `%define gdb_python_configure \
201236
%if 0%{?with_python}\

0 commit comments

Comments
 (0)