Skip to content

Fix: Resolve syntax error in workflow and improve label checker error handling#4739

Open
HLUSN wants to merge 1 commit intowso2:mainfrom
HLUSN:main
Open

Fix: Resolve syntax error in workflow and improve label checker error handling#4739
HLUSN wants to merge 1 commit intowso2:mainfrom
HLUSN:main

Conversation

@HLUSN
Copy link

@HLUSN HLUSN commented Mar 1, 2026

Description

Hi! I found some bugs in the GitHub Actions workflows that were causing automation failures, so I went ahead and fixed them.

What I Fixed

1. Missing Quote in resolution_label_notifier.yml (Line 18)

There was a missing closing quote on 'Resolution/Done' that would break the entire workflow. The GitHub Action wouldn't even start running because of this syntax error, which meant issues weren't being validated properly when closed. I added the missing quote to fix it.

2. Several Problems in label_checker.py

While reviewing the label checker script, I noticed a few issues:

The version extraction was too rigid - It was hardcoded to grab exactly 5 characters for the version number ([j+13:j+18]), which breaks for versions like "4.3.0-beta" or anything that isn't exactly 5 characters long. I changed it to dynamically read until it hits a newline or the next section.

No safety checks - The script would crash if the ISSUE_BODY environment variable was missing or if someone submitted an issue without the required template headers. I added proper error handling so it fails gracefully instead.

Wrong calculation - The component extraction was using an offset of 23 instead of 25 characters, which could cause it to miss the actual component name.

What I did:

  • Wrapped everything in a try-catch block so errors don't crash the workflow
  • Made version extraction flexible to handle any length
  • Added checks to make sure required data exists before trying to use it
  • Fixed the offset math
  • Made sure it always returns "Missing/Component" as a safe fallback

Testing

I've verified that the YAML syntax is now valid, the Python script handles edge cases properly, and there are no linting errors in either file.

Summary by CodeRabbit

  • Bug Fixes
    • Fixed a critical GitHub workflow condition syntax error that was preventing the issue resolution workflow from executing correctly.
    • Enhanced issue body validation with improved error handling to gracefully manage missing or incomplete issue metadata sections.
    • Improved label extraction and application logic with better whitespace trimming and validation against existing label definitions.

Copilot AI review requested due to automatic review settings March 1, 2026 05:57
@CLAassistant
Copy link

CLA assistant check
Thank you for your submission! We really appreciate it. Like many open source projects, we ask that you sign our Contributor License Agreement before we can accept your contribution.
You have signed the CLA already but the status is still pending? Let us recheck it.

@coderabbitai
Copy link

coderabbitai bot commented Mar 1, 2026

Walkthrough

This PR enhances error handling in the GitHub Actions label checker script and fixes a syntax error in the resolution label notifier workflow. The label checker now includes preliminary validation, robust try/except wrapping, and more flexible version extraction logic. The resolution notifier fix resolves a missing quote in a conditional string check.

Changes

Cohort / File(s) Summary
Label Checker Enhancement
.github/workflows/label_checker.py
Adds robust issue body handling with try/except wrapper. Implements preliminary checks for required sections ("### Affected Component" and "### Version"), recomputes component extraction with adjusted offset, and introduces flexible version extraction that reads up to newline or next section. Only emits labels if they exist in all_existing_labels.
Workflow Syntax Fix
.github/workflows/resolution_label_notifier.yml
Fixes syntax error by properly closing the string literal for the 'Resolution/Done' label in the contains(...) check within the workflow gate condition.

Estimated code review effort

🎯 2 (Simple) | ⏱️ ~10 minutes

Poem

🐰 A rabbit checks each label with care,
Components and versions pair by pair,
Syntax errors fixed without a fuss,
GitHub workflows now work for us! ✨

🚥 Pre-merge checks | ✅ 3
✅ Passed checks (3 passed)
Check name Status Explanation
Description Check ✅ Passed Check skipped - CodeRabbit’s high-level summary is enabled.
Title check ✅ Passed The title accurately summarizes both main changes in the pull request: fixing a syntax error in the workflow file and improving error handling in the label checker script.
Docstring Coverage ✅ Passed No functions found in the changed files to evaluate docstring coverage. Skipping docstring coverage check.

✏️ Tip: You can configure your own custom pre-merge checks in the settings.

✨ Finishing Touches
🧪 Generate unit tests (beta)
  • Create PR with unit tests
  • Post copyable unit tests in a comment

Tip

Try Coding Plans. Let us write the prompt for your AI agent so you can ship faster (with fewer bugs).
Share your feedback on Discord.


Thanks for using CodeRabbit! It's free for OSS, and your support helps us grow. If you like it, consider giving us a shout-out.

❤️ Share

Comment @coderabbitai help to get the list of available commands and usage tips.

Copy link

Copilot AI left a comment

Choose a reason for hiding this comment

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

Pull request overview

This PR fixes a GitHub Actions workflow YAML syntax error that prevented the “resolution label” automation from running, and updates the issue label checker script to be more resilient to missing/variant issue template content.

Changes:

  • Fix malformed string quoting in resolution_label_notifier.yml so the workflow can execute.
  • Add error handling and more flexible parsing in label_checker.py for extracting component/version from issue bodies.

Reviewed changes

Copilot reviewed 2 out of 2 changed files in this pull request and generated 3 comments.

File Description
.github/workflows/resolution_label_notifier.yml Fixes a broken contains(...) condition by correcting a missing closing quote.
.github/workflows/label_checker.py Adds guarded parsing + fallback behavior for component/version extraction to prevent runtime crashes.

💡 Add Copilot custom instructions for smarter, more guided reviews. Learn how to get started.

Comment on lines +27 to +29
i = issue_body.index("### Affected Component")
j = issue_body.index("### Version")
component = issue_body[i+25:j].strip()
Copy link

Copilot AI Mar 1, 2026

Choose a reason for hiding this comment

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

component = issue_body[i+25:j].strip() relies on a hard-coded offset that can truncate the first character of the component depending on whether the issue body uses \n\n vs \r\n\r\n after the header. Safer approach is to slice from i + len('### Affected Component') and then trim leading whitespace/newlines (or parse the section by splitting on headers / using a regex).

Suggested change
i = issue_body.index("### Affected Component")
j = issue_body.index("### Version")
component = issue_body[i+25:j].strip()
affected_header = "### Affected Component"
i = issue_body.index(affected_header)
j = issue_body.index("### Version")
component = issue_body[i + len(affected_header):j].strip()

Copilot uses AI. Check for mistakes.
Comment on lines +35 to +36
version_start = j + 13
version_text = issue_body[version_start:].strip()
Copy link

Copilot AI Mar 1, 2026

Choose a reason for hiding this comment

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

The version_start = j + 13 offset is still hard-coded to a specific header+newline layout. This can break with different newline conventions or template formatting. Consider deriving the start index from len('### Version') and then skipping any following whitespace/newlines before extracting the value (or reuse the same section-parsing helper as for the component).

Suggested change
version_start = j + 13
version_text = issue_body[version_start:].strip()
header = "### Version"
header_len = len(header)
version_start = j + header_len
# Skip any whitespace/newlines immediately after the header
while version_start < len(issue_body) and issue_body[version_start] in (" ", "\t", "\r", "\n"):
version_start += 1
version_text = issue_body[version_start:]

Copilot uses AI. Check for mistakes.
Comment on lines +18 to +25
if not issue_body:
print("Missing/Component")
sys.exit(0)

# Get affected component
if "### Affected Component" not in issue_body or "### Version" not in issue_body:
print("Missing/Component")
sys.exit(0)
Copy link

Copilot AI Mar 1, 2026

Choose a reason for hiding this comment

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

The fallback print('Missing/Component') bypasses the existing-label check and will make gh issue edit --add-label $labels fail if that label doesn’t already exist in the repo. Either verify Missing/Component is in all_existing_labels before printing it, or print an empty string and have the workflow skip --add-label when no valid labels were found.

Copilot uses AI. Check for mistakes.
Copy link

@coderabbitai coderabbitai bot left a comment

Choose a reason for hiding this comment

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

Actionable comments posted: 1

🧹 Nitpick comments (1)
.github/workflows/label_checker.py (1)

56-59: Remove unused exception variable.

The exception variable e is assigned but never used. Replace with _ to indicate intentional discard, or log it for debugging purposes.

🧹 Proposed fix
-except Exception as e:
+except Exception:
     # If any error occurs, default to Missing/Component label
     print("Missing/Component")
     sys.exit(0)

Alternatively, if you want to preserve error info for debugging in workflow logs:

-except Exception as e:
+except Exception as e:
     # If any error occurs, default to Missing/Component label
+    print(f"Error processing issue body: {e}", file=sys.stderr)
     print("Missing/Component")
     sys.exit(0)
🤖 Prompt for AI Agents
Verify each finding against the current code and only fix it if needed.

In @.github/workflows/label_checker.py around lines 56 - 59, The except block
currently declares an unused exception variable `e` in `except Exception as e:`;
remove or use it: either change the clause to `except Exception:` (or `except
Exception as _:`) to indicate the exception is intentionally discarded, or
capture and log it (e.g., via `print(e)` or `logging.exception`) before the
existing `print("Missing/Component")` and `sys.exit(0)` so the error info is
preserved for debugging.
🤖 Prompt for all review comments with AI agents
Verify each finding against the current code and only fix it if needed.

Inline comments:
In @.github/workflows/label_checker.py:
- Around line 27-32: The current logic that slices issue_body using index("###
Affected Component") fails because GitHub form output is plain text; replace
that slicing with a regex search against issue_body (e.g., a multiline regex
that finds the plain "Affected Component" label and captures the user-provided
value on the same line or the following line) to set component and
component_label and append to labels only if it matches all_existing_labels;
also remove the unused variable e and change the broad except Exception handler
to catch specific errors (e.g., ValueError/IndexError from parsing or re-related
exceptions) so parsing failures fall back to adding "Missing/Component" without
hiding other bugs.

---

Nitpick comments:
In @.github/workflows/label_checker.py:
- Around line 56-59: The except block currently declares an unused exception
variable `e` in `except Exception as e:`; remove or use it: either change the
clause to `except Exception:` (or `except Exception as _:`) to indicate the
exception is intentionally discarded, or capture and log it (e.g., via
`print(e)` or `logging.exception`) before the existing
`print("Missing/Component")` and `sys.exit(0)` so the error info is preserved
for debugging.

ℹ️ Review info

Configuration used: Organization UI

Review profile: CHILL

Plan: Pro

📥 Commits

Reviewing files that changed from the base of the PR and between c16a70e and 7eb7524.

📒 Files selected for processing (2)
  • .github/workflows/label_checker.py
  • .github/workflows/resolution_label_notifier.yml

Comment on lines +27 to +32
i = issue_body.index("### Affected Component")
j = issue_body.index("### Version")
component = issue_body[i+25:j].strip()
component_label = "Component/" + component
if component_label in all_existing_labels:
labels.append(component_label)
Copy link

Choose a reason for hiding this comment

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

⚠️ Potential issue | 🔴 Critical

🧩 Analysis chain

🏁 Script executed:

# Find the label_checker.py file and examine its content
find . -name "label_checker.py" -type f

Repository: wso2/api-manager

Length of output: 96


🏁 Script executed:

# List files in .github directory to understand structure
ls -la .github/ | head -20

Repository: wso2/api-manager

Length of output: 359


🏁 Script executed:

# Search for issue template files
find .github -type f \( -name "*.md" -o -name "*.yml" -o -name "*.yaml" \) | grep -i template

Repository: wso2/api-manager

Length of output: 328


🏁 Script executed:

# Read the label_checker.py file to see the implementation
cat -n .github/workflows/label_checker.py

Repository: wso2/api-manager

Length of output: 2416


🏁 Script executed:

# Check one of the issue template files to see the actual format
cat .github/ISSUE_TEMPLATE/bug.yml

Repository: wso2/api-manager

Length of output: 1039


🏁 Script executed:

# Check another issue template to see if format is consistent
cat .github/ISSUE_TEMPLATE/new-feature.yml

Repository: wso2/api-manager

Length of output: 895


🏁 Script executed:

# Search for "Affected Component" in the codebase to see if it's defined anywhere
rg -i "affected component" --type md --type yml --type yaml

Repository: wso2/api-manager

Length of output: 87


🏁 Script executed:

# Check if there are any other references to this in the repository
rg -i "affected component" -type py

Repository: wso2/api-manager

Length of output: 87


🏁 Script executed:

# Let's check all issue templates to see which ones might have these fields
for file in .github/ISSUE_TEMPLATE/*.yml; do echo "=== $file ===" && cat "$file"; done

Repository: wso2/api-manager

Length of output: 5198


🏁 Script executed:

# Let's check the git history to see if these templates were recently changed
git log --oneline .github/ISSUE_TEMPLATE/ | head -20

Repository: wso2/api-manager

Length of output: 149


🏁 Script executed:

# Check if there are any other references to "Affected Component" in the codebase
rg "Affected Component"

Repository: wso2/api-manager

Length of output: 42


🏁 Script executed:

# Let's verify how GitHub renders issue form bodies by checking any documentation or examples
rg "### Affected" -A 3 -B 3

Repository: wso2/api-manager

Length of output: 42


🏁 Script executed:

# Check when the label_checker.py was last modified and what the commit message says
git log --oneline .github/workflows/label_checker.py | head -10

Repository: wso2/api-manager

Length of output: 149


🏁 Script executed:

# Check the git diff for the recent commit to understand what changed
git show 7eb7524 --stat

Repository: wso2/api-manager

Length of output: 1201


🏁 Script executed:

# See the full diff of the recent commit
git show 7eb7524

Repository: wso2/api-manager

Length of output: 27211


🏁 Script executed:

# Check if there are any workflow files that reference ISSUE_BODY
rg "ISSUE_BODY"

Repository: wso2/api-manager

Length of output: 42


🏁 Script executed:

# Let's verify how GitHub renders the issue body from these YAML form templates
# by checking if there's any example or documentation about the format
python3 << 'EOF'
# Simulate what GitHub would render from the question_form.yml template
# When a user fills out a GitHub issue form, the rendered body looks like:
# FieldLabel
# user_input
# 
# Not as:
# ### FieldLabel
# user_input

template_example = """Description
Example question

Affected Component
APIM

Version
3.2.0"""

print("Example rendered issue body from GitHub form:")
print(template_example)
print("\nSearching for '### Affected Component' in this body:")
try:
    index = template_example.index("### Affected Component")
    print(f"Found at index {index}")
except ValueError:
    print("NOT FOUND - ValueError would be raised")
    print("\nThe code would fail at line 27 with ValueError")
    print("This exception is caught by the broad except block")
    print("Script always outputs: 'Missing/Component'")
EOF

Repository: wso2/api-manager

Length of output: 409


Critical issue: Code expects markdown headers that GitHub issue forms don't produce.

The script searches for "### Affected Component" in the issue body (line 27), but GitHub's YAML form templates don't render field labels as markdown headers. The actual rendered issue body uses plain text format (e.g., Affected Component followed by the user input). This means index() will always raise ValueError, caught by the broad exception handler on line 56, causing the script to always output "Missing/Component" regardless of input.

The script is fundamentally incompatible with the current issue templates and needs to be rewritten to parse the correct plain-text format produced by GitHub forms. Additionally, remove the unused variable e on line 56 and replace the broad except Exception with specific exception handling.

🤖 Prompt for AI Agents
Verify each finding against the current code and only fix it if needed.

In @.github/workflows/label_checker.py around lines 27 - 32, The current logic
that slices issue_body using index("### Affected Component") fails because
GitHub form output is plain text; replace that slicing with a regex search
against issue_body (e.g., a multiline regex that finds the plain "Affected
Component" label and captures the user-provided value on the same line or the
following line) to set component and component_label and append to labels only
if it matches all_existing_labels; also remove the unused variable e and change
the broad except Exception handler to catch specific errors (e.g.,
ValueError/IndexError from parsing or re-related exceptions) so parsing failures
fall back to adding "Missing/Component" without hiding other bugs.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

3 participants