ListStream touchup (#12524)

# Description

Does some misc changes to `ListStream`:
- Moves it into its own module/file separate from `RawStream`.
- `ListStream`s now have an associated `Span`.
- This required changes to `ListStreamInfo` in `nu-plugin`. Note sure if
this is a breaking change for the plugin protocol.
- Hides the internals of `ListStream` but also adds a few more methods.
- This includes two functions to more easily alter a stream (these take
a `ListStream` and return a `ListStream` instead of having to go through
the whole `into_pipeline_data(..)` route).
  -  `map`: takes a `FnMut(Value) -> Value`
  - `modify`: takes a function to modify the inner stream.
This commit is contained in:
Ian Manske
2024-05-05 16:00:59 +00:00
committed by GitHub
parent 3143ded374
commit e879d4ecaf
106 changed files with 957 additions and 874 deletions

View File

@ -183,7 +183,7 @@ pub trait InterfaceManager {
PipelineDataHeader::ListStream(info) => {
let handle = self.stream_manager().get_handle();
let reader = handle.read_stream(info.id, self.get_interface())?;
PipelineData::ListStream(ListStream::from_stream(reader, ctrlc.cloned()), None)
ListStream::new(reader, info.span, ctrlc.cloned()).into()
}
PipelineDataHeader::ExternalStream(info) => {
let handle = self.stream_manager().get_handle();
@ -203,7 +203,7 @@ pub trait InterfaceManager {
.map(|list_info| {
handle
.read_stream(list_info.id, self.get_interface())
.map(|reader| ListStream::from_stream(reader, ctrlc.cloned()))
.map(|reader| ListStream::new(reader, info.span, ctrlc.cloned()))
})
.transpose()?,
span: info.span,
@ -278,7 +278,10 @@ pub trait Interface: Clone + Send {
PipelineData::ListStream(stream, _) => {
let (id, writer) = new_stream(LIST_STREAM_HIGH_PRESSURE)?;
Ok((
PipelineDataHeader::ListStream(ListStreamInfo { id }),
PipelineDataHeader::ListStream(ListStreamInfo {
id,
span: stream.span(),
}),
PipelineDataWriter::ListStream(writer, stream),
))
}
@ -316,7 +319,7 @@ pub trait Interface: Clone + Send {
.map(|(stream, (id, _))| RawStreamInfo::new(*id, stream)),
exit_code: exit_code_stream
.as_ref()
.map(|&(id, _)| ListStreamInfo { id }),
.map(|&(id, _)| ListStreamInfo { id, span }),
trim_end_newline,
});
// Collect the writers

View File

@ -161,7 +161,10 @@ fn read_pipeline_data_list_stream() -> Result<(), ShellError> {
}
test.add(StreamMessage::End(7));
let header = PipelineDataHeader::ListStream(ListStreamInfo { id: 7 });
let header = PipelineDataHeader::ListStream(ListStreamInfo {
id: 7,
span: Span::test_data(),
});
let pipe = manager.read_pipeline_data(header, None)?;
assert!(
@ -221,7 +224,10 @@ fn read_pipeline_data_external_stream() -> Result<(), ShellError> {
is_binary: true,
known_size: None,
}),
exit_code: Some(ListStreamInfo { id: 14 }),
exit_code: Some(ListStreamInfo {
id: 14,
span: Span::test_data(),
}),
trim_end_newline: true,
});
@ -273,7 +279,10 @@ fn read_pipeline_data_external_stream() -> Result<(), ShellError> {
}
assert_eq!(iterations, count, "stderr length");
assert_eq!(vec![Value::test_int(1)], exit_code.collect::<Vec<_>>());
assert_eq!(
vec![Value::test_int(1)],
exit_code.into_iter().collect::<Vec<_>>()
);
}
_ => panic!("unexpected PipelineData: {pipe:?}"),
}
@ -284,30 +293,13 @@ fn read_pipeline_data_external_stream() -> Result<(), ShellError> {
Ok(())
}
#[test]
fn read_pipeline_data_ctrlc() -> Result<(), ShellError> {
let manager = TestInterfaceManager::new(&TestCase::new());
let header = PipelineDataHeader::ListStream(ListStreamInfo { id: 0 });
let ctrlc = Default::default();
match manager.read_pipeline_data(header, Some(&ctrlc))? {
PipelineData::ListStream(
ListStream {
ctrlc: stream_ctrlc,
..
},
_,
) => {
assert!(Arc::ptr_eq(&ctrlc, &stream_ctrlc.expect("ctrlc not set")));
Ok(())
}
_ => panic!("Unexpected PipelineData, should have been ListStream"),
}
}
#[test]
fn read_pipeline_data_prepared_properly() -> Result<(), ShellError> {
let manager = TestInterfaceManager::new(&TestCase::new());
let header = PipelineDataHeader::ListStream(ListStreamInfo { id: 0 });
let header = PipelineDataHeader::ListStream(ListStreamInfo {
id: 0,
span: Span::test_data(),
});
match manager.read_pipeline_data(header, None)? {
PipelineData::ListStream(_, meta) => match meta {
Some(PipelineMetadata { data_source }) => match data_source {
@ -404,7 +396,7 @@ fn write_pipeline_data_list_stream() -> Result<(), ShellError> {
// Set up pipeline data for a list stream
let pipe = PipelineData::ListStream(
ListStream::from_stream(values.clone().into_iter(), None),
ListStream::new(values.clone().into_iter(), Span::test_data(), None),
None,
);
@ -474,8 +466,9 @@ fn write_pipeline_data_external_stream() -> Result<(), ShellError> {
span,
None,
)),
exit_code: Some(ListStream::from_stream(
exit_code: Some(ListStream::new(
std::iter::once(exit_code.clone()),
Span::test_data(),
None,
)),
span,