nanocoai/nanoclaw · warning

Could not read group standing instructions; omitting persona

Error message

Could not read group standing instructions; omitting persona

What it means

Reading the group's standing-instructions (persona) file failed for a reason other than not-existing (ENOENT returns null silently). The persona is omitted from this session's composed context, so the agent behaves less customized until fixed.

Source

Thrown at src/group-persona.ts:38

    return true;
  } catch (err) {
    if (typeof err === 'object' && err !== null && 'code' in err && err.code === 'EEXIST') return false;
    throw err;
  }
}

/** Read a group's standing instructions without following symlinks. */
export function readGroupPersona(groupDir: string): string | null {
  const file = path.join(groupDir, PERSONA_PREPEND_FILE);
  let fd: number | undefined;
  try {
    fd = fs.openSync(file, fs.constants.O_RDONLY | fs.constants.O_NOFOLLOW);
    if (!fs.fstatSync(fd).isFile()) return null;
    const content = fs.readFileSync(fd, 'utf-8').trim();
    return content || null;
  } catch (err) {
    if (typeof err === 'object' && err !== null && 'code' in err && err.code === 'ENOENT') return null;
    log.warn('Could not read group standing instructions; omitting persona', {
      file,
      error: err instanceof Error ? err.message : String(err),
    });
    return null;
  } finally {
    if (fd !== undefined) fs.closeSync(fd);
  }
}

View on GitHub (pinned to 294ef2aee8)

Solutions

  1. Check the file path in the log: `ls -la` it and its parents
  2. Replace symlinks with real files (O_NOFOLLOW rejects them by design)
  3. Fix ownership/permissions so the host user can read it

Example fix

# before
ln -s ~/shared/persona.md groups/mygroup/persona.md
# after
cp ~/shared/persona.md groups/mygroup/persona.md
Defensive patterns

Strategy: try-catch

Validate before calling

import fs from 'node:fs';
const st = fs.lstatSync(file);
if (st.isSymbolicLink()) throw new Error('persona must be a real file');

Type guard

function isReadableRegularFile(file: string): boolean {
  try { return fs.lstatSync(file).isFile(); } catch { return false; }
}

Try / catch

try { return readPersona(file); } catch (err) { if ((err as NodeJS.ErrnoException).code === 'ENOENT') return null; log.warn(...); return null; }

Prevention

When it happens

Trigger: openSync with O_NOFOLLOW fails on a symlink (ELOOP), a permission error, or the path is a directory. The O_NOFOLLOW guard makes symlinked persona files fail deliberately.

Common situations: Group folder is a symlink (migration moved it), perms changed, or someone replaced the file with a symlink for editing convenience.

Related errors


AI-assisted analysis of nanocoai/nanoclaw@294ef2aee8 (2026-08-28). Data as JSON: /api/errors/7ce147c8ddc02499. Report an issue: GitHub.