Commit Graph

94 Commits

Author SHA1 Message Date
Melvin Ragusa
f3866fc2de Merge pull request #37 from ragusa-it/fix/gradient-blinds-mobile-scroll-5721743487777744153
Fix GradientBlinds scroll drift on mobile
2026-01-30 01:16:59 +01:00
google-labs-jules[bot]
c0d541d31b Fix GradientBlinds scroll drift on mobile and address dampening regression
- Added isMobile detection (<= 768px) in GradientBlinds.tsx
- Updated onPointerMove to calculate container-relative coordinates immediately on mobile
- Updated animation loop to skip scroll-based target updates on mobile
- Fixed regression where disabling mouse dampening on mobile would freeze the spotlight
- Prevents spotlight from drifting across the background during scroll inertia on mobile devices

Co-authored-by: ragusa-it <196988693+ragusa-it@users.noreply.github.com>
2026-01-29 22:30:40 +00:00
google-labs-jules[bot]
7bc42f8d48 Fix GradientBlinds scroll drift on mobile
- Added isMobile detection (<= 768px) in GradientBlinds.tsx
- Updated onPointerMove to calculate container-relative coordinates immediately on mobile
- Updated animation loop to skip scroll-based target updates on mobile
- Prevents spotlight from drifting across the background during scroll inertia on mobile devices

Co-authored-by: ragusa-it <196988693+ragusa-it@users.noreply.github.com>
2026-01-29 22:09:19 +00:00
Melvin Ragusa
0ba794a1d3 chore: remove leftover jules verification artifact 2026-01-29 04:33:03 +00:00
Melvin Ragusa
4aca67efbb Merge pull request #23 from ragusa-it/bolt/route-lazy-loading-17202030222576625568
 Bolt: Implement route lazy loading
2026-01-29 05:21:06 +01:00
Melvin Ragusa
220b03ad97 Merge branch 'main' into bolt/route-lazy-loading-17202030222576625568 2026-01-29 05:20:57 +01:00
Melvin Ragusa
e35b4de514 Merge pull request #33 from ragusa-it/palette-contact-a11y-2847648259567731202
🎨 Palette: Improve Contact form accessibility
2026-01-29 05:20:30 +01:00
Melvin Ragusa
5745e07da2 Merge branch 'main' into palette-contact-a11y-2847648259567731202 2026-01-29 05:19:59 +01:00
Melvin Ragusa
f91f487fda Merge pull request #34 from ragusa-it/sentinel-input-limits-8405607204449411064
🛡️ Sentinel: [Medium] Add input length limits to Contact form
2026-01-29 05:19:01 +01:00
Melvin Ragusa
a9bf3cecbe Merge pull request #29 from ragusa-it/sentinel-add-headers-1105893154342715755
🛡️ Sentinel: [HIGH] Add HSTS and Permissions-Policy headers
2026-01-29 05:18:46 +01:00
Melvin Ragusa
68727e8b39 Merge pull request #31 from ragusa-it/palette/required-fields-a11y-7470820225000300564
🎨 Palette: Add accessible required field indicators
2026-01-29 05:17:56 +01:00
Melvin Ragusa
7277b9377e Merge pull request #30 from ragusa-it/bolt/optimize-hero-rerenders-1995284140926395636
 Bolt: Optimize Hero re-renders
2026-01-29 05:16:34 +01:00
Melvin Ragusa
71e66d347e Merge pull request #32 from ragusa-it/bolt-perf-gradient-blinds-9776062727377295977
 Bolt: Optimize GradientBlinds pointer handling
2026-01-29 05:15:57 +01:00
google-labs-jules[bot]
e84a3313c7 feat(security): enforce input length limits in contact form
- Added `EMAIL_MAX_LENGTH` constant (254).
- Added `maxLength` attributes to Name, Email, Subject, and Message inputs.
- Updated `validateForm` to check email length.
- Mitigates client-side DoS and improves UX.

Co-authored-by: ragusa-it <196988693+ragusa-it@users.noreply.github.com>
2026-01-29 02:00:58 +00:00
google-labs-jules[bot]
2c9cb547e7 🎨 Palette: Improve Contact form accessibility
💡 What: Added ARIA roles to form status messages and hid decorative icons.
🎯 Why: Screen readers were missing dynamic success/error messages on form submission.
 Accessibility:
- Added `role="alert"` and `aria-live="polite"` to success, error, and rate-limit messages.
- Added `aria-hidden="true"` to decorative icons in the contact info section.

Co-authored-by: ragusa-it <196988693+ragusa-it@users.noreply.github.com>
2026-01-29 01:48:58 +00:00
google-labs-jules[bot]
bac867f228 perf(GradientBlinds): decouple pointer events from render loop
- Move scroll position and bounding client rect calculations from `pointermove` handler to `requestAnimationFrame` loop.
- Use `pointerPosRef` to store raw event coordinates, reducing overhead in high-frequency event handlers.
- Ensure spotlight effect correctly accounts for scroll position updates during animation frames.
- Add regression test to verify `scrollX` is not accessed during pointer events.

Co-authored-by: ragusa-it <196988693+ragusa-it@users.noreply.github.com>
2026-01-29 01:40:38 +00:00
google-labs-jules[bot]
e14ce38f61 feat: add accessible required field indicators and alerts
- Add visual asterisk for required inputs in Input.tsx
- Add .required style in Input.module.css
- Update Contact form to use required props and noValidate
- Add role="alert" to Contact form success/error messages
- Add tests for required field rendering

Co-authored-by: ragusa-it <196988693+ragusa-it@users.noreply.github.com>
2026-01-28 02:10:17 +00:00
google-labs-jules[bot]
669e96a77c feat: optimize Hero component by isolating typing effect state
Extracted the high-frequency typing animation logic into a new, memoized `TypedText` component.
This prevents the entire `Hero` component (including the heavy `GradientBlinds`) from re-rendering on every character update.

- Created `TypedText` component in `Hero.tsx`
- Wrapped `TypedText` in `React.memo`
- Moved `useTypingEffect` call into `TypedText`
- Updated `Hero` to use `TypedText`

Co-authored-by: ragusa-it <196988693+ragusa-it@users.noreply.github.com>
2026-01-28 01:58:55 +00:00
google-labs-jules[bot]
1afa2f3cd8 🛡️ Sentinel: [HIGH] Add HSTS and Permissions-Policy headers
Added Strict-Transport-Security (HSTS) and Permissions-Policy headers to firebase.json to improve security posture.

- HSTS ensures browsers only connect via HTTPS for 1 year.
- Permissions-Policy restricts usage of sensitive features (camera, mic, geolocation).

Co-authored-by: ragusa-it <196988693+ragusa-it@users.noreply.github.com>
2026-01-28 01:56:37 +00:00
Melvin Ragusa
6b8f54072e Merge pull request #28 from ragusa-it/sentinel/strict-email-validation-13033948493013017418
🛡️ Sentinel: [HIGH] Strict Email Validation to Prevent XSS
2026-01-27 05:11:54 +01:00
Melvin Ragusa
f79cc5f51b Merge pull request #27 from ragusa-it/palette/improve-button-loading-a11y-7318493501161328143
🎨 Palette: Improve Button loading state accessibility
2026-01-27 05:11:31 +01:00
google-labs-jules[bot]
57f7c5667f 🛡️ Sentinel: [HIGH] Implement strict email validation
- Implemented `isValidEmail` utility with strict regex validation (rejects `<` and `>`) to prevent XSS vectors.
- Updated `Contact.tsx` to use `isValidEmail` instead of weak regex.
- Added comprehensive tests for `isValidEmail` in `src/utils/security.test.ts`.
- Fixed flaky test in `src/pages/__tests__/Contact.test.tsx` by clearing `localStorage` in `afterEach`.
- Added test case for invalid email submission.
- Documented findings in `.jules/sentinel.md`.

Co-authored-by: ragusa-it <196988693+ragusa-it@users.noreply.github.com>
2026-01-27 01:56:08 +00:00
google-labs-jules[bot]
6d94ac7b93 🎨 Palette: Improve Button loading state accessibility
- Add `aria-busy` attribute to Button when loading.
- Refactor Button rendering to keep children in DOM (visually hidden) instead of unmounting.
- Fix layout shift regression by replicating flex properties in content wrapper.
- Move inline styles to CSS modules.
- Add tests for loading state accessibility.

Co-authored-by: ragusa-it <196988693+ragusa-it@users.noreply.github.com>
2026-01-27 01:42:19 +00:00
Melvin Ragusa
9223331ee9 Merge pull request #25 from ragusa-it/sentinel/add-rate-limiting-6220090788029597128
🛡️ Sentinel: [Enhancement] Add rate limiting to contact form
2026-01-26 08:55:45 +01:00
google-labs-jules[bot]
839e1bf82f feat: add client-side rate limiting to contact form
- Added `useRateLimit` hook
- Integrated hook into `Contact.tsx`
- Added translations for rate limit error
- Added unit tests
- Fixed type error in `Button.tsx` to allow build to pass
2026-01-26 01:49:05 +00:00
google-labs-jules[bot]
0fe47a3790 feat(perf): implement route lazy loading for About and Contact pages
- Splits About and Contact pages into separate chunks using React.lazy and Suspense.
- Keeps Home page eager loaded to prevent layout shifts.
- Adds PageLoader component as a fallback for Suspense.
- Reduces initial bundle size by loading secondary pages only when needed.
2026-01-26 01:41:35 +00:00
Melvin Ragusa
13df58342a Merge pull request #22 from ragusa-it/bolt-optimize-fancycursor-3615259032599906398
 Bolt: Optimize FancyCursor mousemove handler
2026-01-25 15:16:27 +01:00
Melvin Ragusa
ca9e365780 Merge pull request #21 from ragusa-it/palette/button-a11y-fix-1082057340107931289
Palette: Enable accessibility attributes on Button component
2026-01-25 15:16:08 +01:00
Melvin Ragusa
2503e71dc5 Merge pull request #20 from ragusa-it/sentinel-security-headers-5394727340569705425
🛡️ Sentinel: Add Security Headers to Firebase Config
2026-01-25 15:15:39 +01:00
google-labs-jules[bot]
7c0a0bbec2 perf(FancyCursor): optimize mousemove handler with ticking pattern
- Replaces the `cancelAnimationFrame` pattern with a boolean ticking flag to reduce function allocation and RAF overhead on high-frequency mousemove events.
- Uses closure variables for coordinates to ensure the latest position is used in the animation frame.
- Improves performance of the custom cursor on high-refresh-rate input devices.
2026-01-25 01:37:50 +00:00
google-labs-jules[bot]
2eb8c57a50 Palette: Enable accessibility attributes on Button component
Refactored the `Button` component to accept and spread standard HTML button attributes.
This allows developers to add `aria-label`, `aria-expanded`, and other accessibility properties,
which were previously ignored.

Added unit tests to verify that attributes are correctly passed to the DOM element.
2026-01-25 01:36:53 +00:00
google-labs-jules[bot]
5f7f422167 🛡️ Sentinel: [HIGH] Add security headers to firebase.json
Added strict security headers to `firebase.json` for Firebase Hosting.
Headers included:
- X-Content-Type-Options: nosniff
- X-Frame-Options: DENY
- Referrer-Policy: strict-origin-when-cross-origin
- Content-Security-Policy: Includes directives for 'self', Google Fonts, EmailJS, and disallows object/frame embedding.

Also initialized `.jules/sentinel.md` with the first security learning.
2026-01-25 01:35:53 +00:00
Melvin Ragusa
949d5ab8b9 style: Adjust navbar backdrop blur intensity and background color opacity. 2026-01-24 14:00:11 +01:00
Melvin Ragusa
821e27ff0e style: increase Navbar background opacity for improved visibility. 2026-01-24 13:56:33 +01:00
Melvin Ragusa
de14bfdf5d style: Add -webkit-backdrop-filter for blur effects and refine mobile navigation background colors. 2026-01-24 13:54:03 +01:00
Melvin Ragusa
cefa3ef7aa feat: implement Navbar styling with responsive design and add localStorage mock to Navbar tests. 2026-01-24 13:50:39 +01:00
Melvin Ragusa
b80db420c2 jules: merged .jules and .Jules directories 2026-01-24 11:50:38 +01:00
Melvin Ragusa
89b24e1256 Merge pull request #17 from ragusa-it/sentinel-contact-form-security-13396691456148792037
🛡️ Sentinel: Add input sanitization and validation to Contact form
2026-01-24 11:48:36 +01:00
Melvin Ragusa
6b17b8b007 perf: optimized gradientblinds 2026-01-24 11:45:39 +01:00
Melvin Ragusa
e6df2d25be Merge pull request #19 from ragusa-it/palette-input-a11y-improvement-8429205258158315670
🎨 Palette: Improve Input accessibility with ARIA attributes
2026-01-24 11:20:57 +01:00
Melvin Ragusa
68262de83c Merge pull request #18 from ragusa-it/perf/navbar-debounce-resize-859095585893287738
 Optimize Navbar resize handler with debounce
2026-01-24 11:20:04 +01:00
Melvin Ragusa
8a80915982 Merge pull request #15 from ragusa-it/perf-gradient-blinds-reflow-11693170314543928560
 Optimize GradientBlinds pointer move handler
2026-01-24 11:18:57 +01:00
google-labs-jules[bot]
ffe37fad37 feat: Improve Input accessibility with ARIA attributes
Add `aria-invalid` and `aria-describedby` attributes to Input and Textarea components when an error is present.
This ensures screen readers announce the validation error when the input is focused.
Also added unit tests for these accessibility attributes.
2026-01-24 10:08:34 +00:00
google-labs-jules[bot]
1f21b7bcb9 Optimize Navbar resize handler with debounce
*   💡 **What:** Implemented a generic `debounce` utility and applied it to the `Navbar` component's window resize event listener (150ms delay). Added a `.cancel()` method to the debounce utility to prevent memory leaks/errors on unmount.
*   🎯 **Why:** The `resize` event fires rapidly, causing `getBoundingClientRect` (a layout-thrashing operation) to run excessively, impacting performance.
*   📊 **Measured Improvement:** In a benchmark test simulating 100 rapid resize events:
    *   **Baseline:** 200 calls to `getBoundingClientRect`.
    *   **Optimized:** 2 calls to `getBoundingClientRect`.
    *   **Result:** ~99% reduction in layout calculations during rapid resizing.
    *   Added `src/components/layout/Navbar.perf.test.tsx` to prevent regression.
2026-01-24 10:07:28 +00:00
google-labs-jules[bot]
6801682c2e Shield: Add input sanitization and length validation to Contact form
Added `sanitizeInput` utility to escape HTML characters.
Updated `Contact.tsx` to sanitize inputs before sending via `emailjs`.
Added max length validation for Name (100), Subject (200), and Message (5000).
Updated tests to cover sanitization and validation logic, including adding `cleanup()` to prevent test leakage.
2026-01-24 10:05:33 +00:00
google-labs-jules[bot]
5d29f05248 perf: Optimize GradientBlinds pointer move handler
- Removed synchronous `getBoundingClientRect` call from `pointermove` handler
- Implemented caching of canvas dimensions and scroll position using `ResizeObserver`
- Added logic to compensate for scroll delta in pointer position calculation
- Added regression test to verify `getBoundingClientRect` is not called during pointer interaction
- Fixed `ogl` mock in tests to include `Geometry`
2026-01-24 10:02:30 +00:00
Melvin Ragusa
77fd62447c fix: updated contact information in imprint & /contact page 2026-01-24 10:47:40 +01:00
Melvin Ragusa
516f29f312 Merge pull request #14 from ragusa-it/fix-emailjs-config-10566427372995944214
fix(emailjs): send emails sequentially and add reply_to
2026-01-24 10:33:47 +01:00
Melvin Ragusa
690e8647bc Merge branch 'main' into fix-emailjs-config-10566427372995944214 2026-01-24 10:33:37 +01:00
google-labs-jules[bot]
043a1b2b1e fix(emailjs): send emails sequentially and add reply_to 2026-01-24 09:30:22 +00:00