Kareadita/Kavita · error · KavitaException

errors.theme-manual-upload

errors.theme-manual-upload

Error message

errors.theme-manual-upload

What it means

Thrown by SiteThemeService.CreateThemeFromFile when the uploaded theme's temp file does not exist on disk when processing starts (directoryService.FileSystem.File.Exists(tempFile) is false). The upload pipeline writes the form file to temp, then hands the path to CreateThemeFromFile; if that file is gone or never written, the upload cannot proceed. KavitaException('errors.theme-manual-upload') is thrown. ThemeController's upload-theme endpoint does not catch it, so it surfaces as HTTP 500 with the raw key 'errors.theme-manual-upload'.

Source

Thrown at Kavita.Services/SiteThemeService.cs:417

        var siteTheme = await unitOfWork.SiteThemeRepository.GetTheme(siteThemeId);
        if (siteTheme == null) return;

        await RemoveTheme(siteTheme);
    }

    /// <summary>
    /// This assumes a file is already in temp directory and will be used for
    /// </summary>
    /// <param name="tempFile"></param>
    /// <param name="username"></param>
    /// <param name="ct"></param>
    /// <returns></returns>
    public async Task<SiteTheme> CreateThemeFromFile(string tempFile, string username, CancellationToken ct = default)
    {
        if (!directoryService.FileSystem.File.Exists(tempFile))
        {
            logger.LogInformation("Unable to create theme from manual upload as file not in temp");
            throw new KavitaException("errors.theme-manual-upload");
        }


        var filename = directoryService.FileSystem.FileInfo.New(tempFile).Name;
        var themeName = Path.GetFileNameWithoutExtension(filename);

        if (await unitOfWork.SiteThemeRepository.GetThemeDtoByName(themeName) != null)
        {
            throw new KavitaException("errors.theme-already-in-use");
        }

        directoryService.CopyFileToDirectory(tempFile, directoryService.SiteThemeDirectory);
        var finalLocation = directoryService.FileSystem.Path.Join(directoryService.SiteThemeDirectory, filename);


        // Create a new entry and note that this is downloaded
        var theme = new SiteTheme()
        {

View on GitHub (pinned to 9c3e540000)

Solutions

  1. Verify the TempDirectory exists and the Kavita process has write permission and free space.
  2. Retry the upload; transient cleanup/contention races usually clear.
  3. Ensure TempDirectory is on persistent, writable storage and not cleared by an external job mid-upload.
Defensive patterns

Strategy: try-catch

Try / catch

try {
  await api.uploadTheme(file);
} catch (e) {
  // HTTP 500 raw key 'errors.theme-manual-upload': temp file missing/unwritable.
  notify('Upload failed (temp directory not writable or full). Free space and retry.');
}

Prevention

When it happens

Trigger: POST /api/theme/upload-theme where the temp file write failed, the file was removed by a concurrent temp cleanup before processing, the TempDirectory is not writable, or the disk is full.

Common situations: TempDirectory on a read-only/unmounted volume; disk full; aggressive nightly/temp cleanup racing with a slow upload; container with an ephemeral or permission-restricted temp dir.

Related errors


AI-assisted analysis of Kareadita/Kavita@9c3e540000 (2026-08-13). Data as JSON: /api/errors/e90f4b98bde93e7a. Report an issue: GitHub.