octobercms/october · error · ApplicationException
Theme [$name] not found
Error message
Theme [$name] not found
What it means
UpdateManager::uninstallTheme() removes a theme via composer and then deletes its directory. It accepts either an October code or a directory name: if CmsTheme::exists($name) fails it retries after themeManager->findDirectoryName($name). If the theme still does not exist, it throws 'Theme [$name] not found' — nothing is installed under that identifier.
Source
Thrown at modules/system/classes/updatemanager/ManagesThemes.php:71
$composerVersion = $details['composer_version'] ?? '';
}
return [$composerCode, $composerVersion];
}
/**
* uninstallTheme attempts to remove the theme using composer before
* deleting from the filesystem
*/
public function uninstallTheme($name)
{
$themeExists = CmsTheme::exists($name);
if (!$themeExists) {
$name = (string) $this->themeManager->findDirectoryName($name);
}
if (!CmsTheme::exists($name)) {
throw new ApplicationException("Theme [$name] not found");
}
// Remove via composer
$composer = ComposerManager::instance();
$composerCode = $this->themeManager->getComposerCode($name);
if ($composerCode && $composer->hasPackage($composerCode)) {
$composer->remove([$composerCode]);
}
$this->themeManager->deleteTheme($name);
}
/**
* requestThemeDetails looks up a theme from the update server
*/
public function requestThemeDetails(string $name): array
{View on GitHub (pinned to b608633a7e)
Solutions
- List the actual directories under /themes and pass the exact one (lowercase, dots converted to dashes, e.g. author-theme)
- Guard with Cms\Classes\Theme::exists($name) before calling uninstallTheme
- If the directory is gone but the theme still appears in the backend, refresh/clear the cached theme list so the stale entry disappears
- For composer-installed themes whose folder is already gone, check composer.json and run composer remove for the package, then delete any leftover directory
Example fix
// before
UpdateManager::instance()->uninstallTheme($name);
// after
if (!\Cms\Classes\Theme::exists($name)) {
$name = strtolower(str_replace('.', '-', $name));
}
if (\Cms\Classes\Theme::exists($name)) {
UpdateManager::instance()->uninstallTheme($name);
} Defensive patterns
Strategy: validation
Validate before calling
if (!\Cms\Classes\Theme::exists($name)) {
$name = strtolower(str_replace('.', '-', $name));
}
if (\Cms\Classes\Theme::exists($name)) {
\UpdateManager::instance()->uninstallTheme($name);
} Try / catch
try { \UpdateManager::instance()->uninstallTheme($name); } catch (\ApplicationException $ex) { /* treat as already-removed or surface the message */ } Prevention
- Build uninstall UI from the live theme list (Theme::all()) so only existing themes are offered
- Pass the directory name (lowercase, dashes) rather than display names
- Avoid deleting theme directories by hand; let the manager keep state consistent
When it happens
Trigger: uninstallTheme('author.theme') when themes/author-theme/ does not exist; calling uninstall twice in a row; passing a display name instead of the code/directory name; the directory was already deleted by hand or by git.
Common situations: Theme folder removed manually while the backend still lists it (stale theme list/record); double-uninstall from the Updates UI; case mismatch between the stored name and the actual directory on a case-sensitive filesystem.
Understand the failure class
Background: 'Could not be found', 'does not exist', 'not found in database': the resource-not-found family when an ID, slug, key, or URI lookup comes back empty — this error's family across 20 libraries.
Related errors
- system::lang.zip.extract_failed
- Values not found for the selected row.
- cms::lang.layout.not_found_name
- cms::lang.cms_object.invalid_file
- cms::lang.cms_object.file_already_exists
AI-assisted analysis of octobercms/october@b608633a7e (2026-08-21).
Data as JSON: /api/errors/76cb09d0dd1ce12c.
Report an issue: GitHub.