Diferencia entre revisiones de «Puppet»
(→Pasos para la instalación de puppet) |
(→Algunos apuntes de trabajo) |
||
(2 revisiones intermedias por el mismo usuario no mostrado) | |||
Línea 352: | Línea 352: | ||
Después, fallaba también el servicio puppet-dashboard-worker, porque por algún motivo no está especificado en ningún sitio la variable DASHBOARD_USER. Para solucionarlo modifiquúe el fichero de arranque, para añadir esa variable. | Después, fallaba también el servicio puppet-dashboard-worker, porque por algún motivo no está especificado en ningún sitio la variable DASHBOARD_USER. Para solucionarlo modifiquúe el fichero de arranque, para añadir esa variable. | ||
+ | |||
+ | |||
+ | * En otra instalación con el dashboard, ya asumiendo que este se iba a ejecutar sin passenger, es decir, el mismo haciendo de servidor "web", he tenido otros problemas. | ||
+ | |||
+ | El problema principal fue cuando configuré el dashboard para consumir datos de puppetdb. En principio lo que buscaba era usar el '''inventory search'''. Para habilitar esta función primero he tenido que dejar bien configurado el puppetdb y que este esté insertando los facter de las máquinas que están consumiendo de puppet. | ||
+ | |||
+ | <pre> | ||
+ | # En el fichero de configuración de puppet /etc/puppet/puppet.conf añadimos estas linas a la seccion de master | ||
+ | storeconfigs_backend = puppetdb | ||
+ | storeconfigs = true | ||
+ | </pre> | ||
+ | |||
+ | En la configuración del dashboard '''/etc/puppet-dashboard/settings.yml''' tenemos que reflejar que queremos un inventory server y le especificamos cual es su ubicación y el puerto: | ||
+ | |||
+ | <pre> | ||
+ | # The "inventory service" allows you to connect to a puppet master to retrieve and node facts | ||
+ | enable_inventory_service: true | ||
+ | |||
+ | # Hostname of the inventory server. | ||
+ | inventory_server: 'puppetserver.ardemans.int' | ||
+ | |||
+ | # Port for the inventory server. | ||
+ | inventory_port: 8140 | ||
+ | </pre> | ||
+ | |||
+ | De esta forma, nos aparecerá una nueva opción en la parte superior del dashboard "inventory search" y además cada vez que consultemos los reportes de cada nodo también nos mostrará los facts que tuvo la última vez. | ||
+ | |||
+ | Cada vez que hacemos una consulta a un nodo o hacemos una búsqueda en el inventary search realiza peticiones a puppetdb (en definitiva a través del puerto de puppet) del estilo: | ||
+ | |||
+ | <pre> | ||
+ | https://192.168.2.25:8140/production/facts/puppetserver.ardemans.int | ||
+ | </pre> | ||
+ | |||
+ | |||
+ | * Otro problema, que solo afecta si solo ponemos el dashboard como NO PASSENGER, es el script de arranque. En la versión 12 de ubuntu no existe el comando status_of_proc, por lo que hay que cambiar el ejecutable por | ||
+ | |||
+ | <pre> | ||
+ | start-stop-daemon -T -p $PIDFILE -u $DASHBOARD_USER | ||
+ | </pre> | ||
+ | |||
+ | y además, por algún motivo que desconozco el fichero PID que se genera contiene siempre un pid que es -2 al PID que realmente tiene el proceso. Por lo que para solucionar momentaneamente la papeleta he añadido | ||
+ | |||
+ | <pre> | ||
+ | echo $((`cat $PIDFILE`+2)) > $PIDFILE | ||
+ | </pre> | ||
+ | |||
+ | para cambiar el fichero PID por el valor correcto, sumando dos al valor que ya tiene. | ||
+ | |||
+ | = Augeas = | ||
+ | |||
+ | Existe una utilidad muy buena para poder navegar entre los diferentes "nodos" de Augeas de la máquina, el augtool. Con esta utilidad podemos ver como si fueran directorios y ficheros las configuraciones de la máquina. Esta utilidad se encuentra dentro de paquete de sistema "augeas" | ||
+ | |||
+ | Como ejemplo, para entrar en la consola de esta herramienta podemos ejecutar: | ||
+ | <pre> | ||
+ | $ augtool | ||
+ | </pre> | ||
+ | |||
+ | Una vez dentro podemos navegar por los ficheros que gestionamos con augeas y los parámetros que hay dentro de forma sencilla: | ||
+ | |||
+ | <pre> | ||
+ | augtool> ls / | ||
+ | augeas/ = (none) | ||
+ | files/ = (none) | ||
+ | augtool> ls /files/etc/sysconfig/network | ||
+ | NETWORKING = yes | ||
+ | HOSTNAME = eciltc1.vag.ardemans.int | ||
+ | augtool> | ||
+ | </pre> | ||
+ | |||
+ | En el ejemplo de arriba hacemos un ls del raiz, donde se ven dos secciones diferentes: | ||
+ | |||
+ | - augeas: se pueden consultar las configuraciones del propio augeas | ||
+ | - files: los ficheros que puede gestionar augeas | ||
+ | |||
+ | Como ejemplo además después vemos los parámetros que hay dentro de unos de los ficheros que pueden ser gestionados por augeas, en este caso el /etc/sysconfig/network, con sus dos parámetros. | ||
+ | |||
+ | Si quisieramos cambiar uno de esos parámetros solo tendríamos que ejecutar el siguiente comando dentro de augtool: | ||
+ | <pre> | ||
+ | augtool> set /files/etc/sysconfig/network/HOSTNAME "eciltc1" | ||
+ | augtool> ls /files/etc/sysconfig/network | ||
+ | NETWORKING = yes | ||
+ | HOSTNAME = eciltc1 | ||
+ | </pre> | ||
+ | |||
+ | Y esto traducido a puppet sería algo así: | ||
+ | |||
+ | <pre> | ||
+ | augeas { 'nombre_red_maquina': | ||
+ | changes => "set /files/etc/sysconfig/network/HOSTNAME \"eciltc1\"" | ||
+ | } | ||
+ | </pre> |
Última revisión de 13:17 7 oct 2015
Contenido
Referencias
- Inforamción sobre primeros pasos en puppet en español aqui
- Documentación oficial de instalación de puppet aqui
- Otro documento sobre Instalación y configuración en español aqui
- Web oficial sobre Marionette Collective
- Importantes son los Anchor, mirar esta página que lo explica
- Articulo interesante de wikimedia, de como pasó su infraestructura a puppet. Incluye un video con explicaciones de como usar puppet (en ingles)
Introducción
Para nuestro entorno de pruebas vamos a instalar la versión enterprise de Puppet, que permite administrar hasta 10 nodos de forma gratuita. Se trata de conocer el producto de pago y ver si interesa en un futuro comprar las licencias.
Pasos para la instalación de puppet
Después de instalar Centos 6.3 añadimos el repositorio de paquetes de puppet para el YUM, con el siguiente comando
rpm -ivh http://yum.puppetlabs.com/el/6/products/i386/puppetlabs-release-6-6.noarch.rpm
Y añadiremos los paquetes para puppet enterprise
rpm -ivh http://yum-enterprise.puppetlabs.com/el/6/extras/i386/puppetlabs-enterprise-release-extras-6-2.noarch.rpm
Eso hará que estén disponibles nuevos paquetes de puppet para nuestra instalación
Para la versión 5 de EL son los siguientes:
rpm -ivh http://yum.puppetlabs.com/el/5/products/i386/puppetlabs-release-5-6.noarch.rpm rpm -ivh http://yum-enterprise.puppetlabs.com/el/5/extras/i386/puppetlabs-enterprise-release-extras-5-2.noarch.rpm
Para la versión 12.04 de Ubuntu la instalación es parecida. Tendremos que buscar el paquete de servidor apt para nuestra versión, en nuestro caso precise pangolin, dentro de la URL http://apt.puppetlabs.com/
cd /tmp wget http://apt.puppetlabs.com/puppetlabs-release-precise.deb dpkg -i puppetlabs-release-precise.deb
Instalación de servidor de puppet
En el servidor que nos hará de server instalamos los siguientes paquetes:
yum install puppet-server
Y después configuramos el arranque automático del servicio
chkconfig puppetmaster on
Instalación de cliente de puppet
En otra máquina instalamos el cliente de puppet, añadiendo los mismos repositorios de instalación de yum que para el server y después instalamos el agente:
yum install puppet
Antes de arrancar el servicio tendremos que cambiar la configuración para que el agente sepa a que servidor de puppet se tiene que conectar: Para ello modificamos el fichero de configuración: /etc/sysconfig/puppet, descomentando la parte que nos interesa
# The puppetmaster server PUPPET_SERVER=puppet1.test.prisadigital.int # If you wish to specify the port to connect to do so here PUPPET_PORT=8140 # Where to log to. Specify syslog to send log messages to the system log. #PUPPET_LOG=/var/log/puppet/puppet.log # You may specify other parameters to the puppet client here #PUPPET_EXTRA_OPTS=--waitforcert=500
puede ser recomendable añadir al fichero de hosts la entrada correspondiente para resolver el servidor de puppet.
Después arrancamos el servicio y lo configuramos para que se arranque de forma automática:
service puppet start chkconfig puppet on
Certificados
La comunicación entre el master y los agentes va encriptada. Para que no sea complicada la gestión de los certificados entre los agentes y el master puppet en si tiene su propia entidad certificadora y su propia gestión mediante el comando puppet.
En la máquina master podemos ver en el directorio /var/lib/puppet/ssl/ los ficheros de la entidad certificadora.
Cada vez que un agente arranque y se conecte contra el servidor master, generará una clave pública y privada, y una petición de firmado. Tendrá que ser firmada por la CA del master. Esto requiere que cada vez que se añada un agente habrá que ejecutar a mano el comando que realizar ese firmado.
Toda la gestión se realiza con los comandos:
puppet ca puppet cert
Para ver todos los certificados firmados podemos usar
puppet cert list --all
Si quitamos el --all veremos solamente las peticiones pendientes de ser firmadas, y si queremos firmar una podemos ejecutar
puppet cert sign "nombre_del_servidor"
Si queremos firmar todas las peticiones pendientes podemos usar el comando
puppet cert sign --all
Auto-firmado de peticiones
También se puede configurar que se firmen de forma automática ciertas peticiones que lleguen. Para ello se puede añadir el fichero /etc/puppet/autosign.conf, donde especificamos un FQDN de máquinas en las que confiamos. En mi caso:
prisadigital.int *.prisadigital.int
Comprobación de los agentes
Teniendo el master arrancado, podemos ejecutar un comando de comprobación del agente.
# puppet agent --test --verbose --server=<master_server> Info: Retrieving plugin Info: Caching catalog for <agent_server> Info: Applying configuration version '1358072141' Notice: Finished catalog run in 0.06 seconds
Arrancar servicios en modo consola
Durante las pruebas, para poder hacer seguimiento de que va haciendo cada servicio, podemos arrancarlos en modo conosola. Para ello, teniendo parado el servicio, podemos arrancar el master de la siguiente manera:
puppet master --no-daemonize --verbose
y el agente lo podemos arrancar con el comando
puppet agent --no-daemonize --verbose
Configuración de Puppet
El fichero principal de configuración es /etc/puppet/puppet.conf. Es el mismo fichero tanto para los agentes como para el master. Dentro de este fichero puede haber secciones [main] [master] y [agent]. Lo que va dentro de la sección main es común para agente y para master, y lo que va dentro de las otras dos secciones son especificas para el rol de esa máquina. Lo que se especifica en esas secciones de master y agente sobreescriben a lo que haya definido en Main en caso de que se duplique.
Primeras pruebas con puppet
Una buena referencia para empezar es el manual learningpuppet
Antes de empezar a crear manifiestos se puede hacer unas cuantas pruebas de como se reciben los datos de estado y como se realizan configuraciones con puppet. De esta forma se ve como usando con puppet la RAL (capa de abstracción de recursos) podemos recibir datos y modificar configuraciones de un servidor.
El ejemplo más sencillo es con los usuarios:
Si queremos ver una lista de usuarios que tiene cualquiera de los agentes podemos ejecutar el comando:
puppet resources user
Nos devolverá una lista de usuarios del sistema, en el formato de puppet:
user { 'pepe': ensure => 'present', comment => 'pepe', gid => '666', groups => ['DDesarrollo', 'nogroup', 'nogroup_old'], home => '/home/pepe', password => '*', password_max_age => '-1', password_min_age => '-1', shell => '/bin/sh', uid => '15094', } (...)
También podemos especificar un objeto en concreto, para ver su estado, de manera que solo nos devolverá los datos de este y no la lista completa
puppet resource user paco
Si añadimos atributos a este comando, además, modificará el objeto con los datos especificados. Por ejemplo, si no existiera el usuario paco, podríamos crearlo de la forma siguiente:
puppet resource user paco ensure="present" shell="/bin/bash" uid="11000"
Manifiestos
Los manifiestos son ficheros con instrucciones sobre recursos, un ejemplo de manifiesto sería un fichero que tuviera la configuración de un usuario o de la existencia de un fichero.
Podriamos definier el siguiente manifiesto /root/ejemplo.pp
file {'FicheroPrueba': ensure => present, path =>'/tmp/prueba', content => "prueba de contenido", mode => 0666, }
Y para aplicarlo localmente a una máquina podriamos ejecutarlo como:
puppet apply ejemplo.pp
de esa forma ejecutaría el comando, o conjunto de ellos, que hay en el manifiesto.
Otro ejemplo, sería el de instalar el paquete apache y levantar el servicio:
package{'httpd': ensure => present, } service{'httpd': ensure => running, enable => true, } Package['httpd'] -> Service['httpd']
La última línea es la que define el orden en el que se han de aplicar los cambios, es decir, que primero instalará el paquete y después arrancará el servicio. Este es el métido de encadenamiento.
Otra cosa que se puede hacer es definir los Metaparámetros before y required. Se añaden a cada recurso como si fuera un atributo, pero realmente no es una propiedad del recurso, solo sirve para definir el comportamiento de Puppet.
Subscribe y Notify
Otro metaparámetro interesante es el subscribe. Se asocia a ciertos recursos que pueden ser "refrescados". Sobre todo se usa con los servicios, para ser reiniciados después de si un fichero de configuración ha sido modificado.
file{'/etc/apache/httpd.conf': ensure => present, source => /opt/template/httpd.conf } service{'httpd': ensure => running, enable => true, subscribe => File['/etc/apache/httpd.conf'], }
Modulos
Son grupos de recursos que puden ser llamados desde otros manifiestos. Están organizados por directorios, generalmente en el directorio /etc/puppet/modules/. Cada módulo tendrá un directorio propio, y dentro de estos directorios se mantiene una estructrua definida como la siguiente:
/etc/puppet/modules/ssh/ /etc/puppet/modules/ssh/manifests /etc/puppet/modules/ssh/files /etc/puppet/modules/ssh/templates
Siempre existe un fichero init.pp dentro del directorio <modulo>/manifests que será el principal del modulo, y que por lo general empieza con una clase con el nombre del módulo:
class ssh { ... }
Módulos de puppet forge
En la comunidad de Puppet existen ya compartidos muchos módulos para casi todo. Una forma de buscarlos es en la web de puppet forge. También se pueden buscar a través del comando puppet, desde la línea de comandos, con:
puppet module search solr puppet module install <modulo>
Control de versiones
Para tener un control de las versiones de los manifiestos que estamos creando y manipulando he creado un repositorio de SVN donde voy actualizando las modificaciones que voy haciendo.
Entornos
Dentro de puppet se pueden definir diferentes entornos, con configuraciones separadas para cada uno. Lo típico es tener el entorno [main] para producción, uno de desarrollo y otro de preproducción.
Para definir diferentes entornos hay que añadir al fichero de configuración /etc/puppet/puppet.conf nuevos tags, como los que tenemos de [main] o [agent], con los nombres de los entornos que queremos añadir.
En mi caso he creado los siguiente entornos:
[development] modulepath = $confdir/environments/development/modules manifest = $confdir/environments/development/manifests/site.pp [testing] modulepath = $confdir/environments/testing/modules manifest = $confdir/environments/testing/manifests/site.pp
Con SVN tenemos diferentes working copy en cada uno de los directorios de modulos de cada entorno, y de esta manera podemos trabajar haciendo cambios en cada working copy sin necesidad de modificiar lo que tenemos en producción.
A la hora de probar un cambio, podemos hacer una ejecución de prueba en un nodo, especificando el entorno que queremos probar:
puppet agent --test --noop --environment development
De esta forma ejecutará los cambios que hemos hecho en el entorno de desarrollo, el resto de máquinas no se entera del cambio que hemos realizado.
Escalabilidad
La comunicación entre master y agentes se realiza a través de HTTPS, con los certificados que se generan de forma automática cuando arrancamos por primera vez un servicio. Salvo que cambiemos la configuración, puppet usa un servidor HTTP pequeñito que proporciona Ruby, que se llama WEBRick. Pero este no da mucho rendimiento, y para más de 100 máquinas nos dará problemas. Además, no se recomienda usarlo en un entorno productivo.
Para estos, se recomienda usar Apache como servidor WEB de Puppet
Puppet trabajando con Cloud
Existe un modulo de puppet que podemos instalar para trabajar con EC2 de Amazon. Este modulo se puede instalar con:
# puppet module install puppetlabs-cloud_provisioner
este modulo no tiene manifiestos como tal, sino que incluye librerías para usar en los nodos.
Para que estas librerías funcionen hay que instalarse dos gemas de ruby:
# gem install fog -v 0.7.2 # gem install guid
y además hay que incluir la librería del modulo que hemos instalado en la variable de entorno RUBYLIB. Lo suyo es añadirlo en el .profile
export RUBYLIB=/etc/puppet/modules/cloud_provisioner/lib:$RUBYLIB
Por otro lado, hay que suministrar las credenciales con las que nos conectamos a Amazón. Estas las epecificamos en el fichero ~/.fog de la siguiente forma:
:default: :aws_access_key_id: XXXXXXXXXXXXXXXXXXXX :aws_secret_access_key: XXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXX
Estas credenciales las podemos conseguir desde la web de Amazon, una vez logados, en el menu de nuestro usuario, con la opcion de security credentials
* NOTA:Instalando el modulo para ec2 he tenido problemas ejecutandolo. Para solucionarlo mirar esta nota
Una vez que tenemos todo esto ya podemos interactuar con Ec2 con comandos desde nuestra consola. Por ejemplo, podemos obtener un listado de las máquinas que tenemos en nuestro EC2:
# puppet node_aws list --region=eu-west-1
Algunos apuntes de trabajo
- Con el dashboard he tenido algunos problemas. El primero era que cuando se iban a guardar por post los reportes a la URL /reports/upload este daba un error 406. El problema estaba en los permisos que había entre el usuario que ejecutaba la aplicación y los que había en el raiz de rails. El servicio rails se ejecutaba con el usuario puppet-dbuser y la mayoria de los ficheros de /usr/share/puppet-dashboard estaban con el usuario puppet-dashboard. No todos, había algunso directorios con usuario puppet-dbuser.
Rails se ejecuta con el owner del fichero de configuración que carga, en mi caso /usr/share/puppet-dashboard/environment.rb
Cambiando el usuario de todo el directorio a puppet-dbuser se soluciona el problema
Después, fallaba también el servicio puppet-dashboard-worker, porque por algún motivo no está especificado en ningún sitio la variable DASHBOARD_USER. Para solucionarlo modifiquúe el fichero de arranque, para añadir esa variable.
- En otra instalación con el dashboard, ya asumiendo que este se iba a ejecutar sin passenger, es decir, el mismo haciendo de servidor "web", he tenido otros problemas.
El problema principal fue cuando configuré el dashboard para consumir datos de puppetdb. En principio lo que buscaba era usar el inventory search. Para habilitar esta función primero he tenido que dejar bien configurado el puppetdb y que este esté insertando los facter de las máquinas que están consumiendo de puppet.
# En el fichero de configuración de puppet /etc/puppet/puppet.conf añadimos estas linas a la seccion de master storeconfigs_backend = puppetdb storeconfigs = true
En la configuración del dashboard /etc/puppet-dashboard/settings.yml tenemos que reflejar que queremos un inventory server y le especificamos cual es su ubicación y el puerto:
# The "inventory service" allows you to connect to a puppet master to retrieve and node facts enable_inventory_service: true # Hostname of the inventory server. inventory_server: 'puppetserver.ardemans.int' # Port for the inventory server. inventory_port: 8140
De esta forma, nos aparecerá una nueva opción en la parte superior del dashboard "inventory search" y además cada vez que consultemos los reportes de cada nodo también nos mostrará los facts que tuvo la última vez.
Cada vez que hacemos una consulta a un nodo o hacemos una búsqueda en el inventary search realiza peticiones a puppetdb (en definitiva a través del puerto de puppet) del estilo:
https://192.168.2.25:8140/production/facts/puppetserver.ardemans.int
- Otro problema, que solo afecta si solo ponemos el dashboard como NO PASSENGER, es el script de arranque. En la versión 12 de ubuntu no existe el comando status_of_proc, por lo que hay que cambiar el ejecutable por
start-stop-daemon -T -p $PIDFILE -u $DASHBOARD_USER
y además, por algún motivo que desconozco el fichero PID que se genera contiene siempre un pid que es -2 al PID que realmente tiene el proceso. Por lo que para solucionar momentaneamente la papeleta he añadido
echo $((`cat $PIDFILE`+2)) > $PIDFILE
para cambiar el fichero PID por el valor correcto, sumando dos al valor que ya tiene.
Augeas
Existe una utilidad muy buena para poder navegar entre los diferentes "nodos" de Augeas de la máquina, el augtool. Con esta utilidad podemos ver como si fueran directorios y ficheros las configuraciones de la máquina. Esta utilidad se encuentra dentro de paquete de sistema "augeas"
Como ejemplo, para entrar en la consola de esta herramienta podemos ejecutar:
$ augtool
Una vez dentro podemos navegar por los ficheros que gestionamos con augeas y los parámetros que hay dentro de forma sencilla:
augtool> ls / augeas/ = (none) files/ = (none) augtool> ls /files/etc/sysconfig/network NETWORKING = yes HOSTNAME = eciltc1.vag.ardemans.int augtool>
En el ejemplo de arriba hacemos un ls del raiz, donde se ven dos secciones diferentes:
- augeas: se pueden consultar las configuraciones del propio augeas - files: los ficheros que puede gestionar augeas
Como ejemplo además después vemos los parámetros que hay dentro de unos de los ficheros que pueden ser gestionados por augeas, en este caso el /etc/sysconfig/network, con sus dos parámetros.
Si quisieramos cambiar uno de esos parámetros solo tendríamos que ejecutar el siguiente comando dentro de augtool:
augtool> set /files/etc/sysconfig/network/HOSTNAME "eciltc1" augtool> ls /files/etc/sysconfig/network NETWORKING = yes HOSTNAME = eciltc1
Y esto traducido a puppet sería algo así:
augeas { 'nombre_red_maquina': changes => "set /files/etc/sysconfig/network/HOSTNAME \"eciltc1\"" }