Compare commits
6 Commits
letterbox-
...
letterbox-
| Author | SHA1 | Date | |
|---|---|---|---|
| e1681edda3 | |||
| 25ee8522ad | |||
| df356e8711 | |||
| 2e43700cd7 | |||
| b3769d99bf | |||
| 2aa85a03f8 |
18
Cargo.lock
generated
18
Cargo.lock
generated
@@ -3156,7 +3156,7 @@ dependencies = [
|
|||||||
|
|
||||||
[[package]]
|
[[package]]
|
||||||
name = "letterbox-notmuch"
|
name = "letterbox-notmuch"
|
||||||
version = "0.17.47"
|
version = "0.17.49"
|
||||||
dependencies = [
|
dependencies = [
|
||||||
"itertools",
|
"itertools",
|
||||||
"log",
|
"log",
|
||||||
@@ -3171,7 +3171,7 @@ dependencies = [
|
|||||||
|
|
||||||
[[package]]
|
[[package]]
|
||||||
name = "letterbox-procmail2notmuch"
|
name = "letterbox-procmail2notmuch"
|
||||||
version = "0.17.47"
|
version = "0.17.49"
|
||||||
dependencies = [
|
dependencies = [
|
||||||
"anyhow",
|
"anyhow",
|
||||||
"clap",
|
"clap",
|
||||||
@@ -3184,7 +3184,7 @@ dependencies = [
|
|||||||
|
|
||||||
[[package]]
|
[[package]]
|
||||||
name = "letterbox-server"
|
name = "letterbox-server"
|
||||||
version = "0.17.47"
|
version = "0.17.49"
|
||||||
dependencies = [
|
dependencies = [
|
||||||
"ammonia",
|
"ammonia",
|
||||||
"anyhow",
|
"anyhow",
|
||||||
@@ -3207,8 +3207,8 @@ dependencies = [
|
|||||||
"html-escape",
|
"html-escape",
|
||||||
"html2text",
|
"html2text",
|
||||||
"ical",
|
"ical",
|
||||||
"letterbox-notmuch 0.17.47",
|
"letterbox-notmuch 0.17.49",
|
||||||
"letterbox-shared 0.17.47",
|
"letterbox-shared 0.17.49",
|
||||||
"linkify",
|
"linkify",
|
||||||
"lol_html",
|
"lol_html",
|
||||||
"mailparse",
|
"mailparse",
|
||||||
@@ -3249,10 +3249,10 @@ dependencies = [
|
|||||||
|
|
||||||
[[package]]
|
[[package]]
|
||||||
name = "letterbox-shared"
|
name = "letterbox-shared"
|
||||||
version = "0.17.47"
|
version = "0.17.49"
|
||||||
dependencies = [
|
dependencies = [
|
||||||
"build-info 0.0.42",
|
"build-info 0.0.42",
|
||||||
"letterbox-notmuch 0.17.47",
|
"letterbox-notmuch 0.17.49",
|
||||||
"regex",
|
"regex",
|
||||||
"serde",
|
"serde",
|
||||||
"sqlx",
|
"sqlx",
|
||||||
@@ -3262,7 +3262,7 @@ dependencies = [
|
|||||||
|
|
||||||
[[package]]
|
[[package]]
|
||||||
name = "letterbox-web"
|
name = "letterbox-web"
|
||||||
version = "0.17.47"
|
version = "0.17.49"
|
||||||
dependencies = [
|
dependencies = [
|
||||||
"build-info 0.0.42",
|
"build-info 0.0.42",
|
||||||
"build-info-build",
|
"build-info-build",
|
||||||
@@ -3274,7 +3274,7 @@ dependencies = [
|
|||||||
"graphql_client",
|
"graphql_client",
|
||||||
"human_format",
|
"human_format",
|
||||||
"itertools",
|
"itertools",
|
||||||
"letterbox-shared 0.17.47",
|
"letterbox-shared 0.17.49",
|
||||||
"log",
|
"log",
|
||||||
"seed",
|
"seed",
|
||||||
"seed_hooks",
|
"seed_hooks",
|
||||||
|
|||||||
@@ -8,7 +8,7 @@ authors = ["Bill Thiede <git@xinu.tv>"]
|
|||||||
edition = "2021"
|
edition = "2021"
|
||||||
license = "UNLICENSED"
|
license = "UNLICENSED"
|
||||||
publish = ["xinu"]
|
publish = ["xinu"]
|
||||||
version = "0.17.47"
|
version = "0.17.49"
|
||||||
repository = "https://git.z.xinu.tv/wathiede/letterbox"
|
repository = "https://git.z.xinu.tv/wathiede/letterbox"
|
||||||
|
|
||||||
[profile.dev]
|
[profile.dev]
|
||||||
|
|||||||
14
server/.sqlx/query-77f79f981a9736d18ffd4b87d3aec34d6a048162154a3aba833370c58a860795.json
generated
Normal file
14
server/.sqlx/query-77f79f981a9736d18ffd4b87d3aec34d6a048162154a3aba833370c58a860795.json
generated
Normal file
@@ -0,0 +1,14 @@
|
|||||||
|
{
|
||||||
|
"db_name": "PostgreSQL",
|
||||||
|
"query": "DELETE FROM snooze WHERE id = $1",
|
||||||
|
"describe": {
|
||||||
|
"columns": [],
|
||||||
|
"parameters": {
|
||||||
|
"Left": [
|
||||||
|
"Int4"
|
||||||
|
]
|
||||||
|
},
|
||||||
|
"nullable": []
|
||||||
|
},
|
||||||
|
"hash": "77f79f981a9736d18ffd4b87d3aec34d6a048162154a3aba833370c58a860795"
|
||||||
|
}
|
||||||
26
server/.sqlx/query-c8383663124a5cc5912b54553f18f7064d33087ebfdf3c0c1c43cbe6d3577084.json
generated
Normal file
26
server/.sqlx/query-c8383663124a5cc5912b54553f18f7064d33087ebfdf3c0c1c43cbe6d3577084.json
generated
Normal file
@@ -0,0 +1,26 @@
|
|||||||
|
{
|
||||||
|
"db_name": "PostgreSQL",
|
||||||
|
"query": "\nSELECT id, message_id\nFROM snooze\nWHERE wake < NOW();\n ",
|
||||||
|
"describe": {
|
||||||
|
"columns": [
|
||||||
|
{
|
||||||
|
"ordinal": 0,
|
||||||
|
"name": "id",
|
||||||
|
"type_info": "Int4"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"ordinal": 1,
|
||||||
|
"name": "message_id",
|
||||||
|
"type_info": "Text"
|
||||||
|
}
|
||||||
|
],
|
||||||
|
"parameters": {
|
||||||
|
"Left": []
|
||||||
|
},
|
||||||
|
"nullable": [
|
||||||
|
false,
|
||||||
|
false
|
||||||
|
]
|
||||||
|
},
|
||||||
|
"hash": "c8383663124a5cc5912b54553f18f7064d33087ebfdf3c0c1c43cbe6d3577084"
|
||||||
|
}
|
||||||
@@ -32,8 +32,8 @@ futures = "0.3.31"
|
|||||||
headers = "0.4.0"
|
headers = "0.4.0"
|
||||||
html-escape = "0.2.13"
|
html-escape = "0.2.13"
|
||||||
ical = "0.11"
|
ical = "0.11"
|
||||||
letterbox-notmuch = { path = "../notmuch", version = "0.17.47", registry = "xinu" }
|
letterbox-notmuch = { path = "../notmuch", version = "0.17.49", registry = "xinu" }
|
||||||
letterbox-shared = { path = "../shared", version = "0.17.47", registry = "xinu" }
|
letterbox-shared = { path = "../shared", version = "0.17.49", registry = "xinu" }
|
||||||
linkify = "0.10.0"
|
linkify = "0.10.0"
|
||||||
lol_html = "2.3.0"
|
lol_html = "2.3.0"
|
||||||
mailparse = "0.16.1"
|
mailparse = "0.16.1"
|
||||||
|
|||||||
@@ -676,6 +676,18 @@ impl MutationRoot {
|
|||||||
|
|
||||||
Ok(true)
|
Ok(true)
|
||||||
}
|
}
|
||||||
|
#[instrument(skip_all, fields(rid=request_id()))]
|
||||||
|
async fn label_unprocessed<'ctx>(
|
||||||
|
&self,
|
||||||
|
ctx: &Context<'ctx>,
|
||||||
|
limit: Option<usize>,
|
||||||
|
) -> Result<bool, Error> {
|
||||||
|
let nm = ctx.data_unchecked::<Notmuch>();
|
||||||
|
let pool = ctx.data_unchecked::<PgPool>();
|
||||||
|
label_unprocessed(&nm, &pool, false, limit, "tag:unprocessed").await?;
|
||||||
|
Ok(true)
|
||||||
|
}
|
||||||
|
|
||||||
#[instrument(skip_all, fields(rid=request_id()))]
|
#[instrument(skip_all, fields(rid=request_id()))]
|
||||||
async fn refresh<'ctx>(&self, ctx: &Context<'ctx>) -> Result<bool, Error> {
|
async fn refresh<'ctx>(&self, ctx: &Context<'ctx>) -> Result<bool, Error> {
|
||||||
let nm = ctx.data_unchecked::<Notmuch>();
|
let nm = ctx.data_unchecked::<Notmuch>();
|
||||||
@@ -687,6 +699,9 @@ impl MutationRoot {
|
|||||||
// Process email labels
|
// Process email labels
|
||||||
label_unprocessed(&nm, &pool, false, Some(1000), "tag:unprocessed").await?;
|
label_unprocessed(&nm, &pool, false, Some(1000), "tag:unprocessed").await?;
|
||||||
|
|
||||||
|
// Look for snoozed messages and mark unread
|
||||||
|
wakeup(&nm, &pool).await?;
|
||||||
|
|
||||||
#[cfg(feature = "tantivy")]
|
#[cfg(feature = "tantivy")]
|
||||||
{
|
{
|
||||||
let tantivy = ctx.data_unchecked::<TantivyConnection>();
|
let tantivy = ctx.data_unchecked::<TantivyConnection>();
|
||||||
@@ -707,6 +722,33 @@ impl SubscriptionRoot {
|
|||||||
|
|
||||||
pub type GraphqlSchema = Schema<QueryRoot, MutationRoot, SubscriptionRoot>;
|
pub type GraphqlSchema = Schema<QueryRoot, MutationRoot, SubscriptionRoot>;
|
||||||
|
|
||||||
|
#[instrument(name = "wakeup", skip_all)]
|
||||||
|
pub async fn wakeup(nm: &Notmuch, pool: &PgPool) -> Result<(), Error> {
|
||||||
|
for row in sqlx::query!(
|
||||||
|
r#"
|
||||||
|
SELECT id, message_id
|
||||||
|
FROM snooze
|
||||||
|
WHERE wake < NOW();
|
||||||
|
"#
|
||||||
|
)
|
||||||
|
.fetch_all(pool)
|
||||||
|
.await?
|
||||||
|
{
|
||||||
|
let query: Query = row.message_id.parse()?;
|
||||||
|
info!("need to wake {query}");
|
||||||
|
let unread = true;
|
||||||
|
newsreader::set_read_status(pool, &query, unread).await?;
|
||||||
|
#[cfg(feature = "tantivy")]
|
||||||
|
tantivy.reindex_thread(pool, &query).await?;
|
||||||
|
nm::set_read_status(nm, &query, unread).await?;
|
||||||
|
|
||||||
|
sqlx::query!("DELETE FROM snooze WHERE id = $1", row.id)
|
||||||
|
.execute(pool)
|
||||||
|
.await?;
|
||||||
|
}
|
||||||
|
Ok(())
|
||||||
|
}
|
||||||
|
|
||||||
#[instrument(skip_all, fields(query=query))]
|
#[instrument(skip_all, fields(query=query))]
|
||||||
pub async fn compute_catchup_ids(
|
pub async fn compute_catchup_ids(
|
||||||
nm: &Notmuch,
|
nm: &Notmuch,
|
||||||
|
|||||||
@@ -12,7 +12,7 @@ version.workspace = true
|
|||||||
|
|
||||||
[dependencies]
|
[dependencies]
|
||||||
build-info = "0.0.42"
|
build-info = "0.0.42"
|
||||||
letterbox-notmuch = { path = "../notmuch", version = "0.17.47", registry = "xinu" }
|
letterbox-notmuch = { path = "../notmuch", version = "0.17.49", registry = "xinu" }
|
||||||
regex = "1.11.1"
|
regex = "1.11.1"
|
||||||
serde = { version = "1.0.219", features = ["derive"] }
|
serde = { version = "1.0.219", features = ["derive"] }
|
||||||
sqlx = "0.8.5"
|
sqlx = "0.8.5"
|
||||||
|
|||||||
@@ -33,7 +33,7 @@ wasm-bindgen = "=0.2.100"
|
|||||||
uuid = { version = "1.16.0", features = [
|
uuid = { version = "1.16.0", features = [
|
||||||
"js",
|
"js",
|
||||||
] } # direct dep to set js feature, prevents Rng issues
|
] } # direct dep to set js feature, prevents Rng issues
|
||||||
letterbox-shared = { path = "../shared/", version = "0.17.47", registry = "xinu" }
|
letterbox-shared = { path = "../shared/", version = "0.17.49", registry = "xinu" }
|
||||||
seed_hooks = { version = "0.4.1", registry = "xinu" }
|
seed_hooks = { version = "0.4.1", registry = "xinu" }
|
||||||
strum_macros = "0.27.1"
|
strum_macros = "0.27.1"
|
||||||
gloo-console = "0.3.0"
|
gloo-console = "0.3.0"
|
||||||
|
|||||||
@@ -739,7 +739,7 @@ fn render_open_header(msg: &ShowThreadQueryThreadOnEmailThreadMessages) -> Node<
|
|||||||
" ",
|
" ",
|
||||||
from_detail.as_ref().map(|text| copy_text_widget(&text))
|
from_detail.as_ref().map(|text| copy_text_widget(&text))
|
||||||
],
|
],
|
||||||
snooze_buttons(&id),
|
snooze_buttons(msg.timestamp, &id),
|
||||||
],
|
],
|
||||||
IF!(!msg.to.is_empty() =>div![
|
IF!(!msg.to.is_empty() =>div![
|
||||||
C!["text-xs"],
|
C!["text-xs"],
|
||||||
@@ -1375,7 +1375,7 @@ pub fn view_tags(tags: &Option<Vec<Tag>>) -> Node<Msg> {
|
|||||||
},
|
},
|
||||||
],
|
],
|
||||||
a![
|
a![
|
||||||
C!["grow", "truncate"],
|
C![indent_cls, "grow", "truncate"],
|
||||||
attrs! {
|
attrs! {
|
||||||
At::Href => href
|
At::Href => href
|
||||||
},
|
},
|
||||||
@@ -1603,7 +1603,7 @@ fn render_news_post_header(post: &ShowThreadQueryThreadOnNewsPost) -> Node<Msg>
|
|||||||
div![
|
div![
|
||||||
C!["flex"],
|
C!["flex"],
|
||||||
div![C!["font-semibold", "text-sm", "flex-1"], from],
|
div![C!["font-semibold", "text-sm", "flex-1"], from],
|
||||||
snooze_buttons(&id),
|
snooze_buttons(Some(post.timestamp), &id),
|
||||||
],
|
],
|
||||||
div![
|
div![
|
||||||
C!["flex", "gap-2", "pt-2", "text-sm"],
|
C!["flex", "gap-2", "pt-2", "text-sm"],
|
||||||
@@ -1700,7 +1700,7 @@ fn click_to_top() -> Node<Msg> {
|
|||||||
]
|
]
|
||||||
}
|
}
|
||||||
|
|
||||||
fn snooze_buttons(id: &str) -> Node<Msg> {
|
fn snooze_buttons(timestamp: Option<i64>, id: &str) -> Node<Msg> {
|
||||||
div![
|
div![
|
||||||
span![C!["px-2"], "⏰"],
|
span![C!["px-2"], "⏰"],
|
||||||
button![
|
button![
|
||||||
@@ -1727,17 +1727,19 @@ fn snooze_buttons(id: &str) -> Node<Msg> {
|
|||||||
}
|
}
|
||||||
})
|
})
|
||||||
],
|
],
|
||||||
button![
|
timestamp.map(
|
||||||
tw_classes::button(),
|
|ts| chrono::DateTime::from_timestamp(ts, 0).map(|ts| button![
|
||||||
C!["rounded-l-none"],
|
tw_classes::button(),
|
||||||
"6m",
|
C!["rounded-l-none"],
|
||||||
ev(Ev::Click, {
|
"+6m",
|
||||||
let id = id.to_string();
|
ev(Ev::Click, {
|
||||||
move |e| {
|
let id = id.to_string();
|
||||||
e.stop_propagation();
|
move |e| {
|
||||||
Msg::Snooze(id, Utc::now() + chrono::Days::new(180))
|
e.stop_propagation();
|
||||||
}
|
Msg::Snooze(id, ts + chrono::Days::new(180))
|
||||||
})
|
}
|
||||||
],
|
})
|
||||||
|
])
|
||||||
|
),
|
||||||
]
|
]
|
||||||
}
|
}
|
||||||
|
|||||||
Reference in New Issue
Block a user