Office System

The Office Developer Blog (by Luiz Cláudio C. V. Rocha - São Paulo, Brazil)

Como evitar processos pendurados na automação do Excel

 

Em linhas gerais, a automação é o mecanismo que permite um aplicativo (chamado cliente) acessar e manipular objetos e recursos de outro aplicativo (chamado servidor). Via de regra, a automação é algo tecnicamente complexo nos bastidores, pois pode envolver diversas interfaces entre cliente, servidor e sistema operacional.

O Office é um dos mais importantes (se não o mais importante) servidores de automação, pois além de oferecer recursos avançados (editor de textos, planilha eletrônica/gráficos, apresentações, etc.) que complementam vários tipos de soluções, conseguiu encapsular a complexidade da automação tornando-a bastante simples ao desenvolvedor. Se compararmos o MS-Office a outros pacotes concorrentes, a facilidade na programação agrega mais valor ainda ao MS-Office, já que praticamente todos seus recursos estão disponíveis programaticamente.

De todas as ferramentas do pacote Office, o Excel é a mais usada como servidor de automação, especialmente por ser um produto muito versátil (troca de dados, cálculos, gráficos, relatórios, etc.) e usado no mercado em praticamente todos os ramos de atividade.

 

Abrir e fechar o aplicativo servidor

Embora a automação do Office seja fácil de se implementar, o desenvolvedor necessita de uma atenção especial: ao abrir um aplicativo, deve cuidar de fechá-lo.

De certa forma, a automação funciona como se um usuário abrisse e manipulasse o aplicativo servidor. Se pegarmos o Excel como exemplo, a automação funciona de maneira semelhante a um usuário que aciona a aplicação Excel, abre uma pasta de trabalho, escolhe uma planilha, lê e preenche células. Assim, um processo do Excel é iniciado no Windows e, quando o usuário fecha o Excel, o processo é finalizado.

 

 

Nos cenários de automação, porém, é muito comum o aplicativo servidor ser executado nos bastidores, de forma invisível ao usuário que, na maioria das vezes, nem sabe que o Excel (ou seja lá qual aplicativo for) está sendo executado. Se o usuário não tem a janela do Excel ativa para poder fechar, quem deve fazer isto é a própria aplicação que o abriu, caso contrário o processo ficará pendurado no Windows. Além de consumir memória, isto pode ter um efeito mais nocivo: deixar a pasta de trabalho do usuário bloqueada de forma que ele não consiga acessá-la nem abrindo o Excel manualmente, nem por outro processo de automação.

 

 

Este erro é bastante comum nos fóruns de discussão: “[meu arquivo] está bloqueado para edição”. O usuário diz que fechou todos os programas (e de fato fechou), abriu seu arquivo do Excel e recebeu esta mensagem de erro.

Ao abrirmos o Windows Task Manager na guia processos e classificarmos por nome da imagem, encontramos repetidas vezes o “EXCEL.EXE”. Finalizamos os processos e, momentaneamente, o problema está resolvido. Mais tarde, porém, o problema volta a se repetir. Motivo: algum aplicativo que usa o Excel como servidor de automação está falhando em fechá-lo. Geralmente ocorre algum erro em tempo de execução no código depois que a aplicação foi instanciada, deixando-a pendurada.

 

Como evitar o processo pendurado

Para evitar este cenário descrito acima, recomendo uma destas duas práticas, por ordem de prioridade:

a)      Trazer a aplicação Excel para a tela do usuário: se o objetivo da rotina de automação for preparar um arquivo e exibir o resultado final ao usuário, nada mais óbvio que torná-lo visível, certo? Porém, muitas vezes o desenvolvedor não faz isto: ele abre o Excel, executa as rotinas de preenchimento, salva, fecha e, por fim, executa o comando Shell para abrir o arquivo em uma nova instância do Excel.

O que recomendo, nestes casos, é deixar visível a própria instância usada no preenchimento, e fazer isto logo no início do código. Desta forma, se ocorrer algum erro durante a execução do código, o processo não ficará perdido no Windows, pois o usuário terá domínio da janela.

 

Sub MySub1()

Dim xlApp As Excel.Application

Dim xlWkb As Excel.Workbook

 

On Error GoTo ErrHandler

 

'Instancia o Excel

Set xlApp = New Excel.Application

 

'Deixa o Excel visível para o usuário

xlApp.Visible = True

 

'Seu código aqui...

 

ExitHere:

Exit Sub

 

ErrHandler:

MsgBox Err.Description & vbCrLf & Err.Number & vbCrLf & Err.Source, vbCritical, "MySub"

Resume ExitHere

End Sub

 

 

b)      Controlar se a aplicação está instanciada e fazer a finalização no tratamento de erro: é comum alguns desenvolvedores colocarem um comando para finalizar (Quit) o Excel no tratamento de erro. Porém, se o erro ocorrer por outro motivo que não a automação e o Excel não tiver instanciado no momento, este tratamento vai gerar outro erro (“Object variable or With block variable not set”):

 

 

 

Para que não ocorra este erro, o mais correto é, antes de fazer o Quit, verificar se o Excel foi instanciado:

 

Sub MySub2()

Dim xlApp As Excel.Application

Dim xlWkb As Excel.Workbook

Dim blnIsOpen As Boolean

 

On Error GoTo ErrHandler

 

'Instancia o Excel

Set xlApp = New Excel.Application

blnIsOpen = True

 

'Seu código aqui...

 

 

'Finaliza a aplicação

xlApp.Quit

blnIsOpen = False

 

ExitHere:

Exit Sub

 

ErrHandler:

 

'Verifica se o Excel está instanciado

If blnIsOpen = True Then

    xlApp.Quit

End If

MsgBox Err.Description & vbCrLf & Err.Number & vbCrLf & Err.Source, vbCritical, "MySub"

Resume ExitHere

End Sub

 

 

Conclusão

Estas duas técnicas são bastante simples, mas ajudam a evitar problemas muito comuns e recorrentes quando fazemos automação de aplicativos, especialmente do Excel. Podem ser usadas a partir de qualquer linguagem, seja VBA (como nos exemplos acima), seja VB6, VB.Net, C# ou outra linguagem.

 

Leave a Comment

(required) 

(required) 

(optional)

(required) 

If you can't read this number refresh your screen
Enter the numbers above: