AGWA / git-crypt

Transparent file encryption in git
https://www.agwa.name/projects/git-crypt/
GNU General Public License v3.0
8.11k stars 472 forks source link

[CI/CD] Add github actions to build windows & linux executables #227

Closed thebino closed 2 years ago

thebino commented 3 years ago

I created github actions to automate builds for windows and linux. It will be triggered on each change

on:
  push:

or pull request

on:
  pull_request:

If the branch or tag contains release, a new release draft will be created.

      - name: Create Release
        if: contains(github.ref, 'release')
        id: create_release
        with:
          draft: true

Since it creates only a draft, the release needs to be published by the owner or a maintainer manually.

Build outputs will be added to this release draft as a zip file.

      - name: Upload Release Asset
        if: contains(github.ref, 'release')
thebino commented 3 years ago

This mostly looks good, but since both workflows serve the same function and have all the same triggers I would suggest combining them into one workflow with two jobs (and failfast disabled) rather than two workflows.

It only looks like the same, but they are using different host systems. So no cross-compiling is necessary.

alerque commented 3 years ago

It only looks like the same, but they are using different host systems. So no cross-compiling is necessary.

I wasn't suggesting cross compiling. The runs-on: key used to specify hosts is per job not per workflow. You can have multiple jobs running on their respective hosts under one workflow.

Perhaps you confused ‘jobs’ with ‘steps’? I didn't mean trying to do this all in one job with steps for each platform.

thebino commented 3 years ago

It only looks like the same, but they are using different host systems. So no cross-compiling is necessary.

I wasn't suggesting cross compiling. The runs-on: key used to specify hosts is per job not per workflow. You can have multiple jobs running on their respective hosts under one workflow.

Perhaps you confused ‘jobs’ with ‘steps’? I didn't mean trying to do this all in one job with steps for each platform.

Ah, true. But separate workflows leverage releasing for a single platform. I don't see any real benefit from merging them into one single file. But I don't mind doing it anyway.

alerque commented 3 years ago

In my opinion releasing should always be done for all platforms in tandem. Even a patch release for a bugfix or packaging snafu that only substantively affects one platform should be released for all platforms because otherwise the "latest version" is messed up on GitHub, Repology, and across dozens of distros. It confuses users, and frustrates/annoys upstream devs and packagers. It's easier to bump a patch release than deal with user complains about not having the latest version even if it wouldn't actually affect them.

thebino commented 3 years ago

I agree, just merged the actions into one single file.

thebino commented 3 years ago

@alerque Would be great to get another review. Anything to improve?

miso-belica commented 2 years ago

It would be really awesome to have this one merged and initial v0.6.0 with attached EXE released here on GitHub. There are various ports that do that but if this is done here, automatically from CI I would really sleep better. It's about the secrets so it's better to trust people here than to some others.

@alerque @AGWA do you think you find a bit of time for that, please? :)

AGWA commented 2 years ago

Thanks @thebino. It would definitely be useful to automate the building of the exe. I'm confused and concerned that this would run on pull requests, since pull requests could contain malicious code. How can we make sure this runs only on trustworthy code that is actually pushed to this repository?

AGWA commented 2 years ago

Could you explain what this means:

If the branch or tag contains release, a new release draft will be created.

git-crypt doesn't currently use this convention. Release tags look like 0.6.0 and are on the master branch. Could the action create a release draft for any tag on master?

thebino commented 2 years ago

@AGWA I just pushed the change to use release tags only.

For clarification:

  1. workflows are only visible to maintainers and admins
  2. releases are only drafts and need to be published
  3. You can also start the workflow manually if you want to skip the tag triggers. Just open github actions in the project, select the workflow and trigger it. (This is also only visible to maintainers)
thebino commented 2 years ago

It would be also possible to pass the git tag via build flag into the build process to set the version for the build binary. But I would recommend to do this in a separate PR since it affects changes on the make files

thebino commented 2 years ago

@alerque @AGWA Anything else I can provide to push this PR?

thebino commented 2 years ago

@alerque @AGWA Is there anything I can do or support you to get this PR merged?

miso-belica commented 2 years ago

@thebino I don't really know how is the workflow here but I think the @AGWA's answers (cited below) suggest that the following modifications are needed.

  1. Remove the on.workflow_dispatch and on.pull_request triggers.
  2. Change trigger on.push so it runs only if the tag with version format is created. I think this does the trick:
    on:
    push:
    tags:
      - "[0-9]+.[0-9]+.[0-9]+"

I'm confused and concerned that this would run on pull requests, since pull requests could contain malicious code. How can we make sure this runs only on trustworthy code that is actually pushed to this repository?

Release tags look like 0.6.0 and are on the master branch. Could the action create a release draft for any tag on master?

Thanks for everybody's work and effort here. I hope this gets merged and we will have trustable builds for Windows :)

thebino commented 2 years ago

workflow_dispatch will add the possibility to manually trigger the build.

The build should be triggered for all pushes and new pull-requests. Otherwise there is no CI/CD functionality.

There will no release be triggered, since there is another check in the build step: https://github.com/AGWA/git-crypt/pull/227/files#diff-d0777657fa3fd81d23aaf7273e58aee453b04e67882517900c56daeef9b3e4c1R102

pravindahal commented 2 years ago

@thebino Thanks for the work.

I see that this is configured such that when a tag is created and pushed, it creates a release, builds artifacts and attaches to the release.

The actions are triggered on every push and builds and artifacts are created needlessly. I can see that it may be useful to know that builds are successful after every push, but saving artifacts may not be necessary?

May I suggest a different workflow? How about the workflow only being triggered when a GitHub release is created?

on:
  release:
    types: [published]

Then, the create_release job can be removed and the only the build job will be necessary. It will need some modifications. I am willing to make those changes and open a new PR soon.

pravindahal commented 2 years ago

I have created a solution for those who are looking to build their own binaries for Windows (using GitHub actions):

  1. Fork this project
  2. Add this file to .github/actions/build.yaml: https://github.com/pravindahal/git-crypt-1/blob/master/.github/workflows/build.yaml
  3. Commit and push

Once you do that, in your repo, create a new GitHub release by going to the releases page: https://github.com/YOUR_USERNAME/git-crypt/releases

Note that using existing tags to create the release does not work. You will need to create a new tag from master. You can use a tag such as 0.6.1 (the latest version tag here is 0.6.0 as of this writing). Also note that the tag name must match MAJOR.MINOR.PATCH format, otherwise the build will not be triggered.

Once you publish the release, go to the Actions tab (https://github.com/YOUR_USERNAME/git-crypt/actions) and wait for the build to complete. Once it is complete, you will be able to find the binaries in the release page (https://github.com/YOUR_USERNAME/git-crypt/releases) as release assets.

You can see what it looks like here: https://github.com/pravindahal/git-crypt-1/releases/tag/0.6.3 (here, you'll find the binaries pre-built, but you need to trust me to use it, which you shouldn't of course).

Also, note that I am using an unofficial GitHub action to upload release assets: https://github.com/pravindahal/git-crypt-1/blob/master/.github/workflows/build.yaml#L89. Here is the link to the action repo for that action: https://github.com/svenstaro/upload-release-action. You need to verify that the action is doing what it says it does.

AGWA commented 2 years ago

Thanks everyone for being patient with this PR. The reason for the delay is that GitHub Actions has a number of security gotchas, and I wasn't knowledgeable enough about GitHub Actions to be able to properly review this PR.

I'm happy to say that I've found the time to learn about GitHub Actions, and have just pushed workflows that automatically build 64-bit Linux and Windows binaries for all releases. You can find the binaries for the new 0.7.0 release here: https://github.com/AGWA/git-crypt/releases/tag/0.7.0

Thank you @thebino and @pravindahal for your contributions. Since it is security-critical that 1) third-party actions not have write access to the repository, and 2) Windows builds can't compromise Linux builds, I ended up writing my own workflows that ensure these properties. However, I found your work very helpful when learning about GitHub Actions.