One sign-in, every hub
the SSO contractIdentity lives in the token, not in PHP's session. Each app keeps
its own $_SESSION for its own state and never shares
PHPSESSID, so two hubs open in two tabs can't tread on each other.
Where it lives
The model and the site registry are in
TLCBase_2026/inc/sso_config.php. Every other hub carries a
drop-in copy of the kit at <hub>/sso/sso.php, configured
with nothing but its own site_key.
The three-part contract
Every site in the family has to agree on exactly three things: the cookie
name (tlc_sso), the token table and database
(sso_sessions in tlc_holiday), and the hash
(sha256 of the raw cookie value). Nothing else is shared.
Cookie scope by environment
*.tlcbase.org → .tlcbase.org;
*.tlcbase.test → .tlcbase.test for local subdomain
testing via the hosts file; plain localhost → host-only, so
path-based XAMPP development is single-site by definition.
The access-keys
one per siteThe site-key doubles as the RBAC key — it is matched against
role_pages.page. Adding a subdomain means adding a line to
sso_sites() and granting the key to a role in the admin role editor.
A key a role does not grant simply never appears in the launcher.
efolio, not eportfolio.enroll, with two Ls.Where the handovers happen
site to siteSix places where one hub genuinely depends on another — the joins worth knowing about before changing anything.
Knowledge Hub → Admin Hub
The evidence form on the Knowledge Hub is rendered from AdminHub's form definitions, and what a user submits lands in AdminHub's evidence in-tray. Two hubs, one form.
e-Portfolio → TLC Base
The assessor and admin halves of the e-Portfolio moved to TLC Base, so
efolio/index.php redirects those roles straight back out.
Learners, line managers, client admins and site admins stay.
Apprenticeships Portal → Induction Hub
The only crossing of the SSO boundary. Everything before it is anonymous and browser-held; everything after it has an account behind it.
Induction Hub → Enrolment Hub → e-Portfolio
Induction sets the learner up and produces the personal development plan; the Enrolment Hub takes the formal paperwork and the signature; the e-Portfolio is where that plan is then worked against, evidence by evidence.
Guides Hub → all of them
It documents four hubs and is gated by their keys, so its own contents shift depending on who is reading. Change a hub's navigation and its guide goes stale.
Every hub → TLC Base
The account dropdown's My profile and Admin links point back to
the master from wherever you are, and the launcher icon bar is drawn from the
shared sso_launcher table — edited in one place, on TLC Base
under Admin › Settings › Hub Launcher.
Two rules the whole estate follows
Two databases, four staff apps
TLC Base, Staffbase, AdminHub and the Knowledge Hub all use
tlcstaffnet and tlc_holiday — a single dump covers
all four, and a schema change has to be considered four times.
tlc_holiday is also the shared auth database that holds
sso_sessions. The e-Portfolio and Enrolment Hub stand apart:
the e-Portfolio has its own eportfolio database, and the
Enrolment Hub has no database of its own at all — which is why its section
tabs are a static list rather than a table.
No upload is ever linked directly
Every upload root is locked down by .htaccess and reached only
through a *_serve.php script that re-checks who is asking on
every single request — evidence_serve,
criteria_serve, course_material_serve,
ep_lms_serve, safeguarding_serve,
designrequest_serve, approval_serve,
proposal_serve. Uploaded files cannot be executed or fetched by
guessing a path.