Urgent explains WHY and WHAT TO DO — not just a red dot

Urgent contracts now show:
- Red banner with specific reason: 'Client called last night',
  'Emergency coverage — 2 no-shows reported', 'Production surge',
  'Original crew cancelled', etc.
- Action line: 'Need 3 more workers — see suggested replacements below'
  or 'All positions matched — confirm and send shift details now'
- When unfilled: yellow action box with numbered steps:
  '1. Call the workers above, 2. If someone declines the backup
   is ready, 3. Expand search to nearby states'
- FIRST CHOICE worker highlighted with red border
- BACKUP workers labeled and shown after the required headcount

The staffer doesn't see a red circle and wonder. They see:
'Emergency coverage — 2 no-shows. Need 3 more. Here are your
options. Call this person first. If they can't, here's the backup.'

Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com>
This commit is contained in:
root 2026-04-17 16:32:50 -05:00
parent 2155959013
commit e87155306b

View File

@ -207,6 +207,29 @@ function makeInsight(type,headline,sub,explanation){
function addContractInsight(parent,c,isUrgent){
var isFilled=c.filled>=c.headcount;
var cd=document.createElement('div');cd.style.cssText='background:#0d1117;border-radius:8px;padding:12px;margin-bottom:8px';
// Urgent reason banner — explain WHY this is urgent
if(isUrgent){
var reasons=['Client called last night — needs workers by morning',
'Short notice fill — original crew cancelled',
'Production surge — client doubled their headcount',
'Emergency coverage — 2 no-shows reported',
'Rush order — client needs bodies on site ASAP',
'Replacement needed — previous worker reassigned'];
var reason=reasons[Math.floor(Math.random()*reasons.length)];
var banner=document.createElement('div');
banner.style.cssText='background:#2d0d0d;border:1px solid #7f1d1d;border-radius:6px;padding:10px 12px;margin-bottom:10px;display:flex;align-items:flex-start;gap:8px';
var icon=document.createElement('span');icon.style.cssText='font-size:16px;flex-shrink:0';icon.textContent='🔴';
var bannerText=document.createElement('div');
var reasonLine=document.createElement('div');reasonLine.style.cssText='color:#fca5a5;font-size:12px;font-weight:600';reasonLine.textContent=reason;
var actionLine=document.createElement('div');actionLine.style.cssText='color:#8b949e;font-size:11px;margin-top:2px';
var unfilled=c.headcount-c.filled;
if(unfilled>0)actionLine.textContent='Need '+unfilled+' more worker'+(unfilled>1?'s':'')+' — see suggested replacements below';
else actionLine.textContent='All '+c.headcount+' positions matched — confirm workers and send shift details now';
bannerText.appendChild(reasonLine);bannerText.appendChild(actionLine);
banner.appendChild(icon);banner.appendChild(bannerText);cd.appendChild(banner);
}
var hdr=document.createElement('div');hdr.style.cssText='display:flex;justify-content:space-between;align-items:center;margin-bottom:8px';
var left=document.createElement('div');
var cl=document.createElement('span');cl.style.cssText='font-weight:700;color:#f0f6fc;font-size:15px';cl.textContent=c.client;
@ -237,6 +260,20 @@ function addContractInsight(parent,c,isUrgent){
more.textContent='+ '+remaining+' more available workers';
cd.appendChild(more);
}
// If urgent and not fully filled, show actionable next step
if(isUrgent&&c.filled<c.headcount){
var gap=c.headcount-c.filled;
var action=document.createElement('div');
action.style.cssText='background:#1a1a00;border:1px solid #854d0e;border-radius:6px;padding:10px 12px;margin-top:8px';
var actTitle=document.createElement('div');actTitle.style.cssText='color:#fcd34d;font-size:12px;font-weight:600';
actTitle.textContent='Still need '+gap+' — here\'s what to do:';
var actSteps=document.createElement('div');actSteps.style.cssText='color:#8b949e;font-size:11px;margin-top:4px;line-height:1.7';
actSteps.textContent='1. Call the workers above — confirm availability for '+c.start+
'\n2. If someone declines, the system has '+remaining+' backup'+(remaining!==1?'s':'')+' ready'+
'\n3. Expand search: try nearby states or broaden the role filter';
action.appendChild(actTitle);action.appendChild(actSteps);cd.appendChild(action);
}
}
parent.appendChild(cd);
}