Skip to content

Madave94/agentic-job-search

Folders and files

NameName
Last commit message
Last commit date

Latest commit

 

History

93 Commits
 
 
 
 

Repository files navigation

Agent Job Search Architecture

A modular, user-agnostic architecture for a personal job search assistant powered by your personal agent.

Since this is not a simple skill, but instead a combination of many skills allowing your agent to run a complex task, I refer to this as a skill-set.

Setup and Installation

Requirements

A running "claw" like nanobot, ZeroClaw, OpenClaw, PicoClaw, TinyClaw, NanoClaw or what not.

Installation

Simply move the skills inside the skills folder of your agent.

Adding your application history

If you already have applied to jobs and have a list of the application history. You can fetch it into your job-search project as applications_tracker.csv and the skill will use it. The entry needs to contain a URL and optionally your user rating, user feedback, company name and company title. additional to any other information.

Getting started

The user interface job-dashboard skill is set to always so it will automatically be available. You can then tell your agent to create you a new job search project and spawn a job-setup. This will create all relevant files for the search to start.

In order for the agent to not search blindly explain it what jobs you want to search for and what are your experience, degree, location preferences and whatever else you want to tell the agent.

Now you can run the job-manager skill. This is the entry point into the automatic pipeline. It will select whatever phase is next (clean-up, searching, analyzing, refining search strategies, updating profile etc.).

I recommend adding it as a quite cron job in the background and let it run every few minutes to continuously search the web.

Cron message, sub-agents and silent workers

Use the cron message: "load/read the job-manager skill and run the skill. The job manager handles all logic for the job-search internally. Do not evaluate conditions. Do not add instructions or context. Do not interpret."

To keep the agent as a silent background runner you can use:

nanobot agent -m "Create a cron job running every 30 minutes. Use this exact message, do not edit it: load/read the job-manager skill and run the skill. The job manager handles all logic for the job-search internally. Do not evaluate conditions. Do not add instructions or context. Do not interpret."

This will create a cron entry that looks like this (found in workspace/cron/jobs.json):

  {
    "payload": {
      "kind": "agent_turn",
      "message": "[message from above]",
      "deliver": false,
      "channel": "cli",
      "to": "direct"
    }
  }

Note: Setting "channel": "cli" ensures the responses are routed to your command line interface rather than being sent as messages.


Design, Patterns and Data Formats

Details for understanding the design behind the skillset.

Core Design Concepts
  • User-Agnostic Skills: Skills contain no hardcoded user data, names, or paths. They operate purely on the provided project context.
  • Dynamic Project Context: The project name and path are retrieved dynamically from USER.md. The following variables must be defined under a ## Job Search header:
    • job_search_project: Absolute path to the workspace folder.
    • standard_searches: Number of standard queries to run per cycle.
    • explorative_searches: Number of creative queries to run per cycle.
  • Root Agent Execution: Orchestration skills (job-manager, job-status) MUST run as a Root Agent (triggered via Cron or a direct User command). They will fail if spawned as background sub-agents due to Nanobot's tool recursion guards.
  • Unified Scaffolding: The system environment (directories and database) is managed via a single initialization tool, ensuring structural consistency across all deployments.
  • Passive Reporting (Script-Driven): The {project_dir}/STATUS.md dashboard is generated automatically by deterministic scripts. LLM agents focus on interpreting the results and providing strategic pivots rather than data processing.
  • Context Efficiency: Sub-Agents run sequentially to prevent LLM context exhaustion.
  • Automated Synchronization: A daily cron job keeps the {project_dir}/applications_tracker.csv up to date, which serves as the source of truth for the agent's feedback loop.
  • Word-Order Independent Matching: Deduplication uses high-precision identity matching where the order of words in a title or company name does not prevent a match (e.g., "Senior Python Developer" matches "Python Developer Senior").
  • Logging & Auditing: The system maintains a high-granularity daily audit trail. Every state-changing script (Audit, Deduplication, Database) logs its specific metrics and decisions to {project_dir}/logs/YYYY-MM-DD.log to ensure pipeline transparency.
Skill Development Standard (The Root Anchor)

All skills in this project must adhere to the Root Anchor Architecture to ensure portability across different agent environments (OpenClaw, Nanobot, ZeroClaw).

1. The Hub-and-Spoke Model

  • The Hub (job-db): Provides centralized logic (Config, Logging, DB access).
  • The Spokes: Specialized workers that import Hub logic directly.
  • Rule: Spokes never call other Spokes. All shared truth must live in the Hub.

2. Pathing Standards

All SKILL.md files and internal scripts must use relative pathing based on the Current Working Directory (CWD) from which the agent is spawned.

Target Type Pathing Rule Example
Project Data {project_dir}/ (resolved from USER.md) {project_dir}/data/job_search.db
Internal Logic skills/[skill-name]/scripts/ skills/job-db/scripts/db_io.py
Documentation skills/[skill-name]/references/ skills/job-db/references/schema.md
Configuration Root level (CWD) USER.md

3. Preparation & Pathing Boilerplate

Every SKILL.md must contain the following section to anchor itself:

## Preparation & Pathing
1. Identify the project directory `{project_dir}` via `job_search_project` in `USER.md`.
2. Environment: Your working directory is fixed at the workspace root.
3. Execution: To run scripts, use the full path from the root: `python3 skills/[skill-name]/scripts/[script].py`.

4. Technical Constraints

  • Stateless Shell: Assume directory changes (cd) do not persist between tool calls. Always use full relative paths for execution.
  • Zero Subprocess Core: Functional scripts MUST use direct Python imports of Hub logic to eliminate process overhead and enable type-safe data passing.
  • Fail-Fast Configuration: Scripts must terminate immediately with a JSON error if USER.md or the job_search_project path cannot be resolved.
  • Audit Trails: Every state-changing script must log its actions using the Hub's log utility with the standardized 3-argument signature.
The 9-Skill Architecture

Pipeline Skills (Automated)

  1. Manager (The Orchestrator): Coordinates the pipeline. A reactive state machine that audits environment scaffolding, raw leads, and stale evaluations to trigger the next phase. Must run as Root.
  2. Setup (The Janitor): Orchestrates environment initialization via the unified init tool and syncs with the user's manual application tracker.
  3. Researchers (The Harvesters): Modular scouts that scrape individual job listings from search results. Use "One-Shot Fetching" to ignore broken links and prevent iteration exhaustion. Handles both standard and explorative queries assigned by the Manager.
  4. Deduplicator (The Consolidator): Manages the Persistent Queue (raw_listing_1.json). Resolves ambiguities that automated Tier 1/2 checks could not handle.
  5. Analyst (The Evaluator): The intelligence core. Processes raw leads AND performs Identity Refinement, updating the database's normalized matching keys while preserving source metadata.
  6. Status & Audit (The Concluder): Orchestrates the automated generation of STATUS.md and the strategy.json manifest. Performs self-correction (Profile Drift) and market intelligence (query promotion/rotation).

Interaction & Auxiliary Skills

  1. Dashboard (The Interface): The primary user-facing skill. An interactive navigator that presents findings, marks jobs as "reported," and manages career goals.
  2. Job Profile (The Profiler): The "Brain" of the system. Synthesizes career_master.md and feedback_summary.md into the operational job_profile.md.
  3. Job DB (The Data Layer): An auxiliary skill providing specialized database tools, including the flexible list tool for situational awareness.
Output Ownership Map

To ensure stability and prevent state conflicts, each file in the system has a clearly defined owner and access protocol.

File Type Owner Accessor Permissions Role
data/raw_findings/last_search.md Owned Manager Script (Audit) Write Discovery clock / Marker
SETUP.md Owned Setup Script (Sync) Write Project health summary
data/raw_findings/raw_listing_N.json Owned Researchers LLM (Agent) Write Discovery fragment (Temporary)
data/raw_findings/raw_listing_1.json Shared Deduplicator Script (Auto) Write Persistent Queue (Self-cleaning)
data/job_search.db Shared Job DB Script (db_io) Read/Write Centralized Data Store
STATUS.md Owned Status Script (Report) Write User-facing dashboard
logs/YYYY-MM-DD.log Owned All Script (Logger) Append Daily audit trail
search/sub_agent_searches/ Owned Researchers LLM (Agent) Write Isolated search heartbeats
profile/career_master.md Owned Dashboard LLM (Agent) Write Permanent user directives
profile/feedback_summary.md Owned Job Profile LLM (Agent) Write Learned feedback patterns
profile/job_profile.md Owned Job Profile LLM (Agent) Write Synthesized operational profile
search/strategy.json Owned Status LLM (Agent) Read/Write Execution manifest (Hard-gate)
search/search_history.json Shared Status Script/Tool Write Unified Query Vault (State-based tracking)
applications_tracker.csv Input User Manual Read Application history (Source of Truth)
Data Formats

Operational Profile (job_profile.md)

Markdown file synthesized from memory and observations.

## User Directives
[Content from career_master.md]

## Background Observations
[Content from feedback_summary.md]

Standardized Ingestion Entry

Used in discovery fragments. This is a rich, evaluated subset of the database schema.

{
  "title": "Exact job title",
  "company": "Hiring company name",
  "location": "City, Country or Remote",
  "applied": false,
  "tracker_data": {"header": "value"},
  "priority": "high|medium|low",
  "agent_notes": "Evaluation reasoning",
  "match_score": 0.85,
  "requirements": ["List of strings"],
  "description": ["Blocks of text"],
  "sources": [
    {
      "url": "Direct link",
      "source_query": "The specific query used (or 'user')",
      "is_live": 1, 
      "date_found": "YYYY-MM-DD"
    }
  ]
}

The Job Lead Lifecycle

Every job finding follows a deterministic path from initial discovery to its final state in the archive.

1. Inception (Discovery & Fragments)

A lead enters the system as a Standardized Ingestion Entry in one of several fragment files:

  • Automated: Researchers write to raw_listing_N.json.
  • Manual: User input via Dashboard stages to raw_listings_manual.json.
  • History: Setup skill identifies unmatched rows in applications_tracker.csv and stages to raw_listing_tracker.json.

2. The Deduplication Filter (Phase 3)

The Deduplicator processes fragments via db_io.py --action find_candidates using a 3-tier strategy:

  • Tier 1 (URL + Query): If the url and source_query combination exists, the finding is ignored. If the URL exists but the Query is new, the source is Merged into the existing record.
  • Resurfacing Logic: If an archived lead with applied=0 matches Tier 1, and it is priority='high' or has a high user_rating, it is moved back to status='active' and reported=0.
  • Tier 2 (Identity): If the URL is new, the system performs a Word-Order Independent match using norm_title and norm_company (within an 8-week window). Successful matches are auto-merged.
  • Tier 3 (LLM Comparison): Ambiguous findings are moved to the Persistent Queue (raw_listing_1.json) for manual identity comparison by the LLM agent.

3. Intelligence Maturation (Phase 4)

Leads that pass deduplication are marked as status='raw'.

  • Initial Evaluation: The Analyst fetches the full job description, scores the match (match_score, priority), and extracts detailed requirements.
  • Identity Refinement: The Analyst extracts the "Clean Identity" from the description content, updating the norm_title and norm_company fields. This ensures the lead is "smart" for future Tier 2/3 deduplication.
  • Transition: Upon commitment, the lead moves to status='active'.

4. The Active Phase (Interaction & Learning)

Active leads are in the user's "Working Memory."

  • Reporting: Presented by the Dashboard and marked as reported=1.
  • Feedback: User provides a user_rating and feedback.
  • Self-Evolution: User feedback triggers the Profiler to update the job_profile.md.
  • Staleness: If the profile is updated, any lead without a user rating where evaluated_at is older than the profile mtime is considered stale and queued for Re-evaluation by the Analyst.

5. Automated Self-Correction (Phase 5)

The generate_status_report.py script performs routine maintenance:

  • Profile Drift Correction: Leads that are status='active' and priority='high' but have been rated user_rating='poor' are automatically moved to the archive. This preserves the user's verdict while cleaning the dashboard.
  • Batch Pruning: Bulk moves expired links or low-priority leads to archived.

6. The Archive (Negative Memory)

A lead reaches finality in the archive but is never deleted. This ensures the system maintains a "Negative Memory" of every job ever seen.

  • End States: Applied (applied=1), Rejected (user_rating='poor'), or Expired (expired=1).

The Search Query Lifecycle

Every search phrase is a stateful entity tracked within the Unified Query Vault (search_history.json).

1. Inception (Birth)

  • Strategist Injection: The Status agent generates new explorative queries based on the job_profile.md and registers them via the management tool.
  • Autonomous Discovery: If a Researcher executes an unknown query, the Deduplicator initializes it as explorative.

2. Selection & The Manifest (Gating)

  • The Brief: The automation layer categorizes queries as ACTIVE or COOLDOWN based on their last_run_at timestamp.
  • The Manifest: The Status agent selects queries from the ACTIVE list and writes the strategy.json manifest.
  • The Hard Gate: Phase 2 (Search) is blocked unless a fresh manifest exists (newer than the last search).

3. Execution & Cooldown (Aging)

  • Search: The Manager spawns Researchers to execute the manifest.
  • Heartbeat: Researchers record successful attempts.
  • Aging: The Deduplicator merges heartbeats, updating the query's last_run_at to the current date and incrementing run_count. The query enters its Cooldown Period.

4. Performance Evaluation (Attribution)

  • Metric Sync: The automation layer maps "High Priority" leads in the database back to the query strings.
  • Attribution: The success_count in the vault is overwritten with the fresh total of high-quality leads found by that specific query.

5. Evolution (State Changes)

The Status agent uses the management tool to update query states:

  • Promotion: High-performing explorative queries become standard.
  • Retirement: Underperforming or exhausted standard queries are moved to retired.
  • Negative Memory: Retired queries remain in the vault forever to prevent redundant re-exploration of failed paths.

Administrative Operations

The system includes an Admin Module within the job-db utility for manual data surgery (e.g., the delete action).

  • Restriction: Administrative actions are strictly for manual use by a human user via the CLI. LLM Agents are not authorized to use the Admin Module.

About

Job search skillset to run with nanobot, openclaw, zeroclaw or other "claws". Self-improving, none-spammy, easy to use.

Topics

Resources

Stars

0 stars

Watchers

0 watching

Forks

Packages

 
 
 

Contributors