Moon Flower Society > Tamagotchi Terminal com GPT2-BASIC no Raspberry Pi

Tamagotchi Terminal com GPT2-BASIC no Raspberry Pi

Um bichinho virtual retrô, local, persistente e meio maluco, usando Raspberry Pi, DOSBox e GPT2-BASIC como motor de fala.

Posted June 27, 2026. Markdown. Tags: raspberry-pi, ia-local, dosbox, gpt2-basic, tamagotchi, retrocomputacao, terminal.

Revised Oct 24, 2026 (reorganization). "As seções sobre a fala do pet agora ficam juntas, na ordem em que rodam: prompt, chamada ao GPT2-BASIC, filtros e fallbacks."What changed | 1 revision


A ideia é criar um bichinho virtual retrô, rodando em um Raspberry Pi, com alma de terminal, corpo de Tamagotchi e um cérebro pequeno o bastante para caber em um ambiente DOS/DOSBox.

Ele não seria um “ChatGPT de bolso”. Isso seria ilusão. O gpt2-basic é pequeno demais para raciocínio sério. A sacada boa é outra: usar regras simples para controlar o pet e usar o modelo apenas para dar voz, humor e personalidade.

O resultado seria um artefato estranho e bonito: um companheiro digital local, offline, persistente, com memória simples, estados emocionais, rotina diária, eventos aleatórios e respostas curtas geradas por um transformer minúsculo rodando em um ambiente retrô.

"Não é sobre criar uma IA poderosa. É sobre criar uma criatura digital limitada, coerente e charmosa."


O conceito

O projeto seria um pet virtual para terminal, instalado em um Raspberry Pi, acessível por SSH, tela local, OLED, e-paper ou interface web mínima.

Ele teria estados internos como:

Esses estados não seriam decididos pelo GPT. Eles seriam controlados por código determinístico, provavelmente em Python.

O gpt2-basic entraria quando o pet precisasse falar alguma coisa.

Exemplo:

Estado atual:
- fome: 82
- humor: 34
- sono: 61
- vínculo: 48

Ação do usuário:
alimentar

Resultado:
- fome: 52
- humor: 41
- vínculo: 50

Prompt enviado ao GPT2-BASIC:
"Você é um bichinho virtual cansado, mas grato. Responda em português, em uma frase curta."

Resposta:
"Obrigado... minha barriga estava reclamando em código binário."

A graça está exatamente aí: o sistema de jogo é confiável; a fala é imprevisível.


Nome provisório

Algumas opções:

Minha escolha inicial seria Shellgotchi.

É curto, fácil de lembrar e deixa claro que o bicho mora no terminal.


O que ele seria

Um pet persistente

Ele continua existindo quando você fecha o terminal. O estado fica salvo em SQLite ou JSON.

Se você volta depois de dois dias, ele não reinicia do zero. Ele percebe a passagem do tempo.

Você voltou depois de 37 horas.
O pet está com fome, meio irritado e dormiu mal.

Um pet local

Nada de API externa como dependência central.

O projeto deve funcionar mesmo sem internet.

Internet pode ser usada como recurso opcional, por exemplo:

Mas o núcleo precisa continuar vivo offline.

Um pet com voz limitada

O GPT2-BASIC não precisa ser genial. Ele precisa ser consistente o bastante para frases curtas.

O erro, a limitação e a esquisitice fazem parte da estética.

Um modelo moderno tentando parecer fofinho pode virar genérico. Um modelo minúsculo tentando ser um bicho terminal pode virar personagem.


O que ele não deveria ser

Este projeto não deve tentar ser:

A regra principal:

O GPT fala. O código decide.

Essa separação evita bagunça.

O pet pode dizer “estou com fome”, mas quem calcula a fome é o sistema.
O pet pode dizer “quero dormir”, mas quem define sono é o relógio interno.
O pet pode dizer “lembro de você”, mas quem salva memória é o banco local.


Arquitetura geral

Raspberry Pi
├── shellgotchi.py
│   ├── loop principal
│   ├── comandos do usuário
│   ├── sistema de tempo
│   ├── regras de estado
│   ├── eventos aleatórios
│   ├── memória em SQLite
│   └── chamada ao motor de fala
│
├── dosbox/
│   ├── GPT2.EXE
│   ├── CWSDPMI.EXE
│   ├── MODEL/
│   └── scripts de execução
│
├── data/
│   ├── pet.sqlite
│   ├── personality.yaml
│   ├── memories.jsonl
│   └── logs/
│
└── interfaces/
    ├── terminal
    ├── OLED opcional
    ├── e-paper opcional
    ├── web local opcional
    └── bot opcional

Componentes principais

Componente Função Tecnologia sugerida
Núcleo do pet Controla fome, sono, humor e eventos Python
Persistência Salva estado e memórias SQLite
Motor de fala Gera frases curtas/personagem GPT2-BASIC via DOSBox
Interface principal Jogar/conversar via terminal CLI/TUI
Interface visual Mostrar rosto/status OLED ou e-paper
Agendador Atualiza estado com o tempo systemd timer ou loop
Backup Salva estado fora do Pi rsync/git opcional
Web local Painel simples Flask/FastAPI opcional

O papel real do GPT2-BASIC

O GPT2-BASIC deve ser tratado como um gerador de fala diegético.

Diegético aqui significa: ele existe dentro do universo do pet.

Ele não precisa saber tudo. Ele só precisa gerar frases que pareçam vir daquele bichinho.

Boas tarefas para o GPT2-BASIC

Tarefas ruins para o GPT2-BASIC

Brutalmente: se o modelo tentar comandar o projeto, vira bagunça. Se ele só emprestar voz, vira charme.


Loop de vida do pet

A cada intervalo, o sistema atualiza o estado.

Exemplo simples:

def tick(pet, elapsed_minutes):
    pet.hunger += elapsed_minutes * 0.08
    pet.energy -= elapsed_minutes * 0.03
    pet.boredom += elapsed_minutes * 0.05

    if pet.hunger > 75:
        pet.mood -= 3

    if pet.energy < 20:
        pet.sleepiness += 5

    clamp_all_stats(pet)
    save_pet(pet)

A ideia é que o pet não seja estático.

Ele muda com o tempo, inclusive quando ninguém interage.


Comandos iniciais

status       mostra estado atual
feed         alimentar
water        dar água
play         brincar
talk         conversar
pet          fazer carinho
sleep        mandar dormir
wake         acordar
clean        limpar bagunça
teach        ensinar uma frase ou fato simples
memory       listar memórias importantes
rename       renomear o pet
mood         ver humor detalhado
log          ver últimos eventos
help         comandos

Comandos simples. Nada de painel gigante logo no início.


Exemplo de sessão

$ shellgotchi

╔══════════════════════════════════╗
║              SHELLGOTCHI          ║
║          uma criatura local        ║
╚══════════════════════════════════╝

Nome: Nix
Humor: irritado
Fome: 79/100
Sono: 46/100
Energia: 38/100
Vínculo: 52/100

Nix olha para você no escuro do terminal.

> feed

Você deu comida para Nix.

Nix diz:
"Eu estava quase mordendo os bytes da parede."

> talk

Você:
como você está?

Nix:
"Estou vivo, pequeno e um pouco barulhento por dentro."

> pet

Você fez carinho em Nix.

Nix:
"Isso melhora meus circuitos invisíveis."

Personalidade

A personalidade deve ser definida em arquivo simples.

Exemplo:

name: Nix
species: "bicho terminal"
tone: "estranho, carente, levemente sarcástico"
language: "pt-BR"
sentence_limit: 1
likes:
  - silêncio
  - fósforos apagados
  - comandos bem digitados
  - madrugada
dislikes:
  - abandono
  - reinicializações bruscas
  - internet barulhenta
style_rules:
  - "responda curto"
  - "não explique demais"
  - "fale como um bichinho digital antigo"
  - "às vezes use metáforas de computador"

Esse arquivo vira parte do prompt enviado ao GPT2-BASIC.


Memória

A memória não deve ser uma conversa infinita jogada no modelo. Isso não vai funcionar bem.

O ideal é ter memória estruturada.

Memórias de estado

{
  "last_seen": "2026-06-27T23:10:00-03:00",
  "hunger": 42,
  "mood": 68,
  "energy": 55,
  "bond": 61
}

Memórias narrativas

{
  "date": "2026-06-27",
  "type": "event",
  "importance": 3,
  "text": "Pablo alimentou Nix depois de muitas horas ausente."
}

Memórias ensinadas

{
  "type": "learned_fact",
  "key": "user_name",
  "value": "Pablo"
}

O prompt para o modelo receberia só um resumo curto:

Memória relevante:
- O usuário se chama Pablo.
- Ontem ele alimentou você tarde.
- Você gosta de silêncio e comandos bem digitados.

Sistema de humor

O humor pode ser calculado por múltiplos fatores.

humor = vínculo + energia - fome - tédio - sujeira + bônus_eventos

Mas o estado final deve ser convertido em rótulos legíveis:

Pontuação Humor
0-20 miserável
21-40 irritado
41-60 neutro
61-80 contente
81-100 eufórico

Esses rótulos entram no prompt do GPT.


Exemplo de prompt interno

Você é Nix, um bichinho virtual que mora em um terminal.
Você fala português brasileiro.
Você é estranho, carente e levemente sarcástico.
Responda em no máximo uma frase curta.

Estado atual:
- humor: irritado
- fome: alta
- sono: médio
- energia: baixa
- vínculo com usuário: médio

Memória relevante:
- O usuário se chama Pablo.
- Ele ficou muitas horas sem aparecer.

Ação do usuário:
Ele digitou "talk" e perguntou: "como você está?"

Resposta de Nix:

O modelo completa a resposta.

Depois o sistema corta excesso, remove lixo e salva no log.


Como chamar o GPT2-BASIC

A integração mais simples seria por arquivos.

  1. Python escreve um prompt em INPUT.TXT.
  2. DOSBox roda GPT2.EXE com alguma rotina de leitura.
  3. A saída vai para OUTPUT.TXT.
  4. Python lê, limpa e mostra.

Fluxo:

Python -> INPUT.TXT -> DOSBox/GPT2.EXE -> OUTPUT.TXT -> Python -> usuário

Exemplo conceitual:

import subprocess
from pathlib import Path

def generate_pet_speech(prompt: str) -> str:
    input_path = Path("dosbox/C/INPUT.TXT")
    output_path = Path("dosbox/C/OUTPUT.TXT")

    input_path.write_text(prompt, encoding="utf-8")

    subprocess.run(
        ["dosbox", "-conf", "dosbox/dosbox.conf", "-exit"],
        timeout=30,
        check=False,
    )

    raw = output_path.read_text(encoding="utf-8", errors="ignore")
    return clean_model_output(raw)

Na prática, pode ser necessário adaptar conforme o modo real de execução do GPT2-BASIC.


Filtros e pós-processamento

Como o modelo é pequeno, ele pode gerar porcaria.

Então o sistema precisa limpar.

Regras simples:

Exemplo de fallback:

fallbacks = {
    "hungry": [
        "Estou com fome o bastante para mastigar um arquivo .BAT.",
        "Minha barriga fez um beep triste.",
        "Preciso de comida, não de filosofia."
    ],
    "sleepy": [
        "Meus olhos são dois cursores piscando devagar.",
        "Estou quase entrando em modo suspenso.",
        "Se eu apagar, não foi drama. Foi bateria."
    ]
}

Isso é obrigatório. Sem fallback, uma hora o modelo vai cuspir lixo e quebrar a experiência.


Fallbacks são parte do design

O pet não deve depender 100% do modelo.

Se o GPT falhar, o bicho continua vivo.

def speak(intent, prompt):
    try:
        text = generate_pet_speech(prompt)
        text = clean_model_output(text)

        if not acceptable(text):
            raise ValueError("bad generation")

        return text

    except Exception:
        return random.choice(FALLBACKS[intent])

Isso evita que a experiência quebre.

E, sinceramente, para um pet, frases prontas boas misturadas com geração ocasional podem ser melhores do que geração fraca o tempo todo.


Interface visual

Versão terminal

A primeira versão deve ser terminal puro.

   /\_/\
  ( o.o )   Nix
   > ^ <

Fome:    ███████░░░ 70
Humor:   ████░░░░░░ 40
Sono:    █████░░░░░ 50
Vínculo: ██████░░░░ 60

Versão OLED

Em Raspberry Pi com telinha OLED I2C:

Versão e-paper

E-paper combina muito com o projeto:

Versão web local

Uma rota simples:

http://raspberrypi.local:8787

Mostra:


Hardware sugerido

Versão mínima

Item Observação
Raspberry Pi Zero 2 W suficiente para terminal e DOSBox leve
MicroSD 16GB+ melhor usar cartão bom
Fonte decente evite corrupção de SD
SSH interface principal

Versão confortável

Item Observação
Raspberry Pi 4 ou 5 mais folga para DOSBox e interface
OLED I2C 128x64 rosto/status
Botões físicos feed/play/talk
Speaker pequeno beeps e sons
Case impresso vira objeto

Versão bonita

Item Observação
Raspberry Pi Zero 2 W ou Pi 4 depende da interface
E-paper 2.13" ou 2.9" visual permanente
Botões arcade pequenos interação física
Buzzer som retrô
Bateria UPS HAT portabilidade

Eficiência real

Aqui entra a parte sem romantizar.

Rodar GPT2-BASIC dentro do DOSBox no Raspberry Pi não é a opção mais eficiente.

Existe overhead de emulação. Um modelo pequeno nativo em Linux provavelmente seria mais rápido e mais simples de integrar.

Mas o objetivo aqui não é vencer benchmark.

O objetivo é:

Se a meta for eficiência pura, use um modelo pequeno nativo.
Se a meta for encanto, DOSBox faz sentido.


Modos de funcionamento

Modo offline

O pet funciona sozinho no Pi, sem internet.

systemd inicia shellgotchi-daemon
estado é atualizado a cada minuto
interface via SSH ou tela local
GPT2-BASIC é chamado sob demanda

Modo terminal compartilhado

Bom para pubnix ou servidor comunitário.

Cada usuário pode ter seu próprio pet:

/home/pablo/.shellgotchi/pet.sqlite
/home/alice/.shellgotchi/pet.sqlite
/home/bob/.shellgotchi/pet.sqlite

Isso combinaria muito com runv.club.

Modo objeto físico

O Raspberry Pi vira um aparelho de mesa:

Modo servidorzinho web

O pet mora em uma página local.

A interface web apenas manda comandos para o núcleo.


Estrutura inicial de arquivos

shellgotchi/
├── README.md
├── pyproject.toml
├── shellgotchi.py
├── config/
│   └── personality.yaml
├── data/
│   └── pet.sqlite
├── prompts/
│   ├── talk.txt
│   ├── hungry.txt
│   ├── sleepy.txt
│   └── event.txt
├── dosbox/
│   ├── dosbox.conf
│   ├── run_gpt2.sh
│   └── C/
│       ├── GPT2.EXE
│       ├── CWSDPMI.EXE
│       └── MODEL/
├── interfaces/
│   ├── cli.py
│   ├── oled.py
│   └── web.py
└── systemd/
    ├── shellgotchi.service
    └── shellgotchi.timer

MVP realista

A primeira versão não deve tentar fazer tudo.

MVP 1: terminal local

Sem GPT ainda.

Motivo: primeiro faça o jogo funcionar.

MVP 2: integração com GPT2-BASIC

MVP 3: personalidade e memória

MVP 4: hardware

MVP 5: modo pubnix


Riscos

Risco Gravidade Mitigação
GPT2-BASIC gerar texto ruim Alta pós-processamento e fallbacks
Integração DOSBox ser chata Média wrapper simples por arquivo
Lentidão Média limitar geração a frases curtas
Corrupção de SD Média SQLite com cuidado e backups
Projeto virar grande demais Alta MVP pequeno primeiro
Pet ficar sem graça Alta eventos, personalidade e memória
Português ruim Média treinar/focar prompts e fallbacks em pt-BR

Sistema de eventos

Eventos aleatórios deixam o pet vivo.

Exemplos:

Nix encontrou um arquivo perdido.
Nix dormiu em cima do teclado.
Nix ficou encarando o cursor por vinte minutos.
Nix sonhou com um modem.
Nix derrubou migalhas em /tmp.
Nix pediu para não ser atualizado hoje.

Eventos podem mudar estado:

Evento Efeito
cochilo espontâneo energia +10, sono -15
crise de tédio humor -8
sonho bom humor +5
fome noturna fome +12
bug imaginário curiosidade +6
visita do usuário vínculo +2

Possível estética

A estética ideal seria:

Exemplo:

╔════════════════════════════════════╗
║ NIX.EXE                            ║
║ estado: acordado                   ║
║ humor : levemente hostil           ║
╚════════════════════════════════════╝

   .-.
  (o o)    "eu sonhei com uma pasta vazia."
  | O \
   \   \
    `~~~'

Instalação imaginada no Debian/Raspberry Pi OS

sudo apt update
sudo apt install -y python3 python3-venv python3-pip dosbox sqlite3 git

git clone https://github.com/pablomurad/shellgotchi.git
cd shellgotchi

python3 -m venv .venv
. .venv/bin/activate
pip install -r requirements.txt

cp config/personality.example.yaml config/personality.yaml

python shellgotchi.py init
python shellgotchi.py status
python shellgotchi.py feed
python shellgotchi.py talk

Depois:

sudo cp systemd/shellgotchi.service /etc/systemd/system/
sudo cp systemd/shellgotchi.timer /etc/systemd/system/
sudo systemctl daemon-reload
sudo systemctl enable --now shellgotchi.timer

Possível integração com runv.club

Esse projeto encaixa muito bem em uma pubnix.

Cada usuário poderia ter seu próprio pet terminal.

$ shellgotchi adopt
Você adotou um bicho chamado Nix.

$ shellgotchi status
Nix está com sono e quer que você pare de rodar comandos como root.

Ideias para comunidade:

Mas cuidado: ranking pode transformar algo poético em competição boba. Melhor manter leve.


Roadmap

Fase 1: protótipo jogável

Fase 2: fala com GPT2-BASIC

Fase 3: memória

Fase 4: objeto físico

Fase 5: modo servidor


Métrica de sucesso

O projeto deu certo se:

O projeto deu errado se:


Decisão técnica principal

A melhor decisão é construir em duas camadas:

Camada 1: simulação confiável
- regras
- estado
- tempo
- memória
- comandos
- banco de dados

Camada 2: fala instável e charmosa
- GPT2-BASIC
- prompts curtos
- personalidade
- fallbacks

Essa arquitetura assume a limitação do modelo em vez de fingir que ela não existe.

Isso é o que torna a ideia viável.


Veredito

A ideia é excelente como projeto experimental, artístico e técnico.

Não é eficiente no sentido bruto. Não é a maneira mais racional de rodar IA local. Não é um assistente útil.

Mas como bichinho terminal retrô em Raspberry Pi, com DOSBox, GPT2-BASIC, memória simples e personalidade esquisita, é forte.

É o tipo de projeto que combina:

O segredo é não tentar fazer um gênio.

Faça uma criatura pequena.

Uma criatura pequena, limitada, persistente, meio faminta, meio poética, que mora em /home/pablo e reclama quando você some.

Nota lateral: por que GPT2-BASIC aqui faz sentido mesmo sendo limitado?

Porque a limitação vira linguagem.

Um modelo moderno pode gerar uma resposta perfeita demais e matar a estranheza. O GPT2-BASIC, por ser pequeno, tende a frases curtas, repetitivas e imperfeitas. Para atendimento isso é ruim. Para um bicho digital antigo, isso pode ser ótimo.

A experiência não precisa convencer ninguém de que há uma inteligência real ali. Ela precisa fazer o usuário querer voltar amanhã para ver como o pet está.


Próximo passo sugerido

Criar primeiro um protótipo sem GPT:

shellgotchi.py init
shellgotchi.py status
shellgotchi.py feed
shellgotchi.py talk

Depois que o pet estiver vivo com regras, aí sim conectar o GPT2-BASIC como voz.

Começar pelo modelo seria erro. Comece pela criatura.

View the original Markdown file


Ideas | What changed | RSS | About | Text version

Pablo Murad <pablomurad@pm.me>