use std::ffi::OsStr;
use super::command_items::CommandItems;
use crate::formats::argv::ArgvItem;
use crate::formats::argv::ArgvRedactionWriter;
use crate::formats::env::EnvRedactionWriter;
use crate::runtime::TextSession;
use crate::runtime::runtime_session::RuntimeSession;
pub struct ProcessRedactionWriter<'session> {
session: &'session mut TextSession,
}
impl<'session> ProcessRedactionWriter<'session> {
#[inline(always)]
#[must_use]
pub(crate) const fn new(session: &'session mut TextSession) -> Self {
Self { session }
}
pub fn command<'arguments, 'variables, A, E>(
&mut self,
program: &'arguments OsStr,
arguments: A,
variables: E,
) -> &mut Self
where
A: IntoIterator<Item = ArgvItem<'arguments>>,
E: IntoIterator<Item = (&'variables OsStr, &'variables OsStr)>,
{
if self.session.skip_aggregate_for_exhausted_output() {
return self;
}
let arguments = arguments.into_iter();
let mut argv = ArgvRedactionWriter::new(self.session);
argv.heuristic_items(CommandItems::new(ArgvItem::plain(program), arguments));
if self.session.skip_aggregate_for_exhausted_output() {
return self;
}
let mut environment = EnvRedactionWriter::new(self.session);
environment.os_pairs(variables);
self
}
pub fn arguments<'arguments, A>(&mut self, arguments: A) -> &mut Self
where
A: IntoIterator<Item = ArgvItem<'arguments>>,
{
let mut argv = ArgvRedactionWriter::new(self.session);
argv.heuristic_items(arguments);
self
}
pub fn variables<'variables, E>(&mut self, variables: E) -> &mut Self
where
E: IntoIterator<Item = (&'variables OsStr, &'variables OsStr)>,
{
let mut env = EnvRedactionWriter::new(self.session);
env.os_pairs(variables);
self
}
}
#[cfg(test)]
mod tests {
use std::ffi::OsStr;
use super::ProcessRedactionWriter;
use crate::Redactor;
use crate::formats::argv::ArgvItem;
#[test]
fn test_command_appends_redacted_argv_and_environment_to_parent_session() {
let arguments = [
ArgvItem::plain(OsStr::new("--password")),
ArgvItem::plain(OsStr::new("argv-secret")),
];
let variables = [(OsStr::new("PASSWORD"), OsStr::new("env-secret"))];
let mut session = Redactor::strict().text_runtime();
let mut process = ProcessRedactionWriter::new(&mut session);
process.command(OsStr::new("client"), arguments, variables);
let output = session.finish();
assert!(!output.text().as_str().contains("argv-secret"));
assert!(!output.text().as_str().contains("env-secret"));
}
}