#!/usr/bin/env bash # kenku --- crawl and reproduce github actions # Copyright © 2026 bdunahu # # This program is free software: you can redistribute it and/or modify # it under the terms of the GNU General Public License as published by # the Free Software Foundation, either version 3 of the License, or # (at your option) any later version. # # This program is distributed in the hope that it will be useful, # but WITHOUT ANY WARRANTY; without even the implied warranty of # MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the # GNU General Public License for more details. # # You should have received a copy of the GNU General Public License # along with this program. If not, see . # # # Takes a file with a repository identifier per line, like this: # # actions/deploy-pages v4 # actions/upload-pages-artifact v4 # astral-sh/setup-uv v7 # actions/setup-python v2 # actions/checkout v2 # # And writes an equivalent file with what it's using. 'using' in this case can # be one of the standard action types in the github actions lingo: 'node', # 'docker', or 'composite'. # The `actions.yaml` or `actions.yml` file does a pretty good job explaining # what is used or not. function curl_action { curl -s \ -H "Accept: application/vnd.github+json" \ -H "Authorization: Bearer ${TOKEN}" \ "https://api.github.com/repos/$1?ref=$2" } function find_action { owner=$(echo "$1" | awk -F'/' '{print $(1)}') repo=$(echo "$1" | awk -F'/' '{print $(2)}') fname=$(echo "$1" | cut -d'/' -f3-) sha="$2" path="$owner/$repo/contents/$fname" if [[ "$path" =~ \.(yml|yaml)$ ]]; then action=$(curl_action "$path" "$sha") exists=true else for c in action.yml action.yaml; do p="$path/$c" action=$(curl_action "$p" "$sha") # endpoint doesn't exist exists=$(echo "$action" | jq -e 'has("message") | not') [[ "$exists" == true ]] && break done fi using=$("$exists" && { echo "$action" \ | jq -r '.content' \ | base64 -d \ | grep -E '^\s*"?using"?:' \ | sed -E 's/.*"?using"?:[[:space:]]*//' } || echo "NO_FILE" ) [[ -z "$using" ]] && using="NO_USING" echo "$1 $sha $using" } while read -r action sha; do find_action "$action" "$sha" done