Dans toute la suite, nous allons créer un plugin :pyfoo
, associé au mot-clef foo
, qui écrit dans le carnet le contenu de l'argument bar
, quasiment sans traitement. Ce plugin se présente sous la forme d'un fichier foo.py
(le nom de fichier est libre), présent dans un sous répertoire python/content
d'un datadir
.
Un plugin se présente sous la forme d'un fichier Python, présent dans un répertoire python/content
(relativement à un des datadir
). Ce fichier doit contenir une variable :pyCONTENT_PLUGIN
, qui est un dictionnaire dont les clefs sont des mots-clefs, et les valeurs des fonctions parse <parse>
.
Lors de la compilation du carnet, au moment de l'analyse de la variable content
du fichier .sb
, lorsqu'un de ces mots-clefs est rencontré, la fonction :pyparse
correspondante est appelée.
Notre plugin d'exemple contient donc le code suivant (où :pyparse
est une fonction, définie plus tôt dans le fichier, dont nous allons parler dans la partie suivante).
CONTENT_PLUGIN = {'foo': parse}
L'objet qui produit quelque chose dans le recueil est une instance de la classe :pycontent.Content
. La méthode d'initialisation est libre, et la méthode principale est la méthode :pycontent.Content.render
, qui prend en argument le contexte courant, et renvoie une chaîne de caractères à inclure dans le fichier .tex
.
Plus de détails sur cette classe (ainsi que sur les autres méthodes utilisées) sont disponibles dans le docstring de cette classe.
Pour notre exemple, nous allons définir une nouvelle classe :pyFoo
, héritant de cette classe :pycontent.Content
.
from patacrep.content import Content
class Foo(Content):
def __init__(self, arguments):
"""Fonction d'initialisation
Le moteur de plugin ne va pas appeler cette fonction directement : chaque
plugin est donc libre de définir cette initialisation comme il l'entend.
"""
self.arguments = arguments
def render(self, __context):
return self.arguments['bar']
La fonction :pyparse
est appelée lorsque le mot clef est rencontré, avec comme arguments :
- keyword
le mot clef ayant déclenché l'appel à cette fonction ;
- argument
l'argument passé au mot-clef ;
- config
le dictionnaire contenant la configuration du recueil en cours de construction. Le modifier est autorisé.
Ainsi, si le contenu du recueil comprend
- foo:
bar: "something"
content:
- "one"
- "two"
notre fonction :pyparse
sera appelée avec comme arguments parse('foo', {'bar': "something", 'content': ['one', 'two']}, config)
.
Cette fonction doit retourner une liste (éventuellement vide) d'objets de classe :pycontent.Content
(ou une de ces sous-classes). Ces objets seront intégrés au carnet (en utilisant principalement leur méthode :pycontent.Content.render
) dans l'ordre dans lequel ils apparaissent dans cette liste.
Notre fonction va donc être la suivante :
def parse(keyword, argument, config):
return [Foo(argument)]
Notre plugin est maintenant fonctionnel et réagit au mot clé foo
.