Skip to content
Open
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
1 change: 1 addition & 0 deletions .github/CODEOWNERS
Original file line number Diff line number Diff line change
@@ -0,0 +1 @@
* @NITISH-R-G
9 changes: 9 additions & 0 deletions .github/ISSUE_TEMPLATE/bug_report.md
Original file line number Diff line number Diff line change
@@ -0,0 +1,9 @@
---
name: Bug report
about: Create a report to help us improve
title: ''
labels: bug
assignees: ''

---
**Describe the bug**
3 changes: 3 additions & 0 deletions .github/PULL_REQUEST_TEMPLATE.md
Original file line number Diff line number Diff line change
@@ -0,0 +1,3 @@
## Description

Please include a summary of the change and which issue is fixed.
Comment on lines +1 to +3

Copy link
Copy Markdown

Choose a reason for hiding this comment

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

📐 Maintainability & Code Quality | 🟡 Minor | ⚡ Quick win

Use a top-level heading here.

markdownlint is flagging the first line because it starts with ##. Switching it to # Description keeps the template compliant and cleaner.

🛠️ Proposed fix
-## Description
+# Description
📝 Committable suggestion

‼️ IMPORTANT
Carefully review the code before committing. Ensure that it accurately replaces the highlighted code, contains no missing lines, and has no issues with indentation. Thoroughly test & benchmark the code to ensure it meets the requirements.

Suggested change
## Description
Please include a summary of the change and which issue is fixed.
# Description
Please include a summary of the change and which issue is fixed.
🧰 Tools
🪛 markdownlint-cli2 (0.22.1)

[warning] 1-1: First line in a file should be a top-level heading

(MD041, first-line-heading, first-line-h1)

🤖 Prompt for AI Agents
Verify each finding against current code. Fix only still-valid issues, skip the
rest with a brief reason, keep changes minimal, and validate.

In @.github/PULL_REQUEST_TEMPLATE.md around lines 1 - 3, The pull request
template starts with a second-level heading, which triggers the markdownlint
warning. Update the opening heading in the PR template from the current
Description section to a top-level heading so the template remains compliant,
keeping the change localized to the template content itself.

Source: Linters/SAST tools

3 changes: 3 additions & 0 deletions .github/PULL_REQUEST_TEMPLATE/pull_request_template.md
Original file line number Diff line number Diff line change
@@ -0,0 +1,3 @@
## Description

Please include a summary of the change and which issue is fixed.
Comment on lines +1 to +3

Copy link
Copy Markdown

Choose a reason for hiding this comment

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

📐 Maintainability & Code Quality | 🟡 Minor | ⚡ Quick win

Use a top-level heading here.

markdownlint is flagging the first line because it starts with ##. Switching it to # Description keeps the template compliant and cleaner.

🛠️ Proposed fix
-## Description
+# Description
📝 Committable suggestion

‼️ IMPORTANT
Carefully review the code before committing. Ensure that it accurately replaces the highlighted code, contains no missing lines, and has no issues with indentation. Thoroughly test & benchmark the code to ensure it meets the requirements.

Suggested change
## Description
Please include a summary of the change and which issue is fixed.
# Description
Please include a summary of the change and which issue is fixed.
🧰 Tools
🪛 markdownlint-cli2 (0.22.1)

[warning] 1-1: First line in a file should be a top-level heading

(MD041, first-line-heading, first-line-h1)

🤖 Prompt for AI Agents
Verify each finding against current code. Fix only still-valid issues, skip the
rest with a brief reason, keep changes minimal, and validate.

In @.github/PULL_REQUEST_TEMPLATE/pull_request_template.md around lines 1 - 3,
The pull request template starts with a second-level heading, which triggers
markdownlint; update the first heading in pull_request_template.md from the
current Description section to a top-level heading so the template is compliant.
Keep the existing wording but change the heading level in the template content
itself, using the Description heading as the anchor to locate it.

Source: Linters/SAST tools

11 changes: 0 additions & 11 deletions .github/dependabot.yml
Original file line number Diff line number Diff line change
Expand Up @@ -4,22 +4,11 @@ updates:
directory: "/"
schedule:
interval: "weekly"
open-pull-requests-limit: 10
ignore:
- dependency-name: "*"
update-types: ["version-update:semver-major"]

- package-ecosystem: "npm"
directory: "/web"
schedule:
interval: "weekly"
open-pull-requests-limit: 10
ignore:
- dependency-name: "*"
update-types: ["version-update:semver-major"]

- package-ecosystem: "github-actions"
directory: "/"
schedule:
interval: "weekly"
open-pull-requests-limit: 10
10 changes: 10 additions & 0 deletions .github/labeler.yml
Original file line number Diff line number Diff line change
@@ -0,0 +1,10 @@
frontend:
- web/**/*
backend:
- server/**/*
- ev_grid_oracle/**/*
docs:
- docs/**/*
- '**/*.md'
github-actions:
- .github/workflows/**/*
Comment on lines +1 to +10

Copy link
Copy Markdown

Choose a reason for hiding this comment

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

🗄️ Data Integrity & Integration | 🟠 Major | ⚡ Quick win

🧩 Analysis chain

🏁 Script executed:

git ls-files .github && printf '\n---\n' && fd -a -t f -g 'labeler.yml' -g 'label*.yml' .github . || true && printf '\n---\n' && rg -n "actions/labeler@|labeler" .github -S

Repository: NITISH-R-G/ev-grid-oracle

Length of output: 951


🏁 Script executed:

sed -n '1,120p' .github/labeler.yml && printf '\n---\n' && sed -n '1,120p' .github/workflows/labeler.yml

Repository: NITISH-R-G/ev-grid-oracle

Length of output: 652


🌐 Web query:

actions/labeler v5 configuration format any-glob-to-any-file changed-files docs

💡 Result:

In actions/labeler v5, the configuration format for changed-files has been significantly redesigned to offer greater flexibility [1][2]. The configuration now supports two primary top-level keys, any and all, which determine the logic for applying labels [3][4]. The changed-files rule within these keys provides four specific matching combinations for glob patterns against changed files [3][5]: 1. any-glob-to-any-file: Matches if ANY of the provided glob patterns match ANY of the changed files [3][5]. 2. any-glob-to-all-files: Matches if ANY of the provided glob patterns match ALL of the changed files [3][5]. 3. all-globs-to-any-file: Matches if ALL of the provided glob patterns match ANY of the changed files [3][5]. 4. all-globs-to-all-files: Matches if ALL of the provided glob patterns match ALL of the changed files [3][5]. When you use changed-files without specifying a top-level key, the action defaults to the any logic [3][4]. Example configuration: LabelName: - changed-files: - any-glob-to-any-file: ['docs/*'] In this example, the label is applied if any file in the docs/ directory is changed [3][5]. The v5 release also introduced the ability to include base-branch and head-branch rules alongside changed-files, allowing for more complex conditional labeling based on the PR environment [4][1][2].

Citations:


🌐 Web query:

"actions/labeler@v5" configuration format "any-glob-to-any-file" "changed-files"

💡 Result:

In version 5 of the actions/labeler GitHub Action, the configuration format underwent a major change that introduced more specific matching logic for changed files [1][2]. The configuration now uses top-level any and all keys to define how labels should be applied based on multiple conditions (such as changed-files, base-branch, and head-branch) [2][3]. When targeting changed-files, you can use one of four specific matching strategies, including any-glob-to-any-file [3]. Configuration Format The changed-files option requires an array of configuration objects, where each object specifies one of the four available matching strategies [3]. The supported strategies for changed-files are [3][4]: - any-glob-to-any-file: ANY glob must match against ANY changed file. - any-glob-to-all-files: ANY glob must match against ALL changed files. - all-globs-to-any-file: ALL globs must match against ANY changed file. - all-globs-to-all-files: ALL globs must match against ALL changed files. Example Usage Within your .github/labeler.yml file, the structure should look like this [2][3]: label-name: - any: - changed-files: - any-glob-to-any-file: ['glob1', 'glob2'] - all: - changed-files: - any-glob-to-any-file: ['glob3'] If you provide an option without an any or all top-level key, it defaults to any [2][3]. Users frequently encounter errors like "found unexpected type for label" when migrating from v4, often because the v5 format strictly requires that changed-files contains an array of these specific matching strategy objects rather than a direct list of strings [5][6].

Citations:


🌐 Web query:

actions/labeler@v5 configuration format any-glob-to-any-file changed-files

💡 Result:

In actions/labeler@v5, the changed-files configuration allows for precise control over how glob patterns are matched against the files changed in a pull request [1]. These options provide four specific logic combinations for matching [1][2]: - any-glob-to-any-file: The label is applied if ANY of the provided glob patterns match ANY of the changed files [1][2]. - any-glob-to-all-files: The label is applied if ANY of the provided glob patterns match ALL of the changed files [1]. - all-globs-to-any-file: The label is applied if ALL of the provided glob patterns match ANY of the changed files [1]. - all-globs-to-all-files: The label is applied if ALL of the provided glob patterns match ALL of the changed files [1]. These configurations are used within the .github/labeler.yml file under any or all top-level keys [3][1]. For example: label-name: - any: - changed-files: - any-glob-to-any-file: ['src//.js', 'test//.js'] If no top-level key (any or all) is provided, the configuration defaults to any [3][1]. Additionally, changed-files can be combined with other criteria like base-branch or head-branch regexps within the same label definition [3][1].

Citations:


Update .github/labeler.yml to the v5 changed-files schema
actions/labeler@v5 no longer reads the flat label: [glob, ...] format, so these labels won’t match until the rules are rewritten to the v5 structure.

🤖 Prompt for AI Agents
Verify each finding against current code. Fix only still-valid issues, skip the
rest with a brief reason, keep changes minimal, and validate.

In @.github/labeler.yml around lines 1 - 10, The label rules in labeler config
still use the old flat mapping and need to be migrated to the v5 changed-files
schema. Update the .github/labeler.yml structure so each label key maps to the
new nested configuration expected by actions/labeler@v5, and keep the existing
frontend, backend, docs, and github-actions glob patterns under their
corresponding rule entries.

27 changes: 0 additions & 27 deletions .github/workflows/ai-insights.yml

This file was deleted.

29 changes: 29 additions & 0 deletions .github/workflows/ai-review.yml
Original file line number Diff line number Diff line change
@@ -0,0 +1,29 @@
name: AI PR Reviewer

on:
pull_request:
types:
- opened
- synchronize
- reopened
pull_request_review_comment:
types:
- created
Comment on lines +3 to +11

Copy link
Copy Markdown

Choose a reason for hiding this comment

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

🚀 Performance & Scalability | 🔵 Trivial | ⚡ Quick win

Add concurrency control to avoid overlapping/queued reviews and wasted OpenAI spend.

♻️ Proposed fix
 permissions:
   contents: read
   pull-requests: write
 
+concurrency:
+  group: ai-review-${{ github.event.pull_request.number || github.event.comment.id }}
+  cancel-in-progress: true
+
 jobs:
📝 Committable suggestion

‼️ IMPORTANT
Carefully review the code before committing. Ensure that it accurately replaces the highlighted code, contains no missing lines, and has no issues with indentation. Thoroughly test & benchmark the code to ensure it meets the requirements.

Suggested change
on:
pull_request:
types:
- opened
- synchronize
- reopened
pull_request_review_comment:
types:
- created
on:
pull_request:
types:
- opened
- synchronize
- reopened
pull_request_review_comment:
types:
- created
concurrency:
group: ai-review-${{ github.event.pull_request.number || github.event.comment.id }}
cancel-in-progress: true
🧰 Tools
🪛 zizmor (1.26.1)

[warning] 3-11: insufficient job-level concurrency limits (concurrency-limits): workflow is missing concurrency setting

(concurrency-limits)

🤖 Prompt for AI Agents
Verify each finding against current code. Fix only still-valid issues, skip the
rest with a brief reason, keep changes minimal, and validate.

In @.github/workflows/ai-review.yml around lines 3 - 11, The workflow trigger
block in ai-review.yml can start multiple overlapping review runs for the same
pull request, which can queue duplicate jobs and waste OpenAI spend. Add a
workflow-level concurrency policy tied to the pull request identity so only one
ai-review run per PR is active at a time and any superseded in-progress or
queued run is canceled. Keep the existing on: pull_request and
pull_request_review_comment triggers unchanged, and apply the concurrency
setting alongside them.

Source: Linters/SAST tools

Comment on lines +4 to +11

Copy link
Copy Markdown

Choose a reason for hiding this comment

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

🎯 Functional Correctness | 🔵 Trivial

OPENAI_API_KEY/GITHUB_TOKEN won't be available on fork PRs with pull_request trigger.

Repository secrets are not passed to workflows triggered by pull_request from forks for security reasons. This is the safer default, but means the AI reviewer will effectively no-op (or error on missing key) for external contributor PRs — likely the majority of PRs on an open, autonomous repo. If AI review on fork PRs is desired, that requires pull_request_target plus careful checkout scoping (increases risk); if internal-only review is intended, this is fine as-is — just worth confirming this matches expectations.

🧰 Tools
🪛 zizmor (1.26.1)

[warning] 3-11: insufficient job-level concurrency limits (concurrency-limits): workflow is missing concurrency setting

(concurrency-limits)

🤖 Prompt for AI Agents
Verify each finding against current code. Fix only still-valid issues, skip the
rest with a brief reason, keep changes minimal, and validate.

In @.github/workflows/ai-review.yml around lines 4 - 11, The AI review workflow
trigger uses pull_request, so repository secrets like OPENAI_API_KEY and
GITHUB_TOKEN will not be available for forked PRs. Update the workflow in
ai-review.yml to either confirm internal-only usage or switch the trigger
strategy to pull_request_target with safe checkout/scoping if fork PR review is
intended, and make sure the choice aligns with the behavior expected by the
workflow jobs that use those secrets.


permissions:
contents: read
pull-requests: write

jobs:
review:
runs-on: ubuntu-latest
if: ${{ github.event.sender.type != 'Bot' }}
steps:
- uses: coderabbitai/openai-pr-reviewer@master
env:
GITHUB_TOKEN: ${{ secrets.GITHUB_TOKEN }}
OPENAI_API_KEY: ${{ secrets.OPENAI_API_KEY }}
with:
debug: false
review_simple_changes: false
review_comment_lgtm: false
42 changes: 42 additions & 0 deletions .github/workflows/ci.yml
Original file line number Diff line number Diff line change
@@ -0,0 +1,42 @@
name: CI

on:
push:
branches: [ "main", "master" ]
pull_request:
branches: [ "main", "master" ]
Comment on lines +3 to +7

Copy link
Copy Markdown

Choose a reason for hiding this comment

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

🚀 Performance & Scalability | 🔵 Trivial | ⚡ Quick win

Add concurrency control to cancel superseded CI runs.

Both push and pull_request trigger this workflow; without concurrency, rapid successive pushes to the same branch/PR queue redundant, resource-consuming runs.

♻️ Proposed fix
 on:
   push:
     branches: [ "main", "master" ]
   pull_request:
     branches: [ "main", "master" ]
 
+concurrency:
+  group: ci-${{ github.workflow }}-${{ github.event.pull_request.number || github.ref }}
+  cancel-in-progress: true
+
 jobs:
📝 Committable suggestion

‼️ IMPORTANT
Carefully review the code before committing. Ensure that it accurately replaces the highlighted code, contains no missing lines, and has no issues with indentation. Thoroughly test & benchmark the code to ensure it meets the requirements.

Suggested change
on:
push:
branches: [ "main", "master" ]
pull_request:
branches: [ "main", "master" ]
on:
push:
branches: [ "main", "master" ]
pull_request:
branches: [ "main", "master" ]
concurrency:
group: ci-${{ github.workflow }}-${{ github.event.pull_request.number || github.ref }}
cancel-in-progress: true
🧰 Tools
🪛 YAMLlint (1.37.1)

[warning] 3-3: truthy value should be one of [false, true]

(truthy)


[error] 5-5: too many spaces inside brackets

(brackets)


[error] 5-5: too many spaces inside brackets

(brackets)


[error] 7-7: too many spaces inside brackets

(brackets)


[error] 7-7: too many spaces inside brackets

(brackets)

🪛 zizmor (1.26.1)

[warning] 3-7: insufficient job-level concurrency limits (concurrency-limits): workflow is missing concurrency setting

(concurrency-limits)

🤖 Prompt for AI Agents
Verify each finding against current code. Fix only still-valid issues, skip the
rest with a brief reason, keep changes minimal, and validate.

In @.github/workflows/ci.yml around lines 3 - 7, The CI workflow triggers on
both push and pull_request without cancellation control, so add a top-level
concurrency setting to the workflow in ci.yml so newer runs supersede older ones
for the same branch or PR. Use a stable group key based on the ref or PR
identifier and set cancel-in-progress to true, placing it alongside the existing
on section so the workflow stays unchanged otherwise.

Source: Linters/SAST tools


jobs:
test:
runs-on: ubuntu-latest
steps:
- uses: actions/checkout@v4

Copy link
Copy Markdown

Choose a reason for hiding this comment

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

🔒 Security & Privacy | 🔵 Trivial | ⚡ Quick win

Pin actions/checkout, actions/setup-python, actions/setup-node to commit SHAs.

Static analysis flags all three as unpinned under the repo's declared pinning policy — mutable tags can be repointed by the action publisher.

Also applies to: 18-18, 23-23

🧰 Tools
🪛 zizmor (1.26.1)

[warning] 13-15: credential persistence through GitHub Actions artifacts (artipacked): does not set persist-credentials: false

(artipacked)


[error] 13-13: unpinned action reference (unpinned-uses): action is not pinned to a hash (required by blanket policy)

(unpinned-uses)

🤖 Prompt for AI Agents
Verify each finding against current code. Fix only still-valid issues, skip the
rest with a brief reason, keep changes minimal, and validate.

In @.github/workflows/ci.yml at line 13, The workflow currently uses mutable
tags for actions, so update the uses entries in the CI workflow to pin
actions/checkout, actions/setup-python, and actions/setup-node to specific
commit SHAs instead of v4 or other tags. Keep the existing job structure intact
and replace the referenced action identifiers in the workflow file with their
pinned SHA forms to match the repo’s pinning policy.

Source: Linters/SAST tools

with:
lfs: true
Comment on lines +13 to +15

Copy link
Copy Markdown

Choose a reason for hiding this comment

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

🔒 Security & Privacy | 🔵 Trivial | ⚡ Quick win

Disable credential persistence on checkout.

The checkout step keeps the GITHUB_TOKEN in the local git config for the rest of the job (persist-credentials defaults to true). Since subsequent steps run npm ci/npm run build (arbitrary package scripts), an explicit persist-credentials: false reduces the blast radius if a dependency script attempts to exfiltrate it.

🔒 Proposed fix
     - uses: actions/checkout@v4
       with:
         lfs: true
+        persist-credentials: false
📝 Committable suggestion

‼️ IMPORTANT
Carefully review the code before committing. Ensure that it accurately replaces the highlighted code, contains no missing lines, and has no issues with indentation. Thoroughly test & benchmark the code to ensure it meets the requirements.

Suggested change
- uses: actions/checkout@v4
with:
lfs: true
- uses: actions/checkout@v4
with:
lfs: true
persist-credentials: false
🧰 Tools
🪛 zizmor (1.26.1)

[warning] 13-15: credential persistence through GitHub Actions artifacts (artipacked): does not set persist-credentials: false

(artipacked)


[error] 13-13: unpinned action reference (unpinned-uses): action is not pinned to a hash (required by blanket policy)

(unpinned-uses)

🤖 Prompt for AI Agents
Verify each finding against current code. Fix only still-valid issues, skip the
rest with a brief reason, keep changes minimal, and validate.

In @.github/workflows/ci.yml around lines 13 - 15, The checkout step currently
leaves the GITHUB_TOKEN persisted in git config by default, which increases
exposure for later npm scripts in the CI job. Update the existing
actions/checkout usage in the workflow to explicitly set persist-credentials to
false alongside the current lfs setting, keeping the fix localized to the
checkout step in the CI workflow.

Source: Linters/SAST tools


- name: Set up Python
uses: actions/setup-python@v5
with:
python-version: '3.12'

- name: Set up Node.js
uses: actions/setup-node@v4
with:
node-version: '22'

- name: Install uv
run: pip install uv

- name: Install Python dependencies
run: |
uv pip install --system -e ".[dev,demo]"

- name: Run Pytest
run: |
uv run pytest tests/

- name: Build Frontend
working-directory: ./web
run: |
npm ci
npm run build
Comment on lines +1 to +42

Copy link
Copy Markdown

Choose a reason for hiding this comment

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

🔒 Security & Privacy | 🔵 Trivial | ⚡ Quick win

No workflow-level permissions block — defaults to broad GITHUB_TOKEN scope.

This job only needs to read repo contents; add an explicit least-privilege permissions block.

🔒 Proposed fix
 name: CI
 
+permissions:
+  contents: read
+
 on:
📝 Committable suggestion

‼️ IMPORTANT
Carefully review the code before committing. Ensure that it accurately replaces the highlighted code, contains no missing lines, and has no issues with indentation. Thoroughly test & benchmark the code to ensure it meets the requirements.

Suggested change
name: CI
on:
push:
branches: [ "main", "master" ]
pull_request:
branches: [ "main", "master" ]
jobs:
test:
runs-on: ubuntu-latest
steps:
- uses: actions/checkout@v4
with:
lfs: true
- name: Set up Python
uses: actions/setup-python@v5
with:
python-version: '3.12'
- name: Set up Node.js
uses: actions/setup-node@v4
with:
node-version: '24'
- name: Install uv
run: pip install uv
- name: Install Python dependencies
run: |
uv pip install --system -e ".[dev,demo]"
- name: Run Pytest
run: |
uv run pytest tests/
- name: Build Frontend
working-directory: ./web
run: |
npm ci
npm run build
name: CI
permissions:
contents: read
on:
push:
branches: [ "main", "master" ]
pull_request:
branches: [ "main", "master" ]
jobs:
test:
runs-on: ubuntu-latest
steps:
- uses: actions/checkout@v4
with:
lfs: true
- name: Set up Python
uses: actions/setup-python@v5
with:
python-version: '3.12'
- name: Set up Node.js
uses: actions/setup-node@v4
with:
node-version: '24'
- name: Install uv
run: pip install uv
- name: Install Python dependencies
run: |
uv pip install --system -e ".[dev,demo]"
- name: Run Pytest
run: |
uv run pytest tests/
- name: Build Frontend
working-directory: ./web
run: |
npm ci
npm run build
🧰 Tools
🪛 YAMLlint (1.37.1)

[warning] 3-3: truthy value should be one of [false, true]

(truthy)


[error] 5-5: too many spaces inside brackets

(brackets)


[error] 5-5: too many spaces inside brackets

(brackets)


[error] 7-7: too many spaces inside brackets

(brackets)


[error] 7-7: too many spaces inside brackets

(brackets)

🪛 zizmor (1.26.1)

[warning] 13-15: credential persistence through GitHub Actions artifacts (artipacked): does not set persist-credentials: false

(artipacked)


[warning] 1-43: overly broad permissions (excessive-permissions): default permissions used due to no permissions: block

(excessive-permissions)


[error] 13-13: unpinned action reference (unpinned-uses): action is not pinned to a hash (required by blanket policy)

(unpinned-uses)


[error] 18-18: unpinned action reference (unpinned-uses): action is not pinned to a hash (required by blanket policy)

(unpinned-uses)


[error] 23-23: unpinned action reference (unpinned-uses): action is not pinned to a hash (required by blanket policy)

(unpinned-uses)


[info] 10-10: workflow or action definition without a name (anonymous-definition): this job

(anonymous-definition)


[warning] 3-7: insufficient job-level concurrency limits (concurrency-limits): workflow is missing concurrency setting

(concurrency-limits)

🤖 Prompt for AI Agents
Verify each finding against current code. Fix only still-valid issues, skip the
rest with a brief reason, keep changes minimal, and validate.

In @.github/workflows/ci.yml around lines 1 - 42, The CI workflow currently
relies on the default broad GITHUB_TOKEN scope, so add an explicit
least-privilege permissions block for the workflow. Update the CI job definition
in the workflow file to restrict access to only what the steps need, and keep
the change near the existing on/jobs sections so it is easy to find alongside
the test, setup-python, setup-node, and build steps.

Source: Linters/SAST tools

6 changes: 6 additions & 0 deletions .github/workflows/code-quality.yml
Original file line number Diff line number Diff line change
Expand Up @@ -13,6 +13,8 @@ jobs:
runs-on: ubuntu-latest
steps:
- uses: actions/checkout@v4
with:
lfs: true
Comment on lines 15 to +17

Copy link
Copy Markdown

Choose a reason for hiding this comment

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

🔒 Security & Privacy | 🔵 Trivial | ⚡ Quick win

Consider setting persist-credentials: false on checkout.

zizmor flags all three checkout steps for credential persistence (artipacked). Since these with: blocks are already being touched to add lfs: true, it's a good opportunity to also add persist-credentials: false where the job doesn't need to push/write back with the default token.

🔒 Proposed fix
     - uses: actions/checkout@v4
       with:
         lfs: true
+        persist-credentials: false

Apply the same pattern to the other two checkout steps in this file if the jobs don't require pushing changes.

Also applies to: 62-64, 86-88

🧰 Tools
🪛 zizmor (1.26.1)

[warning] 15-17: credential persistence through GitHub Actions artifacts (artipacked): does not set persist-credentials: false

(artipacked)


[error] 15-15: unpinned action reference (unpinned-uses): action is not pinned to a hash (required by blanket policy)

(unpinned-uses)

🤖 Prompt for AI Agents
Verify each finding against current code. Fix only still-valid issues, skip the
rest with a brief reason, keep changes minimal, and validate.

In @.github/workflows/code-quality.yml around lines 15 - 17, The checkout steps
in the workflow are persisting GitHub credentials unnecessarily, which zizmor
flags as an artipacked risk. Update the existing actions/checkout uses in this
workflow to set persist-credentials to false alongside the current lfs setting
where the job only needs read access. Apply the same change to the other
checkout invocations in this file unless a job explicitly needs to push or write
back using the default token.

Source: Linters/SAST tools


- name: Set up Python
uses: actions/setup-python@v5
Expand Down Expand Up @@ -58,6 +60,8 @@ jobs:
working-directory: ./web
steps:
- uses: actions/checkout@v4
with:
lfs: true

- name: Set up Node.js
uses: actions/setup-node@v4
Expand All @@ -80,6 +84,8 @@ jobs:
runs-on: ubuntu-latest
steps:
- uses: actions/checkout@v4
with:
lfs: true

- name: Set up Node.js
uses: actions/setup-node@v4
Expand Down
21 changes: 21 additions & 0 deletions .github/workflows/greetings.yml
Original file line number Diff line number Diff line change
@@ -0,0 +1,21 @@
name: Greetings

on:
pull_request_target:
types: [opened]
issues:
types: [opened]

permissions:
issues: write
pull-requests: write
Comment on lines +3 to +11

Copy link
Copy Markdown

Choose a reason for hiding this comment

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

🔒 Security & Privacy | 🟡 Minor | ⚡ Quick win

Scope permissions to job level.

Workflow-level issues: write / pull-requests: write grants broad access to every job that might be added later. Move permissions into the greeting job block, and add a short comment explaining why write access is required (posting welcome comments).

🔒 Proposed fix
-permissions:
-  issues: write
-  pull-requests: write
-
 jobs:
   greeting:
     runs-on: ubuntu-latest
+    permissions:
+      issues: write        # required to comment on first issues
+      pull-requests: write # required to comment on first PRs
     steps:
🧰 Tools
🪛 zizmor (1.26.1)

[error] 10-10: overly broad permissions (excessive-permissions): issues: write is overly broad at the workflow level

(excessive-permissions)


[error] 11-11: overly broad permissions (excessive-permissions): pull-requests: write is overly broad at the workflow level

(excessive-permissions)


[error] 3-7: use of fundamentally insecure workflow trigger (dangerous-triggers): pull_request_target is almost always used insecurely

(dangerous-triggers)


[warning] 10-10: permissions without explanatory comments (undocumented-permissions): needs an explanatory comment

(undocumented-permissions)


[warning] 3-7: insufficient job-level concurrency limits (concurrency-limits): workflow is missing concurrency setting

(concurrency-limits)

🤖 Prompt for AI Agents
Verify each finding against current code. Fix only still-valid issues, skip the
rest with a brief reason, keep changes minimal, and validate.

In @.github/workflows/greetings.yml around lines 3 - 11, The workflow currently
grants broad `issues: write` and `pull-requests: write` permissions at the top
level, which should be narrowed to the `greeting` job. Move those permissions
into the `greeting` job definition in the greetings workflow, and add a brief
comment there explaining that write access is needed to post welcome comments on
issues and pull requests.

Source: Linters/SAST tools


jobs:
greeting:
runs-on: ubuntu-latest
steps:
- uses: actions/first-interaction@v1

Copy link
Copy Markdown

Choose a reason for hiding this comment

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

🔒 Security & Privacy | 🟡 Minor | ⚡ Quick win

Pin action to a commit SHA.

actions/first-interaction@v1 is a mutable tag; pin to a full commit SHA (with the version as a comment) to guard against tag-hijacking supply-chain attacks.

🔒 Proposed fix
-      - uses: actions/first-interaction@v1
+      - uses: actions/first-interaction@<commit-sha> # v1
🧰 Tools
🪛 zizmor (1.26.1)

[error] 17-17: unpinned action reference (unpinned-uses): action is not pinned to a hash (required by blanket policy)

(unpinned-uses)

🤖 Prompt for AI Agents
Verify each finding against current code. Fix only still-valid issues, skip the
rest with a brief reason, keep changes minimal, and validate.

In @.github/workflows/greetings.yml at line 17, The workflow step using
actions/first-interaction@v1 is relying on a mutable tag; update the existing
first-interaction action reference in greetings.yml to a full commit SHA and
keep the v1 version noted in a comment. This change should be applied directly
to the actions/first-interaction usage so the workflow is pinned to an immutable
revision.

Source: Linters/SAST tools

with:
repo-token: ${{ secrets.GITHUB_TOKEN }}
issue-message: "Welcome to the repository! Thank you for opening your first issue. Our AI maintainer and human team will review it shortly."
pr-message: "Welcome to the repository! Thank you for your first pull request. Our automated checks are running, and we will review your changes soon."
3 changes: 2 additions & 1 deletion .github/workflows/health-dashboard.yml
Original file line number Diff line number Diff line change
Expand Up @@ -22,7 +22,8 @@ jobs:
- name: Checkout repository
uses: actions/checkout@v4
with:
fetch-depth: 0 # Needed for git stats
fetch-depth: 0
lfs: true
Comment on lines 22 to +26

Copy link
Copy Markdown

Choose a reason for hiding this comment

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

🔒 Security & Privacy | 🔵 Trivial | ⚡ Quick win

Consider setting persist-credentials: false on checkout.

zizmor flags this checkout step for credential persistence (artipacked). This job deploys to GitHub Pages using an explicit github_token in a later step, so the default persisted credential from checkout isn't needed here.

🔒 Proposed fix
       - name: Checkout repository
         uses: actions/checkout@v4
         with:
           fetch-depth: 0
           lfs: true
+          persist-credentials: false
📝 Committable suggestion

‼️ IMPORTANT
Carefully review the code before committing. Ensure that it accurately replaces the highlighted code, contains no missing lines, and has no issues with indentation. Thoroughly test & benchmark the code to ensure it meets the requirements.

Suggested change
- name: Checkout repository
uses: actions/checkout@v4
with:
fetch-depth: 0 # Needed for git stats
fetch-depth: 0
lfs: true
- name: Checkout repository
uses: actions/checkout@v4
with:
fetch-depth: 0
lfs: true
persist-credentials: false
🧰 Tools
🪛 zizmor (1.26.1)

[warning] 22-26: credential persistence through GitHub Actions artifacts (artipacked): does not set persist-credentials: false

(artipacked)


[error] 23-23: unpinned action reference (unpinned-uses): action is not pinned to a hash (required by blanket policy)

(unpinned-uses)

🤖 Prompt for AI Agents
Verify each finding against current code. Fix only still-valid issues, skip the
rest with a brief reason, keep changes minimal, and validate.

In @.github/workflows/health-dashboard.yml around lines 22 - 26, The Checkout
repository step is persisting the default GitHub credentials unnecessarily,
which triggers the credential-persistence warning. Update the
actions/checkout@v4 configuration in the health dashboard workflow to disable
persisted credentials by setting persist-credentials to false, while keeping the
existing fetch-depth and lfs settings unchanged.

Source: Linters/SAST tools


- name: Set up Python
uses: actions/setup-python@v5
Expand Down
17 changes: 17 additions & 0 deletions .github/workflows/labeler.yml
Original file line number Diff line number Diff line change
@@ -0,0 +1,17 @@
name: "Pull Request Labeler"
on:
pull_request_target:
types: [opened, synchronize, reopened]
Comment on lines +2 to +4

Copy link
Copy Markdown

Choose a reason for hiding this comment

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

🚀 Performance & Scalability | 🔵 Trivial | ⚡ Quick win

Add a concurrency group to cancel superseded triage runs.

Repeated synchronize events on the same PR queue redundant labeler runs.

♻️ Proposed fix
 on:
   pull_request_target:
     types: [opened, synchronize, reopened]
 
+concurrency:
+  group: labeler-${{ github.event.pull_request.number }}
+  cancel-in-progress: true
+
 permissions:
📝 Committable suggestion

‼️ IMPORTANT
Carefully review the code before committing. Ensure that it accurately replaces the highlighted code, contains no missing lines, and has no issues with indentation. Thoroughly test & benchmark the code to ensure it meets the requirements.

Suggested change
on:
pull_request_target:
types: [opened, synchronize, reopened]
on:
pull_request_target:
types: [opened, synchronize, reopened]
concurrency:
group: labeler-${{ github.event.pull_request.number }}
cancel-in-progress: true
🧰 Tools
🪛 zizmor (1.26.1)

[warning] 2-4: insufficient job-level concurrency limits (concurrency-limits): workflow is missing concurrency setting

(concurrency-limits)

🤖 Prompt for AI Agents
Verify each finding against current code. Fix only still-valid issues, skip the
rest with a brief reason, keep changes minimal, and validate.

In @.github/workflows/labeler.yml around lines 2 - 4, Add a concurrency group to
the workflow so repeated pull_request_target runs for the same PR cancel older
labeler executions. Update the workflow configuration in labeler.yml by adding a
concurrency setting tied to the PR identity and enabling cancel-in-progress, so
the labeler job does not queue redundant synchronize runs.

Source: Linters/SAST tools


permissions:
contents: read
pull-requests: write

jobs:
triage:
runs-on: ubuntu-latest
steps:
- uses: actions/labeler@v5
with:
repo-token: "${{ secrets.GITHUB_TOKEN }}"
sync-labels: true
Comment on lines +14 to +17

Copy link
Copy Markdown

Choose a reason for hiding this comment

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

🔒 Security & Privacy | 🔵 Trivial | ⚡ Quick win

Pin actions/labeler to a commit SHA instead of the mutable @v5 tag.

Tags can be moved by the action maintainer; pinning to a full commit SHA prevents a compromised/updated tag from silently changing behavior in a workflow with pull-requests: write access.

🔒 Proposed fix
-      - uses: actions/labeler@v5
+      - uses: actions/labeler@<pinned-sha> # v5.x.x
🧰 Tools
🪛 zizmor (1.26.1)

[error] 14-14: unpinned action reference (unpinned-uses): action is not pinned to a hash (required by blanket policy)

(unpinned-uses)

🤖 Prompt for AI Agents
Verify each finding against current code. Fix only still-valid issues, skip the
rest with a brief reason, keep changes minimal, and validate.

In @.github/workflows/labeler.yml around lines 14 - 17, The workflow step using
actions/labeler is pinned to a mutable version tag, so update the uses reference
in the labeler job to a full commit SHA instead of `@v5`. Keep the existing with
settings for repo-token and sync-labels, and only change the action identifier
on the labeler step so the workflow stays functionally the same while using an
immutable pin.

Source: Linters/SAST tools

36 changes: 36 additions & 0 deletions .github/workflows/pages.yml
Original file line number Diff line number Diff line change
@@ -0,0 +1,36 @@
name: GitHub Pages

on:
push:
branches:
- main

permissions:
contents: read
pages: write
id-token: write
Comment on lines +8 to +11

Copy link
Copy Markdown

Choose a reason for hiding this comment

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

🔒 Security & Privacy | 🔵 Trivial | ⚡ Quick win

Scope permissions to the job, not the workflow.

pages: write and id-token: write are granted at workflow level, so any job later added to this workflow inherits them even if unneeded. Move permissions into the deploy job block instead.

🔒 Proposed fix
-permissions:
-  contents: read
-  pages: write
-  id-token: write
-
 concurrency:
   group: "pages"
   cancel-in-progress: false
 
 jobs:
   deploy:
+    permissions:
+      contents: read
+      pages: write
+      id-token: write
     environment:
       name: github-pages
📝 Committable suggestion

‼️ IMPORTANT
Carefully review the code before committing. Ensure that it accurately replaces the highlighted code, contains no missing lines, and has no issues with indentation. Thoroughly test & benchmark the code to ensure it meets the requirements.

Suggested change
permissions:
contents: read
pages: write
id-token: write
concurrency:
group: "pages"
cancel-in-progress: false
jobs:
deploy:
permissions:
contents: read
pages: write
id-token: write
environment:
name: github-pages
🧰 Tools
🪛 zizmor (1.26.1)

[error] 10-10: overly broad permissions (excessive-permissions): pages: write is overly broad at the workflow level

(excessive-permissions)


[error] 11-11: overly broad permissions (excessive-permissions): id-token: write is overly broad at the workflow level

(excessive-permissions)


[warning] 10-10: permissions without explanatory comments (undocumented-permissions): needs an explanatory comment

(undocumented-permissions)

🤖 Prompt for AI Agents
Verify each finding against current code. Fix only still-valid issues, skip the
rest with a brief reason, keep changes minimal, and validate.

In @.github/workflows/pages.yml around lines 8 - 11, The workflow-level
permissions in pages.yml are too broad because pages: write and id-token: write
apply to every job; move these permissions into the deploy job’s permissions
block so only that job gets them, while keeping the top-level permissions
limited to what the entire workflow actually needs. Use the deploy job
definition in the pages workflow as the place to scope the permissions.

Source: Linters/SAST tools


concurrency:
group: "pages"
cancel-in-progress: false

jobs:
deploy:
environment:
name: github-pages
url: ${{ steps.deployment.outputs.page_url }}
runs-on: ubuntu-latest
steps:
- name: Checkout
uses: actions/checkout@v4

Copy link
Copy Markdown

Choose a reason for hiding this comment

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

🔒 Security & Privacy | 🔵 Trivial | ⚡ Quick win

Pin actions to a commit SHA.

actions/checkout@v4, actions/configure-pages@v5, actions/upload-pages-artifact@v3, and actions/deploy-pages@v4 are referenced by mutable tags. Pin each to an immutable commit SHA to guard against supply-chain tag-repointing attacks, consistent with the blanket policy flagged by static analysis.

Also applies to: 29-29, 31-31, 36-36

🧰 Tools
🪛 zizmor (1.26.1)

[error] 25-25: unpinned action reference (unpinned-uses): action is not pinned to a hash (required by blanket policy)

(unpinned-uses)

🤖 Prompt for AI Agents
Verify each finding against current code. Fix only still-valid issues, skip the
rest with a brief reason, keep changes minimal, and validate.

In @.github/workflows/pages.yml at line 25, The GitHub Actions workflow uses
mutable version tags for actions, so update the jobs in pages.yml to pin actions
to immutable commit SHAs instead of tags. Apply this to the uses entries for
actions/checkout, actions/configure-pages, actions/upload-pages-artifact, and
actions/deploy-pages so the workflow references fixed revisions and not v4/v5/v3
tags.

Source: Linters/SAST tools

with:
lfs: true
Comment on lines +24 to +27

Copy link
Copy Markdown

Choose a reason for hiding this comment

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

🔒 Security & Privacy | 🟡 Minor | ⚡ Quick win

Disable credential persistence on checkout.

This job never pushes commits, so leaving the default persist-credentials: true unnecessarily leaves the GitHub token on the runner filesystem after checkout.

🔒 Proposed fix
       - name: Checkout
         uses: actions/checkout@v4
         with:
           lfs: true
+          persist-credentials: false
📝 Committable suggestion

‼️ IMPORTANT
Carefully review the code before committing. Ensure that it accurately replaces the highlighted code, contains no missing lines, and has no issues with indentation. Thoroughly test & benchmark the code to ensure it meets the requirements.

Suggested change
- name: Checkout
uses: actions/checkout@v4
with:
lfs: true
- name: Checkout
uses: actions/checkout@v4
with:
lfs: true
persist-credentials: false
🧰 Tools
🪛 zizmor (1.26.1)

[warning] 24-27: credential persistence through GitHub Actions artifacts (artipacked): does not set persist-credentials: false

(artipacked)


[error] 25-25: unpinned action reference (unpinned-uses): action is not pinned to a hash (required by blanket policy)

(unpinned-uses)

🤖 Prompt for AI Agents
Verify each finding against current code. Fix only still-valid issues, skip the
rest with a brief reason, keep changes minimal, and validate.

In @.github/workflows/pages.yml around lines 24 - 27, The Checkout step in the
pages workflow leaves GitHub credentials persisted on the runner even though
this job never pushes changes. Update the actions/checkout@v4 usage in the
Checkout step to explicitly disable credential persistence by setting
persist-credentials to false, while keeping the existing lfs setting intact.

Source: Linters/SAST tools

- name: Setup Pages
uses: actions/configure-pages@v5
- name: Upload artifact
uses: actions/upload-pages-artifact@v3
with:
path: './docs'
Comment on lines +30 to +33

Copy link
Copy Markdown

Choose a reason for hiding this comment

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

🧹 Nitpick | 🔵 Trivial

Verify ./docs is kept in sync before this push-triggered deploy runs.

This workflow deploys ./docs on every push to main, but the docs generation (tools/docs_sync.py) appears to be invoked separately, on the scheduled repo-maintenance.yml workflow. If a push to main lands between maintenance runs, Pages could deploy stale or missing docs content.

🧰 Tools
🪛 zizmor (1.26.1)

[error] 31-31: unpinned action reference (unpinned-uses): action is not pinned to a hash (required by blanket policy)

(unpinned-uses)

🤖 Prompt for AI Agents
Verify each finding against current code. Fix only still-valid issues, skip the
rest with a brief reason, keep changes minimal, and validate.

In @.github/workflows/pages.yml around lines 30 - 33, The Pages deploy currently
uploads ./docs from the push-triggered workflow without first ensuring the
generated docs are up to date. Update the pages workflow so the docs are
synchronized before the upload step, either by invoking the same docs
generation/sync logic used by tools/docs_sync.py or by otherwise guaranteeing
the checked-in ./docs content is refreshed before
actions/upload-pages-artifact@v3 runs. Use the existing Upload artifact step and
docs sync path as the anchor points for the fix.

- name: Deploy to GitHub Pages
id: deployment
uses: actions/deploy-pages@v4
68 changes: 68 additions & 0 deletions .github/workflows/repo-maintenance.yml
Original file line number Diff line number Diff line change
@@ -0,0 +1,68 @@
name: Repository Maintenance Automation

on:
push:
branches:
- main
- master
schedule:
- cron: '0 0 * * *' # Daily at midnight UTC
Comment on lines +3 to +9

Copy link
Copy Markdown

Choose a reason for hiding this comment

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

🩺 Stability & Availability | 🔵 Trivial | ⚡ Quick win

Add a concurrency group to prevent overlapping maintenance runs.

Push-triggered and nightly-scheduled runs of this job can overlap, both attempting to git add -A/commit/push against the same branch, risking push races or duplicate commits.

♻️ Suggested fix
 on:
   push:
     branches:
       - main
       - master
   schedule:
     - cron: '0 0 * * *' # Daily at midnight UTC
+
+concurrency:
+  group: repo-maintenance-${{ github.ref }}
+  cancel-in-progress: false
📝 Committable suggestion

‼️ IMPORTANT
Carefully review the code before committing. Ensure that it accurately replaces the highlighted code, contains no missing lines, and has no issues with indentation. Thoroughly test & benchmark the code to ensure it meets the requirements.

Suggested change
on:
push:
branches:
- main
- master
schedule:
- cron: '0 0 * * *' # Daily at midnight UTC
on:
push:
branches:
- main
- master
schedule:
- cron: '0 0 * * *' # Daily at midnight UTC
concurrency:
group: repo-maintenance-${{ github.ref }}
cancel-in-progress: false
🧰 Tools
🪛 zizmor (1.26.1)

[warning] 3-9: insufficient job-level concurrency limits (concurrency-limits): workflow is missing concurrency setting

(concurrency-limits)

🤖 Prompt for AI Agents
Verify each finding against current code. Fix only still-valid issues, skip the
rest with a brief reason, keep changes minimal, and validate.

In @.github/workflows/repo-maintenance.yml around lines 3 - 9, Add a concurrency
group to the repository maintenance workflow so only one run can execute against
the same branch at a time. Update the workflow definition in the
repo-maintenance job to use a concurrency setting keyed off the workflow and
branch, and enable canceling in-progress runs so push-triggered and scheduled
executions do not overlap. Use the workflow’s existing trigger section and
maintenance job context to place the change cleanly.

Source: Linters/SAST tools


permissions:
contents: write
Comment on lines +11 to +12

Copy link
Copy Markdown

Choose a reason for hiding this comment

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

🔒 Security & Privacy | 🟠 Major | ⚡ Quick win

Scope down contents: write permission.

Workflow-level contents: write is overly broad — every step in this job (including uv pip install executing arbitrary project/setup code) inherits write access to the repo. Static analysis flags this as excessive and undocumented.

🔒 Suggested fix
 permissions:
-  contents: write
+  contents: write # required by the auto-commit step to push maintenance updates

Consider moving the permission to job level and documenting why it's needed, as flagged by zizmor.

🧰 Tools
🪛 zizmor (1.26.1)

[error] 12-12: overly broad permissions (excessive-permissions): contents: write is overly broad at the workflow level

(excessive-permissions)


[warning] 12-12: permissions without explanatory comments (undocumented-permissions): needs an explanatory comment

(undocumented-permissions)

🤖 Prompt for AI Agents
Verify each finding against current code. Fix only still-valid issues, skip the
rest with a brief reason, keep changes minimal, and validate.

In @.github/workflows/repo-maintenance.yml around lines 11 - 12, The workflow
currently grants broad repo write access via the top-level permissions block,
which should be scoped down. Move contents: write from the workflow-level
permissions into the specific job that needs it in repo-maintenance.yml, and
keep the scope limited to only that maintenance job. If the job uses any step
that requires it, document that requirement near the job definition so the need
for write access is explicit.

Source: Linters/SAST tools


jobs:
maintenance:
if: github.repository == github.event.repository.full_name
runs-on: ubuntu-latest
steps:
- name: Checkout repository
uses: actions/checkout@v4
with:
fetch-depth: 0
ref: ${{ github.head_ref || github.ref }}
lfs: true
Comment on lines +19 to +24

Copy link
Copy Markdown

Choose a reason for hiding this comment

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

🔒 Security & Privacy | 🟠 Major | ⚡ Quick win

Set persist-credentials: false (or scope token) given untrusted install step runs.

This job installs project dependencies (uv pip install --system -e ".[dev,demo]") and runs ruff --fix/ruff format before pushing with a contents: write token. Without persist-credentials: false, the token remains in the git config for the whole job, so any malicious code executed via package install/build scripts could exfiltrate it (zizmor's artipacked finding).

🔒 Suggested fix
       - name: Checkout repository
         uses: actions/checkout@v4
         with:
           fetch-depth: 0
           ref: ${{ github.head_ref || github.ref }}
           lfs: true
+          persist-credentials: false

If credentials are needed later for the push step, re-authenticate explicitly right before git push rather than persisting them for the entire job.

📝 Committable suggestion

‼️ IMPORTANT
Carefully review the code before committing. Ensure that it accurately replaces the highlighted code, contains no missing lines, and has no issues with indentation. Thoroughly test & benchmark the code to ensure it meets the requirements.

Suggested change
- name: Checkout repository
uses: actions/checkout@v4
with:
fetch-depth: 0
ref: ${{ github.head_ref || github.ref }}
lfs: true
- name: Checkout repository
uses: actions/checkout@v4
with:
fetch-depth: 0
ref: ${{ github.head_ref || github.ref }}
lfs: true
persist-credentials: false
🧰 Tools
🪛 zizmor (1.26.1)

[warning] 19-24: credential persistence through GitHub Actions artifacts (artipacked): does not set persist-credentials: false

(artipacked)


[error] 20-20: unpinned action reference (unpinned-uses): action is not pinned to a hash (required by blanket policy)

(unpinned-uses)

🤖 Prompt for AI Agents
Verify each finding against current code. Fix only still-valid issues, skip the
rest with a brief reason, keep changes minimal, and validate.

In @.github/workflows/repo-maintenance.yml around lines 19 - 24, The Checkout
repository step leaves the GitHub token persisted for the whole job, which is
unsafe given the untrusted dependency install and formatting steps. Update the
actions/checkout usage in the repo-maintenance workflow to disable persisted
credentials, and if the push later needs authentication, re-establish it
explicitly right before the push step instead of relying on the checkout token.
Use the existing Checkout repository step as the anchor for this change.

Source: Linters/SAST tools


- name: Set up Python
uses: actions/setup-python@v5
Comment on lines +20 to +27

Copy link
Copy Markdown

Choose a reason for hiding this comment

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

🔒 Security & Privacy | 🟠 Major | ⚡ Quick win

Pin actions to a commit SHA per repository policy.

actions/checkout@v4 and actions/setup-python@v5 are unpinned tag references; zizmor reports this as a blocking policy violation (unpinned-uses).

🧰 Tools
🪛 zizmor (1.26.1)

[error] 20-20: unpinned action reference (unpinned-uses): action is not pinned to a hash (required by blanket policy)

(unpinned-uses)


[error] 27-27: unpinned action reference (unpinned-uses): action is not pinned to a hash (required by blanket policy)

(unpinned-uses)

🤖 Prompt for AI Agents
Verify each finding against current code. Fix only still-valid issues, skip the
rest with a brief reason, keep changes minimal, and validate.

In @.github/workflows/repo-maintenance.yml around lines 20 - 27, The workflow is
using unpinned action tags, which violates the repository policy and triggers
the unpinned-uses check. Update the repository maintenance workflow to replace
actions/checkout@v4 and actions/setup-python@v5 with commit SHA references,
keeping the same step names (“checkout” and “Set up Python”) so the workflow
behavior stays unchanged while satisfying the pinning requirement.

Source: Linters/SAST tools

with:
python-version: '3.12'

- name: Install uv
run: pip install uv

- name: Install dependencies
run: |
uv pip install --system -e ".[dev,demo]"
uv pip install --system cyclonedx-bom

- name: Auto-fix formatting and linting
run: |
uv run --with ruff ruff check --fix .
uv run --with ruff ruff format .

- name: Generate Knowledge Graph
run: |
python tools/generate_knowledge_graph.py

- name: Generate Architecture Diagrams
run: |
# Use pyreverse/pydeps if available in the future, placeholder for now
echo "Architecture generation..."
mkdir -p artifacts/architecture
touch artifacts/architecture/README.md

- name: Generate SBOM
run: |
cyclonedx-py environment -o bom.json

- name: Sync Documentation
run: |
python tools/docs_sync.py

- name: Commit and push changes
run: |
git config --global user.name "github-actions[bot]"
git config --global user.email "github-actions[bot]@users.noreply.github.com"
git add -A
git diff --quiet && git diff --staged --quiet || (git commit -m "chore(auto): autonomous repository maintenance updates" && git push)
Comment on lines +63 to +68

Copy link
Copy Markdown

Choose a reason for hiding this comment

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

📐 Maintainability & Code Quality | 🔵 Trivial | ⚡ Quick win

git add -A stages everything unconditionally before commit.

Generated artifacts land at the repo root (bom.json) and in artifacts//docs/; staging with -A risks sweeping in unintended files (stray caches, partial uv/ruff output) not covered by .gitignore. Consider staging only the known generated paths explicitly.

♻️ Suggested fix
-          git add -A
+          git add artifacts/ docs/ bom.json
📝 Committable suggestion

‼️ IMPORTANT
Carefully review the code before committing. Ensure that it accurately replaces the highlighted code, contains no missing lines, and has no issues with indentation. Thoroughly test & benchmark the code to ensure it meets the requirements.

Suggested change
- name: Commit and push changes
run: |
git config --global user.name "github-actions[bot]"
git config --global user.email "github-actions[bot]@users.noreply.github.com"
git add -A
git diff --quiet && git diff --staged --quiet || (git commit -m "chore(auto): autonomous repository maintenance updates" && git push)
- name: Commit and push changes
run: |
git config --global user.name "github-actions[bot]"
git config --global user.email "github-actions[bot]`@users.noreply.github.com`"
git add artifacts/ docs/ bom.json
git diff --quiet && git diff --staged --quiet || (git commit -m "chore(auto): autonomous repository maintenance updates" && git push)
🤖 Prompt for AI Agents
Verify each finding against current code. Fix only still-valid issues, skip the
rest with a brief reason, keep changes minimal, and validate.

In @.github/workflows/repo-maintenance.yml around lines 63 - 68, The commit step
in the workflow is staging too broadly with git add -A, which can pull in
unintended generated or stray files; update the commit logic in the workflow
step that uses git add -A / git commit / git push to stage only the known
maintenance outputs instead. Keep the commit/push flow the same, but restrict
staging to the explicit generated paths used by this job (for example the
repository maintenance artifacts and docs outputs) so only intended changes are
committed.

5 changes: 5 additions & 0 deletions .github/workflows/security.yml
Original file line number Diff line number Diff line change
Expand Up @@ -13,6 +13,8 @@ jobs:
runs-on: ubuntu-latest
steps:
- uses: actions/checkout@v4
with:
lfs: true
Comment on lines 15 to +17

Copy link
Copy Markdown

Choose a reason for hiding this comment

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

🔒 Security & Privacy | 🔵 Trivial | ⚡ Quick win

Consider setting persist-credentials: false on checkout.

zizmor flags these checkout steps for credential persistence (artipacked), same pattern as in code-quality.yml.

🔒 Proposed fix
     - uses: actions/checkout@v4
       with:
         lfs: true
+        persist-credentials: false

Also applies to: 56-58

🧰 Tools
🪛 zizmor (1.26.1)

[warning] 15-17: credential persistence through GitHub Actions artifacts (artipacked): does not set persist-credentials: false

(artipacked)


[error] 15-15: unpinned action reference (unpinned-uses): action is not pinned to a hash (required by blanket policy)

(unpinned-uses)

🤖 Prompt for AI Agents
Verify each finding against current code. Fix only still-valid issues, skip the
rest with a brief reason, keep changes minimal, and validate.

In @.github/workflows/security.yml around lines 15 - 17, The checkout step in
the security workflow is persisting repository credentials by default, which
zizmor flags as an artipacked risk. Update the actions/checkout configuration
used in this workflow to explicitly set persist-credentials to false, matching
the existing pattern in code-quality.yml. Apply the same change to the other
checkout step referenced in the review so both workflows use the same safer
checkout behavior.

Source: Linters/SAST tools


- name: Set up Python
uses: actions/setup-python@v5
Expand All @@ -38,6 +40,7 @@ jobs:
steps:
- uses: actions/checkout@v4
with:
lfs: true
fetch-depth: 0

- name: TruffleHog OSS
Expand All @@ -51,6 +54,8 @@ jobs:
runs-on: ubuntu-latest
steps:
- uses: actions/checkout@v4
with:
lfs: true

- name: Run Trivy vulnerability scanner in repo mode
uses: aquasecurity/trivy-action@master
Expand Down
22 changes: 22 additions & 0 deletions .github/workflows/stale.yml
Original file line number Diff line number Diff line change
@@ -0,0 +1,22 @@
name: Close Stale Issues

on:
schedule:
- cron: '30 1 * * *'

permissions:
issues: write
pull-requests: write
Comment on lines +3 to +9

Copy link
Copy Markdown

Choose a reason for hiding this comment

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

🔒 Security & Privacy | 🟡 Minor | ⚡ Quick win

Scope permissions to job level.

Same concern as greetings.yml: workflow-level issues: write / pull-requests: write is broader than necessary. Scope to the stale job and document why write access is needed.

🔒 Proposed fix
-permissions:
-  issues: write
-  pull-requests: write
-
 jobs:
   stale:
     runs-on: ubuntu-latest
+    permissions:
+      issues: write        # required to label/comment/close stale issues
+      pull-requests: write # required to label/comment/close stale PRs
     steps:
🧰 Tools
🪛 zizmor (1.26.1)

[error] 8-8: overly broad permissions (excessive-permissions): issues: write is overly broad at the workflow level

(excessive-permissions)


[error] 9-9: overly broad permissions (excessive-permissions): pull-requests: write is overly broad at the workflow level

(excessive-permissions)


[warning] 8-8: permissions without explanatory comments (undocumented-permissions): needs an explanatory comment

(undocumented-permissions)


[warning] 3-5: insufficient job-level concurrency limits (concurrency-limits): workflow is missing concurrency setting

(concurrency-limits)

🤖 Prompt for AI Agents
Verify each finding against current code. Fix only still-valid issues, skip the
rest with a brief reason, keep changes minimal, and validate.

In @.github/workflows/stale.yml around lines 3 - 9, The workflow currently
grants broad `issues: write` and `pull-requests: write` permissions at the top
level; move these permissions into the `stale` job so access is limited to only
the job that needs it. Update the workflow around the `stale` job definition to
scope write access there, and add a brief note in the job configuration or
accompanying comments explaining why the job needs write permissions.

Source: Linters/SAST tools


jobs:
stale:
runs-on: ubuntu-latest
steps:
- uses: actions/stale@v9

Copy link
Copy Markdown

Choose a reason for hiding this comment

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

🔒 Security & Privacy | 🟡 Minor | ⚡ Quick win

🧩 Analysis chain

🌐 Web query:

What changed in actions/stale v10 compared to v9?

💡 Result:

The transition from actions/stale v9 to v10 introduced a primary breaking change and included new functional enhancements. Breaking Change The major breaking change in v10 is the upgrade of the underlying runtime from Node.js 20 to Node.js 24 [1][2][3]. Because of this upgrade, users must ensure that their GitHub Actions runner is on version v2.327.1 or later to maintain compatibility with the action [2][3][4]. New Features and Enhancements In addition to the runtime upgrade, v10 introduced the following feature: - Sort-by option: A new configuration option, sort-by, was added to allow for better control over how issues and pull requests are processed [2][5]. Subsequent updates in the v10 series (such as v10.1.0) also introduced the only-issue-types option, allowing users to filter issues by type [1][6]. Compatibility To use actions/stale v10, confirm your runner environment meets the minimum version requirement (v2.327.1+) to support the Node.js 24 runtime [2][3].

Citations:


🏁 Script executed:

sed -n '1,120p' .github/workflows/stale.yml

Repository: NITISH-R-G/ev-grid-oracle

Length of output: 846


🏁 Script executed:

rg -n "runs-on|actions/stale|workflow_dispatch|schedule" .github/workflows -g '*.yml' -g '*.yaml'

Repository: NITISH-R-G/ev-grid-oracle

Length of output: 1339


🌐 Web query:

GitHub-hosted ubuntu-latest runner version v2.327.1 Node.js 24 compatibility

💡 Result:

GitHub Actions runner version v2.327.1 is the minimum version required to support the execution of actions built on the Node.js 24 runtime [1][2][3]. Key details regarding this compatibility include: * Requirement: Runner version v2.327.1 or higher is necessary for any GitHub Action that specifies using: node24 in its action.yml file [4][5][3]. * Self-Hosted Runners: If you are using self-hosted runners, they must be updated to at least v2.327.1 to successfully run actions that utilize Node.js 24 [1][5]. GitHub documentation advises that self-hosted runners should generally be updated within 30 days to ensure compatibility with new runner capabilities [5]. * Node.js Availability: GitHub-hosted runners (such as ubuntu-latest) include Node.js 24 in their pre-installed environment [6]. You can explicitly use it in your workflows by using the actions/setup-node action [6][7]. * Usage: When developing or updating GitHub Actions to use Node.js 24, ensure that your environment and target runners meet the v2.327.1 version requirement to avoid errors such as "Parameter 'using: node24' is not supported" [4][5][2].

Citations:


Pin actions/stale to a full commit SHA
actions/stale@v9 is mutable. Pinning to a SHA avoids supply-chain drift; v10 is available, but it needs a runner that supports Node 24.

🧰 Tools
🪛 zizmor (1.26.1)

[error] 15-15: unpinned action reference (unpinned-uses): action is not pinned to a hash (required by blanket policy)

(unpinned-uses)

🤖 Prompt for AI Agents
Verify each finding against current code. Fix only still-valid issues, skip the
rest with a brief reason, keep changes minimal, and validate.

In @.github/workflows/stale.yml at line 15, The workflow uses a mutable
actions/stale tag, so update the stale step in the stale workflow to a full
commit SHA instead of actions/stale@v9. Locate the existing actions/stale
reference and replace it with the pinned SHA for the same major version, keeping
the step otherwise unchanged; if considering v10, ensure the runner
compatibility with Node 24 first.

Source: Linters/SAST tools

with:
stale-issue-message: 'This issue is stale because it has been open 30 days with no activity. Remove stale label or comment or this will be closed in 5 days.'
stale-pr-message: 'This PR is stale because it has been open 30 days with no activity. Remove stale label or comment or this will be closed in 5 days.'
days-before-stale: 30
days-before-close: 5
stale-issue-label: 'stale'
stale-pr-label: 'stale'
12 changes: 12 additions & 0 deletions CODE_OF_CONDUCT.md
Original file line number Diff line number Diff line change
@@ -0,0 +1,12 @@
# Contributor Covenant Code of Conduct

## Our Pledge

We as members, contributors, and leaders pledge to make participation in our
community a harassment-free experience for everyone, regardless of age, body
size, visible or invisible disability, ethnicity, sex characteristics, gender
identity and expression, level of experience, education, socio-economic status,
nationality, personal appearance, race, religion, or sexual identity
and orientation.

## Our Standards
Comment on lines +1 to +12

Copy link
Copy Markdown

Choose a reason for hiding this comment

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

📐 Maintainability & Code Quality | 🟠 Major | ⚡ Quick win

Complete the code of conduct before merging.

The file ends at ## Our Standards, so the actual standards, enforcement, and contact sections are missing. As written, this is not a complete Code of Conduct.

🤖 Prompt for AI Agents
Verify each finding against current code. Fix only still-valid issues, skip the
rest with a brief reason, keep changes minimal, and validate.

In `@CODE_OF_CONDUCT.md` around lines 1 - 12, The Code of Conduct is incomplete
because it stops at the “Our Standards” section and is missing the required
standards, enforcement, and contact sections. Extend the existing Contributor
Covenant in CODE_OF_CONDUCT.md by adding the remaining standard sections after
the current “Our Standards” heading so the document is complete before merge.

Loading
Loading