Skip to content

johnmccutchan/rfwpad #2610

johnmccutchan/rfwpad

johnmccutchan/rfwpad #2610

name: Fork - Clone - Build flutter App - Deploy to gh-pages
run-name: ${{ github.event.inputs.owner }}/${{ github.event.inputs.repo }}
on:
workflow_dispatch:
inputs:
owner:
description: "Repository Owner"
required: true
repo:
description: "Repository"
required: true
fork-org:
description: "Fork organization"
required: true
run-id:
description: "Run identifier"
required: true
jobs:
webfolder:
runs-on: ubuntu-latest
env:
new-repo-name: ${{ github.event.inputs.owner }}-${{ github.event.inputs.repo }}
delay-miliseconds-to-validate-fork-finished: 5000
timeout-minutes: 7
steps:
- name: ${{ github.event.inputs.run-id }}
run: |
echo "run identifier ${{ github.event.inputs.run-id }}"
echo "new-repo-name ${{ env.new-repo-name }}"
- name: Fork repository
uses: actions/github-script@v4
with:
github-token: ${{ secrets.PERSONAL_ACCESS_TOKEN }}
script: |
const owner = '${{ github.event.inputs.owner }}';
const repo = '${{ github.event.inputs.repo }}';
const org = '${{ github.event.inputs.fork-org }}';
const name = '${{ env.new-repo-name }}';
async function forkRepo() {
try {
const response = await github.repos.createFork({
owner: owner,
repo: repo,
organization: org,
name: name
});
console.log(`Repository ${response.data.full_name} forked to organization ${org}`);
} catch (error) {
console.error('Failed to fork repository:', error);
if(error.status === 404){
console.error('Repository not found. Stop workflow');
throw error
}
}
}
forkRepo();
- name: Wait until the fork finishes
uses: actions/github-script@v4
with:
github-token: ${{ secrets.PERSONAL_ACCESS_TOKEN }}
script: |
const owner = '${{ github.event.inputs.fork-org }}';
const repo = '${{ env.new-repo-name }}';
const delayTime = ${{ env.delay-miliseconds-to-validate-fork-finished }};
async function repoExists() {
try {
const response = await github.repos.get({
owner: owner,
repo: repo
});
console.log(`Repository ${response.data.full_name} was found.`);
} catch (error) {
console.error('Failed to get repository', error);
throw error;
}
}
async function repoHasCommits() {
try {
const response = await github.repos.listCommits({
owner: owner,
repo: repo
});
if(response.status !== 200){
console.log(`Didn't find commits for the repository ${repo}. Response ${response}`);
return false;
}
console.log(`Repository ${repo} has commits.`);
return true;
} catch (error) {
console.error(`Failed to list commits of repository ${repo}`, error);
return false;
}
}
function delay(time) {
console.log(`Delay for ${time} miliseconds`)
return new Promise(resolve => setTimeout(resolve, time));
}
repoExists();
let hasCommits = await repoHasCommits();
while(!hasCommits){
await delay(delayTime)
hasCommits = await repoHasCommits();
}
- name: Clone or Checkout repository
uses: actions/checkout@v2
with:
token: ${{ secrets.PERSONAL_ACCESS_TOKEN }}
repository: ${{ github.event.inputs.fork-org }}/${{ env.new-repo-name }}
- name: Find Flutter project path
id: flutter-project-project-path
run: |
# Find the directory containing the file with the string 'project_type: app'
METADATA_DIR=$(dirname $(grep -Eril "project_type: app" *) | sort -u)
if [ ! -z "$METADATA_DIR" ]; then
echo "Found .metadata file under '$METADATA_DIR' folder"
echo "FLUTTER_PROJECT_PATH=$METADATA_DIR" >> "$GITHUB_OUTPUT"
else
# Find the directory containing the file 'pubspec.lock'
PUBSPEC_LOCK_DIR=$(find . -name "pubspec.lock" -exec dirname {} \;)
if [ ! -z "$PUBSPEC_LOCK_DIR" ]; then
echo "pubspec.lock file was found."
while IFS= read -r dir
do
if [[ -d "$dir/web" || -d "$dir/android" || -d "$dir/ios" || -d "$dir/linux" || -d "$dir/windows" || -d "$dir/macos" ]]; then
echo "Found pubspec.lock in the same folder as the other important flutter folders. This is under '$dir'"
echo "FLUTTER_PROJECT_PATH=$dir" >> "$GITHUB_OUTPUT"
exit 0
else
shift
fi
done <<< "$PUBSPEC_LOCK_DIR"
echo "None of the pubspec.lock files was found in the same folder as the other important flutter folders."
fi
# Find the first directory containing the file 'pubspec.yaml'
PUBSPEC_DIR=$(dirname $(find . -name "pubspec.yaml" | head -n 1))
if [ -z "$PUBSPEC_DIR" ]; then
echo "pubspec.yaml file was not found. Stop workflow."
exit 1
else
echo "pubspec.yaml file was found under '$PUBSPEC_DIR'."
echo "FLUTTER_PROJECT_PATH=$PUBSPEC_DIR" >> "$GITHUB_OUTPUT"
fi
fi
- name: Find supported Flutter version
id: flutter-version-finder
uses: ukoreh/actions/flutter-version-finder@master
with:
project-path: ${{ steps.flutter-project-project-path.outputs.FLUTTER_PROJECT_PATH }}
- name: Set up Flutter
uses: subosito/flutter-action@v2
with:
flutter-version: ${{ steps.flutter-version-finder.outputs.flutter-version }}
channel: ${{ steps.flutter-version-finder.outputs.flutter-channel }}
- name: Setup Flutter web
run: |
channel=${{ steps.flutter-version-finder.outputs.flutter-channel }}
echo "on channel: $channel"
if [ "$channel" = "beta" ]; then
flutter config --enable-web
fi
- name: Check if 'web' folder exists
id: web-folder
run: |
cd ${{ steps.flutter-project-project-path.outputs.FLUTTER_PROJECT_PATH }}
echo "path now: ${{ steps.flutter-project-project-path.outputs.FLUTTER_PROJECT_PATH }}"
if [ -d "web" ]; then
echo "'web' folder exists in the same directory as 'pubspec.yaml'."
echo "WEB_FOLDER_LOCATION=$PWD" >> "$GITHUB_OUTPUT"
else
echo "'web' folder does not exist in the same directory as 'pubspec.yaml'. So create it!!!"
flutter create --org com.ukoreh.actions --platforms web .
echo "WEB_FOLDER_LOCATION=$PWD" >> "$GITHUB_OUTPUT"
fi
- name: Clean flutter
run: |
cd ${{ steps.web-folder.outputs.WEB_FOLDER_LOCATION }}
flutter clean
- name: Get packages
run: |
cd ${{ steps.web-folder.outputs.WEB_FOLDER_LOCATION }}
flutter pub get
- name: Build web app
run: |
cd ${{ steps.web-folder.outputs.WEB_FOLDER_LOCATION }}
flutter_version=${{ steps.flutter-version-finder.outputs.flutter-version }}
base_href="/${{ env.new-repo-name }}/"
if [[ "$flutter_version" =~ [1|2]\.[0-4]{1,}.+ ]]; then
flutter build web --release
sed -i "s|<base href=.*>|<!-- empty -> g" build/web/index.html
sed -i "s|<head>|<head><base href=\"$base_href\">|g" build/web/index.html
else
flutter build web --release --base-href $base_href
fi
- name: Deploy to GitHub Pages
uses: peaceiris/actions-gh-pages@v3
with:
personal_token: ${{ secrets.PERSONAL_ACCESS_TOKEN }}
publish_dir: ${{ steps.web-folder.outputs.WEB_FOLDER_LOCATION }}/build/web
external_repository: ${{ github.event.inputs.fork-org }}/${{ env.new-repo-name }}
publish_branch: gh-pages
- name: Create issue in the forked repository
if: ${{ vars.FF_STEP_CREATE_ISSUE == 'true' }}
uses: actions/github-script@v4
with:
github-token: ${{ secrets.PERSONAL_ACCESS_TOKEN }}
script: |
const owner = '${{ github.event.inputs.owner }}';
const repo = '${{ github.event.inputs.repo }}';
const org = '${{ github.event.inputs.fork-org }}';
const name = '${{ env.new-repo-name }}';
const title = "Your web app is ready! 🚀";
const body = `Hey! 👋
Someone has requested a demo of your project using [Ukoreh](https://ukoreh.fun/)! 🧙‍♂️.
The app compiled fine and is now live at https://${org}.github.io/${name}`;
async function createIssue() {
try {
const newIssue = await github.issues.create({
owner: owner,
repo: repo,
title: title,
body: body,
});
console.log(`Created issue ${newIssue.data.number}: ${newIssue.data.title}`);
} catch (error) {
console.error('Failed to create issue:', error);
if(error.status === 410){
console.error('Issues are disabled in the repository');
}
}
}
async function issueExists() {
try {
const { data: issues } = await github.issues.listForRepo({
owner: owner,
repo: repo,
state: 'all'
});
const existingIssue = issues.find(issue => issue.title === title);
const exists = existingIssue !== undefined;
console.log(`Issue with title "${title}" exists: ${exists}`);
return exists;
} catch (error) {
console.error('Failed to validate if issue already exists:', error);
}
}
const exists = await issueExists();
if (!exists) {
console.log(`Creating issue with title ${title}`);
createIssue();
}