Skip to content

feat: add about, terms, and feedback pages#70

Open
ghanshyam2005singh wants to merge 4 commits into
alphaonelabs:mainfrom
ghanshyam2005singh:feat/about-term-feedback
Open

feat: add about, terms, and feedback pages#70
ghanshyam2005singh wants to merge 4 commits into
alphaonelabs:mainfrom
ghanshyam2005singh:feat/about-term-feedback

Conversation

@ghanshyam2005singh

@ghanshyam2005singh ghanshyam2005singh commented Jun 21, 2026

Copy link
Copy Markdown
Contributor

Implements the About, Terms, and Feedback pages for Alpha One Labs and wires them into the site navigation.

About Page

  • Added dedicated About page
  • Added organization timeline (2009–2025)
  • Added platform statistics section
  • Added mission and values section
  • Added call-to-action section for learners and teachers

Terms Page

  • Added comprehensive Terms page
  • Added sticky table of contents navigation
  • Added active section highlighting while scrolling
  • Added privacy-related subsections with anchor links
  • Added support and contact section

Feedback Page

  • Added feedback submission form
  • Added optional name and email fields
  • Added live character counter
  • Added success state with reset flow
  • Added community contact links

Backend

Added:

  • POST /api/feedback

Features:

  • Mailgun email notifications

  • Optional Slack notifications

  • Environment variable support for:

    • ADMIN_EMAIL
    • SLACK_WEBHOOK_URL

Navigation Updates

Updated navbar and footer links to point to:

  • /about.html
  • /terms.html
  • /feedback.html

Testing

Verified:

  • Page rendering
  • Mobile responsiveness
  • Terms page navigation
  • Feedback form validation
  • Character limits
  • Success state handling
  • Navigation links
  • API submission flow
Screencast.from.2026-06-21.11-49-39.mp4

Added three new site pages and a feedback API to expand Alpha One Labs’ public-facing experience.

  • About page: redesigned with a hero/mission section, stats cards, a detailed 2009–2025 timeline, core values, and CTAs for learners and teachers.
  • Terms page: reworked into a structured policy layout with a sticky table of contents, anchor-linked sections, privacy/data subsections, and a support link to Feedback.
  • Feedback page: added a richer form experience with optional contact fields, live character counting, validation, success/reset states, and community contact links.
  • Backend: introduced POST /api/feedback to validate submissions, send admin email notifications via Mailgun when configured, and optionally forward best-effort Slack notifications.

Navigation was updated to point to the new pages, improving discoverability across the site. The main user impact is clearer onboarding, easier access to policies, and a smoother way to send feedback.

@coderabbitai

coderabbitai Bot commented Jun 21, 2026

Copy link
Copy Markdown

Review Change Stack

Warning

Review limit reached

@ghanshyam2005singh, you've reached your PR review limit, so we couldn't start this review.

Next review available in: 43 minutes

Enable usage-based reviews in Billing to review now. Otherwise, wait until the next included review is available.
You're only billed for reviews past your plan's rate limits ($0.25/file).

How can I continue?

After more reviews become available, a review can be triggered using the @coderabbitai review command as a PR comment. Alternatively, push new commits to this PR.

To avoid repeated limits, reduce automatic review volume by pausing incremental auto-reviews earlier, using label-based review opt-in, excluding WIP or generated PR titles, or requesting reviews manually when the PR is ready. If your team needs uninterrupted high-volume reviews, an organization admin can enable usage-based reviews.

How do review limits work?

CodeRabbit enforces per-developer PR review limits for each organization. Most developers receive the normal plan review availability.

For paid Pro and Pro+ PR reviews, CodeRabbit uses adaptive limits for sustained high-volume activity. When a developer's recent PR review activity reaches the 95th percentile or higher among CodeRabbit users, additional reviews become available more gradually as earlier reviews age out of the rolling window.

Please refer docs for additional details.

Review details
⚙️ Run configuration

Configuration used: Repository: alphaonelabs/coderabbit/.coderabbit.yaml

Review profile: ASSERTIVE

Plan: Pro

Run ID: f9ee4c04-2946-4909-b409-6ce3ee0d85be

📥 Commits

Reviewing files that changed from the base of the PR and between a01a483 and 576e33c.

📒 Files selected for processing (1)
  • public/feedback.html

Walkthrough

This PR adds a new POST /api/feedback backend endpoint in worker.py that validates input, sends admin notification emails via Mailgun, and posts to Slack, alongside major content restructuring of about.html, feedback.html, and terms.html into styled multi-section layouts.

Changes

New Pages and Feedback API

Layer / File(s) Summary
Feedback API endpoint
src/worker.py
Adds POST /api/feedback route dispatch and api_submit_feedback handler validating description length, normalizing name/email, sending admin emails via Mailgun, and posting best-effort Slack notifications.
Feedback page UI and client-side submission
public/feedback.html
Adds hero/sidebar layout with external contact links, a form with hidden success/error states, character-counted description textarea, and a submit listener posting JSON to /api/feedback.
About page restructure
public/about.html
Replaces content with hero/mission section, four-card stats grid, card-based multi-year timeline, values section, and CTA linking to /dashboard.html and /teach.html.
Terms page with sticky TOC
public/terms.html
Replaces content with a two-column layout featuring a sticky TOC sidebar and seven anchored sections, ending with a support callout linking to /feedback.html.

Estimated code review effort: 3 (Moderate) | ~25 minutes

Sequence Diagram(s)

sequenceDiagram
  participant Browser
  participant Dispatch as worker.py _dispatch
  participant Handler as api_submit_feedback
  participant Mailgun
  participant Slack

  Browser->>Dispatch: POST /api/feedback (JSON body)
  Dispatch->>Handler: route match
  Handler->>Handler: parse JSON, validate description ≤5000 chars
  Handler->>Mailgun: _send_email_via_mailgun (if ADMIN_EMAIL configured)
  Handler->>Slack: POST to SLACK_WEBHOOK_URL (if configured)
  Handler-->>Browser: 200 ok(response) or 400
Loading

Related issues: None linked in the provided context.

Related PRs: None linked in the provided context.

Suggested labels: frontend, backend, enhancement

Suggested reviewers: None identified from the provided context.


🐰 A rabbit hops through pages new,
Feedback flies to Slack and mail too,
Timelines bloom in cards so bright,
Terms find order, TOC in sight,
Hop hop — the docs feel right!

🚥 Pre-merge checks | ✅ 4 | ❌ 1

❌ Failed checks (1 warning)

Check name Status Explanation Resolution
Docstring Coverage ⚠️ Warning Docstring coverage is 0.00% which is insufficient. The required threshold is 80.00%. Write docstrings for the functions missing them to satisfy the coverage threshold.
✅ Passed checks (4 passed)
Check name Status Explanation
Description Check ✅ Passed Check skipped - CodeRabbit’s high-level summary is enabled.
Title check ✅ Passed The title clearly summarizes the main change by adding the About, Terms, and Feedback pages.
Linked Issues check ✅ Passed Check skipped because no linked issues were found for this pull request.
Out of Scope Changes check ✅ Passed Check skipped because no linked issues were found for this pull request.
✨ Finishing Touches
🧪 Generate unit tests (beta)
  • Create PR with unit tests

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.

@coderabbitai coderabbitai Bot left a comment

Copy link
Copy Markdown

Choose a reason for hiding this comment

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

Actionable comments posted: 11

🤖 Prompt for all review comments with 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.

Inline comments:
In `@public/about.html`:
- Around line 11-13: The script tag loading from cdn.tailwindcss.com and the
link tag loading from cdnjs.cloudflare.com do not include integrity attributes
for Subresource Integrity (SRI) protection. Add the integrity attribute with the
appropriate SRI hash value to both the Tailwind CSS script tag and the Font
Awesome stylesheet link tag. You can generate the SRI hashes by computing the
base64-encoded SHA-384 hash of the respective files or by using an online SRI
hash generator tool with the CDN URLs.
- Around line 66-69: The decorative hero icons (fa-microscope, fa-robot,
fa-wrench, and fa-graduation-cap) are not hidden from screen readers, causing
assistive technology to announce non-informational visual elements. Add
aria-hidden="true" attribute to each of the four icon wrapper divs (or directly
to the i elements) to prevent screen readers from announcing this decorative
content, improving accessibility for users relying on assistive technology.

In `@public/feedback.html`:
- Line 149: The reset CTA button with onclick="resetForm()" is missing an
explicit type attribute, which could cause it to default to type="submit" if the
HTML structure changes, leading to accidental form submissions. Add the
`type="button"` attribute to the button element to explicitly define its
behavior and prevent any unintended form-submit behavior regardless of future
markup reorganization.
- Around line 168-208: The form labels for the Name, Email, and Feedback fields
are not programmatically associated with their corresponding input controls. Add
the for attribute to each label element to match the id attributes of their
associated form controls: add for="feedback-name" to the label preceding the
input with id="feedback-name", add for="feedback-email" to the label preceding
the input with id="feedback-email", and add for="feedback-description" to the
label preceding the textarea with id="feedback-description". This establishes
the proper programmatic relationship required for accessibility and screen
reader navigation.

In `@public/partials/navbar.html`:
- Around line 145-147: The anchor element with the "Status" link in the navbar
contains a placeholder href="#" that points to nowhere, creating a dead-end menu
item. Replace the href="#" with the actual route path where the Status page will
be located (for example, href="/status" or whatever the real endpoint is), or
alternatively, remove the entire anchor element and its containing list item if
the Status page does not exist yet and should not be exposed to users until it
is ready.

In `@public/terms.html`:
- Around line 386-392: In the IntersectionObserver callback, when toggling the
'active' class on tocLinks, also set the aria-current attribute for
accessibility. When a link receives the 'active' class (when
entry.isIntersecting is true), set aria-current="location" on that link. When
removing the 'active' class from other links via classList.toggle, also remove
the aria-current attribute by using removeAttribute. This ensures screen reader
users receive equivalent navigation context alongside the visual CSS indication.
- Line 90: The table of contents has a numbering inconsistency where the TOC
link with href="`#ip-rights`" and the corresponding section header jump from
subsection 6.2 directly to 6.4, skipping 6.3 entirely. Fix this by either adding
the missing subsection 6.3 between the 6.2 and 6.4 entries in both the TOC link
and the actual section header in the document, or by renumbering the 6.4
reference to 6.3 to maintain sequential numbering consistency throughout the
terms document.

In `@src/worker.py`:
- Around line 2723-2726: The try-except block around json.loads is catching
Exception which is too broad and masks internal errors as 400 responses. Replace
the generic Exception handler with a specific exception type for JSON parsing
failures (json.JSONDecodeError in Python 3.5+, or ValueError for compatibility).
This allows unexpected runtime errors to propagate through normal error handling
while still catching legitimate JSON parsing failures and returning the 400
status code appropriately.
- Around line 2756-2767: The bare except Exception pass statement in the Slack
webhook delivery block silently swallows all failures including non-2xx
responses, making operational issues unobservable. Replace the except Exception
pass with proper error logging that captures exception details. Additionally,
capture the response object returned from js.fetch(slack_url, options), check
its status property, and log a warning if the status indicates failure (not in
the 2xx range), including both the status code and response body in the log
message so Slack delivery issues are properly tracked and debuggable.
- Around line 2723-2729: After successfully parsing the JSON with json.loads in
the try block, add a validation check to ensure that the parsed body variable is
a dictionary before attempting to call the .get() method on it. If body is not a
dictionary (for example, if it's a list or string), return the same "Invalid
JSON" error with a 400 status code immediately. This prevents AttributeError
exceptions when .get("description") is called on non-dict objects, which would
otherwise result in an unhandled 500 error.
- Around line 2741-2748: The variables name, email, and description are being
directly interpolated into the HTML email template without escaping, creating an
XSS vulnerability where users could inject malicious HTML or scripts. Import
html.escape from the standard library and apply it to each of these three
variables (name, email, description) before they are interpolated into the
f-string to properly sanitize user-supplied input and prevent HTML injection
attacks.
🪄 Autofix (Beta)

Fix all unresolved CodeRabbit comments on this PR:

  • Push a commit to this branch (recommended)
  • Create a new PR with the fixes

ℹ️ Review info
⚙️ Run configuration

Configuration used: Repository: alphaonelabs/coderabbit/.coderabbit.yaml

Review profile: ASSERTIVE

Plan: Pro

Run ID: 7aa767a7-80d4-483c-bf16-5a65d728ba3e

📥 Commits

Reviewing files that changed from the base of the PR and between 997b01e and 6b0be5a.

📒 Files selected for processing (6)
  • public/about.html
  • public/feedback.html
  • public/partials/footer.html
  • public/partials/navbar.html
  • public/terms.html
  • src/worker.py

Comment thread public/about.html Outdated
Comment thread public/about.html Outdated
Comment thread public/feedback.html Outdated
Comment thread public/feedback.html Outdated
Comment thread public/partials/navbar.html Outdated
Comment thread public/terms.html Outdated
Comment thread src/worker.py
Comment thread src/worker.py
Comment thread src/worker.py
Comment thread src/worker.py Outdated
@A1L13N

A1L13N commented Jul 6, 2026

Copy link
Copy Markdown
Contributor

please update and show screenshots

@A1L13N

A1L13N commented Jul 6, 2026

Copy link
Copy Markdown
Contributor

oh I see the video, please update the code to fix the conflicts

@coderabbitai coderabbitai Bot left a comment

Copy link
Copy Markdown

Choose a reason for hiding this comment

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

Actionable comments posted: 3

Caution

Some comments are outside the diff and can’t be posted inline due to platform limitations.

⚠️ Outside diff range comments (5)
public/feedback.html (2)

133-141: 🎯 Functional Correctness | 🟡 Minor | ⚡ Quick win

Character counter isn't wired up, and textarea has no maxlength.

The #char-count element (Line 141) displays "0 / 5000" but nothing in the script updates it on input, so it will remain static regardless of what the user types — despite the PR describing a "live character counter." Additionally, the textarea has no maxlength attribute, so users can type past the 5000-character server-side limit before submitting, only to be rejected after the fact.

Proposed fix
               <textarea
                 id="feedback-description"
                 name="description"
                 rows="5"
                 required
+                maxlength="5000"
                 placeholder="Your feedback..."
document.getElementById('feedback-description').addEventListener('input', (e) => {
  document.getElementById('char-count').textContent = `${e.target.value.length} / 5000`;
});
🤖 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 `@public/feedback.html` around lines 133 - 141, The feedback textarea currently
shows a static char count and allows input beyond the intended limit. Update the
feedback form markup in the feedback textarea/char-count section so the
`feedback-description` field enforces a 5000-character `maxlength`, and wire the
`char-count` element to the `input` event so it updates live as the user types.
Use the existing `feedback-description` and `char-count` IDs to locate the
elements and keep the counter in sync with the textarea value.

145-152: 🩺 Stability & Availability | 🟠 Major | ⚡ Quick win

Submit button isn't disabled during the request, allowing duplicate submissions.

Since the button stays enabled and un-labeled as "submitting" throughout the await fetch(...) call, a user (or an impatient double-click) can fire multiple non-idempotent feedback submissions before the first response returns.

🤖 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 `@public/feedback.html` around lines 145 - 152, The submit button in the
feedback form stays enabled during the async request, which allows duplicate
submissions. Update the feedback submission flow in the code that drives the
`submit-btn` and `submit-label` elements so the button is disabled immediately
before the `await fetch(...)` call, then re-enabled in the completion/error
path. Also change the label to a submitting state while the request is in
flight, and restore it afterward.
public/about.html (3)

45-56: 📐 Maintainability & Code Quality | 🟠 Major | ⚡ Quick win

Use real heading elements for section titles, not styled <span>.

"Our Journey" (Line 52) and "What We Stand For" (Line 201) are the visual titles for major page sections but are rendered as <span> inside a decorative divider row, not actual <h2>/<h3> elements. Screen reader users navigating by heading structure (a common a11y workflow) will skip these section titles entirely, even though h1 and h3 are used elsewhere on the page.

♿ Suggested fix
-<span class="text-2xl font-extrabold bg-gradient-to-r from-teal-600 to-cyan-600 dark:from-teal-400 dark:to-cyan-400 bg-clip-text text-transparent">Our Journey</span>
+<h2 class="text-2xl font-extrabold bg-gradient-to-r from-teal-600 to-cyan-600 dark:from-teal-400 dark:to-cyan-400 bg-clip-text text-transparent">Our Journey</h2>

Apply the same pattern to the "What We Stand For" span at Line 201.

As per path instructions, review HTML templates for accessibility (semantic elements).

Also applies to: 193-204

🤖 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 `@public/about.html` around lines 45 - 56, The section titles in the decorative
divider rows are using styled spans instead of real headings, so update the “Our
Journey” markup in the about page to use an appropriate heading element and
apply the same semantic fix to the “What We Stand For” block. Keep the visual
styling, but move it onto the heading element inside the existing divider
structure so the page preserves heading navigation for assistive tech and
matches the other semantic headings already used in the template.

Source: Path instructions


50-50: 📐 Maintainability & Code Quality | 🟠 Major | ⚡ Quick win

Hide decorative icons from assistive tech.

All the new <i class="fas ..."> icons across the timeline badges, value cards, and CTA buttons are purely decorative — each is paired with adjacent visible text (year badges, headings, button labels). Without aria-hidden="true", screen readers may announce meaningless icon-font glyph names alongside the real label. This mirrors the same fix already applied to the hero icons in commit dc4af65; the newly added icons in this restructure need the same treatment.

♿ Example fix pattern (apply to each decorative icon)
-<i class="fas fa-flag text-white text-sm"></i>
+<i class="fas fa-flag text-white text-sm" aria-hidden="true"></i>

As per path instructions, review HTML templates for accessibility (ARIA attributes, semantic elements).

Also applies to: 63-63, 79-79, 95-95, 111-111, 127-127, 143-143, 159-159, 175-175, 199-199, 209-209, 219-219, 229-229, 245-245, 248-248

🤖 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 `@public/about.html` at line 50, The decorative Font Awesome icons used
throughout the about page should be hidden from assistive technology. Update the
repeated icon elements in the timeline badges, value cards, and CTA buttons
within the about template so the existing icon markup includes
aria-hidden="true", matching the pattern already used for the hero icons. Use
the repeated <i class="fas ..."> elements in the about page as the targets for
this accessibility fix.

Source: Path instructions


240-251: 🎯 Functional Correctness | 🟡 Minor | ⚡ Quick win

Close the CTA section and wrapper divs in public/about.html:240-251. The CTA block opens a <section> and an inner flex <div>, but only one </div> appears before </main>. Add the missing </section> and the outer wrapper </div> so the HTML stays well-formed.

🤖 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 `@public/about.html` around lines 240 - 251, The CTA block in about.html is
missing closing tags, leaving the section and flex wrapper unbalanced. Update
the markup around the CTA area by closing the inner flex div and the enclosing
section before the main element ends, using the existing CTA section and anchor
structure as the reference points so the HTML remains well-formed.
🤖 Prompt for all review comments with 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.

Inline comments:
In `@public/feedback.html`:
- Around line 159-177: The submit handler in feedback.html is wired to a missing
feedback-status element, so it fails before the request and never toggles the
built-in success/error UI. Update the feedback-form listener to use the existing
success-state, error-banner, and error-message elements (and any other relevant
UI hooks in this markup), guard against null lookups, and drive those states
explicitly on submit, success, and failure. Keep the fetch flow in the same
handler, but replace the current status.textContent usage with show/hide logic
that matches the existing feedback form UI.
- Around line 166-172: The feedback form payload key is mismatched with the API
contract, causing api_feedback to miss the expected message field. Update the
submit logic in the feedback form handler so the FormData-derived body sends
message instead of description, or adjust api_feedback to accept description as
an alias; use the existing fetch('/api/feedback') submission path and the form
submit flow to locate the fix.

In `@public/terms.html`:
- Line 22: Add aria-hidden="true" to every purely decorative Font Awesome <i>
icon in public/terms.html, including the Contents marker and the other
section/contact icons referenced in the review. Update the affected markup in
the terms page so only meaningful text remains exposed to assistive tech, and
keep the same pattern consistently across all decorative icon tags in the file.

---

Outside diff comments:
In `@public/about.html`:
- Around line 45-56: The section titles in the decorative divider rows are using
styled spans instead of real headings, so update the “Our Journey” markup in the
about page to use an appropriate heading element and apply the same semantic fix
to the “What We Stand For” block. Keep the visual styling, but move it onto the
heading element inside the existing divider structure so the page preserves
heading navigation for assistive tech and matches the other semantic headings
already used in the template.
- Line 50: The decorative Font Awesome icons used throughout the about page
should be hidden from assistive technology. Update the repeated icon elements in
the timeline badges, value cards, and CTA buttons within the about template so
the existing icon markup includes aria-hidden="true", matching the pattern
already used for the hero icons. Use the repeated <i class="fas ..."> elements
in the about page as the targets for this accessibility fix.
- Around line 240-251: The CTA block in about.html is missing closing tags,
leaving the section and flex wrapper unbalanced. Update the markup around the
CTA area by closing the inner flex div and the enclosing section before the main
element ends, using the existing CTA section and anchor structure as the
reference points so the HTML remains well-formed.

In `@public/feedback.html`:
- Around line 133-141: The feedback textarea currently shows a static char count
and allows input beyond the intended limit. Update the feedback form markup in
the feedback textarea/char-count section so the `feedback-description` field
enforces a 5000-character `maxlength`, and wire the `char-count` element to the
`input` event so it updates live as the user types. Use the existing
`feedback-description` and `char-count` IDs to locate the elements and keep the
counter in sync with the textarea value.
- Around line 145-152: The submit button in the feedback form stays enabled
during the async request, which allows duplicate submissions. Update the
feedback submission flow in the code that drives the `submit-btn` and
`submit-label` elements so the button is disabled immediately before the `await
fetch(...)` call, then re-enabled in the completion/error path. Also change the
label to a submitting state while the request is in flight, and restore it
afterward.
🪄 Autofix (Beta)

Fix all unresolved CodeRabbit comments on this PR:

  • Push a commit to this branch (recommended)
  • Create a new PR with the fixes

ℹ️ Review info
⚙️ Run configuration

Configuration used: Repository: alphaonelabs/coderabbit/.coderabbit.yaml

Review profile: ASSERTIVE

Plan: Pro

Run ID: 9c95e551-cb34-4539-a591-0d623eb9f394

📥 Commits

Reviewing files that changed from the base of the PR and between 6b0be5a and a01a483.

📒 Files selected for processing (4)
  • public/about.html
  • public/feedback.html
  • public/terms.html
  • src/worker.py
💤 Files with no reviewable changes (1)
  • src/worker.py

@coderabbitai coderabbitai Bot left a comment

Copy link
Copy Markdown

Choose a reason for hiding this comment

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

Caution

Inline review comments failed to post. This is likely due to GitHub's internal server error or limits when posting large numbers of comments. If you are seeing this consistently it is likely a permissions issue. Please check "Moderation" -> "Code review limits" under your organization settings.

Actionable comments posted: 3

Caution

Some comments are outside the diff and can’t be posted inline due to platform limitations.

⚠️ Outside diff range comments (5)
public/feedback.html (2)

133-141: 🎯 Functional Correctness | 🟡 Minor | ⚡ Quick win

Character counter isn't wired up, and textarea has no maxlength.

The #char-count element (Line 141) displays "0 / 5000" but nothing in the script updates it on input, so it will remain static regardless of what the user types — despite the PR describing a "live character counter." Additionally, the textarea has no maxlength attribute, so users can type past the 5000-character server-side limit before submitting, only to be rejected after the fact.

Proposed fix
               <textarea
                 id="feedback-description"
                 name="description"
                 rows="5"
                 required
+                maxlength="5000"
                 placeholder="Your feedback..."
document.getElementById('feedback-description').addEventListener('input', (e) => {
  document.getElementById('char-count').textContent = `${e.target.value.length} / 5000`;
});
🤖 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 `@public/feedback.html` around lines 133 - 141, The feedback textarea currently
shows a static char count and allows input beyond the intended limit. Update the
feedback form markup in the feedback textarea/char-count section so the
`feedback-description` field enforces a 5000-character `maxlength`, and wire the
`char-count` element to the `input` event so it updates live as the user types.
Use the existing `feedback-description` and `char-count` IDs to locate the
elements and keep the counter in sync with the textarea value.

145-152: 🩺 Stability & Availability | 🟠 Major | ⚡ Quick win

Submit button isn't disabled during the request, allowing duplicate submissions.

Since the button stays enabled and un-labeled as "submitting" throughout the await fetch(...) call, a user (or an impatient double-click) can fire multiple non-idempotent feedback submissions before the first response returns.

🤖 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 `@public/feedback.html` around lines 145 - 152, The submit button in the
feedback form stays enabled during the async request, which allows duplicate
submissions. Update the feedback submission flow in the code that drives the
`submit-btn` and `submit-label` elements so the button is disabled immediately
before the `await fetch(...)` call, then re-enabled in the completion/error
path. Also change the label to a submitting state while the request is in
flight, and restore it afterward.
public/about.html (3)

45-56: 📐 Maintainability & Code Quality | 🟠 Major | ⚡ Quick win

Use real heading elements for section titles, not styled <span>.

"Our Journey" (Line 52) and "What We Stand For" (Line 201) are the visual titles for major page sections but are rendered as <span> inside a decorative divider row, not actual <h2>/<h3> elements. Screen reader users navigating by heading structure (a common a11y workflow) will skip these section titles entirely, even though h1 and h3 are used elsewhere on the page.

♿ Suggested fix
-<span class="text-2xl font-extrabold bg-gradient-to-r from-teal-600 to-cyan-600 dark:from-teal-400 dark:to-cyan-400 bg-clip-text text-transparent">Our Journey</span>
+<h2 class="text-2xl font-extrabold bg-gradient-to-r from-teal-600 to-cyan-600 dark:from-teal-400 dark:to-cyan-400 bg-clip-text text-transparent">Our Journey</h2>

Apply the same pattern to the "What We Stand For" span at Line 201.

As per path instructions, review HTML templates for accessibility (semantic elements).

Also applies to: 193-204

🤖 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 `@public/about.html` around lines 45 - 56, The section titles in the decorative
divider rows are using styled spans instead of real headings, so update the “Our
Journey” markup in the about page to use an appropriate heading element and
apply the same semantic fix to the “What We Stand For” block. Keep the visual
styling, but move it onto the heading element inside the existing divider
structure so the page preserves heading navigation for assistive tech and
matches the other semantic headings already used in the template.

Source: Path instructions


50-50: 📐 Maintainability & Code Quality | 🟠 Major | ⚡ Quick win

Hide decorative icons from assistive tech.

All the new <i class="fas ..."> icons across the timeline badges, value cards, and CTA buttons are purely decorative — each is paired with adjacent visible text (year badges, headings, button labels). Without aria-hidden="true", screen readers may announce meaningless icon-font glyph names alongside the real label. This mirrors the same fix already applied to the hero icons in commit dc4af65; the newly added icons in this restructure need the same treatment.

♿ Example fix pattern (apply to each decorative icon)
-<i class="fas fa-flag text-white text-sm"></i>
+<i class="fas fa-flag text-white text-sm" aria-hidden="true"></i>

As per path instructions, review HTML templates for accessibility (ARIA attributes, semantic elements).

Also applies to: 63-63, 79-79, 95-95, 111-111, 127-127, 143-143, 159-159, 175-175, 199-199, 209-209, 219-219, 229-229, 245-245, 248-248

🤖 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 `@public/about.html` at line 50, The decorative Font Awesome icons used
throughout the about page should be hidden from assistive technology. Update the
repeated icon elements in the timeline badges, value cards, and CTA buttons
within the about template so the existing icon markup includes
aria-hidden="true", matching the pattern already used for the hero icons. Use
the repeated <i class="fas ..."> elements in the about page as the targets for
this accessibility fix.

Source: Path instructions


240-251: 🎯 Functional Correctness | 🟡 Minor | ⚡ Quick win

Close the CTA section and wrapper divs in public/about.html:240-251. The CTA block opens a <section> and an inner flex <div>, but only one </div> appears before </main>. Add the missing </section> and the outer wrapper </div> so the HTML stays well-formed.

🤖 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 `@public/about.html` around lines 240 - 251, The CTA block in about.html is
missing closing tags, leaving the section and flex wrapper unbalanced. Update
the markup around the CTA area by closing the inner flex div and the enclosing
section before the main element ends, using the existing CTA section and anchor
structure as the reference points so the HTML remains well-formed.
🤖 Prompt for all review comments with 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.

Inline comments:
In `@public/feedback.html`:
- Around line 159-177: The submit handler in feedback.html is wired to a missing
feedback-status element, so it fails before the request and never toggles the
built-in success/error UI. Update the feedback-form listener to use the existing
success-state, error-banner, and error-message elements (and any other relevant
UI hooks in this markup), guard against null lookups, and drive those states
explicitly on submit, success, and failure. Keep the fetch flow in the same
handler, but replace the current status.textContent usage with show/hide logic
that matches the existing feedback form UI.
- Around line 166-172: The feedback form payload key is mismatched with the API
contract, causing api_feedback to miss the expected message field. Update the
submit logic in the feedback form handler so the FormData-derived body sends
message instead of description, or adjust api_feedback to accept description as
an alias; use the existing fetch('/api/feedback') submission path and the form
submit flow to locate the fix.

In `@public/terms.html`:
- Line 22: Add aria-hidden="true" to every purely decorative Font Awesome <i>
icon in public/terms.html, including the Contents marker and the other
section/contact icons referenced in the review. Update the affected markup in
the terms page so only meaningful text remains exposed to assistive tech, and
keep the same pattern consistently across all decorative icon tags in the file.

---

Outside diff comments:
In `@public/about.html`:
- Around line 45-56: The section titles in the decorative divider rows are using
styled spans instead of real headings, so update the “Our Journey” markup in the
about page to use an appropriate heading element and apply the same semantic fix
to the “What We Stand For” block. Keep the visual styling, but move it onto the
heading element inside the existing divider structure so the page preserves
heading navigation for assistive tech and matches the other semantic headings
already used in the template.
- Line 50: The decorative Font Awesome icons used throughout the about page
should be hidden from assistive technology. Update the repeated icon elements in
the timeline badges, value cards, and CTA buttons within the about template so
the existing icon markup includes aria-hidden="true", matching the pattern
already used for the hero icons. Use the repeated <i class="fas ..."> elements
in the about page as the targets for this accessibility fix.
- Around line 240-251: The CTA block in about.html is missing closing tags,
leaving the section and flex wrapper unbalanced. Update the markup around the
CTA area by closing the inner flex div and the enclosing section before the main
element ends, using the existing CTA section and anchor structure as the
reference points so the HTML remains well-formed.

In `@public/feedback.html`:
- Around line 133-141: The feedback textarea currently shows a static char count
and allows input beyond the intended limit. Update the feedback form markup in
the feedback textarea/char-count section so the `feedback-description` field
enforces a 5000-character `maxlength`, and wire the `char-count` element to the
`input` event so it updates live as the user types. Use the existing
`feedback-description` and `char-count` IDs to locate the elements and keep the
counter in sync with the textarea value.
- Around line 145-152: The submit button in the feedback form stays enabled
during the async request, which allows duplicate submissions. Update the
feedback submission flow in the code that drives the `submit-btn` and
`submit-label` elements so the button is disabled immediately before the `await
fetch(...)` call, then re-enabled in the completion/error path. Also change the
label to a submitting state while the request is in flight, and restore it
afterward.
🪄 Autofix (Beta)

Fix all unresolved CodeRabbit comments on this PR:

  • Push a commit to this branch (recommended)
  • Create a new PR with the fixes

ℹ️ Review info
⚙️ Run configuration

Configuration used: Repository: alphaonelabs/coderabbit/.coderabbit.yaml

Review profile: ASSERTIVE

Plan: Pro

Run ID: 9c95e551-cb34-4539-a591-0d623eb9f394

📥 Commits

Reviewing files that changed from the base of the PR and between 6b0be5a and a01a483.

📒 Files selected for processing (4)
  • public/about.html
  • public/feedback.html
  • public/terms.html
  • src/worker.py
💤 Files with no reviewable changes (1)
  • src/worker.py
🛑 Comments failed to post (3)
public/feedback.html (2)

159-177: 🩺 Stability & Availability | 🔴 Critical | ⚡ Quick win

Script references a non-existent element and never drives the success/error UI.

document.getElementById('feedback-status') (Line 163) targets an id that doesn't exist anywhere in this file — the markup instead defines #success-state, #error-banner/#error-message, and #char-count. Since status will be null, status.textContent = 'Submitting feedback...' (Line 165) throws immediately, aborting the handler before the fetch call even runs (or at best silently fails depending on strict mode). The success state (Lines 70-81) and error banner (Lines 92-96) built into the markup are never shown/hidden, so the "success state with reset flow" and inline error UX described in the PR are not actually functional.

🐛 Proposed fix wiring the real success/error elements
 <script>
-   document.getElementById('feedback-form').addEventListener('submit', async (event) => {
+   document.getElementById('feedback-form').addEventListener('submit', async (event) => {
       event.preventDefault();
       const form = event.currentTarget;
-      const status = document.getElementById('feedback-status');
+      const errorBanner = document.getElementById('error-banner');
+      const errorMessage = document.getElementById('error-message');
+      const successState = document.getElementById('success-state');
+      const submitBtn = document.getElementById('submit-btn');
       const token = localStorage.getItem('edu_token');
-      status.textContent = 'Submitting feedback...';
+      errorBanner.classList.add('hidden');
+      submitBtn.disabled = true;
       const body = Object.fromEntries(new FormData(form).entries());
       const headers = { 'Content-Type': 'application/json' };
       if (token) headers.Authorization = 'Bearer ' + token;
       try {
         const res = await fetch('/api/feedback', { method: 'POST', headers, body: JSON.stringify(body) });
         const data = await res.json();
         if (!res.ok) throw new Error(data.error || 'Could not submit feedback');
-        status.textContent = data.message || 'Thank you for the feedback.';
         form.reset();
-      } catch (err) { status.textContent = err.message; }
+        form.classList.add('hidden');
+        successState.classList.remove('hidden');
+      } catch (err) {
+        errorMessage.textContent = err.message;
+        errorBanner.classList.remove('hidden');
+      } finally {
+        submitBtn.disabled = false;
+      }
     });
   </script>
📝 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.

<script>
   document.getElementById('feedback-form').addEventListener('submit', async (event) => {
      event.preventDefault();
      const form = event.currentTarget;
      const errorBanner = document.getElementById('error-banner');
      const errorMessage = document.getElementById('error-message');
      const successState = document.getElementById('success-state');
      const submitBtn = document.getElementById('submit-btn');
      const token = localStorage.getItem('edu_token');
      errorBanner.classList.add('hidden');
      submitBtn.disabled = true;
      const body = Object.fromEntries(new FormData(form).entries());
      const headers = { 'Content-Type': 'application/json' };
      if (token) headers.Authorization = 'Bearer ' + token;
      try {
        const res = await fetch('/api/feedback', { method: 'POST', headers, body: JSON.stringify(body) });
        const data = await res.json();
        if (!res.ok) throw new Error(data.error || 'Could not submit feedback');
        form.reset();
        form.classList.add('hidden');
        successState.classList.remove('hidden');
      } catch (err) {
        errorMessage.textContent = err.message;
        errorBanner.classList.remove('hidden');
      } finally {
        submitBtn.disabled = false;
      }
    });
  </script>
🤖 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 `@public/feedback.html` around lines 159 - 177, The submit handler in
feedback.html is wired to a missing feedback-status element, so it fails before
the request and never toggles the built-in success/error UI. Update the
feedback-form listener to use the existing success-state, error-banner, and
error-message elements (and any other relevant UI hooks in this markup), guard
against null lookups, and drive those states explicitly on submit, success, and
failure. Keep the fetch flow in the same handler, but replace the current
status.textContent usage with show/hide logic that matches the existing feedback
form UI.

166-172: 🗄️ Data Integrity & Integration | 🟠 Major | ⚡ Quick win

🧩 Analysis chain

🏁 Script executed:

#!/bin/bash
# Confirm which /api/feedback branch is reachable first in worker.py
rg -n 'path == "/api/feedback"' -A2 src/worker.py

Repository: alphaonelabs/learn

Length of output: 416


🏁 Script executed:

#!/bin/bash
set -euo pipefail

# Inspect the router around both /api/feedback branches.
sed -n '6198,6315p' src/worker.py

Repository: alphaonelabs/learn

Length of output: 5583


🏁 Script executed:

#!/bin/bash
set -euo pipefail

# Inspect the feedback handlers and their expected payload keys.
rg -n 'async def api_(feedback|submit_feedback)\b|message|description' src/worker.py -A20 -B5

Repository: alphaonelabs/learn

Length of output: 50375


Feedback form sends the wrong payload key
/api/feedback is routed to api_feedback, which reads message; this form sends description, so submissions will fail with “Feedback message is required.” Send message here or have the handler accept description.

🤖 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 `@public/feedback.html` around lines 166 - 172, The feedback form payload key
is mismatched with the API contract, causing api_feedback to miss the expected
message field. Update the submit logic in the feedback form handler so the
FormData-derived body sends message instead of description, or adjust
api_feedback to accept description as an alias; use the existing
fetch('/api/feedback') submission path and the form submit flow to locate the
fix.
public/terms.html (1)

22-22: 📐 Maintainability & Code Quality | 🟠 Major | ⚡ Quick win

Decorative icons should be hidden from assistive tech.

Font Awesome icons used purely for visual decoration (list markers, section badges, contact icon) have no aria-hidden="true", so screen readers may announce meaningless icon glyphs/empty elements alongside the text. Add aria-hidden="true" to purely decorative <i> tags throughout the file.

♿ Example fix (repeat pattern for all decorative icons)
-<i class="fas fa-list text-teal-500"></i> Contents
+<i class="fas fa-list text-teal-500" aria-hidden="true"></i> Contents
-<i class="fas fa-lock text-white"></i>
+<i class="fas fa-lock text-white" aria-hidden="true"></i>

As per path instructions, "Review HTML templates for accessibility (ARIA attributes, semantic elements)."

Also applies to: 195-217, 224-226, 235-238, 248-262, 304-304, 310-310

🤖 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 `@public/terms.html` at line 22, Add aria-hidden="true" to every purely
decorative Font Awesome <i> icon in public/terms.html, including the Contents
marker and the other section/contact icons referenced in the review. Update the
affected markup in the terms page so only meaningful text remains exposed to
assistive tech, and keep the same pattern consistently across all decorative
icon tags in the file.

Source: Path instructions

@ghanshyam2005singh

Copy link
Copy Markdown
Contributor Author
Screencast.from.2026-07-06.21-52-46.mp4

@A1L13N Merge conflicts has been resolved, i have used the same UI as earlier but this time with your django syntax. PTAL!

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.

2 participants