16 jul. 2017

Consultar DNS por medio de Scapy

Hace unos años escribí un artículo sobre descubrir equipos de una red local con python usando ipcalc y scapy, ahora muestro el uso de scapy para consultar DNS a un servidor de DNS determinado.



El programa es muy sencillo, es una función que se le pasa el servidor y el url a consultary devuelve la IP del url. A continuación se muestra el código:


#!/usr/bin/env python3


from scapy.all import *


def consulta(dns="8.8.8.8",dominio="www.google.com"):
    dnsServer = dns
    domconsulta= dominio
    #Se define la estructura del paquete de consulta de DNS, que es un paquete UDP
    #Que va por el puerto 53, se le pasa el servidor y el url.
    paquete_dns= IP(dst=dnsServer)/UDP(dport=53)/DNS(rd=1,qd=DNSQR(qname=domconsulta))
    #Se hace la consulta y se devuelve el resultado
    request_pqt = sr1(paquete_dns,verbose=0)
    return request_pqt[DNS].summary()
    
if __name__ == "__main__":
    print (consulta("8.8.8.8","www.debian.org"))


Al ejecutar el script se tiene el siguiente resultado:

sudo python3 pydns1.py
WARNING: No route found for IPv6 destination :: (no default route?). This affects only IPv6
DNS Ans "'128.31.0.62'"


Como se puede notar, la IP de www.debian.org es la 128.31.0.62.




9 jul. 2017

Instalar Docker en Debian Stretch (actualización 2017).

El primer artículo de la serie  de artículos sobre Docker fue, el de la Instalación de Docker en Debian Jessie, ahora explicaré el proceso de instalación de Docer CE para Debian Stretch. La guía en inglés de instalación de docker para Debian la pueden encontrar en el siguiente enlace.

El procedimiento es el siguiente:

1. Instalación de paquetes necesarios para soporte de https en apt-get:

#apt-get install apt-transport-https ca-certificates curl gnupg2 software-properties-common


2. Agregar llave gpg oficial de Docker:

# curl -fsSL https://download.docker.com/linux/debian/gpg |  apt-key add -
OK

Si devuelve "OK" se bajo la llave y la agregó sin problemas.

3. Verificar la llave:

# apt-key fingerprint 0EBFCD88
pub   rsa4096 2017-02-22 [SCEA]
      9DC8 5822 9FC7 DD38 854A  E2D8 8D81 803C 0EBF CD88
uid           Docker Release (CE deb) <docker@docker.com>
sub   rsa4096 2017-02-22 [S]

4. Se agrega el repositorio Estable para la versión de Debian que se tiene en el equipo:
add-apt-repository \
>    "deb [arch=amd64] https://download.docker.com/linux/debian \
>    $(lsb_release -cs) \
>    stable"

5. Se actualiza la lista de paquetes:
#apt-get update

6. Se instala docker-ce :

# apt-get install docker-ce

7. Se verifica que docker-ce se instaló correctamente:

# docker run hello-world
Unable to find image 'hello-world:latest' locally
latest: Pulling from library/hello-world
b04784fba78d: Pull complete 
Digest: sha256:f3b3b28a45160805bb16542c9531888519430e9e6d6ffc09d72261b0d26ff74f
Status: Downloaded newer image for hello-world:latest

Hello from Docker!
This message shows that your installation appears to be working correctly.

To generate this message, Docker took the following steps:
 1. The Docker client contacted the Docker daemon.
 2. The Docker daemon pulled the "hello-world" image from the Docker Hub.
 3. The Docker daemon created a new container from that image which runs the
    executable that produces the output you are currently reading.
 4. The Docker daemon streamed that output to the Docker client, which sent it
    to your terminal.

To try something more ambitious, you can run an Ubuntu container with:
 $ docker run -it ubuntu bash

Share images, automate workflows, and more with a free Docker ID:
 https://cloud.docker.com/

For more examples and ideas, visit:
 https://docs.docker.com/engine/userguide/


8. Instalar docker-compose:

#apt-get install  docker-compose



Manejar docker como un usuario normal:

1. Crear el grupo docker:
$sudo groupadd docker

2. Agregar el usuario al grupo docker:
$sudo usermod -aG docker $USER

3. Verificar que se puede usar docker desde el usuario:

$ docker run hello-world

Hello from Docker!
This message shows that your installation appears to be working correctly.

To generate this message, Docker took the following steps:
 1. The Docker client contacted the Docker daemon.
 2. The Docker daemon pulled the "hello-world" image from the Docker Hub.
 3. The Docker daemon created a new container from that image which runs the
    executable that produces the output you are currently reading.
 4. The Docker daemon streamed that output to the Docker client, which sent it
    to your terminal.

To try something more ambitious, you can run an Ubuntu container with:
 $ docker run -it ubuntu bash

Share images, automate workflows, and more with a free Docker ID:
 https://cloud.docker.com/

For more examples and ideas, visit:
 https://docs.docker.com/engine/userguide/



Configurar Docker para que inicie en el arranque del equipo:

1. Habilitar Docker:
$ sudo systemctl enable docker
Synchronizing state of docker.service with SysV service script with /lib/systemd/systemd-sysv-install.
Executing: /lib/systemd/systemd-sysv-install enable docker


Si requieren detalles de configuración lo pueden ver en la documentación de docker.

Para terminar se prueba el arranque de cloud9 ya explicado en un artículo anterior.

$docker run -it -d -p 9080:80 -v /home/ernesto/worksplace/:/workspace/ kdelfour/cloud9-docker
99cfe3af5bf4480ac456ec43916612317a49da111ab27e32a361639984eb2128

La siguiente captura de pantalla muestra cloud9 en funcionamiento:

En el diectorio worksplace se guarda los proyectos que se editan desde cloud9.

$ tree worksplace
worksplace
├── hola.py
├── New Folder
│   ├── mvc1.py
│   ├── New Folder
│   └── usuario.py
└── trabajo.txt

2 directories, 4 files


25 jun. 2017

Desarrollar un API con GraphQL en Flask

Continuando con los artículos sobre Flask, donde el último artículo fue de como crear un API Restful con Flask y MongoDB.

En este artículo se toca el uso de GraphQL para crear un API. GraphQL es un lenguaje de consulta de datos desarrollado por Facebook, es una alternativa a Rest (más información en wikipedia).

La librería para Flask de GraphQL lo pueden ver en el siguiente enlace. El artículo explicará el ejemplo que aparece en la página oficial de graphQL para Flask.

Instalación:
#pip3 install flask graphene flask-graphql


Script servidor (server.py):


#!/usr/bin/env python3

#Se importa flask, graphene y graphql.

from flask import Flask

from graphene import ObjectType, String, Schema

from flask_graphql import GraphQLView



#Se crea la clase Query que hereda de graphene ObjectType.

class Query(ObjectType):

    #Se define la descripcion

    hello = String(description='Hello')

    #Se define la funcion resolve_hello, se le pasa args, context e info.

    def resolve_hello(self, args, context, info):

        return 'World'



#Se define la funcion de la vista.

#que se le pasa el esquema con la clase Query.

view_func = GraphQLView.as_view('graphql', schema=Schema(query=Query))



#Se crea la app como instancia de la clase Flask.

app = Flask(__name__)

#Se define el url donde se le pasa la funcion de la vista

app.add_url_rule('/', view_func=view_func)



if __name__ == '__main__':

    #Se ejecuta flask.

    app.run()



Al ejecutar el script:


Se consulta usando curl:
curl -H 'Content-type: application/graphql' -d '{hello}' http://localhost:5000/

Y este devuelve:

{"data":{"hello":"World"}}




Desde un script en python:



Instalación de librerías necesarias:

#pip3 install gql requests



El script cliente.py :



#!/usr/bin/env python3



#Se importa json

import json

#se importa ggl

from gql import gql, Client

from gql.transport.requests import RequestsHTTPTransport



#Se define el transport, se conecta el cliente.

transport = RequestsHTTPTransport('http://localhost:5000/')

client = Client(transport=transport)

#Se realiza una consulta buscando la  variable hello

response = client.execute(gql('{hello}'))



#muestra en pantalla la respuesta como un json.

print(json.dumps(response))



Se ejecuta el script:

python3 cliente.py 
{"hello": "World"}

En un artículo en genbetadev comparan API Restful con GraphQL y por que es necesario dejar de usar API Restful.
En futuros artículos se ampliará el uso de GraphQL.

24 jun. 2017

Base de datos InfluxDB en Debian Stretch

InfluxDB es una base de datos opensource de series de tiempo, para manejo de eventos,monitoreo, métricas, Internet de las cosas y Analítica en tiempo real. Desarrollada por InfluxData en Lenguaje Go. Pueden ver más información en wikipedia.

Para instalar en Debian simplemente se usa apt-get:

# apt-cache search influxdb 
golang-github-influxdb-enterprise-client-dev - Golang client for speaking to the InfluxDB Enterprise application
golang-github-influxdb-usage-client-dev - library for speaking to the InfluxDB Anonymous Usage Reporting API
golang-gopkg-alexcesaro-statsd.v1-dev - simple and efficient Golang StatsD client
golang-github-influxdb-influxdb-dev - Scalable datastore for metrics, events, and real-time analytics. Dev package
influxdb - Scalable datastore for metrics, events, and real-time analytics
influxdb-client - command line interface for InfluxDB
influxdb-dev - Transitional package for golang-github-influxdb-influxdb-dev
ruby-influxdb - library for InfluxDB


Para instalar:

# apt-get install influxdb influxdb-client

Para probar que está en funcionamiento:

# influx
Visit https://enterprise.influxdata.com to register for updates, InfluxDB server management, and monitoring.
Connected to http://localhost:8086 version 1.0.2
InfluxDB shell version: 1.0.2




Para crear una base de datos llamada mydb:

> create database mydb

Listar las bases de datos:

> show databases
name: databases
---------------
name
_internal
mydb



Insertar datos y consultarlos en la base de datos mydb:

> use mydb
Using database mydb
> INSERT cpu,host=ServerA,region=us_west value=0.64
> SELECT host, region, value FROM cpu
name: cpu
---------
time                 host         region value
1498340879346347895 ServerA us_west 0.64

Por lo que se ve, la clave primaria de los datos siempre es el tiempo. 

Ahora una pequeña prueba con Python.

Para instalar la librería en Python:
# pip3 install influxdb



Se tiene el siguiente script:


#!/usr/bin/env python3
#Se importa influxdb
from influxdb import InfluxDBClient
#Se define un json con los datos a insertar
json_body = [
    {
        "measurement": "cpu_load_short",
        "tags": {
            "host": "server01",
            "region": "us-west"
        },
        "time": "2009-11-10T23:00:00Z",
        "fields": {
            "value": 0.64
        }
    },
    {
        "measurement": "cpu_load_short",
        "tags": {
            "host": "server02",
            "region": "us-west"
        },
        "time": "2009-12-10T23:00:00Z",
        "fields": {
            "value": 0.65
        }
    }
]
#Se conecta a la base de datos
client = InfluxDBClient('localhost', 8086, 'root', 'root', 'mydb')
#Se crea la base de datos mydb
client.create_database('mydb')
#Se inserta los datos
client.write_points(json_body)
#Se consulta y se muestra en pantalla
result = client.query('select value from cpu_load_short;')
print("Result: {0}".format(result))

Al ejecutar el script, este devuelve lo siguiente:

./prueba-influxdb.py 
Result: ResultSet({'('cpu_load_short', None)': [{'value': 0.64, 'time': '2009-11-10T23:00:00Z'}, {'value': 0.65, 'time': '2009-12-10T23:00:00Z'}]})


O desde el cliente de influxdb:

> use mydb
Using database mydb
> select value from cpu_load_short;
name: cpu_load_short
--------------------
time value
1257894000000000000 0.64
1260486000000000000 0.65

Como se muestra, la clave que maneja las consultas es el tiempo.

Para más información se tiene los siguientes enlaces: