segunda-feira, 15 de agosto de 2016

[Advpl] Manipulação de Arquivos


Fala galera!

Vamos trocar uma ideia hoje sobre manipulação de arquivos utilizando a linguagem Advpl. Antes de começar a codificar, preciso apresentar o motivo que originou esse post.



Na empresa onde trabalho, havia a necessidade do usuário obter um arquivo que é salvo pelo sistema em sua pasta no servidor.  E para que isso fosse possível, o usuário utilizava de um arquivo .bat - veja mais sobre arquivos bat nesses posts - que automatizava  o processo, ou seja, buscava o arquivo no servidor, renomeava e salvava no desktop do usuário.

Então, utilizando deste cenário, poderemos aprender várias funções de manipulação de arquivo com Advpl.

Primeiramente vamos desenvolver a tela principal do nosso programa, onde teremos um combo-box com as opções de arquivos que iremos recuperar/pegar do servidor e dois botões, um para confirmar e outro para sair.

Nossa tela será exibida da seguinte forma:



Aqui está o código para que a tela seja gerada:

/*
_____________________________________________________________________________
¦¦¦¦¦¦¦¦¦¦¦¦¦¦¦¦¦¦¦¦¦¦¦¦¦¦¦¦¦¦¦¦¦¦¦¦¦¦¦¦¦¦¦¦¦¦¦¦¦¦¦¦¦¦¦¦¦¦¦¦¦¦¦¦¦¦¦¦¦¦¦¦¦¦¦¦¦
¦¦+-----------------------------------------------------------------------+¦¦
¦¦¦Programa  ¦ BUSARQ     ¦ Autor ¦ Renan R. Ramos      ¦ Data ¦ 11.08.16 ¦¦¦
¦¦¦----------+------------------------------------------------------------¦¦¦
¦¦¦Descriçäo ¦ Rotina para recuperar arquivo do servidor para o computador¦¦¦
¦¦¦          ¦ do usuário.                                                ¦¦¦
¦¦+-----------------------------------------------------------------------+¦¦
¦¦¦¦¦¦¦¦¦¦¦¦¦¦¦¦¦¦¦¦¦¦¦¦¦¦¦¦¦¦¦¦¦¦¦¦¦¦¦¦¦¦¦¦¦¦¦¦¦¦¦¦¦¦¦¦¦¦¦¦¦¦¦¦¦¦¦¦¦¦¦¦¦¦¦¦¦
¯¯¯¯¯¯¯¯¯¯¯¯¯¯¯¯¯¯¯¯¯¯¯¯¯¯¯¯¯¯¯¯¯¯¯¯¯¯¯¯¯¯¯¯¯¯¯¯¯¯¯¯¯¯¯¯¯¯¯¯¯¯¯¯¯¯¯¯¯¯¯¯¯¯¯¯¯
*/
user function busArq

private oWinMain                               
private oCombo
private cCombo := ""
private aOpcoes := {"1=Arquivo_1","2=Arquivo_2"}

define msDialog oWinMain title "" from 000,000 to 210,250 pixel of oWinMain

 @005,005 to 100,120 LABEL "Busca arquivo" pixel of oWinMain

 oCombo := TComboBox():New(030,014,{|u|if(PCount()>0,cCombo := u,cCombo)},aOpcoes,100,20,oWinMain,,{||},,,,.T.,,,,,,,,,'cCombo') 
 
 @075,020 button "Confirmar" size 040,010 pixel of oWinMain action getArq(val(cCombo)) 
 @075,065 button "Sair" size 040,010 pixel of oWinMain action close(oWinMain)
  
activate msDialog oWinMain centered

return

No botão "Confirmar" possuímos o método getArq(val(cCombo)) que será o principal método da nossa rotina. Ele efetuará toda a transição e manipulação dos arquivos.
A seguir vocês podem visualizar o código completo com explicações em seus comentários.

/*
_____________________________________________________________________________
¦¦¦¦¦¦¦¦¦¦¦¦¦¦¦¦¦¦¦¦¦¦¦¦¦¦¦¦¦¦¦¦¦¦¦¦¦¦¦¦¦¦¦¦¦¦¦¦¦¦¦¦¦¦¦¦¦¦¦¦¦¦¦¦¦¦¦¦¦¦¦¦¦¦¦¦¦
¦¦+-----------------------------------------------------------------------+¦¦
¦¦¦Programa  ¦ GETARQ     ¦ Autor ¦ Renan R. Ramos      ¦ Data ¦ 11.08.16 ¦¦¦
¦¦¦----------+------------------------------------------------------------¦¦¦
¦¦¦Descriçäo ¦ Função responsável por efetuar a cópia dos arquivos.       ¦¦¦
¦¦+-----------------------------------------------------------------------+¦¦
¦¦¦¦¦¦¦¦¦¦¦¦¦¦¦¦¦¦¦¦¦¦¦¦¦¦¦¦¦¦¦¦¦¦¦¦¦¦¦¦¦¦¦¦¦¦¦¦¦¦¦¦¦¦¦¦¦¦¦¦¦¦¦¦¦¦¦¦¦¦¦¦¦¦¦¦¦
¯¯¯¯¯¯¯¯¯¯¯¯¯¯¯¯¯¯¯¯¯¯¯¯¯¯¯¯¯¯¯¯¯¯¯¯¯¯¯¯¯¯¯¯¯¯¯¯¯¯¯¯¯¯¯¯¯¯¯¯¯¯¯¯¯¯¯¯¯¯¯¯¯¯¯¯¯
*/
static function getArq(nNumOpc)
  
local cArquivo := ""
local cNomeArq := ""
local lCompacta := .T.
local lSuccess := .T.
local nRetorno := 0
local cTemp1 := getTempPath()
local cTemp := substr(cTemp1,1,AT("\AppData",cTemp1))+"desktop\"
    
//obtém as informações do usuário logado no protheus
PswOrder(2)

if PswSeek(cUsername, .T.) 
 //array com todas as informações de configuração do usuário
 aArray := PswRet()
endIf

//verifica se existe configurado um diretório de impressão 
//do sistema para este usuário
if !empty(allTrim(aArray[2][3]))
           
 //se escolha por Arquivo_1
 if nNumOpc = 1 
    cArquivo := "Arquivo_1.txt"
    cNomeArq := "\PRIMEIRO_ARQUIVO.txt"
 else//se escolha por Arquivo_2
    cArquivo := "Arquivo_2.txt"
    cNomeArq := "\SEGUNDO_ARQUIVO.txt"
 endIf                   
 
 //se o arquivo já existe, ele é deletado
 if file(cTemp+cArquivo)
     fErase(cTemp+cArquivo)
 endIf
    
 //se a cópia foi efetuada com sucesso, o método CpyS2t() retorna .T.
 lSuccess := CpyS2T(allTrim(aArray[2][3])+cArquivo,cTemp,lCompacta)

 if lSuccess
  //se o arquivo já existe, ele é deletado
  if file(cTemp+cNomeArq)
      fErase(cTemp+cNomeArq)
  endIf
        
  //se o arquivo foi renomeado, o método fRename() retorna 0
     nRetorno := fRename(cTemp+cArquivo,upper(cTemp+cNomeArq))

  //se renomear o arquivo estiver ok retorna 0   
  if nRetorno = 0
   msgInfo("Arquivo salvo com sucesso!")
  endIf
 else
  msgInfo("Arquivo não copiado!")
 endIf
else
 msgInfo("Verificar configurações de pasta do usuário no servidor")
endIf

return

Para definirmos em qual local do computador será salvo o arquivo, utilizamos o método getTempPath(), mas como desejamos salvar no desktop do usuário, utilizamos o código abaixo para substituir a string do diretório obtido e adicionamos a string "\desktop" e assim teremos o nosso diretório final.

local cTemp1 := getTempPath() //obtém o diretório temporario do usuario logado no sistema
local cTemp := substr(cTemp1,1,AT("\AppData",cTemp1))+"desktop\" //obtemos a posição da pasta "\AppData" e adicionamos a string "\desktop\"

Explicação rápida de algumas funções utilizadas:

  • PswOrder: seleciona a ordem de pesquisa de usuário. Em nosso fonte utilizamos a ordem 2 que é feita por nome de usuário.
  • PswSeek: pesquisa e posiciona o arquivo de senhas de acordo com a ordem definida pela função PswOrder.
  • PswRet: retorna um vetor com as informações do usuário;
  • File: verifica se o arquivo existe no diretório informado;
  • FErase: apaga o arquivo no diretório informado;
  • FRename: renomeia o arquivo original do primeiro parâmetro de acordo com o outro informado no segundo parâmetro.
  • CpyS2t: faz a cópia do diretório do servidor no primeiro parâmetro para o diretório de destino que deve ser colocado no segundo parâmetro.

Para obter mais informações sobre todas essas funções, acesse o TDN Totvs.

É isso ai galera! Um fonte fácil e simples que poderá ser de grande utilidade não só para este contexto que passei, mas para qualquer outra necessidade de manipulação de arquivo.

Deixe seu comentário, crítica ou sugestão!

Até mais!

;)
Renan Rodrigues Ramos Desenvolvedor

Sou desenvolvedor, amo desenvolvimento de software, músico e apaixonado por filmes e seriados.