Communitygithub.com

OrrZwebner/conference-reimbursement

Prepara um pedido de reembolso de despesas de viagem (החזר הוצאות נסיעה) para uma universidade israelense após uma viagem de conferência ao exterior: coleta recibos da pasta de recibos da viagem e do e-mail (voo e extras, seguro de viagem, hotel, inscrição, jantar da conferência, impressão de pôster, transporte terrestre), salva cada um como PDF nomeado e constrói a planilha de despesas em hebraico da direita para a esquerda a partir do modelo de solicitação incluído, convertendo para shekels às taxas representativas do Banco de Israel (שער יציג) e compila um relatório.

O que é conference-reimbursement?

Esta skill foi projetada para automatizar o tedioso processo de solicitação de reembolso de despesas de viagem para acadêmicos israelenses que retornam de conferências no exterior. Ela atua como um assistente completo, substituindo o trabalho manual de coletar recibos, converter moedas e preencher planilhas burocráticas. A skill é usada principalmente no contexto do Claude Code, aproveitando suas capacidades de interação com o sistema de arquivos, ferramentas de busca e execução de scripts Python. O fluxo de trabalho começa com a coleta inteligente de recibos: a skill localiza automaticamente recibos físicos em uma pasta designada, baixa anexos de e-mail (como passagens aéreas e faturas de hotéis) e lê o formulário de orçamento aprovado em PDF da universidade. Em seguida, ela aplica um conjunto de regras de negócio, como determinar as taxas de câmbio corretas do Banco de Israel, decidir como alocar despesas compartilhadas (como contas de hotel ou refeições) e categorizar cada item de acordo com as linhas orçamentárias da universidade. O resultado final são duas planilhas em hebraico (direita para esquerda): um arquivo para ser enviado ao departamento financeiro e uma cópia interna para o usuário com detalhes adicionais. A skill também gera um relatório completo, verifica a consistência dos dados e pode até rascunhar o e-mail para o contato financeiro, anexando os arquivos necessários. Sua abordagem modular e baseada em instruções garante que cada solicitação seja tratada com precisão, reduzindo erros e economizando horas de trabalho.

Funciona com✓Claude Code~Codex CLI~Cursor
npx skills add https://github.com/OrrZwebner/conference-reimbursement/tree/HEAD/skills/conference-reimbursement

Perguntar na sua IA favorita

Abre um novo chat com esta habilidade de agente já pré-carregada.

Documentação

Reembolso de despesas de conferência

Produz duas planilhas a partir das mesmas linhas, com os mesmos totais, e salva cada recibo que elas citam em <pasta da conferência>/החזרים/קבלות/:

  • Arquivo ENVIADO <pasta da conferência>/החזרים/<nome completo> הוצאות.xlsx — o único arquivo que vai para o financeiro. Coluna B סעיף = categoria do formulário de orçamento; folha de recibos; bloco bancário; taxas. Sem comparação orçamento vs. real.
  • Arquivo INTERNO <pasta da conferência>/החזרים/<nome completo> הוצאות - פנימי.xlsx — a cópia local do usuário, nunca anexada ou enviada. Coluna B השירות = o que cada item foi (ex.: "קפה", "רכבת שדה–עיר"), uma coluna de categoria סעיף após הערות e a tabela de comparação orçamentária.

Ambos estão em hebraico e da direita para a esquerda; fale com o usuário em inglês. O layout vem do modelo assets/claim-template.xlsx incluído (apenas rótulos); o usuário nunca fornece uma planilha.

Perfil (nome completo e dados bancários). Leia ~/.config/conference-reimbursement/profile.json ({"full_name": "...", "bank": {"בנק": "...", "סניף": "...", "מספר חשבון": "..."}}). Se estiver faltando ou incompleto, peça os campos ausentes com a ferramenta AskUserQuestion (o usuário digita os valores como sua própria resposta) e salve o arquivo com permissões 600. Mantenha-o apenas lá — fora de qualquer repositório ou pasta de projeto. Nunca o envie, nunca imprima os dados bancários no chat ou no relatório (diga "dados bancários: do perfil") e copie-os apenas na chave bank da especificação do scratchpad.

Faça cada pergunta ao usuário por meio da ferramenta AskUserQuestion — nunca em prosa — uma decisão por pergunta, opção recomendada primeiro.

Escolha o modo

  • Modo A — solicitação completa. O formulário de orçamento aprovado em PDF, os dados bancários (perfil), a pasta de recibos e o acesso à caixa de correio estão todos disponíveis. Execute as etapas 1–7.
  • Modo B — entradas parciais. Um ou mais desses itens estão faltando. Execute as mesmas etapas e omita a parte faltante, nunca a invente:
    • usuário se recusa a fornecer dados bancários → omita bank; o script escreve células vazias rotuladas e avisa "dados bancários ausentes — preencher manualmente"; reporte;
    • sem acesso à caixa de correio → use apenas os arquivos que o usuário colocar em קבלות/; reporte que o e-mail não foi pesquisado; na etapa 7, imprima o corpo do e-mail em vez de rascunhá-lo;
    • sem formulário de orçamento → omita budget; o arquivo INTERNO é construído sem a tabela de orçamento e não há comparação com valores aprovados.

Liste cada lacuna do Modo B no relatório sob "a completar manualmente".

1. Coletar entradas (somente leitura)

  1. Orçamento aprovado. Abra o formulário de orçamento de viagem em PDF na pasta da conferência (*טופס נסיעות*). Leia você mesmo; os formulários diferem por instituição. Registre cada linha aprovada em USD (diárias אש״ל, voo טיסה, hotel, seguro, inscrição, outros) e as datas da viagem.
  2. Perfil. Carregue o nome completo e os dados bancários conforme descrito acima (pergunte apenas na primeira vez).
  3. Recibos físicos. Liste קבלות/ e leia cada imagem (converta HEIC primeiro, etapa 3). Registre data, fornecedor, valor, moeda, últimos dígitos do cartão e número de comensais.
  4. Recibos de e-mail. Pesquise na caixa de correio no período da data de reserva → data de retorno mais cerca de duas semanas e a etiqueta ou pasta de viagem do usuário. Execute as consultas por categoria juntas em uma única rodada — leia references/email-sources.md primeiro. Olhe além do que o usuário listou: encontrar despesas não notadas faz parte do trabalho; proponha cada uma encontrada.
  5. Excluir outras viagens. Abra cada transferência financeira e cada reserva de voo na janela e compare conferência, rota e datas. Registre cada exclusão para o relatório.

2. Perguntar as decisões de política

Pergunte apenas aquelas que se aplicam, uma decisão por pergunta, opção recomendada primeiro. Esses padrões vêm de uma solicitação passada; são sugestões, não regras institucionais.

  • Reserva de hotel compartilhada → apenas o próprio quarto (Recomendado) / reserva inteira.
  • Refeições compartilhadas → conta total / apenas a própria parte. Sinalize a opção escolhida para o funcionário do financeiro.
  • Taxa de câmbio → taxa representativa do Banco de Israel do dia de retorno, uma taxa por moeda (Recomendado) / a taxa de cada data do recibo.
  • Itens compartilhados (uma fatura de pôster cobrindo duas pessoas) → reivindique a parte do usuário, com uma nota.
  • Extras comprados com o voo (assento, bagagem, seguro) → dentro da linha de voo (Recomendado).

3. Salvar recibos como PDFs

  1. Anexos de e-mail. Se o conector de e-mail retornar o texto da mensagem, mas não os anexos, primeiro verifique novamente se ele pode agora buscá-los; se não, baixe por automação de navegador (abra a mensagem, clique no ícone de download do anexo e mova o arquivo de ~/Downloads). Sem automação de navegador, peça ao usuário para baixá-los ou soltá-los em קבלות/.
  2. E-mails sem anexo (confirmações de pedido) → imprimir para PDF.
  3. Nomeie cada arquivo <o que> <fornecedor> <número do documento>.pdf, em hebraico.
  4. Fotos HEIC → adicione uma cópia PDF ao lado do original, nunca modifique o original. macOS: sips -s format pdf IN.heic --out IN.pdf. Em outros lugares, use Pillow com pillow-heif se instalado, caso contrário, peça ao usuário para exportar a foto como PDF ou JPEG. Para a folha de recibos da planilha, converta também cada foto e captura de tela para um JPEG nomeado pelo nome base do recibo, no scratchpad (nunca sobrescreva o original): sips -s format jpeg -s formatOptions 70 -Z 1400 IN --out "<nome base do recibo>.jpg".
  5. Leia cada PDF salvo. Pegue o valor do documento, não do texto do e-mail. Se diferirem, use o documento e sinalize a diferença.

4. Construir a planilha

  1. Busque as taxas representativas do Banco de Israel (boi.org.il) para a data escolhida para cada moeda estrangeira usada. Coloque a data em rates.label: שער יציג בנק ישראל, <dd.mm.yyyy>. Nunca reutilize uma taxa da memória ou de uma solicitação anterior.

  2. Escreva o JSON da especificação no scratchpad. Esquema, layout e comportamento do Modo B: references/spec-format.md; exemplo de trabalho sintético: references/example-spec.json. Defina bank a partir do perfil. Deixe template de fora: o modelo incluído é o padrão.

  3. Regras de linha:

    • uma linha por recibo, ordenada por data;
    • o valor em exatamente uma chave: sua moeda original (usd, eur ou um código extra que também esteja em rates) ou ils;
    • receipt = nome(s) de arquivo base em קבלות/, vários unidos com +;
    • note explica qualquer coisa que um funcionário do financeiro possa questionar (conta compartilhada, meia fatura, item separado de uma fatura de hotel);
    • line = um nome de linha orçamentária escrito exatamente como em budget; a coluna B do arquivo ENVIADO mostra isso (apenas categoria, nunca "café" ou "jantar" — os funcionários veem categorias de aprovação), e a coluna סעיף do arquivo INTERNO e a tabela de orçamento usam isso;
    • service = uma breve descrição em hebraico do item ("קפה", "ארוחת ערב", "רכבת שדה–עיר"); mostrado apenas na coluna B do arquivo INTERNO (omitido → a categoria é mostrada);
    • refeições, incluindo o jantar da conferência → a linha de diárias;
    • cobranças de restaurante em uma fatura de hotel → sua própria linha de refeição, linha de hotel reduzida.
    • receipt_images = os JPEGs da etapa 3 (apenas fotos e capturas de tela desta viagem). Eles vão na folha קבלות, 5 por linha, cada um com uma célula de legenda segurando seu nome de arquivo base. PDFs enviados por e-mail não são incorporados; eles vão no zip na etapa 7.
  4. Execute:

    python3 -I "${CLAUDE_PLUGIN_ROOT}/skills/conference-reimbursement/scripts/build_claim.py" spec.json
    

    Uma execução escreve ambos os arquivos. Ele imprime JSON com output (ENVIADO), output_internal, total_ILS, total_USD e warnings. Corrija cada aviso sobre linhas orçamentárias; carregue os avisos do Modo B para o relatório. output_internal assume como padrão o caminho ENVIADO com - פנימי antes de .xlsx; defina-o na especificação apenas para colocar a cópia local em outro lugar.

  5. O script se recusa a sobrescrever qualquer saída a menos que "overwrite": true. Nunca defina isso em um arquivo que o usuário editou manualmente; escreva um novo nome ou pergunte.

5. Verificar

Concluído significa executado e verificado. Leia references/pitfalls.md primeiro.

  1. Execute as verificações:

    python3 -I "${CLAUDE_PLUGIN_ROOT}/skills/conference-reimbursement/scripts/check_claim.py" spec.json
    
    • total / total_internal: o total Python do script é igual ao célula סה״כ בש״ח de cada arquivo após recálculo do LibreOffice (para 0,01 ₪), então ambos os arquivos carregam o mesmo total;
    • sent_no_budget: o arquivo ENVIADO não contém tabela de comparação de orçamento;
    • receipts: cada arquivo citado existe em קבלות/;
    • budget: cada linha da linha é uma linha de orçamento e o total real da tabela de orçamento do arquivo INTERNO é igual a total_ILS / taxa USD.

    Reporte uma verificação not_run como não executada, nunca como aprovada.

  2. Auditoria independente: inicie um subagente apenas com a planilha ENVIADA e a pasta de recibos — não suas conclusões. Peça a ele para verificar o valor, moeda, data e arquivo de cada linha em relação ao recibo e listar qualquer coisa que um funcionário do financeiro possa questionar. Corrija erros reais; reporte o resto.

6. Relatório

Nesta ordem:

  1. Ambos os caminhos (ENVIADO, para anexar; INTERNO, apenas local), contagem de linhas, total ₪ e ≈ USD versus o total aprovado.
  2. Recibos adicionados (e quais foram encontrados pesquisando além da lista do usuário).
  3. Taxas usadas, com fonte e data.
  4. Linhas acima do orçamento, como uma tabela: linha, aprovado, real, diferença.
  5. Discrepâncias entre fontes (e-mail versus documento).
  6. Exclusões (itens pertencentes a outras viagens).
  7. Sinalizações do funcionário (de references/pitfalls.md).
  8. A completar manualmente (lacunas do Modo B, avisos do script).
  9. Decisões tomadas sem perguntar.

7. Rascunhar o e-mail para o contato financeiro

Leia references/email-draft.md primeiro; siga-o em ordem. Use e anexe apenas o arquivo ENVIADO (output, <nome completo> הוצאות.xlsx); nunca anexe, carregue ou cite o arquivo INTERNO - פנימי — email_summary.py recusa isso. Em resumo:

  1. Leia o tópico de solicitação anterior do usuário com o contato financeiro (e-mails enviados, cerca de dois anos atrás, com respostas incluídas) e copie seu estilo e padrão de assunto.
  2. Pergunte: dados bancários dentro ou fora; linhas de orçamento ou taxa (padrão: nenhum); BCC um colega de viagem (padrão: não; nunca invente um endereço).
  3. scripts/zip_ereceipts.py spec.json → קבלות אלקטרוניות.zip dos PDFs de recibos eletrônicos (nomes UTF-8; nunca o comando zip do macOS). Fotos e capturas de tela estão na folha קבלות em vez disso.
  4. scripts/email_summary.py spec.json ... → o corpo HTML RTL ("היי ," / "מה שלומך? :)" ... "תודה רבה!"), a tabela de resumo com uma coluna קבלה dizendo onde cada recibo está e os dados bancários lidos da planilha.
  5. Verifique se seu total_ILS é igual ao do build; mencione qualquer rounding_diff.
  6. Gmail create_draft com htmlBody primeiro. Em seguida, anexe a planilha ENVIADA e o zip por meio do Claude no Chrome (file_upload na entrada de arquivo de composição do rascunho) e confirme ambos os chips — o conector aceita anexos apenas como base64 na chamada, e update_draft os descarta. Nunca envie. Dê ao usuário o link do rascunho.

Fórmulas

  • Linha: ILS_i = valor_i × taxa[moeda_i], ou o próprio valor em ₪.
  • Total: T = Σ ILS_i; em dólares T / taxa[USD].
  • Por linha de orçamento ℓ (arquivo INTERNO): real_ℓ = Σ_{linha_i = ℓ} ILS_i / taxa[USD]; dif_ℓ = aprovado_ℓ − real_ℓ, negativo significa acima do orçamento. Σ_ℓ real_ℓ = T / taxa[USD] quando cada linha da linha está no orçamento.

Exemplo: taxas USD 4,00, EUR 4,50; inscrição $500, hotel €600, táxi ₪200 → 2.000 + 2.700 + 200 = 4.900 ₪ = $1.225.

Julgamentos

  • A própria fatura do hotel prevalece sobre a confirmação do site de reservas (é o documento fiscal).
  • Os dados bancários vêm do perfil local para a chave bank da especificação; o script os escreve por rótulo. Peça-os apenas por meio de AskUserQuestion, nunca em prosa, e nunca os repita.
  • Um reembolso parcial anterior que pertence a esta viagem → marque essas linhas como já reivindicadas.
  • As regras da instituição do usuário decidem questões de política; pergunte em vez de afirmar uma regra.

Referências

  • references/email-sources.md — consultas de caixa de correio por categoria e o que verificar (etapa 1.4).
  • references/spec-format.md — chaves da especificação, layout de ambos os arquivos, saída do script, comportamento do Modo B (etapa 4).
  • references/example-spec.json — especificação completa sintética (etapa 4).
  • references/pitfalls.md — falhas vistas antes e a lista de verificação de sinalizações do funcionário (etapas 5–6).
  • references/email-draft.md — o rascunho do e-mail: tópico anterior, redação, anexos (etapa 7).

Habilidades Relacionadas