Browser ExtensionAutomationSaaS

OutreachGenie LinkedIn Automation Case Study

How OutreachGenie separates campaign state, approvals, quotas, and browser execution so interrupted LinkedIn outreach work can be reviewed and reconciled.

Delivered value

Keeps the durable campaign record outside the browser, with each claimed task, result, approval, quota, and failure tied back to one workspace.

Published
Updated
Stack
6 technologies
Editorial system visual showing prospect records moving through a timed outreach sequence into campaign reporting
Editorial system visual. Delivered product evidence appears below.

The problem

OutreachGenie began with a state problem, not a browser problem. A profile tab could show what was open at that moment, but it could not be the only record of which prospect belonged to a campaign, which flow version applied, whether copy was still approved, or whether an action had already happened.

Spreadsheets and message drafts made that split worse. The same prospect could appear in more than one list, browser work could stop halfway through a sequence, and an operator could not reliably distinguish work that was pending from work another extension instance had already claimed.

The product needed one durable campaign record outside LinkedIn while keeping browser-side execution visible and reviewable. It also needed to report uncertainty honestly. A missing browser response is not proof that an action failed, and treating it as a simple retry can create a duplicate.

The system response

I built OutreachGenie as four connected responsibilities instead of one autonomous browser script.

The web application is the control plane

The Next.js workspace is where an operator organizes prospects, builds flows, reviews campaigns, and sees activity. It does not rely on an open LinkedIn tab to remember campaign eligibility or progress.

The API owns the durable state

The Django API and PostgreSQL store prospect identity, list membership, flow definitions, campaign execution, approvals, quota reservations, runtime tasks, action events, and connection-request records. Workspace boundaries are enforced across those relationships.

The extension claims bounded work

The Manifest V3 TypeScript extension calls versioned runtime endpoints. It claims a task with a claim identifier and expiry, performs the browser-side step, then returns a result tied to that claim. The backend reconciles the result with the durable campaign record. A stale worker cannot silently complete a newer claim.

Controls stay separate from message generation

Approval, daily limits, cooldowns, deduplication, and task state remain deterministic application decisions. ChatGPT can help draft or review outreach, but it does not decide whether a prospect is eligible, whether an approval is current, or whether an action already happened.

What shipped

The result is an inspectable LinkedIn automation system rather than a collection of browser macros. An operator can see the prospect, flow, campaign state, waiting work, completed work, and failure record in one workspace.

The important case is an interruption. If the extension claims a task and the browser closes, the task still has an identity, claim expiry, and attempt history in PostgreSQL. The backend can distinguish pending work from claimed work and a confirmed result from an uncertain one. Unknown outcomes are not converted into blind retries.

Editing approved content can invalidate the approval that applied to the earlier version. Quota reservations can be committed when work counts or released when it does not. This does not make OutreachGenie an official LinkedIn product, guarantee account safety, or prove campaign performance. It makes the software's own decisions and recovery paths explicit.

Keeps the durable campaign record outside the browser, with each claimed task, result, approval, quota, and failure tied back to one workspace.

Architecture decisions

  1. Keep the Next.js workspace as the control plane and PostgreSQL as the record of campaign truth.
  2. Give each runtime task a claim identity, expiry, attempt history, and result receipt so interrupted work can be reconciled.
  3. Separate approval from execution so an edit can invalidate approval for an earlier content version.
  4. Reserve and commit quota through backend records instead of trusting counters held by one browser instance.
  5. Keep LinkedIn publishing and native scheduling distinct from the outreach campaign queue, with uncertain outcomes requiring review.

Release checks

  • Test prospect imports, list membership, deduplication, and workspace isolation.
  • Run runtime tasks through pending, claimed, completed, failed, expired, and uncertain paths.
  • Reject stale claim results and confirm a lost browser session does not create an automatic duplicate retry.
  • Verify quota reservations are committed or released with the matching work outcome.
  • Build and test the extension against the versioned runtime contract before release.

Questions buyers should ask

What makes this a LinkedIn automation case study?

It documents a shipped control plane, API, PostgreSQL data model, and Manifest V3 extension. The case study focuses on how prospects, flows, approvals, quotas, runtime tasks, and results remain connected when browser execution is interrupted.

What happens if the browser closes during a campaign task?

The backend still has the task identity, claim identifier, expiry, and attempt history. It can distinguish pending, claimed, confirmed, failed, and uncertain work. An uncertain result is not treated as permission for a blind retry.

Can ChatGPT run the LinkedIn campaign?

ChatGPT can assist with bounded drafting and review. OutreachGenie keeps campaign eligibility, approval, deduplication, quotas, task state, and result reconciliation in deterministic application logic rather than handing those decisions to a language model.

Is OutreachGenie approved or endorsed by LinkedIn?

No. OutreachGenie is an independent product and is not endorsed by LinkedIn. Its engineering controls address software reliability and operator review. They do not guarantee platform compliance or account safety.

Why does this case study not publish acceptance or revenue results?

The available public evidence supports the product architecture, interface, tests, and release process. It does not include a public campaign dataset that would support acceptance rates, SQL counts, or revenue claims, so those claims are not made.

Project evidence

Real interface screenshots and diagrams are kept separate from the editorial cover visual.

OutreachGenie visual flow builder for visits, waits, connection requests, and messages
Product interface: build a visible sequence of visits, connection checks, waits, and messages.
OutreachGenie browser extension capturing LinkedIn prospects into an organized list
Extension interface: capture a profile or search result into an OutreachGenie prospect list.
OutreachGenie campaign analytics showing progress, outcomes, waiting work, and failed-action reporting
Campaign interface: review progress, outcomes, waiting work, and failed actions without opening a spreadsheet.

Evidence note: The public product, interface screenshots, repository, tests, and release records support the architecture described here. No private customer data is shown. Acceptance rates, SQL counts, revenue, and account-safety claims are omitted because no public dataset supports them. OutreachGenie is not endorsed by LinkedIn.

Have a workflow that needs the same level of control?

Bring the current process, the systems involved, and the failure points. I will turn them into a written scope with acceptance checks before recommending a build.