Shorten the time until the next tick if it's required to send a start notification

This commit is contained in:
2022-10-25 23:51:50 +02:00
parent f9c09d61b1
commit bd7d936dbd

View File

@@ -4,14 +4,16 @@ mod db;
mod error;
mod schema;
use std::{env, fs::File, io::BufReader, sync::Arc, time::Duration};
use std::time::Duration;
use std::{env, fs::File, io::BufReader, sync::Arc};
use anyhow::Result;
use async_mutex::Mutex;
use bot::fetch_and_announce_appointment;
use chrono::{DateTime, NaiveTime, TimeZone, Utc};
use chrono::{DateTime, NaiveDateTime, NaiveTime, TimeZone, Utc};
use chrono_tz::Europe;
use db::ChatInfo;
use diesel::result::Error::NotFound;
use diesel::{Connection, RunQueryDsl, SqliteConnection};
use diesel::{ExpressionMethods, QueryDsl};
use diesel_migrations::{embed_migrations, EmbeddedMigrations, MigrationHarness};
@@ -23,7 +25,7 @@ use teloxide::prelude::RequesterExt;
use teloxide::requests::Requester;
use teloxide::types::ChatId;
use teloxide::{adaptors::throttle::Limits, Bot};
use tokio::time::interval;
use tokio::time::sleep;
use crate::db::DbChat;
@@ -77,11 +79,36 @@ async fn main() {
{
let db = db.clone();
let bot = bot.clone();
let poll_duration = Duration::from_secs(config.poll_interval);
tokio::task::spawn(async move {
let mut interval = interval(Duration::from_secs(config.poll_interval));
interval.set_missed_tick_behavior(tokio::time::MissedTickBehavior::Delay);
loop {
interval.tick().await;
let now = Utc::now();
let next_appointment = db.lock().await.transaction(|db| {
use schema::chat::dsl::*;
chat.select(next_appointment_start)
.filter(next_appointment_start.is_not_null())
.filter(next_appointment_start.gt(now.timestamp()))
.order(next_appointment_start.asc())
.first::<Option<i64>>(db)
});
let next_appointment = match next_appointment {
Err(NotFound) => None,
Ok(appointment) => appointment,
Err(e) => Err(e).unwrap(),
};
let sleep_duration = next_appointment
.map(|timestamp| NaiveDateTime::from_timestamp(timestamp, 0))
.map(|naive_date_time| DateTime::<Utc>::from_utc(naive_date_time, Utc))
.map(|date_time| date_time - now)
.map(|duration| duration.to_std().unwrap())
.filter(|duration| *duration < poll_duration)
.unwrap_or(poll_duration);
sleep(sleep_duration).await;
// TODO Log the error and continue instead
check_task(&bot, config.reminder_time, &db).await.unwrap();
}