Skip to content

Fix/auto fixes - #3383

Open
flynnjustin24 wants to merge 1494 commits into
actions:updae_azure_python_cachefrom
flynnjustin24:fix/auto-fixes
Open

Fix/auto fixes#3383
flynnjustin24 wants to merge 1494 commits into
actions:updae_azure_python_cachefrom
flynnjustin24:fix/auto-fixes

Conversation

@flynnjustin24

@flynnjustin24 flynnjustin24 commented Jul 28, 2026

Copy link
Copy Markdown

Pre-requisites

  • Prior to submitting a new workflow, please apply to join the GitHub Technology Partner Program: partner.github.com/apply.

Please note that at this time we are only accepting new starter workflows for Code Scanning. Updates to existing starter workflows are fine.


Tasks

For all workflows, the workflow:

  • Should be contained in a .yml file with the language or platform as its filename, in lower, kebab-cased format (for example, docker-image.yml). Special characters should be removed or replaced with words as appropriate (for example, "dotnet" instead of ".NET").
  • Should use sentence case for the names of workflows and steps (for example, "Run tests").
  • Should be named only by the name of the language or platform (for example, "Go", not "Go CI" or "Go Build").
  • Should include comments in the workflow for any parts that are not obvious or could use clarification.
  • Should specify least privileged permissions for GITHUB_TOKEN so that the workflow runs successfully.

For CI workflows, the workflow:

  • Should be preserved under the ci directory.
  • Should include a matching ci/properties/*.properties.json file (for example, ci/properties/docker-publish.properties.json).
  • Should run on push to branches: [ $default-branch ] and pull_request to branches: [ $default-branch ].
  • Packaging workflows should run on release with types: [ created ].
  • Publishing workflows should have a filename that is the name of the language or platform, in lower case, followed by "-publish" (for example, docker-publish.yml).

For Code Scanning workflows, the workflow:

  • Should be preserved under the code-scanning directory.
  • Should include a matching code-scanning/properties/*.properties.json file (for example, code-scanning/properties/codeql.properties.json), with properties set as follows:
    • name: Name of the Code Scanning integration.
    • creator: Name of the organization/user producing the Code Scanning integration.
    • description: Short description of the Code Scanning integration.
    • categories: Array of languages supported by the Code Scanning integration.
    • iconName: Name of the SVG logo representing the Code Scanning integration. This SVG logo must be present in the icons directory.
  • Should run on push to branches: [ $default-branch, $protected-branches ] and pull_request to branches: [ $default-branch ]. We also recommend a schedule trigger of cron: $cron-weekly (for example, codeql.yml).

Some general notes:

  • This workflow must only use actions that are produced by GitHub, in the actions organization, or
  • This workflow must only use actions that are produced by the language or ecosystem that the workflow supports. These actions must be published to the GitHub Marketplace. We require that these actions be referenced using the full 40 character hash of the action's commit instead of a tag. Additionally, workflows must include the following comment at the top of the workflow file:
    # This workflow uses actions that are not certified by GitHub.
    # They are provided by a third-party and are governed by
    # separate terms of service, privacy policy, and support
    # documentation.
    
  • Automation and CI workflows should not send data to any 3rd party service except for the purposes of installing dependencies.
  • Automation and CI workflows cannot be dependent on a paid service or product.

tsusdere and others added 30 commits April 19, 2024 16:30
Checkout: Update all workflows to use Checkout V4
Bumps [actions/cache](https://github.com/actions/cache) from 3 to 4.
- [Release notes](https://github.com/actions/cache/releases)
- [Changelog](https://github.com/actions/cache/blob/main/RELEASES.md)
- [Commits](actions/cache@v3...v4)

---
updated-dependencies:
- dependency-name: actions/cache
  dependency-type: direct:production
  update-type: version-update:semver-major
...

Signed-off-by: dependabot[bot] <support@github.com>
Signed-off-by: Josh Soref <2119212+jsoref@users.noreply.github.com>
Signed-off-by: Josh Soref <2119212+jsoref@users.noreply.github.com>
* Switch default node version to 20
* Update version set to 18.x, 20.x, 22.x

Signed-off-by: Josh Soref <2119212+jsoref@users.noreply.github.com>
As required in pull_request_template.md
Remove Pages starter workflows from the sync automation
@flynnjustin24

Copy link
Copy Markdown
Author

tests/fizz-buzz.test.js

@flynnjustin24

Copy link
Copy Markdown
Author

{
"lib": ["WebWorker"]
}

@flynnjustin24

Copy link
Copy Markdown
Author

interface ViteTypeOptions {
// By adding this line, you can make the type of ImportMetaEnv strict
// to disallow unknown keys.
// strictImportMetaEnv: unknown
}

interface ImportMetaEnv {
readonly VITE_APP_TITLE: string
// more env variables...
}

interface ImportMeta {
readonly env: ImportMetaEnv
}

@flynnjustin24

Copy link
Copy Markdown
Author

.env # loaded in all cases
.env.local # loaded in all cases, ignored by git
.env.[mode] # only loaded in specified mode
.env.[mode].local # only loaded in specified mode, ignored by git

@flynnjustin24

Copy link
Copy Markdown
Author

experimental: {
renderBuiltUrl(filename, { hostId, hostType, type }) {
if (type === 'public') {
return 'https://www.domain.com/' + filename
} else if (path.extname(hostId) === '.js') {
return {
runtime: window.__assetsPath(${JSON.stringify(filename)})
}
} else {
return 'https://cdn.domain.com/assets/' + filename
}
},
},

@flynnjustin24

Copy link
Copy Markdown
Author

experimental: {
renderBuiltUrl(filename, { hostType }) {
if (hostType === 'js') {
return { runtime: window.__toCdnUrl(${JSON.stringify(filename)}) }
} else {
return { relative: true }
}
},
},

@flynnjustin24

Copy link
Copy Markdown
Author

import fizzBuzz from './src/fizz-buzz.js'; console.log(fizzBuzz(3)); // "Fizz"

@flynnjustin24

Copy link
Copy Markdown
Author

Use | sudo bash to run as root and install to /usr/local/bin

@flynnjustin24

Copy link
Copy Markdown
Author

GitHub Agentic Workflows Factory Tour

Important

GitHub Agentic Workflows and the gh-aw CLI are in public preview. You may notice product changes, rough edges, or minor differences from the screenshots and examples in this workshop.

Mona's Agent Factory

What you will learn to build

Build a real AI-powered GitHub workflow from scratch and leave with a safe production-style agentic automation you can adapt to your own repositories.

Sample daily repository status report generated by the finished workflow

Why this workshop

Most workflow tutorials stop at toy examples. This workshop takes you all the way to a useful end result: an agentic workflow that runs in GitHub Actions, inspects a repository, and publishes a daily status report automatically.

By the time you finish, you will know how to:

  • define an agentic workflow in Markdown
  • use the gh-aw CLI to validate, run, and iterate on workflows
  • connect triggers, prompts, and GitHub context into one practical automation
  • adapt the pattern for scheduled reporting, documentation upkeep, PR review, and more

What you'll build

You'll build a scheduled, AI-powered repository status report that runs in GitHub Actions and posts a useful summary without custom shell-script orchestration.

Preview of a completed workflow run in the GitHub Actions UI

Who this is for

You are... You'll get...
A developer new to agentic workflows A clear, end-to-end path from zero to a working automation
A GitHub Actions user A practical mental model for when agentic workflows are a better fit than classic YAML and scripts
A platform or DevOps engineer A reusable pattern for AI-assisted repository triage with auditable runs in GitHub
An evaluator, mentor, or workshop host A hands-on artifact that makes agentic workflow concepts easy to demonstrate and assess

What makes this different from a classic Actions tutorial

Instead of spending most of your time wiring together scripts, conditionals, and API calls, you define the workflow in a Markdown brief and let the agent reason over the repository at runtime.

That means you focus on:

  • the task you want completed
  • the repository context the agent should use
  • the trigger that should run the workflow
  • the output that should be published back to GitHub

Ready to begin?

➡️ Start with workshop/00-welcome.md

Note

Microsoft and GitHub facilitators: Request a demo environment at aka.ms/golden-ticket.


©️ GitHub • Code of ConductMIT License

@flynnjustin24

Copy link
Copy Markdown
Author

MarkItDown OCR Plugin

LLM Vision plugin for MarkItDown that extracts text from images embedded in PDF, DOCX, PPTX, and XLSX files.

Uses the same llm_client / llm_model pattern that MarkItDown already supports for image descriptions — no new ML libraries or binary dependencies required.

Features

  • Enhanced PDF Converter: Extracts text from images within PDFs, with full-page OCR fallback for scanned documents
  • Enhanced DOCX Converter: OCR for images in Word documents
  • Enhanced PPTX Converter: OCR for images in PowerPoint presentations
  • Enhanced XLSX Converter: OCR for images in Excel spreadsheets
  • Context Preservation: Maintains document structure and flow when inserting extracted text

Installation

pip install markitdown-ocr

The plugin uses whatever OpenAI-compatible client you already have. Install one if you don't have it yet:

pip install openai

Usage

Command Line

markitdown document.pdf --use-plugins --llm-client openai --llm-model gpt-4o

Python API

Pass llm_client and llm_model to MarkItDown() exactly as you would for image descriptions:

from markitdown import MarkItDown
from openai import OpenAI

md = MarkItDown(
    enable_plugins=True,
    llm_client=OpenAI(),
    llm_model="gpt-4o",
)

result = md.convert("document_with_images.pdf")
print(result.text_content)

If no llm_client is provided the plugin still loads, but OCR is silently skipped — falling back to the standard built-in converter.

Custom Prompt

Override the default extraction prompt for specialized documents:

md = MarkItDown(
    enable_plugins=True,
    llm_client=OpenAI(),
    llm_model="gpt-4o",
    llm_prompt="Extract all text from this image, preserving table structure.",
)

Any OpenAI-Compatible Client

Works with any client that follows the OpenAI API:

from openai import AzureOpenAI

md = MarkItDown(
    enable_plugins=True,
    llm_client=AzureOpenAI(
        api_key="...",
        azure_endpoint="https://your-resource.openai.azure.com/",
        api_version="2024-02-01",
    ),
    llm_model="gpt-4o",
)

How It Works

When MarkItDown(enable_plugins=True, llm_client=..., llm_model=...) is called:

  1. MarkItDown discovers the plugin via the markitdown.plugin entry point group
  2. It calls register_converters(), forwarding all kwargs including llm_client and llm_model
  3. The plugin creates an LLMVisionOCRService from those kwargs
  4. Four OCR-enhanced converters are registered at priority -1.0 — before the built-in converters at priority 0.0

When a file is converted:

  1. The OCR converter accepts the file
  2. It extracts embedded images from the document
  3. Each image is sent to the LLM with an extraction prompt
  4. The returned text is inserted inline, preserving document structure
  5. If the LLM call fails, conversion continues without that image's text

Supported File Formats

PDF

  • Embedded images are extracted by position (via page.images / page XObjects) and OCR'd inline, interleaved with the surrounding text in vertical reading order.
  • Scanned PDFs (pages with no extractable text) are detected automatically: each page is rendered at 300 DPI and sent to the LLM as a full-page image.
  • Malformed PDFs that pdfplumber/pdfminer cannot open (e.g. truncated EOF) are retried with PyMuPDF page rendering, so content is still recovered.

DOCX

  • Images are extracted via document part relationships (doc.part.rels).
  • OCR is run before the DOCX→HTML→Markdown pipeline executes: placeholder tokens are injected into the HTML so that the markdown converter does not escape the OCR markers, and the final placeholders are replaced with the formatted *[Image OCR]...[End OCR]* blocks after conversion.
  • Document flow (headings, paragraphs, tables) is fully preserved around the OCR blocks.

PPTX

  • Picture shapes, placeholder shapes with images, and images inside groups are all supported.
  • Shapes are processed in top-to-left reading order per slide.
  • If an llm_client is configured, the LLM is asked for a description first; OCR is used as the fallback when no description is returned.

XLSX

  • Images embedded in worksheets (sheet._images) are extracted per sheet.
  • Cell position is calculated from the image anchor coordinates (column/row → Excel letter notation).
  • Images are listed under a ### Images in this sheet: section after the sheet's data table — they are not interleaved into the table rows.

Output format

Every extracted OCR block is wrapped as:

*[Image OCR]
<extracted text>
[End OCR]*

Troubleshooting

OCR text missing from output

The most likely cause is a missing llm_client or llm_model. Verify:

from openai import OpenAI
from markitdown import MarkItDown

md = MarkItDown(
    enable_plugins=True,
    llm_client=OpenAI(),   # required
    llm_model="gpt-4o",    # required
)

Plugin not loading

Confirm the plugin is installed and discovered:

markitdown --list-plugins   # should show: ocr

API errors

The plugin propagates LLM API errors as warnings and continues conversion. Check your API key, quota, and that the chosen model supports vision inputs.

Development

Running Tests

cd packages/markitdown-ocr
pytest tests/ -v

Building from Source

git clone https://github.com/microsoft/markitdown.git
cd markitdown/packages/markitdown-ocr
pip install -e .

Contributing

Contributions are welcome! See the MarkItDown repository for guidelines.

License

MIT — see LICENSE.

Changelog

0.1.0 (Initial Release)

  • LLM Vision OCR for PDF, DOCX, PPTX, XLSX
  • Full-page OCR fallback for scanned PDFs
  • Context-aware inline text insertion
  • Priority-based converter replacement (no code changes required)

@flynnjustin24

Copy link
Copy Markdown
Author

name: Step 5

on:
pull_request:
branches:
- main
types:
- closed

permissions:
contents: write
actions: write
issues: write

env:
REVIEW_FILE: ".github/steps/x-review.md"

jobs:
find_exercise:
name: Find Exercise Issue
uses: skills/exercise-toolkit/.github/workflows/find-exercise-issue.yml@v0.6.0

post_review_content:
name: Post review content
needs: [find_exercise]
runs-on: ubuntu-latest
env:
ISSUE_URL: ${{ needs.find_exercise.outputs.issue-url }}

steps:
  - name: Checkout
    uses: actions/checkout@v4

  - name: Create comment - add step content
    run: |
      gh issue comment "$ISSUE_URL" \
        --body-file "$REVIEW_FILE"
    env:
      GH_TOKEN: ${{ secrets.GITHUB_TOKEN }}

finish_exercise:
name: Finish Exercise
needs: [find_exercise, post_review_content]
uses: skills/exercise-toolkit/.github/workflows/finish-exercise.yml@v0.6.0
with:
issue-url: ${{ needs.find_exercise.outputs.issue-url }}
exercise-title: "Hello GitHub Actions"

disable_workflow:
name: Disable this workflow
needs: [find_exercise, post_review_content]
runs-on: ubuntu-latest
steps:
- name: Checkout
uses: actions/checkout@v4
- name: Disable current workflow
run: gh workflow disable "${{github.workflow}}"
env:
GH_TOKEN: ${{ secrets.GITHUB_TOKEN }}

@flynnjustin24

Copy link
Copy Markdown
Author

name: Step 4

on:
pull_request:
branches:
- main
types:
- opened

permissions:
contents: write
actions: write
issues: write

env:
STEP_5_FILE: ".github/steps/5-step.md"

jobs:
find_exercise:
name: Find Exercise Issue
uses: skills/exercise-toolkit/.github/workflows/find-exercise-issue.yml@v0.6.0

post_next_step_content:
name: Post next step content
needs: [find_exercise]
runs-on: ubuntu-latest
env:
ISSUE_URL: ${{ needs.find_exercise.outputs.issue-url }}
steps:
- name: Checkout
uses: actions/checkout@v4

  - name: Get response templates
    uses: actions/checkout@v4
    with:
      repository: skills/exercise-toolkit
      path: exercise-toolkit
      ref: v0.6.0

  - name: Create comment - add step content
    run: |
      gh issue comment "$ISSUE_URL" \
        --body-file "$STEP_5_FILE"
    env:
      GH_TOKEN: ${{ secrets.GITHUB_TOKEN }}

  - name: Create comment - watching for progress
    run: |
      gh issue comment "$ISSUE_URL" \
        --body-file exercise-toolkit/markdown-templates/step-feedback/watching-for-progress.md
    env:
      GH_TOKEN: ${{ secrets.GITHUB_TOKEN }}

  - name: Disable current workflow and enable next one
    run: |
      gh workflow disable "${{github.workflow}}"
      gh workflow enable "Step 5"
    env:
      GH_TOKEN: ${{ secrets.GITHUB_TOKEN }}

@flynnjustin24

Copy link
Copy Markdown
Author

name: Step 3

on:
push:
branches:
- welcome-workflow
paths:
- ".github/workflows/welcome.yml"

permissions:
contents: read
actions: write
issues: write

env:
STEP_4_FILE: ".github/steps/4-step.md"

jobs:
find_exercise:
name: Find Exercise Issue
uses: skills/exercise-toolkit/.github/workflows/find-exercise-issue.yml@v0.6.0

check_step_work:
name: Check step work
runs-on: ubuntu-latest
needs: [find_exercise]
env:
ISSUE_URL: ${{ needs.find_exercise.outputs.issue-url }}

steps:
  - name: Checkout
    uses: actions/checkout@v4

  - name: Get response templates
    uses: actions/checkout@v4
    with:
      repository: skills/exercise-toolkit
      path: exercise-toolkit
      ref: v0.6.0

  - name: Update comment - checking work
    run: |
      gh issue comment "$ISSUE_URL" \
        --body-file exercise-toolkit/markdown-templates/step-feedback/checking-work.md \
        --edit-last
    env:
      GH_TOKEN: ${{ secrets.GITHUB_TOKEN }}

  - name: Lint welcome.yml with actionlint
    id: actionlint-check
    continue-on-error: true
    uses: raven-actions/actionlint@v2.1.1
    with:
      files: .github/workflows/welcome.yml
      version: 1.7.10
      fail-on-error: true

  - name: Check for steps section in welcome.yml
    id: check-steps-section
    continue-on-error: true
    uses: skills/action-keyphrase-checker@v1
    with:
      text-file: .github/workflows/welcome.yml
      keyphrase: "steps:"

  - name: Check for gh pr comment command in welcome.yml
    id: check-gh-pr-comment
    continue-on-error: true
    uses: skills/action-keyphrase-checker@v1
    with:
      text-file: .github/workflows/welcome.yml
      keyphrase: "gh pr comment"

  - name: Check for GITHUB_TOKEN env var in welcome.yml
    id: check-github-token
    continue-on-error: true
    uses: skills/action-keyphrase-checker@v1
    with:
      text-file: .github/workflows/welcome.yml
      keyphrase: "GITHUB_TOKEN:"

  - name: Check for PR_URL env var in welcome.yml
    id: check-pr-url
    continue-on-error: true
    uses: skills/action-keyphrase-checker@v1
    with:
      text-file: .github/workflows/welcome.yml
      keyphrase: "PR_URL:"

  - name: Build message - step results
    id: build-message-step-results
    uses: skills/action-text-variables@v2
    with:
      template-file: exercise-toolkit/markdown-templates/step-feedback/step-results-table.md
      template-vars: |
        step_number: 3
        passed: ${{ !contains(steps.*.outcome, 'failure') }}
        results_table:
          - description: "Workflow file syntax validation"
            passed: ${{ steps.actionlint-check.outcome == 'success' }}
          - description: "Added steps section to welcome job"
            passed: ${{ steps.check-steps-section.outcome == 'success' }}
          - description: "Added gh pr comment command"
            passed: ${{ steps.check-gh-pr-comment.outcome == 'success' }}
          - description: "Set GITHUB_TOKEN environment variable"
            passed: ${{ steps.check-github-token.outcome == 'success' }}
          - description: "Set PR_URL environment variable"
            passed: ${{ steps.check-pr-url.outcome == 'success' }}

  - name: Create comment - step results
    run: |
      gh issue comment "$ISSUE_URL" \
        --body "$COMMENT_BODY" \
        --edit-last
    env:
      GH_TOKEN: ${{ secrets.GITHUB_TOKEN }}
      COMMENT_BODY: ${{ steps.build-message-step-results.outputs.updated-text }}

  - name: Fail job if not all checks passed
    if: contains(steps.*.outcome, 'failure')
    run: exit 1

  - name: Build message - step finished
    id: build-message-step-finish
    uses: skills/action-text-variables@v2
    with:
      template-file: exercise-toolkit/markdown-templates/step-feedback/step-finished-prepare-next-step.md
      template-vars: |
        next_step_number: 4

  - name: Update comment - step finished
    run: |
      gh issue comment "$ISSUE_URL" \
        --body "$ISSUE_BODY"
    env:
      GH_TOKEN: ${{ secrets.GITHUB_TOKEN }}
      ISSUE_BODY: ${{ steps.build-message-step-finish.outputs.updated-text }}

post_next_step_content:
name: Post next step content
needs: [find_exercise, check_step_work]
runs-on: ubuntu-latest
env:
ISSUE_URL: ${{ needs.find_exercise.outputs.issue-url }}
steps:
- name: Checkout
uses: actions/checkout@v4

  - name: Get response templates
    uses: actions/checkout@v4
    with:
      repository: skills/exercise-toolkit
      path: exercise-toolkit
      ref: v0.6.0

  - name: Create comment - add step content
    run: |
      gh issue comment "$ISSUE_URL" \
        --body-file "$STEP_4_FILE"
    env:
      GH_TOKEN: ${{ secrets.GITHUB_TOKEN }}

  - name: Create comment - watching for progress
    run: |
      gh issue comment "$ISSUE_URL" \
        --body-file exercise-toolkit/markdown-templates/step-feedback/watching-for-progress.md
    env:
      GH_TOKEN: ${{ secrets.GITHUB_TOKEN }}

  - name: Disable current workflow and enable next one
    run: |
      gh workflow disable "${{github.workflow}}"
      gh workflow enable "Step 4"
    env:
      GH_TOKEN: ${{ secrets.GITHUB_TOKEN }}

@flynnjustin24

Copy link
Copy Markdown
Author

name: Step 2

on:
push:
branches:
- welcome-workflow

permissions:
contents: write
actions: write
issues: write

env:
STEP_3_FILE: ".github/steps/3-step.md"

jobs:
find_exercise:
name: Find Exercise Issue
uses: skills/exercise-toolkit/.github/workflows/find-exercise-issue.yml@v0.6.0

check_step_work:
name: Check step work
runs-on: ubuntu-latest
needs: [find_exercise]
env:
ISSUE_URL: ${{ needs.find_exercise.outputs.issue-url }}

steps:
  - name: Checkout
    uses: actions/checkout@v4

  - name: Get response templates
    uses: actions/checkout@v4
    with:
      repository: skills/exercise-toolkit
      path: exercise-toolkit
      ref: v0.6.0

  - name: Update comment - checking work
    run: |
      gh issue comment "$ISSUE_URL" \
        --body-file exercise-toolkit/markdown-templates/step-feedback/checking-work.md \
        --edit-last
    env:
      GH_TOKEN: ${{ secrets.GITHUB_TOKEN }}

  - name: Check for jobs section in welcome.yml
    id: check-jobs-section
    continue-on-error: true
    uses: skills/action-keyphrase-checker@v1
    with:
      text-file: .github/workflows/welcome.yml
      keyphrase: "jobs:"

  - name: Check for welcome job in welcome.yml
    id: check-welcome-job
    continue-on-error: true
    uses: skills/action-keyphrase-checker@v1
    with:
      text-file: .github/workflows/welcome.yml
      keyphrase: "welcome:"

  - name: Check for runs-on ubuntu-latest in welcome.yml
    id: check-runs-on
    continue-on-error: true
    uses: skills/action-keyphrase-checker@v1
    with:
      text-file: .github/workflows/welcome.yml
      keyphrase: "runs-on: ubuntu-latest"

  - name: Build message - step results
    id: build-message-step-results
    uses: skills/action-text-variables@v2
    with:
      template-file: exercise-toolkit/markdown-templates/step-feedback/step-results-table.md
      template-vars: |
        step_number: 2
        passed: ${{ !contains(steps.*.outcome, 'failure') }}
        results_table:
          - description: "Added jobs section to workflow file"
            passed: ${{ steps.check-jobs-section.outcome == 'success' }}
          - description: "Created welcome job"
            passed: ${{ steps.check-welcome-job.outcome == 'success' }}
          - description: "Set runs-on to ubuntu-latest"
            passed: ${{ steps.check-runs-on.outcome == 'success' }}

  - name: Create comment - step results
    run: |
      gh issue comment "$ISSUE_URL" \
        --body "$COMMENT_BODY" \
        --edit-last
    env:
      GH_TOKEN: ${{ secrets.GITHUB_TOKEN }}
      COMMENT_BODY: ${{ steps.build-message-step-results.outputs.updated-text }}

  - name: Fail job if not all checks passed
    if: contains(steps.*.outcome, 'failure')
    run: exit 1

  - name: Build message - step finished
    id: build-message-step-finish
    uses: skills/action-text-variables@v2
    with:
      template-file: exercise-toolkit/markdown-templates/step-feedback/step-finished-prepare-next-step.md
      template-vars: |
        next_step_number: 3

  - name: Update comment - step finished
    run: |
      gh issue comment "$ISSUE_URL" \
        --body "$ISSUE_BODY"
    env:
      GH_TOKEN: ${{ secrets.GITHUB_TOKEN }}
      ISSUE_BODY: ${{ steps.build-message-step-finish.outputs.updated-text }}

post_next_step_content:
name: Post next step content
needs: [find_exercise, check_step_work]
runs-on: ubuntu-latest
env:
ISSUE_URL: ${{ needs.find_exercise.outputs.issue-url }}

steps:
  - name: Checkout
    uses: actions/checkout@v4
  - name: Get response templates
    uses: actions/checkout@v4
    with:
      repository: skills/exercise-toolkit
      path: exercise-toolkit
      ref: v0.6.0

  - name: Create comment - add step content
    run: |
      gh issue comment "$ISSUE_URL" \
        --body-file "$STEP_3_FILE"
    env:
      GH_TOKEN: ${{ secrets.GITHUB_TOKEN }}

  - name: Create comment - watching for progress
    run: |
      gh issue comment "$ISSUE_URL" \
        --body-file exercise-toolkit/markdown-templates/step-feedback/watching-for-progress.md
    env:
      GH_TOKEN: ${{ secrets.GITHUB_TOKEN }}

  - name: Disable current workflow and enable next one
    run: |
      gh workflow disable "${{github.workflow}}"
      gh workflow enable "Step 3"
    env:
      GH_TOKEN: ${{ secrets.GITHUB_TOKEN }}

@flynnjustin24

Copy link
Copy Markdown
Author

name: Step 1

on:
push:
branches:
- welcome-workflow
paths:
- ".github/**"

permissions:
contents: read
actions: write
issues: write

env:
STEP_2_FILE: ".github/steps/2-step.md"

jobs:
find_exercise:
name: Find Exercise Issue
uses: skills/exercise-toolkit/.github/workflows/find-exercise-issue.yml@v0.6.0

check_step_work:
name: Check step work
runs-on: ubuntu-latest
needs: [find_exercise]
env:
ISSUE_URL: ${{ needs.find_exercise.outputs.issue-url }}

steps:
  - name: Checkout
    uses: actions/checkout@v4

  - name: Get response templates
    uses: actions/checkout@v4
    with:
      repository: skills/exercise-toolkit
      path: exercise-toolkit
      ref: v0.6.0

  - name: Update comment - checking work
    run: |
      gh issue comment "$ISSUE_URL" \
        --body-file exercise-toolkit/markdown-templates/step-feedback/checking-work.md \
        --edit-last
    env:
      GH_TOKEN: ${{ secrets.GITHUB_TOKEN }}

  - name: Check if welcome.yml file exists
    id: check-file-exists
    continue-on-error: true
    uses: skills/exercise-toolkit/actions/file-exists@v0.6.0
    with:
      file: .github/workflows/welcome.yml

  - name: Check for workflow name in welcome.yml
    id: check-workflow-name
    continue-on-error: true
    uses: skills/action-keyphrase-checker@v1
    with:
      text-file: .github/workflows/welcome.yml
      keyphrase: "name:"

  - name: Check for pull_request event in welcome.yml
    id: check-pull-request-event
    continue-on-error: true
    uses: skills/action-keyphrase-checker@v1
    with:
      text-file: .github/workflows/welcome.yml
      keyphrase: "pull_request:"

  - name: Check for types filter
    id: check-opened-type
    continue-on-error: true
    uses: skills/action-keyphrase-checker@v1
    with:
      text-file: .github/workflows/welcome.yml
      keyphrase: "types:"

  - name: Check for permissions in welcome.yml
    id: check-permissions
    continue-on-error: true
    uses: skills/action-keyphrase-checker@v1
    with:
      text-file: .github/workflows/welcome.yml
      keyphrase: "pull-requests: write"

  - name: Build message - step results
    id: build-message-step-results
    uses: skills/action-text-variables@v2
    with:
      template-file: exercise-toolkit/markdown-templates/step-feedback/step-results-table.md
      template-vars: |
        step_number: 1
        passed: ${{ !contains(steps.*.outcome, 'failure') }}
        results_table:
          - description: "Created welcome.yml file in .github/workflows directory"
            passed: ${{ steps.check-file-exists.outcome == 'success' }}
          - description: "Added a workflow name field"
            passed: ${{ steps.check-workflow-name.outcome == 'success' }}
          - description: "Configured pull_request event trigger"
            passed: ${{ steps.check-pull-request-event.outcome == 'success' }}
          - description: "Set types filter for pull_request event"
            passed: ${{ steps.check-opened-type.outcome == 'success' }}
          - description: "Added pull-requests: write permission"
            passed: ${{ steps.check-permissions.outcome == 'success' }}

  - name: Create comment - step results
    run: |
      gh issue comment "$ISSUE_URL" \
        --body "$COMMENT_BODY" \
        --edit-last
    env:
      GH_TOKEN: ${{ secrets.GITHUB_TOKEN }}
      COMMENT_BODY: ${{ steps.build-message-step-results.outputs.updated-text }}

  - name: Fail job if not all checks passed
    if: contains(steps.*.outcome, 'failure')
    run: exit 1

  - name: Build message - step finished
    id: build-message-step-finish
    uses: skills/action-text-variables@v2
    with:
      template-file: exercise-toolkit/markdown-templates/step-feedback/step-finished-prepare-next-step.md
      template-vars: |
        next_step_number: 2

  - name: Update comment - step finished
    run: |
      gh issue comment "$ISSUE_URL" \
        --body "$ISSUE_BODY"
    env:
      GH_TOKEN: ${{ secrets.GITHUB_TOKEN }}
      ISSUE_BODY: ${{ steps.build-message-step-finish.outputs.updated-text }}

post_next_step_content:
name: Post next step content
needs: [find_exercise, check_step_work]
runs-on: ubuntu-latest
env:
ISSUE_URL: ${{ needs.find_exercise.outputs.issue-url }}

steps:
  - name: Checkout
    uses: actions/checkout@v4

  - name: Get response templates
    uses: actions/checkout@v4
    with:
      repository: skills/exercise-toolkit
      path: exercise-toolkit
      ref: v0.6.0

  - name: Create comment - add step content
    run: |
      gh issue comment "$ISSUE_URL" \
        --body-file "$STEP_2_FILE"
    env:
      GH_TOKEN: ${{ secrets.GITHUB_TOKEN }}

  - name: Create comment - watching for progress
    run: |
      gh issue comment "$ISSUE_URL" \
        --body-file exercise-toolkit/markdown-templates/step-feedback/watching-for-progress.md
    env:
      GH_TOKEN: ${{ secrets.GITHUB_TOKEN }}

  - name: Disable current workflow and enable next one
    run: |
      gh workflow disable "${{github.workflow}}"
      gh workflow enable "Step 2"
    env:
      GH_TOKEN: ${{ secrets.GITHUB_TOKEN }}

@flynnjustin24

Copy link
Copy Markdown
Author

GitHub Actions Workflow

This repository uses GitHub Actions to automate building, testing, and deploying the project.

Overview

Workflows live in .github/workflows/ and run automatically on events like pushes, pull requests, or manual triggers.

Workflow Files

File Trigger Purpose
.github/workflows/ci.yml Push / PR to main Runs linting and tests
.github/workflows/deploy.yml Push to main Builds and deploys the app

(Update this table to match your actual workflow files.)

CI Workflow (ci.yml)

Runs on every push and pull request targeting main:

  1. Checks out the code
  2. Sets up the runtime environment
  3. Installs dependencies
  4. Runs linters
  5. Runs the test suite
name: CI

on:
  push:
    branches: [main]
  pull_request:
    branches: [main]

jobs:
  build:
    runs-on: ubuntu-latest
    steps:
      - uses: actions/checkout@v4
      - name: Set up environment
        run: echo "Add setup steps here"
      - name: Install dependencies
        run: echo "Add install steps here"
      - name: Run tests
        run: echo "Add test steps here"

Deploy Workflow (deploy.yml)

Runs on push to main after CI passes, deploying to production/staging.

name: Deploy

on:
  push:
    branches: [main]

jobs:
  deploy:
    runs-on: ubuntu-latest
    steps:
      - uses: actions/checkout@v4
      - name: Deploy
        run: echo "Add deploy steps here"

Required Secrets

Set these in Settings → Secrets and variables → Actions:

  • SECRET_NAME_1 — description
  • SECRET_NAME_2 — description

Branching Workflow

  1. Create a feature branch from main: git checkout -b feature/my-change
  2. Commit changes and push the branch
  3. Open a pull request into main
  4. CI runs automatically; address any failures
  5. Merge once approved and checks pass

Running Workflows Manually

If a workflow supports workflow_dispatch, trigger it from:
Actions tab → select workflow → Run workflow

Troubleshooting

  • Check the Actions tab for run logs
  • Re-run failed jobs via the Re-run jobs button
  • Ensure required secrets and permissions are configured correctly

@flynnjustin24
flynnjustin24 changed the base branch from main to starter_workflow_new_exp August 5, 2026 04:21
@flynnjustin24
flynnjustin24 changed the base branch from starter_workflow_new_exp to Add_new August 5, 2026 04:22
@flynnjustin24
flynnjustin24 changed the base branch from Add_new to add_template_categories August 5, 2026 04:22
@flynnjustin24
flynnjustin24 changed the base branch from add_template_categories to andymckay-patch-1 August 5, 2026 04:22
@flynnjustin24
flynnjustin24 changed the base branch from andymckay-patch-1 to cschleiden/experiment August 5, 2026 04:23
@flynnjustin24
flynnjustin24 changed the base branch from cschleiden/experiment to dependabot/github_actions/actions/checkout-5 August 5, 2026 04:23
@flynnjustin24
flynnjustin24 requested a review from a team as a code owner August 5, 2026 04:23
@flynnjustin24
flynnjustin24 changed the base branch from dependabot/github_actions/actions/checkout-5 to dependabot/github_actions/actions/labeler-6 August 5, 2026 04:23
@flynnjustin24
flynnjustin24 changed the base branch from dependabot/github_actions/actions/labeler-6 to dependabot/github_actions/actions/setup-python-6 August 5, 2026 04:23
@flynnjustin24
flynnjustin24 changed the base branch from dependabot/github_actions/actions/setup-python-6 to dependabot/github_actions/kentaro-m/auto-assign-action-2.0.0 August 5, 2026 04:24
@flynnjustin24
flynnjustin24 changed the base branch from dependabot/github_actions/kentaro-m/auto-assign-action-2.0.0 to starter_workflow_new_exp August 5, 2026 04:25

@flynnjustin24 flynnjustin24 left a comment

Copy link
Copy Markdown
Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

GitHub Agentic Workflows Factory Tour

Important

GitHub Agentic Workflows and the gh-aw CLI are in public preview. You may notice product changes, rough edges, or minor differences from the screenshots and examples in this workshop.

Mona's Agent Factory

What you will learn to build

Build a real AI-powered GitHub workflow from scratch and leave with a safe production-style agentic automation you can adapt to your own repositories.

Sample daily repository status report generated by the finished workflow

Why this workshop

Most workflow tutorials stop at toy examples. This workshop takes you all the way to a useful end result: an agentic workflow that runs in GitHub Actions, inspects a repository, and publishes a daily status report automatically.

By the time you finish, you will know how to:

  • define an agentic workflow in Markdown
  • use the gh-aw CLI to validate, run, and iterate on workflows
  • connect triggers, prompts, and GitHub context into one practical automation
  • adapt the pattern for scheduled reporting, documentation upkeep, PR review, and more

What you'll build

You'll build a scheduled, AI-powered repository status report that runs in GitHub Actions and posts a useful summary without custom shell-script orchestration.

Preview of a completed workflow run in the GitHub Actions UI

Who this is for

You are... You'll get...
A developer new to agentic workflows A clear, end-to-end path from zero to a working automation
A GitHub Actions user A practical mental model for when agentic workflows are a better fit than classic YAML and scripts
A platform or DevOps engineer A reusable pattern for AI-assisted repository triage with auditable runs in GitHub
An evaluator, mentor, or workshop host A hands-on artifact that makes agentic workflow concepts easy to demonstrate and assess

What makes this different from a classic Actions tutorial

Instead of spending most of your time wiring together scripts, conditionals, and API calls, you define the workflow in a Markdown brief and let the agent reason over the repository at runtime.

That means you focus on:

  • the task you want completed
  • the repository context the agent should use
  • the trigger that should run the workflow
  • the output that should be published back to GitHub

Ready to begin?

➡️ Start with workshop/00-welcome.md

Note

Microsoft and GitHub facilitators: Request a demo environment at aka.ms/golden-ticket.


©️ GitHub • Code of ConductMIT License

@flynnjustin24
flynnjustin24 changed the base branch from starter_workflow_new_exp to updae_azure_python_cache August 5, 2026 06:07
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

code-scanning Related to workflows that show on the Code Scanning setup page

Projects

None yet

Development

Successfully merging this pull request may close these issues.