Baixe arquivos em pedaços com o DCDownloader
Publicado por Davidson Francis (última atualização em 11/04/2014)
[ Hits: 18.610 ]
O Divide and Conker Downloader (não, não é da Detective Comics, kkk) permite que o download de um arquivo (em link direto) possa ser dividido em n partes de modo que o usuário possa literalmente dividir o download em fragmentos.
Vejo no mínimo duas utilidades interessantes:
- Quando é necessário baixar arquivos realmente grandes e você dispõe de mais de uma conexão com a internet.
Desta forma um arquivo de 10 GB poderia ser facilmente distribuído entre 10 amigos, cada um deles baixando partes diferentes do mesmo arquivo simultaneamente; no término do download, basta fazer a junção das partes e obterá o arquivo original novamente.
- Quando o servidor limita a banda, com o uso de downloads simultâneos pode obter um aproveitamento muito maior da internet em questão. O que ilustro nesse vídeo: https://www.youtube.com/watch?v=aG59N51cWAQ
O script possui basicamente três comandos:
-g url qtd - Nesta opção geramos os arquivos de configuração que serão utilizados em cada máquina separadamente, onde:
url é o link do download e qtd é quantidade de máquinas e/ou instâncias que serão executadas.
-r file - Realiza a leitura do arquivo de configuração, onde file é o arquivo gerado pela opção "-g". Deve-se atentar ao executar o download em pastas separadas, devido aos arquivos auxiliares gerados no processo.
-j - Realiza o "join" de todos os arquivos baixados em um único arquivo.
Um exemplo de uso seria:
$ ./DCDownloader.sh -g http://link/file.tar.gz 2
PC1:
$ ./DCDownloader.sh -r DC1.conf
PC2:
$ ./DCDownloader.sh -r DC2.conf
Posteriormente:
$ ./DCDownloader -j
É isso pessoal, espero que tenham gostado e fico a disposição a quaisquer dúvidas, críticas e sugestões.
#!/bin/bash clear echo "------------------------------------------------" echo " Divide and Conker Downloader, by Theldus" echo "------------------------------------------------" echo "" gerarConfiguracao() { #Verifica se quantidade e valida tam=`curl -sI $1 | grep Content-Length | cut -d ' ' -f 2 | sed 's/\r$//'` tam=`echo "scale=2;$tam/1048576" | bc` tam=`echo "$tam/$2" | bc` if [ $tam -lt 1 ]; then echo "> Por favor, entre com uma distribuicao >= 1MB por execucao" else #Distribuicao de blocos OK if [ $2 -lt 2 ]; then echo "> Escolha algo >=2" else if [ $2 -eq 2 ]; then #Processa = 2,gera config e inicio e fim rm DC1.conf 2>/dev/null rm DC2.conf 2>/dev/null #Inicio echo "start" >> DC1.conf echo $tam >> DC1.conf echo $1 >> DC1.conf echo "1" >> DC1.conf #Final echo "final" >> DC2.conf echo $tam >> DC2.conf echo $1 >> DC2.conf echo "2" >> DC2.conf echo "> Arquivos de configuracao gerados com sucesso" echo "> $[tam*$2] MB divididos em $2 partes de $tam MB cada, :D" echo -e "> Use o arquivo de configuracao para o download individual\n em cada pc" else #Processa > 2 rm DC*.conf 2>/dev/null #Start echo "start" >> DC1.conf echo $tam >> DC1.conf echo $1 >> DC1.conf echo "1" >> DC1.conf quantidade=$[$2-2] indice=2 tam_ac=$tam #Middle while [ $quantidade -gt 0 ] do echo "middle" >> DC$indice.conf echo $tam_ac >> DC$indice.conf echo $[tam_ac+tam] >> DC$indice.conf echo $tam >> DC$indice.conf echo $1 >> DC$indice.conf echo $indice >> DC$indice.conf quantidade=$[quantidade-1] indice=$[indice+1] tam_ac=$[tam_ac+tam] done #Final echo "final" >> DC$indice.conf echo $tam_ac >> DC$indice.conf echo $1 >> DC$indice.conf echo $indice >> DC$indice.conf echo "> Arquivos de configuracao gerados com sucesso" echo "> $[tam*$2] MB divididos em $2 partes de $tam MB cada, :D" echo -e "> Use o arquivo de configuracao para o download individual\n em cada pc" fi fi fi } lerConfiguracao() { if [ -e "$1" ]; then #Verifica o tipo do .conf para processamento individual tipo=`head -n1 $1` echo "Caso esteja executando em uma mesma maquina todos os arquivos de" echo "configuracao, atente-se em executar o script em pastas diferentes!" echo "OK?" read trash if [ "$tipo" == "start" ]; then #Processa inicio tam=`head -n2 DC1.conf | tail -n1` url=`head -n3 DC1.conf | tail -n1` fileName=`echo $url | tr "/" "\n" | tail -n1` echo "PC 1, baixando..." rm wget-log* 2>/dev/null rm $fileName 2>/dev/null pid=`wget -b $url | head -n1 | sed 's/[^0-9]//g'` while [ ! -f $fileName ] do #Sim, nao faz nada,apenas para obter o delay necessario #antes de verificar se arquivo existe echo "nop" > /dev/null done while [ $[`wc -c $fileName | cut -d' ' -f1`/1048576] -lt $tam ] do echo -e "`tail -n1 wget-log`" sleep 1 done kill $pid echo "Download concluindo, limando..." dd if=./$fileName of=./DCDpc1 bs=1M count=$tam 2>/dev/null rm $fileName rm wget-log* 2>/dev/null echo "Parte 1 concluida com sucesso, ;)" else if [ "$tipo" == "middle" ]; then tamStub=`head -n2 $1 | tail -n1` tamBaix=`head -n3 $1 | tail -n1` tamBloco=`head -n4 $1 | tail -n1` url=`head -n5 $1 | tail -n1` fileName=`echo $url | tr "/" "\n" | tail -n1` position=`tail -n1 $1` #Gera um 'stub' rm $fileName 2>/dev/null dd if=/dev/zero of=./$fileName bs=1M count=$tamStub 2>/dev/null echo "PC $position, baixando..." rm wget-log* 2>/dev/null pid=`wget -b -c $url | head -n1 | sed 's/[^0-9]//g'` while [ ! -f "wget-log" ] do #Sim, nao faz nada,apenas para obter o delay necessario #antes de verificar se arquivo existe echo "nop" > /dev/null done while [ $[`wc -c $fileName | cut -d' ' -f1`/1048576] -lt $tamBaix ] do echo -e "`tail -n1 wget-log`" sleep 1 done kill $pid echo "Download concluindo, limando..." dd if=./$fileName of=./DCDtmp$position bs=1M ibs=1M skip=$tamStub 2>/dev/null rm $fileName 2>/dev/null dd if=./DCDtmp$position of=./DCDpc$position bs=1M count=$tamBloco 2>/dev/null rm DCDtmp$position 2>/dev/null rm wget-log* 2>/dev/null echo "Parte $position concluida com sucesso, ;)" else if [ "$tipo" == "final" ]; then tam=`head -n2 $1 | tail -n1` url=`head -n3 $1 | tail -n1` fileName=`echo $url | tr "/" "\n" | tail -n1` position=`tail -n1 $1` #Gera um 'stub' rm $fileName 2>/dev/null dd if=/dev/zero of=./$fileName bs=1M count=$tam 2>/dev/null echo "PC $position, baixando..." rm wget-log* 2>/dev/null pid=`wget -b -c $url | head -n1 | sed 's/[^0-9]//g'` while [ ! -f "wget-log" ] do #Sim, nao faz nada,apenas para obter o delay necessario #antes de verificar se arquivo existe echo "nop" > /dev/null done while [ -n "`pgrep wget | grep $pid`" ] do echo -e "`tail -n1 wget-log`" sleep 1 done echo "Download concluindo, limando..." dd if=./$fileName of=./DCDpcFinal bs=1M ibs=1M skip=$tam 2>/dev/null rm $fileName 2>/dev/null rm wget-log* 2>/dev/null echo "Parte $position concluida com sucesso, ;)" fi fi fi else error fi } Join() { echo "Antes de iniciar-mos o merge, certifique-se de que todos os arquivos" echo "estao em um mesmo diretorio!" echo "OK?" read trash echo "Juntando downloads..." cat DCDpc* > DCDFinal echo "Arquivo finalizado: DCDFinal, tenha um bom dia!" } error() { echo "-----------------------------------------------------------------------------" echo "Parametros incorretos:" echo "DCDownloader [operando] -g, -r" echo "-g url quantidade - (Gera os arquivos de configuracao para cada download)" echo "-r DCx.conf - (Le o x-esimo arquivo de configuracao para efetuar o" echo " download)" echo "-j - (Junta as partes em um unico arquivo novamente)" echo "-----------------------------------------------------------------------------" } if [ "$1" == "-g" ]; then gerarConfiguracao $2 $3 else if [ "$1" == "-r" ]; then lerConfiguracao $2 else if [ "$1" == "-j" ]; then Join else error fi fi fi
Limitando largura de banda com o CBQ
Instalação e configuração do celular Nokia 6670 no Ubuntu 8.10
Sincronizar arquivos com rsync
IP Info - Pesquisa geográfica pelo endereço IP
Compartilhando a tela do Computador no Celular via Deskreen
Como Configurar um Túnel SSH Reverso para Acessar Sua Máquina Local a Partir de uma Máquina Remota
Configuração para desligamento automatizado de Computadores em um Ambiente Comercial
Como renomear arquivos de letras maiúsculas para minúsculas
Imprimindo no formato livreto no Linux
Vim - incrementando números em substituição
Efeito "livro" em arquivos PDF
Como resolver o erro no CUPS: Unable to get list of printer drivers
Preciso resolver um erro de DPKG (1)
Melhores Práticas de Nomenclatura: Pastas, Arquivos e Código (2)
Não to conseguindo resolver este problemas ao instalar o playonelinux (1)
[Python] Automação de scan de vulnerabilidades
[Python] Script para analise de superficie de ataque
[Shell Script] Novo script para redimensionar, rotacionar, converter e espelhar arquivos de imagem
[Shell Script] Iniciador de DOOM (DSDA-DOOM, Doom Retro ou Woof!)
[Shell Script] Script para adicionar bordas às imagens de uma pasta