Repository: goreleaser/nfpm
Pull request #788 (2024-02-21 17:27:07)

feat(rpm): add support for verify scriptlet
RPM allows users to add custom verify scriptlets that are run by `rpm -V` in addition to the normal checksum validation. This is useful when there are additional factors that indicate a valid installation, like, for example, checking for valid contents of configuration files.

codecov[bot]: ## [Codecov](https://app.codecov.io/gh/goreleaser/nfpm/pull/788?src=pr&el=h1&utm_medium=referral&utm_source=github&utm_content=comment&utm_campaign=pr+comments&utm_term=goreleaser) Report
Attention: `2 lines` in your changes are missing coverage. Please review.
> Comparison is base [(`0b1bc17`)](https://app.codecov.io/gh/goreleaser/nfpm/commit/0b1bc17d46c53329aeb44562f26d20d2458e996e?el=desc&utm_medium=referral&utm_source=github&utm_content=comment&utm_campaign=pr+comments&utm_term=goreleaser) 72.10% compared to head [(`396e252`)](https://app.codecov.io/gh/goreleaser/nfpm/pull/788?src=pr&el=desc&utm_medium=referral&utm_source=github&utm_content=comment&utm_campaign=pr+comments&utm_term=goreleaser) 72.07%.

| [Files](https://app.codecov.io/gh/goreleaser/nfpm/pull/788?src=pr&el=tree&utm_medium=referral&utm_source=github&utm_content=comment&utm_campaign=pr+comments&utm_term=goreleaser) | Patch % | Lines |
|---|---|---|
| [rpm/rpm.go](https://app.codecov.io/gh/goreleaser/nfpm/pull/788?src=pr&el=tree&utm_medium=referral&utm_source=github&utm_content=comment&utm_campaign=pr+comments&utm_term=goreleaser#diff-cnBtL3JwbS5nbw==) | 60.00% | [1 Missing and 1 partial :warning: ](https://app.codecov.io/gh/goreleaser/nfpm/pull/788?src=pr&el=tree&utm_medium=referral&utm_source=github&utm_content=comment&utm_campaign=pr+comments&utm_term=goreleaser) |

<details><summary>Additional details and impacted files</summary>


```diff
@@            Coverage Diff             @@
##             main     #788      +/-   ##
==========================================
- Coverage   72.10%   72.07%   -0.03%     
==========================================
  Files          20       20              
  Lines        2201     2206       +5     
==========================================
+ Hits         1587     1590       +3     
- Misses        434      435       +1     
- Partials      180      181       +1     
```



</details>

[:umbrella: View full report in Codecov by Sentry](https://app.codecov.io/gh/goreleaser/nfpm/pull/788?src=pr&el=continue&utm_medium=referral&utm_source=github&utm_content=comment&utm_campaign=pr+comments&utm_term=goreleaser).   
:loudspeaker: Have feedback on the report? [Share it here](https://about.codecov.io/codecov-pr-comment-feedback/?utm_medium=referral&utm_source=github&utm_content=comment&utm_campaign=pr+comments&utm_term=goreleaser).


Patch:
diff --git a/nfpm.go b/nfpm.go
index 06e30d4..62c9a1a 100644
--- a/nfpm.go
+++ b/nfpm.go
@@ -362,6 +362,7 @@ type RPM struct {
 type RPMScripts struct {
 	PreTrans  string `yaml:"pretrans,omitempty" json:"pretrans,omitempty" jsonschema:"title=pretrans script"`
 	PostTrans string `yaml:"posttrans,omitempty" json:"posttrans,omitempty" jsonschema:"title=posttrans script"`
+	Verify    string `yaml:"verify,omitempty" json:"verify,omitempty" jsonschema:"title=verify script"`
 }
 
 type PackageSignature struct {
diff --git a/rpm/rpm.go b/rpm/rpm.go
index f533f54..8dfed1a 100644
--- a/rpm/rpm.go
+++ b/rpm/rpm.go
@@ -342,6 +342,14 @@ func addScriptFiles(info *nfpm.Info, rpm *rpmpack.RPM) error {
 		rpm.AddPosttrans(string(data))
 	}
 
+	if info.RPM.Scripts.Verify != "" {
+		data, err := os.ReadFile(info.RPM.Scripts.Verify)
+		if err != nil {
+			return err
+		}
+		rpm.AddVerifyScript(string(data))
+	}
+
 	return nil
 }
 
diff --git a/www/docs/configuration.md b/www/docs/configuration.md
index b7abfbf..5fd8912 100644
--- a/www/docs/configuration.md
+++ b/www/docs/configuration.md
@@ -322,6 +322,8 @@ rpm:
     pretrans: ./scripts/pretrans.sh
     # The posttrans script runs after all RPM package transactions / stages.
     posttrans: ./scripts/posttrans.sh
+    # The verify script runs when verifying packages using `rpm -V`.
+    verify: ./scripts/verify.sh
 
   # The package group. This option is deprecated by most distros
   # but required by old distros like CentOS 5 / EL 5 and earlier.
diff --git a/www/docs/static/schema.json b/www/docs/static/schema.json
index b459eb8..ea21881 100644
--- a/www/docs/static/schema.json
+++ b/www/docs/static/schema.json
@@ -719,6 +719,10 @@
 					"posttrans": {
 						"type": "string",
 						"title": "posttrans script"
+					},
+					"verify": {
+						"type": "string",
+						"title": "verify script"
 					}
 				},
 				"additionalProperties": false,
@@ -768,4 +772,4 @@
 			}
 		},
 		"description": "nFPM configuration definition file"
-	}
\ No newline at end of file
+	}


Test patch:
diff --git a/acceptance_test.go b/acceptance_test.go
index bbb5459..02796fc 100644
--- a/acceptance_test.go
+++ b/acceptance_test.go
@@ -202,6 +202,7 @@ func TestRPMSpecific(t *testing.T) {
 	testNames := []string{
 		"release",
 		"directories",
+		"verify",
 	}
 	for _, name := range testNames {
 		for _, arch := range formatArchs[format] {
diff --git a/rpm/rpm_test.go b/rpm/rpm_test.go
index 60fa1f5..9af8cc6 100644
--- a/rpm/rpm_test.go
+++ b/rpm/rpm_test.go
@@ -82,6 +82,7 @@ func exampleInfo() *nfpm.Info {
 				Scripts: nfpm.RPMScripts{
 					PreTrans:  "../testdata/scripts/pretrans.sh",
 					PostTrans: "../testdata/scripts/posttrans.sh",
+					Verify:    "../testdata/scripts/verify.sh",
 				},
 			},
 		},
@@ -481,6 +482,13 @@ echo "Pretrans" > /dev/null
 
 echo "Posttrans" > /dev/null
 `, data, "Posttrans script does not match")
+
+	data, err = rpm.Header.GetString(rpmutils.VERIFYSCRIPT)
+	require.NoError(t, err)
+	require.Equal(t, `#!/bin/bash
+
+echo "Verify" > /dev/null
+`, data, "Verify script does not match")
 }
 
 func TestRPMFileDoesNotExist(t *testing.T) {
diff --git a/testdata/acceptance/core.complex.yaml b/testdata/acceptance/core.complex.yaml
index 76330fc..a100bbf 100644
--- a/testdata/acceptance/core.complex.yaml
+++ b/testdata/acceptance/core.complex.yaml
@@ -72,6 +72,7 @@ rpm:
   scripts:
     pretrans: ./testdata/acceptance/scripts/pretrans.sh
     posttrans: ./testdata/acceptance/scripts/posttrans.sh
+    verify: ./testdata/acceptance/scripts/verify.sh
 apk:
   scripts:
     preupgrade: ./testdata/acceptance/scripts/preupgrade.sh
diff --git a/testdata/acceptance/rpm.dockerfile b/testdata/acceptance/rpm.dockerfile
index 1c64be2..496d9f3 100644
--- a/testdata/acceptance/rpm.dockerfile
+++ b/testdata/acceptance/rpm.dockerfile
@@ -220,3 +220,9 @@ RUN test ! -f /etc/bar/file
 RUN test -d /etc/foo
 RUN test ! -d /etc/bar
 RUN test ! -d /etc/baz
+
+# ---- verify test ----
+FROM min as verify
+RUN rpm -V foo
+RUN rm /tmp/postinstall-proof
+RUN ! rpm -V foo
diff --git a/testdata/acceptance/rpm.verify.yaml b/testdata/acceptance/rpm.verify.yaml
new file mode 100644
index 0000000..1b4435c
--- /dev/null
+++ b/testdata/acceptance/rpm.verify.yaml
@@ -0,0 +1,20 @@
+name: "foo"
+arch: "${BUILD_ARCH}"
+platform: "linux"
+version: "v1.2.3"
+maintainer: "Foo Bar"
+release: "4"
+description: |
+  Foo bar
+    Multiple lines
+vendor: "foobar"
+homepage: "https://foobar.org"
+license: "MIT"
+contents:
+  - src: ./testdata/fake
+    dst: /etc/foo/file
+scripts:
+  postinstall: ./testdata/acceptance/scripts/postinstall.sh
+rpm:
+  scripts:
+    verify: ./testdata/acceptance/scripts/verify.sh
diff --git a/testdata/acceptance/scripts/verify.sh b/testdata/acceptance/scripts/verify.sh
new file mode 100644
index 0000000..a10d8b5
--- /dev/null
+++ b/testdata/acceptance/scripts/verify.sh
@@ -0,0 +1,3 @@
+#!/bin/sh
+
+test -e /tmp/postinstall-proof
diff --git a/testdata/scripts/verify.sh b/testdata/scripts/verify.sh
new file mode 100644
index 0000000..d935d4d
--- /dev/null
+++ b/testdata/scripts/verify.sh
@@ -0,0 +1,3 @@
+#!/bin/bash
+
+echo "Verify" > /dev/null