forum_notifier/src/main.rs
author unc0rr
Sun, 05 May 2019 00:06:52 +0200
changeset 1 52bbcfcbd850
parent 0 5696442fee1c
permissions -rw-r--r--
- Add check for skipped page ids - Silence spam with repeated author/title pair
Ignore whitespace changes - Everywhere: Within whitespace: At end of lines:
0
5696442fee1c Add new forum topics notificator
unC0Rr
parents:
diff changeset
     1
use curl::easy::{Easy, WriteError};
5696442fee1c Add new forum topics notificator
unC0Rr
parents:
diff changeset
     2
use curl::Error;
5696442fee1c Add new forum topics notificator
unC0Rr
parents:
diff changeset
     3
use dbus::{BusType, Connection, Message};
5696442fee1c Add new forum topics notificator
unC0Rr
parents:
diff changeset
     4
use log::{debug, info, warn};
5696442fee1c Add new forum topics notificator
unC0Rr
parents:
diff changeset
     5
use scraper::{Html, Selector};
5696442fee1c Add new forum topics notificator
unC0Rr
parents:
diff changeset
     6
use std::fs;
5696442fee1c Add new forum topics notificator
unC0Rr
parents:
diff changeset
     7
use std::str;
5696442fee1c Add new forum topics notificator
unC0Rr
parents:
diff changeset
     8
use std::thread;
5696442fee1c Add new forum topics notificator
unC0Rr
parents:
diff changeset
     9
use std::time;
5696442fee1c Add new forum topics notificator
unC0Rr
parents:
diff changeset
    10
1
52bbcfcbd850 - Add check for skipped page ids
unc0rr
parents: 0
diff changeset
    11
struct StateInfo {
52bbcfcbd850 - Add check for skipped page ids
unc0rr
parents: 0
diff changeset
    12
    url: String,
52bbcfcbd850 - Add check for skipped page ids
unc0rr
parents: 0
diff changeset
    13
    previous_title: String,
52bbcfcbd850 - Add check for skipped page ids
unc0rr
parents: 0
diff changeset
    14
    previous_author: String,
52bbcfcbd850 - Add check for skipped page ids
unc0rr
parents: 0
diff changeset
    15
}
52bbcfcbd850 - Add check for skipped page ids
unc0rr
parents: 0
diff changeset
    16
52bbcfcbd850 - Add check for skipped page ids
unc0rr
parents: 0
diff changeset
    17
fn inform(state: &mut StateInfo, title: &str, author: &str) {
52bbcfcbd850 - Add check for skipped page ids
unc0rr
parents: 0
diff changeset
    18
    if state.previous_title == title && state.previous_author == author {
52bbcfcbd850 - Add check for skipped page ids
unc0rr
parents: 0
diff changeset
    19
        return;
52bbcfcbd850 - Add check for skipped page ids
unc0rr
parents: 0
diff changeset
    20
    }
52bbcfcbd850 - Add check for skipped page ids
unc0rr
parents: 0
diff changeset
    21
52bbcfcbd850 - Add check for skipped page ids
unc0rr
parents: 0
diff changeset
    22
    state.previous_title = title.to_string();
52bbcfcbd850 - Add check for skipped page ids
unc0rr
parents: 0
diff changeset
    23
    state.previous_author = author.to_string();
52bbcfcbd850 - Add check for skipped page ids
unc0rr
parents: 0
diff changeset
    24
0
5696442fee1c Add new forum topics notificator
unC0Rr
parents:
diff changeset
    25
    let c = Connection::get_private(BusType::Session).unwrap();
5696442fee1c Add new forum topics notificator
unC0Rr
parents:
diff changeset
    26
    let mut m = Message::new_method_call(
5696442fee1c Add new forum topics notificator
unC0Rr
parents:
diff changeset
    27
        "org.kde.konversation",
5696442fee1c Add new forum topics notificator
unC0Rr
parents:
diff changeset
    28
        "/irc",
5696442fee1c Add new forum topics notificator
unC0Rr
parents:
diff changeset
    29
        "org.kde.konversation",
5696442fee1c Add new forum topics notificator
unC0Rr
parents:
diff changeset
    30
        "say",
5696442fee1c Add new forum topics notificator
unC0Rr
parents:
diff changeset
    31
    )
5696442fee1c Add new forum topics notificator
unC0Rr
parents:
diff changeset
    32
    .unwrap();
1
52bbcfcbd850 - Add check for skipped page ids
unc0rr
parents: 0
diff changeset
    33
    let msg_str = &format!("[{}] {}: {}", state.url, author, title)[..];
0
5696442fee1c Add new forum topics notificator
unC0Rr
parents:
diff changeset
    34
5696442fee1c Add new forum topics notificator
unC0Rr
parents:
diff changeset
    35
    info!("Notification: {}", msg_str);
5696442fee1c Add new forum topics notificator
unC0Rr
parents:
diff changeset
    36
5696442fee1c Add new forum topics notificator
unC0Rr
parents:
diff changeset
    37
    m.append_items(&["freenode".into(), "#hedgewars".into(), msg_str.into()]);
1
52bbcfcbd850 - Add check for skipped page ids
unc0rr
parents: 0
diff changeset
    38
    let _r = c.send(m).unwrap();
0
5696442fee1c Add new forum topics notificator
unC0Rr
parents:
diff changeset
    39
}
5696442fee1c Add new forum topics notificator
unC0Rr
parents:
diff changeset
    40
1
52bbcfcbd850 - Add check for skipped page ids
unc0rr
parents: 0
diff changeset
    41
fn handle_page(state: &mut StateInfo, data: &[u8]) -> Result<usize, WriteError> {
0
5696442fee1c Add new forum topics notificator
unC0Rr
parents:
diff changeset
    42
    let page = str::from_utf8(data).unwrap();
5696442fee1c Add new forum topics notificator
unC0Rr
parents:
diff changeset
    43
    let document = Html::parse_document(page);
5696442fee1c Add new forum topics notificator
unC0Rr
parents:
diff changeset
    44
5696442fee1c Add new forum topics notificator
unC0Rr
parents:
diff changeset
    45
    let title_selector = Selector::parse("title").unwrap();
5696442fee1c Add new forum topics notificator
unC0Rr
parents:
diff changeset
    46
    let mut titles = document.select(&title_selector);
5696442fee1c Add new forum topics notificator
unC0Rr
parents:
diff changeset
    47
5696442fee1c Add new forum topics notificator
unC0Rr
parents:
diff changeset
    48
    if let Some(title_str) = titles.next() {
5696442fee1c Add new forum topics notificator
unC0Rr
parents:
diff changeset
    49
        let t = &title_str.inner_html();
5696442fee1c Add new forum topics notificator
unC0Rr
parents:
diff changeset
    50
        let title = &t[..t.len() - 12];
5696442fee1c Add new forum topics notificator
unC0Rr
parents:
diff changeset
    51
        //info!("Topic is '{}'", title);
5696442fee1c Add new forum topics notificator
unC0Rr
parents:
diff changeset
    52
5696442fee1c Add new forum topics notificator
unC0Rr
parents:
diff changeset
    53
        let author_selector = Selector::parse("div.forum-post-wrapper div.forum-post-panel-sub div.author-pane div.author-pane-inner div.author-pane-name-status.author-pane-section div.author-pane-line.author-name").unwrap();
5696442fee1c Add new forum topics notificator
unC0Rr
parents:
diff changeset
    54
        let mut authors = document.select(&author_selector);
5696442fee1c Add new forum topics notificator
unC0Rr
parents:
diff changeset
    55
5696442fee1c Add new forum topics notificator
unC0Rr
parents:
diff changeset
    56
        if let Some(author_name) = authors.next() {
5696442fee1c Add new forum topics notificator
unC0Rr
parents:
diff changeset
    57
            let author = &author_name.inner_html();
5696442fee1c Add new forum topics notificator
unC0Rr
parents:
diff changeset
    58
            //info!("Author is '{}'", author);
5696442fee1c Add new forum topics notificator
unC0Rr
parents:
diff changeset
    59
1
52bbcfcbd850 - Add check for skipped page ids
unc0rr
parents: 0
diff changeset
    60
            inform(state, title, &author[1..author.len() - 1]);
0
5696442fee1c Add new forum topics notificator
unC0Rr
parents:
diff changeset
    61
        } else {
5696442fee1c Add new forum topics notificator
unC0Rr
parents:
diff changeset
    62
            warn!("Author not found");
5696442fee1c Add new forum topics notificator
unC0Rr
parents:
diff changeset
    63
        }
5696442fee1c Add new forum topics notificator
unC0Rr
parents:
diff changeset
    64
    } else {
5696442fee1c Add new forum topics notificator
unC0Rr
parents:
diff changeset
    65
        warn!("No title found");
5696442fee1c Add new forum topics notificator
unC0Rr
parents:
diff changeset
    66
    }
5696442fee1c Add new forum topics notificator
unC0Rr
parents:
diff changeset
    67
5696442fee1c Add new forum topics notificator
unC0Rr
parents:
diff changeset
    68
    Ok(data.len())
5696442fee1c Add new forum topics notificator
unC0Rr
parents:
diff changeset
    69
}
5696442fee1c Add new forum topics notificator
unC0Rr
parents:
diff changeset
    70
1
52bbcfcbd850 - Add check for skipped page ids
unc0rr
parents: 0
diff changeset
    71
fn query(state: &mut StateInfo) -> Result<(), Error> {
0
5696442fee1c Add new forum topics notificator
unC0Rr
parents:
diff changeset
    72
    let mut easy = Easy::new();
5696442fee1c Add new forum topics notificator
unC0Rr
parents:
diff changeset
    73
1
52bbcfcbd850 - Add check for skipped page ids
unc0rr
parents: 0
diff changeset
    74
    easy.url(&state.url)?;
52bbcfcbd850 - Add check for skipped page ids
unc0rr
parents: 0
diff changeset
    75
    easy.fail_on_error(true)?;
0
5696442fee1c Add new forum topics notificator
unC0Rr
parents:
diff changeset
    76
5696442fee1c Add new forum topics notificator
unC0Rr
parents:
diff changeset
    77
    let mut transfer = easy.transfer();
1
52bbcfcbd850 - Add check for skipped page ids
unc0rr
parents: 0
diff changeset
    78
    transfer.write_function(|data| handle_page(state, data))?;
0
5696442fee1c Add new forum topics notificator
unC0Rr
parents:
diff changeset
    79
    transfer.perform()
5696442fee1c Add new forum topics notificator
unC0Rr
parents:
diff changeset
    80
}
5696442fee1c Add new forum topics notificator
unC0Rr
parents:
diff changeset
    81
5696442fee1c Add new forum topics notificator
unC0Rr
parents:
diff changeset
    82
fn main() {
5696442fee1c Add new forum topics notificator
unC0Rr
parents:
diff changeset
    83
    stderrlog::new()
5696442fee1c Add new forum topics notificator
unC0Rr
parents:
diff changeset
    84
        .verbosity(3)
5696442fee1c Add new forum topics notificator
unC0Rr
parents:
diff changeset
    85
        .timestamp(stderrlog::Timestamp::Second)
5696442fee1c Add new forum topics notificator
unC0Rr
parents:
diff changeset
    86
        .module(module_path!())
5696442fee1c Add new forum topics notificator
unC0Rr
parents:
diff changeset
    87
        .init()
5696442fee1c Add new forum topics notificator
unC0Rr
parents:
diff changeset
    88
        .unwrap();
5696442fee1c Add new forum topics notificator
unC0Rr
parents:
diff changeset
    89
5696442fee1c Add new forum topics notificator
unC0Rr
parents:
diff changeset
    90
    let short_delay = time::Duration::from_secs(3);
1
52bbcfcbd850 - Add check for skipped page ids
unc0rr
parents: 0
diff changeset
    91
    let long_delay = time::Duration::from_secs(100);
0
5696442fee1c Add new forum topics notificator
unC0Rr
parents:
diff changeset
    92
    let file_name = "/usr/home/unC0Rr/.local/unC0Rr/forumchecker/node.txt";
5696442fee1c Add new forum topics notificator
unC0Rr
parents:
diff changeset
    93
    let mut node_id: u32 = fs::read_to_string(file_name).unwrap().parse().unwrap();
1
52bbcfcbd850 - Add check for skipped page ids
unc0rr
parents: 0
diff changeset
    94
    let mut known_good_id: Option<u32> = None;
52bbcfcbd850 - Add check for skipped page ids
unc0rr
parents: 0
diff changeset
    95
    let mut shift: u32 = 0;
52bbcfcbd850 - Add check for skipped page ids
unc0rr
parents: 0
diff changeset
    96
52bbcfcbd850 - Add check for skipped page ids
unc0rr
parents: 0
diff changeset
    97
    let mut state = StateInfo {
52bbcfcbd850 - Add check for skipped page ids
unc0rr
parents: 0
diff changeset
    98
        url: String::new(),
52bbcfcbd850 - Add check for skipped page ids
unc0rr
parents: 0
diff changeset
    99
        previous_title: String::new(),
52bbcfcbd850 - Add check for skipped page ids
unc0rr
parents: 0
diff changeset
   100
        previous_author: String::new()
52bbcfcbd850 - Add check for skipped page ids
unc0rr
parents: 0
diff changeset
   101
    };
0
5696442fee1c Add new forum topics notificator
unC0Rr
parents:
diff changeset
   102
5696442fee1c Add new forum topics notificator
unC0Rr
parents:
diff changeset
   103
    info!("Starting from node id {}", node_id);
5696442fee1c Add new forum topics notificator
unC0Rr
parents:
diff changeset
   104
5696442fee1c Add new forum topics notificator
unC0Rr
parents:
diff changeset
   105
    loop {
1
52bbcfcbd850 - Add check for skipped page ids
unc0rr
parents: 0
diff changeset
   106
        let try_id = node_id + shift;
52bbcfcbd850 - Add check for skipped page ids
unc0rr
parents: 0
diff changeset
   107
52bbcfcbd850 - Add check for skipped page ids
unc0rr
parents: 0
diff changeset
   108
        debug!("Quering node id {}", try_id);
0
5696442fee1c Add new forum topics notificator
unC0Rr
parents:
diff changeset
   109
1
52bbcfcbd850 - Add check for skipped page ids
unc0rr
parents: 0
diff changeset
   110
        thread::sleep(short_delay);
52bbcfcbd850 - Add check for skipped page ids
unc0rr
parents: 0
diff changeset
   111
52bbcfcbd850 - Add check for skipped page ids
unc0rr
parents: 0
diff changeset
   112
        state.url = format!("https://www.hedgewars.org/node/{}", try_id);
52bbcfcbd850 - Add check for skipped page ids
unc0rr
parents: 0
diff changeset
   113
52bbcfcbd850 - Add check for skipped page ids
unc0rr
parents: 0
diff changeset
   114
        let res = query(&mut state);
0
5696442fee1c Add new forum topics notificator
unC0Rr
parents:
diff changeset
   115
5696442fee1c Add new forum topics notificator
unC0Rr
parents:
diff changeset
   116
        if let Ok(_) = res {
1
52bbcfcbd850 - Add check for skipped page ids
unc0rr
parents: 0
diff changeset
   117
            if shift > 0 && known_good_id == None {
52bbcfcbd850 - Add check for skipped page ids
unc0rr
parents: 0
diff changeset
   118
                known_good_id = Some(try_id);
52bbcfcbd850 - Add check for skipped page ids
unc0rr
parents: 0
diff changeset
   119
                shift = 0;
52bbcfcbd850 - Add check for skipped page ids
unc0rr
parents: 0
diff changeset
   120
            } else {
52bbcfcbd850 - Add check for skipped page ids
unc0rr
parents: 0
diff changeset
   121
                node_id = try_id + 1;
52bbcfcbd850 - Add check for skipped page ids
unc0rr
parents: 0
diff changeset
   122
                if Some(node_id) == known_good_id {
52bbcfcbd850 - Add check for skipped page ids
unc0rr
parents: 0
diff changeset
   123
                    node_id += 1;
52bbcfcbd850 - Add check for skipped page ids
unc0rr
parents: 0
diff changeset
   124
                    known_good_id = None;
52bbcfcbd850 - Add check for skipped page ids
unc0rr
parents: 0
diff changeset
   125
                }
52bbcfcbd850 - Add check for skipped page ids
unc0rr
parents: 0
diff changeset
   126
                shift = 0;
52bbcfcbd850 - Add check for skipped page ids
unc0rr
parents: 0
diff changeset
   127
                fs::write(file_name, node_id.to_string()).unwrap();
52bbcfcbd850 - Add check for skipped page ids
unc0rr
parents: 0
diff changeset
   128
            }
0
5696442fee1c Add new forum topics notificator
unC0Rr
parents:
diff changeset
   129
        } else {
1
52bbcfcbd850 - Add check for skipped page ids
unc0rr
parents: 0
diff changeset
   130
            if known_good_id == None {
52bbcfcbd850 - Add check for skipped page ids
unc0rr
parents: 0
diff changeset
   131
                shift = (shift + 1) % 11;
52bbcfcbd850 - Add check for skipped page ids
unc0rr
parents: 0
diff changeset
   132
                thread::sleep(long_delay);
52bbcfcbd850 - Add check for skipped page ids
unc0rr
parents: 0
diff changeset
   133
            } else if Some(try_id + 1) == known_good_id {
52bbcfcbd850 - Add check for skipped page ids
unc0rr
parents: 0
diff changeset
   134
                node_id = known_good_id.unwrap() + 1;
52bbcfcbd850 - Add check for skipped page ids
unc0rr
parents: 0
diff changeset
   135
                known_good_id = None;
52bbcfcbd850 - Add check for skipped page ids
unc0rr
parents: 0
diff changeset
   136
                shift = 0;
52bbcfcbd850 - Add check for skipped page ids
unc0rr
parents: 0
diff changeset
   137
                fs::write(file_name, node_id.to_string()).unwrap();
52bbcfcbd850 - Add check for skipped page ids
unc0rr
parents: 0
diff changeset
   138
            } else {
52bbcfcbd850 - Add check for skipped page ids
unc0rr
parents: 0
diff changeset
   139
                shift += 1;
52bbcfcbd850 - Add check for skipped page ids
unc0rr
parents: 0
diff changeset
   140
            }
0
5696442fee1c Add new forum topics notificator
unC0Rr
parents:
diff changeset
   141
        }
5696442fee1c Add new forum topics notificator
unC0Rr
parents:
diff changeset
   142
    }
5696442fee1c Add new forum topics notificator
unC0Rr
parents:
diff changeset
   143
}