mirror of
https://github.com/nushell/nushell.git
synced 2025-08-16 04:47:53 +02:00
A bunch of rework
I'm gonna use a VecDeque now instead of trying to get async streams working to make progress, but the intent is that we should be able to use async streams in and out to interleave the work better.
This commit is contained in:
@ -1,20 +1,60 @@
|
||||
use crate::object::Value;
|
||||
use crate::ShellError;
|
||||
use derive_new::new;
|
||||
use std::cell::Cell;
|
||||
use std::collections::VecDeque;
|
||||
|
||||
#[derive(Debug, Default)]
|
||||
pub struct ObjectStream {
|
||||
queue: VecDeque<Value>,
|
||||
#[derive(Debug)]
|
||||
pub enum LogLevel {
|
||||
Trace,
|
||||
Debug,
|
||||
Info,
|
||||
Warn,
|
||||
Error,
|
||||
Fatal,
|
||||
}
|
||||
|
||||
#[derive(Debug)]
|
||||
pub struct LogItem {
|
||||
level: LogLevel,
|
||||
value: Value,
|
||||
}
|
||||
|
||||
#[derive(Debug, Default)]
|
||||
pub struct ObjectStream<T> {
|
||||
queue: VecDeque<T>,
|
||||
}
|
||||
|
||||
impl<T> ObjectStream<T> {
|
||||
crate fn empty() -> ObjectStream<T> {
|
||||
ObjectStream {
|
||||
queue: VecDeque::new(),
|
||||
}
|
||||
}
|
||||
|
||||
crate fn iter(&self) -> impl Iterator<Item = &T> {
|
||||
self.queue.iter()
|
||||
}
|
||||
|
||||
crate fn take(&mut self) -> Option<T> {
|
||||
self.queue.pop_front()
|
||||
}
|
||||
|
||||
crate fn add(&mut self, value: T) {
|
||||
self.queue.push_back(value);
|
||||
}
|
||||
}
|
||||
|
||||
#[derive(new)]
|
||||
pub struct Streams {
|
||||
success: Cell<ObjectStream>,
|
||||
// error: ObjectStream,
|
||||
// warning: ObjectStream,
|
||||
// debug: ObjectStream,
|
||||
// trace: ObjectStream,
|
||||
// verbose: ObjectStream,
|
||||
#[new(value = "ObjectStream::empty()")]
|
||||
success: ObjectStream<Value>,
|
||||
|
||||
#[new(value = "ObjectStream::empty()")]
|
||||
errors: ObjectStream<ShellError>,
|
||||
|
||||
#[new(value = "ObjectStream::empty()")]
|
||||
log: ObjectStream<LogItem>,
|
||||
}
|
||||
|
||||
impl std::fmt::Debug for Streams {
|
||||
@ -24,16 +64,12 @@ impl std::fmt::Debug for Streams {
|
||||
}
|
||||
|
||||
impl Streams {
|
||||
crate fn new() -> Streams {
|
||||
Streams {
|
||||
success: Cell::new(ObjectStream::default()),
|
||||
}
|
||||
crate fn read(&mut self) -> Option<Value> {
|
||||
self.success.take()
|
||||
}
|
||||
|
||||
crate fn take_success(&mut self) -> Cell<ObjectStream> {
|
||||
let new_stream = Cell::new(ObjectStream::default());
|
||||
self.success.swap(&new_stream);
|
||||
new_stream
|
||||
crate fn add(&mut self, value: Value) {
|
||||
self.success.add(value);
|
||||
}
|
||||
|
||||
// fn take_stream(&mut self, stream: &mut ObjectStream) -> ObjectStream {
|
||||
|
@ -1,6 +1,7 @@
|
||||
use crate::errors::ShellError;
|
||||
use crate::object::process::Process;
|
||||
use crate::object::{DirEntry, ShellObject, Value};
|
||||
use crate::prelude::*;
|
||||
use crate::Args;
|
||||
use derive_new::new;
|
||||
use std::path::{Path, PathBuf};
|
||||
@ -12,13 +13,13 @@ pub struct CdBlueprint;
|
||||
impl crate::CommandBlueprint for CdBlueprint {
|
||||
fn create(
|
||||
&self,
|
||||
args: Args,
|
||||
host: &dyn crate::Host,
|
||||
env: &mut crate::Environment,
|
||||
) -> Result<Box<dyn crate::Command>, ShellError> {
|
||||
args: Vec<Value>,
|
||||
host: &dyn Host,
|
||||
env: &mut Environment,
|
||||
) -> Result<Box<dyn Command>, ShellError> {
|
||||
let target = match args.first() {
|
||||
// TODO: This needs better infra
|
||||
None => return Err(ShellError::new(format!("cd must take one arg"))),
|
||||
None => return Err(ShellError::string(format!("cd must take one arg"))),
|
||||
Some(v) => v.as_string()?.clone(),
|
||||
};
|
||||
|
||||
@ -36,12 +37,10 @@ pub struct Cd {
|
||||
}
|
||||
|
||||
impl crate::Command for Cd {
|
||||
fn run(&mut self) -> Result<crate::CommandSuccess, ShellError> {
|
||||
Ok(crate::CommandSuccess {
|
||||
value: Value::nothing(),
|
||||
action: vec![crate::CommandAction::ChangeCwd(dunce::canonicalize(
|
||||
self.cwd.join(&self.target).as_path(),
|
||||
)?)],
|
||||
})
|
||||
fn run(&mut self, stream: VecDeque<Value>) -> Result<VecDeque<ReturnValue>, ShellError> {
|
||||
let mut stream = VecDeque::new();
|
||||
let path = dunce::canonicalize(self.cwd.join(&self.target).as_path())?;
|
||||
stream.push_back(ReturnValue::change_cwd(path));
|
||||
Ok(stream)
|
||||
}
|
||||
}
|
||||
|
@ -1,31 +1,38 @@
|
||||
use crate::errors::ShellError;
|
||||
use crate::object::Value;
|
||||
use crate::prelude::*;
|
||||
use std::path::PathBuf;
|
||||
|
||||
pub trait CommandBlueprint {
|
||||
fn create(
|
||||
&self,
|
||||
input: crate::Args,
|
||||
input: Vec<Value>,
|
||||
host: &dyn crate::Host,
|
||||
env: &mut crate::Environment,
|
||||
) -> Result<Box<dyn Command>, ShellError>;
|
||||
}
|
||||
|
||||
crate enum CommandAction {
|
||||
pub enum CommandAction {
|
||||
ChangeCwd(PathBuf),
|
||||
}
|
||||
|
||||
pub struct CommandSuccess {
|
||||
crate value: Value,
|
||||
crate action: Vec<CommandAction>,
|
||||
pub enum ReturnValue {
|
||||
Value(Value),
|
||||
Action(CommandAction),
|
||||
}
|
||||
|
||||
impl ReturnValue {
|
||||
crate fn single(value: Value) -> VecDeque<ReturnValue> {
|
||||
let mut v = VecDeque::new();
|
||||
v.push_back(ReturnValue::Value(value));
|
||||
v
|
||||
}
|
||||
|
||||
crate fn change_cwd(path: PathBuf) -> ReturnValue {
|
||||
ReturnValue::Action(CommandAction::ChangeCwd(path))
|
||||
}
|
||||
}
|
||||
|
||||
pub trait Command {
|
||||
fn begin(&mut self) -> Result<(), ShellError> {
|
||||
Ok(())
|
||||
}
|
||||
fn run(&mut self) -> Result<CommandSuccess, ShellError>;
|
||||
fn end(&mut self) -> Result<(), ShellError> {
|
||||
Ok(())
|
||||
}
|
||||
fn run(&mut self, stream: VecDeque<Value>) -> Result<VecDeque<ReturnValue>, ShellError>;
|
||||
}
|
||||
|
@ -1,8 +1,9 @@
|
||||
use crate::errors::ShellError;
|
||||
use crate::object::process::Process;
|
||||
use crate::object::{DirEntry, ShellObject, Value};
|
||||
use crate::prelude::*;
|
||||
use crate::Args;
|
||||
use crate::{Command, CommandSuccess};
|
||||
use crate::Command;
|
||||
use derive_new::new;
|
||||
use std::path::PathBuf;
|
||||
use sysinfo::SystemExt;
|
||||
@ -13,7 +14,7 @@ pub struct LsBlueprint;
|
||||
impl crate::CommandBlueprint for LsBlueprint {
|
||||
fn create(
|
||||
&self,
|
||||
args: Args,
|
||||
args: Vec<Value>,
|
||||
host: &dyn crate::Host,
|
||||
env: &mut crate::Environment,
|
||||
) -> Result<Box<dyn Command>, ShellError> {
|
||||
@ -29,20 +30,17 @@ pub struct Ls {
|
||||
}
|
||||
|
||||
impl crate::Command for Ls {
|
||||
fn run(&mut self) -> Result<CommandSuccess, ShellError> {
|
||||
fn run(&mut self, stream: VecDeque<Value>) -> Result<VecDeque<ReturnValue>, ShellError> {
|
||||
let entries =
|
||||
std::fs::read_dir(&self.cwd).map_err((|e| ShellError::new(format!("{:?}", e))))?;
|
||||
std::fs::read_dir(&self.cwd).map_err((|e| ShellError::string(format!("{:?}", e))))?;
|
||||
|
||||
let mut shell_entries = vec![];
|
||||
let mut shell_entries = VecDeque::new();
|
||||
|
||||
for entry in entries {
|
||||
let value = Value::object(DirEntry::new(entry?)?);
|
||||
shell_entries.push(value)
|
||||
shell_entries.push_back(ReturnValue::Value(value))
|
||||
}
|
||||
|
||||
Ok(CommandSuccess {
|
||||
value: Value::list(shell_entries),
|
||||
action: vec![],
|
||||
})
|
||||
Ok(shell_entries)
|
||||
}
|
||||
}
|
||||
|
@ -1,6 +1,7 @@
|
||||
use crate::errors::ShellError;
|
||||
use crate::object::process::Process;
|
||||
use crate::object::{ShellObject, Value};
|
||||
use crate::prelude::*;
|
||||
use crate::Command;
|
||||
use derive_new::new;
|
||||
use std::cell::RefCell;
|
||||
@ -15,7 +16,7 @@ pub struct PsBlueprint {
|
||||
impl crate::CommandBlueprint for PsBlueprint {
|
||||
fn create(
|
||||
&self,
|
||||
args: crate::Args,
|
||||
args: Vec<Value>,
|
||||
host: &dyn crate::Host,
|
||||
env: &mut crate::Environment,
|
||||
) -> Result<Box<dyn Command>, ShellError> {
|
||||
@ -29,7 +30,7 @@ pub struct Ps {
|
||||
}
|
||||
|
||||
impl crate::Command for Ps {
|
||||
fn run(&mut self) -> Result<crate::CommandSuccess, ShellError> {
|
||||
fn run(&mut self, stream: VecDeque<Value>) -> Result<VecDeque<ReturnValue>, ShellError> {
|
||||
let mut system = self.system.borrow_mut();
|
||||
system.refresh_all();
|
||||
|
||||
@ -37,13 +38,12 @@ impl crate::Command for Ps {
|
||||
|
||||
let list = list
|
||||
.into_iter()
|
||||
.map(|(_, process)| Value::Object(Box::new(Process::new(process.clone()))))
|
||||
.map(|(_, process)| {
|
||||
ReturnValue::Value(Value::Object(Box::new(Process::new(process.clone()))))
|
||||
})
|
||||
.take(5)
|
||||
.collect();
|
||||
.collect::<VecDeque<_>>();
|
||||
|
||||
Ok(crate::CommandSuccess {
|
||||
value: Value::List(list),
|
||||
action: vec![],
|
||||
})
|
||||
Ok(list)
|
||||
}
|
||||
}
|
||||
|
Reference in New Issue
Block a user