Catégorie « Quelques trucs sur… »

Quelques trucs sur Jekyll #2

Lisibilité des erreurs

Par défaut, le serveur de développement de Jekyll remonte des erreurs assez sommaires en ne précisant que le template concerné. C’est inutilisable quand on débugue un template (même si un numéro de ligne ne serait pas du luxe) mais quand l’erreur vient d’un plugin c’est plutôt limité.

Pour un affichage un peu plus détaillé avec une trace d’exécution permettant de déterminer quelle ligne de quel plugin est en cause, il faut utiliser l’option --trace ou -t.

bundle exec jekyll serve --drafts -t

Fichiers sitemap.xml et robots.txt

Il existe un plugin pour générer le fichier sitemap.xml, par contre je n’ai rien trouvé pour gérer son intégration au fichier robots.txt. On peut certes faire un fichier robots.txt à la main mais le lien est censé être absolu, donc ce n’est pas super propre de le mettre en dur.

Finalement je m’en suis sorti en ajoutant un fichier robots.html avec le contenu suivant :

---
layout: null
permalink: robots.txt
---

Sitemap: {{ site.url }}/sitemap.xml

La directive permalink: robots.txt permet de forcer le bon nom de fichier, layout: null dit que le contenu ne doit pas du tout être habillé et comme on est dans une page normale on a accès aux variables globales, notamment site.url.

Éviter la profusion d’espaces dans les pages

Le moteur de template de Jekyll fonctionne en ajoutant des pseudo balises dans le code HTML notamment pour indiquer les structures de contrôles, boucles, affectations de variables, etc.

Pour que le code reste lisible on fait des retours à la ligne entre ces différentes balises et on indente. Ceci aboutit à de très nombreuses lignes uniquement peuplées d’espaces (ceux de l’indentation).

Exemple :

<h2>Catégories</h2>
{% assign groupedCategories = site.categories | group_categories %}
{% for group in groupedCategories %}
  <h3>{{ group[0] }}</h3>
  <ul>
    {% assign categories = group[1] | sort_by_keys %}
    {% for category in categories %}
      <li><a href="/categories/{{ category[0]|slugify:'latin' }}/">{{ category[0] }}</a> ({{ category[1].size }})</li>
    {% endfor %}
  </ul>
{% endfor %}

Il est possible d’y remédier en utilisant un caractère - dans les balises. Chaque - suivant une ouverture de balise ({% devient {%-) indique que les espaces précédents doivent être ignorés et sur les fermetures ( (%} devient -%})) que les espaces suivants doivent être ignorés.

L’exemple précédent devient alors :

<h2>Catégories</h2>
{%- assign groupedCategories = site.categories | group_categories -%}
{% for group in groupedCategories %}
  <h3>{{ group[0] }}</h3>
  <ul>
    {%- assign categories = group[1] | sort_by_keys -%}
    {% for category in categories %}
      <li><a href="/categories/{{ category[0]|slugify:'latin' }}/">{{ category[0] }}</a> ({{ category[1].size }})</li>
    {%- endfor %}
  </ul>
{% endfor %}

C’est la même syntaxe que l’on retrouve dans d’autres moteurs de templates comme Twig pour PHP (la plupart des syntaxes sont assez proches en fait entre ces deux moteurs).

Remarque : cette syntaxe semble ne pas bien fonctionner avec le tag endraw, en effet j’ai des erreurs dès que je place un tiret un en début de ce tag (alors qu’à la fin et sur le tag raw ça marche)…


Quelques trucs sur UNIX/Linux #5

Générer un mot de passe aléatoire

Pour générer une chaîne aléatoire, pouvant par exemple servir de mot de passe, dans un terminal entrer la ligne suivante :

< /dev/urandom tr -dc _A-Z-a-z-0-9 | head -c 10; echo ""

Il est possible de modifier les caractères autorisés via l’option -dc de urandom et le nombre de caractères via l’option -c de head.

Le echo "" sert juste à forcer un retour à la ligne.

Correction d’une commande

Dans le terminal, il est possible de la ré-exécuter la dernière commande en remplaçant la première occurrence d’une chaîne par une autre.

Exemple :

# Affiche 'toto'
echo 'toto'
# Affiche 'tato'
^to^ta^

Ceci peut être utile pour corriger une faute de frappe. Attention, seule la première occurrence est remplacée et la nouvelle commande est exécutée dans la foulée sans demande de confirmation.

Revenir en arrière dans les répertoires

La commande cd permet de revenir au précédent répertoire où l’on était via cd -.

Attention, cela fait bien retourner au dernier dossier où l’on était et pas remonter d’un cran dans l’arborescence (qui se fait via cd ..).


Quelques trucs sur UNIX/Linux #4

Crontab et 49-3

Crontab : changer l’adresse e-mail de destination

Il est possible de spécifier l’utilisateur destinataire des mails de la crontab en définissant la variable MAILTO en début de fichier.

Remplacement de l’adresse par défaut :

MAILTO=webmaster@mon-site.fake

Désactivation de l’envoir de mail :

MAILTO=""

(source)

Crontab : redirection de la sortie dans un fichier

Par défaut cron envoie par mail l’ensemble des sorties (standard et erreur) des tâches exécutées. Il peut être intéressant d’écrire tout ça dans des fichiers de logs à la place.

Pour ce faire il suffit d’utiliser les mécanismes de redirections de sorties habituellement disponibles dans les terminaux en terminant la ligne par > /path/to/log/file 2>&1. La première partie (> /path/to/log/file) déclenche la redirection de la sortie standard, la seconde partie (2>&1) effectue la redirection de la sortie d’erreur dans la sortie standard.

Exemples :

# Redirection de la sortie standard dans le fichier /path/cron.log et envoi par e-mail de la sortie d'erreur
* * * * * /path/to/script > /path/cron.log

# Redirection des sorties standard et erreur dans le fichier /path/cron.log
* * * * * /path/to/script > /path/cron.log 2>&1

(source)

Rejouer la dernière commande en ajoutant sudo

Il m’arrive de temps en temps de lancer une commande nécessitant les droits root en oubliant de la précéder par sudo. Il est possible de rappeler la dernière commande l’historique mais la syntaxe est un poil longue et compliquée.

La solution que j’ai retenue est donc d’ajouter un alias dans mon fichier .bash_aliases :

# 49.3
alias 49.3='sudo "$BASH" -c "$(history -p !!)"'

Le nom 49.3 est court et facile à retenir puisqu’il fait directement référence à l’article 49 alinéa 3 de la constitution française dont le principe est somme toute assez proche ^^


Quelques trucs sur Jekyll #1

Histoire de pas spammer avec trop d’articles je vais reprendre mon habitude de faire des tirs groupés pour les petites astuces, remarques et autres ^^

Publication avec les bonnes URL dans les métas SEO

Une petite subtilité que je n’avais pas remarquée tout de suite : les URL générées dans les métas SEO sont des URL absolues et dans les pages générées par le mode serveur dédié au dev (via bundle exec jekyll serve) commencent par l’IP locale et non le domaine spécifié dans le _config.yml (c’est pas illogique mais comme ça ne touche que des métas SEO, ça ne saute pas aux yeux).

J’ai rapidement trouvé dans la doc qu’il faut utiliser jekyll build pour générer en mode production. Plus précisément jekyll build --destination _deploy qui génère les pages dans un autre dossier histoire que les deux ne se marchent pas sur les pieds.

En y repensant c’est effectivement plus propre de travailler comme ça avec une commande dédiée à la génération pour la prod et un dossier séparé, ça évite de déployer par erreur des brouillons par exemple.

Brouillons et gestion des dates

Jekyll gère les brouillons en les plaçant dans un dossier à part et en ajoutant une option à la génération si on veut les inclure (cf la documentation).

Tout ça fonctionne très bien à une exception près : la doc dit que la date de l’article sera la date de dernière modification du fichier. Jusque là pourquoi pas, ça se tient assez bien. Mais elle ne précise pas plusieurs subtilités :

  • d’une part ça ne fonctionne que pour le fichier Markdown et pas pour les HTML (là, l’article n’est apparemment pas visible sans date)
  • d’autre part il ne s’agit que d’une valeur par défaut dans le cas où la date n’est pas présente dans l’en-tête de l’article
  • enfin, si la date spécifiée est dans le futur, l’article ne sera pas visible, même pour un brouillon (donc on ne peut pas planifier une date à l’avance)

Dans l’ensemble c’est assez bancal comme fonctionnement je trouve, mais une fois qu’on sais comme ça marche, on s’en sort.


Quelques trucs sur PHPMyAdmin #1

Durée de la session

C'est toujours lourd d'avoir une session qui expire et de devoir se reconnecter. Pour augmenter la durée de la session, rendez-vous dans le fichier config.inc.php situé à la racine du site et modifiez la valeur de la clé 'LoginCookieValidity' du tableau $cfg :

$cfg['LoginCookieValidity'] = 3600 * 48; // 48 hours

Évidemment, c'est à éviter sur les serveurs en production, pour des raisons de sécurité mais sur un poste de développement c'est tout à fait approprié.

Si ça ne passe pas c'est que la valeur de session.gc_maxlifetime est trop restrictive dans le php.ini. Ceci peut être changé là bas ou bien directement via ini_set() dans le fichier de configuration de PHPMyAdmin si votre configuration serveur l'autorise.

Pagination des tables

Un projet Change comporte en facilement plus de 200 à 300 tables (selon le nombre de modules utilisés) du coup, ça active la pagination de la liste. Pour augmenter le nombre d'éléments par page et éviter ce problème, rendez-vous dans le fichier config.inc.php situé à la racine du site ajoutez l'entrée suivante :

$cfg['MaxTableList'] = 500;

Défilement des colonnes

Toujours dans Change, les tables comportent un assez grand nombre de champs puisqu'on a toujours au moins la 15aine de champs standards des documents qui se retrouvent devant... Du coup quand on défile pour voir les champs utiles, on perd les menus, notamment le bouton "actualiser", ce qui oblige à défiler en sens inverse (puisque PHPMyAdmin a la mauvaise idée d'être basé sur des frames, faire juste un F5 n'est pas forcément toujours une bonne idée).

Du coup je me suis ajouté les styles suivants via Stylish sur Firefox qui place le défilement horizontal sur le tableau plutôt que sur la page complète (en remplaçant évidemment l'URL du site) :

@namespace url(http://www.w3.org/1999/xhtml);
@-moz-document url-prefix("<URL_DU_SITE>") {
  .data {
    overflow-x: auto !important;
    overflow-y: hidden !important;
    max-width: 100% !important;
  }
}