Plugins use **plugin hooks** to customize LLM's behavior. These hooks are powered by the [Pluggy plugin system](https://pluggy.readthedocs.io/).
Each plugin can implement one or more hooks using the @hookimpl decorator against one of the hook function names described on this page.
LLM imitates the Datasette plugin system. The [Datasette plugin documentation](https://docs.datasette.io/en/stable/writing_plugins.html) describes how plugins work.
This demonstrates how to register a model with both sync and async versions, and how to specify an alias for that model.
The {ref}`model plugin tutorial <tutorial-model-plugin>` describes how to use this hook in detail. Asynchronous models {ref}`are described here <advanced-model-plugins-async>`.
Plugins can register new {ref}`template loaders <prompt-templates-loaders>` using the `register_template_loaders` hook.
Template loaders work with the `llm -t prefix:name` syntax. The prefix specifies the loader, then the registered loader function is called with the name as an argument. The loader function should return an `llm.Template()` object.
This example plugin registers `my-prefix` as a new template loader. Once installed it can be used like this:
The loader function should raise a `ValueError` if the template cannot be found or loaded correctly, providing a clear error message.
(plugin-hooks-register-fragment-loaders)=
## register_fragment_loaders(register)
Plugins can register new fragment loaders using the `register_template_loaders` hook. These can then be used with the `llm -f prefix:argument` syntax.
The `prefix` specifies the loader. The `argument` will be passed to that registered callback..
The callback works in a very similar way to template loaders, but returns either a single `llm.Fragment` or a list of `llm.Fragment` objects.
The `llm.Fragment` constructor takes a required string argument (the content of the fragment) and an optional second `source` argument, which is a string that may be displayed as debug information. For files this is a path and for URLs it is a URL. Your plugin can use anything you like for the `source` value.
If multiple fragments are returned they will be used as if the user passed multiple `-f X` arguments to the command.
Multiple fragments are useful for things like plugins that return every file in a directory. By giving each file its own fragment we can avoid having multiple copies of the full collection stored if only a single file has changed.