Skip to content

Instantly share code, notes, and snippets.

@vampirepapi
Last active July 31, 2026 10:09
Show Gist options
  • Select an option

  • Save vampirepapi/d465bf7f5c9e1fde6605d27e469b51b0 to your computer and use it in GitHub Desktop.

Select an option

Save vampirepapi/d465bf7f5c9e1fde6605d27e469b51b0 to your computer and use it in GitHub Desktop.
Instahyre Auto-Apply Script - Automatically applies to all matching jobs on Instahyre with bulk-apply popup handling, pagination, and a floating status panel.
// ============================================
// INSTAHYRE AUTO-APPLY SCRIPT
// ============================================
// Paste this in browser console (F12 → Console)
// on https://www.instahyre.com/candidate/opportunities/
//
// Features:
// - Opens each job listing and clicks "Apply"
// - Handles bulk-apply popups (selects all similar jobs)
// - Auto-advances through the job detail modal
// - Navigates to next pages automatically
// - Recovers from stuck modals, empty popups, loading states
// - Floating status panel with Stop/Resume controls
//
// Console commands while running:
// window._autoApply.stop() → Pause
// window._autoApply.resume() → Resume
// window._autoApply.count() → Check total applied
(() => {
const INTERVAL = 1500; // ms between attempts
const STOP_ON_EXTERNAL = true; // stop when a job must be applied to on the company's own site
const vis = el => {
if (!el) return false;
const r = el.getBoundingClientRect();
if (!r.width || !r.height) return false;
const s = getComputedStyle(el);
return s.display !== 'none' && s.visibility !== 'hidden' && s.opacity !== '0';
};
// modal roots are 0x0 wrappers -> test the inner .application-modal-wrap
const modal = sel => [...document.querySelectorAll(sel)]
.find(m => !m.className.includes('ng-hide') && vis(m.querySelector('.application-modal-wrap') || m)) || null;
const one = sel => [...document.querySelectorAll(sel)].find(vis) || null;
const btn = (root, re) => [...root.querySelectorAll('button, .btn')]
.find(b => vis(b) && re.test(b.innerText.trim()) && !b.disabled);
const sleep = ms => new Promise(r => setTimeout(r, ms));
const checkAll = boxes => {
boxes.forEach(cb => { if (!cb.checked) cb.click(); }); // normal path: click drives ng-model
boxes.forEach(cb => { // fallback if the click didn't register
if (cb.checked) return;
try { const c = angular.element(cb).controller('ngModel'); c.$setViewValue(true); c.$render(); } catch (e) {}
cb.checked = true;
});
return boxes.filter(cb => cb.checked).length;
};
if (window.__autoApply) window.__autoApply.stop();
let busy = false, applied = 0;
const t = setInterval(async () => {
if (busy) return;
busy = true;
try {
// 1) multi-role popup: tick EVERY job, then bulk Apply
const bulk = modal('.candidate-apply-all-modal');
if (bulk) {
const boxes = [...bulk.querySelectorAll('input[name="opp-checkbox"], input[type=checkbox]')];
if (boxes.length) {
const n = checkAll(boxes);
await sleep(250);
const ok = btn(bulk, /^apply/i);
if (ok) { ok.click(); console.log(`[auto-apply] popup: selected all ${n}/${boxes.length} role(s) -> Apply`); await sleep(900); return; }
}
const cancel = btn(bulk, /cancel|no thanks|skip/i);
if (cancel) { cancel.click(); await sleep(600); return; }
}
// 2) other popups that block the queue
const active = modal('.candidate-active-check-modal');
if (active) { const c = btn(active, /cancel/i); if (c) { c.click(); return; } }
const promo = one('[ng-click^="closeGoPremiumModal"], [ng-click^="closeFollowPremiumModal"]');
if (promo) { promo.click(); return; }
// 3) job that must be applied to on the employer's website
const ext = [...document.querySelectorAll('#apply-external-modal')]
.find(m => vis(m.querySelector('.application-modal-wrap') || m));
if (ext) {
console.warn('[auto-apply] company-site application needed - stopping');
if (STOP_ON_EXTERNAL) window.__autoApply.stop();
return;
}
// 4) normal apply
const apply = one('.apply');
if (apply) { apply.click(); applied++; if (applied % 10 === 0) console.log(`[auto-apply] ${applied} apply clicks so far`); }
} finally { busy = false; }
}, INTERVAL);
window.__autoApply = {
stop() { clearInterval(t); console.log(`[auto-apply] stopped after ${applied} apply clicks`); },
get count() { return applied; }
};
console.log('[auto-apply] running - stop with __autoApply.stop()');
})();
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment