Skip to content

Compile All

Compile All #99

name: Compile All
on:
workflow_dispatch:
jobs:
build:
name: Build for ${{ matrix.target.name }}
runs-on: ubuntu-latest
strategy:
matrix:
target:
# sd_spi_cs_pin: 23, sd_spi_clk_pin: 19, sd_spi_miso_pin: 20, sd_spi_mosi_pin: 18, gps_uart_rx_pin: 15, gps_uart_tx_pin: 14
# Generic configurations (no LED, no screen support)
- { name: "esp32-generic", idf_target: "esp32", sdkconfig_file: "configs/sdkconfig.default.esp32", zip_name: "esp32-generic.zip" }
- { name: "esp32s2-generic", idf_target: "esp32s2", sdkconfig_file: "configs/sdkconfig.default.esp32s2", zip_name: "esp32s2-generic.zip"}
- { name: "esp32s3-generic", idf_target: "esp32s3", sdkconfig_file: "configs/sdkconfig.default.esp32s3", zip_name: "esp32s3-generic.zip" }
- { name: "esp32c3-generic", idf_target: "esp32c3", sdkconfig_file: "configs/sdkconfig.default.esp32c3", zip_name: "esp32c3-generic.zip" }
- { name: "esp32c6-generic", idf_target: "esp32c6", sdkconfig_file: "configs/sdkconfig.default.esp32c6", zip_name: "esp32c6-generic.zip" }
- { name: "Awok V5", idf_target: "esp32s2", sdkconfig_file: "configs/sdkconfig.default.esp32s2", zip_name: "esp32v5_awok.zip"}
# Dev Kit configurations (LED on, no screen support)
- { name: "esp32c3-devkit", idf_target: "esp32c3", sdkconfig_file: "configs/sdkconfig.devkit.esp32c3", zip_name: "esp32c3-devkit.zip"}
- { name: "esp32c6-devkit", idf_target: "esp32c6", sdkconfig_file: "configs/sdkconfig.devkit.esp32c6", zip_name: "esp32c6-devkit.zip"}
# Ghost board (LED on, special pin and LED count)
- { name: "ghostboard", idf_target: "esp32c6", sdkconfig_file: "configs/sdkconfig.ghostboard", zip_name: "ghostboard.zip"}
# Screen-supported builds
- { name: "MarauderV4_FlipperHub", idf_target: "esp32", sdkconfig_file: "configs/sdkconfig.marauderv4", zip_name: "MarauderV4_FlipperHub.zip"}
- { name: "MarauderV6&AwokDual", idf_target: "esp32", sdkconfig_file: "configs/sdkconfig.marauderv6", zip_name: "MarauderV6_AwokDual.zip"}
- { name: "AwokMini", idf_target: "esp32", sdkconfig_file: "configs/sdkconfig.awokmini", zip_name: "AwokMini.zip"}
- { name: "ESP32-S3-Cardputer", idf_target: "esp32s3", sdkconfig_file: "configs/sdkconfig.cardputer", zip_name: "ESP32-S3-Cardputer.zip"}
- { name: "LillyGoTWatch_S3", idf_target: "esp32s3", sdkconfig_file: "configs/sdkconfig.S3TWatch", zip_name: "lillygos3watch.zip"}
# CYD (Cheap Yellow Display) with touch screen
- { name: "CYD2USB", idf_target: "esp32", sdkconfig_file: "configs/sdkconfig.CYD2USB", zip_name: "CYD2USB.zip"}
- { name: "CYDMicroUSB", idf_target: "esp32", sdkconfig_file: "configs/sdkconfig.CYDMicroUSB", zip_name: "CYDMicroUSB.zip"}
- { name: "CYDDualUSB", idf_target: "esp32", sdkconfig_file: "configs/sdkconfig.CYDDualUSB", zip_name: "CYDDualUSB.zip"}
- { name: "CYD2USB2.4_Inch", idf_target: "esp32", sdkconfig_file: "configs/sdkconfig.CYD2USB2.4Inch", zip_name: "CYD2USB2.4Inch.zip"}
# 7-inch boards
- { name: "Waveshare_LCD", idf_target: "esp32s3", sdkconfig_file: "configs/sdkconfig.waveshare7inch", zip_name: "Waveshare_LCD.zip"}
- { name: "Crowtech_LCD", idf_target: "esp32s3", sdkconfig_file: "configs/sdkconfig.crowtech7inch", zip_name: "Crowtech_LCD.zip"}
steps:
- name: Checkout Repository
uses: actions/checkout@v3
- name: Set up Python
uses: actions/setup-python@v4
with:
python-version: '3.9'
# Manual ESP-IDF Installation
- name: Install ESP-IDF
run: |
sudo apt-get update
sudo apt-get install -y wget git flex bison gperf python3-pip python3-setuptools cmake ninja-build ccache libffi-dev libssl-dev dfu-util
git clone -b v5.3.1 --depth 1 https://github.com/espressif/esp-idf.git ~/esp-idf
~/esp-idf/install.sh
- name: Apply Custom SDK Config
run: |
cp "${{ matrix.target.sdkconfig_file }}" sdkconfig.defaults
- name: Set up ESP-IDF and Target
run: |
. ~/esp-idf/export.sh
echo "FLAPPY_GHOST_WEB_HOOK=${{ secrets.FLAPPY_GHOST_WEB_HOOK }}" >> $GITHUB_ENV
echo "IDF_TARGET=${{ matrix.target.idf_target }}" >> $GITHUB_ENV
export IDF_TARGET=${{ matrix.target.idf_target }}
echo "IDF_TARGET is set to $IDF_TARGET"
- name: Verify SDK Config Options
run: |
echo "Checking if configurations exist in sdkconfig.defaults"
grep -E "CONFIG_WITH_SCREEN|CONFIG_TFT_WIDTH|CONFIG_TFT_HEIGHT|CONFIG_USE_TOUCHSCREEN|CONFIG_USE_JOYSTICK|CONFIG_USE_CARDPUTER|CONFIG_IS_GHOST_BOARD|CONFIG_USE_7_INCHER|CONFIG_Waveshare_LCD|CONFIG_Crowtech_LCD|CONFIG_Sunton_LCD|CONFIG_USE_ILI9341_2" sdkconfig.defaults || echo "One or more options not found in sdkconfig.defaults"
- name: Clean and Remove Previous SDK Config
run: |
# Remove any previously generated sdkconfig file to avoid conflicts
rm -f sdkconfig
. ~/esp-idf/export.sh
idf.py clean
- name: Build Project with sdkconfig.defaults
env:
SDKCONFIG_DEFAULTS: "sdkconfig.defaults"
run: |
. ~/esp-idf/export.sh
idf.py build
- name: Verify SDK Config Options
run: |
echo "Checking if configurations exist in sdkconfig.defaults"
grep -E "CONFIG_WITH_SCREEN|CONFIG_TFT_WIDTH|CONFIG_TFT_HEIGHT|CONFIG_USE_TOUCHSCREEN|CONFIG_USE_JOYSTICK|CONFIG_USE_CARDPUTER|CONFIG_IS_GHOST_BOARD|CONFIG_USE_7_INCHER|CONFIG_Waveshare_LCD|CONFIG_Crowtech_LCD|CONFIG_Sunton_LCD|CONFIG_USE_ILI9341_2" sdkconfig.defaults || echo "One or more options not found in sdkconfig.defaults"
- name: Download Correct Bootloader
run: |
BOOTLOADER_URL="https://cdn.spookytools.com/bootloaders/${{ matrix.target.idf_target }}.bin"
BOOTLOADER_PATH="packaged_artifacts/bootloader.bin"
echo "Downloading bootloader from $BOOTLOADER_URL"
mkdir -p packaged_artifacts
curl -L -o "$BOOTLOADER_PATH" "$BOOTLOADER_URL"
if [ ! -f "$BOOTLOADER_PATH" ]; then
echo "Error: Bootloader could not be downloaded from $BOOTLOADER_URL"
exit 1
else
echo "Bootloader downloaded successfully to $BOOTLOADER_PATH"
fi
- name: Package Build Artifacts
run: |
. ~/esp-idf/export.sh
PARTITION_TABLE_BIN=build/partition_table/partition-table.bin
GHOST_ESP_IDF_BIN=build/Ghost_ESP_IDF.bin
if [ ! -f "$PARTITION_TABLE_BIN" ]; then
echo "Error: $PARTITION_TABLE_BIN not found!"
exit 1
fi
if [ ! -f "$GHOST_ESP_IDF_BIN" ]; then
echo "Error: $GHOST_ESP_IDF_BIN not found!"
exit 1
fi
cp "$PARTITION_TABLE_BIN" packaged_artifacts/
cp "$GHOST_ESP_IDF_BIN" packaged_artifacts/
ZIP_NAME="${{ matrix.target.zip_name }}"
cd packaged_artifacts
zip "$ZIP_NAME" bootloader.bin partition-table.bin Ghost_ESP_IDF.bin
cd ..
- name: Get the Latest Release ID (Including Pre-releases)
id: get_release
env:
GITHUB_TOKEN: ${{ secrets.GITHUB_TOKEN }}
run: |
latest_release=$(curl -s \
-H "Authorization: token $GITHUB_TOKEN" \
-H "Accept: application/vnd.github.v3+json" \
"https://api.github.com/repos/${{ github.repository }}/releases" | jq '[.[] | select(.draft == false)] | .[0]')
release_id=$(echo "$latest_release" | jq -r '.id')
echo "Latest release ID (including pre-releases) is $release_id"
echo "::set-output name=release_id::$release_id"
- name: Upload to Latest Release
env:
GITHUB_TOKEN: ${{ secrets.GITHUB_TOKEN }}
run: |
zip_file="packaged_artifacts/${{ matrix.target.zip_name }}"
release_id=${{ steps.get_release.outputs.release_id }}
curl -X POST \
-H "Authorization: token $GITHUB_TOKEN" \
-H "Content-Type: application/zip" \
--data-binary @"$zip_file" \
"https://uploads.github.com/repos/${{ github.repository }}/releases/$release_id/assets?name=$(basename $zip_file)"
- name: Install rclone
run: |
curl -fsSL https://rclone.org/install.sh | sudo bash
- name: Configure rclone for Cloudflare R2
env:
R2_ACCESS_KEY: ${{ secrets.R2_ACCESS_KEY }}
R2_SECRET_KEY: ${{ secrets.R2_SECRET_KEY }}
run: |
mkdir -p ~/.config/rclone
echo "[cloudflare_r2]" > ~/.config/rclone/rclone.conf
echo "type = s3" >> ~/.config/rclone/rclone.conf
echo "provider = Cloudflare" >> ~/.config/rclone/rclone.conf
echo "access_key_id = $R2_ACCESS_KEY" >> ~/.config/rclone/rclone.conf
echo "secret_access_key = $R2_SECRET_KEY" >> ~/.config/rclone/rclone.conf
echo "endpoint = https://fb5f7d31bedfe4f3538ddfa6db491962.r2.cloudflarestorage.com" >> ~/.config/rclone/rclone.conf
- name: Acquire Mutex Lock
uses: crazy-max/ghaction-mutex@v1
with:
mutex: cloudflare-upload-lock
timeout: 3000
- name: Upload Artifacts to Cloudflare R2
env:
R2_BUCKET: "spooksapi"
R2_PATH: "GhostESPBins"
run: |
echo "Uploading ${{ matrix.target.zip_name }} to Cloudflare R2..."
rclone copy "packaged_artifacts/${{ matrix.target.zip_name }}" "cloudflare_r2:${R2_BUCKET}/${R2_PATH}" --progress
if [ $? -ne 0 ]; then
echo "Upload failed. Exiting..."
exit 1
fi
echo "Upload of ${{ matrix.target.zip_name }} to Cloudflare R2 completed successfully."
- name: Release Mutex Lock
uses: crazy-max/ghaction-mutex@v1
with:
mutex: cloudflare-upload-lock
release: true
- name: Notify Discord of Successful Release
if: success()
env:
DISCORD_WEBHOOK_URL: ${{ secrets.DISCORD_WEBHOOK_URL }}
run: |
payload=$(cat <<EOF
{
"embeds": [
{
"title": "🎉 New Release for Ghost ESP!",
"description": "A new release for Ghost ESP has been successfully compiled and is now available! Check out the latest release for details.",
"url": "${{ github.server_url }}/${{ github.repository }}/releases/latest",
"color": 5814783,
"fields": [
{
"name": "Repository",
"value": "${{ github.repository }}",
"inline": true
},
{
"name": "Version",
"value": "${{ github.event.release.tag_name }}",
"inline": true
},
{
"name": "Commit",
"value": "${{ github.sha }}",
"inline": true
}
],
"footer": {
"text": "GitHub Actions Bot",
"icon_url": "https://github.githubassets.com/images/modules/logos_page/GitHub-Mark.png"
},
"timestamp": "$(date -u +"%Y-%m-%dT%H:%M:%SZ")"
}
]
}
EOF
)
curl -X POST \
-H "Content-Type: application/json" \
-d "$payload" \
"$DISCORD_WEBHOOK_URL"