.reveal{opacity:1!important;transform:none!important}

From application to first day

Applications, messages and hiring stages in one system. Candidates can check their status in a personal portal.

Applications arrive from different job boards. Recruiters need to avoid duplicates and know who has already spoken to each candidate.

Candidates, messages and recruitment stages sit together. Each candidate can have an assigned manager and a visible path through to hiring.

  • Applications from hh.ru and Avito

  • Duplicate candidate detection

  • Interview, trial day and hiring stages

Anonymized vacancy and response list with synthetic candidatesOpen full image ↗
Back office: vacancies and responses (screen reconstruction, synthetic data)Mobile view shows an enlarged detail. The full image opens in a new tab.
More product screens
Candidate record with invented contact detailsOpen full image ↗
Candidate record: contact details and status history (screen reconstruction, synthetic data)Mobile view shows an enlarged detail. The full image opens in a new tab.
Messenger screen with synthetic conversationOpen full image ↗
Messenger: recruiter and candidate conversation (screen reconstruction, synthetic data)Mobile view shows an enlarged detail. The full image opens in a new tab.
Candidate portal with a sample response statusOpen full image ↗
Candidate portal: response status and notifications (screen reconstruction, synthetic data)Mobile view shows an enlarged detail. The full image opens in a new tab.
  1. Intake & deduplication

    The system accepts webhook events from external platforms and matches a response and a candidate against existing records by source and contact details.

  2. Assignment & communication

    A response is assigned to an owner based on the candidate's identity on that platform; further communication happens through the internal messenger with live updates.

  3. Hiring stages

    Interviews, internships, and the hiring decision are recorded with a status history and reasons for rejection.

  4. Sync & data lifecycle

    A status change is reliably sent back to the platform with retries; personal data is anonymized automatically once the retention period expires.

For your technical team: inside the solution

A connector layer receives events from external platforms and hands them to background jobs that update the candidate and vacancy model; the back office and the candidate portal share the same data with different access rights, and live updates travel over a separate messaging channel.

  • Connector layer for external job platforms
  • Background intake and sync jobs
  • Back office
  • Candidate portal
  • Live-update channel
Shared candidate, vacancy, and status model

Reliability

  • Role-based access with a separate, restricted view for security staff.
  • Versioned consent for personal-data processing with a date and source.
  • Time limits on background jobs to guard against stuck network calls.
  • A candidate can request deletion of their own data from the portal after re-confirming their password.

Decisions and trade-offs

An unresolved event is stored in full and can be replayed later instead of being discarded.

An incoming event from an external platform sometimes cannot be processed immediately, for example before a vacancy is synced.

A response is not lost because of a temporary data-sync gap.

Deduplication also checks for a matching candidate by contact details, not only the event identifier.

An external platform can redeliver the same event with a new identifier.

The same candidate is not created twice in the system.

Outbound sync runs through a separate durable mechanism with state and retries.

A status change must be synced to the external platform reliably, not inside a single user HTTP request.

A temporary platform outage does not lose a status update.

Identifying fields are anonymized automatically once the configured retention period expires.

Candidate personal data cannot be kept indefinitely after the process ends.

The personal-data lifecycle is built into the product rather than left to a manual process.

An outgoing message sent by the system is "adopted" once the platform confirms it, instead of creating a duplicate record.

A candidate may message the chat more than once, and an outgoing operator message does not always get a platform identifier right away.

The conversation is not duplicated even when platform confirmation is delayed.

Each outbound sync operation keeps its own state and is processed independently of the others.

Syncing a status change to the platform and sending the candidate an autoreply are different operations, and neither should depend on the outcome of the other.

A failure in one operation does not block or roll back the other.

Technologies

  • Python
  • Django
  • PostgreSQL
  • Celery
  • Redis
  • Channels / WebSocket
  • Docker Compose

Working through something similar?

What gets in the way?

A few words are enough. You do not need a technical brief or a final budget to start a conversation.

Andrei will read your message and ask about the task. If we can help, we will suggest a next step.

By submitting the form, you accept the data processing terms.