iOfficeAI/OfficeCLI · error · CliException

plugin_create_failed

plugin_create_failed

Error message

Format-handler plugin '{plugin.Manifest.Name}' timed out creating {path} (60s).

What it means

Thrown when a format-handler plugin process started by TryCreateViaPlugin does not exit within the 60-second WaitForExit timeout. The process is killed (proc.Kill(true)) and a CliException with code `plugin_create_failed` is raised. It guards against a hung plugin blocking the `create` command indefinitely.

Source

Thrown at src/officecli/BlankDocCreator.cs:71

            RedirectStandardError = true,
            // CONSISTENCY(child-stream-encoding): pin UTF-8 on every redirected
            // child stream. Unset, .NET decodes with the console's code page,
            // which is the host's default (CP936/CP437) — officecli no longer
            // switches the console to 65001 for redirected runs, so a plugin's
            // non-ASCII diagnostics would decode wrong.
            StandardErrorEncoding = System.Text.Encoding.UTF8,
            CreateNoWindow = true,
        };
        using var proc = System.Diagnostics.Process.Start(psi);
        if (proc is null) return false;
        // Bound the wait: a hung plugin previously blocked `create` forever
        // (stderr is the only redirected stream, so the read itself cannot
        // deadlock, but WaitForExit had no timeout or Kill).
        var stderrTask = proc.StandardError.ReadToEndAsync();
        if (!proc.WaitForExit(60_000))
        {
            try { proc.Kill(true); } catch { }
            throw new OfficeCli.Core.CliException(
                $"Format-handler plugin '{plugin.Manifest.Name}' timed out creating {path} (60s).")
            { Code = "plugin_create_failed" };
        }
        var stderr = stderrTask.Result;
        if (proc.ExitCode != 0)
        {
            // Treat unknown-subcommand exit-64 as "plugin doesn't implement
            // create" — fall back to NotSupportedException so the user sees
            // the same error they'd see without any plugin installed.
            if (proc.ExitCode == 64) return false;
            throw new OfficeCli.Core.CliException(
                $"Format-handler plugin '{plugin.Manifest.Name}' failed to create {path}: {stderr.Trim()}")
            { Code = "plugin_create_failed" };
        }
        return true;
    }

    private static void CreateExcel(string path, string? locale = null)

View on GitHub (pinned to 1ced45e900)

Solutions

  1. Run the plugin's create subcommand directly in a shell to reproduce the hang: `<plugin-exe> create <path>` and observe where it blocks.
  2. Check the plugin for interactive prompts, infinite loops, or missing input; ensure it is non-interactive when invoked from OfficeCLI.
  3. If 60s is genuinely too short for a legitimate large operation, split the work or pre-generate the file outside the plugin.
  4. File a bug against the plugin with the reproduction; the timeout is a safety bound, not a tunable in OfficeCLI.
Defensive patterns

Strategy: try-catch

Validate before calling

// No pre-call validation can predict a plugin hang; run create through a wrapper that owns the timeout.
// Pre-check the plugin is non-interactive: run `<plugin> create --help` once and fail fast if it prompts.

Type guard

// Guard: does a plugin exist and is it reachable for this extension before relying on it?
static bool PluginCanCreate(string ext) =>
    OfficeCli.Core.Plugins.PluginRegistry.FindFor(
        OfficeCli.Core.Plugins.PluginKind.FormatHandler, ext) is not null;

Try / catch

// Catch the timeout specifically so a fallback (built-in create / different plugin) can run.
try { BlankDocCreator.Create(path); }
catch (OfficeCli.Core.CliException ex) when (ex.Code == "plugin_create_failed")
{
    // log ex.Message, then fall back to a built-in format or surface to the user
    Log.PluginCreateFailed(ex.Message);
    throw;
}

Prevention

When it happens

Trigger: `officecli create data.xlsx` (or any extension) where the registered plugin's `create` subcommand deadlocks, loops infinitely, or blocks on a prompt/lock with no input. Also if the plugin waits on a network resource that never responds, or holds an exclusive file lock that itself waits.

Common situations: A plugin executable prompts for input under non-interactive use; a plugin has an unbounded retry loop; the plugin binary is misconfigured and spins; a plugin depends on a license server that is unreachable; the target path is on a slow/network mount causing the plugin to stall past 60s.

Understand the failure class

Related errors


AI-assisted analysis of iOfficeAI/OfficeCLI@1ced45e900 (2026-08-13). Data as JSON: /api/errors/5699b5c72f03805a. Report an issue: GitHub.