doc: obey SOURCE_DATE_EPOCH with manpage generation

Previously if a cobra user didn't specify an explicit .Date header, the
current time would be included in all of the generated man pages each
time they were built. This causes an issue for reproducible builds,
since each re-build of a package that includes the man pages will have
different times listed in the man pages.

To fix this, add support for SOURCE_DATE_EPOCH (which is a standardised
packaging environment variable, designed to be used specifically for
this purpose[1]).

[1]: https://reproducible-builds.org/specs/source-date-epoch/

Signed-off-by: Aleksa Sarai <asarai@suse.de>
This commit is contained in:
Aleksa Sarai 2018-08-23 21:31:44 +10:00
parent 6fd8e29b07
commit 29e3a0992f
No known key found for this signature in database
GPG key ID: 9E18AA267DDB8DB4

View file

@ -20,6 +20,7 @@ import (
"os" "os"
"path/filepath" "path/filepath"
"sort" "sort"
"strconv"
"strings" "strings"
"time" "time"
@ -104,14 +105,16 @@ func GenMan(cmd *cobra.Command, header *GenManHeader, w io.Writer) error {
if header == nil { if header == nil {
header = &GenManHeader{} header = &GenManHeader{}
} }
fillHeader(header, cmd.CommandPath()) if err := fillHeader(header, cmd.CommandPath()); err != nil {
return err
}
b := genMan(cmd, header) b := genMan(cmd, header)
_, err := w.Write(md2man.Render(b)) _, err := w.Write(md2man.Render(b))
return err return err
} }
func fillHeader(header *GenManHeader, name string) { func fillHeader(header *GenManHeader, name string) error {
if header.Title == "" { if header.Title == "" {
header.Title = strings.ToUpper(strings.Replace(name, " ", "\\-", -1)) header.Title = strings.ToUpper(strings.Replace(name, " ", "\\-", -1))
} }
@ -120,12 +123,20 @@ func fillHeader(header *GenManHeader, name string) {
} }
if header.Date == nil { if header.Date == nil {
now := time.Now() now := time.Now()
if epoch := os.Getenv("SOURCE_DATE_EPOCH"); epoch != "" {
unixEpoch, err := strconv.ParseInt(epoch, 10, 64)
if err != nil {
return fmt.Errorf("invalid SOURCE_DATE_EPOCH: %v", err)
}
now = time.Unix(unixEpoch, 0)
}
header.Date = &now header.Date = &now
} }
header.date = (*header.Date).Format("Jan 2006") header.date = (*header.Date).Format("Jan 2006")
if header.Source == "" { if header.Source == "" {
header.Source = "Auto generated by spf13/cobra" header.Source = "Auto generated by spf13/cobra"
} }
return nil
} }
func manPreamble(buf *bytes.Buffer, header *GenManHeader, cmd *cobra.Command, dashedName string) { func manPreamble(buf *bytes.Buffer, header *GenManHeader, cmd *cobra.Command, dashedName string) {