EveryInc/compound-engineering-plugin · warning

Ignoring unreadable Pi install manifest at ${manifestPath}.

Error message

Ignoring unreadable Pi install manifest at ${manifestPath}.

What it means

Emitted by the Pi target's readInstallManifest when the Pi install manifest exists but fails to parse or read with an error other than ENOENT. Like the managed variant, the function swallows the error, warns, and returns null so Pi installation continues without stale owned-file tracking. ENOENT is silently treated as 'no manifest yet'.

Source

Thrown at src/targets/pi.ts:355

      const promptsRoot = paths?.promptsDir ?? managedDir
      const extensionsRoot = paths?.extensionsDir ?? managedDir
      const agentsRoot = paths?.agentsDir ?? managedDir
      // `agents` was added in v2.69+; accept missing/omitted to stay
      // backward-compatible with v2.x manifests that only tracked skills,
      // prompts, and extensions. Drop non-array values defensively.
      const rawAgents = Array.isArray(parsed.agents) ? parsed.agents : []
      return {
        version: 1,
        pluginName,
        skills: filterSafePiManifestEntries(parsed.skills, skillsRoot, manifestPath, "skills"),
        prompts: filterSafePiManifestEntries(parsed.prompts, promptsRoot, manifestPath, "prompts"),
        extensions: filterSafePiManifestEntries(parsed.extensions, extensionsRoot, manifestPath, "extensions"),
        agents: filterSafePiManifestEntries(rawAgents, agentsRoot, manifestPath, "agents"),
      }
    }
  } catch (err) {
    if ((err as NodeJS.ErrnoException).code !== "ENOENT") {
      console.warn(`Ignoring unreadable Pi install manifest at ${manifestPath}.`)
    }
  }
  return null
}

function filterSafePiManifestEntries(
  entries: unknown[],
  rootDir: string,
  manifestPath: string,
  group: string,
): string[] {
  const safe: string[] = []
  for (const entry of entries) {
    if (isSafeManagedPath(rootDir, entry)) {
      safe.push(entry)
    } else {
      console.warn(
        `Dropping unsafe Pi install-manifest entry in ${manifestPath} (group "${group}"): ${JSON.stringify(entry)}`,

View on GitHub (pinned to c9c10f8c75)

Solutions

  1. Delete the unreadable Pi manifest so the next run starts clean (ENOENT path).
  2. Fix the JSON syntax or permissions on manifestPath.
  3. Reinstall the Pi plugin target to regenerate the manifest.
  4. Check for concurrent installs that may have raced while writing the manifest.

Example fix

// before
Pi manifest with a trailing comma -> warning on every run
// after
rm <manifestPath> && reinstall  // fresh valid manifest
Defensive patterns

Strategy: fallback

Validate before calling

const raw = await readFile(manifestPath, "utf8").catch(() => null);
const valid = raw !== null && (() => { try { JSON.parse(raw); return true; } catch { return false; } })();

Try / catch

const manifest = await readPiInstallManifest(manifestPath);
if (manifest === null) {
  // absent or unreadable: treat as fresh install, manifest will be rewritten
}

Prevention

When it happens

Trigger: Calling readPiInstallManifest / readInstallManifestWithLegacyFallback / owned when the Pi manifest at manifestPath contains invalid JSON, is unreadable due to permissions, or fails I/O with a non-ENOENT errno.

Common situations: Manifest truncated by an interrupted Pi install; hand-edited JSON; permission mismatch after copying a home directory; format drift from an older plugin version.

Related errors


AI-assisted analysis of EveryInc/compound-engineering-plugin@c9c10f8c75 (2026-08-31). Data as JSON: /api/errors/7eb7b61c069d2405. Report an issue: GitHub.