JSON Resume Schema in Hiring Agent: Standardized Data Models Explained

The Hiring Agent project adopts the official JSON Resume specification as its canonical data model, implementing type-safe Pydantic models in models.py to validate and structure candidate résumés.

The interviewstreet/hiring-agent repository automates candidate evaluation through LLM extraction and GitHub profile enrichment. To ensure consistent data handling across pipelines, the project leverages the JSON Resume schema as its standardized interchange format, encoding the specification via robust Python data models that guarantee interoperability with external tools.

Schema Implementation in models.py

The complete JSON Resume schema definition resides in models.py, where the JSONResume class acts as the root container (defined around lines 200-216). This class aggregates all resume sections as optional Pydantic fields, mirroring the official JSON Resume specification exactly.

Core Data Models

Each resume section maps to a dedicated Pydantic model with strict type annotations:

Section Model Key Fields
Basics Basics name, email, phone, url, summary, location, profiles
Work Experience Work name, position, url, startDate, endDate, summary, highlights
Education Education institution, url, area, studyType, startDate, endDate, score, courses
Skills Skill name, level, keywords
Projects Project name, startDate, endDate, description, highlights, url, technologies, skills
Awards Award title, date, awarder, summary
Certificates Certificate name, date, issuer, url
Publications Publication name, publisher, releaseDate, url, summary
Languages Language language, fluency
Interests Interest name, keywords
References Reference name, reference
Volunteer Work Volunteer organization, position, url, startDate, endDate, summary, highlights

All fields within these models are optional, allowing the schema to accommodate partial résumés while maintaining strict type safety for any provided data.

Creating and Validating Resume Data

Instantiation with Pydantic Models

You can construct resume objects programmatically using the model classes defined in models.py:

from models import JSONResume, Basics, Location, Profile, Work, Education, Skill, Project

resume = JSONResume(
    basics=Basics(
        name="Alice Doe",
        email="alice@example.com",
        location=Location(city="San Francisco", region="CA", countryCode="US"),
        profiles=[
            Profile(network="GitHub", username="alice", url="https://github.com/alice")
        ],
    ),
    work=[
        Work(
            name="Acme Corp",
            position="Software Engineer",
            startDate="2020-01",
            endDate="Present",
            summary="Built scalable backend services.",
        )
    ],
    education=[
        Education(
            institution="University of Example",
            studyType="Bachelor",
            area="Computer Science",
            startDate="2016-09",
            endDate="2020-06",
            score="3.9",
        )
    ],
    skills=[
        Skill(name="Programming Languages", keywords=["Python", "Go", "Rust"])
    ],
    projects=[
        Project(
            name="OpenAI-Wrapper",
            description="A Python wrapper for OpenAI APIs.",
            url="https://github.com/alice/openai-wrapper",
            technologies=["Python", "FastAPI"],
        )
    ],
)

JSON Serialization

Convert validated objects to standard JSON format using Pydantic's built-in methods:

import json

json_output = resume.json(indent=2)

This produces output conforming to the JSON Resume schema, ready for storage or API transmission.

Schema Validation and Parsing

When ingesting external data, use parse_obj() to validate against the JSON Resume schema:

from models import JSONResume

with open("candidate_resume.json") as f:
    data = json.load(f)

validated_resume = JSONResume.parse_obj(data)

If any field violates the expected type constraints, Pydantic raises a validation error immediately, preventing downstream processing of malformed data.

Integration with LLM Pipelines

The project enforces JSON Resume schema compliance during LLM extraction through two critical components:

  • transform.py: Normalizes raw LLM outputs into the strict JSON Resume structure defined in models.py
  • prompt.py and prompts/templates/*.jinja: Jinja templates instruct the LLM to generate output conforming to the exact property names and types expected by the schema

This ensures that unstructured résumé text converts reliably into the standardized format before evaluation and enrichment.

Summary

  • The JSON Resume schema provides the canonical data model for all candidate information in the Hiring Agent project
  • models.py implements the complete specification using Pydantic classes (JSONResume, Basics, Work, Education, etc.)
  • Type-safe validation occurs via parse_obj(), preventing malformed data from entering the pipeline
  • LLM outputs are normalized through transform.py and schema-specific prompts to guarantee compliance
  • All schema fields are optional, accommodating partial résumés while maintaining strict validation for provided data

Frequently Asked Questions

What specific JSON Resume version does the Hiring Agent implement?

The Hiring Agent implements the standard JSON Resume specification as defined at jsonresume.org. The Pydantic models in models.py reflect the current stable schema, covering all standard sections including basics, work, education, skills, projects, awards, and certificates.

How does the code handle incomplete résumé data?

All fields in the JSONResume model and its sub-models are optional, allowing partial résumés to validate successfully. Pydantic only enforces type constraints on fields that are actually present, so missing sections simply result in null values or empty lists in the JSON output without causing validation failures.

Where does the conversion from LLM output to JSON Resume occur?

The transform.py module handles normalization of raw LLM outputs into the JSON Resume structure. Additionally, prompt.py and the Jinja templates in prompts/templates/ prime the LLM to emit data matching the expected schema property names and types directly, reducing the transformation burden.

Can I extend the schema with custom fields?

While the base models strictly follow the official JSON Resume specification, Pydantic supports model inheritance. You can extend the existing classes in models.py to include additional custom fields, though this may break compatibility with standard JSON Resume consumers unless they ignore unknown properties.

Have a question about this repo?

These articles cover the highlights, but your codebase questions are specific. Give your agent direct access to the source. Share this with your agent to get started:

Share the following with your agent to get started:
curl -s "https://instagit.com/install.md"

Works with
Claude Codex Cursor VS Code OpenClaw Any MCP Client

Maintain an open-source project? Get it listed too →