From 39a42868ab7560f63b9634b61f31bac1ac93b000 Mon Sep 17 00:00:00 2001 From: Kevin Matthes <92332892+kevinmatthes@users.noreply.github.com> Date: Sun, 11 Feb 2024 15:22:32 +0100 Subject: [PATCH 1/7] Added ::= PathBufLikeAppendix --- src/writing.rs | 103 +++++++++++++++++++++++++++++++++++++++++++++++++ 1 file changed, 103 insertions(+) diff --git a/src/writing.rs b/src/writing.rs index 330c44c..75fa6cb 100644 --- a/src/writing.rs +++ b/src/writing.rs @@ -20,6 +20,109 @@ use std::{io::Write, path::PathBuf}; use sysexits::Result; +/// Append to the files given as instances convertible to a +/// [`std::path::PathBuf`]. +pub trait PathBufLikeAppendix +where + PathBuf: From, +{ + /// Append the data this method is called on to the given destination. + /// + /// This method behaves just like + /// [`crate::PathBufLikeAppendix::append_silently`] despite also printing + /// error messages to [`std::io::Stderr`]. + /// + /// # Errors + /// + /// See [`sysexits::ExitCode`]. + fn append_loudly(self, destination: T) -> Result<()>; + + /// Append the data this method is called on to the given destination. + /// + /// The data this method is called on will be converted to a [`String`] and + /// appended to the given file. The data therefore needs to implement + /// [`ToString`]. The file needs to be convertible to a + /// [`std::path::PathBuf`]. The data will be appended at the end of the + /// file, already existing data will not be changed. In case that the file + /// should not already exist, it will be created before writing to it. + /// + /// The return value is either the unit type, in case of success, or a + /// [`sysexits::ExitCode`] to describe the error cause, otherwise. + /// + /// Error messages are not written to [`std::io::Stderr`]. + /// + /// # Errors + /// + /// See [`sysexits::ExitCode`]. + fn append_silently(self, destination: T) -> Result<()>; +} + +impl PathBufLikeAppendix

for T +where + PathBuf: From

, +{ + fn append_loudly(self, destination: P) -> Result<()> { + match std::fs::File::options() + .append(true) + .create(true) + .truncate(false) + .write(true) + .open(PathBuf::from(destination)) + { + Err(e) => { + eprintln!("{e}"); + Err(e.into()) + } + Ok(mut file) => { + let bytes = self.to_string().as_bytes().to_vec(); + + match file.write(&bytes) { + Err(e) => { + eprintln!("{e}"); + Err(e.into()) + } + Ok(n) => { + if n == bytes.len() { + Ok(()) + } else { + eprintln!( + "Creating an exact copy was not possible." + ); + Err(sysexits::ExitCode::IoErr) + } + } + } + } + } + } + + fn append_silently(self, destination: P) -> Result<()> { + match std::fs::File::options() + .append(true) + .create(true) + .truncate(false) + .write(true) + .open(PathBuf::from(destination)) + { + Err(e) => Err(e.into()), + Ok(mut file) => { + let bytes = self.to_string().as_bytes().to_vec(); + + match file.write(&bytes) { + Err(e) => Err(e.into()), + Ok(n) => { + if n == bytes.len() { + Ok(()) + } else { + Err(sysexits::ExitCode::IoErr) + } + } + } + } + } + } +} + /// Truncate files given as instances convertible to a [`std::path::PathBuf`]. pub trait PathBufLikeTruncation where From 81ec0d8382b5ebf6d46dd0428b9ea97487bd93e9 Mon Sep 17 00:00:00 2001 From: Kevin Matthes <92332892+kevinmatthes@users.noreply.github.com> Date: Sun, 11 Feb 2024 15:23:04 +0100 Subject: [PATCH 2/7] Added ::= PathBufLikeAppendix::append_silently --- src/lib.rs | 4 +++- 1 file changed, 3 insertions(+), 1 deletion(-) diff --git a/src/lib.rs b/src/lib.rs index c546ed3..fe03e79 100644 --- a/src/lib.rs +++ b/src/lib.rs @@ -134,7 +134,9 @@ mod writing; pub use reading::{ BufReadReader, OptionReader, PathBufLikeReader, VectorReader, }; -pub use writing::{OptionTruncation, PathBufLikeTruncation, Writer}; +pub use writing::{ + OptionTruncation, PathBufLikeAppendix, PathBufLikeTruncation, Writer, +}; /// This crate's name. pub const NAME: &str = "aeruginous-io"; From b7d3b4d7d8fb63a221440d89f4488c4aa3c481e8 Mon Sep 17 00:00:00 2001 From: Kevin Matthes <92332892+kevinmatthes@users.noreply.github.com> Date: Sun, 11 Feb 2024 15:35:37 +0100 Subject: [PATCH 3/7] Added ::= PathBufLikaAppendix::append_loudly --- src/writing.rs | 2 -- 1 file changed, 2 deletions(-) diff --git a/src/writing.rs b/src/writing.rs index 75fa6cb..97cab2d 100644 --- a/src/writing.rs +++ b/src/writing.rs @@ -66,7 +66,6 @@ where .append(true) .create(true) .truncate(false) - .write(true) .open(PathBuf::from(destination)) { Err(e) => { @@ -101,7 +100,6 @@ where .append(true) .create(true) .truncate(false) - .write(true) .open(PathBuf::from(destination)) { Err(e) => Err(e.into()), From 7a8a5aa11fea3e5fe0c068a1d9f369e627f28b72 Mon Sep 17 00:00:00 2001 From: Kevin Matthes <92332892+kevinmatthes@users.noreply.github.com> Date: Sun, 11 Feb 2024 15:38:11 +0100 Subject: [PATCH 4/7] Changed ::= MSRV: 1.76.0 --- tests/reading.rs | 82 ++++++++++++++++++++++++------------------------ 1 file changed, 41 insertions(+), 41 deletions(-) diff --git a/tests/reading.rs b/tests/reading.rs index 075ad4f..e93dddd 100644 --- a/tests/reading.rs +++ b/tests/reading.rs @@ -53,41 +53,40 @@ mod buf_read_reader { } } -mod path_buf_like_reader { - use aeruginous_io::PathBufLikeReader; +mod option_reader { + use aeruginous_io::OptionReader; #[test] - fn method_result_equality() { + fn method_result_equality_none() { assert_eq!( - "tests/assets/GPL-3.0.rs".read_loudly().unwrap(), - "tests/assets/GPL-3.0.rs".read_silently().unwrap(), + None::<&str>.read_loudly(&b"test"[..]).unwrap(), + None::<&str>.read_silently(&b"test"[..]).unwrap() ); } #[test] - fn read_loudly_failure_attempt_to_read_directory() { - assert!(".github/".read_loudly().is_err()); - } - - #[test] - fn read_loudly_failure_file_does_not_exist() { - assert!("no_such_file.txt".read_loudly().is_err()); - } - - #[test] - fn read_silently_failure_attempt_to_read_directory() { - assert!(".github/".read_silently().is_err()); + fn method_result_equality_some() { + assert_eq!( + Some("tests/assets/GPL-3.0.rs") + .read_loudly(&b""[..]) + .unwrap(), + Some("tests/assets/GPL-3.0.rs") + .read_silently(&b""[..]) + .unwrap(), + ); } #[test] - fn read_silently_failure_file_does_not_exist() { - assert!("no_such_file.txt".read_silently().is_err()); + fn read_silently_success_none() { + assert_eq!(None::<&str>.read_silently(&b"test"[..]).unwrap(), "test\n"); } #[test] - fn read_silently_success() { + fn read_silently_success_some() { assert_eq!( - "tests/assets/GPL-3.0.rs".read_silently().unwrap(), + Some("tests/assets/GPL-3.0.rs") + .read_silently(&b""[..]) + .unwrap(), "\ /// Copyright (C) 2024 Kevin Matthes /// @@ -108,40 +107,41 @@ mod path_buf_like_reader { } } -mod option_reader { - use aeruginous_io::OptionReader; +mod path_buf_like_reader { + use aeruginous_io::PathBufLikeReader; #[test] - fn method_result_equality_none() { + fn method_result_equality() { assert_eq!( - None::<&str>.read_loudly(&b"test"[..]).unwrap(), - None::<&str>.read_silently(&b"test"[..]).unwrap() + "tests/assets/GPL-3.0.rs".read_loudly().unwrap(), + "tests/assets/GPL-3.0.rs".read_silently().unwrap(), ); } #[test] - fn method_result_equality_some() { - assert_eq!( - Some("tests/assets/GPL-3.0.rs") - .read_loudly(&b""[..]) - .unwrap(), - Some("tests/assets/GPL-3.0.rs") - .read_silently(&b""[..]) - .unwrap(), - ); + fn read_loudly_failure_attempt_to_read_directory() { + assert!(".github/".read_loudly().is_err()); } #[test] - fn read_silently_success_none() { - assert_eq!(None::<&str>.read_silently(&b"test"[..]).unwrap(), "test\n"); + fn read_loudly_failure_file_does_not_exist() { + assert!("no_such_file.txt".read_loudly().is_err()); } #[test] - fn read_silently_success_some() { + fn read_silently_failure_attempt_to_read_directory() { + assert!(".github/".read_silently().is_err()); + } + + #[test] + fn read_silently_failure_file_does_not_exist() { + assert!("no_such_file.txt".read_silently().is_err()); + } + + #[test] + fn read_silently_success() { assert_eq!( - Some("tests/assets/GPL-3.0.rs") - .read_silently(&b""[..]) - .unwrap(), + "tests/assets/GPL-3.0.rs".read_silently().unwrap(), "\ /// Copyright (C) 2024 Kevin Matthes /// From 8a194d10f8d54b406b918187f3fc40e55b8b8799 Mon Sep 17 00:00:00 2001 From: Kevin Matthes <92332892+kevinmatthes@users.noreply.github.com> Date: Sun, 11 Feb 2024 15:38:58 +0100 Subject: [PATCH 5/7] Added ::= tests for PathBufLikeAppendix --- tests/writing.rs | 38 ++++++++++++++++++++++++++++++++++++++ 1 file changed, 38 insertions(+) diff --git a/tests/writing.rs b/tests/writing.rs index 1bf33d3..f82d38f 100644 --- a/tests/writing.rs +++ b/tests/writing.rs @@ -17,6 +17,44 @@ | | \******************************************************************************/ +mod path_buf_like_appendix { + use aeruginous_io::{PathBufLikeAppendix, PathBufLikeReader}; + + #[test] + fn append_loudly_failure() { + assert!(String::new().append_loudly("tests/").is_err()); + } + + #[test] + fn append_loudly_success() { + let f = "path_buf_like_appendix_append_loudly_success.txt"; + + assert!("test line 1\n".append_loudly(f).is_ok()); + assert_eq!(f.read_silently().unwrap(), "test line 1\n"); + assert!("test line 2\n".append_loudly(f).is_ok()); + assert_eq!(f.read_silently().unwrap(), "test line 1\ntest line 2\n"); + + std::fs::remove_file(f).unwrap(); + } + + #[test] + fn append_silently_failure() { + assert!(String::new().append_silently("tests/").is_err()); + } + + #[test] + fn append_silently_success() { + let f = "path_buf_like_appendix_append_silently_success.txt"; + + assert!("test line 1\n".append_silently(f).is_ok()); + assert_eq!(f.read_silently().unwrap(), "test line 1\n"); + assert!("test line 2\n".append_silently(f).is_ok()); + assert_eq!(f.read_silently().unwrap(), "test line 1\ntest line 2\n"); + + std::fs::remove_file(f).unwrap(); + } +} + mod path_buf_like_io { use aeruginous_io::{PathBufLikeReader, PathBufLikeTruncation}; From 506e37e5c865ef5ac83471116ff2bcdf76022b76 Mon Sep 17 00:00:00 2001 From: GitHub Actions <41898282+github-actions[bot]@users.noreply.github.com> Date: Sun, 11 Feb 2024 15:01:58 +0000 Subject: [PATCH 6/7] Create summary of recent changes --- ...50158_GitHub_Actions_path-buf-like-appendix.ron | 14 ++++++++++++++ 1 file changed, 14 insertions(+) create mode 100644 changelog.d/20240211_150158_GitHub_Actions_path-buf-like-appendix.ron diff --git a/changelog.d/20240211_150158_GitHub_Actions_path-buf-like-appendix.ron b/changelog.d/20240211_150158_GitHub_Actions_path-buf-like-appendix.ron new file mode 100644 index 0000000..7c32854 --- /dev/null +++ b/changelog.d/20240211_150158_GitHub_Actions_path-buf-like-appendix.ron @@ -0,0 +1,14 @@ +( + references: {}, + changes: { + "Added": [ + "PathBufLikaAppendix::append_loudly", + "PathBufLikeAppendix", + "PathBufLikeAppendix::append_silently", + "tests for PathBufLikeAppendix", + ], + "Changed": [ + "MSRV: 1.76.0", + ], + }, +) From 1ca61a92c91e018aebd3606fa4671794dbdc2351 Mon Sep 17 00:00:00 2001 From: Kevin Matthes <92332892+kevinmatthes@users.noreply.github.com> Date: Sun, 11 Feb 2024 16:06:06 +0100 Subject: [PATCH 7/7] Skip ::= fix typo --- .../20240211_150158_GitHub_Actions_path-buf-like-appendix.ron | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/changelog.d/20240211_150158_GitHub_Actions_path-buf-like-appendix.ron b/changelog.d/20240211_150158_GitHub_Actions_path-buf-like-appendix.ron index 7c32854..7e4e002 100644 --- a/changelog.d/20240211_150158_GitHub_Actions_path-buf-like-appendix.ron +++ b/changelog.d/20240211_150158_GitHub_Actions_path-buf-like-appendix.ron @@ -2,7 +2,7 @@ references: {}, changes: { "Added": [ - "PathBufLikaAppendix::append_loudly", + "PathBufLikeAppendix::append_loudly", "PathBufLikeAppendix", "PathBufLikeAppendix::append_silently", "tests for PathBufLikeAppendix",