You are already familiar with the basic structure of the Ktor server application project and its main parts. In this topic, we will discuss another important part of the Ktor framework, which no Ktor application can do without — Ktor plugins.
Purpose of Ktor plugins
When a user initiates a request to your server, it's routed to the appropriate handler that processes the request and sends back the response. This is the basic pipeline:
Everything seems to be fine, but in a real-world application, you will have to deal with many common tasks, such as authorization, cookie support, handling headers, and so on. Luckily, Ktor offers ready-made solutions for these common tasks. It simplifies the development process and allows you to focus on the business logic of your application.
To take advantage of Ktor's built-in functionality, you'll need to install the appropriate plugins. This approach gives Ktor flexibility as it allows you to use only the features you need.
How plugins work
Plugins were developed to take the load off handlers (app logic) and extend their functionality. When a user request comes in, it's first routed to the correct handler via the routing mechanism, but before it reaches the handler, it may pass through one or more plugins (for example, plugin1 in the diagram). After the handler processes the request and generates a response, that response can again pass through one or more plugins (such as plugin2) before being sent back to the client.
This approach allows you to easily expand the functionality of your application by simply installing the appropriate plugins.
Fun fact: routing itself is implemented as just another plugin.
Now, let's look at a real example to see how to install and use a plugin.
Installing plugins
Imagine that you are making a website and want your users to connect using the secure HTTPS protocol. You could check the protocol in every handler and redirect the user from HTTP to HTTPS if necessary. However, it's much easier to use a plugin called HttpsRedirect created for this purpose.
First we need to add the plugin's dependency to our project. We'll go through two ways to do that:
The first and easiest way is to generate a project with pre-selected plugins using the Ktor Project Generator.
This is also true for other project generation methods covered in Ktor Setting-up First App.
Just go to the generator and, after specifying the settings of the project, you can choose which plugins you want to include. Then click "Download" to get a project template with those plugins' dependencies already added.
Also, when you select a plugin, its description appears, explaining what the plugin does:
This method is very convenient, but it won't work if you want to add a plugin dependency to an existing project.
The second method involves manually adding the appropriate dependency to your build script and rebuild the project. The dependencies needed for different plugins are described in the official Ktor documentation. For
HttpsRedirect, you would add the following:implementation("io.ktor:ktor-server-http-redirect:$ktor_version")implementation "io.ktor:ktor-server-http-redirect:$ktor_version"
Once the dependency is added, you can install the plugin. If you generated your project with the plugin already included, you will likely find it pre-installed. If you've added the dependency manually, you need to call the install function. You can do this at different levels depending on your needs:
embeddedServerinstallationIf you are using
embeddedServer, you can install the plugin directly within its setup:// ... import io.ktor.server.application.* import io.ktor.server.plugins.httpsredirect.HttpsRedirect fun main() { embeddedServer(Netty, port = 8080) { install(HttpsRedirect) // ... }.start(wait = true) }This ensures that every request handled by this application will be processed by the
HttpsRedirectplugin.Module installation
You can install a plugin within a module, and any requests handled by that module will be processed by the plugin:
import io.ktor.server.application.* import io.ktor.server.plugins.httpsredirect.HttpsRedirect fun Application.module() { install(HttpsRedirect) // ... }Route-level installation
In some cases, you may want a plugin to apply only to a specific part of your application. While this can be achieved through multiple modules with unique functionalities, you can also do it by using the
installfunction inside a route. This creates a route-scoped plugin that will only execute for requests matching that route. We'll cover this more in a later topic.
Configuring plugins
Plugins can have optional configuration. For example, for a Compression plugin that can be used to compress a response body and decompress a request body, different compression algorithms can be used, such as gzip and deflate which can be specified and further configured.
In our case, for HttpsRedirect, we could specify if our redirection is permanent which tells the client to use the new HTTPS address for all future requests. This is done by sending an HTTP 301 Moved Permanently status code instead of a temporary one. Browsers and search engines will then update their records to directly access the secure version of the page which is more efficient.
Here is how you would configure it:
install(HttpsRedirect) {
// This is the default behavior if not specified
permanentRedirect = true
}The Ktor documentation for each plugin explains what can be configured and how to do it.
You don't need to know the details of the plugins discussed here, just the overall plugin system in Ktor.
More about installing plugins
You are not limited to the list of standard plugins and can install third-party plugins. The description and configuration can be found on the website of the plugin developers. For example, we can install the Koin plugin for dependency injection as follows, as shown on the official Koin website:
fun Application.module() {
// Install Koin
install(Koin) {
slf4jLogger()
modules(helloAppModule)
}
}You can also create custom plugins if needed, but creating custom plugins is beyond the scope of this topic. First, you need to gain experience in using existing plugins.
Conclusion
In this topic, we've introduced you to the plugin system in Ktor. Now you know what plugins are for and how to install and configure them.
You've seen that using plugins can significantly simplify development because a part of the functionality is implemented in the plugin, and you will focus on developing your application's logic.