Jinni

Uma ferramenta para fornecer contexto de projeto a Grandes Modelos de Linguagem, filtrando e concatenando arquivos relevantes de forma inteligente.

Documentação

Jinni Banner

Jinni: Traga Seu Projeto Para o Contexto

Jinni: Bring Your Project Into Context MCP server

Jinni é uma ferramenta para fornecer eficientemente a Modelos de Linguagem de Grande Porte (LLMs) o contexto dos seus projetos. Ela oferece uma visão consolidada dos arquivos relevantes do projeto, superando as limitações e ineficiências de ler arquivos um por um. O conteúdo de cada arquivo é precedido por um cabeçalho simples indicando seu caminho:

```path=src/app.py
print("hello")

A filosofia por trás desta ferramenta é que as janelas de contexto dos LLMs são grandes, os modelos são inteligentes, e ver diretamente seu projeto é o que melhor prepara o modelo para ajudar com qualquer coisa que você apresentar.

Há um servidor MCP (Model Context Protocol) para integração com ferramentas de IA e um utilitário de linha de comando (CLI) para uso manual que copia o contexto do projeto para a área de transferência, pronto para colar onde precisar.

Estas ferramentas têm opiniões sobre o que conta como contexto relevante do projeto para funcionar bem imediatamente na maioria dos casos de uso, excluindo automaticamente:

* Arquivos binários
* Dotfiles e diretórios ocultos
* Convenções de nomenclatura comuns para logs, diretórios de build, arquivos temporários, etc.

Inclusões/exclusões são personalizáveis com granularidade completa, se necessário, usando .contextfiles – isso funciona como .gitignore, exceto que define inclusões. Arquivos .gitignore também são respeitados automaticamente, mas quaisquer regras em .contextfiles têm prioridade.

O servidor MCP pode fornecer tanto ou tão pouco do projeto quanto desejado. Por padrão, o escopo é o projeto inteiro, mas o modelo pode solicitar módulos específicos / padrões correspondentes / etc.

Início Rápido com MCP

Arquivo de configuração do servidor MCP para Cursor / Roo / Claude Desktop / cliente de sua escolha:

{
    "mcpServers": {
        "jinni": {
            "command": "uvx",
            "args": ["jinni-server"]
        }
    }
}

Você pode opcionalmente restringir o servidor para ler apenas dentro de uma árvore por segurança, caso seu LLM saia do controle: adicione "--root", "/absolute/path/" à lista de args.

Instale o uv se ele não estiver no seu sistema: https://docs.astral.sh/uv/getting-started/installation/

Recarregue seu IDE e agora você pode pedir ao agente para ler o contexto.

Se você quiser restringir isso a módulos/caminhos específicos, basta pedir - ex.: "Leia o contexto para testes".

Em ação com o Cursor:

Usage Example

Nota Para Usuários do Cursor

O Cursor pode silenciosamente descartar contexto maior que o máximo permitido, então se você tem um projeto considerável e o agente age como se a chamada de ferramenta nunca tivesse acontecido, tente reduzir o que você está trazendo ("leia o contexto para xyz")

Componentes

  1. jinni Servidor MCP:

    • Integra-se com clientes MCP como Cursor, Cline, Roo, Claude Desktop, etc.
    • Expõe uma ferramenta read_context que retorna uma string concatenada dos conteúdos dos arquivos relevantes de um diretório de projeto especificado.
  2. jinni CLI:

    • Uma ferramenta de linha de comando para gerar manualmente o despejo de contexto do projeto.
    • Útil para alimentar contexto a LLMs via copiar-colar ou entrada de arquivo. Ou canalize a saída para onde precisar.

Recursos

  • Coleta Eficiente de Contexto: Lê e concatena arquivos relevantes do projeto em uma única operação.
  • Filtragem Inteligente (Inclusão no Estilo Gitignore):
    • Usa um sistema baseado na sintaxe .gitignore (biblioteca pathspec's gitwildmatch).
    • Carrega automaticamente arquivos .gitignore do diretório raiz do projeto para baixo. Essas exclusões podem ser substituídas por regras em .contextfiles.
    • Suporta configuração hierárquica usando .contextfiles colocados dentro dos diretórios do seu projeto. As regras são aplicadas dinamicamente com base no arquivo/diretório sendo processado.
    • Comportamento de Correspondência: Padrões correspondem ao caminho relativo ao diretório alvo sendo processado. Os caminhos de saída permanecem relativos à raiz original do projeto.
    • Comportamento da Raiz de Regras: Cada alvo tem sua própria raiz de regras:
      • Alvos dentro da raiz do projeto (ou CWD) usam a raiz do projeto/CWD como sua raiz de regras
      • Alvos externos usam a si mesmos como sua raiz de regras, garantindo conjuntos de regras autocontidos
    • Substituições: Suporta --overrides (CLI) ou rules (MCP) para usar um conjunto específico de regras exclusivamente. Quando substituições estão ativas, tanto as regras padrão embutidas quanto quaisquer .contextfiles são ignoradas. A correspondência de caminho para substituições ainda é relativa ao diretório alvo.
    • Inclusão Explícita de Alvo: Arquivos fornecidos explicitamente como alvos são sempre incluídos (ignorando verificações de regras, mas não verificações binárias/de tamanho).
  • Configuração Personalizável (.contextfiles / Substituições):
    • Defina precisamente quais arquivos/diretórios incluir ou excluir usando padrões no estilo .gitignore aplicados ao caminho relativo.
    • Padrões começando com ! negam a correspondência (um padrão de exclusão). (Veja a seção de Configuração abaixo).
  • Manipulação de Contexto Grande: Aborta com um DetailedContextSizeError se o tamanho total dos arquivos incluídos exceder um limite configurável (padrão: 100MB). A mensagem de erro inclui uma lista dos 10 maiores arquivos que contribuem para o tamanho, ajudando você a identificar candidatos para exclusão. Veja a seção de Solução de Problemas para orientação sobre gerenciamento do tamanho do contexto.
  • Cabeçalhos de Metadados: A saída inclui um cabeçalho de caminho para cada arquivo incluído (ex.: ````path=src/app.py). Isso pode ser desabilitado com list_only`.
  • Manipulação de Codificação: Tenta múltiplas codificações de texto comuns (UTF-8, Latin-1, etc.).
  • Modo Somente Lista: Opção para listar apenas os caminhos relativos dos arquivos que seriam incluídos, sem seu conteúdo.

Uso

Servidor MCP (ferramenta read_context)

  1. Configuração: Configure seu cliente MCP (ex.: claude_desktop_config.json do Claude Desktop) para executar o servidor jinni via uvx.
  2. Invocação: Ao interagir com seu LLM via cliente MCP, o modelo pode invocar a ferramenta read_context.
    • project_root (string, obrigatório): O caminho absoluto para o diretório raiz do projeto. A descoberta de regras e os caminhos de saída são relativos a esta raiz.
    • targets (array JSON de strings, obrigatório): Especifica uma lista obrigatória de arquivo(s)/diretório(s) dentro de project_root para processar. Deve ser um array JSON de caminhos de string (ex.: ["path/to/file1", "path/to/dir2"]). Os caminhos podem ser absolutos ou relativos ao CWD. Todos os caminhos alvo devem resolver para locais dentro de project_root. Se uma lista vazia [] for fornecida, todo o project_root é processado.
    • rules (array JSON de strings, obrigatório): Uma lista obrigatória de regras de filtragem inline (usando sintaxe no estilo .gitignore, ex.: ["src/**/*.py", "!*.tmp"]). Forneça uma lista vazia [] se nenhuma regra específica for necessária (isso usará os padrões embutidos). Se não vazio, essas regras são usadas exclusivamente, ignorando padrões embutidos e .contextfiles.
    • list_only (booleano, opcional): Se verdadeiro, retorna apenas a lista de caminhos de arquivos relativos em vez do conteúdo.
    • size_limit_mb (inteiro, opcional): Substitui o limite de tamanho de contexto em MB.
    • debug_explain (booleano, opcional): Habilita registro de depuração no servidor.
    • exclusions (objeto, opcional): Configuração de exclusão com três campos opcionais:
      • global (array de strings): Palavras-chave para excluir globalmente (ex.: ["tests", "deprecated"])
      • scoped (objeto): Mapa de caminhos para arrays de palavras-chave para exclusões com escopo (ex.: {"src/legacy": ["old", "deprecated"]})
      • patterns (array de strings): Padrões de arquivo para excluir (ex.: ["*.test.js", "*_old.*"])
    1. Saída: A ferramenta retorna uma única string contendo o conteúdo concatenado (com cabeçalhos) ou a lista de arquivos. Os caminhos nos cabeçalhos/listas são relativos ao project_root fornecido. Em caso de erro de tamanho de contexto, retorna um DetailedContextSizeError com detalhes sobre os maiores arquivos.

Servidor MCP (ferramenta usage)

  • Invocação: O modelo pode invocar a ferramenta usage (nenhum argumento necessário).
  • Saída: Retorna o conteúdo do arquivo README.md como uma string.

(Instruções detalhadas de configuração do servidor variarão dependendo do seu cliente MCP. Geralmente, você precisa configurar o cliente para executar o servidor Jinni.)

Executando o Servidor:

  • Método Recomendado: Use uvx para executar o ponto de entrada do servidor diretamente (requer que o pacote jinni esteja publicado no PyPI ou encontrável por uvx):
    uvx jinni-server [OPTIONS]
    
    Exemplo de configuração do cliente MCP (ex.: claude_desktop_config.json):
    {
      "mcpServers": {
        "jinni": {
          "command": "uvx",
          "args": ["jinni-server"]
        }
      }
    }
    

Você pode opcionalmente restringir o servidor para ler apenas dentro de uma árvore por segurança, caso seu LLM saia do controle: adicione "--root", "/absolute/path/" à lista de args.

Consulte a documentação específica do seu cliente MCP para etapas precisas de configuração. Certifique-se de que uv esteja instalado

Utilitário de Linha de Comando (CLI jinni)

jinni [OPTIONS] [<PATH...>]
  • <PATH...> (opcional): Um ou mais caminhos para os diretórios ou arquivos do projeto a analisar. Padrão para o diretório atual (.) se nenhum for fornecido.
  • -r <DIR> / --root <DIR> (opcional): Especifique o diretório raiz do projeto. Se fornecido, a descoberta de regras começa aqui, e os caminhos de saída são relativos a este diretório. Se omitido, a raiz é inferida do ancestral comum dos argumentos <PATH...> (ou CWD se apenas '.' for processado).
  • --output <FILE> / -o <FILE> (opcional): Escreva a saída em <FILE> em vez de imprimir na saída padrão.
  • --list-only / -l (opcional): Apenas liste os caminhos relativos dos arquivos que seriam incluídos.
  • --overrides <FILE> (opcional): Adicione regras de <FILE> como regras de alta prioridade, além de .contextfiles e .gitignore.
  • --size-limit-mb <MB> / -s <MB> (opcional): Substitua o tamanho máximo de contexto em MB.
  • --debug-explain (opcional): Imprima razões detalhadas de inclusão/exclusão em stderr e jinni_debug.log.
  • --root <DIR> / -r <DIR> (opcional): Veja acima.
  • --no-copy (opcional): Evite copiar automaticamente o conteúdo da saída para a área de transferência do sistema ao imprimir na saída padrão (o padrão é copiar).
  • --not <keyword> (opcional, repetível): Exclua módulos/diretórios correspondentes à palavra-chave (ex.: --not tests --not vendor). Pode ser usado múltiplas vezes.
  • --not-in <path:keywords> (opcional, repetível): Exclua palavras-chave específicas dentro de um caminho (ex.: --not-in src/legacy:old,deprecated). Pode ser usado múltiplas vezes.
  • --not-files <pattern> (opcional, repetível): Exclua arquivos correspondentes ao padrão (ex.: --not-files '*.test.js' --not-files '*_old.*'). Pode ser usado múltiplas vezes.
  • --keep-only <modules> (opcional): Mantenha apenas módulos/diretórios especificados, exclua todo o resto (separados por vírgula, ex.: --keep-only src,lib,docs).

Exemplos de Exclusão

Exemplos de CLI:

# Exclude all test directories
jinni --not tests

# Exclude multiple keywords
jinni --not tests --not vendor --not deprecated

# Exclude old code only in specific paths
jinni --not-in src/legacy:old,deprecated --not-in lib/v1:legacy

# Exclude specific file patterns
jinni --not-files "*.test.js" --not-files "*_old.*"

# Keep only src and docs, exclude everything else
jinni --keep-only src,docs

# Combine different exclusion types
jinni --not tests --not-in src/experimental:wip --not-files "*.bak"

Nota: Comandos de exclusão (flags --not*) funcionam além das regras existentes de .gitignore e .contextfiles. Eles filtram ainda mais o que seria incluído de outra forma.

Exemplos de MCP:

{
  "project_root": "/path/to/project",
  "targets": [],
  "rules": [],
  "exclusions": {
    "global": ["tests", "vendor"],
    "scoped": {
      "src/legacy": ["old", "deprecated"],
      "lib/experimental": ["wip", "unstable"]
    },
    "patterns": ["*.test.js", "*_backup.*"]
  }
}

Instalação

Você pode instalar o Jinni usando pip ou uv:

Usando pip:

pip install jinni

Usando uv:

uv pip install jinni

Isso tornará o comando CLI jinni disponível no seu ambiente. Veja a seção "Executando o Servidor" acima para saber como iniciar o servidor MCP dependendo do seu método de instalação.

Notas específicas de plataforma

Windows + WSL

Jinni v0.1.7+ converte automaticamente caminhos WSL.

Forneça qualquer um destes como project_root (CLI --root ou argumento MCP):

/home/user/project
vscode-remote://wsl+Ubuntu-22.04/home/user/project

Sem wrappers, montagens ou flags extras necessários—Jinni resolve o caminho UNC (\\wsl$\...) no Windows automaticamente. Formato de Caminho UNC: O Jinni sempre usa \\wsl$\<distro>\... para máxima compatibilidade com todas as versões do Windows que suportam WSL. Tratamento de Nome de Distribuição: Espaços e a maioria dos caracteres especiais são permitidos no nome da distribuição. Apenas caracteres verdadeiramente ilegais em UNC são substituídos por _. Cache: As consultas e conversões de caminhos WSL são armazenadas em cache por desempenho. Se você instalar o WSL enquanto o Jinni estiver em execução, reinicie o Jinni para detectar o novo wslpath. Opt-out: Defina a variável de ambiente JINNI_NO_WSL_TRANSLATE=1 para desativar toda a lógica de tradução de caminhos WSL.

Apenas URIs wsl+<distro> e caminhos POSIX absolutos (começando com /) são traduzidos; para remotos SSH ou de contêiner, execute o Jinni dentro desse ambiente.

SO em execuçãoO que você informaO que _translate_wsl_path() retorna
Windowsvscode-remote://wsl%2BUbuntu/home/a/b\\wsl$\\Ubuntu\home\a\b
Windows/home/a/b\\wsl$\\Ubuntu\home\a\b (via wslpath)
Linux/WSLvscode-remote://wsl+Ubuntu/home/a/b/home/a/b
Linux/WSL/home/a/b/home/a/b (inalterado)

Exemplos

  • Despejar contexto de my_project/ no console:

    jinni ./my_project/ # Process a single directory
    jinni ./src ./docs/README.md # Process multiple targets
    jinni # Process current directory (.)
    
  • Listar arquivos que seriam incluídos em my_project/ sem conteúdo:

    jinni -l ./my_project/
    jinni --list-only ./src ./docs/README.md
    
  • Despejar contexto de my_project/ em um arquivo chamado context_dump.txt:

    jinni -o context_dump.txt ./my_project/
    
  • Usar regras de substituição de custom.rules em vez de .contextfiles:

    jinni --overrides custom.rules ./my_project/
    
  • Mostrar informações de depuração:

    jinni --debug-explain ./src
    
  • Despejar contexto (a saída é copiada automaticamente para a área de transferência por padrão):

    jinni ./my_project/
    
  • Despejar contexto, mas não copiar para a área de transferência:

    jinni --no-copy ./my_project/
    

Configuração (.contextfiles e Substituições)

O Jinni usa .contextfiles (ou um arquivo de substituição) para determinar quais arquivos e diretórios incluir ou excluir, com base em padrões no estilo .gitignore.

  • Princípio Central: As regras são aplicadas dinamicamente durante a travessia, em relação ao diretório de destino atual que está sendo processado.
  • Localização (.contextfiles): Coloque .contextfiles em qualquer diretório. A descoberta de regras começa na raiz de regras (raiz do projeto para destinos internos, o próprio destino para destinos externos) e desce até o diretório atual que está sendo processado.
  • Formato: Texto simples, codificado em UTF-8, um padrão por linha.
  • Sintaxe: Usa a sintaxe padrão de padrões .gitignore (especificamente a implementação de gitwildmatch do pathspec).
    • Comentários: Linhas que começam com # são ignoradas.
    • Padrões de Inclusão: Especifique arquivos/diretórios a incluir (por exemplo, src/**/*.py, *.md, /config.yaml).
    • Padrões de Exclusão: Linhas que começam com ! indicam que um arquivo correspondente deve ser excluído (nega o padrão).
    • Ancoragem: Um / inicial ancora o padrão ao diretório que contém o .contextfiles.
    • Correspondência de Diretórios: Um / final corresponde apenas a diretórios.
    • Curingas: *, **, ? funcionam como em .gitignore.
  • Lógica de Aplicação de Regras:
    1. Determinar o Destino: O Jinni identifica o diretório de destino (fornecido explicitamente ou a raiz do projeto).
    2. Verificação de Substituição: Se --overrides (CLI) ou rules (MCP) forem fornecidos, essas regras são usadas exclusivamente. Todos os .contextfiles e padrões internos são ignorados. A correspondência de caminhos é relativa ao diretório de destino.
    3. Regras de Contexto Dinâmico (Sem Substituições): Ao processar um arquivo ou subdiretório:
      • O Jinni encontra todos os .gitignore e .contextfiles desde a raiz de regras até o diretório do item atual.
      • As regras são combinadas em ordem: padrões internos, regras de .gitignore, regras de .contextfiles (que têm precedência).
      • Ele compila essas regras combinadas em uma especificação (PathSpec).
      • Ele compara o caminho atual do arquivo/subdiretório, calculado em relação ao diretório de destino, com essa especificação.
    4. Correspondência: O último padrão no conjunto de regras combinadas que corresponde ao caminho relativo do item determina seu destino. ! nega a correspondência. Se nenhum padrão definido pelo usuário corresponder, o item é incluído, a menos que corresponda a uma exclusão padrão interna (como !.*).
    5. Tratamento do Destino: Arquivos explicitamente direcionados ignoram as verificações de regras. Os caminhos de saída sempre permanecem relativos ao project_root original.

Exemplos (.contextfiles)

Exemplo 1: Incluir Código-Fonte Python e Configuração da Raiz

Localizado em my_project/.contextfiles:

# Include all Python files in the src directory and subdirectories
src/**/*.py

# Include the main config file at the root of the project
/config.json

# Include all markdown files anywhere
*.md

# Exclude any test data directories found anywhere
!**/test_data/

Exemplo 2: Substituindo em um Subdiretório

Localizado em my_project/src/.contextfiles:

# In addition to rules inherited from parent .contextfiles...

# Include specific utility scripts in this directory
utils/*.sh

# Exclude a specific generated file within src, even if *.py is included elsewhere
!generated_parser.py

Desenvolvimento

  • Detalhes de Design: DESIGN.md

  • Executando o Servidor Localmente: Durante o desenvolvimento (após instalar com uv pip install -e . ou similar), você pode executar o módulo do servidor diretamente:

    python -m jinni.server [OPTIONS]
    

    Exemplo de configuração de cliente MCP para desenvolvimento local:

    {
      "mcpServers": {
        "jinni": {
          // Adjust python path if needed, or ensure the correct environment is active
          "command": "python -m jinni.server"
          // Optionally constrain the server to only read within a tree (recommended for security):
          // "command": "python -m jinni.server --root /absolute/path/to/repo"
        }
      }
    }
    

Solução de Problemas

Erros de Tamanho de Contexto (DetailedContextSizeError)

Se você encontrar um erro indicando que o limite de tamanho de contexto foi excedido, o Jinni fornecerá uma lista dos 10 maiores arquivos que tentou incluir. Isso ajuda a identificar possíveis candidatos para exclusão.

Para resolver isso:

  1. Revise os Maiores Arquivos: Verifique a lista fornecida na mensagem de erro. Há arquivos grandes (por exemplo, arquivos de dados, logs, artefatos de build, mídia) que não deveriam fazer parte do contexto do LLM?
  2. Configure Exclusões: Use .contextfiles ou as opções --overrides / rules para excluir arquivos ou diretórios desnecessários.
    • Exemplo (.contextfiles): Para excluir todos os arquivos .log e um diretório de dados grande específico:
      # Exclude all log files
      !*.log
      
      # Exclude a large data directory
      !large_data_files/
      
    • Consulte a seção Configuração acima para obter sintaxe e uso detalhados.
  3. Aumente o Limite (Use com Cautela): Se todos os arquivos incluídos forem genuinamente necessários, você pode aumentar o limite de tamanho usando --size-limit-mb (CLI) ou size_limit_mb (MCP). Esteja atento aos limites da janela de contexto do LLM e aos custos de processamento.
  4. Use jinni usage / usage: Se você precisar consultar estas instruções ou os detalhes de configuração durante a solução de problemas, use o comando jinni usage ou a ferramenta MCP usage.