Ene082016

Como actualizar temas custom de WordPress desde GitHub

Cuando íbamos a liberar nuestro template de WordPress en GitHub, una de las primeras cosas que quisimos hacer fue que pudiese detectar cuando hay disponible una versión nueva y se lo notificase al usuario, como sucede con los temas alojados en el repositorio de WordPress.

WordPress implementa un sistema de actualizaciones automáticas para sus plugins y temas, pero solo funciona de forma transparente si estos están alojados en sus repositorios oficiales. En nuestro caso nos interesa que dichas actualizaciones se puedan hacer desde el repositorio de GitHub, donde subo todos los cambios que voy haciéndole al mismo y donde cualquiera puede proponer mejoras fácilmente.

Para que nuestro tema se pueda actualizar desde nuestro repositorio, tan solo ha sido necesario añadir este código al fichero functions.php:

1  // set_site_transient('update_themes', null);
2  function geko_check_update( $transient ) {
3      if ( empty( $transient->checked ) ) {
4          return $transient;
5      }
6      $theme_data = wp_get_theme(wp_get_theme()->template);
7      $theme_slug = $theme_data->get_template();
8      //Delete '-master' from the end of slug
9      $theme_uri_slug = preg_replace('/-master$/', '', $theme_slug);
10     
11     $remote_version = '0.0.0';
12     $style_css = wp_remote_get("https://raw.githubusercontent.com/erm2587/".$theme_uri_slug."/master/style.css")['body'];
13     if ( preg_match( '/^[ \t\/*#@]*' . preg_quote( 'Version', '/' ) . ':(.*)$/mi', $style_css, $match ) && $match[1] )
14         $remote_version = _cleanup_header_comment( $match[1] );
15    
16     if (version_compare($theme_data->version, $remote_version, '<')) {
17         $transient->response[$theme_slug] = array(
18             'theme'       => $theme_slug,
19             'new_version' => $remote_version,
20             'url'         => 'https://github.com/erm2587/'.$theme_uri_slug,
21             'package'     => 'https://github.com/erm2587/'.$theme_uri_slug.'/archive/master.zip',
22         );
23     }
24        
25     return $transient;
26 }
27 add_filter( 'pre_set_site_transient_update_themes', 'geko_check_update' );

Cómo funciona

Básicamente hay que registrar una función al filtro pre_set_site_transient_update_themes, donde se consulta cual es la versión que hay en el repositorio, se comparar con la versión local y se emite una notificación de actualización, en caso de que sea necesario.

Nuestra implementación es muy simple. Obtiene el fichero style.css directamente del repositorio, comprueba la versión y si es mayor que la del tema instalado, emite la notificación de actualización. Por lo que es recomendable tener varias ramas, una de desarrollo y otra de producción, de modo que todos los commits que vayan a la rama de producción sean los que afecten a las actualizaciones.

Como ya habrás notado, por muchos commits que hagas en la rama de producción, no se emitirá una actualización hasta que en alguno de ellos se cambia la versión en el fichero style.css.

Algunos detalles que debes conocer

En la línea 6 se averigua cual es el tema que está activo. Como el código está escrito para ser lo más universal posible, no se nombra el tema de forma explícita sino que se obtiene usando la función wp_get_theme(). Dicha función se llama dos veces, una para obtener la ruta del tema padre y la otra para obtener todos los datos del mismo. Esto se hace para garantizar que si este tema es padre de otro, las actualizaciones que se detecten sean relativas al tema padre y no al hijo, donde normalmente se hacen todas las personalizaciones propias de cada usuario.

Cuando nos descargamos un repositorio de GitHub en ZIP, este añade al final del nombre un guion seguido del nombre de la rama desde la que se ha hecho la descarga, pero en la URL el nombre de la rama no se especifica del mismo modo. En la línea 9 se obtiene el nombre del tema en la URL eliminando la palabra -master del final del nombre del tema. Como desventaja del uso de esta técnica, el nombre de la carpeta de nuestro tema tiene que terminar con el nombre de la rama de GitHub a la que pertenece pero, como es algo invisible para usuario, no es muy importante.

En las líneas 12, 20 y 21 he marcado en rojo el nombre de usuario de GitHub, tendrás que reemplazarlo por el tuyo…

En las líneas 9, 12 y 21, se especifica la rama de nuestro tema, si el tuyo está en otra deberás cambiarla (marcada en verde).

 

Política de comentarios

Dada la importancia de los comentarios como espacio de participación, te pedimos por favor que leas detenidamente y cumplas con las siguientes normas de participación.

4 respuestas para “Como actualizar temas custom de WordPress desde GitHub

Zagur

Pff chicos, no se como agradeceros que compartáis este código. De verdad mil gracias, pero mil mil y mil veces de gracias. Llevaba mucho tiempo intentando hacer esto y esta noche hablando con un amigo programador me dio una idea para hacerlo. El cual intentaré hacer y si funciona lo compartiré para comparar.

He estado probando el código y funciona genial, pero he tenido que hacer unas modificaciones para adaptarlo a GitLab. Las rutas de la hoja de estilos y del paquete zip son distintas. Algunas líneas quedarían así:

$style_css = wp_remote_get("https://gitlab.com/zagur/".$theme_uri_slug."/blob/master/style.css")['body'];

$transient->response[$theme_slug] = array(
            'theme'       => $theme_slug,
            'new_version' => $remote_version,
            'url'         => 'https://gitlab.com/zagur/'.$theme_uri_slug,
            'package'     => 'https://gitlab.com/zagur/'.$theme_uri_slug.'/repository/archive.zip',
        );

Mi tema usa un Theme Options y he pensado en hacer un apartado para configurar el repo y que el usuario pueda decidir por dos brancas: la estable y la de desarrollo. Habéis pensado en hacer un plugin con esto? Puede ser buena idea, que cada uno configure su repo y que pueda actualizar temas o plugins. Si necesitáis ayuda con esto yo os ayudo.

Por lo demás funciona genial. Este código lo añadiré en la próxima versión y cuando documente la documentación de mi tema os pongo los primeros en mis créditos! De verdad, muchas gracias, si algún día viajo a las islas, os invito a unas cañas. Prometido queda.

Zagur,
Saludos.


Elías R.M.

Hola Zagur

Me alegro mucho de que te hayamos podido ser de ayuda. Muchas gracias también por tu aportación, será muy útil para los que trabajen con GitLab.

Estoy pensando en escribir una implementación algo más universal, manteniendo la simplicidad al máximo, y esa podría ser la escusa perfecta para convertirlo en plugin, muy buena idea.

Saludos


Liamngls

Qué buena la info y el aporte de Zagur, gracias a ambos 🙂


Elías R.M.

Gracias a ti por tu comentario Liamngls.

Saludos


Deja un comentario

Tu dirección de correo electrónico no será publicada.