From 8655bc4ca37d12a0814591916a1f43974f4bfb0b Mon Sep 17 00:00:00 2001 From: Bibesh Pyakurel <167917999+bibeshpyakurel@users.noreply.github.com> Date: Mon, 21 Sep 2026 08:35:42 -0500 Subject: [PATCH] docs: rewrite the README around the security boundary and how to load it MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit JobInsight is a Chrome extension with no hosted demo, so the README now says that plainly and puts the unpacked-install steps where a live demo link would be. Adds a one-line description, CI/license/language badges, and five bullets on the decisions worth noticing — the Express proxy that keeps the OpenAI key out of the client and the origin gate CI tests, the MV3 content script / service worker / popup split, the 7-day per-job cache, structured six-field extraction, and the manifest validation that catches breaks invisible until reinstall. Backend quick start commands are taken verbatim from backend/package.json. The existing LinkedInFeed.png screenshot is kept; two further shots that would help are named with their paths and commented-out image lines. Co-Authored-By: Claude Opus 5 (1M context) --- README.md | 157 ++++++++++++++++++++++++++++++++++++------------------ 1 file changed, 105 insertions(+), 52 deletions(-) diff --git a/README.md b/README.md index 3d32a28..2d43cf9 100644 --- a/README.md +++ b/README.md @@ -1,79 +1,132 @@ -# JobInsight — LinkedIn Job Analyzer +# JobInsight -A Chrome extension that automatically analyzes LinkedIn job postings and shows a floating overlay with key details extracted by AI. +A Chrome extension that reads the LinkedIn job posting you're looking at and answers the +questions a job seeker actually screens on — does it sponsor, does it require citizenship, +how many years of experience — in a draggable overlay, without leaving the page. -## Preview +[![CI](https://github.com/bibeshpyakurel/JobInsight/actions/workflows/ci.yml/badge.svg)](https://github.com/bibeshpyakurel/JobInsight/actions/workflows/ci.yml) +[![License: MIT](https://img.shields.io/github/license/bibeshpyakurel/JobInsight)](LICENSE) +[![Top language](https://img.shields.io/github/languages/top/bibeshpyakurel/JobInsight)](https://github.com/bibeshpyakurel/JobInsight) -

- JobInsight overlay on the LinkedIn job feed -

+JobInsight is a browser extension, not a hosted site, so there is no live demo link — +it runs inside LinkedIn. [Load it in about a minute](#install) and it works on any +LinkedIn job listing. -## What it shows - -- **Experience** — years required -- **Education** — degree level and whether required or preferred -- **Sponsorship** — Sponsors / Does Not Sponsor / Not Mentioned -- **US Citizenship** — flags if citizenship or security clearance is required -- **Summary** — 2-3 sentence overview of the role -- **Keywords** — job-specific technical terms, highlighted in the job description - -## Installation - -1. Go to `chrome://extensions` in Chrome -2. Enable **Developer Mode** (top-right toggle) -3. Click **Load unpacked** and select this folder +## Screenshots -## Setup +![JobInsight overlay on the LinkedIn job feed](screenshots/LinkedInFeed.png) -1. Click the **JobInsight** icon in the Chrome toolbar -2. Sign in with your **Google account** -3. Make sure the **JobInsight backend** is deployed and reachable -4. Open any LinkedIn job listing +> Two more shots would round this out. Drop each file at the path shown and uncomment +> the matching line. -## Usage +| Screenshot | Path | Why it matters | +|---|---|---| +| The overlay close-up on a single job, with the sponsorship and citizenship rows visible | `screenshots/overlay-detail.png` | The product in one frame — the fields people install this for | +| The popup showing the Google sign-in state | `screenshots/popup-signin.png` | Shows the auth gate that sits in front of the backend proxy | -Open any LinkedIn job listing — the overlay appears automatically in the top-right corner. Drag it to reposition, or resize it from any edge. + + -Results are cached for 7 days so re-opening the same job is instant. - -## Configuration +## What it shows -This extension uses a backend proxy for OpenAI requests. +For each job posting, the overlay extracts: -- Users sign in with Google before using the extension. -- The Chrome extension sends job description text to the backend. -- The backend holds the OpenAI API key securely and calls OpenAI. -- The API key is never stored in the extension source code. +- **Experience** — years required +- **Education** — degree level, and whether required or preferred +- **Sponsorship** — Sponsors / Does Not Sponsor / Not Mentioned +- **US Citizenship** — flags if citizenship or security clearance is required +- **Summary** — a 2–3 sentence overview of the role +- **Keywords** — job-specific technical terms, highlighted in the job description -## Backend +## What it demonstrates technically + +- **The API key never ships to the client.** The extension holds no OpenAI credential; + it posts job text to a Node/Express proxy that holds the key server-side. The proxy + gates `/api/analyze` on the configured extension origin, and CI tests that gate + specifically — it is the security boundary the whole design rests on. +- **A complete Chrome MV3 architecture**: a content script that scrapes and renders the + overlay into LinkedIn's DOM, a service worker that brokers the backend calls, and a + popup that owns Google OAuth via `chrome.identity`. +- **A 7-day client-side cache** (`JOB_CACHE_TTL` in `content/linkedin-scraper.js`) keyed + per job, so revisiting a posting is instant and costs nothing — the cheapest possible + fix for redundant LLM calls. +- **Structured extraction, not free text.** GPT-4o-mini is prompted to return six fixed + fields the UI can render directly, rather than prose the extension would have to parse. +- **CI catches the failure mode that is invisible until reinstall** — it validates + `manifest.json`, checks every script the manifest names actually exists, syntax-checks + every extension script, and audits production dependencies. + +## Stack + +| Layer | Technology | +|---|---| +| Extension | Chrome MV3, vanilla JavaScript (content script, service worker, popup) | +| Backend proxy | Node.js, Express 4 | +| Auth | Google OAuth 2.0 via `chrome.identity` | +| AI | OpenAI GPT-4o-mini | +| Hosting | Render (backend proxy) | +| CI | GitHub Actions (Node 20 and 22) | + +## Install + +The extension is not on the Chrome Web Store — load it unpacked: + +1. Clone this repository. +2. Open `chrome://extensions` in Chrome. +3. Enable **Developer mode** (top-right toggle). +4. Click **Load unpacked** and select the repository root (the folder containing + `manifest.json`). +5. Click the **JobInsight** icon in the toolbar and sign in with Google. +6. Open any LinkedIn job listing — the overlay appears in the top-right corner. Drag it + to reposition, or resize it from any edge. + +The packaged extension points at the deployed proxy at +`https://jobinsight-6nyq.onrender.com`, so it works out of the box after sign-in. + +## Quick start (backend proxy) + +Only needed if you want to run the proxy yourself. Commands are the scripts in +`backend/package.json`. + +```bash +cd backend +npm install +cp .env.example .env # then set OPENAI_API_KEY +npm run dev # node --watch server.js +npm test # node --test +``` -The production extension is configured to call the deployed API at `https://jobinsight-6nyq.onrender.com`. +The proxy exposes `POST /api/analyze` and `GET /api/health`. -For local backend development: +## Cost -1. Go to `backend/` -2. Run `npm install` -3. Create `.env` from `.env.example` -4. Add your `OPENAI_API_KEY` -5. Run `npm run dev` +Uses GPT-4o-mini. Each job analysis costs roughly **$0.0003–0.0005** — less than a tenth +of a cent. -## File structure +## Project structure ``` JobInsight/ ├── manifest.json # Chrome MV3 config -├── backend/ # Backend proxy for OpenAI +├── backend/ # Express proxy that holds the OpenAI key +│ └── server.js # POST /api/analyze, GET /api/health ├── background/ │ └── service-worker.js # Extension -> backend API calls ├── content/ -│ ├── linkedin-scraper.js # Page scraping + overlay logic +│ ├── linkedin-scraper.js # Page scraping, overlay, 7-day cache │ └── overlay.css # Overlay styles -├── icons/ # Extension icons -└── popup/ - ├── popup.html # Sign-in UI - └── popup.js # Google OAuth & user management +├── popup/ +│ ├── popup.html # Sign-in UI +│ └── popup.js # Google OAuth & user management +├── icons/ +└── screenshots/ ``` -## Cost +## Status + +Working and in personal use. The proxy is deployed on Render and CI runs on every push +to `main`. Built as a portfolio project; not published to the Chrome Web Store. + +## License -Uses GPT-4o-mini. Each job analysis costs roughly **$0.0003–0.0005** — less than a tenth of a cent. +MIT — see [LICENSE](LICENSE).