Follow-up to #3551634 (3.x rewrite for Domain 3.x compatibility).
Background
The 2.x version of this module shipped a permission named domain administration theme (human-readable label "Use domain admin theme") used by the now-deleted ThemeSwitchNegotiator:
public function applies(RouteMatchInterface $route_match) {
if (!($domain = $this->negotiator->getActiveDomain())) {
return FALSE;
}
$this->defaultTheme = $this->adminTheme = $this->domainThemeLookup->getDefaultTheme($domain->id());
if ($this->currentUser->hasPermission('domain administration theme')) {
$this->adminTheme = $this->domainThemeLookup->getAdminTheme($domain->id());
}
return TRUE;
}
public function determineActiveTheme(RouteMatchInterface $route_match) {
return ($this->isAdminRouteUrl($route_match) === FALSE) ? $this->defaultTheme : $this->adminTheme;
}The permission gated the application of the per-domain ADMIN theme: only users holding it saw Claro/Gin/etc. on /admin/* paths; everyone else saw the per-domain front-end theme even on admin pages.
Why the permission is gone in 3.x (and is staying gone)
Drupal core has been discussing for a while the deprecation of the separate admin-theme system in favour of a single unified UI (Claro/Gin convergence, the broader Starshot conversations). Nothing is formally deprecated yet, but the signal is consistent enough that the 3.x rewrite chose to align with it: the custom ThemeSwitchNegotiator (and the gate permission with it) was scrapped, and per-domain themes are now applied via domain_config overrides on system.theme:default / system.theme:admin, picked up uniformly by Drupal core's existing theme resolution.
The 2.x gate could be reinstated as a thin ThemeNegotiatorInterface ordered above theme.negotiator.admin_theme: when the current user is on an admin route and lacks the permission, return the per-domain front-end theme; otherwise let core's admin negotiator pick the per-domain admin theme. Roughly 30-50 lines plus a resurrected permissions.yml. The reason not to do that here is the same direction-of-travel argument: re-investing in the admin/front-end theme split for the sake of a niche per-user gating feature is hard to justify when core may retire the split. If the gate turns out to matter for actual users, restoring it remains an easy follow-up issue against a future minor release; cleaning up the dead permission first does not foreclose that.
The permission was removed (along with its permissions.yml and the negotiator class) in commit f1168dd27fcab112cb6c68781c2c88d9b3697336 as part of #3551634.
Symptom
Sites updating from 2.x to 3.x have role configs that still reference the deleted permission. Drupal warns on each role save / config import:
Les autorisations inexistantes attribuées au rôle "..." ont été supprimées. Autorisation(s) invalide(s) : domain administration theme.
Drupal cleans the active config but the staged config in config/sync stays out of sync until each affected role is re-saved or hand-edited.
Proposed fix
Add domain_theme_switch_update_10002() that revokes the obsolete permission from any role that still has it. Idempotent: no-op on sites that never had the permission or whose roles have already been cleaned.
function domain_theme_switch_update_10002() {
$obsolete_permission = 'domain administration theme';
$cleaned_role_ids = [];
foreach (Role::loadMultiple() as $role_id => $role) {
if ($role->hasPermission($obsolete_permission)) {
$role->revokePermission($obsolete_permission);
$role->save();
$cleaned_role_ids[] = $role_id;
}
}
if (empty($cleaned_role_ids)) {
return t('No roles referenced the obsolete "@permission" permission; nothing to clean up.', [
'@permission' => $obsolete_permission,
]);
}
return t('Revoked the obsolete "@permission" permission from @count role(s): @roles.', [
'@permission' => $obsolete_permission,
'@count' => count($cleaned_role_ids),
'@roles' => implode(', ', $cleaned_role_ids),
]);
}This is the kind of cleanup that should have shipped alongside the permission removal in #3551634; filing now as a follow-up.
Issue fork domain_theme_switch-3589055
Show commands
Start within a Git clone of the project using the version control instructions.
Or, if you do not have SSH keys set up on git.drupalcode.org:
Comments
Comment #3
mably commentedComment #5
mably commented