clamav-tray
Indicador de bandeja para uma instalação de ClamAV gerenciada por systemd. Responde, sem abrir terminal: os serviços estão de pé, tem varredura rodando agora, e como terminou a última?
Um clique abre o estado completo — serviços, varredura, mídia removível e quarentena:
As imagens são renderizações fiéis, montadas a partir da estrutura que o próprio programa produz, com os SVGs do tema Adwaita. Os ícones aparecem brancos porque é assim que são de fato: o indicador pede um ícone pelo nome (
security-high-symbolic) e quem pinta é o shell, com a cor de primeiro plano do painel — o que distingue um estado do outro é a forma e o rótulo ao lado, não a cor. A barra de progresso usa as constantes do própriowidgets.py, lidas do código, para a imagem não poder divergir do programa. As duas são regeneráveis:python3 docs/screenshots/make-tray-states.pyemake-menu-states.py.
Por que existe
O ClamTk é a referência da categoria (436★), mas é um scanner sob demanda: zero referências a systemd, zero a bandeja, e o último push de código foi em março de 2024. Os demais projetos da busca têm 0 ou 1 estrela.
Ninguém preencheu o espaço de "meu ClamAV já roda por systemd, quero ver o estado dele".
Requer systemd. É a premissa, não uma limitação temporária — o valor do projeto é justamente ler o estado das unidades.
Instalação
# 1. dependências de sistema — escolha a sua distro
sudo apt install python3-gi gir1.2-ayatanaappindicator3-0.1 pipx # Debian/Ubuntu
sudo dnf install python3-gobject gtk3 libayatana-appindicator-gtk3 pipx # Fedora
sudo pacman -S python-gobject gtk3 libayatana-appindicator python-pipx # Arch
# 2. o programa
pipx install --system-site-packages clamav-tray
Os três comandos foram conferidos em containers limpos (Ubuntu 24.04, Fedora e Arch atuais), instalando o pacote. No Fedora e no Arch o container rodava o systemd, e a descoberta das unidades foi conferida ao vivo; no Ubuntu, ela é a de uso diário na máquina de origem.
--system-site-packages é obrigatório. O PyGObject (gi) vem da distro, não
do pip — compilá-lo num virtualenv exige toolchain e os cabeçalhos do GTK. Sem a
flag, o venv do pipx não enxerga o python3-gi do sistema; o programa detecta
isso e diz como corrigir.
Dependências de sistema: python3-gi, GTK 3 e um dos dois AppIndicator
(gir1.2-ayatanaappindicator3-0.1 ou gir1.2-appindicator3-0.1 — o programa
tenta os dois).
Do código-fonte: clone e pipx install --system-site-packages .
Antes: o ClamAV precisa estar no ar
O tray observa as unidades do ClamAV; não as cria. Se nenhuma for encontrada, ele diz isso ("nenhum serviço do ClamAV encontrado") em vez de mostrar o escudo verde. Duas armadilhas conferidas:
- Fedora não habilita nada, e o
/etc/clamd.d/scan.confvem com oLocalSocketcomentado. DescomenteLocalSocket(eLogFile, se quiser o log), rodesudo freshclame entãosudo systemctl enable --now clamd@scan. - Arch (e o pacote upstream): o
clamav-daemon.servicetemConditionPathExistsGlobpara a base de assinaturas. Semsudo freshclamantes, a unidade "inicia" sem erro, fica inativa e some da lista do systemd. Rodefreshclamprimeiro, depoissudo systemctl enable --now clamav-daemon.
Subir sozinho no login
Um programa que se registra para rodar a cada login pede confiança. Por isso o primeiro passo é olhar, não instalar:
clamav-tray --show-autostart # mostra destino, comando e conteúdo exato — não grava nada
clamav-tray --show-autostart --xdg # o mesmo, para o autostart XDG
Ele mostra onde o arquivo seria gravado, que comando rodaria a cada login, o
arquivo inteiro e os comandos systemctl --user que viriam depois. Se já existe
um arquivo no destino — seu, de outra versão, ou editado à mão —, mostra a
diferença linha a linha em vez do arquivo inteiro.
Conferido, instale:
clamav-tray --install-autostart # serviço de usuário, supervisionado (recomendado)
clamav-tray --install-autostart --xdg # autostart XDG, sem supervisão
clamav-tray --uninstall-autostart # desfaz (com --xdg, o XDG)
O --install-autostart mostra de novo o mesmo conteúdo e só grava depois de
você responder s. Fora de um terminal ele recusa, a menos que receba --yes —
assim nenhum script grava autostart sem que alguém tenha decidido isso. A remoção
segue a mesma regra.
Nada disso precisa de root: o serviço vai para ~/.config/systemd/user/ e o XDG
para ~/.config/autostart/. Prefira o serviço: se o processo morrer, ele volta, e
o journal guarda o motivo. O autostart XDG dispara e esquece — foi assim que o
indicador que deu origem a este projeto sumiu da bandeja sem deixar rastro.
Depois de gravar, o instalador confere que o serviço subiu, em vez de afirmar
"ativado" sem olhar. Rodando do código-fonte (sem clamav-tray no PATH), ele
aponta a unidade para python3 -m clamav_tray neste diretório — e o
--show-autostart diz isso antes. Quem clonou pode usar também
./packaging/install-autostart.sh [xdg], que encaminha para o mesmo comando.
Os extras (varredura agendada, USB, Downloads) continuam só no repositório: instalam unidade de sistema e pedem root, o que o pacote não faz por decisão.
Bandeja no seu desktop
| Desktop | Situação |
|---|---|
| KDE, XFCE, Cinnamon, MATE | nativo |
| Ubuntu | funciona (a Canonical embarca ubuntu-appindicators) |
| GNOME puro | precisa de extensão — o GNOME removeu a bandeja na 3.26 |
O que funciona numa instalação limpa
O programa observa o que existe. Não instala unidade, não agenda varredura e não decide o que varrer — é essa escolha que o mantém instalável sem root.
| De fábrica | |
|---|---|
| ClamAV Daemon, Freshclam, On-Access | sim, vêm nos pacotes |
| Varrer a home, varrer mídia removível | sim, precisa só do clamd no ar |
| Quarentena do usuário, barra de progresso | sim |
| Varredura agendada, "Próxima", "Última" | não — nenhuma distro entrega |
| Monitor de pasta, quarentena do sistema | não |
Metade de cima funciona; a metade da varredura nasce vazia. Não é bug: a distro não agenda varredura, e o programa não deve inventar uma.
Para preencher, há extras opcionais e independentes em
contrib/extras/ — varredura diária, monitor de Downloads,
varredura de USB e publicação das estatísticas de quarentena. Cada um com
instalador próprio, que recusa sobrescrever e diz como desinstalar.
Configuração
Há um item Configurações no menu: ele cria o arquivo comentado se não existir e abre no seu editor. O arquivo é relido sozinho ao salvar.
Nada é obrigatório — o programa descobre as unidades pelo glob clam* e os
caminhos pelo clamconf.
Para scripts e painéis
clamav-tray --dump # o que o tray veria, em texto
clamav-tray --dump --json # o mesmo, como dado — formato estável
clamav-tray --dump --json | jq -r .status # ok | busy | warn | threat
Não precisa de tela nem de PyGObject. O JSON é um contrato versionado (campo
schema), descrito em docs/json.md.
Idioma
Inglês é o padrão e a fonte. Traduzir é opcional por construção: chave sem tradução aparece em inglês em vez de quebrar.
[general]
language = "pt_BR" # ou "auto" para seguir o locale
Para contribuir com um idioma, copie o bloco pt_BR em
clamav_tray/i18n.py e traduza — sem instalar ferramenta
nenhuma. Não usa gettext de propósito; o porquê está em
docs/design.md.
Documentação
| docs/design.md | decisões de desenho e o que elas custaram |
| docs/dbusmenu.md | o que atravessa o protocolo do menu, e o que não |
| docs/quarantine.md | as duas quarentenas e a convenção de estatísticas |
| docs/progress.md | progresso por contagem, não por relógio |
| docs/json.md | o formato do --dump --json e o que é estável nele |
| docs/removable-media.md | detecção sem subprocesso |
| ROADMAP.md | o produto, e a migração para Rust |
| CONTRIBUTING.md | como contribuir |
Este projeto é também meu caderno de Rust
Decidi usar este projeto para aprender Rust, migrando um módulo por vez até que não sobre Python.
- A migração acontece em branch separada (
rust), nunca namain - A
maincontinua sendo a versão Python, funcional e mantida - A virada de chave só acontece quando eu tiver confiança na linguagem — não por prazo, não por metade dos módulos portados. Se essa confiança não vier, a versão Python permanece e isso não é fracasso
- Quem instala usa Python e não precisa saber de nada disso
O desenho em módulos existe por causa disso: cada arquivo tem uma fronteira clara e pode ser portado sozinho. A ordem e o critério estão no ROADMAP.
Se você é contribuidor: mande PR contra a main, em Python. A branch rust
é exercício pessoal e pode ser reescrita à força a qualquer momento.
Estado
v0.1, em uso diário por uma pessoa. Publicado porque o nicho estava vazio, não porque seja maduro. Se você usar, espere arestas — e abra issue.
Licença
MIT.
Metadata
Release files for clamav-tray 0.3.0
For a detailed explanation of source distributions (sdists) and built distributions (wheels), please see the package formats documentation.
Source distribution (sdist)
| File | Size | Uploaded | Provenance | |
|---|---|---|---|---|
| clamav_tray-0.3.0.tar.gz | 58.9 kB | With provenance | Details |
Built distribution (wheel)
| File | Interpreter | ABI | Platform | Reset |
|---|---|---|---|---|
| clamav_tray-0.3.0-py3-none-any.whl | Python 3 | none | any | Details |
Total release size: 116.2 kB
Release files / clamav_tray-0.3.0.tar.gz
| Download URL | clamav_tray-0.3.0.tar.gz |
|---|---|
| Size | 58.9 kB |
| Tags | Source |
|
SHA-256 checksum How to use checksums |
8acac46ee82b89cea22c567975e916d6461a759eedecf37a2ce5f6ce118f11fe
|
|
BLAKE2b-256 checksum How to use checksums |
c0c893a4a48b0f29a1e41e5117a7597ab20c49a3d4db1711583e03c2f70f525e
|
| Upload date | |
|
Uploaded using Trusted Publishing? What is trusted publishing? |
Yes |
| Uploaded via |
twine/7.0.0 CPython/3.13.14
|
Provenance
Provenance describes where a file came from. On PyPI, provenance is shared via attestations, which provide a verifiable record of the build or publishing details. View details, limitations and caveats.
PyPI Publish Attestation
PyPI verified that this artifact, at this checksum, originated from the publisher listed below.
Signed by GitHub Actions, verified by PyPI on Oct 13, 2026.
Transparency logRelease files / clamav_tray-0.3.0-py3-none-any.whl
| Download URL | clamav_tray-0.3.0-py3-none-any.whl |
|---|---|
| Size | 57.3 kB |
| Tags | Python 3 |
|
SHA-256 checksum How to use checksums |
de1e9a4a40a6ee553def0d249268e9c2fdc1b28b9e44a650fb5c7b852136f28b
|
|
BLAKE2b-256 checksum How to use checksums |
ae6f2d3e34467346bc297ba7c0c6944d45fa0d96060b975296744bafbc7ac197
|
| Upload date | |
|
Uploaded using Trusted Publishing? What is trusted publishing? |
Yes |
| Uploaded via |
twine/7.0.0 CPython/3.13.14
|
Provenance
Provenance describes where a file came from. On PyPI, provenance is shared via attestations, which provide a verifiable record of the build or publishing details. View details, limitations and caveats.
PyPI Publish Attestation
PyPI verified that this artifact, at this checksum, originated from the publisher listed below.
Signed by GitHub Actions, verified by PyPI on Oct 13, 2026.
Transparency logSecurity for clamav-tray 0.3.0
Provenance
Provenance describes where a file came from. On PyPI, provenance is shared via attestations, which provide a verifiable record of the build or publishing details. View details, limitations and caveats.
Full provenance
All 2 files in this release have been uploaded with provenance metadata.
Attestation for clamav_tray-0.3.0.tar.gz
PyPI Publish Attestation
PyPI verified that this artifact, at this checksum, originated from the publisher listed below.
Signed by GitHub Actions, verified by PyPI on Oct 13, 2026.
Transparency logA note on package security
PyPI is a repository for distributing packages, not a service for auditing them. While third-party security researchers and our staff do their best to detect and remove malicious packages, PyPI cannot guarantee the quality, security or suitability of any given package.
To learn more about protecting yourself from malicious actors, visit our package security documentation.