Skip to content

Consolidate the duplicate archetype registries (core vs intelligence) #91

Description

@SaharPak

Why this matters for Tech Immigrants

The core package (which the CLI and Web UI consume) and the
intelligence package (which the prompt pack and eval fixtures
consume) each maintain their own archetype registry. They use
different types, different IDs, and have no shared source of truth.

This causes three concrete problems for the project:

  1. The README's "8 archetypes" claim was wrongcore has 7,
    intelligence has 3. Auditors found the gap and corrected it.
  2. A user-facing PM resume misdetects as backend-engineer
    because the live detector (in core) only knows about
    ai-product-manager, never the plain product-manager that
    intelligence knows about. Plain-PM detection is functionally
    broken in the public surface.
  3. pnpm eval tests a different system than the CLI/Web UI use.
    The golden fixtures (pm-strong, swe-strong, data-ml-strong)
    run against intelligence.detectArchetype and the Archetype
    type. They never exercise the live core.evaluate() path.

Until this is consolidated, every new archetype has to be added in
two places, with two key shapes, and two detectArchetype
implementations — all with the risk that one drifts from the other.

Current state

Package File Type Count Has version?
@cv-builder/core packages/core/src/archetypes/index.ts RoleArchetype (plain TS, packages/core/src/types.ts) 7 No
@cv-builder/intelligence packages/intelligence/src/archetypes/index.ts Archetype (Zod, packages/schemas/src/archetype.ts) 3 Yes

Both expose listArchetypes(), getArchetype(id), detectArchetype(text).

Goal

After this is closed, one archetype registry is the source of
truth. All consumers (packages/core, packages/cli, apps/web-ui,
packages/prompts, packages/eval, .claude/skills/cv-evaluation/)
import from the same place. The Archetype type lives in
@cv-builder/schemas and is the only one. RoleArchetype is
removed.

Recommended approach (high level — design freedom belongs to the PR)

The cleanest design is:

  1. Promote packages/schemas/src/archetype.ts to the canonical
    Archetype schema. Add version to the existing core entries
    (just "1.0.0"; no semantic change).
  2. Move the merged archetype files into packages/intelligence/src/archetypes/
    (it's already the place the prompts and skill reference).
  3. Re-implement core.detectArchetype and core.listArchetypes as
    thin re-exports of intelligence.detectArchetype /
    intelligence.listArchetypes. The existing core.getArchetype
    becomes listArchetypes().find(...) or delegates.
  4. Update packages/core/src/evaluator/index.ts to use the Archetype
    shape (notably, the EvaluationResult.archetype field gains a
    version string — wire it through and bump the docs).
  5. Update packages/eval/fixtures/ to use the consolidated IDs (or
    alias the existing fixture archetypes to the merged IDs).
  6. Add version to every existing Archetype file in
    packages/intelligence/src/archetypes/*.ts if not already there
    (the three currently shipping — software-engineer,
    product-manager, data-ml-engineer — already do).

This is a medium-to-large refactor (~10 files, schema migration,
test updates). It does not add new role types — it only merges.

Scope fence (do not do in this PR)

  • No new role archetypes. Adding roles on top of an unmerged
    registry widens the eventual migration. Land the merge first, add
    roles after.
  • No LLM provider changes. Provider work is in packages/llm
    (separate).
  • No prompt-package changes other than anything required to
    consume the merged Archetype shape.

Acceptance criteria

  • packages/core no longer defines its own archetype registry;
    it re-exports from packages/intelligence.
  • pnpm --filter @cv-builder/cli start archetypes and
    pnpm eval both produce the same list of archetypes with the
    same IDs and display names.
  • apps/web-ui/src/app/results/page.tsx still renders
    result.archetype.name correctly (no UI change required).
  • Golden fixtures (packages/eval/fixtures/{swe,pm,data-ml}-strong/expected.json)
    continue to pass without modification (or with a one-line
    alias update if IDs changed — that is acceptable).
  • pnpm test, pnpm lint, pnpm build all green.
  • RoleArchetype removed from packages/core/src/types.ts;
    EvaluationResult.archetype is typed as
    packages/schemas/src/archetype.ts Archetype.

Tests needed

  • Cross-package integration test asserting that the evaluator's
    detected archetype has the same id and name as
    intelligence.detectArchetype(cv).id on a small set of fixtures.
  • Unit tests preserved from the existing
    packages/eval/src/__tests__/fixtures.test.ts.
  • A core.detectArchetype unit test (the currently-open issue [Core] Add unit tests for archetype detection #15,
    [Core] Add unit tests for archetype detection, can land as part
    of this work).

Docs / updates needed

  • docs/ARCHETECTURE.md
    remove the language that puts core and intelligence on
    parallel footings for archetypes. After the merge,
    intelligence becomes the only owner.
  • Update the packages/intelligence/README.md "Archetypes" section
    to reflect that it is now the canonical source (and remove the
    core's 'How to add an archetype' comments from
    packages/core/src/archetypes/index.ts).
  • Add a short paragraph in this file's conclusion pointing to
    the audit.

Related issues / docs

Metadata

Metadata

Assignees

No one assigned

    Labels

    archetypeNew role archetypecoreCore engine logicenhancementNew feature or request

    Type

    No type

    Fields

    No fields configured for issues without a type.

    Projects

    No projects

    Milestone

    No milestone

    Relationships

    None yet

    Development

    No branches or pull requests

    Issue actions