mirror of
https://codeberg.org/PostERG/xamxam.git
synced 2026-06-25 08:09:18 +02:00
10 KiB
10 KiB
TODO
Last updated: 2026-06-24 Context: Security audit — fix open redirects, fragment auth, dead code, CSRF gaps
Completed
- #sec-open-redirect Fix open redirect in tag.php + language.php (protocol-relative URL bypass via str_starts_with) ✓
- #build-pipeline Setup biome + rolldown + lightningcss build pipeline ✓
- #build-packagejson Create package.json with devDependencies ✓
- #build-biomecss Update biome.json to handle CSS formatting ✓
- #build-rolldown-config Create rolldown.config.mjs + build-js.mjs for JS bundling ✓
- #build-lightningcss Add lightningcss CSS bundling (resolve @import chain) ✓
- #build-justfile Add just build/deploy recipes + integrate build into deploy ✓
- #build-head Update head.php + form-page.php + controllers to use bundled assets ✓
- #build-gitignore Add dist/ to .gitignore ✓
- #build-cssfix Fix stray
}syntax error in admin.css line 305 ✓
Pending
- #sec-fragments-auth Gate partagé fragments on share_active session + CSRF
(partage/fragments/*.php, partage/index.php) - #sec-retry-csrf Add CSRF check to partage/retry-email.php POST
- #sec-cleanup-dead-code Remove dead App::verifyCsrf() or refactor action handlers to use it
- #rep-student-touch Replace hover student popover with tap-to-open drawer for mobile
(repertoire.php, repertoire.css) - #rep-polish Polish: scroll-position memory on HTMX swap, animation tuning
(repertoire.css) - #icon-color-verify Verify icon colors render correctly across all pages (header, admin tables, forms, dialogs, cleanup modal)
Completed (before this session)
- #gzip-nginx Enable gzip compression in nginx config
(nginx/xamxam.conf)✓ - #extract-inline-js Move inline JS to external files across 17 templates → 15 new JS files created
(app/public/assets/js/app/*.js)✓ - #inline-icon-helper Create
icon()PHP helper + auto-load in bootstrap(src/icon.php, bootstrap.php)✓ - #icon-fill-currentcolor Ensure all 36 icon SVGs use fill="currentColor" or stroke="currentColor"
(assets/icons/*.svg)✓ - #migrate-all-img-icons Replace all remaining
<img src="/assets/icons/">with<?= icon() ?>across 26 template files ✓ - #icon-css-cleanup Remove
<img>filter hacks from admin.css, add explicit sizes for header nav + public search icons(admin.css, search.css)✓ - #icon-em-sizing Set icon helper to output width="1em" height="1em" so icons scale with parent font-size
(icon.php)✓ - #inline-svg-to-icons Move all inline SVGs to asset icon files, ensure currentColor fill for proper color inheritance
(33 icons, 22 files, 67+ inline SVGs replaced, 2 dynamic SVGs remain)✓ - #cleanup-modal-fixes Fix nettoyage modal: SVG caret icons, margin→padding, BBBDMSans summary
(admin.css, details.css)✓ - #structure-formulaire-page Move "Structure du Formulaire" from contenus.php to its own dedicated page with back button
(structure-formulaire.php [new], contenus.php)✓ - #contenus-indexes Add index on thesis_languages(language_id) + tags(deleted_at, name); fix count queries to exclude soft-deleted theses
(Database.php, DatabaseMigrations.php, schema.sql, migrations/applied/041_thesis_languages_index.sql)✓ - #peertube-orphans-check Add Peertube orphan video check + relink in admin — listChannelVideos (PeerTubeService), peertube-orphans.php endpoint, UI in nettoyage dialog, relink support on edit page
(peertube-relink.php, peertube-browser.php, fichiers-fragment.php, file-upload-filepond.js)✓ - #tfe-optional-formats Make TFE file optional when format is Site web (1), Performance (4) or Installation (6) — fixed incorrect format IDs [3→1,4,6] + added client-side JS toggle for TFE required/asterisk. Note d'intention remains required. 🎯
(fichiers-fragment.php, file-upload-filepond.js)✓ - #typography-weight-300 Set search placeholder + apropos/charte/licence
content to BBBDMSans weight 300
(search.css, apropos.css)✓ - #toc-parts-uppercase Hardcode "PARTIES" uppercase + black bottom border on TOC label
(about.php, charte.php, licence.php, apropos.css)✓ - #apropos-overflow Prevent #apropos-intro and content-section children from overflowing
(apropos.css)✓ - #toc-navigation Fix TOC links not navigating to headings — added
apply_id_to_heading: trueto CommonMark config so IDs land on headings not hidden elements; added scroll-margin-top to headings; unstuck main from flex container so sticky TOC works for full page height(CharteController.php, LicenceController.php, apropos.css)✓ - #apropos-toc-style Fix TOC "Parties" label: Ductus font + lowercase, remove border-left from links, match global link style; rename .apropos-content → section.content, .apropos-section → .content-section, remove .prose wrapper
(apropos.css, about.php, charte.php, licence.php)✓ - #apropos-toc-confirm Fixed sticky TOC: removed
flex: 1; min-height: 0on main for apropos-body so the sticky container is full content height; addedmax-height+overflow-y: autoto TOC for long lists(apropos.css)✓ - #fix-finality-types Create standalone script + just command to rename finality types (Approfondi→Approfondie, Enseignement→Didactique, Spécialisé→Spécialisée)
(scripts/fix-finality-types.php, justfile)✓ - #context-note-synopsis Display contextual note above synopsis (italic) instead of in meta column on TFE page
(tfe.php, tfe.css)✓ - #decouple-contacts Decouple contact_visible (public) & contact_interne (private email): backend already decoupled; made contact_public checkbox functional in admin add/edit forms; contact_public now controls TFE page visibility
(FormBootstrap.php, ThesisCreateController.php, ThesisEditController.php, tfe.php, form.php)✓ - #csrf-rotation-race Stop CSRF token rotation in draft.php + remove hx-post from — both broke FilePond uploads and form submission
(admin/actions/draft.php, partage/fragments/draft.php, FormBootstrap.php, pill-search.js)✓ - #adminold-return-type Fix adminOld closure return type from
:stringto:string|array(FormBootstrap.php)✓ - #duration-integer-units Make duration field: integer for pages/Mo, dedicated h/m/s time inputs
(form.php, ThesisCreateController.php, tfe.php, form-base.css)✓ - #licence-svg-fix Fix licence details/summary SVG: width 1rem, inline-flex layout
(fieldset-licence-explanation.php, form-base.css)✓ - #restore-languages Un-soft-delete anglais (id=2) and néerlandais (id=71) in dev DB ✓
- #php-upload-limits Increase PHP upload_max_filesize to 8G, post_max_size to 8.5G
(.user.ini)✓ - #formdata-fieldset-crash Remove leftover debug console.log that called new FormData(fieldset)
(admin/footer.php)✓ - #csp-media-iframe-fix Fix CSP
frame-ancestors 'none'blocking PDF iframes — replacedtry_filesredirect with directfastcgi_passinlocation = /mediasoadd_headerCSP override survives internal nginx redirect(nginx/xamxam.conf)✓ - #duration-migration Add migration to reintroduce
duration_valueandduration_unitcolumns + update views(migrations/applied/040_duration_fields.sql)✓ - #duration-database Update
createThesis,updateThesis,getThesisRawFieldsin Database(Database.php)✓ - #duration-controllers Handle duration in
ThesisCreateControllerandThesisEditController(ThesisCreateController.php, ThesisEditController.php)✓ - #duration-form Add duration fieldset (value + unit dropdown) to form template
(templates/partials/form/form.php)✓ - #duration-display Show duration on public TFE detail page
(templates/public/tfe.php)✓ - #duration-view Include duration in v_theses_full and v_theses_public
(migrations/applied/040_duration_fields.sql, schema.sql, schema.sql.new)✓ - #duration-bootstrapWire Wire duration variables through FormBootstrap adminFormVariables
(FormBootstrap.php)✓ - #cleanup-drafts Add periodic cleanup job for orphaned drafts (
Database.php,justfile,deploy/xamxam-cleanup.cron,scripts/cleanup-drafts.php) ✓ - #form-setup-helper Add
FormBootstraphelper class to reduce bootstrap duplication across add/edit/partage(admin/add.php)(admin/edit.php)✓ - #two-phase-commit Add two-phase commit: INSERT thesis
status='draft', COMMIT, move files, UPDATE toactive(ThesisCreateController.php)✓ - #filepond-preserve Preserve FilePond temp file IDs on partage validation redirect
(partage/index.php)(FilepondHandler.php)✓ - #refactor-partage Extract partage form page chrome to
templates/partage/form-page.php(partage/index.php)✓ - #htmx-migration HTMX v2 migration: OverType editors, autosave handler, backend
HX-Requestdetection ✓ - #filepond-crash FilePond crash on TFE upload forms: root cause fixed (
.filename→.name), all crashes resolved ✓ - #aria-errormessage WCAG AA: field-level
aria-errormessage,aria-invalid,aria-describedbyon all form fields ✓ - #nojs-upload-fix No-JS file uploads:
filepond_modedefault to0 disabled, server-side$_FILESfallback ✓ - #autosave-partage Autosave text fields on partage form: session draft endpoint (
fragments/draft.php), HTMX autosave on change/input, page-load hydration, "Brouillon enregistré" indicator, draft cleared on submit ✓ - #autosave-partage-wire Wire
formExtraAttrs,showAutosaveStatus, draft hydration,autosave-handler.js, draft cleanup into partage form (partage/index.php,partage/form-page.php) ✓ - #mobile-responsive Mobile-responsive form layout:
@media (max-width: 600px)breakpoint, 44×44px touch targets ✓ - #aria-fieldset-fix Remove invalid
requiredattribute from<fieldset>, keeparia-required="true", addrole="group"✓ - #split-form-css Split
form.cssintoform-base.cssandform-admin.css✓ - #extra-css-admin Update
head.phpto support$extraCssAdminfor admin-only stylesheets(head.php)✓
Deferred / Blocked
- #tighten-csp Tighten CSP to remove 'unsafe-inline' after inline JS extraction