UniFi AP manager: como monitorar Wireless Ubiquiti (Unifi APs) via Zabbix

UniFi AP manager: como monitorar Wireless Ubiquiti (Unifi APs) via Zabbix

A Ubiquiti fornece uma gama de produtos Wireless geralmente utilizados por pequenos provedores de acesso à internet. Além da área de comercialização de Acessos à internet, ela vem bastante agressiva para atendimento à área empresarial. Para todos os casos, a empresa apela fortemente ao custo benefício em relação a qualidade x preço: Hardware muito barato, potente e estável, além de Software grátis (para aquisição, uso e atualização).

Controlador Ubiquiti

Controlador Ubiquiti – gerenciador de APs Unifi

Neste tutorial nos focaremos na plataforma Wireless Unifi. Aqui integrarei o Unifi Manager ao Zabbix, trazendo melhorias à gerência Wireless permitindo extrair, visualizar e guardar dados importantes sobre a utilização deste importante parque.

Para melhor aproveitamento deste tutorial é preciso ter experiência com Templates, LLD (configuração no Zabbix) e conhecimento básico de Shell Script (bash).

Motivação

Se já existe um software para gerência fornecido pelo fabricante, porquê reinventar a roda?

  • Para gerência, ele é perfeito:
    • Configuração de todos os APs de forma central (adoção, configuração, atualização, reboot, reset);
    • Análise do parque (área de cobertura, versão dos APs, atividade de clientes);
    • Análise de clientes (conexão atual, histórico e tempos de permanência);
    • Bloqueio de clientes (aplicado uma vez, repassado a todos os APs do parque);
  • Para monitoramento, nem tanto:
    • Os gráficos não são conclusivos;
    • Gráficos são estáticos e limitados (tanto em disposição na tela, quanto mostram dados incorretos);
    • Não é possível ver os dados “granulados” (somente diário e mensal);
    • Não é possível ver nos últimos minutos, dados sobre clientes por SSID;
    • Dados históricos “bagunçados”.

Foco

Neste tutorial, demonstrarei a capacidade do Zabbix monitorar os seguinte itens:

  • Relacionado aos APs:
    • Lista completa de APs (texto);
    • Quantidade total de APs;
    • Quantidade de APs ativos;
    • Estado dos APs (via ICMP-ping).
  • Relacionado aos SSIDs (WLANs):
    • Quantidade total de SSIDs;
    • Lista completa de SSIDs (texto);
  • Em relação aos clientes:
    • Quantidade total de Clientes (considerando todo o parque);
    • Quantidade de clientes em cada AP;
    • Quantidade de clientes em cada SSID (independente da quantidade de APs no SSID).

Recursos

Para viabilizar o acesso aos dados, foram utilizados os seguintes recursos:

  • Controlador Unifi instalado em um CentOS 6.6 (x86_64)
    • Testado nas versões do Unifi 3.2.1 , 3.2.5 , 3.2.7 e 3.2.10, com algumas alterações à partir da 3.2.7 (que serão comentadas adiante);
    • Cliente Zabbix (testado nas versões 2.2.5 e 2.4.5) instalado no mesmo servidor que roda o Controlador Unifi (também pode ser utilizado outro computador para pegar os dados do controlador);
    • Diretório scripts criando dentro da raiz de instalação do Zabbix (por exemplo: /etc/zabbix/scripts ou outro, de acordo com a sua instalação);
    • Python 2.6 (talvez funcione com versões mais novas);
    • pip (um gerenciador de pacotes para Python);
    • Pacote Python unifi (instalado via ‘pip’): aplicação desenvolvida em Python para acesso aos dados da API Unifi;
  • Scripts, desenvolvidos por mim, que acessam os dados do controlador e devolvem ao servidor Zabbix
    • Utilização de LLD (Low Leve Discovery) para descoberta automática de novos itens;
    • Descoberta automática de novas WLANs e novos APs.
  • Arquivo com “UserParameter” para ativar as novas funcionalidades (novos itens do Zabbix)
    • Arquivo com as chamadas aos Scripts citados acima para recuperação de informações.
  • API UNIFI (aberta, por padrão)
    • Fonte de dados fornecida pela Ubiquiti (no controlador) para estender as capacidades e possibilidades de seus Softwares.
  • Servidor Zabbix (testado nas versões 2.2.5 e 2.4.5)
    • Sendo o primeiro teste, recomenda-se utilizar uma instalação do Zabbix server específica para testes com o intuito de não ter nenhum tipo de problema com o server de produção;
    • Com um template criado especificamente para monitoramento do controlador Unifi.

Atenção 1: Os scripts não conseguem trabalhar com nomes (para APs ou WLANs) que possuam dois pontos (“:”), acentos ou caracteres especiais (como “Salão de Festas 01” ou “AP do Terraço”, por exemplo). Antes de prosseguir, altere todos os identificadores.

Atenção 2: De acordo com alguns testes, não foi possível integrar a solução quando o controlador está instalando em Windows (reportado pelo usuário Victor nos comentários).

Preparação/Instalação

Com o controlador instalado e funcionando, será preciso instalar as dependências (logado como root ou utilizando o ‘sudo’).

Instalando o ‘pip’:

yum install -y python-pip

Resultado:

Dependências resolvidas
=================================================================================
 Pacote Arq. Versão Repo Tam.
=================================================================================
Instalando:
 python-pip noarch 1.3.1-4.el6 epel 330 k
Instalando para as dependências:
 python-setuptools noarch 0.6.10-3.el6 base 336 k
Resumo da transação
=================================================================================
Install 2 Package(s)

Obs: Para ver uma lista de comandos suportados pelo ‘pip’, utilize “pip -h”.

Instalando pacote ‘unifi’ via ‘pip’:

pip install unifi

Resultado:

Downloading/unpacking unifi
 Downloading unifi-1.2.2.tar.gz
 Running setup.py egg_info for package unifi
Installing collected packages: unifi
 Running setup.py install for unifi
 changing mode of build/scripts-2.6/unifi-low-snr-reconnect from 644 to 755
 changing mode of build/scripts-2.6/unifi-ls-clients from 644 to 755
 changing mode of build/scripts-2.6/unifi-save-statistics from 644 to 755
 changing mode of build/scripts-2.6/unifi-log-roaming from 644 to 755
 changing mode of /usr/bin/unifi-ls-clients to 755
 changing mode of /usr/bin/unifi-low-snr-reconnect to 755
 changing mode of /usr/bin/unifi-save-statistics to 755
 changing mode of /usr/bin/unifi-log-roaming to 755
Successfully installed unifi
Cleaning up...

Com tudo instalado, vamos aos testes.

Obs: Para versões do controlador a partir da 3.2.7, será preciso editar o arquivo “/usr/lib/python2.6/site-packages/unifi/controller.py” antes de prosseguir com os testes.

Neste arquivo, comente a seguinte linha, salvando a alteração:

_ssl.PROTOCOL_SSLv23 = _ssl.PROTOCOL_SSLv3

Baixando scripts e conf

No CentOS (controlador Unifi), faça o download destes arquivos e descompacte-os no diretório scripts (comentado na área de Recursos). No caso desta instalação, ficou em “/usr/local/zabbix/scripts/”. Depois de descompactado o arquivo, a lista de arquivos resultantes deve ser:

ubiquiti (diretório)
  \
   --> aps.py (arquivo)
  \
   --> clients.py (arquivo)
  \
   --> wlans.py (arquivo)
unifi-discovery.sh (arquivo)
unifi-monitor.sh (arquivo)

Ainda no controlador, faça também o download deste aquivo conf, (unifi.conf) salvando-o no diretório de configurações extras do seu cliente Zabbix (onde ficam os UserParameters). No caso desta instalação, ele ficou no diretório “/usr/local/zabbix/etc/zabbix_agentd.conf.d/”.

Obs: Para ativar a leitura destas configurações pelo Agente Zabbix (no controlador unifi), edite o arquivo de configuração do Agente (zabbix_agentd.conf), procure a linha Include e informe o diretório utilizado para guardar os ‘UserParameter’. No caso desta instalação ficou assim:

Include=/usr/local/zabbix/etc/zabbix_agentd.conf.d/*.conf

Edite o ‘unifi.conf’ alterando a linha que chama os Script ‘unifi-monitor.sh’, para o diretório em que vocês os salvou (baseado nos itens anteriores). Neste caso, a linha ficou desta forma:

UserParameter=up.unifi[*],/usr/local/zabbix/scripts/unifi-monitor.sh $1 $2 "$3" $4

Depois disto, reinicie o agente Zabbix no controlador Unifi para validar o novo item (up.unifi).

O que são e o que fazem estes Scripts:

Tendo navegado até o diretório escolhido para descompactar, será possível verificar alguns aquivos (no diretório ubiquiti): ‘aps.py’, ‘clients.py’ e ‘wlans.py’. Estes são os Scripts Python base para todas as consultas. Estes Scripts são utilizados pelos Scripts ‘unifi-monitor.sh’ e ‘unifi-discovery.sh’ fornecendo os dados brutos. Os Scripts “unifi-monitor.sh” e “unifi-discovery.sh” trabalham os dados e os trazem no formato entendível pelo Zabbix e de acordo com os itens utilizados nas consultas.

A imagem a seguir, ilustrar o roteamento e dependência entre os Scripts:

OBS: Para facilitar, todos os Scripts (Python ou Shell) possuem comentários internos.

A imagem vale mais que mil palavras: toda a interação do servidor Zabbix é feita inicialmente com o Script “unifi-monitor.sh”. Dependendo da necessidade, ele irá buscar serviços no “unifi-discovery.sh” ou diretamente num dos três Scripts Python (aps.py, wlans.py e clients.py).

Primeiro teste (validador das configurações): Listando os APs.

Edite o arquivo “aps.py”, procurando pela linha abaixo, preenchendo com as informações do seu Setup:

c = Controller('endereco-controlador-unifi', 'Usuario', 'Senha', 'v3', 'Site')

Esta configuração será lida pelo Software que acessa a API do Unifi, todas as vezes que um dos Scripts for executado.

Explicação dos parâmetros

  1. Primeiro: IP ou nome do controlador Ubiquiti (aqui, ‘localhost’ que tanto é a máquina onde está o controlador, quanto é a máquina que fará a coleta dos dados);
  2. Segundo: Usuário devidamente cadastrado no controlador;
  3. Terceiro: Senha do usuário informado;
  4. Quarto: versão base do controlador;
  5. Quinto: Nome do site (nas versões mais novas, existe a possibilidade de gerência multi-sites).

Depois de preenchidas as informações, a linha ficaria mais ou menos assim:

c = Controller('localhost', 'Admin', '123lab123', 'v3', 'Site-padrao')

Para testar, no servidor onde estão os Scripts, execute o Script Python “aps.py”:

python /usr/src/unifi/ubiquiti/aps.py

A saída deve ser a lista de APs (algo neste formato):

UniFi LR - Corredor sala01 - SW24-Pt01;10.1.3.102;24:a4:3c:00:00:01;1
Unifi LR - Sala dos Professores - SW39-Pt15;10.1.3.74;24:a4:3c:00:00:02;1
UniFi LR - Reitoria - SW45-Pt05;10.13.3.70;24:a4:3c:00:00:03;None
(...)

Os valores devem chegar em quatro colunas, divididas por “;”:

  1. Nome do AP (conforme configurado no controlador (via interface WEB));
  2. IP do AP;
  3. MAC do AP;
  4. Estado do AP: 1 para ativo e “None” para inativo.

Caso obtenha êxito neste teste, prossiga com a mesma alteração (da linha que informa o endereço do servidor, usuário e senha), para os arquivos “clients.py” e “wlans.py”. Aproveite para testar as saídas dos dois Scripts também.

Testando os Scripts ‘unifi-monitor.sh’ e ‘unifi-discovery.sh’:

Antes de configurar tudo no Zabbix, é importante testar o funcionamento de todos os Scripts, evitando problemas básicos que muitas vezes nos levam à ideia de que o Zabbix não está configurado corretamente. Com todos os Scripts base (‘aps.py’, ‘wlans.py’ e ‘clients.py’) testados, execute o Script ‘unifi-monitor.sh’:

./unifi-monitor.sh

A saída deve ser algo como:

É preciso informar ao menos um parametro! -> aps | clients | wlans

Assim, teste cada um dos três parâmetros e veja se obtém dados corretos. Visualizando o conteúdo do Script é possível ver as variações e filtros de cada um dos parâmetros. É interessante checar  todos eles para que no momento da configuração no Zabbix, não ocorram surpresas.

Se você está acompanhando atentamente o Tutorial e viu a imagem do roteamento de mensagens, percebeu que não é preciso testar diretamente o Script ‘unifi-discovery.sh’, pois o ‘monitor’ utiliza os serviços dele para o ‘LLD’. Assim, se os ‘LLD’ do ‘monitor’ estiverem Ok, o Script ‘discovery’ estará Ok também!

Se qualquer um deles retornar erros, possivelmente não foi seguido algum dos cuidados e configurações expostas acima (incluindo configurações de usuário/URL/senha). Volte um pouco e revise-as confirmando cada passo.

Testando o acesso aos dados pelo Zabbix

Neste ponto você deve estar ávido por colocar logo pra funcionar. Bem, vamos com calma… Só assim conseguiremos garantir que “erros malucos inexplicáveis” não aparecerão na hora H.

Para testar o retorno de dados pelo Servidor Zabbix, podermos utilizar o utilitário “zabbix_get”. Ele está presente em qualquer instalação e precisar apenas ter seu caminho verificado pois, a exemplo da instalação via pacotes (RPM ou DPKG), é possível que o caminho seja diferente. A instalação utilizada como exemplo aqui, tem como raiz o diretório “/usr/local/zabbix”. Assim, o utilitário “zabbix_get” pode ser encontrado em “/usr/local/zabbix/bin”.

Para testar a consulta aos dados do controlador via linha de comandos, execute:

/usr/local/zabbix/bin/zabbix_get -s 10.13.3.49 -k up.unifi[wlans]

O retorno deve ser a lista completa de suas WLANs, como em (IP do controlador onde estão os Scripts):

[root@zabbix-server bin]# /usr/local/zabbix/bin/zabbix_get -s 10.1.3.49 -k up.unifi[wlans]
Sala de aulas 01;Ativo
Area de convivencia;Ativo
Auditorio;Ativo
Biblioteca;Ativo
Ensino Fundamental;Ativo
Professores;Ativo

Para certificar e ver mais resultados, utilize as chaves “up.unifi[aps]” e “up.unifi[clients]”.

Importando os templates

Com todos os testes executados, é chegada a tão esperada hora: A importação dos templates para ver a coisa acontecer. Faça o download deste template e importe-o para o Zabbix.

  1. Cadastre seu host controlador Unifi;
  2. Atrele ele ao template importado acima;
  3. Aguarde por volta de cinco minutos e vá até “Lastest Data” (ou Dados Recentes, de acordo com o idioma utilizado no Zabbix).

Os dados recentes devem se parecer com isto:

Lastest Data - informações dos primeiros itens

Cerca de quinze minutos depois da configuração, será possível ver a lista de gráficos gerados:

Lista de gráficos

Gráfico do panorama:

Panorama Wireless - template unifi

Gráfico de um AP:

Gráfico de um AP

Conclusão

Quais são as capacidades do Zabbix?

Quais são os limites do Zabbix?

Resposta: sua imaginação!

Para mais perguntas e respostas, sinta-se a vontade para nos visitar:

Pendências:

  • Tornar o script LLD multi-sites automático (solicitação Eid Victor);
  • Monitorar dados de consumo dos APs (UP/Download).

Abraço!

Anúncios

22 comentários sobre “UniFi AP manager: como monitorar Wireless Ubiquiti (Unifi APs) via Zabbix

  1. Boa tarde, poderia me ajudar com este erro:

    [root@SRV-CENTOS ubiquiti]# python aps.py
    Traceback (most recent call last):
    File “aps.py”, line 25, in
    for ap in c.get_aps():
    File “/usr/lib/python2.6/site-packages/unifi/controller.py”, line 137, in get_aps
    return self._read(self.api_url + ‘stat/device’, params)
    File “/usr/lib/python2.6/site-packages/unifi/controller.py”, line 76, in _read
    res = self.opener.open(url, params)
    File “/usr/lib/python2.6/urllib2.py”, line 397, in open
    response = meth(req, response)
    File “/usr/lib/python2.6/urllib2.py”, line 510, in http_response
    ‘http’, request, response, code, msg, hdrs)
    File “/usr/lib/python2.6/urllib2.py”, line 435, in error
    return self._call_chain(*args)
    File “/usr/lib/python2.6/urllib2.py”, line 369, in _call_chain
    result = func(*args)
    File “/usr/lib/python2.6/urllib2.py”, line 518, in http_error_default
    raise HTTPError(req.get_full_url(), code, msg, hdrs, fp)
    urllib2.HTTPError: HTTP Error 401: Unauthorized
    [root@SRV-CENTOS ubiquiti]#

    • Victor, boa tarde.
      Pelo retorno de erros, parece que vc tem algum problema no acesso ao controlador:

      HTTP Error 401: Unauthorized

      Checa se o usuário/senha/versão/site estão corretos (no aps.py).

      • WerneckCosta muito obrigado pelo retorno!

        Bom aqui no (aps.py) está dessa forma:
        c = Controller( ‘192.168.25.89’, ‘Admin’, ‘xxxx’, ‘v3’, ‘site-padrao’)

        É pq meu Unifi Controler está instalado em outro servidor, porem eu consigo acesso-lo via browser por este endereço: ( https://192.168.25.89:8443/login?url=/manage)
        Fique na duvida de como preencher esse campo (site -padrão).

          • Werneckcosta, consegui verificar era o “A” do “admin” que estava maiúsculo, porem deu outro erro:

            [root@SRV-CENTOS ubiquiti]# python aps.py
            Traceback (most recent call last):
            File “aps.py”, line 25, in
            for ap in c.get_aps():
            File “/usr/lib/python2.6/site-packages/unifi/controller.py”, line 137, in get_aps
            return self._read(self.api_url + ‘stat/device’, params)
            File “/usr/lib/python2.6/site-packages/unifi/controller.py”, line 76, in _read
            res = self.opener.open(url, params)
            File “/usr/lib/python2.6/urllib2.py”, line 397, in open
            response = meth(req, response)
            File “/usr/lib/python2.6/urllib2.py”, line 510, in http_response
            ‘http’, request, response, code, msg, hdrs)
            File “/usr/lib/python2.6/urllib2.py”, line 435, in error
            return self._call_chain(*args)
            File “/usr/lib/python2.6/urllib2.py”, line 369, in _call_chain
            result = func(*args)
            File “/usr/lib/python2.6/urllib2.py”, line 518, in http_error_default
            raise HTTPError(req.get_full_url(), code, msg, hdrs, fp)
            urllib2.HTTPError: HTTP Error 400: Bad Request

            Ai eu entrei no arquivo e alterei o caminho do servidor, colocando dessa forma:
            c = Controller( ‘192.168.25.89:8443/login?url=/manage’, ‘admin’, ‘xxxx’, ‘v3’, ‘site-padrao’)

            Gerou este erro:

            [root@SRV-CENTOS ubiquiti]# python aps.py
            Traceback (most recent call last):
            File “aps.py”, line 25, in
            for ap in c.get_aps():
            File “/usr/lib/python2.6/site-packages/unifi/controller.py”, line 137, in get_aps
            return self._read(self.api_url + ‘stat/device’, params)
            File “/usr/lib/python2.6/site-packages/unifi/controller.py”, line 77, in _read
            return self._jsondec(res.read())
            File “/usr/lib/python2.6/site-packages/unifi/controller.py”, line 67, in _jsondec
            obj = json.loads(data)
            File “/usr/lib/python2.6/json/__init__.py”, line 307, in loads
            return _default_decoder.decode(s)
            File “/usr/lib/python2.6/json/decoder.py”, line 319, in decode
            obj, end = self.raw_decode(s, idx=_w(s, 0).end())
            File “/usr/lib/python2.6/json/decoder.py”, line 338, in raw_decode
            raise ValueError(“No JSON object could be decoded”)
            ValueError: No JSON object could be decoded

            A versão: Unifi Controller (3.2.1) Started. Posso mandar o print no seu e-mail?

          • Victor, efetuei alguns testes. Pelo que vi, o acesso à API quando o controlador está instalado em Windows, não é a mesma pra Linux. Desta forma, o erro “HTTPError: HTTP Error 400: Bad Request” permanece.
            Uma alternativa seria migrar para Linux, o que é muito mais estável e de fácil manutenção.

  2. Boa Tarde, criei todo o ambiente com centos, e unifi controller funcionando tudo lindo! Antes de dar inicio ao artigo, gostaria de tirar uma dúvida, acabei instalando o controller 4.6.6, pode haver alguma modificação em específico? Obrigado!

  3. Werneckcosta, ainda estou tentando subir na versão do controller 4.6, tudo esta funcionando quando vou testar o python aps.py ele retorna,

    root@unifisrv:/usr/local/etc/scripts/ubiquiti# python aps.py
    Traceback (most recent call last):
    File “aps.py”, line 23, in
    c = Controller(‘localhost’, ‘admin’, ‘xxxxx’, ‘v4’, ‘site’)
    File “/usr/local/lib/python2.7/dist-packages/unifi/controller.py”, line 92, in __init__
    self._login(version)
    File “/usr/local/lib/python2.7/dist-packages/unifi/controller.py”, line 156, i n _login
    self.opener.open(self.url + ‘login’, params).read()
    File “/usr/lib/python2.7/urllib2.py”, line 431, in open
    response = self._open(req, data)
    File “/usr/lib/python2.7/urllib2.py”, line 449, in _open
    ‘_open’, req)
    File “/usr/lib/python2.7/urllib2.py”, line 409, in _call_chain
    result = func(*args)
    File “/usr/lib/python2.7/urllib2.py”, line 1240, in https_open
    context=self._context)
    File “/usr/lib/python2.7/urllib2.py”, line 1166, in do_open
    h = http_class(host, timeout=req.timeout, **http_conn_args)
    File “/usr/lib/python2.7/httplib.py”, line 1192, in __init__
    source_address)
    File “/usr/lib/python2.7/httplib.py”, line 712, in __init__
    (self.host, self.port) = self._get_hostport(host, port)
    File “/usr/lib/python2.7/httplib.py”, line 754, in _get_hostport
    raise InvalidURL(“nonnumeric port: ‘%s'” % host[i+1:])
    httplib.InvalidURL: nonnumeric port: ‘v4’
    Exception httplib.InvalidURL: InvalidURL(“nonnumeric port: ‘v4′”,) in <bound met hod Controller.__del__ of > ignored

  4. Boa tarde WerneckCosta,

    Não chegaste a atualizar o script para v4 do controlador?

    Possuo um server com essa versão, e gostaria de monitorar meus APs pelo Zabbix.

Se desejar, comente!

Preencha os seus dados abaixo ou clique em um ícone para log in:

Logotipo do WordPress.com

Você está comentando utilizando sua conta WordPress.com. Sair / Alterar )

Imagem do Twitter

Você está comentando utilizando sua conta Twitter. Sair / Alterar )

Foto do Facebook

Você está comentando utilizando sua conta Facebook. Sair / Alterar )

Foto do Google+

Você está comentando utilizando sua conta Google+. Sair / Alterar )

Conectando a %s