Add import maildir command

pull/1/head
Manos Pitsidianakis 2022-08-26 22:37:39 +03:00
parent 615b49b448
commit b97ab650ce
10 changed files with 417 additions and 39 deletions

274
Cargo.lock generated
View File

@ -19,7 +19,7 @@ version = "0.12.1"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "d52a9bb7ec0cf484c551830a7ce27bd20d67eac647e1befb56b0be4ee39a55d2"
dependencies = [
"winapi",
"winapi 0.3.9",
]
[[package]]
@ -124,7 +124,7 @@ dependencies = [
"slab",
"socket2",
"waker-fn",
"winapi",
"winapi 0.3.9",
]
[[package]]
@ -155,13 +155,13 @@ checksum = "cf2c06e30a24e8c78a3987d07f0930edf76ef35e027e7bdb063fccafdad1f60c"
dependencies = [
"async-io",
"blocking",
"cfg-if",
"cfg-if 1.0.0",
"event-listener",
"futures-lite",
"libc",
"once_cell",
"signal-hook",
"winapi",
"winapi 0.3.9",
]
[[package]]
@ -205,7 +205,7 @@ checksum = "d9b39be18770d11421cdb1b9947a45dd3f37e93092cbf377614828a319d5fee8"
dependencies = [
"hermit-abi",
"libc",
"winapi",
"winapi 0.3.9",
]
[[package]]
@ -313,6 +313,12 @@ version = "1.0.73"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "2fff2a6927b3bb87f9595d67196a70493f627687a71d87a0d692242c33f58c11"
[[package]]
name = "cfg-if"
version = "0.1.10"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "4785bdd1c96b2a846b2bd7cc02e86b6b3dbf14e7e53446c4f54c92a361040822"
[[package]]
name = "cfg-if"
version = "1.0.0"
@ -330,7 +336,7 @@ dependencies = [
"num-traits",
"serde",
"time",
"winapi",
"winapi 0.3.9",
]
[[package]]
@ -434,7 +440,7 @@ checksum = "1b1d1d91c932ef41c0f2663aa8b0ca0342d444d842c06914aa0a7e352d0bada6"
dependencies = [
"libc",
"redox_users",
"winapi",
"winapi 0.3.9",
]
[[package]]
@ -543,6 +549,18 @@ dependencies = [
"instant",
]
[[package]]
name = "filetime"
version = "0.2.17"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "e94a7bbaa59354bc20dd75b67f23e2797b4490e9d6928203fb105c79e448c86c"
dependencies = [
"cfg-if 1.0.0",
"libc",
"redox_syscall",
"windows-sys",
]
[[package]]
name = "fnv"
version = "1.0.7"
@ -574,6 +592,41 @@ dependencies = [
"percent-encoding",
]
[[package]]
name = "fsevent"
version = "0.4.0"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "5ab7d1bd1bd33cc98b0889831b72da23c0aa4df9cec7e0702f46ecea04b35db6"
dependencies = [
"bitflags",
"fsevent-sys",
]
[[package]]
name = "fsevent-sys"
version = "2.0.1"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "f41b048a94555da0f42f1d632e2e19510084fb8e303b0daa2816e733fb3644a0"
dependencies = [
"libc",
]
[[package]]
name = "fuchsia-zircon"
version = "0.3.3"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "2e9763c69ebaae630ba35f74888db465e49e259ba1bc0eda7d06f4a067615d82"
dependencies = [
"bitflags",
"fuchsia-zircon-sys",
]
[[package]]
name = "fuchsia-zircon-sys"
version = "0.3.3"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "3dcaa9ae7725d12cdb85b3ad99a434db70b468c09ded17e012d86b5c1010f7a7"
[[package]]
name = "futures"
version = "0.3.21"
@ -694,7 +747,7 @@ version = "0.2.7"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "4eb1a864a501629691edf6c15a593b7a51eebaa1e8468e9ddc623de7c9b58ec6"
dependencies = [
"cfg-if",
"cfg-if 1.0.0",
"libc",
"wasi 0.11.0+wasi-snapshot-preview1",
]
@ -868,13 +921,42 @@ dependencies = [
"serde",
]
[[package]]
name = "inotify"
version = "0.7.1"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "4816c66d2c8ae673df83366c18341538f234a26d65a9ecea5c348b453ac1d02f"
dependencies = [
"bitflags",
"inotify-sys",
"libc",
]
[[package]]
name = "inotify-sys"
version = "0.1.5"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "e05c02b5e89bff3b946cedeca278abc628fe811e604f027c45a8aa3cf793d0eb"
dependencies = [
"libc",
]
[[package]]
name = "instant"
version = "0.1.12"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "7a5bbe824c507c5da5956355e86a746d82e0e1464f65d862cc5e71da70e94b2c"
dependencies = [
"cfg-if",
"cfg-if 1.0.0",
]
[[package]]
name = "iovec"
version = "0.1.4"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "b2b3ea6ff95e175473f8ffe6a7eb7c00d054240321b84c57051175fe3c1e075e"
dependencies = [
"libc",
]
[[package]]
@ -892,12 +974,28 @@ dependencies = [
"wasm-bindgen",
]
[[package]]
name = "kernel32-sys"
version = "0.2.2"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "7507624b29483431c0ba2d82aece8ca6cdba9382bff4ddd0f7490560c056098d"
dependencies = [
"winapi 0.2.8",
"winapi-build",
]
[[package]]
name = "lazy_static"
version = "1.4.0"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "e2abad23fbc42b3700f2f279844dc832adb2b2eb069b2df918f455c4e18cc646"
[[package]]
name = "lazycell"
version = "1.3.0"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "830d08ce1d1d941e6b30645f1a0eb5643013d835ce3779a5fc208261dbe10f55"
[[package]]
name = "libc"
version = "0.2.126"
@ -910,8 +1008,8 @@ version = "0.7.3"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "efbc0f03f9a775e9f6aed295c6a1ba2253c5757a9e03d55c6caa46a681abcddd"
dependencies = [
"cfg-if",
"winapi",
"cfg-if 1.0.0",
"winapi 0.3.9",
]
[[package]]
@ -941,7 +1039,7 @@ version = "0.4.17"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "abb12e687cfb44aa40f41fc3978ef76448f9b6038cad6aef4259d3c095a2382e"
dependencies = [
"cfg-if",
"cfg-if 1.0.0",
]
[[package]]
@ -1019,7 +1117,6 @@ checksum = "a3e378b66a060d48947b590737b30a1be76706c8dd7b8ba0f2fe3989c68a853f"
[[package]]
name = "melib"
version = "0.7.2"
source = "git+https://github.com/meli/meli?branch=master#ce269c64e16db344f0e65461e56dbced2f1a4d64"
dependencies = [
"async-stream",
"base64",
@ -1034,6 +1131,7 @@ dependencies = [
"native-tls",
"nix",
"nom 7.1.1",
"notify",
"serde",
"serde_derive",
"smallvec",
@ -1081,6 +1179,25 @@ version = "0.2.1"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "68354c5c6bd36d73ff3feceb05efa59b6acb7626617f4962be322a825e61f79a"
[[package]]
name = "mio"
version = "0.6.23"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "4afd66f5b91bf2a3bc13fad0e21caedac168ca4c707504e75585648ae80e4cc4"
dependencies = [
"cfg-if 0.1.10",
"fuchsia-zircon",
"fuchsia-zircon-sys",
"iovec",
"kernel32-sys",
"libc",
"log",
"miow",
"net2",
"slab",
"winapi 0.2.8",
]
[[package]]
name = "mio"
version = "0.8.4"
@ -1093,6 +1210,30 @@ dependencies = [
"windows-sys",
]
[[package]]
name = "mio-extras"
version = "2.0.6"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "52403fe290012ce777c4626790c8951324a2b9e3316b3143779c72b029742f19"
dependencies = [
"lazycell",
"log",
"mio 0.6.23",
"slab",
]
[[package]]
name = "miow"
version = "0.2.2"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "ebd808424166322d4a38da87083bfddd3ac4c131334ed55856112eb06d46944d"
dependencies = [
"kernel32-sys",
"net2",
"winapi 0.2.8",
"ws2_32-sys",
]
[[package]]
name = "mpot-archives"
version = "0.1.0"
@ -1140,6 +1281,17 @@ dependencies = [
"tempfile",
]
[[package]]
name = "net2"
version = "0.2.37"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "391630d12b68002ae1e25e8f974306474966550ad82dac6886fb8910c19568ae"
dependencies = [
"cfg-if 0.1.10",
"libc",
"winapi 0.3.9",
]
[[package]]
name = "nix"
version = "0.24.1"
@ -1147,7 +1299,7 @@ source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "8f17df307904acd05aa8e32e97bb20f2a0df1728bbc2d771ae8f9a90463441e9"
dependencies = [
"bitflags",
"cfg-if",
"cfg-if 1.0.0",
"libc",
"memoffset",
]
@ -1172,6 +1324,24 @@ dependencies = [
"minimal-lexical",
]
[[package]]
name = "notify"
version = "4.0.17"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "ae03c8c853dba7bfd23e571ff0cff7bc9dceb40a4cd684cd1681824183f45257"
dependencies = [
"bitflags",
"filetime",
"fsevent",
"fsevent-sys",
"inotify",
"libc",
"mio 0.6.23",
"mio-extras",
"walkdir",
"winapi 0.3.9",
]
[[package]]
name = "num-integer"
version = "0.1.45"
@ -1220,7 +1390,7 @@ source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "618febf65336490dfcf20b73f885f5651a0c89c64c2d4a8c3662585a70bf5bd0"
dependencies = [
"bitflags",
"cfg-if",
"cfg-if 1.0.0",
"foreign-types",
"libc",
"once_cell",
@ -1280,7 +1450,7 @@ version = "0.9.3"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "09a279cbf25cb0757810394fbc1e359949b59e348145c643a939a525692e6929"
dependencies = [
"cfg-if",
"cfg-if 1.0.0",
"libc",
"redox_syscall",
"smallvec",
@ -1337,11 +1507,11 @@ version = "2.2.0"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "685404d509889fade3e86fe3a5803bca2ec09b0c0778d5ada6ec8bf7a8de5259"
dependencies = [
"cfg-if",
"cfg-if 1.0.0",
"libc",
"log",
"wepoll-ffi",
"winapi",
"winapi 0.3.9",
]
[[package]]
@ -1472,7 +1642,7 @@ version = "0.5.3"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "3acd125665422973a33ac9d3dd2df85edad0f4ae9b00dafb1a05e43a9f5ef8e7"
dependencies = [
"winapi",
"winapi 0.3.9",
]
[[package]]
@ -1487,7 +1657,7 @@ dependencies = [
"spin",
"untrusted",
"web-sys",
"winapi",
"winapi 0.3.9",
]
[[package]]
@ -1538,6 +1708,15 @@ version = "0.3.3"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "ef703b7cb59335eae2eb93ceb664c0eb7ea6bf567079d843e09420219668e072"
[[package]]
name = "same-file"
version = "1.0.6"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "93fc1dc3aaa9bfed95e02e6eadabb4baf7e3078b0bd1b4d7b6b0b68378900502"
dependencies = [
"winapi-util",
]
[[package]]
name = "schannel"
version = "0.1.20"
@ -1649,7 +1828,7 @@ source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "99cd6713db3cf16b6c84e06321e049a9b9f699826e16096d23bbcc44d15d51a6"
dependencies = [
"block-buffer 0.9.0",
"cfg-if",
"cfg-if 1.0.0",
"cpufeatures",
"digest 0.9.0",
"opaque-debug",
@ -1661,7 +1840,7 @@ version = "0.10.0"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "028f48d513f9678cda28f6e4064755b3fbb2af6acd672f2c209b62323f7aea0f"
dependencies = [
"cfg-if",
"cfg-if 1.0.0",
"cpufeatures",
"digest 0.10.3",
]
@ -1731,7 +1910,7 @@ source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "66d72b759436ae32898a2af0a14218dbf55efde3feeb170eb623637db85ee1e0"
dependencies = [
"libc",
"winapi",
"winapi 0.3.9",
]
[[package]]
@ -1810,12 +1989,12 @@ version = "3.3.0"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "5cdb1ef4eaeeaddc8fbd371e5017057064af0911902ef36b39801f67cc6d79e4"
dependencies = [
"cfg-if",
"cfg-if 1.0.0",
"fastrand",
"libc",
"redox_syscall",
"remove_dir_all",
"winapi",
"winapi 0.3.9",
]
[[package]]
@ -1879,7 +2058,7 @@ checksum = "6db9e6914ab8b1ae1c260a4ae7a49b6c5611b40328a735b21862567685e73255"
dependencies = [
"libc",
"wasi 0.10.0+wasi-snapshot-preview1",
"winapi",
"winapi 0.3.9",
]
[[package]]
@ -1907,7 +2086,7 @@ dependencies = [
"bytes",
"libc",
"memchr",
"mio",
"mio 0.8.4",
"num_cpus",
"once_cell",
"parking_lot",
@ -1915,7 +2094,7 @@ dependencies = [
"signal-hook-registry",
"socket2",
"tokio-macros",
"winapi",
"winapi 0.3.9",
]
[[package]]
@ -2011,7 +2190,7 @@ version = "0.1.35"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "a400e31aa60b9d44a52a8ee0343b5b18566b03a8321e0d321f695cf56e940160"
dependencies = [
"cfg-if",
"cfg-if 1.0.0",
"log",
"pin-project-lite",
"tracing-core",
@ -2179,6 +2358,17 @@ version = "1.1.0"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "9d5b2c62b4012a3e1eca5a7e077d13b3bf498c4073e33ccd58626607748ceeca"
[[package]]
name = "walkdir"
version = "2.3.2"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "808cf2735cd4b6866113f648b791c6adc5714537bc222d9347bb203386ffda56"
dependencies = [
"same-file",
"winapi 0.3.9",
"winapi-util",
]
[[package]]
name = "want"
version = "0.3.0"
@ -2237,7 +2427,7 @@ version = "0.2.81"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "7c53b543413a17a202f4be280a7e5c62a1c69345f5de525ee64f8cfdbc954994"
dependencies = [
"cfg-if",
"cfg-if 1.0.0",
"wasm-bindgen-macro",
]
@ -2314,6 +2504,12 @@ dependencies = [
"cc",
]
[[package]]
name = "winapi"
version = "0.2.8"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "167dc9d6949a9b857f3451275e911c3f44255842c1f7a76f33c55103a909087a"
[[package]]
name = "winapi"
version = "0.3.9"
@ -2324,6 +2520,12 @@ dependencies = [
"winapi-x86_64-pc-windows-gnu",
]
[[package]]
name = "winapi-build"
version = "0.1.1"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "2d315eee3b34aca4797b2da6b13ed88266e6d612562a0c46390af8299fc699bc"
[[package]]
name = "winapi-i686-pc-windows-gnu"
version = "0.4.0"
@ -2336,7 +2538,7 @@ version = "0.1.5"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "70ec6ce85bb158151cae5e5c87f95a8e97d2c0c4b001223f33a334e3ce5de178"
dependencies = [
"winapi",
"winapi 0.3.9",
]
[[package]]
@ -2388,6 +2590,16 @@ version = "0.36.1"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "c811ca4a8c853ef420abd8592ba53ddbbac90410fab6903b3e79972a631f7680"
[[package]]
name = "ws2_32-sys"
version = "0.2.1"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "d59cefebd0c892fa2dd6de581e937301d8552cb44489cdff035c6187cb63fa5e"
dependencies = [
"winapi 0.2.8",
"winapi-build",
]
[[package]]
name = "xdg"
version = "2.4.1"

View File

@ -1,5 +1,5 @@
# mailpot REST http server
```shell
cargo run --bin mpot-http
cargo run --bin mpot-archives
```

View File

@ -28,15 +28,44 @@ pub use mailpot::*;
use askama::Template;
use percent_encoding::percent_decode_str;
#[derive(Template)]
#[template(path = "lists.html")]
struct ListsTemplate<'a> {
title: &'a str,
description: &'a str,
lists_len: usize,
lists: Vec<ListTemplate<'a>>,
}
#[derive(Template)]
#[template(path = "list.html")]
struct ListTemplate<'a> {
title: &'a str,
_list: &'a DbVal<MailingList>,
list: &'a DbVal<MailingList>,
posts: Vec<DbVal<Post>>,
months: Vec<String>,
body: &'a str,
}
impl<'a> Into<ListTemplate<'a>> for (&'a DbVal<MailingList>, &'a Database) {
fn into(self: (&'a DbVal<MailingList>, &'a Database)) -> ListTemplate<'a> {
let (list, db) = self;
let months = db.months(list.pk).unwrap();
let posts = db.list_posts(list.pk, None).unwrap();
ListTemplate {
title: &list.name,
list: &list,
posts,
months,
body: &list
.description
.as_ref()
.map(|s| s.as_str())
.unwrap_or_default(),
}
}
}
#[derive(Template)]
#[template(path = "post.html")]
struct PostTemplate<'a> {
@ -57,10 +86,12 @@ async fn main() {
let list_handler = warp::path!("lists" / i64).map(|list_pk: i64| {
let db = Database::open_or_create_db().unwrap();
let list = db.get_list(list_pk).unwrap().unwrap();
let months = db.months(list_pk).unwrap();
let posts = db.list_posts(list_pk, None).unwrap();
let template = ListTemplate {
title: &list.name,
_list: &list,
list: &list,
months,
posts,
body: &list.description.clone().unwrap_or_default(),
};
@ -99,12 +130,31 @@ async fn main() {
let res = template.render().unwrap();
Ok(warp::reply::html(res))
});
let routes = warp::get().and(list_handler).or(post_handler);
let index_handler = warp::path::end().map(|| {
let db = Database::open_or_create_db().unwrap();
let lists_values = db.list_lists().unwrap();
let lists = lists_values
.iter()
.map(|list| (list, &db).into())
.collect::<Vec<ListTemplate<'_>>>();
let template = ListsTemplate {
title: "mailing list archive",
description: "",
lists_len: lists.len(),
lists: lists,
};
let res = template.render().unwrap();
Ok(warp::reply::html(res))
});
let routes = warp::get()
.and(index_handler)
.or(list_handler)
.or(post_handler);
// Note that composing filters for many routes may increase compile times (because it uses a lot of generics).
// If you wish to use dynamic dispatch instead and speed up compile times while
// making it slightly slower at runtime, you can use Filter::boxed().
eprintln!("Running at 127.0.0.1:3030");
eprintln!("Running at http://127.0.0.1:3030");
warp::serve(routes).run(([127, 0, 0, 1], 3030)).await;
}

View File

@ -3,6 +3,12 @@
<h1>{{title}}</h1>
<div class="body">
{{body}}
<h2>Months</h2>
<ul>
{% for month in months %}
<li><a href="/list/{{list.pk}}/{{ month }}">{{ month }}</a></li>
{% endfor %}
</ul>
<h2>Posts</h2>
<ul>
{% for post in posts %}

View File

@ -0,0 +1,10 @@
{% include "header.html" %}
<div class="entry">
<p>{{lists_len}} lists</p>
<div class="body">
{% for list in lists %}
{{ list }}
{% endfor %}
</div>
</div>
{% include "footer.html" %}

View File

@ -108,6 +108,13 @@ enum Command {
#[structopt(subcommand)]
cmd: ErrorQueueCommand,
},
/// Import a maildir folder into an existing list.
ImportMaildir {
///Selects mailing list to operate on
list_id: String,
#[structopt(long, parse(from_os_str))]
maildir_path: PathBuf,
},
}
#[derive(Debug, StructOpt)]
@ -628,6 +635,53 @@ fn run_app(opt: Opt) -> Result<()> {
}
}
},
ImportMaildir {
list_id,
mut maildir_path,
} => {
let db = Database::open_or_create_db()?;
let list = match db.get_list_by_id(&list_id)? {
Some(v) => v,
None => {
return Err(format!("No list with id {} was found", list_id).into());
}
};
use melib::backends::maildir::MaildirPathTrait;
use melib::{Envelope, EnvelopeHash};
use std::collections::hash_map::DefaultHasher;
use std::hash::{Hash, Hasher};
use std::io::Read;
if !maildir_path.is_absolute() {
maildir_path = std::env::current_dir()
.expect("could not detect current directory")
.join(&maildir_path);
}
fn get_file_hash(file: &std::path::Path) -> EnvelopeHash {
let mut hasher = DefaultHasher::default();
file.hash(&mut hasher);
hasher.finish()
}
let mut buf = Vec::with_capacity(4096);
let files = melib::backends::maildir::MaildirType::list_mail_in_maildir_fs(
maildir_path.clone(),
true,
)?;
let mut ctr = 0;
for file in files {
let hash = get_file_hash(&file);
let mut reader = std::io::BufReader::new(std::fs::File::open(&file)?);
buf.clear();
reader.read_to_end(&mut buf)?;
if let Ok(mut env) = Envelope::from_bytes(buf.as_slice(), Some(file.flags())) {
env.set_hash(hash);
db.insert_post(list.pk, &buf, &env)?;
ctr += 1;
}
}
println!("Inserted {} posts to {}.", ctr, list_id);
}
}
Ok(())

View File

@ -56,6 +56,7 @@ impl Database {
}
pub fn open_or_create_db() -> Result<Self> {
crate::config::Configuration::init()?;
let mut db_path = Self::db_path()?;
db_path = db_path
.canonicalize()

View File

@ -21,10 +21,24 @@ use super::*;
impl Database {
pub fn insert_post(&self, list_pk: i64, message: &[u8], env: &Envelope) -> Result<i64> {
let address = env.from()[0].get_email();
let from_ = env.from();
let address = if from_.is_empty() {
String::new()
} else {
from_[0].get_email()
};
let mut datetime: std::borrow::Cow<'_, str> = env.date.as_str().into();
if env.timestamp != 0 {
datetime = melib::datetime::timestamp_to_string(
env.timestamp,
Some(melib::datetime::RFC3339_FMT_WITH_TIME),
true,
)
.into();
}
let message_id = env.message_id_display();
let mut stmt = self.connection.prepare(
"INSERT INTO post(list, address, message_id, message, datetime, timestamp) VALUES(?, ?, ?, ?, ?, ?) RETURNING pk;",
"INSERT OR REPLACE INTO post(list, address, message_id, message, datetime, timestamp) VALUES(?, ?, ?, ?, ?, ?) RETURNING pk;",
)?;
let pk = stmt.query_row(
rusqlite::params![
@ -32,7 +46,7 @@ impl Database {
&address,
&message_id,
&message,
&env.date,
&datetime,
&env.timestamp
],
|row| {
@ -296,4 +310,21 @@ impl Database {
}
Ok(())
}
pub fn months(&self, list_pk: i64) -> Result<Vec<String>> {
let mut stmt = self.connection.prepare(
"SELECT DISTINCT strftime('%Y-%m', CAST(timestamp AS INTEGER), 'unixepoch') FROM post WHERE list = ?;",
)?;
let months_iter = stmt.query_map([list_pk], |row| {
let val: String = row.get(0)?;
Ok(val)
})?;
let mut ret = vec![];
for month in months_iter {
let month = month?;
ret.push(month);
}
Ok(ret)
}
}

View File

@ -34,6 +34,11 @@ Create new list.
Post message from STDIN to list.
.It Ic error-queue
Mail that has not been handled properly end up in the error queue.
.It Ic import-maildir
.Fl -maildir-path Ar maildir-path
.
Import a maildir folder into an existing list.
.It Ic db-location
Prints database filesystem location.
.It Ic config-location
@ -50,5 +55,7 @@ Create new list.
Post message from STDIN to list.
.It Ic error-queue
Mail that has not been handled properly end up in the error queue.
.It Ic import-maildir
Import a maildir folder into an existing list.
.El
.Pp

View File

@ -65,6 +65,11 @@ Create new list.
Post message from STDIN to list.
.It Ic error-queue
Mail that has not been handled properly end up in the error queue.
.It Ic import-maildir
.Fl -maildir-path Ar maildir-path
.
Import a maildir folder into an existing list.
.It Ic db-location
Prints database filesystem location.
.It Ic config-location
@ -81,6 +86,8 @@ Create new list.
Post message from STDIN to list.
.It Ic error-queue
Mail that has not been handled properly end up in the error queue.
.It Ic import-maildir
Import a maildir folder into an existing list.
.El
.Pp