Blog Drupal

Actualización automática de Drupal y sus módulos con drush (Actualizado)

Reviso esta entrada para añadir al final la estupenda aportación de Eduardo Hernandez .

Drupal ha avanzado mucho en todo lo que se refiere a actualización automática. Sin embargo todavía es algo engorroso.
Afortunadamente existe drush que aunque es un poco lioso de instalar para aquellos que no son amigos de la consola, es una verdadera maravilla una vez instalado.

Te actualiza todo, te instala lo que quieras .. etc etc etc

Pero una vez que lo tienes no puedes evitar pensar, ¿Por qué no lo hará todo el solo? No es que sea muy recomendable si tenemos drupales muy complejos y con mucho código creado. Está claro que siempre puede haber alguna incompatibilidad, aunque yo hasta ahora no me he encontrado con ninguna y estas actualizaciones habrá que revisarlas.

Como no encontré nada por ahí decidí hacer este sencillo script que comprueba si son necesarias actualizaciones, las realiza , y te manda un correo si ha realizado alguna para que revises que todo esta bien.

Si os es útil hacédmelo saber dejando un comentario.

#!/bin/bash
#Shell que vamos a usar. Podemos averiguar el path de nuestro servidor con el comando --> which bash

# directorio donde se encuentra instalado drush, modificalo para acomodarlo al lugar en el que lo hayas instalado
drush=/home/miusuario/drush/drush
echo "Usando drush en la ruat $drush"

# Asignando a una variable la salida del drush sin provocar actualización para saber si hay algo que actualizar
updatedr=`echo "Primer drupal blabla.es" && cd ~/directorio_raiz/deldrupalblabla && $drush up -n && echo " Segundo drupal a actualizar petepete.es" && cd ~/public_html/petepete  && $drush up -n -l petepete.es &&  echo "tercer drupal miweb.es" && cd ~/public_html/miweb  && $drush up -n | mail -s "Actualizacion de core y modulos drupal realizada" micorreo@midominio.es`

#Sólo para saber si todo va bien mostramos que nos ha devuelto este comando, para saber que hay dentro de la variable.
echo 'la variable updatedr es igual a -->' $updatedr

# La palabra NOTE en mayúsculas sólo aparece cuando hay algo que actualizar en drush
# Actualmente lo he cambiado por la detección de la palabra SECURITY
updatoso=`echo $updatedr | grep SECURITY`

#Sólo por seguir el funcionamiento del script mostramos  el valor almacenado. Si no hay nada que actualizar updatoso no tendrá valor
#Ésta es la frase que aparece cuando hay algo que actualizar.
#NOTE: A security update for the Drupal core is available.
#Actualmente lo he cambiado por la detección de la palabra SECURITY

echo 'updatoso igual a -->'  $updatoso

#Si updatoso no tiene valor no actualizamos nada y salimos
#Si updatoso tiene algún valor realizamos actualización automática con drush -y
if [ "$updatoso" = "" ]; then
    echo "hemos llegado al then"
    echo "No hay nada que actualizar y salimos"
	else
    echo "hemos llegado al else"
	echo "existen actualizaciones"
	echo "Primer drupal blabla.es" && cd ~/directorio_raiz/deldrupalblabla && $drush up -y && echo " Segundo drupal a actualizar petepete.es" && cd ~/public_html/petepete  && $drush up -y -l petepete.es &&  echo "tercer drupal miweb.es" && cd ~/public_html/miweb  && $drush up -y | mail -s "Actualización de core y módulos drupal realizada" micorreo@midominio.es

fi

Sólo haceros notar que la línea de comandos drush es igual al principio que al final excepto porque le indicamos a drush que no actualize “drush up -n” mientras que la linea de comandos del final que se ejecuta sólo cuando sabemos que hay que actualizar algo usamos “drush up -y” .

Esto evita que nos esté mandando correos todos los días avisando solo cuando hay algo que actualizar.

Si como yo en algún caso usáis multi-instalaciones de drupal deberéis usar el parámetro -l por cada dominio alojado. Como ocurre en el dominio imaginario “drush up -y -l petepete.es”

Sólo os queda ponerlo en el cron (tareas programadas) de vuestro servidor , por ejemplo cada 12 horas y dormiréis mejor por las noches cuando penséis en esos drupales abandonados que ya casi no tocáis.

 

Actualización 7-05-2012

Os dejo también este estupendo script que realizó Eduardo Hernandez  motivado por este post. Hace básicamente lo mismo pero con una programación más elegante.  Personalmente solo lo he probado en modo interactivo, si alguien se anima a dejar el cuidado de sus drupales a él no dejéis de comentar y decirme que tal os ha ido.

Se ha creado un repositorio de versiones en github.com para ir generando un histórico de los avanzes, si quieres participar sube tus versiones o mándamelas para aportarlas.

#!/bin/bash
#
########################################################
#                   DRUPAL UPDATER v0.1                #
######################### por Edu ######################
#      Automatizador de actualizaciones de Drupal      #
########################################################

##############################
# VARIABLES DE CONFIGURACION #
#----------------------------#
# Editar para configuración  #
##############################
# URLs y directorios de los sitios Drupal a examinar
URLDRU[0]='http://www.miweb.com/contenidos'
DIRDRU[0]='/var/www/contenidos'
URLDRU[1]='http://www.drupalweb.com:888'
DIRDRU[1]='/var/www/drupalweb'
URLDRU[2]='http://www.otrositio.es'
DIRDRU[2]='/home/otrositio/public_html'
# Modo de funcionamiento (si se teclea el comando sin parámetros)
#   P = Informar por Pantalla, pero no actualizar. Equivale a parámetro "pantalla"
#   E = Si hay actualizaciones informar por Email, pero no actualizar. Equivale a parámetro "email"
#   A = Intentar Actualizar y si se hace informar de ello por email. Equivale a parámetro "actualizar"
MODFUN='E'
# Dirección email a la que mandar información de actualizaciones
EMAIL='miemail@micorreo.com'
# Ruta al binario de drush (en blanco lo busca en el PATH)
DRUSHCMD=''
# Directorio temporal
DIRTMP='/tmp'

##############################
# AJUSTE DE CONFIGURACIONES  #
#----------------------------#
#       No modificar         #
##############################
# Si no se ha definido ruta a DRUSH, la tomamos del PATH
if [ -z "$DRUSHCMD" ] ; then DRUSHCMD=`which drush` ; fi
if [ -z "$DRUSHCMD" ] ; then
  echo "Error: drush no encontrado en el PATH. Debes definir la variable DRUSHCMD del script"
  exit 1
fi
# Si el usuario teclea como parámetro "pantalla", "email" o "actualizar", pasamos el programa
# al modo correspondiente independientemente de lo que se determine en el modo de funcionamiento.
if [ "$1" = "pantalla" ] ; then MODFUN='P' ; fi
if [ "$1" = "email" ] ; then MODFUN='E' ; fi
if [ "$1" = "actualizar" ] ; then MODFUN='A' ; fi
# Nombre de este script para aparecer en los logs
APLI=actdru
# Establecemos el nombre del fichero temporal
FICTMP=${DIRTMP}/actdrup.tmp

##############################
#         PROGRAMA           #
#----------------------------#
#       No modificar         #
##############################
# Realizamos un bucle para todas las entradas del array DIRPRU
for ((S = 0 ; S < ${#DIRDRU[@]} ; S++)); do
  # Consultamos en DRUSH la lista de core y módulos pendientes de actualizar (array SALIDADRUSH)
  SALIDADRUSH=( `$DRUSHCMD up -p -r ${DIRDRU[$S]} -l ${URLDRU[$S]} -n | grep -v ^$ 2> /dev/null` )
  # Contamos el número de palabras resultantes
  NUMPALAB=${#SALIDADRUSH[@]}
  # Dado que cada actualizacion presenta 4 datos, calculamos su número dividiendo
  NUMACTUALIZ=`expr $NUMPALAB / 4`
  if [ $NUMACTUALIZ -eq 0 ]
    # Si no hay actualizaciones sacamos un mensaje por pantalla
    then
      FECHA=`date +"%x %X"`
      echo ${FECHA} ${APLI}: ${URLDRU[$S]} no necesita actualizaciones
    else
      # Compruebo si hay que actualizar el core de drupal buscando la cadena al principio de la lista de
      # actualizaciones y modifico consecuentemente las variables que indican el numero de módulos
      if [ "${SALIDADRUSH[0]}" == "drupal" ]
        then
          NUMACTDRUPAL=1
          NUMACTMODUL=`expr $NUMACTUALIZ - 1`
        else
          NUMACTDRUPAL=0
          NUMACTMODUL=$NUMACTUALIZ
      fi
      # Si además de haber actualizaciones el programa está en modo mostrar info por pantalla/email...
      #
      if [ ! "$MODFUN" = "A" ]
        then
          FECHA=`date +"%x %X"`
          # Escribo el mensaje resumen de lo que se necesita actualizar
          if [ $NUMACTDRUPAL -eq 1 ]
	    then
	      echo ${FECHA} ${APLI}: ${URLDRU[$S]} necesita actualizar su núcleo y $NUMACTMODUL módulo/s
	    else
	      echo ${FECHA} ${APLI}: ${URLDRU[$S]} necesita actualizar $NUMACTMODUL módulo/s
	  fi
          # Con este bucle voy listando nombres y versiones de todo lo que se necesita actualizar
	  for ((J = 0 ; J < ${NUMACTUALIZ} ; J++)); do
	    INDICEMODULO=`expr $J \* 4`
	    INDICEVVIEJA=`expr $INDICEMODULO + 1`
	    INDICEVNUEVA=`expr $INDICEMODULO + 2`
            echo ${FECHA} ${APLI}:\ \ \ ${SALIDADRUSH[$INDICEMODULO]} está en la versión ${SALIDADRUSH[$INDICEVVIEJA]} y ya existe la ${SALIDADRUSH[$INDICEVNUEVA]}
	  done
      fi
      # Si además de haber actualizaciones el programa está en modo mandar emails...
      #
      if [ "$MODFUN" = "E" ]
        then
          FECHA=`date +"%x %X"`
          # Escribo cabecera e introducción del email si no existe
	  if [ ! -f $FICTMP ] ; then
            echo En su ejecución de ${FECHA}, el script ${APLI} ha detectado estas actualizaciones de sitios Drupal pendientes de realizar: > $FICTMP
            echo >> $FICTMP
          fi
          # Escribo el mensaje resumen de lo que se necesita actualizar
          if [ $NUMACTDRUPAL -eq 1 ]
	    then
	      echo SITIO: ${URLDRU[$S]} Necesita actualizar su núcleo y $NUMACTMODUL módulo/s >> $FICTMP
	    else
	      echo SITIO: ${URLDRU[$S]} Necesita actualizar $NUMACTMODUL módulo/s >> $FICTMP
	  fi
          # Con este bucle voy listando nombres y versiones de todo lo que se necesita actualizar
	  for ((J = 0 ; J < ${NUMACTUALIZ} ; J++)); do
	    INDICEMODULO=`expr $J \* 4`
	    INDICEVVIEJA=`expr $INDICEMODULO + 1`
	    INDICEVNUEVA=`expr $INDICEMODULO + 2`
            echo \ \ - ${SALIDADRUSH[$INDICEMODULO]} está en la versión ${SALIDADRUSH[$INDICEVVIEJA]} y ya existe la ${SALIDADRUSH[$INDICEVNUEVA]} >> $FICTMP
	  done
      fi
      # Si además de haber actualizaciones el programa está en modo mandar actualizar...
      #
      if [ "$MODFUN" = "A" ]
        then
          FECHA=`date +"%x %X"`
          # Escribo cabecera e introducción del email si no existe
	  if [ ! -f $FICTMP ] ; then
            echo Estos son los resultados de la actualización automática de sitios Drupal llevada a cabo por el script ${APLI} en su ejecución de fecha ${FECHA}: > $FICTMP
            echo >> $FICTMP
          fi
          # Escribo el mensaje resumen de lo que se necesita actualizar
          if [ $NUMACTDRUPAL -eq 1 ]
	    then
	      echo ${FECHA} ${APLI}: ${URLDRU[$S]} actualiza su núcleo y $NUMACTMODUL módulo/s
	      echo SITIO: ${URLDRU[$S]} actualiza su núcleo y $NUMACTMODUL módulo/s >> $FICTMP
	    else
	      echo ${FECHA} ${APLI}: ${URLDRU[$S]} actualiza $NUMACTMODUL módulo/s
	      echo SITIO: ${URLDRU[$S]} actualiza $NUMACTMODUL módulo/s >> $FICTMP
	  fi
          # Con este bucle voy listando nombres y versiones de todo lo que se necesita actualizar
	  for ((J = 0 ; J < ${NUMACTUALIZ} ; J++)); do
	    INDICEMODULO=`expr $J \* 4`
	    INDICEVVIEJA=`expr $INDICEMODULO + 1`
	    INDICEVNUEVA=`expr $INDICEMODULO + 2`
            echo \ \ - ${SALIDADRUSH[$INDICEMODULO]} está en la versión ${SALIDADRUSH[$INDICEVVIEJA]} y se actualiza a ${SALIDADRUSH[$INDICEVNUEVA]} >> $FICTMP
	  done
          echo ----------------------------------------------------------------------------------------- >> $FICTMP
	  $DRUSHCMD up -r ${DIRDRU[$S]} -l ${URLDRU[$S]} -y >>$FICTMP 2>>$FICTMP
          echo >>$FICTMP
      fi
  fi
done


if [ "$MODFUN" = "E" ]
  then
    # Notifico en pantalla que envío la información de actualizaciones detectada por email
    if [ -n "$EMAIL" ]
      then
        echo ${FECHA} ${APLI}: Enviando mensaje a $EMAIL sobre las actualizaciones detectadas
      else
        echo ${FECHA} ${APLI}: Email no especificado, no se pudo enviar información por correo electrónico
        rm $FICTMP
        exit
    fi
    # Despedida de email
    echo >> $FICTMP
    echo Si desea que el script actualice todo este software sólo tiene que acceder a su servidor y teclear el comando \"${APLI}.sh actualizar\" y todo lo notificado se actualizará de forma automática. >> $FICTMP
    # Envío de email y borrado de fichero temporal
    mail -s "${APLI}: Sitios Drupal con actualizaciones pendientes" $EMAIL < $FICTMP
    rm $FICTMP
fi

if [ "$MODFUN" = "A" ]
  then
    if [ -n "$EMAIL" ] ; then
      # Notifico en pantalla que envío la información de actualizaciones detectada por email
      echo ${FECHA} ${APLI}: Enviando mensaje a $EMAIL sobre las actualizaciones realizadas
      # Envío de email y borrado de fichero temporal
      mail -s "${APLI}: Sitios Drupal actualizados" $EMAIL < $FICTMP
      rm $FICTMP
    fi
fi

4 comments

  1. Soy nuevo en esto de drupal y mas en drush, no se como ejecutar el script, ya tengo instalado y funcionando el drush (ya lo probe con algunos comando basicos xD), tambien ya baje el script con extension sh, pero no he encontrado la forma de ejecutarlo, me puedes ayudar por favor =D

    1. Para ejecutarlos solo tienes que hacer ./nombre_script
      Ese script es un script para tener los drupales actualizados en un servidor, pero para una instalaci´´on en local, lo mejor es hacerlo direcamente desde línea de comandos.

  2. Me gustaria saber actualizar la versión que me pide de Drupal 7.38, le he realizado de todo pero no encuentro como hacerlo, lo he intentado en actualizaciones, le copio/pego enlace de drupal core y no me hace nada, lo realizo desde modulos y tampoco.
    Me podriais hechar una mano, estoy bastante avanzado en este sistema opor los distintos tutoriales de Internet, pero actualizaciones no encuentro. Me encanta Drupal7 es sencillo cuando le coger el aire.
    Aun tengo muchooooo que aprender, llevo unos seis meses y he medio hecho 5 paginas, y me siento un aficionado total, pero me engancha.
    Un saludo y gracias

Leave a Reply

Your email address will not be published. Required fields are marked *