Skip to content

Birthdate field on profile (#167) + compact-print project link fix (#168)#169

Merged
vincentmakes merged 12 commits into
mainfrom
claude/zealous-wright-aJFjS
May 29, 2026
Merged

Birthdate field on profile (#167) + compact-print project link fix (#168)#169
vincentmakes merged 12 commits into
mainfrom
claude/zealous-wright-aJFjS

Conversation

@vincentmakes
Copy link
Copy Markdown
Owner

Closes #167. Closes #168.

Summary

Two issues bundled into one release (v1.50.0):

#167 — Add birthday to contactBadges (improvement)

  • New birthdate column on the profile table, added via automatic migration. Stored as ISO YYYY-MM-DD.
  • Profile modal gets a native <input type="date"> between Phone and the LinkedIn URL — labelled and hinted via the new form.birthdate / form.birthdate_hint i18n keys.
  • When set, the date renders as a contact badge in the admin view (with a cake Material icon) and as a Born: … line in the ATS PDF and static-site exports, formatted via Intl.DateTimeFormat in the active locale. So:
    • EN: Born: March 14, 1990
    • DE: Geb.: 14. März 1990
    • FR: Né(e) le : 14 mars 1990
  • When empty, nothing renders anywhere — no badge, no orphan span, no "Born: " line. This is the invariant the issue requested.
  • Treated as sensitive PII: stripped on the public read-only side in three places — publicApp.get('/api/profile'), serveDatasetData, and serveDatasetDataById, plus removed from the static-site export. The new helper stripPublicSensitiveProfile(data) is the single chokepoint.
  • form.birthdate, form.birthdate_hint, and contact.born keys added to all 8 locale files (en, de, fr, nl, es, it, pt, zh) — key parity test still passes.

#168 — Project link missing in compact print (bug)

Confirmed bug in public/shared/styles.css:2031-2034: when the Projects section had the "print compact" toggle on, .project-link was in the display:none !important list, so the link icon vanished in print — even though the same link was always rendered by the ATS PDF export and by the non-compact print view. Removed .project-link from the selector list; .drag-handle, .item-actions, and .tech-tags still hide as before (admin chrome / explicit compactness trade-off).

Test plan

  • All 281 backend + frontend tests pass (npm test).
  • Six new regression tests in tests/backend.test.jsBirthdate on profile:
    • PUT/GET round-trip of a valid ISO date.
    • 400 on invalid format.
    • Empty string clears a previously-set value.
    • Public /api/profile (port 3001) does NOT include birthdate even after the admin sets one.
    • ATS PDF byte length increases when a birthdate is added.
    • EN and DE ATS PDFs both with birthdate produce different byte lengths (localized prefix is wired through serverT).
  • Manual: npm run dev, edit profile, leave birthdate empty → no badge anywhere (admin view, print preview, ATS PDF, static-site export). Set a birthdate → appears localized on admin + ATS exports, still absent from public site at :3001.
  • Manual: enable "print compact" on the Projects section, open print preview — confirm the project link icon now appears next to each project title.

Version

MINOR bump 1.49.5 → 1.50.0 (new feature). All four files updated (package.json, package-lock.json top-level + packages[""], version.json, CHANGELOG.md).


Generated by Claude Code

claude added 12 commits May 27, 2026 14:07
…int (#168)

- Add `birthdate` column to `profile` via automatic migration; new
  `<input type="date">` in the admin profile modal. Renders as a
  localized contact badge in the admin view and as a "Born: …" line
  on the ATS PDF and static-site exports, formatted via
  Intl.DateTimeFormat in the active locale. When empty, nothing
  renders anywhere.
- Treat birthdate as sensitive PII: stripped from the public
  /api/profile endpoint and from the public dataset endpoints
  (serveDatasetData / serveDatasetDataById) so it never reaches
  the public read-only site even when a dataset is marked public.
- Add `form.birthdate`, `form.birthdate_hint`, `contact.born`
  translation keys to all 8 locale files.
- Bug fix: drop `.project-link` from the print-compact hide rule in
  styles.css so the link icon appears next to the project title in
  compact print mode (matching ATS export behavior).
- Regression tests in tests/backend.test.js: round-trip, validation,
  empty-clears-value, public endpoint never exposes birthdate, PDF
  byte-length differs when birthdate is present vs absent and
  across locales.
- Wrap the birthdate field in a form-row so it occupies one grid
  cell (1fr of 2) instead of stretching across the full modal,
  matching the email/phone visual width.
- Add explicit white background and a softened calendar-picker
  indicator on input[type="date"].form-input so the native
  browser styling no longer paints a grey fill that differed from
  the surrounding text inputs.
Fold the half-width / white-background tweak into the 1.50.0
changelog entry instead of cutting a separate 1.50.1 patch — the
UI polish is part of the same feature ship.
The native <input type="date"> renders through Chromium's
::-webkit-datetime-edit* shadow DOM with its own line metrics,
intrinsic min-width, and placeholder color — even with a heavy
CSS override the field looked taller, wider, and lighter than the
surrounding text inputs, and the fix was browser-specific.

Switch to type="text" with pattern="\d{4}-\d{2}-\d{2}",
maxlength=10, inputmode="numeric", autocomplete="bday", and a
"YYYY-MM-DD" placeholder. The field now inherits the exact same
.form-input styling as email/phone/etc. Server-side validation
already enforces the same regex so the round-trip is unchanged.
Reverts the type="text" workaround. Keep <input type="date"> so
the native calendar picker is still available, but normalize the
Chromium ::-webkit-datetime-edit* shadow-DOM tree so the field
visually matches the other .form-input text fields:

- appearance: none + min-width: 0 so the date input uses the box
  model from .form-input instead of its intrinsic dimensions.
- Pseudo-element color inherits from .form-input (no more light
  grey "yyyy-mm-dd" placeholder) and line-height/padding are
  zeroed so the box collapses to the same height as text inputs.
- .form-input now declares explicit color, background and
  line-height (which the date input pseudo-elements inherit).
- Calendar picker indicator dimmed to 0.55 opacity so the icon
  feels in-place rather than the visual centerpiece.
Without this override .project-link's default display:flex,
28×28 box, and grey button background made the link wrap to its
own line and dominate the row in compact print mode. The
print-compact rule now strips the box (display:inline, no
background, no margin) and shrinks the icon to 9px so the link
sits right after the project title as a small inline glyph.
- Force the icon to 10px with !important so it overrides the
  inline style="font-size:14px" emitted by materialIcon(), which
  was leaving the icon larger than the surrounding 11px text.
- Switch the anchor to inline-block + vertical-align: middle so
  the glyph centers on the text's vertical midline instead of
  sitting on the baseline.
- Margin 0 4px so the icon has equal breathing room on both
  sides of the em-dash that separates title from description.
PDF generators use the anchor box as the hyperlink hit region.
With width/height auto and no padding the box collapsed to the
10×10 glyph — a tiny click target in saved PDFs. Add invisible
2px/4px padding around the icon so the clickable region is wide
enough to hit reliably while the visible glyph stays the same
size. Reduce horizontal margin to 2px to compensate.
…urvives

Safari's "Save as PDF" + iOS Preview drop the hyperlink annotation
on anchors that lay out as display:inline or display:inline-block
with width:auto — the PDF generator attaches the annotation to
the anchor's box, and an effectively empty rectangle means the
link is unclickable in the resulting PDF.

Switch to display:inline-flex with explicit 14×14 dimensions and
align-items/justify-content centering. The icon stays the same
visible size but the anchor now has a concrete rectangle that
iOS Preview (and other PDF viewers) honour as a clickable region.
The icon-only approach kept dropping out as a non-clickable
glyph in some PDF viewers (notably iOS Preview) because the
hyperlink annotation attached to an effectively empty/oddly
positioned anchor box.

Hide the Material icon in compact print and emit the URL as
text via .project-link::after { content: attr(href) }. The
visible text is the anchor's content, so the PDF generator
attaches the link annotation to actual rendered glyphs — the
most reliably clickable form across PDF viewers. Style is
small/grey/inline so it doesn't dominate the title row.
@coderabbitai
Copy link
Copy Markdown

coderabbitai Bot commented May 27, 2026

Important

Review skipped

Auto reviews are disabled on base/target branches other than the default branch.

Please check the settings in the CodeRabbit UI or the .coderabbit.yaml file in this repository. To trigger a single review, invoke the @coderabbitai review command.

⚙️ Run configuration

Configuration used: defaults

Review profile: CHILL

Plan: Pro Plus

Run ID: cc685634-9dd2-4995-9a3c-f8d79d97337a

You can disable this status message by setting the reviews.review_status to false in the CodeRabbit configuration file.

Use the checkbox below for a quick retry:

  • 🔍 Trigger review
✨ Finishing Touches
🧪 Generate unit tests (beta)
  • Create PR with unit tests

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

@vincentmakes vincentmakes merged commit 87eee16 into main May 29, 2026
4 checks passed
@vincentmakes vincentmakes deleted the claude/zealous-wright-aJFjS branch May 29, 2026 13:00
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.

Bug: Selected Projects - Compact Print missing project-link Improvement: Add birthday to contactBadges

2 participants