Script para Verificar a Bateria do Notebook [Shell Script]

Eu precisei usar o PostyBirb, um programa que posta as artes colocadas nele em diversos sites a sua escolha, e até onde sei esse programa precisaria estar com o computador ligado para ele funcionar.

Assim eu fiz, desativei a suspensão automática do notebook e deixei ele ligado durante a noite toda com esse programa, e de manhã eu ainda tinha uma bateria restante. E tive uma ideia: Por que não fazer um script para gerar um registro de como está a bateria e do consumo do notebook de tempos em tempos?

Dependências

Esse Script tem as seguintes dependências:

  • acpi: Para mostrar o tempo restante e a porcentagem atual da bateria
  • upower: Para mostrar a taxa de Carga/Descarga da bateria

Precisei usar duas ferramentas diferentes, pois o acpi não tinha a informação da Taxa de Descarga/Carga da Bateria e não gosto muito da forma que o upower mostra a informação do tempo restante.

Usando o Script

O melhor nome para salvar esse Script, seria bateria.sh, pois foi assim que me referi a esse script em alguns textos de instrução dentro dele. Também, precisa dar a permissão de execução (chmod +x bateria.sh).

E esse Script tem quatro formas em que ele pode funcionar

  • ./bateria.sh: Nessa forma, o script vai apenas gerar essa saída, com a data e hora em que o script foi executado, a porcentagem atual da bateria, o tempo restante e a taxa em que a bateria está descarregando/carregando:

Saída básica do Script

  • ./bateria.sh -l [VEZES]: Nessa forma, o Script irá criar uma pasta Logs na Pasta Pessoal do usuário e irá gerar um arquivo de Log com a data e hora em que o script foi executado. Os registros são feitos a cada 5 minutos. Para gerar 10 registros, o comando seria ./bateria.sh -l 10.

  • ./bateria.sh -ut [VEZES] [INTERVALO]: Funciona quase da mesma forma que o ./bateria.sh -l, mas o intervalo pode ser personalizado. Para gerar 10 registros a cada 15 minutos, o comando seria ./bateria.sh -ut 10 15

-./bateria.sh -b [BATERIA]: Esse modo gera registros a cada 1 minuto até a bateria atingir a porcentagem desejada. Se não entrar com a porcentagem, o script irá fazer registros até a bateria atingir 20% restantes. Para gerar registros até a bateria atingir 50%, o comando seria ./bateria.sh -b 50

E o Arquivo de Log se parecerá mais ou menos assim:

Palavras Finais

Esse foi um pequeno experimento que gostei de fazer e decidi compartilhar. Sei que tem algumas coisas a serem melhoradas, mas creio que isso poderia ajudar alguém que precisasse monitorar o consumo da bateria do notebook.

O Script

O código do Script está logo abaixo e está disponível no Pastebin

Código do Script
#!/bin/bash

batStatus () {
	#Extraindo a Porcentagem Atual da Bateria do acpi
	BatAtual=`acpi -b | gawk -F ',' -P '{ print $2 }' | gawk -P '{ print $1 }'`

	#Extraindo o tempo restante do acpi
	TempoRestante=`acpi -b | gawk -P '{ print $5 }'` 

	#Extraindo a Taxa de Carregamento/Descarregamento da Bateria
	Taxa=`upower -i /org/freedesktop/UPower/devices/battery_BAT0 | grep -e 'energy-rate' | gawk -F ':' -P '{ print $2 }' | sed 's/ //g'` 

	echo "["`date +"%d-%m-%Y - %H:%M:%S"`"]" # Exibe a Data
	echo "Bateria Atual:" $BatAtual #Exibe a porcentagem da bateria
	echo "Tempo restante:" $TempoRestante #Exibe o tempo restante
	echo "Taxa:" $Taxa #Exibe a Taxa de Descarregamento
}

ajudaComandos () {
	echo "
Uso: ./bateria.sh [OPÇÕES]
Opções:
	-l	Registra o estado da Bateria a cada 5 minutos na pasta ~/Logs por algumas vezes.
	-ut	Registra o estado da Bateria por algumas vezes pelo intervalo definido pelo usuário
	-b	Registra o estado da Bateria a cada um minuto na pasta ~/Logs até a bateria atingir a porcentagem restante desejada. O valor padrão é 20%
	-h	Exibe essa tela com as opções disponíveis
"
}

criarLog () {
	if [ -d ~/Logs ]; then # Verificando se a pasta de Logs existe
		echo "" > /dev/null # Jogando a saída fora para prosseguir com o Script
	else 
		mkdir ~/Logs # Se não existe, criar a pasta de Logs
	fi

	Arquivo=~/Logs/Bat_`date +"%d-%m-%Y_%H-%M-%S"`.txt #Variável com a Data do Arquivo de Log

	touch $Arquivo # Criando o Arquivo
}

if [ $# -lt 1 ]; then # Se não tiver argumentos, executar o script normalmente
		batStatus
		exit 1
fi

if [ $1 == "-l" ]; then
	if [ $# -lt 2 ]; then # Verificando se tem as vezes em que o Log será registrado
		echo "Faltou o número de vezes em que o estado da Bateria será registrado.

Uso: ./bateria.sh -l [VEZES]
Exemplo: \"./bateria.sh -l 5\" para fazer cinco registros do estado da Bateria na pasta ~/Logs
"
		exit 1
	fi
	echo "O Log começou a ser gerado em:" `date +"%d-%m-%Y às %H:%M:%S"` "
E serão feitos" $2 "registros com um intervalo de 5 minutos entre cada um deles"
	
	criarLog
	batStatus >> $Arquivo
	
	for ((  runs=1 ; runs<=$2-1 ; runs++ )); do # Jogando a saída para o arquivo de Log
		echo "" >> $Arquivo
		sleep 300
		batStatus >> $Arquivo
	done
	
elif [ $1 == "-ut" ]; then
	if [ $# -lt 3 ]; then # Verificando se tem as vezes em que o Log será registrado
		echo "Faltou o número de vezes em que o estado da Bateria será registrado e o intervalo dos registros.

Uso: ./bateria.sh -ut [VEZES] [INTERVALO]
Exemplo: \"./bateria.sh -ut 5 10\" para fazer cinco registros do estado da Bateria na pasta ~/Logs com um intervalo de 10 minutos a cada registro"
		exit 1
	fi
	echo "O Log começou a ser gerado em:" `date +"%d-%m-%Y às %H:%M:%S"` "
E serão feitos" $2 "registros com um intervalo de" $3 "minutos entre cada um deles"

	criarLog
	batStatus >> $Arquivo
	
	for ((  runs=1 ; runs<=$2-1 ; runs++ )); do # Jogando a saída para o arquivo de Log 
		echo "" >> $Arquivo
		sleep $((60 * $3))
		batStatus >> $Arquivo
	done

elif [ $1 == "-b" ]; then
	BatBenchAtual=`acpi -b | gawk -F ',' -P '{ print $2 }' | gawk -P '{ print $1 }' | tr -d '%'` # Verificando o Valor atual da Bateria
	
	if [ $# -lt 2 ]; then # Colocou o valor na hora de dar o comando?
		BatBench=20 # O valor padrão é 20%, que é a Bateria fraca no Gnome
	else
		BatBench=$2 # O valor definido pelo usuário
	fi
	
	criarLog
	
	echo "O Log começou a ser gerado com" $BatBenchAtual"% de Bateria Restante em" `date +"%d-%m-%Y às %H:%M:%S"` " 
E será feito até" $BatBench"% de Bateria restante com registros num intervalo de um minuto entre eles"
	
	batStatus >> $Arquivo	
	until [ $BatBenchAtual == $BatBench ]; do # Um Loop para fazer o Log até a porcentagem do -b
		BatBenchAtual=`acpi -b | gawk -F ',' -P '{ print $2 }' | gawk -P '{ print $1 }' | tr -d '%'`
		sleep 60
		echo "" >> $Arquivo
		batStatus >> $Arquivo
	done
elif [ $1 == "-h" ]; then
	ajudaComandos
else
	echo "Opção Inválida! Consulte a lista de opções usando o -h"
	
	exit 1
fi
7 curtidas

Atualização [30/03/25]

Já faz um bom tempo que fiz esse Script, e tinha duas coisinhas que me incomodaram quando precisei fazer um teste de bateria:

  • Ele não mostrar a duração do teste na opção -b
  • Demorar muito para acabar com o teste na opção -b

E acabei resolvendo esse problema com duas mudanças simples.

Colocando a duração do teste

Eu estava em dúvida em como fazer isso. Até que descobri uma coisinha no comando date. Eu consigo uma data em Unix Epoch com o date +%s, e com isso, eu obtenho uma saída mais ou menos assim:

E com isso, fiz uma adição ao Script: Colocar uma variável com o Unix Epoch de quando o Script começou a rodar e outra de quando o Benchmark terminou. E com essas duas variáveis, tirar a diferença e converter o Unix Epoch para um formato legível.

E a conversão é feita por uma função no Script que é mais ou menos assim:

calcularTempo () {
	Tempo=$(( $1 - $2 )) ## Pegando a Data do Fim e do Início em Unix Epoch para poder calcular a diferença de tempo em segundos

	Horas=$(( $Tempo / 3600 )) ## Calculando Horas. Pegando o tempo em segundos e dividindo por 3600.
	Minutos=$(( ($Tempo - $Horas * 3600) / 60 )) ## Calculando os Minutos. Pegando o Tempo, subtrando as horas e multiplicando por 3600 e por fim, dividindo por 60.
	Segundos=$(( $Tempo % 60 )) ## Calculando os Segundos. Pegando o tempo e extraindo o resto.

	echo -e "${Horas}h:${Minutos}m:${Segundos}s."

}

E assim, pude adicionar essa informação ao Script, deixando ele bem útil. E também me usei do tee para deixar a saída tanto no Terminal como no arquivo de Log.

Fazendo o Script finalizar o Benchmark mais rapidamente

Basicamente, foi uma mudança nessa parte do Script em que ela era assim:

	until [ $BatBenchAtual == $BatBench ]; do 
		BatBenchAtual=`acpi -b | gawk -F ',' -P '{ print $2 }' | gawk -P '{ print $1 }' | tr -d '%'`
		sleep 60
		echo "" >> $Arquivo
		batStatus >> $Arquivo
	done

Basicamente, o Script verificava a bateria, esperava 60 segundos, dava um espaço e registrava o estado da bateria no Log. O que causava situações como essa aqui, onde o Script ao atingir a porcentagem desejada no parâmetro -b, ele fazia dois registros no Log.

[20-02-2025 - 02:00:43]
Bateria Atual: 20%
Tempo restante: 01:41:55
Taxa: 4,846W

[20-02-2025 - 02:01:43]
Bateria Atual: 20%
Tempo restante: 01:43:49
Taxa: 4,854W

E acabei corrigindo essa parte do Script para:

	until [ $BatBenchAtual == $BatBench ]; do 
		BatBenchAtual=`RegistrarBateria`
		sleep 60
		echo "" | tee -a  $Arquivo
		batStatus | tee -a $Arquivo
		BatBenchAtual=`RegistrarBateria`
	done

As únicas mudanças além do tee -a e da função, é que o Script verifica novamente a bateria no final do loop, e quando o Scipt verifica novamente se a porcentagem da bateria é igual ao desejado, ele encerra os registros.

[30-03-2025 - 06:21:07]
Bateria Atual: 7%
Tempo restante: 00:29:34
Taxa: 5,848W

[30-03-2025 - 06:22:07]
Bateria Atual: 6%
Tempo restante: 00:29:33
Taxa: 5,752W


[Final do Benchmark] 
- Horário de Início: 30-03-2025 às 01:01:34 
- Bateria no Início: 90%
- Horário de Término: 30-03-2025 às 06:22:07 
- Bateria no Final: 6%

[O Teste durou 5h:20m:33s.]

Duas pequenas mudanças…

Como tem um comando que é muito usado, decidi fazer ele ser uma função. Para facilitar a manutenção do Script.

RegistrarBateria () {
	acpi -b | gawk -F ',' -P '{ print $2 }' | gawk -P '{ print $1 }' | tr -d '%'
}

Pois fica bem mais fácil chamar o comando pela função do que colocar esse comando inteiro.

E o nome do script foi mudado de bateria.sh para batbench.sh. Justamente, porque a função principal dele é fazer um registro de quanto a bateria durou.

GitHub

E agora, esse Script está também no GitHub.

2 curtidas