vercel/ai · error · Error

Duplicate Cline skill name: ${skill.name}

Error message

Duplicate Cline skill name: ${skill.name}

What it means

projectClineSkills builds the projected skill list for the Cline harness and requires each skill directory name to be unique. When two skills resolve to the same name it throws to prevent ambiguous skill references. This guards the integrity of the skill catalog exposed to the model.

Source

Thrown at packages/harness-cline/src/cline-skills.ts:99

function projectClineSkills({
  skills,
}: {
  skills: ReadonlyArray<HarnessV1Skill>;
}): ReadonlyArray<ProjectedClineSkill> {
  const names = new Set<string>();
  const ids = new Set<string>();
  return skills
    .map(skill => {
      if (
        !CLINE_SKILL_NAME_PATTERN.test(skill.name) ||
        skill.name === '.' ||
        skill.name === '..'
      ) {
        throw new Error(`Invalid Cline skill name: ${skill.name}`);
      }
      if (names.has(skill.name)) {
        throw new Error(`Duplicate Cline skill name: ${skill.name}`);
      }
      names.add(skill.name);

      const id = normalizeSkillToken(skill.name);
      if (ids.has(id)) {
        throw new Error(`Duplicate Cline skill identifier: ${id}`);
      }
      ids.add(id);

      return {
        id,
        name: skill.name,
        description: skill.description,
        content: skill.content,
        files: (skill.files ?? [])
          .map(file => ({
            path: normalizeSkillFilePath({
              skillName: skill.name,

View on GitHub (pinned to 69428b1f8b)

Solutions

  1. Rename one of the conflicting skills so every skill name is unique.
  2. Deduplicate the skill list before passing it to the harness (filter by name).
  3. If skills come from overlapping directories, exclude the duplicated source directory.

Example fix

// before
const skills = [...userSkills, ...repoSkills]; // both contain 'review-pr'
// after
const seen = new Set();
const skills = [...userSkills, ...repoSkills].filter(s =>
  !seen.has(s.name) && seen.add(s.name)
);
Defensive patterns

Strategy: validation

Validate before calling

const names = new Set();
for (const s of skills) {
  if (names.has(s.name)) throw new Error(`duplicate skill name: ${s.name}`);
  names.add(s.name);
}

Try / catch

try {
  await projectedSkills(input);
} catch (e) {
  if (/Duplicate Cline skill name/.test(String(e?.message))) {
    // dedupe/rename skills and retry
  } else throw e;
}

Prevention

When it happens

Trigger: Calling projectedSkills/projectClineSkills with a skills input where two skill entries have the same `name` property (e.g. two directories or declared skills both named 'deploy').

Common situations: Mounting multiple skill directories that contain same-named skill folders; merging skill sources (user + repo skills) without deduplication; copying a skill folder under two parents that both get scanned.

Related errors


AI-assisted analysis of vercel/ai@69428b1f8b (2026-08-30). Data as JSON: /api/errors/e6a5a553e27fb148. Report an issue: GitHub.