Release v0.6.1

### Added

* Added `-s|--sanitize` flag for the `read` command.
  
### Changed

* Changed the behaviour of the `-t|--mime-type` argument of the `read`
  command. It is less strict now: if no part is found for the given
  MIME type, it will fallback to the other one. For example, giving
  `-t html` will show in priority HTML parts, but if none of them are
  found it will show plain parts instead (and vice versa).

* Sanitization is not done by default when using the `read` command,
  the flag `-s|--sanitize` needs to be explicitly provided.

### Fixed

* Fixed empty text bodies when reading html part on plain text email
  [#352].

## himalaya-lib [[v0.4.0](2425269e6d)]

### Added

* Added pipe support for `(imap|smtp)-passwd-cmd` [#373].
* Added `imap-ssl` and `smtp-ssl` options to be able to disable
  encryption [#347].
* Implemented sendmail sender [#351].
* Fixed `process` module for `MINGW*` [#254].

### Changed

* Moved `Email::fold_text_plain_parts` to `Parts::to_readable`. It
  take now a `PartsReaderOptions` as parameter:
  * `plain_first`: shows plain texts first, switch to html if empty.
  * `sanitize`: sanitizes or not text bodies (both plain and html).

### Fixed

* Fixed long subject decoding issue [#380].
* Fixed bad mailbox name encoding from UTF7-IMAP [#370].
This commit is contained in:
Clément DOUIN 2022-10-12 17:00:03 +02:00 committed by GitHub
commit bda37ca0ed
No known key found for this signature in database
GPG key ID: 4AEE18F83AFDEB23
11 changed files with 483 additions and 191 deletions

3
.gitignore vendored
View file

@ -1,3 +1,6 @@
# Cargo config directory
.cargo/
# Cargo build directory
target/
debug/

View file

@ -7,6 +7,28 @@ and this project adheres to [Semantic Versioning](https://semver.org/spec/v2.0.0
## [Unreleased]
## [0.6.1] - 2022-10-12
### Added
* Added `-s|--sanitize` flag for the `read` command.
### Changed
* Changed the behaviour of the `-t|--mime-type` argument of the `read`
command. It is less strict now: if no part is found for the given
MIME type, it will fallback to the other one. For example, giving
`-t html` will show in priority HTML parts, but if none of them are
found it will show plain parts instead (and vice versa).
* Sanitization is not done by default when using the `read` command,
the flag `-s|--sanitize` needs to be explicitly provided.
### Fixed
* Fixed empty text bodies when reading html part on plain text email
[#352].
## [0.6.0] - 2022-10-10
### Changed
@ -22,6 +44,8 @@ and this project adheres to [Semantic Versioning](https://semver.org/spec/v2.0.0
* This repository only contains the CLI source code (it was not
possible to move it to sourcehut because of cross platform builds)
* [**BREAKING**] Renamed `-m|--mailbox` to `-f|--folder`
* [**BREAKING**] Refactored config system [#344].
The configuration has been rethought in order to be more intuitive
@ -412,7 +436,8 @@ and this project adheres to [Semantic Versioning](https://semver.org/spec/v2.0.0
* Password from command [#22]
* Set up README [#20]
[unreleased]: https://github.com/soywod/himalaya/compare/v0.6.0...HEAD
[unreleased]: https://github.com/soywod/himalaya/compare/v0.6.1...HEAD
[0.6.1]: https://github.com/soywod/himalaya/compare/v0.6.0...v0.6.1
[0.6.0]: https://github.com/soywod/himalaya/compare/v0.5.10...v0.6.0
[0.5.10]: https://github.com/soywod/himalaya/compare/v0.5.9...v0.5.10
[0.5.9]: https://github.com/soywod/himalaya/compare/v0.5.8...v0.5.9
@ -569,3 +594,4 @@ and this project adheres to [Semantic Versioning](https://semver.org/spec/v2.0.0
[#340]: https://github.com/soywod/himalaya/issues/340
[#344]: https://github.com/soywod/himalaya/issues/344
[#346]: https://github.com/soywod/himalaya/issues/346
[#352]: https://github.com/soywod/himalaya/issues/352

491
Cargo.lock generated
View file

@ -3,19 +3,28 @@
version = 3
[[package]]
name = "aho-corasick"
version = "0.7.18"
name = "ahash"
version = "0.3.8"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "1e37cfd5e7657ada45f742d6e99ca5788580b5c529dc78faf11ece6dc702656f"
checksum = "e8fd72866655d1904d6b0997d0b07ba561047d070fbe29de039031c641b61217"
dependencies = [
"const-random",
]
[[package]]
name = "aho-corasick"
version = "0.7.19"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "b4f55bd91a0978cbfd91c457a164bab8b4001c833b7f323132c0a4e1922dd44e"
dependencies = [
"memchr 2.5.0",
]
[[package]]
name = "ammonia"
version = "3.2.0"
version = "3.2.1"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "d5ed2509ee88cc023cccee37a6fab35826830fe8b748b3869790e7720c2c4a74"
checksum = "4b477377562f3086b7778d241786e9406b883ccfaa03557c0fe0924b9349f13a"
dependencies = [
"html5ever",
"maplit",
@ -24,6 +33,15 @@ dependencies = [
"url",
]
[[package]]
name = "android_system_properties"
version = "0.1.5"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "819e7219dbd41043ac279b19830f2efc897156490d7fd6ea916720117ee66311"
dependencies = [
"libc",
]
[[package]]
name = "ansi_term"
version = "0.12.1"
@ -35,9 +53,9 @@ dependencies = [
[[package]]
name = "anyhow"
version = "1.0.58"
version = "1.0.65"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "bb07d2053ccdbe10e2af2995a2f116c1330396493dc1269f6a91d0ae82e19704"
checksum = "98161a4e3e2184da77bb14f02184cdd111e83bbbcc9979dfee3c44b9a85f5602"
[[package]]
name = "atty"
@ -86,6 +104,12 @@ version = "0.1.4"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "40e38929add23cdf8a366df9b0e088953150724bcbe5fc330b0d8eb3b328eec8"
[[package]]
name = "bumpalo"
version = "3.11.0"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "c1ad822118d20d2c234f427000d5acc36eabe1e29a348c89b63dd60b13f28e5d"
[[package]]
name = "cc"
version = "1.0.73"
@ -116,17 +140,28 @@ dependencies = [
[[package]]
name = "chrono"
version = "0.4.19"
version = "0.4.22"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "670ad68c9088c2a963aaa298cb369688cf3f9465ce5e2d4ca10e6e0098a1ce73"
checksum = "bfd4d1b31faaa3a89d7934dbded3111da0d2ef28e3ebccdb4f0179f5929d1ef1"
dependencies = [
"libc",
"iana-time-zone",
"js-sys",
"num-integer",
"num-traits",
"time",
"wasm-bindgen",
"winapi",
]
[[package]]
name = "chumsky"
version = "0.8.0"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "8d02796e4586c6c41aeb68eae9bfb4558a522c35f1430c14b40136c3706e09e4"
dependencies = [
"ahash",
]
[[package]]
name = "clap"
version = "2.34.0"
@ -150,6 +185,38 @@ dependencies = [
"bitflags",
]
[[package]]
name = "codespan-reporting"
version = "0.11.1"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "3538270d33cc669650c4b093848450d380def10c331d38c768e34cac80576e6e"
dependencies = [
"termcolor",
"unicode-width",
]
[[package]]
name = "const-random"
version = "0.1.13"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "f590d95d011aa80b063ffe3253422ed5aa462af4e9867d43ce8337562bac77c4"
dependencies = [
"const-random-macro",
"proc-macro-hack",
]
[[package]]
name = "const-random-macro"
version = "0.1.13"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "615f6e27d000a2bffbc7f2f6a8669179378fa27ee4d0a509e985dfc0a7defb40"
dependencies = [
"getrandom",
"lazy_static",
"proc-macro-hack",
"tiny-keccak",
]
[[package]]
name = "convert_case"
version = "0.5.0"
@ -172,6 +239,56 @@ version = "0.8.3"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "5827cebf4670468b8772dd191856768aedcb1b0278a04f989f7766351917b9dc"
[[package]]
name = "crunchy"
version = "0.2.2"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "7a81dae078cea95a014a339291cec439d2f232ebe854a9d672b796c6afafa9b7"
[[package]]
name = "cxx"
version = "1.0.78"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "19f39818dcfc97d45b03953c1292efc4e80954e1583c4aa770bac1383e2310a4"
dependencies = [
"cc",
"cxxbridge-flags",
"cxxbridge-macro",
"link-cplusplus",
]
[[package]]
name = "cxx-build"
version = "1.0.78"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "3e580d70777c116df50c390d1211993f62d40302881e54d4b79727acb83d0199"
dependencies = [
"cc",
"codespan-reporting",
"once_cell",
"proc-macro2",
"quote",
"scratch",
"syn",
]
[[package]]
name = "cxxbridge-flags"
version = "1.0.78"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "56a46460b88d1cec95112c8c363f0e2c39afdb237f60583b0b36343bf627ea9c"
[[package]]
name = "cxxbridge-macro"
version = "1.0.78"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "747b608fecf06b0d72d440f27acc99288207324b793be2c17991839f3d4995ea"
dependencies = [
"proc-macro2",
"quote",
"syn",
]
[[package]]
name = "darling"
version = "0.10.2"
@ -214,20 +331,19 @@ source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "3ee2393c4a91429dffb4bedf19f4d6abf27d8a732c8ce4980305d782e5426d57"
[[package]]
name = "dirs-next"
version = "2.0.0"
name = "dirs"
version = "4.0.0"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "b98cf8ebf19c3d1b223e151f99a4f9f0690dca41414773390fc824184ac833e1"
checksum = "ca3aa72a6f96ea37bbc5aa912f6788242832f75369bdfdadcb0e38423f100059"
dependencies = [
"cfg-if 1.0.0",
"dirs-sys-next",
"dirs-sys",
]
[[package]]
name = "dirs-sys-next"
version = "0.1.2"
name = "dirs-sys"
version = "0.3.7"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "4ebda144c4fe02d1f7ea1a7d9641b6fc6b580adcfa024ae48797ecdeb6825b4d"
checksum = "1b1d1d91c932ef41c0f2663aa8b0ca0342d444d842c06914aa0a7e352d0bada6"
dependencies = [
"libc",
"redox_users",
@ -246,9 +362,9 @@ dependencies = [
[[package]]
name = "email_address"
version = "0.2.1"
version = "0.2.3"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "8684b7c9cb4857dfa1e5b9629ef584ba618c9b93bae60f58cb23f4f271d0468e"
checksum = "b1b32a7a2580c4473f10f66b512c34bdd7d33c5e3473227ca833abdb5afe4809"
[[package]]
name = "encoding_rs"
@ -274,18 +390,18 @@ dependencies = [
[[package]]
name = "erased-serde"
version = "0.3.21"
version = "0.3.23"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "81d013529d5574a60caeda29e179e695125448e5de52e3874f7b4c1d7360e18e"
checksum = "54558e0ba96fbe24280072642eceb9d7d442e32c7ec0ea9e7ecd7b4ea2cf4e11"
dependencies = [
"serde",
]
[[package]]
name = "fastrand"
version = "1.7.0"
version = "1.8.0"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "c3fcf0cee53519c866c09b5de1f6c56ff9d647101f81c1964fa632e148896cdf"
checksum = "a7a407cfaa3385c4ae6b23e84623d48c2798d06e3e6a1878f7f59f17b3f86499"
dependencies = [
"instant",
]
@ -319,11 +435,10 @@ checksum = "00b0228411908ca8685dba7fc2cdd70ec9990a6e753e89b6ac91a84c40fbaf4b"
[[package]]
name = "form_urlencoded"
version = "1.0.1"
version = "1.1.0"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "5fc25a87fa4fd2094bffb06925852034d90a17f0d1e05197d4956d3555752191"
checksum = "a9c384f161156f5260c24a097c56119f9be8c798586aecc13afbcbe7b7e26bf8"
dependencies = [
"matches",
"percent-encoding",
]
@ -366,27 +481,27 @@ dependencies = [
[[package]]
name = "futures-core"
version = "0.3.21"
version = "0.3.24"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "0c09fd04b7e4073ac7156a9539b57a484a8ea920f79c7c675d05d289ab6110d3"
checksum = "4e5aa3de05362c3fb88de6531e6296e85cde7739cccad4b9dfeeb7f6ebce56bf"
[[package]]
name = "futures-io"
version = "0.3.21"
version = "0.3.24"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "fc4045962a5a5e935ee2fdedaa4e08284547402885ab326734432bed5d12966b"
checksum = "bbf4d2a7a308fd4578637c0b17c7e1c7ba127b8f6ba00b29f717e9655d85eb68"
[[package]]
name = "futures-task"
version = "0.3.21"
version = "0.3.24"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "57c66a976bf5909d801bbef33416c41372779507e7a6b3a5e25e4749c58f776a"
checksum = "a6508c467c73851293f390476d4491cf4d227dbabcd4170f3bb6044959b294f1"
[[package]]
name = "futures-util"
version = "0.3.21"
version = "0.3.24"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "d8b7abd5d659d9b90c8cba917f6ec750a74e2dc23902ef9cd4cc8c8b22e6036a"
checksum = "44fb6cb1be61cc1d2e43b262516aafcf63b241cffdb1d3fa115f91d9c7b09c90"
dependencies = [
"futures-core",
"futures-io",
@ -420,9 +535,9 @@ dependencies = [
[[package]]
name = "hashbrown"
version = "0.12.1"
version = "0.12.3"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "db0d4cf898abf0081f964436dc980e96670a0f36863e4b83aaacdb65c9d7ccc3"
checksum = "8a9ee70c43aaf417c914396645a0fa852624801b24ebb7ae78fe8272889ac888"
[[package]]
name = "hermit-abi"
@ -435,29 +550,18 @@ dependencies = [
[[package]]
name = "himalaya"
version = "0.6.0"
version = "0.6.1"
dependencies = [
"ammonia",
"anyhow",
"atty",
"chrono",
"clap",
"convert_case",
"env_logger",
"erased-serde",
"himalaya-lib",
"html-escape",
"imap",
"imap-proto",
"lettre",
"log",
"maildir",
"mailparse",
"md5",
"native-tls",
"notmuch",
"regex",
"rfc2047-decoder",
"serde",
"serde_json",
"shellexpand",
@ -465,7 +569,6 @@ dependencies = [
"termcolor",
"terminal_size",
"toml",
"tree_magic",
"unicode-width",
"url",
"uuid",
@ -473,9 +576,7 @@ dependencies = [
[[package]]
name = "himalaya-lib"
version = "0.3.1"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "33465f9a8c4dd3db2838c299bc897d4c29acd56ec1713f81a4666ef800abb1e4"
version = "0.4.0"
dependencies = [
"ammonia",
"chrono",
@ -496,6 +597,7 @@ dependencies = [
"shellexpand",
"thiserror",
"tree_magic",
"utf7-imap",
"uuid",
]
@ -545,6 +647,30 @@ version = "2.1.0"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "9a3a5bfb195931eeb336b2a7b4d761daec841b97f947d34394601737a7bba5e4"
[[package]]
name = "iana-time-zone"
version = "0.1.51"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "f5a6ef98976b22b3b7f2f3a806f858cb862044cfa66805aa3ad84cb3d3b785ed"
dependencies = [
"android_system_properties",
"core-foundation-sys",
"iana-time-zone-haiku",
"js-sys",
"wasm-bindgen",
"winapi",
]
[[package]]
name = "iana-time-zone-haiku"
version = "0.1.0"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "fde6edd6cef363e9359ed3c98ba64590ba9eecba2293eb5a723ab32aee8926aa"
dependencies = [
"cxx",
"cxx-build",
]
[[package]]
name = "ident_case"
version = "1.0.1"
@ -562,6 +688,16 @@ dependencies = [
"unicode-normalization",
]
[[package]]
name = "idna"
version = "0.3.0"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "e14ddfc70884202db2244c223200c204c2bda1bc6e0998d11b5e024d657209e6"
dependencies = [
"unicode-bidi",
"unicode-normalization",
]
[[package]]
name = "imap"
version = "3.0.0-alpha.4"
@ -608,9 +744,18 @@ dependencies = [
[[package]]
name = "itoa"
version = "1.0.2"
version = "1.0.4"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "112c678d4050afce233f4f2852bb2eb519230b3cf12f33585275537d7e41578d"
checksum = "4217ad341ebadf8d8e724e264f13e593e0648f5b3e94b3896a5df283be015ecc"
[[package]]
name = "js-sys"
version = "0.3.60"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "49409df3e3bf0856b916e2ceaca09ee28e6871cf7d9ce97a692cacfdb2a25a47"
dependencies = [
"wasm-bindgen",
]
[[package]]
name = "lazy_static"
@ -631,7 +776,7 @@ dependencies = [
"futures-util",
"hostname",
"httpdate",
"idna",
"idna 0.2.3",
"mime",
"native-tls",
"nom 7.1.1",
@ -643,9 +788,18 @@ dependencies = [
[[package]]
name = "libc"
version = "0.2.126"
version = "0.2.135"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "349d5a591cd28b49e1d1037471617a32ddcda5731b99419008085f72d5a53836"
checksum = "68783febc7782c6c5cb401fbda4de5a9898be1762314da0bb2c10ced61f18b0c"
[[package]]
name = "link-cplusplus"
version = "1.0.7"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "9272ab7b96c9046fbc5bc56c06c117cb639fe2d509df0c421cad82d2915cf369"
dependencies = [
"cc",
]
[[package]]
name = "lock_api"
@ -658,9 +812,9 @@ dependencies = [
[[package]]
name = "lock_api"
version = "0.4.7"
version = "0.4.9"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "327fa5b6a6940e4699ec49a9beae1ea4845c6bab9314e4f84ac68742139d8c53"
checksum = "435011366fe56583b16cf956f9df0095b405b82d76425bc8981c0e22e60ec4df"
dependencies = [
"autocfg",
"scopeguard",
@ -853,15 +1007,15 @@ dependencies = [
[[package]]
name = "once_cell"
version = "1.12.0"
version = "1.15.0"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "7709cef83f0c1f58f666e746a08b21e0085f7440fa6a29cc194d68aac97a4225"
checksum = "e82dad04139b71a90c080c8463fe0dc7902db5192d939bd0950f074d014339e1"
[[package]]
name = "openssl"
version = "0.10.40"
version = "0.10.42"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "fb81a6430ac911acb25fe5ac8f1d2af1b4ea8a4fdfda0f1ee4292af2e2d8eb0e"
checksum = "12fc0523e3bd51a692c8850d075d74dc062ccf251c0110668cbd921917118a13"
dependencies = [
"bitflags",
"cfg-if 1.0.0",
@ -891,9 +1045,9 @@ checksum = "ff011a302c396a5197692431fc1948019154afc178baf7d8e37367442a4601cf"
[[package]]
name = "openssl-sys"
version = "0.9.74"
version = "0.9.76"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "835363342df5fba8354c5b453325b110ffd54044e588c539cf2f20a8014e4cb1"
checksum = "5230151e44c0f05157effb743e8d517472843121cf9243e8b81393edb5acd9ce"
dependencies = [
"autocfg",
"cc",
@ -918,7 +1072,7 @@ version = "0.12.1"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "3742b2c103b9f06bc9fff0a37ff4912935851bee6d36f3c02bcc755bcfec228f"
dependencies = [
"lock_api 0.4.7",
"lock_api 0.4.9",
"parking_lot_core 0.9.3",
]
@ -944,16 +1098,16 @@ checksum = "09a279cbf25cb0757810394fbc1e359949b59e348145c643a939a525692e6929"
dependencies = [
"cfg-if 1.0.0",
"libc",
"redox_syscall 0.2.13",
"redox_syscall 0.2.16",
"smallvec",
"windows-sys",
]
[[package]]
name = "percent-encoding"
version = "2.1.0"
version = "2.2.0"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "d4fd5641d01c8f18a23da7b6fe29298ff4b55afcccdf78973b24cf3175fee32e"
checksum = "478c572c3d73181ff3c2539045f6eb99e5491218eae919370993b890cdbdd98e"
[[package]]
name = "petgraph"
@ -1034,19 +1188,25 @@ source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "925383efa346730478fb4838dbe9137d2a47675ad789c546d150a6e1dd4ab31c"
[[package]]
name = "proc-macro2"
version = "1.0.40"
name = "proc-macro-hack"
version = "0.5.19"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "dd96a1e8ed2596c337f8eae5f24924ec83f5ad5ab21ea8e455d3566c69fbcaf7"
checksum = "dbf0c48bc1d91375ae5c3cd81e3722dff1abcf81a30960240640d223f59fe0e5"
[[package]]
name = "proc-macro2"
version = "1.0.46"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "94e2ef8dbfc347b10c094890f778ee2e36ca9bb4262e86dc99cd217e35f3470b"
dependencies = [
"unicode-ident",
]
[[package]]
name = "quote"
version = "1.0.20"
version = "1.0.21"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "3bcdf212e9776fbcb2d23ab029360416bb1706b1aea2d1a5ba002727cbcab804"
checksum = "bbe448f377a7d6961e30f5955f9b8d106c3f5e449d493ee1b125c1d43c2b5179"
dependencies = [
"proc-macro2",
]
@ -1086,9 +1246,9 @@ dependencies = [
[[package]]
name = "rand_core"
version = "0.6.3"
version = "0.6.4"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "d34f1408f55294453790c48b2f1ebbb1c5b4b7563eb1f418bcfcfdbb06ebb4e7"
checksum = "ec0be4795e2f6a28069bec0b5ff3e2ac9bafc99e6a9a7dc3547996c5c816922c"
dependencies = [
"getrandom",
]
@ -1101,9 +1261,9 @@ checksum = "41cc0f7e4d5d4544e8861606a285bb08d3e70712ccc7d2b84d7c0ccfaf4b05ce"
[[package]]
name = "redox_syscall"
version = "0.2.13"
version = "0.2.16"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "62f25bc4c7e55e0b0b7a1d43fb893f4fa1361d0abe38b9ce4f323c2adfe6ef42"
checksum = "fb5a58c1855b4b6819d59012155603f0b22ad30cad752600aadfcb695265519a"
dependencies = [
"bitflags",
]
@ -1115,15 +1275,15 @@ source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "b033d837a7cf162d7993aded9304e30a83213c648b6e389db233191f891e5c2b"
dependencies = [
"getrandom",
"redox_syscall 0.2.13",
"redox_syscall 0.2.16",
"thiserror",
]
[[package]]
name = "regex"
version = "1.5.6"
version = "1.6.0"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "d83f127d94bdbcda4c8cc2e50f6f84f4b611f69c902699ca385a39c3a75f9ff1"
checksum = "4c4eb3267174b8c6c2f654116623910a0fef09c4753f8dd83db29c48a0df988b"
dependencies = [
"aho-corasick",
"memchr 2.5.0",
@ -1132,9 +1292,9 @@ dependencies = [
[[package]]
name = "regex-syntax"
version = "0.6.26"
version = "0.6.27"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "49b3de9ec5dc0a3417da371aab17d729997c15010e7fd24ff707773a33bddb64"
checksum = "a3f87b73ce11b1619a3c6332f45341e0047173771e8b8b73f87bfeefb7b56244"
[[package]]
name = "remove_dir_all"
@ -1147,20 +1307,23 @@ dependencies = [
[[package]]
name = "rfc2047-decoder"
version = "0.1.2"
version = "0.2.0"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "87ecf2ba387f446155e26796aabb727e9ae1427dd13ac9cc21773a3fbda19d77"
checksum = "11347d014ae34e1d367aaf9191c37bf071b161e2e1c09c8559c7717e87030e11"
dependencies = [
"base64",
"charset",
"chumsky",
"memchr 2.5.0",
"quoted_printable",
"thiserror",
]
[[package]]
name = "ryu"
version = "1.0.10"
version = "1.0.11"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "f3f6f92acf49d1b98f7a81226834412ada05458b7364277387724a237f062695"
checksum = "4501abdff3ae82a1c1b477a17252eb69cee9e66eb915c1abaa4f44d873df9f09"
[[package]]
name = "schannel"
@ -1179,10 +1342,16 @@ source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "d29ab0c6d3fc0ee92fe66e2d99f700eab17a8d57d1c1d3b748380fb20baa78cd"
[[package]]
name = "security-framework"
version = "2.6.1"
name = "scratch"
version = "1.0.2"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "2dc14f172faf8a0194a3aded622712b0de276821addc574fa54fc0a1167e10dc"
checksum = "9c8132065adcfd6e02db789d9285a0deb2f3fcb04002865ab67d5fb103533898"
[[package]]
name = "security-framework"
version = "2.7.0"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "2bc1bb97804af6631813c55739f771071e0f2ed33ee20b68c86ec505d906356c"
dependencies = [
"bitflags",
"core-foundation",
@ -1203,18 +1372,18 @@ dependencies = [
[[package]]
name = "serde"
version = "1.0.138"
version = "1.0.145"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "1578c6245786b9d168c5447eeacfb96856573ca56c9d68fdcf394be134882a47"
checksum = "728eb6351430bccb993660dfffc5a72f91ccc1295abaa8ce19b27ebe4f75568b"
dependencies = [
"serde_derive",
]
[[package]]
name = "serde_derive"
version = "1.0.138"
version = "1.0.145"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "023e9b1467aef8a10fb88f25611870ada9800ef7e22afce356bb0d2387b6f27c"
checksum = "81fa1584d3d1bcacd84c277a0dfe21f5b0f6accf4a23d04d4c6d61f1af522b4c"
dependencies = [
"proc-macro2",
"quote",
@ -1223,9 +1392,9 @@ dependencies = [
[[package]]
name = "serde_json"
version = "1.0.82"
version = "1.0.86"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "82c2c1fdcd807d1098552c5b9a36e425e42e9fbd7c6a37a8425f390f781f7fa7"
checksum = "41feea4228a6f1cd09ec7a3593a682276702cd67b5273544757dae23c096f074"
dependencies = [
"itoa",
"ryu",
@ -1234,11 +1403,11 @@ dependencies = [
[[package]]
name = "shellexpand"
version = "2.1.0"
version = "2.1.2"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "83bdb7831b2d85ddf4a7b148aa19d0587eddbe8671a436b7bd1182eaad0f2829"
checksum = "7ccc8076840c4da029af4f87e4e8daeb0fca6b87bbb02e10cb60b791450e11e4"
dependencies = [
"dirs-next",
"dirs",
]
[[package]]
@ -1249,21 +1418,24 @@ checksum = "7bd3e3206899af3f8b12af284fafc038cc1dc2b41d1b89dd17297221c5d225de"
[[package]]
name = "slab"
version = "0.4.6"
version = "0.4.7"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "eb703cfe953bccee95685111adeedb76fabe4e97549a58d16f03ea7b9367bb32"
checksum = "4614a76b2a8be0058caa9dbbaf66d988527d86d003c11a94fbd335d7661edcef"
dependencies = [
"autocfg",
]
[[package]]
name = "smallvec"
version = "1.9.0"
version = "1.10.0"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "2fd0db749597d91ff862fd1d55ea87f7855a744a8425a64695b6fca237d1dad1"
checksum = "a507befe795404456341dfab10cef66ead4c041f62b8b11bbb92bffe5d0953e0"
[[package]]
name = "socket2"
version = "0.4.4"
version = "0.4.7"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "66d72b759436ae32898a2af0a14218dbf55efde3feeb170eb623637db85ee1e0"
checksum = "02e2d2db9033d13a1567121ddd7a095ee144db4e1ca1b1bda3419bc0da294ebd"
dependencies = [
"libc",
"winapi",
@ -1309,9 +1481,9 @@ checksum = "6446ced80d6c486436db5c078dde11a9f73d42b57fb273121e160b84f63d894c"
[[package]]
name = "syn"
version = "1.0.98"
version = "1.0.102"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "c50aef8a904de4c23c788f104b7dddc7d6f79c647c7c8ce4cc8f73eb0ca773dd"
checksum = "3fcd952facd492f9be3ef0d0b7032a6e442ee9b361d4acc2b1d0c4aaa5f613a1"
dependencies = [
"proc-macro2",
"quote",
@ -1333,7 +1505,7 @@ dependencies = [
"cfg-if 1.0.0",
"fastrand",
"libc",
"redox_syscall 0.2.13",
"redox_syscall 0.2.16",
"remove_dir_all",
"winapi",
]
@ -1379,18 +1551,18 @@ dependencies = [
[[package]]
name = "thiserror"
version = "1.0.31"
version = "1.0.37"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "bd829fe32373d27f76265620b5309d0340cb8550f523c1dda251d6298069069a"
checksum = "10deb33631e3c9018b9baf9dcbbc4f737320d2b576bac10f6aefa048fa407e3e"
dependencies = [
"thiserror-impl",
]
[[package]]
name = "thiserror-impl"
version = "1.0.31"
version = "1.0.37"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "0396bc89e626244658bef819e22d0cc459e795a5ebe878e6ec336d1674a8d79a"
checksum = "982d17546b47146b28f7c22e3d08465f6b8903d0ea13c1660d9d84a6e7adcdbb"
dependencies = [
"proc-macro2",
"quote",
@ -1408,6 +1580,15 @@ dependencies = [
"winapi",
]
[[package]]
name = "tiny-keccak"
version = "2.0.2"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "2c9d3793400a45f954c52e73d068316d76b6f4e36977e3fcebb13a2721e80237"
dependencies = [
"crunchy",
]
[[package]]
name = "tinyvec"
version = "1.6.0"
@ -1453,34 +1634,33 @@ checksum = "099b7128301d285f79ddd55b9a83d5e6b9e97c92e0ea0daebee7263e932de992"
[[package]]
name = "unicode-ident"
version = "1.0.1"
version = "1.0.5"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "5bd2fe26506023ed7b5e1e315add59d6f584c621d037f9368fea9cfb988f368c"
checksum = "6ceab39d59e4c9499d4e5a8ee0e2735b891bb7308ac83dfb4e80cad195c9f6f3"
[[package]]
name = "unicode-normalization"
version = "0.1.21"
version = "0.1.22"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "854cbdc4f7bc6ae19c820d44abdc3277ac3e1b2b93db20a636825d9322fb60e6"
checksum = "5c5713f0fc4b5db668a2ac63cdb7bb4469d8c9fed047b1d0292cc7b0ce2ba921"
dependencies = [
"tinyvec",
]
[[package]]
name = "unicode-width"
version = "0.1.9"
version = "0.1.10"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "3ed742d4ea2bd1176e236172c8429aaf54486e7ac098db29ffe6529e0ce50973"
checksum = "c0edd1e5b14653f783770bce4a4dabb4a5108a5370a5f5d8cfe8710c361f6c8b"
[[package]]
name = "url"
version = "2.2.2"
version = "2.3.1"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "a507c383b2d33b5fc35d1861e77e6b383d158b2da5e14fe51b83dfedf6fd578c"
checksum = "0d68c799ae75762b8c3fe375feb6600ef5602c883c5d21eb51c09f22b83c4643"
dependencies = [
"form_urlencoded",
"idna",
"matches",
"idna 0.3.0",
"percent-encoding",
]
@ -1490,6 +1670,17 @@ version = "0.7.6"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "09cc8ee72d2a9becf2f2febe0205bbed8fc6615b7cb429ad062dc7b7ddd036a9"
[[package]]
name = "utf7-imap"
version = "0.3.2"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "5e326365261fc2761f0809dfb6032810534a0427bbd8f0edf546f6afeef89f5d"
dependencies = [
"base64",
"encoding_rs",
"regex",
]
[[package]]
name = "utf8-width"
version = "0.1.6"
@ -1529,6 +1720,60 @@ version = "0.11.0+wasi-snapshot-preview1"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "9c8d87e72b64a3b4db28d11ce29237c246188f4f51057d65a7eab63b7987e423"
[[package]]
name = "wasm-bindgen"
version = "0.2.83"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "eaf9f5aceeec8be17c128b2e93e031fb8a4d469bb9c4ae2d7dc1888b26887268"
dependencies = [
"cfg-if 1.0.0",
"wasm-bindgen-macro",
]
[[package]]
name = "wasm-bindgen-backend"
version = "0.2.83"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "4c8ffb332579b0557b52d268b91feab8df3615f265d5270fec2a8c95b17c1142"
dependencies = [
"bumpalo",
"log",
"once_cell",
"proc-macro2",
"quote",
"syn",
"wasm-bindgen-shared",
]
[[package]]
name = "wasm-bindgen-macro"
version = "0.2.83"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "052be0f94026e6cbc75cdefc9bae13fd6052cdcaf532fa6c45e7ae33a1e6c810"
dependencies = [
"quote",
"wasm-bindgen-macro-support",
]
[[package]]
name = "wasm-bindgen-macro-support"
version = "0.2.83"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "07bc0c051dc5f23e307b13285f9d75df86bfdf816c5721e573dec1f9b8aa193c"
dependencies = [
"proc-macro2",
"quote",
"syn",
"wasm-bindgen-backend",
"wasm-bindgen-shared",
]
[[package]]
name = "wasm-bindgen-shared"
version = "0.2.83"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "1c38c045535d93ec4f0b4defec448e4291638ee608530863b1e2ba115d4fff7f"
[[package]]
name = "winapi"
version = "0.3.9"

View file

@ -1,7 +1,7 @@
[package]
name = "himalaya"
description = "Command-line interface for email management."
version = "0.6.0"
version = "0.6.1"
authors = ["soywod <clement.douin@posteo.net>"]
edition = "2021"
license = "MIT"
@ -16,47 +16,31 @@ priority = "optional"
section = "mail"
[features]
imap-backend = ["imap", "imap-proto"]
maildir-backend = ["maildir", "md5"]
notmuch-backend = ["himalaya-lib/notmuch-backend", "maildir-backend", "notmuch"]
imap-backend = ["himalaya-lib/imap-backend"]
maildir-backend = ["himalaya-lib/maildir-backend"]
notmuch-backend = ["himalaya-lib/notmuch-backend"]
default = ["imap-backend", "maildir-backend"]
[dev-dependencies]
tempfile = "3.3.0"
[dependencies]
ammonia = "3.1.2"
anyhow = "1.0.44"
atty = "0.2.14"
chrono = "0.4.19"
clap = { version = "2.33.3", default-features = false, features = ["suggestions", "color"] }
convert_case = "0.5.0"
env_logger = "0.8.3"
erased-serde = "0.3.18"
# himalaya-lib = { version = "=0.3.1", git = "https://git.sr.ht/~soywod/himalaya-lib", branch = "develop" }
himalaya-lib = "=0.3.1"
html-escape = "0.2.9"
himalaya-lib = "=0.4.0"
lettre = { version = "=0.10.0-rc.7", features = ["serde"] }
log = "0.4.14"
mailparse = "0.13.6"
native-tls = "0.2.8"
regex = "1.5.4"
rfc2047-decoder = "0.1.2"
serde = { version = "1.0.118", features = ["derive"] }
serde_json = "1.0.61"
shellexpand = "2.1.0"
termcolor = "1.1"
terminal_size = "0.1.15"
toml = "0.5.8"
tree_magic = "0.2.3"
unicode-width = "0.1.7"
url = "2.2.2"
uuid = { version = "0.8", features = ["v4"] }
# Optional dependencies:
imap = { version = "=3.0.0-alpha.4", optional = true }
imap-proto = { version = "0.14.3", optional = true }
maildir = { version = "0.6.1", optional = true }
md5 = { version = "0.7.0", optional = true }
notmuch = { version = "0.7.1", optional = true }

View file

@ -10,8 +10,8 @@ before the `v1.0.0`.*
## Installation
[![homebrew](https://img.shields.io/homebrew/v/himalaya?color=success&style=flat-square)](https://formulae.brew.sh/formula/himalaya)
[![crates](https://img.shields.io/crates/v/himalaya?color=success&style=flat-square)](https://crates.io/crates/himalaya)
[![Packaging
status](https://repology.org/badge/vertical-allrepos/himalaya.svg)](https://repology.org/project/himalaya/versions)
```sh
curl -sSL https://raw.githubusercontent.com/soywod/himalaya/master/install.sh | PREFIX=~/.local sh

View file

@ -18,6 +18,8 @@ struct SmtpConfigDef {
pub host: String,
#[serde(rename = "smtp-port")]
pub port: u16,
#[serde(rename = "smtp-ssl")]
pub ssl: Option<bool>,
#[serde(rename = "smtp-starttls")]
pub starttls: Option<bool>,
#[serde(rename = "smtp-insecure")]
@ -36,6 +38,8 @@ pub struct ImapConfigDef {
pub host: String,
#[serde(rename = "imap-port")]
pub port: u16,
#[serde(rename = "imap-ssl")]
pub ssl: Option<bool>,
#[serde(rename = "imap-starttls")]
pub starttls: Option<bool>,
#[serde(rename = "imap-insecure")]

View file

@ -21,6 +21,7 @@ const ARG_PAGE_SIZE: &str = "page-size";
const ARG_QUERY: &str = "query";
const ARG_RAW: &str = "raw";
const ARG_REPLY_ALL: &str = "reply-all";
const ARG_SANITIZE: &str = "sanitize";
const CMD_ATTACHMENTS: &str = "attachments";
const CMD_COPY: &str = "copy";
const CMD_DEL: &str = "delete";
@ -41,6 +42,7 @@ type Folder<'a> = &'a str;
type Page = usize;
type PageSize = usize;
type Query = String;
type Sanitize = bool;
type Raw = bool;
type RawEmail<'a> = &'a str;
type TextMime<'a> = &'a str;
@ -60,7 +62,7 @@ pub enum Cmd<'a> {
Forward(Id<'a>, Attachments<'a>, Encrypt),
List(table::args::MaxTableWidth, Option<PageSize>, Page),
Move(Id<'a>, Folder<'a>),
Read(Id<'a>, TextMime<'a>, Raw, Headers<'a>),
Read(Id<'a>, TextMime<'a>, Sanitize, Raw, Headers<'a>),
Reply(Id<'a>, All, Attachments<'a>, Encrypt),
Save(RawEmail<'a>),
Search(Query, table::args::MaxTableWidth, Option<PageSize>, Page),
@ -116,9 +118,10 @@ pub fn matches<'a>(m: &'a ArgMatches) -> Result<Option<Cmd<'a>>> {
debug!("read command matched");
let id = parse_id_arg(m);
let mime = parse_mime_type_arg(m);
let sanitize = parse_sanitize_flag(m);
let raw = parse_raw_flag(m);
let headers = parse_headers_arg(m);
Cmd::Read(id, mime, raw, headers)
Cmd::Read(id, mime, sanitize, raw, headers)
} else if let Some(m) = m.subcommand_matches(CMD_REPLY) {
debug!("reply command matched");
let id = parse_id_arg(m);
@ -210,9 +213,10 @@ pub fn subcmds<'a>() -> Vec<App<'a, 'a>> {
.about("Saves a raw email")
.arg(raw_arg()),
SubCommand::with_name(CMD_READ)
.about("Reads text bodies of a email")
.about("Reads text bodies of an email")
.arg(id_arg())
.arg(mime_type_arg())
.arg(sanitize_flag())
.arg(raw_flag())
.arg(headers_arg()),
SubCommand::with_name(CMD_REPLY)
@ -399,14 +403,27 @@ pub fn parse_headers_arg<'a>(matches: &'a ArgMatches<'a>) -> Vec<&'a str> {
matches.values_of(ARG_HEADERS).unwrap_or_default().collect()
}
/// Represents the sanitize flag.
pub fn sanitize_flag<'a>() -> Arg<'a, 'a> {
Arg::with_name(ARG_SANITIZE)
.help("Sanitizes text bodies")
.long("sanitize")
.short("s")
}
/// Represents the raw flag.
pub fn raw_flag<'a>() -> Arg<'a, 'a> {
Arg::with_name(ARG_RAW)
.help("Reads a raw email")
.help("Returns raw version of email")
.long("raw")
.short("r")
}
/// Represents the sanitize flag parser.
pub fn parse_sanitize_flag<'a>(matches: &'a ArgMatches<'a>) -> bool {
matches.is_present(ARG_SANITIZE)
}
/// Represents the raw flag parser.
pub fn parse_raw_flag<'a>(matches: &'a ArgMatches<'a>) -> bool {
matches.is_present(ARG_RAW)

View file

@ -5,7 +5,8 @@
use anyhow::{Context, Result};
use atty::Stream;
use himalaya_lib::{
AccountConfig, Backend, Email, Part, Parts, Sender, TextPlainPart, TplOverride,
AccountConfig, Backend, Email, Part, Parts, PartsReaderOptions, Sender, TextPlainPart,
TplOverride,
};
use log::{debug, info, trace};
use mailparse::addrparse;
@ -93,7 +94,7 @@ pub fn forward<'a, P: Printer, B: Backend<'a> + ?Sized, S: Sender + ?Sized>(
.into_forward(config)?
.add_attachments(attachments_paths)?
.encrypt(encrypt);
editor::edit_msg_with_editor(
editor::edit_email_with_editor(
msg,
TplOverride::default(),
config,
@ -184,7 +185,7 @@ pub fn mailto<'a, P: Printer, B: Backend<'a> + ?Sized, S: Sender + ?Sized>(
};
trace!("message: {:?}", msg);
editor::edit_msg_with_editor(
editor::edit_email_with_editor(
msg,
TplOverride::default(),
config,
@ -214,6 +215,7 @@ pub fn move_<'a, P: Printer, B: Backend<'a> + ?Sized>(
pub fn read<'a, P: Printer, B: Backend<'a> + ?Sized>(
seq: &str,
text_mime: &str,
sanitize: bool,
raw: bool,
headers: Vec<&str>,
mbox: &str,
@ -224,10 +226,18 @@ pub fn read<'a, P: Printer, B: Backend<'a> + ?Sized>(
let msg = backend.email_get(mbox, seq)?;
printer.print_struct(if raw {
// Emails don't always have valid utf8. Using "lossy" to display what we can.
// Emails do not always have valid utf8. Using "lossy" to
// display what we can.
String::from_utf8_lossy(&msg.raw).into_owned()
} else {
msg.to_readable_string(text_mime, headers, config)?
msg.to_readable(
config,
PartsReaderOptions {
plain_first: text_mime == "plain",
sanitize,
},
headers,
)?
})
}
@ -248,7 +258,7 @@ pub fn reply<'a, P: Printer, B: Backend<'a> + ?Sized, S: Sender + ?Sized>(
.into_reply(all, config)?
.add_attachments(attachments_paths)?
.encrypt(encrypt);
editor::edit_msg_with_editor(
editor::edit_email_with_editor(
msg,
TplOverride::default(),
config,
@ -341,7 +351,7 @@ pub fn sort<'a, P: Printer, B: Backend<'a> + ?Sized>(
/// Send a raw message.
pub fn send<'a, P: Printer, B: Backend<'a> + ?Sized, S: Sender + ?Sized>(
raw_msg: &str,
raw_email: &str,
config: &AccountConfig,
printer: &mut P,
backend: &mut B,
@ -357,8 +367,8 @@ pub fn send<'a, P: Printer, B: Backend<'a> + ?Sized, S: Sender + ?Sized>(
let sent_folder = config.folder_alias("sent")?;
debug!("sent folder: {:?}", sent_folder);
let raw_msg = if is_tty || is_json {
raw_msg.replace("\r", "").replace("\n", "\r\n")
let raw_email = if is_tty || is_json {
raw_email.replace("\r", "").replace("\n", "\r\n")
} else {
io::stdin()
.lock()
@ -367,10 +377,10 @@ pub fn send<'a, P: Printer, B: Backend<'a> + ?Sized, S: Sender + ?Sized>(
.collect::<Vec<String>>()
.join("\r\n")
};
trace!("raw message: {:?}", raw_msg);
let msg = Email::from_tpl(&raw_msg)?;
sender.send(&config, &msg)?;
backend.email_add(&sent_folder, raw_msg.as_bytes(), "seen")?;
trace!("raw message: {:?}", raw_email);
let email = Email::from_tpl(&raw_email)?;
sender.send(&email)?;
backend.email_add(&sent_folder, raw_email.as_bytes(), "seen")?;
Ok(())
}
@ -384,9 +394,9 @@ pub fn write<'a, P: Printer, B: Backend<'a> + ?Sized, S: Sender + ?Sized>(
backend: &mut B,
sender: &mut S,
) -> Result<()> {
let msg = Email::default()
let email = Email::default()
.add_attachments(attachments_paths)?
.encrypt(encrypt);
editor::edit_msg_with_editor(msg, tpl, config, printer, backend, sender)?;
editor::edit_email_with_editor(email, tpl, config, printer, backend, sender)?;
Ok(())
}

View file

@ -71,16 +71,15 @@ pub fn save<'a, P: Printer, B: Backend<'a> + ?Sized>(
.collect::<Vec<String>>()
.join("\n")
};
let msg = Email::from_tpl(&tpl)?.add_attachments(attachments_paths)?;
let raw_msg = msg.into_sendable_msg(config)?.formatted();
backend.email_add(mbox, &raw_msg, "seen")?;
let email = Email::from_tpl(&tpl)?.add_attachments(attachments_paths)?;
let raw_email = email.into_sendable(config)?.formatted();
backend.email_add(mbox, &raw_email, "seen")?;
printer.print_struct("Template successfully saved")
}
/// Sends a message based on a template.
pub fn send<'a, P: Printer, B: Backend<'a> + ?Sized, S: Sender + ?Sized>(
mbox: &str,
account: &AccountConfig,
attachments_paths: Vec<&str>,
tpl: &str,
printer: &mut P,
@ -97,8 +96,8 @@ pub fn send<'a, P: Printer, B: Backend<'a> + ?Sized, S: Sender + ?Sized>(
.collect::<Vec<String>>()
.join("\n")
};
let msg = Email::from_tpl(&tpl)?.add_attachments(attachments_paths)?;
let sent_msg = sender.send(account, &msg)?;
let email = Email::from_tpl(&tpl)?.add_attachments(attachments_paths)?;
let sent_msg = sender.send(&email)?;
backend.email_add(mbox, &sent_msg, "seen")?;
printer.print_struct("Template successfully sent")
}

View file

@ -161,10 +161,11 @@ fn main() -> Result<()> {
Some(email::args::Cmd::Move(seq, mbox_dst)) => {
return email::handlers::move_(seq, &folder, mbox_dst, &mut printer, backend.as_mut());
}
Some(email::args::Cmd::Read(seq, text_mime, raw, headers)) => {
Some(email::args::Cmd::Read(seq, text_mime, sanitize, raw, headers)) => {
return email::handlers::read(
seq,
text_mime,
sanitize,
raw,
headers,
&folder,
@ -302,7 +303,6 @@ fn main() -> Result<()> {
Some(tpl::args::Cmd::Send(atts, tpl)) => {
return tpl::handlers::send(
&folder,
&account_config,
atts,
tpl,
&mut printer,

View file

@ -37,14 +37,18 @@ pub fn open_with_draft() -> Result<String> {
open_with_tpl(tpl)
}
fn _edit_msg_with_editor(msg: &Email, tpl: TplOverride, config: &AccountConfig) -> Result<Email> {
let tpl = msg.to_tpl(tpl, config)?;
fn _edit_email_with_editor(
email: &Email,
tpl: TplOverride,
config: &AccountConfig,
) -> Result<Email> {
let tpl = email.to_tpl(tpl, config)?;
let tpl = open_with_tpl(tpl)?;
Email::from_tpl(&tpl).context("cannot parse message from template")
Email::from_tpl(&tpl).context("cannot parse email from template")
}
pub fn edit_msg_with_editor<'a, P: Printer, B: Backend<'a> + ?Sized, S: Sender + ?Sized>(
mut msg: Email,
pub fn edit_email_with_editor<'a, P: Printer, B: Backend<'a> + ?Sized, S: Sender + ?Sized>(
mut email: Email,
tpl: TplOverride,
config: &AccountConfig,
printer: &mut P,
@ -60,11 +64,11 @@ pub fn edit_msg_with_editor<'a, P: Printer, B: Backend<'a> + ?Sized, S: Sender +
Ok(choice) => match choice {
PreEditChoice::Edit => {
let tpl = open_with_draft()?;
msg.merge_with(Email::from_tpl(&tpl)?);
email.merge_with(Email::from_tpl(&tpl)?);
break;
}
PreEditChoice::Discard => {
msg.merge_with(_edit_msg_with_editor(&msg, tpl.clone(), config)?);
email.merge_with(_edit_email_with_editor(&email, tpl.clone(), config)?);
break;
}
PreEditChoice::Quit => return Ok(()),
@ -76,35 +80,35 @@ pub fn edit_msg_with_editor<'a, P: Printer, B: Backend<'a> + ?Sized, S: Sender +
}
}
} else {
msg.merge_with(_edit_msg_with_editor(&msg, tpl.clone(), config)?);
email.merge_with(_edit_email_with_editor(&email, tpl.clone(), config)?);
}
loop {
match choice::post_edit() {
Ok(PostEditChoice::Send) => {
printer.print_str("Sending message")?;
let sent_msg: Vec<u8> = sender.send(config, &msg)?;
printer.print_str("Sending email")?;
let sent_email: Vec<u8> = sender.send(&email)?;
let sent_folder = config.folder_alias("sent")?;
printer.print_str(format!("Adding message to the {:?} folder…", sent_folder))?;
backend.email_add(&sent_folder, &sent_msg, "seen")?;
printer.print_str(format!("Adding email to the {:?} folder…", sent_folder))?;
backend.email_add(&sent_folder, &sent_email, "seen")?;
remove_local_draft()?;
printer.print_struct("Done!")?;
break;
}
Ok(PostEditChoice::Edit) => {
msg.merge_with(_edit_msg_with_editor(&msg, tpl.clone(), config)?);
email.merge_with(_edit_email_with_editor(&email, tpl.clone(), config)?);
continue;
}
Ok(PostEditChoice::LocalDraft) => {
printer.print_struct("Message successfully saved locally")?;
printer.print_struct("Email successfully saved locally")?;
break;
}
Ok(PostEditChoice::RemoteDraft) => {
let tpl = msg.to_tpl(TplOverride::default(), config)?;
let draft_folder = config.folder_alias("draft")?;
let tpl = email.to_tpl(TplOverride::default(), config)?;
let draft_folder = config.folder_alias("drafts")?;
backend.email_add(&draft_folder, tpl.as_bytes(), "seen draft")?;
remove_local_draft()?;
printer.print_struct(format!("Message successfully saved to {}", draft_folder))?;
printer.print_struct(format!("Email successfully saved to {}", draft_folder))?;
break;
}
Ok(PostEditChoice::Discard) => {