Skip to content

Commit 5a8945b

Browse files
committed
adding post on organization readme badge generator
1 parent eb330dc commit 5a8945b

6 files changed

+137
-0
lines changed

Diff for: _posts/2024-06-18-github-composite-action-python.md

+2
Original file line numberDiff line numberDiff line change
@@ -51,6 +51,7 @@ runs:
5151
run: |
5252
python3 ${{ github.action_path }}/main.py ${{ inputs.directory }} ${{ inputs.token }}
5353
```
54+
{: file='action.yml'}
5455
5556
The magic 🪄 is that we are calling the Python script from the shell using the `${{ github.action_path }}` [environment variable](https://help.github.com/en/actions/configuring-and-managing-workflows/using-environment-variables). This variable maps to the local directory the action is cloned to so that we can reference files from the repo.
5657

@@ -153,6 +154,7 @@ runs:
153154
creds = sys.argv[2]
154155
main(${{ inputs.directory }}, ${{ inputs.token }})
155156
```
157+
{: file='action.yml'}
156158

157159
This certainly works, but you can see that it's not as flexible/portable as the [preferred method above](#preferred-python-composite-action). For one, if you wanted to run this locally, you would have to copy/paste and then swap the hardcoded GitHub Actions-isms, like in this example: `${{ inputs.directory }}` and `${{ inputs.token }}`. It's also harder to read and maintain. 😬
158160

Original file line numberDiff line numberDiff line change
@@ -0,0 +1,135 @@
1+
---
2+
title: 'GitHub Organization Readme Badge Generator'
3+
author: Josh Johanning
4+
date: 2024-08-14 3:30:00 -0500
5+
description: A GitHub action to create markdown badges for your GitHub organization's README.md file
6+
categories: [GitHub, Actions]
7+
tags: [GitHub, GitHub Actions]
8+
media_subpath: /assets/screenshots/2024-08-14-github-organization-readme-badge-generator
9+
image:
10+
path: markdown-badges-light-header.png
11+
width: 100%
12+
height: 100%
13+
alt: Markdown badges in a GitHub organization's README
14+
---
15+
16+
## Overview
17+
18+
In this post, I will show you how to add an Actions workflow to generate markdown badges to spruce up your organization READMEs. Badges are a great way to provide a quick visual representation of data; you might see them often on your favorite open source repository showing the code quality or number of stars. My action will generate badges for the following (right now):
19+
20+
- Number of repositories
21+
- Number of pull requests open in the last 30 days
22+
- Number of pull requests merged in the last 30 days
23+
24+
Here's an [example](https://github.com/joshjohanning-org#joshjohanning-org) of this in action:
25+
![Markdown badges in a GitHub organization's README](markdown-badges-light.png){: .shadow }{: .light }
26+
![Markdown badges in a GitHub organization's README](markdown-badges-dark.png){: .shadow }{: .dark }
27+
_Markdown badges in a GitHub organization's README_
28+
29+
## What is an organization README?
30+
31+
[Organization READMEs](https://github.blog/changelog/2021-09-14-readmes-for-organization-profiles/) are a great way to showcase your organization to the world. Take [GitHub's organization README](https://github.com/github) as an example. There's a fun picture, a description of what's in the organization, how to contribute, and much more. [Member-only READMEs](https://github.blog/changelog/2022-04-20-organization-profile-updates-member-only-readmes-and-pinned-private-repositories/) are also a great extension of this functionality. Instead of providing information to the general public, you can provide information to your organization's members. For example, when I navigate to GitHub's organization page, I see a different README by default with internal information.
32+
33+
It's really easy to create a public and/or member-only organization README. For a public organization README, you just need to create a `.github` repository and add a `profile/README.md`{: .filepath} file. For an organization member-only README, create a `.github-private` repository and add a `profile/README.md`{: .filepath} file.
34+
35+
## The Workflow
36+
37+
My [action](https://github.com/joshjohanning/organization-readme-badge-generator) is fairly generic in the sense that all it does is generate the markdown badges. It's up to you to decide where to put them in your README. Here's an example of me overwriting some placeholder text by using my action and a bash script:
38+
39+
{% raw %}
40+
41+
```yml
42+
name: update-organization-readme-badges
43+
44+
on:
45+
schedule:
46+
- cron: '0 7 * * *' # runs daily at 07:00
47+
workflow_dispatch:
48+
49+
permissions:
50+
contents: write
51+
52+
jobs:
53+
generate-badges:
54+
runs-on: ubuntu-latest
55+
56+
steps:
57+
- uses: actions/checkout@v4
58+
59+
- uses: actions/create-github-app-token@v1
60+
id: app-token
61+
with:
62+
app-id: ${{ vars.APP_ID }}
63+
private-key: ${{ secrets.PRIVATE_KEY }}
64+
owner: ${{ github.repository_owner }}
65+
66+
- name: organization-readme-badge-generator
67+
id: organization-readme-badge-generator
68+
uses: joshjohanning/organization-readme-badge-generator@v1
69+
with:
70+
organization: ${{ github.repository_owner }}
71+
token: ${{ steps.app-token.outputs.token }} # recommend to use a GitHub App and not a PAT
72+
73+
- name: write to job summary
74+
run: |
75+
echo "${{ steps.organization-readme-badge-generator.outputs.badges }}" >> $GITHUB_STEP_SUMMARY
76+
77+
- name: add to readme
78+
run: |
79+
readme=profile/README.md
80+
81+
# get SHA256 before
82+
beforeHash=$(sha256sum $readme | awk '{ print $1 }')
83+
84+
# Define start and end markers
85+
startMarker="<!-- start organization badges -->"
86+
endMarker="<!-- end organization badges -->"
87+
88+
replacement="${{ steps.organization-readme-badge-generator.outputs.badges }}"
89+
90+
# Escape special characters in the replacement text
91+
replacementEscaped=$(printf '%s\n' "$replacement" | perl -pe 's/([\\\/\$\(\)@])/\\$1/g')
92+
93+
# Use perl to replace the text between the markers
94+
perl -i -pe "BEGIN{undef $/;} s/\Q$startMarker\E.*?\Q$endMarker\E/$startMarker\n$replacementEscaped\n$endMarker/smg" $readme
95+
# get SHA256 after
96+
afterHash=$(sha256sum $readme | awk '{ print $1 }')
97+
# Compare the hashes and commit if required
98+
if [ "$afterHash" = "$beforeHash" ]; then
99+
echo "The hashes are equal - exiting script"
100+
exit 0
101+
else
102+
git config --global user.name 'github-actions[bot]'
103+
git config --global user.email 'github-actions[bot]@users.noreply.github.com'
104+
git add $readme
105+
git commit -m "docs: update organization readme badges"
106+
git push
107+
fi
108+
```
109+
{: file='.github/workflows/update-organization-readme-badges.yml'}
110+
111+
{% endraw %}
112+
113+
> I have this [workflow](https://github.com/joshjohanning-org/.github/actions/workflows/update-organization-readme-badges.yml) running in my public `joshjohanning-org/.github` repository for reference.
114+
{: .prompt-tip }
115+
116+
This workflow runs and generates the badges with my action. Afterwards, it finds placeholder text in the `profile/README.md`{: .filepath} file and updates the markdown badges. The workflow then commits the change and pushes it back to the repository.
117+
118+
Here's an example of the placeholder text in the `profile/README.md`{: .filepath} file that it's expecting (your badges would be dynamically inserted between the tags):
119+
120+
```md
121+
# my-org-name
122+
123+
<!-- start organization badges -->
124+
125+
<!-- end organization badges -->
126+
```
127+
{: file='profile/README.md'}
128+
129+
## Summary
130+
131+
I like the ability to add quick little badges to my organization README to give the public / my members an idea of the status and activity stats for the organization. This action is a great way to do that.
132+
133+
I have this running as a scheduled workflow in both my `.github` and `.github-private` repositories.
134+
135+
I hope you find this useful! Let me know if there are other features or badges that I should add! For example, one of the things I was [envisioning](https://github.com/joshjohanning/organization-readme-badge-generator/issues/4) was number of GitHub Actions workflows ran / successful.. 🚀
Loading
Loading
Loading
Loading

0 commit comments

Comments
 (0)