/* ===== Preço e pedidos — etapa 2 da operação (13/11) ================
   P3 do plano. Fecha o buraco que o Mapa mental mostra: as etapas 1 e
   2 rodam inteiras no WhatsApp e não entram no sistema.

   DECISÃO DELE (13/11): "Vendedor manda uma mensagem via WhatsApp para
   o Paulo com o pedido". Ou seja, o vendedor NÃO digita em sistema
   nenhum. Então a entrada aqui é a mensagem como ela chega, colada.
   Quando (e se) a integração oficial com o WhatsApp for ligada, só a
   porta de entrada muda: o leitor e o resto da tela continuam iguais.

   O QUE ESTA TELA FAZ
   1. Preço do dia: ele define, vendo o custo e a cobertura do estoque,
      e o sistema escreve a mensagem pronta para ele mandar.
   2. Pedido que chega: cola a mensagem, o leitor extrai os campos,
      confere contra o preço do dia e contra o estoque, e vira pedido.

   REGRA DE HONESTIDADE
   O leitor erra. Tudo que ele não entendeu aparece em branco e pede
   confirmação — nunca é preenchido por chute. O custo do estoque é
   dado simulado e editável: o sistema não sabe quanto ele pagou.
   ================================================================== */

const PP_MARGEM_ALVO = 0.12;   /* R$/L — ponto de partida da sugestão */
const PP_NUM  = new RegExp('[0-9][0-9.,]*', 'g');
const PP_ACEN = new RegExp('['+String.fromCharCode(768)+'-'+String.fromCharCode(879)+']','g');
const ppSemAcento = (t)=>String(t||'').normalize('NFD').replace(PP_ACEN,'').toLowerCase();

const PP_EXEMPLOS = [
  'Boa tarde Paulo, o Posto Avenida de Bebedouro quer 8 mil de alcool pra amanha cedo, fechei a 3,85',
  'paulo, irmaos colina 15000 etanol, eles mandam o caminhao buscar na quinta',
  'fechei com a rede barretos 25 mil de etanol entrega amanha 3,55 o litro',
];

/* palavras que aparecem em meio posto do Brasil: nao servem para identificar */
const PP_GENERICO = ['posto','auto','rede','distribuidora','comercio','combustiveis','ltda'];

/* So etanol. As chaves cobrem como o vendedor escreve na mensagem. */
const PP_PRODS = [
  {p:'Etanol', chaves:['etanol','alcool','hidratado','anidro']},
];

/* ---- O leitor --------------------------------------------------- */
function ppLer(texto, clients){
  const n = ppSemAcento(texto);
  const r = {cliente:null, produto:null, litros:null, quando:null, modo:null, preco:null, naoEntendeu:[]};

  /* cliente: o nome cadastrado que aparece na mensagem, o mais longo */
  let melhor = null, melhorPonto = 0;
  clients.forEach(c=>{
    const alvo = ppSemAcento(c.name);
    const partes = alvo.split(' ').filter(x=>x.length>3 && PP_GENERICO.indexOf(x)<0);
    const casou = partes.filter(x=>n.includes(x));
    /* duas palavras proprias batendo, ou uma longa o bastante para nao ser coincidencia */
    const ponto = n.includes(alvo) ? 99
                : casou.length>=2 ? casou.length
                : (casou.length===1 && casou[0].length>=6) ? 1 : 0;
    if(ponto > melhorPonto){ melhorPonto = ponto; melhor = c; }
  });
  r.cliente = melhor;

  /* produto */
  const pr = PP_PRODS.find(x=>x.chaves.some(k=>n.includes(k)));
  r.produto = pr ? pr.p : null;

  /* preço: número com duas casas, entre 1 e 20 */
  const precos = (n.match(PP_NUM)||[]).map(t=>t.replace('.',',')).filter(t=>{
    const m = t.match(new RegExp('^[0-9]{1,2},[0-9]{2}$')); return !!m;
  }).map(t=>parseFloat(t.replace(',','.')));
  r.preco = precos.length ? precos[0] : null;

  /* litros: número grande, ou número seguido de "mil" */
  let litros = null;
  const porMil = n.match(new RegExp('([0-9]+)[ ]*mil'));
  if(porMil) litros = parseInt(porMil[1],10)*1000;
  if(litros===null){
    (n.match(PP_NUM)||[]).forEach(t=>{
      const limpo = t.replace(new RegExp('[.,]','g'),'');
      const v = parseInt(limpo,10);
      if(v>=1000 && v<=60000 && t.indexOf(',')<0 && (litros===null||v>litros)) litros = v;
    });
  }
  r.litros = litros;

  /* quando */
  if(n.includes('depois de amanha')) r.quando='Depois de amanhã';
  else if(n.includes('amanha')) r.quando = n.includes('cedo')?'Amanhã, cedo':'Amanhã';
  else if(n.includes('hoje')) r.quando='Hoje';
  else {
    const dias=[['segunda','Segunda'],['terca','Terça'],['quarta','Quarta'],['quinta','Quinta'],['sexta','Sexta'],['sabado','Sábado']];
    const d = dias.find(x=>n.includes(x[0]));
    r.quando = d ? d[1] : null;
  }

  /* retira x entrega */
  if(['buscar','retira','vem pegar','caminhao deles','mandam o caminhao','manda o caminhao'].some(k=>n.includes(k))) r.modo='retira';
  else if(['entrega','entregar','levar'].some(k=>n.includes(k))) r.modo='entrega';
  else if(melhor) r.modo = melhor.modo || 'entrega';

  if(!r.cliente) r.naoEntendeu.push('qual cliente');
  if(!r.produto) r.naoEntendeu.push('qual produto');
  if(!r.litros)  r.naoEntendeu.push('quantos litros');
  if(!r.quando)  r.naoEntendeu.push('para quando');
  if(!r.preco)   r.naoEntendeu.push('por quanto fechou');
  return r;
}

/* ---- Preço do dia: dois valores (14/11) -------------------------
   Decisao dele: "se o cliente vai retirar e um preco, se quer que
   entregue e outro". Entao o Paulo abre o dia com DOIS numeros, e a
   tela do vendedor le daqui. O resto do sistema nao inventa preco. */
function PpPreco({precoDia, setPrecoDia, sellers, notify, clients, bases}){
  const [aberto,setAberto]=useState(false);
  const est = prEstoque();
  const mudar=(campo,v)=>{
    const num = parseFloat(String(v).replace(',','.'));
    setPrecoDia({...precoDia, [campo]: isNaN(num)?null:num, fechadoEm:null});
  };
  const txt=(v)=> v==null?'':String(v.toFixed(2)).replace('.',',');
  const pronto = precoDia.retira!=null && precoDia.entrega!=null;
  const frete = pronto ? precoDia.entrega - precoDia.retira : null;

  /* Frete real de cada cliente que RECEBE em casa, com o mesmo cálculo da
     Carteira. O preço de entrega e um so para todos; o custo, nao. */
  const entregas = pronto
    ? (clients||[]).filter(c=>(c.modo||'entrega')==='entrega')
        .map(c=>{ const f=prFreteCliente(c,bases,precoDia.custoKm); return f?{c, f, piso: precoDia.retira+f.porL}:null; })
        .filter(Boolean)
        .sort((a,b)=>b.piso-a.piso)
    : [];
  const noVermelho = entregas.filter(x=>precoDia.entrega < x.piso - 0.0005);
  const caro = entregas.slice(0,3);

  const nl = String.fromCharCode(10);
  const recado = pronto
    ? `Preço de hoje — etanol${nl}Cliente que retira: ${brl3(precoDia.retira)}/L${nl}`
      + `Nós entregamos: ${brl3(precoDia.entrega)}/L${nl}`
      + `A margem de negociação de cada cliente já está no sistema. Fora dela, me chame.`
    : '';

  const fecharDia=()=>{
    setPrecoDia({...precoDia, fechadoEm: Date.now()});
    setAberto(true);
    notify && notify(`Preço de hoje aberto para ${sellers.length} ${sellers.length===1?'vendedor':'vendedores'}`);
  };

  return <section className="panel pp-painel">
    <div className="panel-title"><div><h2>Preço do dia</h2>
      <p>Dois valores: quem vem buscar paga um, quem recebe em casa paga outro. É o que os vendedores veem.</p></div></div>

    <div className="pp-dois">
      <label className="field pp-caixa"><span className="pp-cx-rot">O cliente retira</span>
        <input className="pp-in forte" inputMode="decimal" placeholder="3,70"
          value={txt(precoDia.retira)} onChange={e=>mudar('retira',e.target.value)} aria-label="Preço para quem retira"/>
        <small>só o produto, ele busca com o caminhão dele</small></label>

      <label className="field pp-caixa"><span className="pp-cx-rot">Nós entregamos</span>
        <input className="pp-in forte" inputMode="decimal" placeholder="3,92"
          value={txt(precoDia.entrega)} onChange={e=>mudar('entrega',e.target.value)} aria-label="Preço para quem recebe"/>
        <small>produto mais o frete até o posto</small></label>

      <div className="pp-caixa pp-calc">
        <span className="pp-cx-rot">Diferença</span>
        <b>{frete!=null?brl3(frete)+'/L':'—'}</b>
        <small>{frete!=null?`${brl(Math.round(frete*50000))} num caminhão cheio de 50.000 L`:'preencha os dois valores'}</small>
      </div>
    </div>

    {pronto && entregas.length>0 && <div className="pp-frete">
      <p className="pp-rec-tit">O frete não é igual para todo cliente</p>
      {noVermelho.length>0
        ? <p className="rs bad pp-aviso pp-fr-l">{noVermelho.length} {noVermelho.length===1?'cliente fica':'clientes ficam'} no prejuízo com {brl3(precoDia.entrega)}: {noVermelho.map(x=>x.c.name).join(', ')}. Entregar para {noVermelho.length===1?'ele':'eles'} custa mais do que a diferença que você cobrou.</p>
        : <p className="rs good pp-aviso pp-fr-l">Com {brl3(precoDia.entrega)}, a entrega cobre o frete de todos os {entregas.length} clientes que recebem em casa.</p>}
      <ul className="pp-fr-lista">{caro.map(x=><li key={x.c.id}>
        <b>{x.c.name}</b> <em>{x.f.km} km · {fmt(x.f.carga)} L por viagem</em>
        <span>frete {brl3(x.f.porL)}/L · piso {brl3(x.piso)}</span></li>)}</ul>
      <label className="field pp-ck"><span>Custo por km rodado — a métrica do frete</span>
        <input className="pp-in" inputMode="decimal" placeholder={String(CUSTO_KM.toFixed(2)).replace('.',',')}
          value={precoDia.custoKm!=null?String(precoDia.custoKm.toFixed(2)).replace('.',','):''}
          onChange={e=>{const n=parseFloat(String(e.target.value).replace(',','.'));
            setPrecoDia({...precoDia, custoKm: isNaN(n)?null:n});}}
          aria-label="Custo por km"/></label>
      <p className="calc-note">Piso = preço de quem retira mais o frete até aquele posto. O sistema não deixa o vendedor negociar abaixo disso.
        <b> Atenção:</b> o cálculo acima (ida e volta × custo por km ÷ litros da viagem) é <b>suposição nossa</b>.
        Falta perguntar ao Paulo qual métrica ele usa para cobrar frete — por isso o campo fica aberto para edição.</p>
    </div>}

    {frete!=null && frete<=0 &&
      <p className="rs bad pp-aviso">A entrega está saindo igual ou mais barata que a retirada. Confira: o frete não está sendo cobrado.</p>}
    {est && est.dias<3 &&
      <p className="rs bad pp-aviso">Só {Math.floor(est.dias)} dias de estoque. Hoje ninguém pode negociar preço — o sistema já vai barrar.</p>}
    {est && est.dias>10 &&
      <p className="rs neutral pp-aviso">{Math.floor(est.dias)} dias de estoque: os vendedores ganham a folga máxima de negociação hoje.</p>}

    <div className="pp-acoes">
      <button className="primary" disabled={!pronto} onClick={fecharDia}>Abrir o dia com esse preço</button>
      {precoDia.fechadoEm && <span className="rs good">Aberto para {sellers.length} {sellers.length===1?'vendedor':'vendedores'}.</span>}
    </div>

    {aberto && pronto && <div className="pp-recado">
      <p className="pp-rec-tit">Mensagem pronta, se ele quiser avisar por WhatsApp também</p>
      <pre className="pp-pre">{recado}</pre>
      <p className="calc-note">Não é obrigatório mandar: o preço já aparece na tela de cada vendedor assim que o dia é aberto.</p>
    </div>}

    <p className="calc-note">A margem de negociação de cada cliente sai sozinha do estoque e do histórico dele — está na tela do vendedor, cliente por cliente. As regras são hipótese, para rever com o Paulo.</p>
  </section>;
}

/* ---- Pedido que chega ------------------------------------------- */
function PpPedido({clients, sellers, precoDia, orders, setOrders, notify, bases}){
  const nomeVendedor=(c)=>{ const v=sellers.find(x=>x.id===c.sellerId); return v?v.name:'sem vendedor no cadastro'; };
  const [txt,setTxt]=useState('');
  const [lido,setLido]=useState(null);
  const ler=(t)=>{ setTxt(t); setLido(t.trim()?ppLer(t,clients):null); };

  const estoqueDo=(prod)=>initialEstoque.find(e=>e.prod===prod);

  const alertas=[];
  if(lido){
    /* o preco cheio depende de o cliente retirar ou receber */
    const neg = prNegociacao(lido.cliente, precoDia, bases);
    const pd = neg ? neg.cheio : null;
    if(lido.preco!=null && neg){
      const cl = prClassificar(lido.preco, neg);
      if(cl.k==='negociado') alertas.push({t:'warn', m:`Fechou a ${brl3(lido.preco)}/L — ${cl.txt}`});
      if(cl.k==='excecao') alertas.push({t:'bad', m:`Fechou a ${brl3(lido.preco)}/L — ${cl.txt} Diferença de ${brl(Math.round((pd-lido.preco)*(lido.litros||0)))} neste pedido.`});
    }
    /* sem estoque lancado (visualizacao real) nao da para conferir volume */
    const e = (!REAL && lido.produto)?estoqueDo(lido.produto):null;
    if(e && lido.litros){
      const podeVender = esVendavel(e);
      if(lido.litros > podeVender)
        alertas.push({t:'bad', m:`Pediu ${fmt(lido.litros)} L de ${e.prod} e o estoque só libera ${fmt(podeVender)} L sem furar a reserva.`});
      else if(lido.litros > e.litros*0.5)
        alertas.push({t:'warn', m:`Este pedido leva mais da metade do ${e.prod} que está no tanque.`});
    }
    if(lido.modo==='retira')
      alertas.push({t:'neutral', m:'O cliente retira: não entra na programação dos caminhões, mas sai do estoque.'});
  }

  const completo = lido && lido.cliente && lido.produto && lido.litros;
  const virar=()=>{
    const id = '#PED-' + (2900 + orders.length);
    setOrders(cur=>[{id, client:lido.cliente.name, city:lido.cliente.city, volume:lido.litros,
      window: lido.quando||'A combinar', deadlineH: (lido.quando||'').indexOf('Hoje')===0?4:20,
      product: lido.produto, priority: (lido.quando||'').indexOf('Hoje')===0?'Alta':'Normal'}, ...cur]);
    notify&&notify(`${id} entrou na fila de logística`);
    setTxt(''); setLido(null);
  };

  const campos = lido ? [
    ['Cliente', lido.cliente?lido.cliente.name:null, lido.cliente?`${lido.cliente.city} · vendedor(a) ${nomeVendedor(lido.cliente)}`:''],
    ['Produto', lido.produto, (lido.produto&&lido.cliente&&prNegociacao(lido.cliente,precoDia,bases))?`preço de hoje ${brl3(prNegociacao(lido.cliente,precoDia,bases).cheio)}/L`:''],
    ['Volume', lido.litros?`${fmt(lido.litros)} L`:null, ''],
    ['Quando', lido.quando, ''],
    ['Entrega', lido.modo?(lido.modo==='retira'?'O cliente retira':'Nós entregamos'):null, lido.modo&&lido.cliente&&!lido.cliente.modo?'veio do cadastro':''],
    ['Preço fechado', lido.preco!=null?`${brl3(lido.preco)}/L`:null, ''],
  ] : [];

  return <section className="panel pp-painel">
    <div className="panel-title"><div><h2>Pedido que chegou no WhatsApp</h2>
      <p>Cole a mensagem como o vendedor mandou. O leitor extrai os campos e confere contra o preço de hoje e o estoque.</p></div></div>

    <div className="pp-grid">
      <div>
        <label className="field"><span className="sr">Mensagem do vendedor</span>
          <textarea className="pp-txt" rows="4" value={txt} onChange={e=>ler(e.target.value)}
            placeholder="Cole aqui a mensagem que chegou..."/></label>
        <p className="pp-ex-tit">Ou use um exemplo real de como a mensagem chega:</p>
        <div className="pp-ex">{PP_EXEMPLOS.map((m,i)=>
          <button key={i} className="secondary pp-ex-btn" onClick={()=>ler(m)}>{m}</button>)}</div>
      </div>

      <div className="pp-saida">
        {!lido && <p className="mm-det pp-vazio">O que o leitor entender aparece aqui, campo por campo.</p>}
        {lido && <>
          <dl className="pp-campos">{campos.map(([r,v,sub])=>
            <div key={r} className={v?'':'falhou'}>
              <dt>{r}</dt>
              <dd>{v||<span className="pp-nao">não entendeu</span>}{sub&&<small>{sub}</small>}</dd>
            </div>)}
          </dl>
          {lido.naoEntendeu.length>0 &&
            <p className="rs warn pp-aviso">Faltou: {lido.naoEntendeu.join(', ')}. Confirme com o vendedor antes de fechar.</p>}
          {alertas.map((a,i)=><p key={i} className={`rs ${a.t} pp-aviso`}>{a.m}</p>)}
          <div className="pp-acoes">
            <button className="primary" disabled={!completo} onClick={virar}>Virar pedido</button>
            <button className="secondary" onClick={()=>{setTxt('');setLido(null);}}>Limpar</button>
          </div>
          {!completo && <p className="calc-note">Sem cliente, produto e volume o pedido não entra — o sistema não chuta o que faltou.</p>}
        </>}
      </div>
    </div>
  </section>;
}

/* ---- A tela ----------------------------------------------------- */
function PrecoPedido({clients, sellers, orders, setOrders, notify, precoDia, setPrecoDia, bases}){
  return <div className="content pp-content">
    <div className="page-heading"><div>
      <p>ETAPA 2 DA OPERAÇÃO</p>
      <h1>Preço e pedidos</h1>
      <span>Onde o preço do dia é fechado e o pedido do vendedor entra no sistema.</span>
    </div></div>

    <section className="ai-tip pp-tip">
      <span>✦</span>
      <div>
        <strong>Esta é a parte que hoje roda só no WhatsApp</strong>
        <p>O vendedor continua mandando mensagem — ele não precisa aprender sistema nenhum. O que muda é o que acontece depois que a mensagem chega.</p>
      </div>
    </section>

    <PpPreco precoDia={precoDia} setPrecoDia={setPrecoDia} sellers={sellers} notify={notify} clients={clients} bases={bases}/>
    <PpPedido clients={clients} sellers={sellers} precoDia={precoDia} orders={orders} setOrders={setOrders} notify={notify} bases={bases}/>

    <p className="calc-note">
      Dados de demonstração. O custo no estoque é simulado e editável — o sistema não sabe quanto foi pago.
      O leitor da mensagem acerta os casos comuns e erra os incomuns: por isso ele mostra o que não entendeu em vez de preencher.
    </p>
  </div>;
}

/* Antes de Pedidos e viagens: a etapa 2 vem antes da 3 */
(function(){
  const i = navItems.findIndex(x=>x.id==='logistica');
  navItems.splice(i<0?1:i, 0,
    {id:'precopedido', label:'Preço e pedidos', short:'Preço', icon:'◪', tag:'novo'});
})();
