nixify and fixify

main
Felix Albrigtsen 2023-08-27 01:51:57 +02:00
parent 29c6f5c4ef
commit 6f125fdb1f
9 changed files with 209 additions and 12 deletions

6
README.md Normal file
View File

@ -0,0 +1,6 @@
# PVV Calendar -> Matrix bot
This bot scrapes https://pvv.ntnu.no/hendelser/, fetches todays events and sends announcement messages in matrix.
Packaged as a nix flake, see ./module.nix for options.

26
flake.lock Normal file
View File

@ -0,0 +1,26 @@
{
"nodes": {
"nixpkgs": {
"locked": {
"lastModified": 1692986144,
"narHash": "sha256-M4VFpy7Av9j+33HF5nIGm0k2+DXXW4qSSKdidIKg5jY=",
"owner": "NixOS",
"repo": "nixpkgs",
"rev": "74e5bdc5478ebbe7ba5849f0d765f92757bb9dbf",
"type": "github"
},
"original": {
"id": "nixpkgs",
"ref": "nixos-23.05",
"type": "indirect"
}
},
"root": {
"inputs": {
"nixpkgs": "nixpkgs"
}
}
},
"root": "root",
"version": 7
}

57
flake.nix Normal file
View File

@ -0,0 +1,57 @@
{
inputs = {
nixpkgs.url = "nixpkgs/nixos-23.05";
};
outputs = { self, nixpkgs }: let
system = "x86_64-linux";
pkgs = nixpkgs.legacyPackages.${system};
in {
packages.${system} = {
default = self.packages.${system}.pvv-calendar-bot;
pvv-calendar-bot = pkgs.python3Packages.buildPythonPackage {
name = "pvv-calendar-bot";
src = ./.;
format = "pyproject";
nativeBuildInputs = [
pkgs.python3Packages.setuptools
];
propagatedBuildInputs = with pkgs.python3Packages; [
beautifulsoup4
markdown2
matrix-nio
requests
];
};
};
nixosModules.default = ./module.nix;
overlays.${system}.default = prevPackages: finalPackages: {
inherit (self.packages.${system}) pvv-calendar-bot;
};
nixosConfigurations."test" = nixpkgs.lib.nixosSystem {
system = "x86_64-linux";
modules = [
self.nixosModules.default
{ nixpkgs.overlays = [ self.overlays."x86_64-linux".default ]; }
{
boot.isContainer = true;
services.pvv-calendar-bot = {
enable = true;
settings.matrix = {
channel = "testchannel";
user = "testuser";
homeserver = "pvv.ntnu.no";
};
settings.secretsFile = pkgs.writeText "calendarSecrets" "snakeoil";
};
}
];
};
};
}

75
module.nix Normal file
View File

@ -0,0 +1,75 @@
{ config, lib, pkgs, ... }:
let
cfg = config.services.pvv-calendar-bot;
inherit (lib) mkDefault mkEnableOption mkPackageOption mkIf mkOption types mdDoc;
in {
options.services.pvv-calendar-bot = {
enable = mkEnableOption (lib.mdDoc "Enable pvv-calendar-bot to post to matrix");
package = mkPackageOption pkgs "pvv-calendar-bot" {};
settings = {
onCalendar = mkOption {
type = types.str;
default = "9 0 * * *";
description = mdDoc "OnCalendar string for the systemd service(e.g. crontab format)";
};
matrix = {
user = mkOption {
type = types.str;
description = mdDoc "Matrix username to authenticate with";
example = "@bot_calendar:pvv.ntnu.no";
};
channel = mkOption {
type = types.str;
description = mdDoc "Room ID of the channel to post announcements in";
example = "!abcdef:matrix.org";
};
homeserver = mkOption {
type = types.str;
description = mdDoc "Matrix homeserver URL to connect to";
example = "https://matrix.org";
};
};
secretsFile = mkOption {
type = types.path;
description = mdDoc "Path to secrets file that defines MATRIX_ACCESS_TOKEN";
};
};
};
config = mkIf cfg.enable {
systemd.timers."pvv-calendar-bot" = {
wantedBy = [ "timers.target" ];
timerConfig = {
OnCalendar = cfg.settings.onCalendar;
Unit = "pvv-calendar-bot";
};
};
systemd.services."pvv-calendar-bot" = {
preStart = let
envFile = pkgs.writeText "pvv-calendar-bot-env" ''
MATRIX_URL=${cfg.settings.matrix.homeserver}
MATRIX_USER=${cfg.settings.matrix.user}
ANNOUNCEMENT_CHANNEL=${cfg.settings.matrix.channel}
MATRIX_TOKEN=@MATRIX_ACCESS_TOKEN@
'';
in ''
${pkgs.replace-secret}/bin/replace-secret '@MATRIX_ACCESS_TOKEN@' ${cfg.settings.secretsFile} /run/pvv-calendar-bot/env
'';
serviceConfig = {
ExecStart = "${cfg.package}/bin/pvv-calendar-bot";
RuntimeDirectory = "pvv-calendar-bot";
DynamicUser = true;
EnvironmentFile = [ "-/run/pvv-calendar-bot/env" ];
};
};
};
}

28
pyproject.toml Normal file
View File

@ -0,0 +1,28 @@
[build-system]
requires = ["setuptools", "setuptools-scm"]
build-backend = "setuptools.build_meta"
[project]
name = "pvv-calendar-bot"
authors = [
{name = "Felix Albrigtsen", email = "felix@albrigtsen.it"},
{name = "Fredrik Robertsen", email = "fredrikrobertsen7@gmail.com"}
]
version = "1.0.0"
description = "PVV Calendar -> Matrix bot"
requires-python = ">=3.10"
keywords = []
license = {text = "MIT"}
dependencies = [
"beautifulsoup4",
"markdown2",
"matrix-nio",
"requests"
]
[tool.setuptools.packages.find]
where = ["src"]
include = ["*"]
[project.scripts]
pvv-calendar-bot = "pvv_calendar_bot:main"

View File

@ -0,0 +1 @@
from pvv_calendar_bot.main import main

View File

@ -1,4 +1,7 @@
from event import Event
#! /usr/bin/env python
from .event import Event
from .scraping import get_soup, process_soup, get_events_today
import os
from nio import AsyncClient
@ -7,8 +10,6 @@ from markdown2 import Markdown
import asyncio
import datetime
from scraping import get_soup, process_soup, get_events_today
MATRIX_URL=os.environ["MATRIX_URL"]
MATRIX_USER=os.environ["MATRIX_USER"]
MATRIX_TOKEN=os.environ["MATRIX_TOKEN"]
@ -44,18 +45,21 @@ async def sendMatrixAnnouncement(event: Event, channel: str = ANNOUNCEMENT_CHANN
}
)
async def main() -> None:
async def sendCalendarEvents() -> None:
global client
client = AsyncClient(MATRIX_URL, MATRIX_USER)
client.access_token = MATRIX_TOKEN
s = get_soup()
es = get_events_today(process_soup(s))
scrapeData = get_soup()
eventsToday = get_events_today(process_soup(scrapeData))
for e in es:
await sendMatrixAnnouncement(e, ANNOUNCEMENT_CHANNEL, False)
for event in eventsToday:
await sendMatrixAnnouncement(event, ANNOUNCEMENT_CHANNEL, False)
await client.close()
asyncio.run(main())
def main():
asyncio.run(sendCalendarEvents())
if __name__ == "__main__":
main()

View File

@ -1,11 +1,11 @@
from .event import Event
from typing import List
from bs4 import BeautifulSoup
import requests
from operator import add
from functools import reduce
import datetime
from event import Event
def get_soup() -> BeautifulSoup:
r = requests.get("http://www.pvv.ntnu.no/hendelser/")