Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

feat: add initial support for source RPMs #3412

Draft
wants to merge 1 commit into
base: main
Choose a base branch
from

Conversation

twpayne
Copy link
Contributor

@twpayne twpayne commented Sep 28, 2022

This PR adds support for generating source RPMs, fixing #3136.

Firstly, thank you for the excellent architecture in goreleaser! It was much easier to add this initial functionality than I expected.

This PR is not ready for merge yet, but is in reasonable shape, and ready for expert input:

  • It generates reasonable .src.rpm files that seem to have the correct contents.
  • the .spec file is configurable.
  • it seems to integrate well with goreleaser's architecture.

There are a certainly missing features:

  • more thorough tests
  • documentation

There are a number of unanswered questions:

  • does this integrate with goreleaser correctly?
  • right now, this PR uses google/rpmpack directly instead of goreleaser/nfpm; should it use goreleaser/nfpm instead?
  • what, exactly should the spec file template look like? I tried to follow Fedora's guidelines on .spec files for Go projects but still have many questions, especially as we're distributing source RPMs that build final binaries and don't want to create packages for every single dependency.

All feedback very welcome!

closes #3136

@pull-request-size pull-request-size bot added the size/L Denotes a PR that changes 100-499 lines, ignoring generated files. label Sep 28, 2022
@twpayne
Copy link
Contributor Author

twpayne commented Sep 28, 2022

The CI failure looks like grype had some kind of internal failure unrelated to this PR. This PR does not change the project's dependencies apart from promoting an indirect dependency on github.com/google/rpmpack to a direct dependency.

@codecov
Copy link

codecov bot commented Sep 28, 2022

Codecov Report

Attention: 42 lines in your changes are missing coverage. Please review.

Comparison is base (5d44ed1) 83.75% compared to head (80fd5c8) 83.66%.
Report is 1 commits behind head on main.

Files Patch % Lines
internal/pipe/srpm/srpm.go 79.56% 25 Missing and 13 partials ⚠️
internal/artifact/artifact.go 0.00% 4 Missing ⚠️
Additional details and impacted files
@@            Coverage Diff             @@
##             main    #3412      +/-   ##
==========================================
- Coverage   83.75%   83.66%   -0.09%     
==========================================
  Files         135      136       +1     
  Lines       12919    13109     +190     
==========================================
+ Hits        10820    10968     +148     
- Misses       1671     1700      +29     
- Partials      428      441      +13     

☔ View full report in Codecov by Sentry.
📢 Have feedback on the report? Share it here.

@caarlos0
Copy link
Member

The CI failure looks like grype had some kind of internal failure unrelated to this PR. This PR does not change the project's dependencies apart from promoting an indirect dependency on github.com/google/rpmpack to a direct dependency.

yes, it checks for vulns... and turns out that go's base image has as couple of them 👀

@caarlos0
Copy link
Member

caarlos0 commented Sep 28, 2022

I think we should be able to use nfpm itself to create the source rpms, as, afaik (and pls correct me if I'm wrong), are regular rpms with some different files in different places and (maybe) extra metadata?

if there are options missing for that on nfpm, we can certainly add those there.

the rpmpack thingy also can become an issue as we are using an internal fork of it in newer versions of nfpm cc/ @goreleaser/nfpm

@caarlos0
Copy link
Member

oh, and most importantly, thanks for the PR! 💜

@twpayne
Copy link
Contributor Author

twpayne commented Sep 28, 2022

Thanks for the feedback! I've updated the PR to use goreleaser/nfpm/v2. I'm reasonably sure that all the required functionality is already present.

I still need to find out exactly what the spec file should look like, so spec.tmpl is still a work in progress.

@caarlos0
Copy link
Member

caarlos0 commented Sep 28, 2022

awesome @twpayne! I don't know how srpms spec files work either, but I'll study about them when I can

@twpayne
Copy link
Contributor Author

twpayne commented Sep 28, 2022

I think the tricky bits with the .spec file will be:

  • The guidelines for .spec files vary from distribution to distribution. I've started by following the Fedora guidelines, but there's a lot of variation.
  • It contains commands to build the project from source, which means in theory reproducing logic from the builds: section of GoReleaser's config.
  • Some distributions (including Fedora) prefer that every single dependency (i.e. each line in go.mod) to be its own package and for the final package to depend on all of these. I think it's OK to ignore this for now.
  • As an eventual inconsistency, the RPMs built by goreleaser will not be the same as the RPMs built from source RPMs built be goreleaser, but I also think this is OK.

The current approach in this PR is to provide a basic default template that should be OK for simple projects, but leave the option for the user to specify their own .spec file template if needed. I suspect that we'll need to add the option to read the .spec file template from a file (as opposed to having it inline in .goreleaser.yaml) as the template will be quite large.

For the record, I won't have much time to work on this for the next ten days or so, but am keen to get good source RPM support added to goreleaser :)

@caarlos0
Copy link
Member

caarlos0 commented Sep 29, 2022

but leave the option for the user to specify their own .spec file template if needed

yes, I think this is the important bit... so users that need more/different stuff can write their spec files themselves, and still use templates for things like version, hashes, etc..

I suspect that we'll need to add the option to read the .spec file template from a file (as opposed to having it inline in .goreleaser.yaml) as the template will be quite large.

yes, probably a good idea as well

For the record, I won't have much time to work on this for the next ten days or so, but am keen to get good source RPM support added to goreleaser :)

same here! will be more offline for a couple of days next week, so if I take too long to reply its probably because of that! Any way, I'm excited to get this into goreleaser as well, if posssible on v1.12.0 or v1.13.0 (next minors) 🤘 (EDIT: no pressure whatsoever, if it is not ready by then its totally fine, and of course I'll help whenever I can 🙏)

@caarlos0
Copy link
Member

hey! anything I could help with here?

@twpayne
Copy link
Contributor Author

twpayne commented Jun 14, 2023

Sorry, I haven't looked at this in a while. I think the code is correct, but it needs testing. I won't have time to look at this again for several weeks, so feel free to close this if the feature is not needed.

@caarlos0
Copy link
Member

hey, no problem, I'll see if I find some time, or worst case, we look at it together in a couple of weeks

thanks for the heads up and the PR 💜

@frzifus
Copy link

frzifus commented Jan 17, 2024

Hi @twpayne @caarlos0, looks like a great PR so far, thanks! Is there something I can do to support you?

@twpayne
Copy link
Contributor Author

twpayne commented Jan 17, 2024

I've not looked at this for a while. I've just re-pushed to resolve conflicts.

@frzifus if you'd like to help, there are a few areas:

  • Testing. Firstly, does the .src.rpm file generated by this pipe actually work? What changes are needed to the .spec template?
  • Is the pipeline written correctly? The PR was opened over a year ago, and goreleaser's core architecture has evolved since (e.g. how skips are handled). Are there other changes needed?
  • internal/pipe/srpm/srpm.go has a few FIXME/TODO comments, mainly missing fields in structures. It would be great if you could have a look at these.

@frzifus
Copy link

frzifus commented Jan 17, 2024

Thanks, I will come back to you asap. I will try to generate a spec/srpm using go2rpm first. Then Ive something to compare.


// Run the pipe.
func (Pipe) Run(ctx *context.Context) error {
sourceArchives := ctx.Artifacts.Filter(artifact.ByType(artifact.UploadableSourceArchive)).List()
Copy link

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Seems the result for me here is always nil. But I expect my test config might be wrong?

May I ask, do you have a config that you used for testing? :)

Here is what I used so far
---
version: 1

env:
  - GO111MODULE=on

before:
  hooks:
    - go mod tidy

gomod:
  proxy: true

report_sizes: true

git:
  ignore_tags:
    - "{{ if not .IsNightly }}nightly{{ end }}"

metadata:
  mod_timestamp: "{{ .CommitTimestamp }}"

builds:
  - env:
      - CGO_ENABLED=0
    goos:
      - linux
    goarch:
      - amd64
    mod_timestamp: "{{ .CommitTimestamp }}"
    main: ./cmd/vlookup/main.go
    flags:
      - -trimpath
    ldflags:
      - -s -w -X main.version={{.Version}} -X main.commit={{.Commit}} -X main.date={{ .CommitDate }} -X main.builtBy=goreleaser -X main.treeState={{ .IsGitDirty }}

universal_binaries:
  - replace: false

checksum:
  name_template: "checksums.txt"

srpm:

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I've not run the code in this PR for a long time. I think you need to build a source archive, something like:

source:
  enabled: true
  prefix_template: '{{ .ProjectName }}-{{ .Version }}/'

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
enhancement New feature or request size/L Denotes a PR that changes 100-499 lines, ignoring generated files.
Projects
None yet
Development

Successfully merging this pull request may close these issues.

Generate source RPMs
3 participants