🏴 English version of this text here!
Não sei vocês, mas eu adoro ter um ambiente de desenvolvimento dockerizado. Não ter que me preocupar com versionamento e dependências quando for pulando de projeto em projeto é muito bom.
Mas algo que eu não gosto tanto assim é quando eu saio do contêiner e mais tarde volto nele e descubro que perdi o histórico de todos os comandos anteriores, então não posso buscar mais nada nem com ctrl+R
nem com seta pra cima
/ctrl+P
. Imagens de dor e sofrimento!
Decidi então tentar manter esse histórico, e para fazer isso, primeiro eu pensei, como que o bash faz pra saber os comandos anteriores?
No fim parece que há uma variável de ambiente chamada HISTFILE
que contém o caminho para um arquivo de texto com o histórico de comandos do bash. Aparentemente, por padrão ela é configurada para $HOME/.bash_history
.
OBS: Se o teu contêiner rodar outro shell diferente do bash, teríamos que descobrir onde que esse outro shell guarda o seu histórico.
Então uma solução que encontrei foi de mudar essa variável de ambiente pra algum outro lugar, algum lugar dentro do diretório do projeto que estou trabalhando pra evitar perdê-lo depois de parar o contêiner.
Vamos supor que a imagem do docker cria um diretório /app
com todo o conteúdo do projeto dentro, eu poderia definir HISTFILE
como sendo /app/.bash_history
, e daí se mapearmos tudo com um volume, vamos ter um histórico persistente entre sessões do docker. O nome do arquivo em si nem precisa ser .bash_history
, poderia ser algo como /app/.docker_bash_history
, por exemplo.
Pra começar um contêiner com uma variável específica, podemos passar a opção -e
:
docker exec -it -e HISTFILE=/app/.bash_history -v <volume> <...outras coisas...>
Se estivermos usando o Docker Compose, podemos ou passar um "env file" (um arquivo com variáveis de ambiente) ou as variáveis diretamente no docker-compose.yml
(ou qualquer outro arquivo de configuração que estejas usando):
# arquivo de configuração de exemplo
services:
app:
build: .
volumes:
- .:/app # mapeando este volume para persistir as modificações no nosso novo arquivo de histórico
command: echo Oi!
env_file: # podemos definir as variáveis dentro deste arquivo .env
- .env
environment: # ou então podemos passá-las diretamente aqui
HISTFILE: /app/.bash_history
Um problema surge com essa solução, entretanto. Agora eu tenho um arquivo novo na raiz do meu projeto, um arquivo que o git vai ver, a menos que eu o coloque no nosso .gitignore
, coisa que eu realmente acho que devíamos. Eu não quero commitar meu histórico e nem quero puxar o histórico de outras pessoas, até porque isso acabaria com o propósito de ter um arquivo de histórico. Além disso, acabei de criar um novo arquivo na raiz, que pode ficar poluindo o diretório base do projeto. Talvez aches um outro lugar melhor para esses arquivos.
E isso é praticamente tudo! Eu não sei o quão ruim ou boa é essa ideia, mas estou gostando até aqui. Eu criei um diretorio novo na raiz do projeto, dotfiles/
, que tem também outros arquivos parecidos, como .irb_history
e .irbrc
em um projeto ruby. Pra conseguir ter isso tudo funcionando, eu tive que adicionar as seguintes linhas ao arquivo dotfiles/.irbrc
:
require 'irb/ext/save-history'
IRB.conf[:SAVE_HISTORY] = 10_000
IRB.conf[:HISTORY_FILE] = ENV['IRB_HISTFILE']
E agora definir não somente a variável HISTFILE
como também
as variáveis IRBRC
e IRB_HISTFILE
, assim:
HISTFILE=/app/dotfiles/.bash_history
IRBRC=/app/dotfiles/.irbrc
IRB_HISTFILE=/app/dotfiles/.irb_history
Uma nota importante sobre o IRB, se você deixar o arquivo .irbrc
na raiz, toda vez que você abrir o IRB, ele vai usar o .irbrc
do projeto, visto que ele é encontrado primeiro. Isso pode não ser desejado, talvez você queira usar o seu próprio IRB normal. Nesse caso, colocar o arquivo .irbrc
dentro de outro diretório, como dotfiles/
, passa a ser essencial.
Obrigado por lerem! (:
Top comments (1)
Muito top, estou salvando na pasta
tmp
do projeto.