Skip to content

perf(front): drop Carbon and Doctrine Inflector from uncached page renders - #2483

Merged
Seiger merged 3 commits into
evolution-cms:3.5.xfrom
elcreator:perf-fresh-install-render
Sep 28, 2026
Merged

Seiger merged 3 commits into
evolution-cms:3.5.xfrom
elcreator:perf-fresh-install-render

Conversation

@elcreator

@elcreator elcreator commented Sep 28, 2026 •

Copy link
Copy Markdown

Summary

A cache-miss render of a page on a fresh install loaded Carbon and Doctrine Inflector although the page needs
neither. This PR removes both from the front-end path and seeds the default template the way the manager creates
new ones.

  • upd(install) – the seeded Minimal Template now uses templatesource = 'db'. It was the only template in
    a fresh system on the legacy "Automatic (a matching file wins)" source; templates created in the manager already
    default to db. This is for consistency: the skipped view-file probes do not change render time measurably.
  • fix(models) – SiteContent::toArray() no longer builds a Carbon instance for deletedon. The base
    soft-delete trait casts that column to datetime, so every uncached page loaded Carbon (~40 files) and
    [*deletedon*] rendered as 1970-01-01T00:00:00.000000Z instead of a Unix timestamp like every other date field.
    The array form now keeps the stored value; reading $doc->deletedon still returns Carbon.
  • ref(models) – all 29 core models without $table now declare it. Without it, Eloquent pluralises the class
    name on the first query, which loads Doctrine Inflector (~20 files). Each name is exactly the one Eloquent derived
    before, so no query changes.

Measurements

Fresh SQLite install, PHP 8.3 with OPcache, Apache, guest request to the home page with the page cache off (200
requests per run):

PHP files loaded median
before 447 5.79–5.97 ms
after 381 5.21–5.45 ms

About 0.55 ms (~9%) per cache miss in the two quiet rounds; later rounds were too noisy to compare. Cached hits (~3
ms, 0 queries) are unaffected.

Behaviour change

toArray() / toJson() of a document now gives deletedon as an integer (0 when never deleted) instead of an
ISO string, matching createdon, editedon and the other date fields.

A subclass of a core model that does not set its own $table now inherits the parent's table instead of one
derived from the subclass name. Nothing shipped does this.

Tests

  • DefaultSiteTemplateSeederTest – both install seeders seed templatesource = 'db'; the CI smoke check asserts
    the same on a real install.
  • SiteContentDeletedOnArrayTest – integer deletedon in arrays, column order and other casts kept, attribute
    access still Carbon, an in-memory deletion time is arrayed as a timestamp, and (in a separate process) arraying a
    document does not load Carbon.
  • ModelTableNamesTest – every core model declares its table, and the 29 new declarations equal Eloquent's derived
    names.

Unit suite: 1097 passed, 2 skipped. PHPStan: 0 errors, as before.

elcreator and others added 3 commits September 28, 2026 22:35
A fresh install left the Minimal Template on the legacy "automatic"
source, the only template in the system showing that option, while every
template created in the manager starts as "database". Seed it as "db" so
it skips the view-file probes like any other database template.

Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
The base soft-delete trait casts deletedon to datetime, so toArray()
built a Carbon instance only to print it as an ISO string. Every uncached
page loaded Carbon (about 40 files) for it, and [*deletedon*] rendered as
1970-01-01T00:00:00.000000Z instead of a timestamp like every other date
field. Array form now keeps the stored value; reading the attribute still
returns Carbon.

Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
Models without $table made Eloquent pluralise the class name on the first
query of a request, which loads Doctrine Inflector (about 20 files) on
every uncached front-end page. Each name is the one Eloquent derived
before, so no query changes.

Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
@Seiger
Seiger merged commit 6d947cc into evolution-cms:3.5.x Sep 28, 2026
12 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.

2 participants