Skip to content

added ability to redo completed challenges on practice mode and minor ux upgrades#80

Merged
aryan4859 merged 46 commits into
FlagForgeCTF:mainv2from
lynxx-st:mainv2
Jan 23, 2026
Merged

added ability to redo completed challenges on practice mode and minor ux upgrades#80
aryan4859 merged 46 commits into
FlagForgeCTF:mainv2from
lynxx-st:mainv2

Conversation

@lynxx-st

Copy link
Copy Markdown
Member

No description provided.

google-labs-jules Bot and others added 30 commits January 6, 2026 13:52
Adds a visible focus ring to the dismiss button on the authentication error message. This resolves a key accessibility issue where keyboard users had no visual indication that the button was focused, making it difficult to interact with.

This change uses standard Tailwind CSS `focus-visible` utility classes to apply a noticeable ring, improving the error recovery flow for keyboard-only and screen reader users without altering the experience for mouse users.
Refactors the `next-sitemap.config.js` to ensure the generated `robots.txt` file is maintainable and correctly synchronized with the sitemap's excluded paths.

Previously, the `robots.txt` generation was handled by an overly simplistic and brittle function that had diverged from the sitemap's `SITEMAP_EXCLUDE` list. This created a risk of search engines crawling and indexing private or low-value pages.

This change:
- Reinstates and improves the `transformRobotsTxt` function to programmatically generate `Disallow` rules directly from the `SITEMAP_EXCLUDE` constant.
- Preserves all original crawling directives, including a custom `Allow` rule for `/llms.txt` and multiple sitemap URLs.
- Removes the redundant and conflicting `policies` and `additionalSitemaps` configurations.

This ensures a single source of truth for path exclusion, improving SEO management and preventing unintended indexing.
…3306976789987

🧭 Streamline: Add visible focus state to auth error dismiss button
…77964526220410349

🔎 Index: Align robots.txt with sitemap exclusions
Fix GitHub link format for Sambat Lama
This commit enhances the user experience and accessibility of the "Privacy Policy" and "Terms & Conditions" links on the authentication page.

Key changes:
- Links now open in a new tab using `target="_blank"` and `rel="noopener noreferrer"`, preventing users from navigating away from the sign-in flow.
- An `ExternalLink` icon is added to visually indicate that the link will open a new tab.
- A screen-reader-only span, `(opens in new tab)`, is included to provide context for users with assistive technologies, ensuring the behavior is communicated clearly to all users.
…68822658620543

🎨 Palette: Improve External Link UX and Accessibility
💡 What: Added a hover state to the `DropdownMenuSubTrigger` component.
🎯 Why: To provide clear visual feedback when a user's cursor is over the element, making the interface feel more responsive.
♿ Accessibility: This change improves the user experience for mouse users by providing a clear visual indicator of the interactive element.
…date-770263327727417010

🎨 Palette: Add hover state to dropdown sub-trigger
…oggle button in the navbar for both desktop and mobile views. This micro-interaction makes the theme change feel more polished and improves the overall user experience.

Additionally, a missing `aria-label` was added to the mobile theme toggle button to improve accessibility for screen reader users.
💡 What: This change replaces `:focus` styles with `:focus-visible` styles for all interactive items in the `DropdownMenu` component. It ensures a visible ring and background color appear only during keyboard navigation.

🎯 Why: Previously, the dropdown items used `outline-none`, which completely removes the browser's default focus indicator. While there was a `focus:bg-accent` style, this appeared for both mouse and keyboard users, creating unnecessary visual noise for mouse users. This change ensures a clear, visible focus state is available *only* when it's needed most: for keyboard navigation.

📸 Before/After:
Before: No visible focus ring, and focus styles were applied on mouse click.
After: A clear focus ring and background color now appear only when tabbing through the menu items with a keyboard.

♿ Accessibility: This significantly improves keyboard accessibility by providing a clear, conventional focus indicator, making it much easier for users who rely on keyboard navigation to see which element is active.
Makes completed challenge cards interactive and provides clearer visual feedback.

Previously, completed challenge cards were disabled with `pointer-events-none` and linked to `#`. This created a dead end for users who wanted to review challenges they had already solved.

This change:
- Removes the disabling styles and ensures the card always links to the problem page.
- Adds a distinct 'Completed' badge with a checkmark icon to clearly indicate the solved state.
- Corrects a typo in the component filename (`QustionCards.tsx` -> `QuestionCards.tsx`).
**💡 What:**
This change improves the tooltips on the "Copy to Clipboard" buttons in the profile page's share modal.

- **Accessibility:** Tooltips now appear on keyboard focus (`focus-visible`) in addition to mouse hover, ensuring they are accessible to all users.
- **Animation:** Added a subtle scale and translate animation to make the tooltip's appearance smoother and more polished.

**🎯 Why:**
The original tooltips were only accessible via mouse hover, completely hiding them from keyboard-only users. This change ensures that critical information ("Copy" or "Copied!") is available to everyone. The animation adds a small touch of delight, making the interaction feel more responsive.

**♿ Accessibility:**
- The primary goal was to make the tooltips keyboard-accessible, which has been achieved using `group-focus-visible`. This directly addresses a WCAG guideline related to providing information to all users.
Groups the "Start Challenge" icon and text within a single anchor tag on the homepage.

Previously, only the text was clickable, which could be frustrating for users who clicked the icon. This change increases the clickable target area, making the interaction more intuitive and forgiving. It also ensures the hover effect is applied to the entire element, providing clearer visual feedback.
💡 What changed
- Added an `isIncorrect` state to the problem submission page.
- The flag input field now displays a red border if the submitted flag is incorrect.
- The red border is removed as soon as the user starts typing a new flag.

🎯 Why it improves the user flow
- Provides immediate and clear visual feedback at the point of interaction.
- Reduces confusion for users, as they no longer have to rely on a small toast notification.
- Improves the overall user experience by making the submission process more intuitive.

🧪 How verified
- Manual verification was attempted but blocked by an authentication issue.
- The code was reviewed and approved.

♿ Accessibility notes
- The change uses a color indicator, which may not be accessible to all users. However, the existing error message toast still appears, providing a non-visual cue.
Severity: HIGH

Vulnerability: A Cross-Site Scripting (XSS) vulnerability was identified in the blog post component. The markdown renderer (`react-markdown`) was configured to use `rehypeSanitize` *before* `rehypeHighlight`. The `rehypeHighlight` plugin generates new HTML elements for syntax highlighting. Because sanitization occurred before this HTML was generated, any potentially malicious content injected by the highlighting process would not be sanitized.

Impact: This could allow an attacker to inject malicious scripts into a blog post, which would then be executed in the browsers of users viewing the post. This could lead to session hijacking, data theft, or other client-side attacks.

Fix: The order of the `rehypePlugins` has been corrected. `rehypeHighlight` is now executed before `rehypeSanitize`. This ensures that all HTML, including the output from the syntax highlighting, is properly sanitized before being rendered to the DOM, effectively mitigating the XSS vulnerability.

Verification:
- The code change was manually inspected to confirm the correct plugin order.
- The build process was run to ensure no regressions were introduced.
- A code review confirmed the correctness and safety of the fix.
Adds an 'aria-label' to the mobile navigation menu trigger in the Navbar component.

This improves accessibility by providing a descriptive label for screen reader users, who would otherwise not know the purpose of this icon-only button.
On the challenges page, the pagination controls remained visible even when a search returned no results. This created a confusing state where the user could click "Next" and lose their search context.

This commit fixes the issue by adding a condition to the rendering logic, ensuring the pagination component is hidden whenever a search is active.
💡 What: Added `aria-label` attributes to the icon-only buttons used to open and close the floating chat component.

🎯 Why: The buttons previously had no accessible name, making them unusable for screen reader users. This change provides clear, descriptive labels, ensuring users of assistive technology can understand and operate the chat feature.

♿ Accessibility: This change directly addresses a critical accessibility issue (WCAG 4.1.2 Name, Role, Value) by providing an accessible name to interactive controls.
…0417270182262

🎨 Palette: Animate Theme Toggle Button
…21333015503523470

🎨 Palette: Improve Dropdown Menu Focus Visibility
…x-6956647589038678481

🧭 Streamline: Improve UX for completed challenge cards
…408821356876813

🎨 Palette: Enhance tooltip accessibility and animation
…link-14491264164863404033

🎨 Palette: Group Start Challenge link for better usability
…306442433977186956

🧭 Streamline: Add visual feedback for incorrect flag submissions
…28773277785210509

🛡️ Sentinel: [HIGH] Fix XSS Vulnerability in Markdown Rendering
…7250479971648022

🧭 Streamline: Hide Pagination on Empty Search Results
…18060874107169363572

🎨 Palette: Add ARIA labels to chat buttons
google-labs-jules Bot and others added 16 commits January 13, 2026 11:07
💡 What:
- Wrapped the entire "Latest Challenge" card on the homepage in a Next.js `<Link>` component.
- The link now correctly points to the specific challenge URL.
- Removed the redundant, inner "Start Challenge" link, which was semantically confusing.
- Used the `group-hover` utility to restore the hover effect on the challenge title.

🎯 Why:
- The previous implementation had a small, hard-to-click target within a larger card that visually suggested it was fully interactive.
- This change makes the entire card a large, easy-to-use click target, improving usability.
- It also corrects the link's destination from a generic page to the specific challenge being displayed, creating a more intuitive user flow.

♿ Accessibility:
- Replaces a non-semantic `div` with a proper `<a>` tag, improving the experience for screen reader users.
- Removes a confusing, non-interactive element that was styled to look like a link, eliminating a potential point of frustration.
This commit enhances application security by hardening the `Permissions-Policy` HTTP header.

The previous policy was permissive. The new, more restrictive policy follows the principle of least privilege by disabling a comprehensive list of browser features that are not essential for the application's functionality. This reduces the potential attack surface against vulnerabilities that might abuse these powerful browser APIs.
- Updated the `canSubmit` function in `app/(main)/problems/[id]/page.tsx` to return a detailed object with a reason for validation failure.
- Modified the `handleSubmit` function to display the validation reason to the user as a temporary message.
- Added specific, contextual reasons for all validation paths, such as "You have already solved this problem," "Please enter a flag," or "This flag was already submitted."

🎯 Why it improves the user flow
Previously, if a user tried to submit a flag under invalid conditions (e.g., empty input, duplicate submission), the "Submit" button would do nothing. This created a confusing "dead click" experience where the user did not know if the system was working or why their action was failing.

This change provides immediate, clear, and actionable feedback for all client-side validation failures. By explaining *why* a submission is blocked, it turns a moment of friction into a moment of guidance, improving user confidence and making the submission flow feel more responsive and intuitive.

🧪 How verified
- **Manual Code Review:** The logic was reviewed and refined multiple times to ensure all validation paths in `canSubmit` provide a descriptive reason.
- **Linting:** I attempted to run the linter, but it failed due to a project configuration issue (`Invalid project directory provided`). This appears to be a pre-existing problem.
- **Frontend Verification:** I attempted to visually verify the feedback message with an automated test. The test failed because the development server could not connect to the database (missing `MONGO_URL`), which prevented the page from rendering completely. The core logic change is self-contained and has been thoroughly reviewed.

♿ Accessibility notes
The feedback message is displayed in a `div` with `role="status"` and `aria-live="polite"`. This ensures that the message is announced by screen readers as it appears, making the validation feedback accessible to users of assistive technology.

📸 Before/After screenshots if visual
Unable to generate screenshots due to the environmental issue blocking the dev server from rendering pages that require a database connection.
💡 What:
Refactored the pagination buttons on the challenges page. Replaced the `disabled` attribute with `aria-disabled` and added a conditional `onClick` handler to prevent navigation when a button is disabled.

🎯 Why:
The original implementation with a `disabled` attribute made the buttons unfocusable for keyboard users, preventing them from understanding why the control was inactive. The `title` attribute is also not reliably announced by screen readers, creating an accessibility gap.

📸 Before/After:
A screenshot could not be generated due to a local environment issue (MongoDB connection failure) that prevented the application from rendering challenges.

♿ Accessibility:
This change significantly improves accessibility:
- **Keyboard Navigation:** `aria-disabled` buttons remain part of the tab order, allowing keyboard users to focus on them. The tooltip (`title`) provides context on focus.
- **Screen Readers:** Screen readers will now correctly announce the button's state (e.g., "dimmed" or "disabled"), providing crucial information to users of assistive technology.
…ck-to-flag-submission-11016555705368275048

🧭 Streamline: Add validation feedback to flag submission
…-12400877289618411199

🎨 Palette: Make Latest Challenge card a single clickable link
…cy-4274807873083356548

🛡️ Sentinel: Harden Permissions-Policy Header
…utton-1862575324298309620

🎨 Palette: Add ARIA Label to Mobile Menu Button
…31170746226396459

🎨 Palette: Improve Pagination Button Accessibility
@aryan4859 aryan4859 merged commit f25d826 into FlagForgeCTF:mainv2 Jan 23, 2026
4 checks passed
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

3 participants