You are correct, that a systemd
timer is designed in a way so that it starts a service at a specific time. So to make it stop a service, it's necessary to make a workaround.
Luckily, there are several ways to achieve this.
Option 1: Make Service A conflict with Service B
The first option is to create a oneshot
Service B that is in conflict with Service A. The advantage of this method is that it relies solely on systemd
unit files, but the disadvantage is that you have to modify Service A (or create drop-in configuration).
First, you need to modify the configuration of Service A, so it conflicts with Service B:
Add this the configuration of A.service:
[Unit]
Conflicts=B.service
...
Then create a B.service that does nothing:
[Unit]
Description=B service description
[Service]
Type=oneshot
ExecStart=/bin/echo ''
This method is taken from this Q&A.
Option 2: Make Service B simply stop Service A
Another option is to create a oneshot
Service B that simply runs the command to stop Service A. The advantage of this method is that you don't have to modify Service A, but the disadvantage is that it relies on running systemctl
and not solely on systemd
unit files.
For this method, you only need to create a B.service, but this time it will run a command:
[Unit]
Description=B service description
[Service]
Type=oneshot
ExecStart=/usr/bin/systemctl stop A.service
For both options, you then create a different timer for each of those services. Timer A will now start Service A, and Timer B will later start Service B - effectively stopping Service A.
See this Q&A for more information about setting up systemd
services and timers.