đ§Ș Remplacer Noti.st par du âas codeâ avec Jekyll đ
đ€ Non je ne quitte pas Noti.st car câest un mauvais outil
Cela me semblait utile de commencer par indiquer que ce blog post nâest pas pour dire que Noti.st est un mauvais outil. Bien au contraire, aprĂšs 3 ans dâutilisation je nâai pas grand chose Ă lui reprocher, il fait trĂšs bien le travail. Pour vous expliquer ce quâest Noti.st je pense que le texte dâaccueil du site rĂ©sume parfaitement son but:
Notist is a place to build your public speaking portfolio. A place to share your slides, but also to collate feedback, tweets, photos, resources and everything to create a permanent history of your speaking events.
Si vous voulez voir ce que cela donne voici mon compte publique : https://noti.st/philippart-s
đ€š Mais alors pourquoi partir de Noti.st ?
Pour plusieurs raisons, mais la principale est le fameux âvendor lockingâ. En effet, tout ce que jâai mis dans Noti.st nâest pas rĂ©cupĂ©rable, je peux rĂ©cupĂ©rer la liste de mes talks mais pas les Ă©lĂ©ments que jâai uploadĂ©s (titres, localisations, slides, liens, âŠ). Ce qui, le jour oĂč je ne souhaite plus payer mon abonnement (> 100$ par an) ou tout simplement arrĂȘter peut ĂȘtre problĂ©matique. Soit jâai tout perdu, soit je vais galĂ©rer avec pleins dâactions manuelles pour le faire (spoiler on en parlera lors de la partie migration đ±).
Et autre raison : cela faisait un petit moment que je me disais quâil y avait moyen de dĂ©velopper un truc au sein mĂȘme de mon blog au final ⊠Oui mĂȘme pour moi qui suit trĂšs loin dâĂȘtre un dĂ©veloppeur front (câest pour cela que jâutilise Jekyll đ).
đ Bon on y va ? Câest quoi les specs ?
Mon but : faire le moins dâactions possibles lorsque je dois rajouter un talk. Jâaurai donc un fichier de donnĂ©es global oĂč je retrouverai mes informations de base pour un talk : nom de la confĂ©rence, date, talk, slides, replay, source, ⊠Des templates pour gĂ©nĂ©rer un maximum de choses, idĂ©alement je ne veux pas Ă avoir Ă crĂ©er un blog post aprĂšs chaque confĂ©rence mais juste une nouvelle entrĂ©e dans mon fichier de donnĂ©es. Ce dernier point va ĂȘtre important dans certains choix par la suite.
Bien entendu, le tout intĂ©grĂ© dans Jekyll afin de facilement lâavoir dans mon blog.
Bonus attendus :
- une gestion as code
- une gestion du cycle de vie dans Git
- une modification simple car via des templates
- la dĂ©couverte dâune utilisation avancĂ©e de Jekyll
đż Les donnĂ©es
Le choix pour mes donnĂ©es de confĂ©rences a Ă©tĂ© assez rapide, YAML. Parce que on ne va pas se mentir, mĂȘme si on dit que lâon nâaime pas ça, câest quand mĂȘme bien pratique et pas trop verbeux. Jekyll permet de manipuler et dâaccĂ©der nativement aux donnĂ©es dans un fichier YAML avec le moteur de templating Liquid.
A ce jour la structure dâune entrĂ©e YAML pour une confĂ©rence est la suivante:
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
conf-2025:
name: conf
post-date: 2025-01-22
date: 22 au 25 janvier 2025
excerpt: "Liste des talks donnés lors de Conf 2025"
categories: Conférences
tags:
- Slides
- Replays
talks:
- title: "blabla"
location: Ville (đ«đ·)
language: Français
date: Mercredi 22 janvier 2025
time: 14h00 - 17h00
duration: 3h mins
abstract: |
blabla
source: xxx
slides: xxx
replay: xxx
âčïž Pour que Jekyll puisse les utiliser il vous suffit de les dĂ©poser dans le rĂ©pertoire _data de votre blog.
đïž Le layout, Ă©viter de rĂ©inventer la roue
Une fois ces donnĂ©es créées, il faut maintenant les afficher, pour cela rien de plus simple avec Jekyll et le moteur de templating Liquid, il est trĂšs simple dâajouter du dynamisme et de la gĂ©nĂ©ricitĂ© dans les blog posts.
Et cerise sur le gateau, Jekyll vient avec un mĂ©canisme de layouts pour faciliter la mise en page de vos articles. Et il est aussi possible dâutiliser Liquid dans un layout đ.
Du coup, pour créer un nouveau layout, il suffit de créer mon fichier conference.html dans le répertoire _layouts de mon blog:
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
---
layout: archive
classes: wide
categories:
- Conférences
tags:
- Slides
- Replays
---
{{ content }}
{% for conferences in site.data.conferences %}
{% assign conferenceFile = conferences[0] %}
{% assign conference = site.data.conferences[conferenceFile] %}
{% if conference[page.conference-name] %}
{% for talk in conference[page.conference-name].talks %}
<h2> {{talk.title}} </h2>
đ{{talk.location}} / đŁïž {{talk.language}} / đïž {{talk.date}} / â° {{talk.time}} / đ {{talk.duration}}
{% capture notice-2 %}
{{talk.abstract}}
{% endcapture %}
<div class="notice">{{ notice-2 | markdownify }}</div>
{% if talk.source %}đ <a href="{{talk.source}}">Code source</a> / {% endif %} {% if talk.slides %}đ
<a href="{{talk.slides}}">Slides</a>
{% endif %} {% if talk.replay %}/ đ„ <a href="{{talk.replay}}">Replay</a>{% endif %}
{% endfor %}
{% endif %}
{% endfor %}
Ce quâil faut retenir :
- la premiĂšre partie (entre le
---
) permet dâutiliser un layout de base si on le souhaite, - les
{{ }}
permettent dâaccĂ©der Ă des variables prĂ©dĂ©finies, commecontent
ou créées, commetalk
{{ content }}
représente le contenu du blog post créé qui utilisera ce layout et sera injecté à cet endroit du layout- les
{% %}
permettent dâajouter des instructions de flow
đ CrĂ©er les articles Ă partir du layout
A ce stade je peux utiliser mon layout dans un article fraßchement créé, par exemple pour Devoxx France:
1
2
3
4
5
6
7
8
9
10
11
---
layout: conference
title: Talks donnés à Devoxx France
date: 2025-04-16
permalink: /talks/devoxx-fr-2025
excerpt: Liste des talks donnés lors de Devoxx France 2025
categories: Conférences
tags:
- ["Slides", "Replays"]
conference-name: devoxx-fr-2025
---
Cela me gĂ©nĂšre lâarticle suivant:
@wildagsx
Câest bien ⊠Mais câest dommage de devoir crĂ©er un fichier Ă chaque talk pour quâau final il soit vide avec juste lâen-tĂȘte renseignĂ©e.
Il doit bien avoir un moyen dâautomatiser ça, dâautant que les donnĂ©es sont prĂ©sentes dans le fichier de donnĂ©es YAML prĂ©cĂ©demment créé.
âïž GĂ©nĂ©rer les articles avec un plugin
Jekyll utilise des plugins, soit communautaires, soit locaux. Câest le deuxiĂšme type qui va nous intĂ©resser, crĂ©er un plugin local. En effet, pour gĂ©nĂ©rer des pages, on va crĂ©er un plugin de type generator (logique đ). Et comme il est petit, pas besoin de le packager, pour cela il suffit de le mettre dans le rĂ©pertoire _plugins de notre site.
Câest du Ruby et voyons Ă quoi il ressemble :
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
require 'jekyll'
require 'fileutils'
module Jekyll
class ConferenceGenerator < Generator
safe true
def generate(site)
puts "---------- ConferenceGenerator started ----------"
if (!defined?@render_count)
@render_count = 1
end
if @render_count < 1
Jekyll.logger.info('already fetched data')
return
end
conferencesFilesKey = site.data['conferences'].keys.select { |key| key.include?('conferences') }
conferencesFilesKey.each do |key|
Jekyll.logger.info("Processing #{key}")
conferences = site.data['conferences'][key]
if conferences
conferences.each do |conference_id, details|
post_path = File.join('_posts', "#{details['post-date']}-#{conference_id}-talks.markdown")
post_data = {
'layout' => 'conference',
'title' => "Talks donnés à #{details['name']}",
'date' => details['post-date'],
'permalink' => "/talks/#{conference_id}",
'excerpt' => details['excerpt'],
'categories' => "#{details['categories']}",
'tags' => "\n - #{details['tags']}",
'conference-name' => conference_id
}
post_content = "---\n"
post_content += post_data.map { |key, value| "#{key}: #{value}" }.join("\n") + "\n"
post_content += "---\n"
# Write the post file
FileUtils.mkdir_p(File.dirname(post_path))
File.write(post_path, post_content)
puts "Generated post: #{post_path}"
end
else
puts "No conferences data found in site.data"
end
Jekyll.logger.info('Data fetched successfully.')
@render_count = @render_count - 1
puts "---------- ConferenceGenerator finished ----------"
end
end
end
end
Rien de bien compliqué ici :
- l10 -> l17 : câest juste un garde fou (pas trĂšs Ă©lĂ©gant) pour Ă©viter Ă Jekyll de boucler indĂ©finiment en mode watch. Le mode watch rĂ©gĂ©nĂšre lâensemble du site et appelle les plugins Ă chaque modification de fichier et comme le plugin Ă chaque exĂ©cution gĂ©nĂšre des fichiers câest un cercle sans fin đ. Il faudra que je trouve une maniĂšre plus Ă©lĂ©gante de le gĂ©rer.
- l19 : jâutilise uniquement les fichier YAML qui ont des donnĂ©es sur les confĂ©rences (ces fichiers commencent par
conferences
) - l20 -> l42: jâitĂšre pour chaque confĂ©rence et je fabrique lâen-tĂȘte
- l45 -> l46: crĂ©ation physique du fichier avec les donnĂ©es prĂ©parĂ©es (pour me repĂ©rer, les articles gĂ©nĂ©rĂ©s ont lâextension
markdown
et ceux écrits à la mainmd
)
Et voilĂ avec ce script Ă chaque modification dans un fichier YAML de donnĂ©es de confĂ©rences, les articles correspondants sont créés đ.
đ° Cerise sur le gĂąteau, une page pour lister les talks
Comme jâai les donnĂ©es qui servent Ă crĂ©er les pages unitaires, il est assez facile de crĂ©er une page qui liste lâensemble de mes confĂ©rences regroupĂ©es par annĂ©e:
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
---
title: "Conférences"
permalink: /conferences/
classes: wide
excerpt: "Liste des conférences avec les ressources (slides, vidéos, ...)"
#author_profile: false
categories:
- Conférences
tags:
- Slides
- Replays
---
Ici vous trouverez l'ensemble des conférences auxquelles j'ai participé et que j'ai présentées.
Vous pouvez aussi retrouver la [liste des sujets]({{ site.baseurl }}/talks) que j'ai donnés en conférence.
<style>
table {
width: 100%;
height: 100%;
display: table;
}
th,
td {
border: 0px solid #000;
padding: 10px;
text-align: center;
vertical-align: middle;
}
th {
background-color: #f2f2f2;
}
</style>
<table>
{% for conferences in site.data.conferences reversed %}
{% assign conferenceFile = conferences[0] %}
<tr>
<th colspan="3">
<h1> {{ conferenceFile | split: "-" | last }} </h1>
</th>
</tr>
{% for conference in site.data.conferences[conferenceFile] %}
<tr>
<td style="width: 35%; text-align: left;">
{{ conference[1].name}}
</td>
<td style="width: 35%;">
đïž {{ conference[1].date }} đïž
</td>
<td style="width: 30%;">
đ€ <a href="{{ site.baseurl }}/talks/{{ conference[0] }}">
Liste des talks
</a> đ€
</td>
</tr>
{% endfor %}
{% endfor %}
</table>
đ Il en reste une âŠ
Jâai aussi créé une page qui liste les talks que jâai donnĂ© et pour chaque talk la confĂ©rence avec le lien vers cette confĂ©rence.
Si jâai toutes les donnĂ©es, elles se trouvent dans lâensemble des fichiers YAML.
Cela demanderait à faire une analyse croisée et des group by
entre les donnĂ©es des fichiers, pas infaisable mais crĂ©er la page Ă la main a Ă©tĂ© moins long đ.
Cette page se trouve ici et son code ici.
Peut-ĂȘtre une amĂ©lioration dans le futur âŠ
đ„ł En conclusion
Ce qui mâa pris le plus de temps a Ă©tĂ© de reporter lâensemble de mes talks depuis Noti.st vers mon blog. Pas dâexport des donnĂ©es donc tout Ă la main talk par talk, pour plus de 50 talks jâai dĂ» y passer 3 Ă 4h.
Maintenant que câest fait, rajouter un talk câest ajouter une entrĂ©e dans le fichier YAML, soit pas plus de 2-3 minutes !
Pour voir ce que cela donne :
- la page qui liste les conférences avec un lien vers chaque article qui indique les talks avec leurs détails
- la page qui liste les talks avec la liste des confĂ©rences oĂč ils ont Ă©tĂ© donnĂ©s (avec un lien vers lâarticle de la dite confĂ©rence)
- un exemple dâarticle gĂ©nĂ©rĂ©
La suite ?
Certainement ajouter la partie rĂ©seau social / photos / la possibilitĂ© de mettre plusieurs liens vers du code source / une carte / ⊠Au final jâai juste Ă modifier mes templates, rajouter les donnĂ©es dans les YAML et ce sera effectif đ.
Si vous ĂȘtes arrivĂ©s jusque lĂ merci de mâavoir lu et si il y a des coquilles nâhĂ©sitez pas Ă me faire une issue ou PR đ.
Comments