-
-
Notifications
You must be signed in to change notification settings - Fork 54
Add a release workflow #9
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
Conversation
Great work @mattwynne. I have many questions.
I feel that the tag should be created locally by the person triggering the release, and that the release action should only be triggered when a new tag is pushed to the |
Another thing to consider is retries. The package managers are occasionally down or unresponsive (especially sonatype, where maven artifacts are published). If a tag is pushed, and the release action fails, we should be able to re-trigger the action manually via GitHub's web interface. |
Would it make sense to have separate |
@mattwynne we have made some tests here: https://github.com/cucumber/release-tests |
@aurelien-reeves I like the approach of splitting the release / publish workflows and using the Let's pair / ensemble on this on Wednesday? |
You do indeed! It's great to have your attention on this.
Right now, the tag is created by GitHub when we create the Release here in the
I think github just creates non-annotated / lightweight tags, so there's no user info / signing associated with the tagging, as far as I can tell.
It's currently made on the
I just dunno about all this. I think that for streamlining the release process we should try to push commit signing as far upstream as we can, but we obviously don't want to put too many barriers in the way of contributions either, so there's a trade-off. I think we should insist on signed commits on the The main pain I see with that scenario is that the commit being released (the squashed commit) is not on
Yes. The idea of factoring out these actions is so that we have a little copy/paste as possible when implementing this automation in the various cucumber repos. Actions are the lowest level of re-use you get in GitHub Actions, so the workflows themselves want to be as minimal as possible. I've sent you another invite. Using that org is not cast in stone - we could move those actions over to the Where did you want to put the links? The workflows themselves have links in them. Did you mean link to them in the docs?
No, the branch name is not relevant at all. We just happen to use the release number as a way to keep each release branch unique, as they're basically throwaway artifacts. The release number/tag is picked up from the top heading in the CHANGELOG, using the After the feedback from @davidjgoss that the original automated release process for cucumber-build was quite onerous, I did some work on an action to create a PR for each release automatically. This works pretty nicely in most cases, but I think we should keep that on the back burner until we're settled on the actual release end of the process.
I had the same instinct initially. The trouble with doing this is that we have to find another way to signal that the release is "done". So far, I've been using the CHANGELOG as the signal to request a new release, and the tag as the signal of what has been released. This enables us to know when a release is needed which is what enables the pre-release PR workflow. |
I've added an NPM publish action and the secret for it, so Ruby and NPM are good to go. |
.github/workflows/release.yaml
Outdated
- uses: actions/setup-node@v2 | ||
with: | ||
node-version: '16' | ||
- uses: cucumber-actions/[email protected] |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Can we use https://github.com/marketplace/actions/npm-publish instead? Less stuff for us to maintain?
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
The idea would be to not use external actions to be able to check a security option to github, thus to have total control over the release pipeline
Eventually we could fork the action
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Fair point. I would prefer to fork a community one rather than maintaining ones we've written from scratch. It has a lower cost of ownership - we can merge in upstream bugfixes as needed.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Agree
But we should be able to understand the code and what it does
(yes, I may be a little bit paranoid 😅)
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Hacking a widely used release plugin could provide attackers with an attack-surface where they can distribute malicious code to a lot of people. It's good to be paranoid about this.
These actions are fairly small and I think the effort required to understand them is smaller than the effort required to write them.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I think that this 3rd party one is way over complex for what we need. It has many features we don't need, where ours is about fifteen lines of bash. i like ours better.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I totally agree about the paranoia though!
.github/workflows/release.yaml
Outdated
with: | ||
ruby-version: 3.0.2 | ||
bundler-cache: true | ||
- uses: cucumber-actions/[email protected] |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Can we use https://github.com/marketplace/actions/publish-to-rubygems instead? Less stuff for us to maintain?
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
@aurelien-reeves pointed out that including 3rd party actions in our release chain is a potential supply-chain attack vector. For simple, stable, stuff like this I think it makes sense to roll our own.
I reviewed that particular one before deciding to write our own, and it's lame. It doesn't actually do the gem publish, it just invokes a rake task. It also writes the token to disk, and needs a github token for a reason I don't understand.
So I like ours better.
Thanks for the explanations @mattwynne - makes a lot more sense to me now. For Maven publishing we can try https://github.com/marketplace/actions/action-maven-publish (there are more here) For Go releases we just need to create and push a If one of the publish actions fail, I don't think we have an automated way to retry. That worries me. |
The version numbers in the various package decriptors (and go code) will have to be bumped before we start the release process. We should figure out how to automate this. Maybe we can reuse some of the scripts from |
We need to add several secrets to the @mattwynne I assume you added a new one in https://www.npmjs.com/settings/cukebot/tokens - but once added they cannot be read. If we want a token per repo, that's fine, but then the tokens must be named. Right now there are way too many tokens in there - we should delete as many as possible and start fresh. |
We need to merge cucumber/action-create-github-release#6 and make a new release of that action before we can merge this PR. Then I think we can test the release process. |
Co-authored-by: Aurélien Reeves <[email protected]>
Co-authored-by: Aurélien Reeves <[email protected]>
Yes, we need to document how to do it. Where would be a good place do you think? No, they've all been generated fresh. I think this is good practice.
As far as I can tell there's no facility for naming tokens in npmjs.com 🤷 FWIW the one I generated for this repo is the one starting I have no idea what the others are for, or why there are so many. I would assume that once we've finished automating all the releases of our javascript packages we can just delete all the older ones. |
.github/workflows/release.yaml
Outdated
needs: create-release | ||
runs-on: ubuntu-latest | ||
steps: | ||
- name: Create go/* tag |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Even though it's trivial, I suggest we factor this out into an action too. That way we keep symmetry with the other publish jobs, and we also have a single lever we can move if we need to make cross-project modifications about how Go packages are released (such as publishing binaries etc.)
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Agree, but I'd prefer to extract it after we're sure it works. It's easier to iterate that way.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Agree, but I'd prefer to extract it after we're sure it works. It's easier to iterate that way.
Mmmyeah. Remember how hard these are to test though - really the only way to test it is to run it and make a release. If we have it in a separate action we can unit test that at least, which gives us a bit more confidence when we bolt the whole thing together.
I've run out of time today but I can do this tomorrow.
Do you mean you want to automatically retry if the publish fails? Or you want to be able to manually re-run the automated release workflow? I expect you mean the latter. I think we have a couple of approaches we could take:
I have a slight preference for (1) since making them idempotent feels sensible anyway in case something gets triggered unintentionally, but (2) is probably a quicker win. I suggest we do that for now. I liked what you did in https://github.com/cucumber/release-tests to chain the actual publish jobs off of the |
.github/workflows/release.yaml
Outdated
run: |- | ||
git config user.name "cukebot" | ||
git config user.email "[email protected]" | ||
git tag "go/${{ steps.create-release.outputs.version }}" |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
We could also use the https://github.com/cucumber-actions/versions action as a prior step in this workflow.
Or, if we factor out our own action for this we can make it self-sufficient about looking up the version.
I meant manually retrying a publish for just a single language.
The whole workflow also includes They are hopefully all easy to query, but I'm worried about nexus/sonatype - not sure if it's possible there.
This would be my preference. @aurelien-reeves and I experimented with this yesterday in https://github.com/cucumber/release-tests/tree/main/.github/workflows (a throwaway repo). We tried to make the
Not sure - see comment above. |
Ah yes. We don't have enough security around Releases - they could be created manually by anyone with the commit bit. So we need to stick to triggering these when there's a push to the protected branch. |
I've actually done this already in the tests for the rubygems and npm publish actions. When I was testing the NPM one the other day I noticed it won't let you push the same package name / version a second time, so it would just fail if you tried to run it again.
Yeah that's a risk until we've done it.
|
I reckon we can have several separate workflows all going off the |
I think we've implemented the suggestions.
I think this is good to go, eh? We can easily / safely factor out a |
I guess you have heavily tested the releases workflows as part of https://github.com/cucumber/release-tests? If so, it looks good to me :) |
Adds an automated release workflow. So far this only works for publishing a Ruby gem, and will need to be extended to publish other language/platform packages.
See cucumber/common#1688
Checklist:
RUBYGEMS_API_KEY
secret in theRelease
environment.NPM_TOKEN
secret in theRelease
environment.publish-go
action?publish-mvn
action?